From 404148c82e2b22ab910c9875393a68aea540b013 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Emilio=20Cobos=20=C3=81lvarez?= Date: Mon, 15 Jan 2018 22:34:34 +0100 Subject: [PATCH] style: Don't allow fallback alignment in place-content shorthand. Bug: 1430622 Reviewed-by: xidorn,mats MozReview-Commit-ID: sALBFJeqvr --- .../properties/shorthand/position.mako.rs | 16 +++-- components/style/values/specified/align.rs | 69 +++++++++++++------ 2 files changed, 57 insertions(+), 28 deletions(-) diff --git a/components/style/properties/shorthand/position.mako.rs b/components/style/properties/shorthand/position.mako.rs index 0ee37c1a9df..1bddeeb8b33 100644 --- a/components/style/properties/shorthand/position.mako.rs +++ b/components/style/properties/shorthand/position.mako.rs @@ -611,17 +611,19 @@ <%helpers:shorthand name="place-content" sub_properties="align-content justify-content" spec="https://drafts.csswg.org/css-align/#propdef-place-content" products="gecko"> - use properties::longhands::align_content; - use properties::longhands::justify_content; + use values::specified::align::{AlignJustifyContent, FallbackAllowed}; - pub fn parse_value<'i, 't>(context: &ParserContext, input: &mut Parser<'i, 't>) - -> Result> { - let align = align_content::parse(context, input)?; + pub fn parse_value<'i, 't>( + _: &ParserContext, + input: &mut Parser<'i, 't>, + ) -> Result> { + let align = AlignJustifyContent::parse_with_fallback(input, FallbackAllowed::No)?; if align.has_extra_flags() { return Err(input.new_custom_error(StyleParseErrorKind::UnspecifiedError)); } - let justify = input.try(|input| justify_content::parse(context, input)) - .unwrap_or(justify_content::SpecifiedValue::from(align)); + let justify = + input.try(|input| AlignJustifyContent::parse_with_fallback(input, FallbackAllowed::No)) + .unwrap_or(align); if justify.has_extra_flags() { return Err(input.new_custom_error(StyleParseErrorKind::UnspecifiedError)); } diff --git a/components/style/values/specified/align.rs b/components/style/values/specified/align.rs index 985a35ee80e..ac2f7719d31 100644 --- a/components/style/values/specified/align.rs +++ b/components/style/values/specified/align.rs @@ -119,6 +119,21 @@ const ALIGN_ALL_SHIFT: u32 = structs::NS_STYLE_ALIGN_ALL_SHIFT; #[cfg_attr(feature = "servo", derive(Deserialize, Serialize))] pub struct AlignJustifyContent(u16); +/// Whether fallback is allowed in align-content / justify-content parsing. +/// +/// This is used for the place-content shorthand, until the resolutions from [1] +/// are specified. +/// +/// [1]: https://github.com/w3c/csswg-drafts/issues/1002 +#[derive(Clone, Copy, PartialEq)] +pub enum FallbackAllowed { + /// Allow fallback alignment. + Yes, + /// Don't allow fallback alignment. + No, +} + + impl AlignJustifyContent { /// The initial value 'normal' #[inline] @@ -159,6 +174,38 @@ impl AlignJustifyContent { pub fn has_extra_flags(self) -> bool { self.primary().intersects(AlignFlags::FLAG_BITS) || self.fallback().intersects(AlignFlags::FLAG_BITS) } + + /// Parse a value for align-content / justify-content, optionally allowing + /// fallback. + pub fn parse_with_fallback<'i, 't>( + input: &mut Parser<'i, 't>, + fallback_allowed: FallbackAllowed, + ) -> Result> { + // normal | + if let Ok(value) = input.try(|input| parse_normal_or_baseline(input)) { + return Ok(AlignJustifyContent::new(value)) + } + + // followed by optional <*-position> + if let Ok(value) = input.try(|input| parse_content_distribution(input)) { + if fallback_allowed == FallbackAllowed::Yes { + if let Ok(fallback) = input.try(|input| parse_overflow_content_position(input)) { + return Ok(AlignJustifyContent::with_fallback(value, fallback)) + } + } + return Ok(AlignJustifyContent::new(value)) + } + + // <*-position> followed by optional + let fallback = parse_overflow_content_position(input)?; + if fallback_allowed == FallbackAllowed::Yes { + if let Ok(value) = input.try(|input| parse_content_distribution(input)) { + return Ok(AlignJustifyContent::with_fallback(value, fallback)) + } + } + + Ok(AlignJustifyContent::new(fallback)) + } } impl ToCss for AlignJustifyContent { @@ -180,27 +227,7 @@ impl Parse for AlignJustifyContent { // normal | | // [ || [ ? && ] ] fn parse<'i, 't>(_: &ParserContext, input: &mut Parser<'i, 't>) -> Result> { - // normal | - if let Ok(value) = input.try(|input| parse_normal_or_baseline(input)) { - return Ok(AlignJustifyContent::new(value)) - } - - // followed by optional <*-position> - if let Ok(value) = input.try(|input| parse_content_distribution(input)) { - if let Ok(fallback) = input.try(|input| parse_overflow_content_position(input)) { - return Ok(AlignJustifyContent::with_fallback(value, fallback)) - } - return Ok(AlignJustifyContent::new(value)) - } - - // <*-position> followed by optional - if let Ok(fallback) = input.try(|input| parse_overflow_content_position(input)) { - if let Ok(value) = input.try(|input| parse_content_distribution(input)) { - return Ok(AlignJustifyContent::with_fallback(value, fallback)) - } - return Ok(AlignJustifyContent::new(fallback)) - } - Err(input.new_custom_error(StyleParseErrorKind::UnspecifiedError)) + Self::parse_with_fallback(input, FallbackAllowed::Yes) } }