@@ -8,9 +8,7 @@ use std::num::{Float, FloatMath};
8
8
9
9
use text_writer:: { mod, TextWriter } ;
10
10
11
- use ast:: { ComponentValue , SkipWhitespaceIterable } ;
12
- use ast:: ComponentValue :: { Number , Percentage , Function , Ident , Hash , IDHash , Comma } ;
13
- use serializer:: ToCss ;
11
+ use super :: { Token , Parser , ToCss } ;
14
12
15
13
16
14
#[ deriving( Clone , PartialEq ) ]
@@ -66,13 +64,18 @@ impl fmt::Show for Color {
66
64
67
65
/// Return `Err(())` on invalid or unsupported value (not a color).
68
66
impl Color {
69
- pub fn parse ( component_value : & ComponentValue ) -> Result < Color , ( ) > {
70
- match * component_value {
71
- Hash ( ref value) | IDHash ( ref value) => parse_color_hash ( value. as_slice ( ) ) ,
72
- Ident ( ref value) => parse_color_keyword ( value. as_slice ( ) ) ,
73
- Function ( ref name, ref arguments)
74
- => parse_color_function ( name. as_slice ( ) , arguments. as_slice ( ) ) ,
75
- _ => Err ( ( ) )
67
+ pub fn parse ( input : & mut Parser ) -> Result < Color , ( ) > {
68
+ match try!( input. next ( ) ) {
69
+ Token :: Hash ( ref value) | Token :: IDHash ( ref value) => {
70
+ parse_color_hash ( value. as_slice ( ) )
71
+ }
72
+ Token :: Ident ( ref value) => parse_color_keyword ( value. as_slice ( ) ) ,
73
+ Token :: Function ( ref name) => {
74
+ input. parse_nested_block ( ) . parse_entirely ( |arguments| {
75
+ parse_color_function ( name. as_slice ( ) , arguments)
76
+ } )
77
+ }
78
+ token => input. unexpected ( token)
76
79
}
77
80
}
78
81
}
@@ -279,70 +282,43 @@ fn parse_color_hash(value: &str) -> Result<Color, ()> {
279
282
280
283
281
284
#[ inline]
282
- fn parse_color_function ( name : & str , arguments : & [ ComponentValue ] )
283
- -> Result < Color , ( ) > {
284
- let lower_name = name. to_ascii_lower ( ) ;
285
- let lower_name = lower_name. as_slice ( ) ;
286
-
285
+ fn parse_color_function ( name : & str , arguments : & mut Parser ) -> Result < Color , ( ) > {
287
286
let ( is_rgb, has_alpha) =
288
- if "rgba" == lower_name { ( true , true ) }
289
- else if "rgb" == lower_name { ( true , false ) }
290
- else if "hsl" == lower_name { ( false , false ) }
291
- else if "hsla" == lower_name { ( false , true ) }
287
+ if name . eq_ignore_ascii_case ( "rgba" ) { ( true , true ) }
288
+ else if name . eq_ignore_ascii_case ( "rgb" ) { ( true , false ) }
289
+ else if name . eq_ignore_ascii_case ( "hsl" ) { ( false , false ) }
290
+ else if name . eq_ignore_ascii_case ( "hsla" ) { ( false , true ) }
292
291
else { return Err ( ( ) ) } ;
293
292
294
- let mut iter = arguments. skip_whitespace ( ) ;
295
- macro_rules! expect_comma(
296
- ( ) => ( match iter. next( ) { Some ( & Comma ) => { } , _ => { return Err ( ( ) ) } } ) ;
297
- )
298
- macro_rules! expect_percentage(
299
- ( ) => ( match iter. next( ) {
300
- Some ( & Percentage ( ref v) ) => v. value,
301
- _ => return Err ( ( ) ) ,
302
- } ) ;
303
- )
304
- macro_rules! expect_integer(
305
- ( ) => ( match iter. next( ) {
306
- Some ( & Number ( ref v) ) if v. int_value. is_some( ) => v. value,
307
- _ => return Err ( ( ) ) ,
308
- } ) ;
309
- )
310
- macro_rules! expect_number(
311
- ( ) => ( match iter. next( ) {
312
- Some ( & Number ( ref v) ) => v. value,
313
- _ => return Err ( ( ) ) ,
314
- } ) ;
315
- )
316
-
317
293
let red: f32 ;
318
294
let green: f32 ;
319
295
let blue: f32 ;
320
296
if is_rgb {
321
297
// Either integers or percentages, but all the same type.
322
- match iter . next ( ) {
323
- Some ( & Number ( ref v) ) if v. int_value . is_some ( ) => {
298
+ match try! ( arguments . next ( ) ) {
299
+ Token :: Number ( ref v) if v. int_value . is_some ( ) => {
324
300
red = ( v. value / 255. ) as f32 ;
325
- expect_comma ! ( ) ;
326
- green = ( expect_integer ! ( ) / 255. ) as f32 ;
327
- expect_comma ! ( ) ;
328
- blue = ( expect_integer ! ( ) / 255. ) as f32 ;
301
+ try! ( arguments . expect_comma ( ) ) ;
302
+ green = try! ( arguments . expect_integer ( ) ) as f32 / 255. ;
303
+ try! ( arguments . expect_comma ( ) ) ;
304
+ blue = try! ( arguments . expect_integer ( ) ) as f32 / 255. ;
329
305
}
330
- Some ( & Percentage ( ref v) ) => {
306
+ Token :: Percentage ( ref v) => {
331
307
red = ( v. value / 100. ) as f32 ;
332
- expect_comma ! ( ) ;
333
- green = ( expect_percentage ! ( ) / 100. ) as f32 ;
334
- expect_comma ! ( ) ;
335
- blue = ( expect_percentage ! ( ) / 100. ) as f32 ;
308
+ try! ( arguments . expect_comma ( ) ) ;
309
+ green = ( try! ( arguments . expect_percentage ( ) ) / 100. ) as f32 ;
310
+ try! ( arguments . expect_comma ( ) ) ;
311
+ blue = ( try! ( arguments . expect_percentage ( ) ) / 100. ) as f32 ;
336
312
}
337
313
_ => return Err ( ( ) )
338
314
} ;
339
315
} else {
340
- let hue = expect_number ! ( ) / 360. ;
316
+ let hue = try! ( arguments . expect_number ( ) ) / 360. ;
341
317
let hue = hue - hue. floor ( ) ;
342
- expect_comma ! ( ) ;
343
- let saturation = ( expect_percentage ! ( ) / 100. ) . max ( 0. ) . min ( 1. ) ;
344
- expect_comma ! ( ) ;
345
- let lightness = ( expect_percentage ! ( ) / 100. ) . max ( 0. ) . min ( 1. ) ;
318
+ try! ( arguments . expect_comma ( ) ) ;
319
+ let saturation = ( try! ( arguments . expect_percentage ( ) ) / 100. ) . max ( 0. ) . min ( 1. ) ;
320
+ try! ( arguments . expect_comma ( ) ) ;
321
+ let lightness = ( try! ( arguments . expect_percentage ( ) ) / 100. ) . max ( 0. ) . min ( 1. ) ;
346
322
347
323
// http://www.w3.org/TR/css3-color/#hsl-color
348
324
fn hue_to_rgb ( m1 : f64 , m2 : f64 , mut h : f64 ) -> f64 {
@@ -363,14 +339,11 @@ fn parse_color_function(name: &str, arguments: &[ComponentValue])
363
339
}
364
340
365
341
let alpha = if has_alpha {
366
- expect_comma ! ( ) ;
367
- ( expect_number ! ( ) ) . max ( 0. ) . min ( 1. ) as f32
342
+ try! ( arguments . expect_comma ( ) ) ;
343
+ ( try! ( arguments . expect_number ( ) ) ) . max ( 0. ) . min ( 1. ) as f32
368
344
} else {
369
345
1.
370
346
} ;
371
- if iter. next ( ) . is_none ( ) {
372
- Ok ( Color :: RGBA ( RGBA { red : red, green : green, blue : blue, alpha : alpha } ) )
373
- } else {
374
- Err ( ( ) )
375
- }
347
+ try!( arguments. expect_exhausted ( ) ) ;
348
+ Ok ( Color :: RGBA ( RGBA { red : red, green : green, blue : blue, alpha : alpha } ) )
376
349
}
0 commit comments