@@ -84,7 +84,7 @@ export function parseHexColor(text: string, start: number = 0): Parsed<ARGB> {
84
84
85
85
function rgbaToArgbNumber ( r : number , g : number , b : number , a : number = 1 ) : number | undefined {
86
86
if ( r >= 0 && r <= 255 && g >= 0 && g <= 255 && b >= 0 && b <= 255 && a >= 0 && a <= 1 ) {
87
- return ( Math . round ( a * 0xFF ) * 0x01000000 ) + ( r * 0x010000 ) + ( g * 0x000100 ) + ( b * 0x000001 ) ;
87
+ return ( Math . round ( a * 0xFF ) * 0x01000000 ) + ( r * 0x010000 ) + ( g * 0x000100 ) + b ;
88
88
} else {
89
89
return null ;
90
90
}
@@ -116,6 +116,67 @@ export function parseRGBAColor(text: string, start: number = 0): Parsed<ARGB> {
116
116
return { start, end, value } ;
117
117
}
118
118
119
+ export function convertHSLToRGBColor ( hue : number , saturation : number , lightness : number ) : { r : number ; g : number ; b : number ; } {
120
+ // Per formula it will be easier if hue is divided to 60° and saturation to 100 beforehand
121
+ // https://en.wikipedia.org/wiki/HSL_and_HSV#HSL_to_RGB
122
+ hue /= 60 ;
123
+ lightness /= 100 ;
124
+
125
+ let chroma = ( 1 - Math . abs ( 2 * lightness - 1 ) ) * saturation / 100 ,
126
+ X = chroma * ( 1 - Math . abs ( hue % 2 - 1 ) ) ,
127
+ // Add lightness match to all RGB components beforehand
128
+ { m : r , m : g , m : b } = { m : lightness - chroma / 2 } ;
129
+
130
+ if ( 0 <= hue && hue < 1 ) { r += chroma ; g += X ; }
131
+ else if ( hue < 2 ) { r += X ; g += chroma ; }
132
+ else if ( hue < 3 ) { g += chroma ; b += X ; }
133
+ else if ( hue < 4 ) { g += X ; b += chroma ; }
134
+ else if ( hue < 5 ) { r += X ; b += chroma ; }
135
+ else if ( hue < 6 ) { r += chroma ; b += X ; }
136
+
137
+ return {
138
+ r : Math . round ( r * 0xFF ) ,
139
+ g : Math . round ( g * 0xFF ) ,
140
+ b : Math . round ( b * 0xFF )
141
+ } ;
142
+ }
143
+
144
+ function hslaToArgbNumber ( h : number , s : number , l : number , a : number = 1 ) : number | undefined {
145
+ let { r, g, b } = convertHSLToRGBColor ( h , s , l ) ;
146
+
147
+ if ( r >= 0 && r <= 255 && g >= 0 && g <= 255 && b >= 0 && b <= 255 && a >= 0 && a <= 1 ) {
148
+ return ( Math . round ( a * 0xFF ) * 0x01000000 ) + ( r * 0x010000 ) + ( g * 0x000100 ) + b ;
149
+ } else {
150
+ return null ;
151
+ }
152
+ }
153
+
154
+ const hslColorRegEx = / \s * ( h s l \( \s * ( [ \d . ] * ) \s * , \s * ( [ \d . ] * ) % \s * , \s * ( [ \d . ] * ) % \s * \) ) / gy;
155
+ export function parseHSLColor ( text : string , start : number = 0 ) : Parsed < ARGB > {
156
+ hslColorRegEx . lastIndex = start ;
157
+ const result = hslColorRegEx . exec ( text ) ;
158
+ if ( ! result ) {
159
+ return null ;
160
+ }
161
+ const end = hslColorRegEx . lastIndex ;
162
+ const value = result [ 1 ] && hslaToArgbNumber ( parseFloat ( result [ 2 ] ) , parseFloat ( result [ 3 ] ) , parseFloat ( result [ 4 ] ) ) ;
163
+
164
+ return { start, end, value } ;
165
+ }
166
+
167
+ const hslaColorRegEx = / \s * ( h s l a \( \s * ( [ \d . ] * ) \s * , \s * ( [ \d . ] * ) % \s * , \s * ( [ \d . ] * ) % \s * , \s * ( [ 0 1 ] ? \. ? \d * ) \s * \) ) / gy;
168
+ export function parseHSLAColor ( text : string , start : number = 0 ) : Parsed < ARGB > {
169
+ hslaColorRegEx . lastIndex = start ;
170
+ const result = hslaColorRegEx . exec ( text ) ;
171
+ if ( ! result ) {
172
+ return null ;
173
+ }
174
+ const end = hslaColorRegEx . lastIndex ;
175
+ const value = hslaToArgbNumber ( parseFloat ( result [ 2 ] ) , parseFloat ( result [ 3 ] ) , parseFloat ( result [ 4 ] ) , parseFloat ( result [ 5 ] ) ) ;
176
+
177
+ return { start, end, value } ;
178
+ }
179
+
119
180
export enum colors {
120
181
transparent = 0x00000000 ,
121
182
aliceblue = 0xFFF0F8FF ,
@@ -280,7 +341,12 @@ export function parseColorKeyword(value, start: number, keyword = parseKeyword(v
280
341
}
281
342
282
343
export function parseColor ( value : string , start : number = 0 , keyword = parseKeyword ( value , start ) ) : Parsed < ARGB > {
283
- return parseHexColor ( value , start ) || parseColorKeyword ( value , start , keyword ) || parseRGBColor ( value , start ) || parseRGBAColor ( value , start ) ;
344
+ return parseHexColor ( value , start ) ||
345
+ parseColorKeyword ( value , start , keyword ) ||
346
+ parseRGBColor ( value , start ) ||
347
+ parseRGBAColor ( value , start ) || <
2851
/div>
348
+ parseHSLColor ( value , start ) ||
349
+ parseHSLAColor ( value , start ) ;
284
350
}
285
351
286
352
const keywordRegEx = / \s * ( [ a - z ] [ \w \- ] * ) \s * / giy;
0 commit comments