fix: isDark() utility can receive null value (#3774)

* Make isDark() not fail as easily with invalid input

Add early return if input looks fishy, minor refactoring and improvements of the entire method.

* Fix double quotes

* Run prettier 🙄

* chore: review

Signed-off-by: Sami Mazouz <sychocouldy@gmail.com>

---------

Signed-off-by: Sami Mazouz <sychocouldy@gmail.com>
Co-authored-by: Sami Mazouz <sychocouldy@gmail.com>
This commit is contained in:
luk 2023-04-22 10:45:51 +02:00 committed by GitHub
parent e55844f3db
commit f8577c8078
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 13 additions and 7 deletions

View File

@ -1,5 +1,5 @@
import isDark from '../utils/isDark';
export default function textContrastClass(hexcolor: string): string {
export default function textContrastClass(hexcolor: string | null): string {
return isDark(hexcolor) ? 'text-contrast--light' : 'text-contrast--dark';
}

View File

@ -7,19 +7,25 @@
* standards, but we use a custom threshold for each light and dark modes
* to preserve design consistency.
*/
export default function isDark(hexcolor: string): boolean {
export default function isDark(hexcolor: string | null): boolean {
// return if hexcolor is undefined or shorter than 4 characters, shortest hex form is #333;
// decided against regex hex color validation for performance considerations
if (!hexcolor || hexcolor.length < 4) {
return false;
}
let hexnumbers = hexcolor.replace('#', '');
if (hexnumbers.length == 3) {
if (hexnumbers.length === 3) {
hexnumbers += hexnumbers;
}
const r = parseInt(hexnumbers.substr(0, 2), 16);
const g = parseInt(hexnumbers.substr(2, 2), 16);
const b = parseInt(hexnumbers.substr(4, 2), 16);
const r = parseInt(hexnumbers.slice(0, 2), 16);
const g = parseInt(hexnumbers.slice(2, 4), 16);
const b = parseInt(hexnumbers.slice(4, 6), 16);
const yiq = (r * 299 + g * 587 + b * 114) / 1000;
const threshold = parseInt(window.getComputedStyle(document.body).getPropertyValue('--yiq-threshold'));
const threshold = parseInt(getComputedStyle(document.body).getPropertyValue('--yiq-threshold').trim()) || 128;
return yiq < threshold;
}