Skip to content

Commit

Permalink
Merge pull request #1 from asamuzaK/initial
Browse files Browse the repository at this point in the history
  • Loading branch information
asamuzaK authored Jan 27, 2024
2 parents 10c27d0 + 2312cf9 commit cd4b901
Show file tree
Hide file tree
Showing 5 changed files with 85 additions and 31 deletions.
20 changes: 15 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,10 +44,20 @@ Resolve CSS color.
* `opt.key` **any?** key e.g. CSS property `background-color`

Returns **([string][93]? | [Array][96])** `rgba?()`, `[r, g, b, a]`, `#rrggbb(aa)?`, `null`, or if `key` is specified, `[key, rgba?()|[r, g, b, a]|#rrggbb(aa)?|null]`
* In `rgb`, `r`, `g`, `b` values are rounded.
* In `array`, values are floats.
* In `hex`, `transparent` keyword resolves as `null`, `currentcolor` as `#000000` if `opt.currentColor` not specified.
* In `hexAlpha`, `transparent` keyword resolves as `#00000000`, `currentcolor` as `#00000000` if `opt.currentColor` not specified.
* In `rgb`:
* `r`, `g`, `b` values are rounded.
* Returns empty string for unknown / unsupported color name.
* In `array`:
* Values are floats.
* Returns array filled with undefined for unknown / unsupported color name, i.e. `[undefined, undefined, undefined, undefined]`.
* In `hex`:
* `transparent` returns `null`.
* Also returns `null` for unknown / unsupported color name.
* `currentcolor` resolves as `#000000` if `opt.currentColor` is not specified.
* In `hexAlpha`:
* `transparent` resolves as `#00000000`.
* `currentcolor` resolves as `#00000000` if `opt.currentColor` is not specified.
* Returns `null` for unknown / unsupported color name.


### parse
Expand All @@ -57,7 +67,7 @@ Parse CSS color.
#### Parameters

