diff --git a/src/util/color.js b/src/util/color.js index 733ca99ff083..4520864b1466 100644 --- a/src/util/color.js +++ b/src/util/color.js @@ -13,6 +13,9 @@ let RGB = new RegExp( let HSL = new RegExp( `^(hsla?)\\(\\s*((?:${VALUE.source})(?:deg|rad|grad|turn)?|${CUSTOM_PROPERTY.source})(?:${SEP.source}(${VALUE.source}|${CUSTOM_PROPERTY.source}))?(?:${SEP.source}(${VALUE.source}|${CUSTOM_PROPERTY.source}))?(?:${ALPHA_SEP.source}(${VALUE.source}|${CUSTOM_PROPERTY.source}))?\\s*\\)$` ) +let OTHER_MODES = new RegExp( + `^(lch|lab|oklab|oklch)\\(\\s*(${VALUE.source}|${CUSTOM_PROPERTY.source})(?:${SEP.source}(${VALUE.source}|${CUSTOM_PROPERTY.source}))?(?:${SEP.source}(${VALUE.source}|${CUSTOM_PROPERTY.source}))?(?:${ALPHA_SEP.source}(${VALUE.source}|${CUSTOM_PROPERTY.source}))?\\s*\\)$` +) // In "loose" mode the color may contain fewer than 3 parts, as long as at least // one of the parts is variable. @@ -44,7 +47,7 @@ export function parseColor(value, { loose = false } = {}) { } } - let match = value.match(RGB) ?? value.match(HSL) + let match = value.match(RGB) ?? value.match(HSL) ?? value.match(OTHER_MODES) if (match === null) { return null diff --git a/tests/color.test.js b/tests/color.test.js index 659a2d045b51..dd6ee059025d 100644 --- a/tests/color.test.js +++ b/tests/color.test.js @@ -60,6 +60,10 @@ describe('parseColor', () => { ${'rgba(var(--foo), var(--alpha))'} | ${{ mode: 'rgba', color: ['var(--foo)'], alpha: 'var(--alpha)' }} ${'hsla(var(--foo), 0.1)'} | ${{ mode: 'hsla', color: ['var(--foo)'], alpha: '0.1' }} ${'hsla(var(--foo), var(--alpha))'} | ${{ mode: 'hsla', color: ['var(--foo)'], alpha: 'var(--alpha)' }} + ${'lch(0% 30 60)'} | ${{ mode: 'lch', color: ['0%', '30', '60'], alpha: undefined }} + ${'lab(0% 30 60 / 0.5)'} | ${{ mode: 'lab', color: ['0%', '30', '60'], alpha: '0.5' }} + ${'oklch(0% 30 var(--foo) / 0.5)'} | ${{ mode: 'oklch', color: ['0%', '30', 'var(--foo)'], alpha: '0.5' }} + ${'oklab(0% 30 var(--foo) / var(--alpha))'} | ${{ mode: 'oklab', color: ['0%', '30', 'var(--foo)'], alpha: 'var(--alpha)' }} ${'transparent'} | ${{ mode: 'rgb', color: ['0', '0', '0'], alpha: '0' }} `('should parse "$color" to the correct value', ({ color, output }) => { expect(parseColor(color)).toEqual(output) @@ -78,6 +82,17 @@ describe('parseColor', () => { }) }) +describe('parseColorLoose', () => { + it.each` + color | output + ${'hsl(var(--foo) / var(--alpha))'} | ${{ mode: 'hsl', color: ['var(--foo)'], alpha: 'var(--alpha)' }} + ${'oklch(var(--foo) / 0.5)'} | ${{ mode: 'oklch', color: ['var(--foo)'], alpha: '0.5' }} + ${'oklab(var(--foo) / var(--alpha))'} | ${{ mode: 'oklab', color: ['var(--foo)'], alpha: 'var(--alpha)' }} + `('should parse "$color" to the correct value', ({ color, output }) => { + expect(parseColor(color, { loose: true })).toEqual(output) + }) +}) + describe('formatColor', () => { it.each` color | output