aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSimon Sapin <simon.sapin@exyr.org>2017-03-07 15:58:13 +0100
committerSimon Sapin <simon.sapin@exyr.org>2017-03-07 23:37:26 +0100
commitda6316fbe34bca671685b6a5153525162729c246 (patch)
treed2a8a1d66ea0a17f8a0e2669e96f9225b41da1b9
parentb11847d86c4983b76a8e8dc11716dc66b66148d7 (diff)
downloadservo-da6316fbe34bca671685b6a5153525162729c246.tar.gz
servo-da6316fbe34bca671685b6a5153525162729c246.zip
Return shorthand decarations as a new enum, don’t push them to a Vec.
-rw-r--r--components/style/properties/helpers.mako.rs39
-rw-r--r--components/style/properties/properties.mako.rs66
2 files changed, 74 insertions, 31 deletions
diff --git a/components/style/properties/helpers.mako.rs b/components/style/properties/helpers.mako.rs
index b85f9de75db..e2f182e3fcb 100644
--- a/components/style/properties/helpers.mako.rs
+++ b/components/style/properties/helpers.mako.rs
@@ -339,7 +339,7 @@
input.reset(start);
let (first_token_type, css) = try!(
::custom_properties::parse_non_custom_with_var(input));
- return Ok(DeclaredValue::WithVariables(Box::new(UnparsedValue {
+ return Ok(DeclaredValue::WithVariables(Arc::new(UnparsedValue {
css: css.into_owned(),
first_token_type: first_token_type,
base_url: context.base_url.clone(),
@@ -483,10 +483,10 @@
#[allow(unused_imports)]
use cssparser::Parser;
use parser::ParserContext;
- use properties::{DeclaredValue, PropertyDeclaration};
+ use properties::{DeclaredValue, PropertyDeclaration, ParsedDeclaration};
use properties::{ShorthandId, UnparsedValue, longhands};
- use properties::declaration_block::Importance;
use std::fmt;
+ use std::sync::Arc;
use style_traits::ToCss;
pub struct Longhands {
@@ -551,10 +551,7 @@
/// Parse the given shorthand and fill the result into the
/// `declarations` vector.
- pub fn parse(context: &ParserContext,
- input: &mut Parser,
- declarations: &mut Vec<(PropertyDeclaration, Importance)>)
- -> Result<(), ()> {
+ pub fn parse(context: &ParserContext, input: &mut Parser) -> Result<ParsedDeclaration, ()> {
input.look_for_var_functions();
let start = input.position();
let value = input.parse_entirely(|input| parse_value(context, input));
@@ -563,31 +560,17 @@
}
let var = input.seen_var_functions();
if let Ok(value) = value {
- % for sub_property in shorthand.sub_properties:
- declarations.push((PropertyDeclaration::${sub_property.camel_case}(
- % if sub_property.boxed:
- DeclaredValue::Value(Box::new(value.${sub_property.ident}))
- % else:
- DeclaredValue::Value(value.${sub_property.ident})
- % endif
- ), Importance::Normal));
- % endfor
- Ok(())
+ Ok(ParsedDeclaration::${shorthand.camel_case}(value))
} else if var {
input.reset(start);
let (first_token_type, css) = try!(
::custom_properties::parse_non_custom_with_var(input));
- % for sub_property in shorthand.sub_properties:
- declarations.push((PropertyDeclaration::${sub_property.camel_case}(
- DeclaredValue::WithVariables(Box::new(UnparsedValue {
- css: css.clone().into_owned(),
- first_token_type: first_token_type,
- base_url: context.base_url.clone(),
- from_shorthand: Some(ShorthandId::${shorthand.camel_case}),
- }))
- ), Importance::Normal));
- % endfor
- Ok(())
+ Ok(ParsedDeclaration::${shorthand.camel_case}WithVariables(Arc::new(UnparsedValue {
+ css: css.into_owned(),
+ first_token_type: first_token_type,
+ base_url: context.base_url.clone(),
+ from_shorthand: Some(ShorthandId::${shorthand.camel_case}),
+ })))
} else {
Err(())
}
diff --git a/components/style/properties/properties.mako.rs b/components/style/properties/properties.mako.rs
index e0a2b24b6cc..f0969ac1eea 100644
--- a/components/style/properties/properties.mako.rs
+++ b/components/style/properties/properties.mako.rs
@@ -568,7 +568,7 @@ pub enum DeclaredValue<T> {
/// A known specified value from the stylesheet.
Value(T),
/// An unparsed value that contains `var()` functions.
- WithVariables(Box<UnparsedValue>),
+ WithVariables(Arc<UnparsedValue>),
/// An CSS-wide keyword.
CSSWideKeyword(CSSWideKeyword),
}
@@ -797,6 +797,61 @@ impl PropertyId {
}
}
+/// Includes shorthands before expansion
+pub enum ParsedDeclaration {
+ % for shorthand in data.shorthands:
+ /// ${shorthand.name}
+ ${shorthand.camel_case}(shorthands::${shorthand.ident}::Longhands),
+ % endfor
+ % for shorthand in data.shorthands:
+ /// ${shorthand.name} with var() functions
+ ${shorthand.camel_case}WithVariables(Arc<UnparsedValue>),
+ % endfor
+ /// Not a shorthand
+ LonghandOrCustom(PropertyDeclaration),
+}
+
+impl ParsedDeclaration {
+ /// Transform this ParsedDeclaration into a sequence of PropertyDeclaration
+ /// by expanding shorthand declarations into their corresponding longhands
+ pub fn expand<F>(self, mut f: F) where F: FnMut(PropertyDeclaration) {
+ match self {
+ % for shorthand in data.shorthands:
+ ParsedDeclaration::${shorthand.camel_case}(
+ shorthands::${shorthand.ident}::Longhands {
+ % for sub_property in shorthand.sub_properties:
+ ${sub_property.ident},
+ % endfor
+ }
+ ) => {
+ % for sub_property in shorthand.sub_properties:
+ f(PropertyDeclaration::${sub_property.camel_case}(
+ % if sub_property.boxed:
+ DeclaredValue::Value(Box::new(${sub_property.ident}))
+ % else:
+ DeclaredValue::Value(${sub_property.ident})
+ % endif
+ ));
+ % endfor
+ }
+ % endfor
+ % for shorthand in data.shorthands:
+ ParsedDeclaration::${shorthand.camel_case}WithVariables(value) => {
+ debug_assert_eq!(
+ value.from_shorthand,
+ Some(ShorthandId::${shorthand.camel_case})
+ );
+ % for sub_property in shorthand.sub_properties:
+ f(PropertyDeclaration::${sub_property.camel_case}(
+ DeclaredValue::WithVariables(value.clone())));
+ % endfor
+ }
+ % endfor
+ ParsedDeclaration::LonghandOrCustom(declaration) => f(declaration),
+ }
+ }
+}
+
/// Servo's representation for a property declaration.
#[derive(PartialEq, Clone)]
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
@@ -1075,8 +1130,13 @@ impl PropertyDeclaration {
% endfor
PropertyDeclarationParseResult::ValidOrIgnoredDeclaration
},
- Err(()) => match shorthands::${shorthand.ident}::parse(context, input, result_list) {
- Ok(()) => PropertyDeclarationParseResult::ValidOrIgnoredDeclaration,
+ Err(()) => match shorthands::${shorthand.ident}::parse(context, input) {
+ Ok(parsed) => {
+ parsed.expand(|declaration| {
+ result_list.push((declaration, Importance::Normal))
+ });
+ PropertyDeclarationParseResult::ValidOrIgnoredDeclaration
+ }
Err(()) => PropertyDeclarationParseResult::InvalidValue,
}
}