* `color` **[string][93]** color value
* `color-mix()` and [<system-color>](https://developer.mozilla.org/en-US/docs/Web/CSS/system-color)s are not supported
* `color-mix()` and [<system-color>](https://developer.mozilla.org/en-US/docs/Web/CSS/system-color)s are not supported. It throws.
* `opt` **[object][94]?** options
* `opt.d50` **[boolean][95]?** get xyz values in d50 white point

Expand Down
37 changes: 25 additions & 12 deletions src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,17 +16,22 @@ import { getType, isString } from './js/common.js';
/**
* resolve CSS color
* @param {string} color - color value
* - system colors are not supported
* - system colors are not supported
* @param {object} [opt] - options
* @param {string} [opt.currentColor] - color to use for 'currentcolor' keyword
* @param {string} [opt.format] - 'rgb'(default), 'array', 'hex' or 'hexAlpha'
* - 'hexAlpha' is a hex color notation with alpha channel, i.e. #rrggbbaa
* @param {string} [opt.currentColor] - color to use for `currentcolor` keyword
* @param {string} [opt.format] - `rgb`(default), `array`, `hex` or `hexAlpha`
* - `hexAlpha` is a hex color notation with alpha channel, i.e. #rrggbbaa
* @param {*} [opt.key] - key e.g. CSS property `background-color`
* @returns {?string|Array} - rgba?(), [r, g, b, a], #rrggbb(aa)?, null
* - if `key` is specified, [key, rgba?()|[r, g, b, a]|#rrggbb(aa)?|null]
* - in 'rgb', 'r', 'g', 'b' values are rounded
* - in 'array', values are floating point
* - in 'hex', 'transparent' resolves as 'null'
* - in `rgb`, `r`, `g`, `b` values are rounded,
* resolves as empty string if any of `r`, `g`, `b`, `a` is not a number
* - in `array`, values are floating point,
* if any of `r`, `g`, `b`, `a` is not a number then they stay as is,
* e.g. [undefined, undefined, undefined, undefined]
* - in `hex`, `transparent` resolves as `null`,
* also resolves as `null` if any of `r`, `g`, `b`, `a` is not a number
* - in `hexAlpha`, resolves as `null` if any of `r`, `g`, `b`, `a` is not a number
*/
export const resolve = (color, opt = {}) => {
if (isString(color)) {
Expand Down Expand Up @@ -75,7 +80,7 @@ export const resolve = (color, opt = {}) => {
}
case 'hex': {
let hex;
if (/^transparent$/i.test(color)) {
if (/^transparent$/i.test(color) || isNaN(r) || isNaN(g) || isNaN(b)) {
hex = null;
} else {
hex = convertRgbToHex([r, g, b]);
Expand All @@ -91,6 +96,8 @@ export const resolve = (color, opt = {}) => {
let hex;
if (/^transparent$/i.test(color)) {
hex = '#00000000';
} else if (isNaN(r) || isNaN(g) || isNaN(b) || isNaN(a)) {
hex = null;
} else {
hex = convertRgbToHex([r, g, b, a]);
}
Expand All @@ -103,11 +110,17 @@ export const resolve = (color, opt = {}) => {
}
default: {
let rgb;
if (a === 1) {
rgb = `rgb(${Math.round(r)}, ${Math.round(g)}, ${Math.round(b)})`;
if (isNaN(r) || isNaN(g) || isNaN(b) || isNaN(a)) {
rgb = '';
} else {
rgb =
`rgba(${Math.round(r)}, ${Math.round(g)}, ${Math.round(b)}, ${a})`;
r = Math.round(r);
g = Math.round(g);
b = Math.round(b);
if (a === 1) {
rgb = `rgb(${r}, ${g}, ${b})`;
} else {
rgb = `rgba(${r}, ${g}, ${b}, ${a})`;
}
}
if (key) {
res = [key, rgb];
Expand Down
24 changes: 12 additions & 12 deletions src/js/color.js
Original file line number Diff line number Diff line change
Expand Up @@ -1805,12 +1805,6 @@ export const resolveColorValue = value => {
g = 0;
b = 0;
a = 0;
// initial
} else {
r = 0;
g = 0;
b = 0;
a = 1;
}
// hex-color
} else if (value.startsWith('#')) {
Expand Down Expand Up @@ -1843,12 +1837,18 @@ export const resolveColorValue = value => {
} else if (value.startsWith('hwb')) {
[r, g, b, a] = parseHwb(value);
}
return [
Math.round(r),
Math.round(g),
Math.round(b),
a
];
let res;
if (isNaN(r) || isNaN(g) || isNaN(b) || isNaN(a)) {
res = [];
} else {
res = [
Math.round(r),
Math.round(g),
Math.round(b),
a
];
}
return res;
};

/**
Expand Down
4 changes: 2 additions & 2 deletions test/color.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -4283,9 +4283,9 @@ describe('resolve color value', () => {
'Expected String but got Undefined.');
});

it('should get null', () => {
it('should get empty array', () => {
const res = func('foo');
assert.deepEqual(res, [0, 0, 0, 1], 'result');
assert.deepEqual(res, [], 'result');
});

it('should get value', () => {
Expand Down
31 changes: 31 additions & 0 deletions test/index.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,11 @@ describe('resolve CSS color', () => {
'Expected String but got Undefined.');
});

it('should get empty string', () => {
const res = func('foo');
assert.strictEqual(res, '', 'result');
});

it('should get value', () => {
const res = func('currentColor', {
currentColor: 'color-mix(in srgb, blue, red)'
Expand Down Expand Up @@ -75,6 +80,18 @@ describe('resolve CSS color', () => {
assert.deepEqual(res, ['foo', 'rgb(128, 0, 128)'], 'result');
});

it('should get value', () => {
const res = func('foo)', {
format: 'array'
});
assert.deepEqual(res, [
undefined,
undefined,
undefined,
undefined
], 'result');
});

it('should get value', () => {
const res = func('color-mix(in srgb, blue, red)', {
format: 'array'
Expand All @@ -97,6 +114,13 @@ describe('resolve CSS color', () => {
assert.isNull(res, 'result');
});

it('should get null', () => {
const res = func('foo', {
format: 'hex'
});
assert.isNull(res, 'result');
});

it('should get value', () => {
const res = func('rgba(0% 50% 0% / 0.5)', {
format: 'hex'
Expand Down Expand Up @@ -126,6 +150,13 @@ describe('resolve CSS color', () => {
assert.strictEqual(res, '#00000000', 'result');
});

it('should get null', () => {
const res = func('foo', {
format: 'hexAlpha'
});
assert.isNull(res, 'result');
});

it('should get value', () => {
const res = func('rgba(0% 50% 0% / 0.5)', {
format: 'hexAlpha'
Expand Down

0 comments on commit cd4b901

Please sign in to comment.