diff --git a/components/style/gecko/conversions.rs b/components/style/gecko/conversions.rs index c48d56f56e1..e077a9f9666 100644 --- a/components/style/gecko/conversions.rs +++ b/components/style/gecko/conversions.rs @@ -5,6 +5,8 @@ //! This module contains conversion helpers between Servo and Gecko types //! Ideally, it would be in geckolib itself, but coherence //! forces us to keep the traits and implementations here +//! +//! FIXME(emilio): This file should generally just die. #![allow(unsafe_code)] @@ -22,6 +24,7 @@ use crate::values::computed::{Angle, CalcLengthOrPercentage, Gradient, Image}; use crate::values::computed::{Integer, LengthOrPercentage}; use crate::values::computed::{LengthOrPercentageOrAuto, NonNegativeLengthOrPercentageOrAuto}; use crate::values::computed::{Percentage, TextAlign}; +use crate::values::generics::NonNegative; use crate::values::generics::box_::VerticalAlign; use crate::values::generics::grid::{TrackListValue, TrackSize}; use crate::values::generics::image::{CompatMode, GradientItem, Image as GenericImage}; @@ -113,7 +116,6 @@ impl From for LengthOrPercentageOrAuto { // disappear as we move more stuff to cbindgen. impl From for NonNegativeLengthOrPercentageOrAuto { fn from(other: nsStyleCoord_CalcValue) -> Self { - use crate::values::generics::NonNegative; use style_traits::values::specified::AllowedNumericType; NonNegative(if other.mLength < 0 || other.mPercent < 0. { LengthOrPercentageOrAuto::Calc(CalcLengthOrPercentage::with_clamping_mode( @@ -675,6 +677,7 @@ pub mod basic_shape { use crate::values::generics::basic_shape::{ BasicShape as GenericBasicShape, InsetRect, Polygon, }; + use crate::values::generics::NonNegative; use crate::values::generics::basic_shape::{Circle, Ellipse, Path, PolygonCoord}; use crate::values::generics::basic_shape::{GeometryBox, ShapeBox, ShapeSource}; use crate::values::generics::border::BorderRadius as GenericBorderRadius; @@ -838,10 +841,10 @@ pub mod basic_shape { fn from(other: &'a nsStyleCorners) -> Self { let get_corner = |index| { BorderCornerRadius::new( - LengthOrPercentage::from_gecko_style_coord(&other.data_at(index)) - .expect(" should be a length, percentage, or calc value"), - LengthOrPercentage::from_gecko_style_coord(&other.data_at(index + 1)) - .expect(" should be a length, percentage, or calc value"), + NonNegative(LengthOrPercentage::from_gecko_style_coord(&other.data_at(index)) + .expect(" should be a length, percentage, or calc value")), + NonNegative(LengthOrPercentage::from_gecko_style_coord(&other.data_at(index + 1)) + .expect(" should be a length, percentage, or calc value")), ) }; diff --git a/components/style/properties/gecko.mako.rs b/components/style/properties/gecko.mako.rs index 5f96b42c10a..218f150e670 100644 --- a/components/style/properties/gecko.mako.rs +++ b/components/style/properties/gecko.mako.rs @@ -1687,8 +1687,8 @@ fn static_assert() { pub fn clone_border_image_slice(&self) -> longhands::border_image_slice::computed_value::T { use crate::gecko_bindings::structs::NS_STYLE_BORDER_IMAGE_SLICE_FILL; - use crate::values::computed::{BorderImageSlice, NumberOrPercentage}; - type NumberOrPercentageRect = crate::values::generics::rect::Rect; + use crate::values::computed::{BorderImageSlice, NonNegativeNumberOrPercentage}; + type NumberOrPercentageRect = crate::values::generics::rect::Rect; BorderImageSlice { offsets: diff --git a/components/style/properties/longhands/border.mako.rs b/components/style/properties/longhands/border.mako.rs index 5a5cdbeb552..2c304780e6d 100644 --- a/components/style/properties/longhands/border.mako.rs +++ b/components/style/properties/longhands/border.mako.rs @@ -153,14 +153,15 @@ ${helpers.predefined_type( ${helpers.predefined_type( "border-image-slice", "BorderImageSlice", - initial_value="computed::NumberOrPercentage::Percentage(computed::Percentage(1.)).into()", - initial_specified_value="specified::NumberOrPercentage::Percentage(specified::Percentage::new(1.)).into()", + initial_value="computed::BorderImageSlice::hundred_percent()", + initial_specified_value="specified::BorderImageSlice::hundred_percent()", spec="https://drafts.csswg.org/css-backgrounds/#border-image-slice", animation_value_type="discrete", flags="APPLIES_TO_FIRST_LETTER", boxed=True, )} +// FIXME(emilio): Why does this live here? ;_; #[cfg(feature = "gecko")] impl crate::values::computed::BorderImageWidth { pub fn to_gecko_rect(&self, sides: &mut crate::gecko_bindings::structs::nsStyleSides) { @@ -177,7 +178,7 @@ impl crate::values::computed::BorderImageWidth { l.to_gecko_style_coord(&mut sides.data_at_mut(${i})) }, BorderImageSideWidth::Number(n) => { - sides.data_at_mut(${i}).set_value(CoordDataValue::Factor(n)) + sides.data_at_mut(${i}).set_value(CoordDataValue::Factor(n.0)) }, } % endfor @@ -191,6 +192,7 @@ impl crate::values::computed::BorderImageWidth { use crate::gecko::values::GeckoStyleCoordConvertible; use crate::values::computed::{LengthOrPercentage, Number}; use crate::values::generics::border::BorderImageSideWidth; + use crate::values::generics::NonNegative; Some( crate::values::computed::BorderImageWidth::new( @@ -201,13 +203,13 @@ impl crate::values::computed::BorderImageWidth { }, eStyleUnit_Factor => { BorderImageSideWidth::Number( - Number::from_gecko_style_coord(&sides.data_at(${i})) - .expect("sides[${i}] could not convert to Number")) + NonNegative(Number::from_gecko_style_coord(&sides.data_at(${i})) + .expect("sides[${i}] could not convert to Number"))) }, _ => { BorderImageSideWidth::Length( - LengthOrPercentage::from_gecko_style_coord(&sides.data_at(${i})) - .expect("sides[${i}] could not convert to LengthOrPercentager")) + NonNegative(LengthOrPercentage::from_gecko_style_coord(&sides.data_at(${i})) + .expect("sides[${i}] could not convert to LengthOrPercentage"))) }, }, % endfor diff --git a/components/style/properties/longhands/inherited_text.mako.rs b/components/style/properties/longhands/inherited_text.mako.rs index f751b29ae68..5a7b88e3823 100644 --- a/components/style/properties/longhands/inherited_text.mako.rs +++ b/components/style/properties/longhands/inherited_text.mako.rs @@ -295,7 +295,7 @@ ${helpers.predefined_type( "-webkit-text-stroke-width", "BorderSideWidth", "crate::values::computed::NonNegativeLength::new(0.)", - initial_specified_value="specified::BorderSideWidth::Length(specified::Length::zero())", + initial_specified_value="specified::BorderSideWidth::zero()", computed_type="crate::values::computed::NonNegativeLength", products="gecko", gecko_pref="layout.css.prefixes.webkit", diff --git a/components/style/values/animated/mod.rs b/components/style/values/animated/mod.rs index 38de8a359a1..cf5ca94bae6 100644 --- a/components/style/values/animated/mod.rs +++ b/components/style/values/animated/mod.rs @@ -12,7 +12,6 @@ use crate::properties::PropertyId; use crate::values::computed::length::CalcLengthOrPercentage; use crate::values::computed::url::ComputedUrl; use crate::values::computed::Angle as ComputedAngle; -use crate::values::computed::BorderCornerRadius as ComputedBorderCornerRadius; use crate::values::CSSFloat; use app_units::Au; use euclid::{Point2D, Size2D}; @@ -340,23 +339,6 @@ trivial_to_animated_value!(ComputedUrl); trivial_to_animated_value!(bool); trivial_to_animated_value!(f32); -impl ToAnimatedValue for ComputedBorderCornerRadius { - type AnimatedValue = Self; - - #[inline] - fn to_animated_value(self) -> Self { - self - } - - #[inline] - fn from_animated_value(animated: Self::AnimatedValue) -> Self { - ComputedBorderCornerRadius::new( - (animated.0).0.width.clamp_to_non_negative(), - (animated.0).0.height.clamp_to_non_negative(), - ) - } -} - impl ToAnimatedZero for Au { #[inline] fn to_animated_zero(&self) -> Result { diff --git a/components/style/values/computed/basic_shape.rs b/components/style/values/computed/basic_shape.rs index 6a7b02cadcd..383c7b39bfc 100644 --- a/components/style/values/computed/basic_shape.rs +++ b/components/style/values/computed/basic_shape.rs @@ -8,7 +8,7 @@ //! [basic-shape]: https://drafts.csswg.org/css-shapes/#typedef-basic-shape use crate::values::computed::url::ComputedUrl; -use crate::values::computed::{Image, LengthOrPercentage}; +use crate::values::computed::{Image, LengthOrPercentage, NonNegativeLengthOrPercentage}; use crate::values::generics::basic_shape as generic; use std::fmt::{self, Write}; use style_traits::{CssWriter, ToCss}; @@ -24,10 +24,10 @@ pub type FloatAreaShape = generic::FloatAreaShape; /// A computed basic shape. pub type BasicShape = - generic::BasicShape; + generic::BasicShape; /// The computed value of `inset()` -pub type InsetRect = generic::InsetRect; +pub type InsetRect = generic::InsetRect; /// A computed circle. pub type Circle = generic::Circle; diff --git a/components/style/values/computed/border.rs b/components/style/values/computed/border.rs index 676e8c1b6be..09dcfbe117a 100644 --- a/components/style/values/computed/border.rs +++ b/components/style/values/computed/border.rs @@ -4,9 +4,9 @@ //! Computed types for CSS values related to borders. -use crate::values::animated::ToAnimatedZero; -use crate::values::computed::length::{LengthOrPercentage, NonNegativeLength}; -use crate::values::computed::{Number, NumberOrPercentage}; +use crate::values::generics::NonNegative; +use crate::values::computed::length::{NonNegativeLengthOrPercentage, NonNegativeLength}; +use crate::values::computed::{NonNegativeNumber, NonNegativeNumberOrPercentage}; use crate::values::generics::border::BorderCornerRadius as GenericBorderCornerRadius; use crate::values::generics::border::BorderImageSideWidth as GenericBorderImageSideWidth; use crate::values::generics::border::BorderImageSlice as GenericBorderImageSlice; @@ -22,16 +22,16 @@ pub use crate::values::specified::border::BorderImageRepeat; pub type BorderImageWidth = Rect; /// A computed value for a single side of a `border-image-width` property. -pub type BorderImageSideWidth = GenericBorderImageSideWidth; +pub type BorderImageSideWidth = GenericBorderImageSideWidth; /// A computed value for the `border-image-slice` property. -pub type BorderImageSlice = GenericBorderImageSlice; +pub type BorderImageSlice = GenericBorderImageSlice; /// A computed value for the `border-radius` property. -pub type BorderRadius = GenericBorderRadius; +pub type BorderRadius = GenericBorderRadius; /// A computed value for the `border-*-radius` longhand properties. -pub type BorderCornerRadius = GenericBorderCornerRadius; +pub type BorderCornerRadius = GenericBorderCornerRadius; /// A computed value for the `border-spacing` longhand property. pub type BorderSpacing = GenericBorderSpacing; @@ -40,7 +40,18 @@ impl BorderImageSideWidth { /// Returns `1`. #[inline] pub fn one() -> Self { - GenericBorderImageSideWidth::Number(1.) + GenericBorderImageSideWidth::Number(NonNegative(1.)) + } +} + +impl BorderImageSlice { + /// Returns the `100%` value. + #[inline] + pub fn hundred_percent() -> Self { + GenericBorderImageSlice { + offsets: Rect::all(NonNegativeNumberOrPercentage::hundred_percent()), + fill: false, + } } } @@ -68,26 +79,18 @@ impl BorderCornerRadius { /// Returns `0 0`. pub fn zero() -> Self { GenericBorderCornerRadius(Size::new( - LengthOrPercentage::zero(), - LengthOrPercentage::zero(), + NonNegativeLengthOrPercentage::zero(), + NonNegativeLengthOrPercentage::zero(), )) } } -impl ToAnimatedZero for BorderCornerRadius { - #[inline] - fn to_animated_zero(&self) -> Result { - // FIXME(nox): Why? - Err(()) - } -} - impl BorderRadius { /// Returns whether all the values are `0px`. pub fn all_zero(&self) -> bool { fn all(corner: &BorderCornerRadius) -> bool { - fn is_zero(l: &LengthOrPercentage) -> bool { - *l == LengthOrPercentage::zero() + fn is_zero(l: &NonNegativeLengthOrPercentage) -> bool { + *l == NonNegativeLengthOrPercentage::zero() } is_zero(corner.0.width()) && is_zero(corner.0.height()) } diff --git a/components/style/values/computed/mod.rs b/components/style/values/computed/mod.rs index 93ee3e73cc1..7ee151a4078 100644 --- a/components/style/values/computed/mod.rs +++ b/components/style/values/computed/mod.rs @@ -543,6 +543,15 @@ pub enum NumberOrPercentage { Number(Number), } +impl NumberOrPercentage { + fn clamp_to_non_negative(self) -> Self { + match self { + NumberOrPercentage::Percentage(p) => NumberOrPercentage::Percentage(p.clamp_to_non_negative()), + NumberOrPercentage::Number(n) => NumberOrPercentage::Number(n.max(0.)), + } + } +} + impl ToComputedValue for specified::NumberOrPercentage { type ComputedValue = NumberOrPercentage; @@ -572,6 +581,31 @@ impl ToComputedValue for specified::NumberOrPercentage { } } +/// A non-negative . +pub type NonNegativeNumberOrPercentage = NonNegative; + +impl NonNegativeNumberOrPercentage { + /// Returns the `100%` value. + #[inline] + pub fn hundred_percent() -> Self { + NonNegative(NumberOrPercentage::Percentage(Percentage::hundred())) + } +} + +impl ToAnimatedValue for NonNegativeNumberOrPercentage { + type AnimatedValue = NumberOrPercentage; + + #[inline] + fn to_animated_value(self) -> Self::AnimatedValue { + self.0 + } + + #[inline] + fn from_animated_value(animated: Self::AnimatedValue) -> Self { + NonNegative(animated.clamp_to_non_negative()) + } +} + /// A type used for opacity. pub type Opacity = CSSFloat; diff --git a/components/style/values/generics/basic_shape.rs b/components/style/values/generics/basic_shape.rs index cbcdadd055f..9390de653d9 100644 --- a/components/style/values/generics/basic_shape.rs +++ b/components/style/values/generics/basic_shape.rs @@ -85,8 +85,8 @@ pub enum ShapeSource { ToComputedValue, ToCss, )] -pub enum BasicShape { - Inset(#[css(field_bound)] InsetRect), +pub enum BasicShape { + Inset(#[css(field_bound)] InsetRect), Circle(#[css(field_bound)] Circle), Ellipse(#[css(field_bound)] Ellipse), Polygon(Polygon), @@ -105,9 +105,9 @@ pub enum BasicShape { SpecifiedValueInfo, ToComputedValue, )] -pub struct InsetRect { +pub struct InsetRect { pub rect: Rect, - pub round: Option>, + pub round: Option>, } /// @@ -258,9 +258,10 @@ impl ToAnimatedZero for ShapeSource { } } -impl ToCss for InsetRect +impl ToCss for InsetRect where - L: ToCss + PartialEq, + Length: ToCss + PartialEq, + NonNegativeLength: ToCss + PartialEq, { fn to_css(&self, dest: &mut CssWriter) -> fmt::Result where diff --git a/components/style/values/generics/border.rs b/components/style/values/generics/border.rs index 0a50721bcda..eb651377e0d 100644 --- a/components/style/values/generics/border.rs +++ b/components/style/values/generics/border.rs @@ -45,6 +45,8 @@ pub struct BorderImageSlice { MallocSizeOf, PartialEq, SpecifiedValueInfo, + ToAnimatedValue, + ToAnimatedZero, ToComputedValue, ToCss, )] @@ -106,19 +108,6 @@ pub struct BorderRadius { pub bottom_left: BorderCornerRadius, } -impl From for BorderImageSlice -where - N: Clone, -{ - #[inline] - fn from(value: N) -> Self { - Self { - offsets: Rect::all(value), - fill: false, - } - } -} - impl BorderRadius { /// Returns a new `BorderRadius`. #[inline] diff --git a/components/style/values/specified/basic_shape.rs b/components/style/values/specified/basic_shape.rs index 981cad00aaa..2f1f510372c 100644 --- a/components/style/values/specified/basic_shape.rs +++ b/components/style/values/specified/basic_shape.rs @@ -16,7 +16,7 @@ use crate::values::specified::border::BorderRadius; use crate::values::specified::image::Image; use crate::values::specified::position::{HorizontalPosition, Position, VerticalPosition}; use crate::values::specified::url::SpecifiedUrl; -use crate::values::specified::LengthOrPercentage; +use crate::values::specified::{LengthOrPercentage, NonNegativeLengthOrPercentage}; use crate::values::specified::SVGPathData; use cssparser::Parser; use std::fmt::{self, Write}; @@ -32,10 +32,10 @@ pub type ClippingShape = generic::ClippingShape; pub type FloatAreaShape = generic::FloatAreaShape; /// A specified basic shape. -pub type BasicShape = generic::BasicShape; +pub type BasicShape = generic::BasicShape; /// The specified value of `inset()` -pub type InsetRect = generic::InsetRect; +pub type InsetRect = generic::InsetRect; /// A specified circle. pub type Circle = generic::Circle; @@ -199,10 +199,7 @@ impl InsetRect { } else { None }; - Ok(generic::InsetRect { - rect: rect, - round: round, - }) + Ok(generic::InsetRect { rect, round }) } } diff --git a/components/style/values/specified/border.rs b/components/style/values/specified/border.rs index cf60c91b329..ee0b491f027 100644 --- a/components/style/values/specified/border.rs +++ b/components/style/values/specified/border.rs @@ -13,8 +13,8 @@ use crate::values::generics::border::BorderRadius as GenericBorderRadius; use crate::values::generics::border::BorderSpacing as GenericBorderSpacing; use crate::values::generics::rect::Rect; use crate::values::generics::size::Size; -use crate::values::specified::length::{Length, LengthOrPercentage, NonNegativeLength}; -use crate::values::specified::{AllowQuirks, Number, NumberOrPercentage}; +use crate::values::specified::length::{NonNegativeLengthOrPercentage, NonNegativeLength}; +use crate::values::specified::{AllowQuirks, NonNegativeNumber, NonNegativeNumberOrPercentage}; use cssparser::Parser; use std::fmt::{self, Write}; use style_traits::{CssWriter, ParseError, ToCss}; @@ -71,28 +71,45 @@ pub enum BorderSideWidth { /// `thick` Thick, /// `` - Length(Length), + Length(NonNegativeLength), } /// A specified value for the `border-image-width` property. pub type BorderImageWidth = Rect; /// A specified value for a single side of a `border-image-width` property. -pub type BorderImageSideWidth = GenericBorderImageSideWidth; +pub type BorderImageSideWidth = GenericBorderImageSideWidth; /// A specified value for the `border-image-slice` property. -pub type BorderImageSlice = GenericBorderImageSlice; +pub type BorderImageSlice = GenericBorderImageSlice; /// A specified value for the `border-radius` property. -pub type BorderRadius = GenericBorderRadius; +pub type BorderRadius = GenericBorderRadius; /// A specified value for the `border-*-radius` longhand properties. -pub type BorderCornerRadius = GenericBorderCornerRadius; +pub type BorderCornerRadius = GenericBorderCornerRadius; /// A specified value for the `border-spacing` longhand properties. pub type BorderSpacing = GenericBorderSpacing; +impl BorderImageSlice { + /// Returns the `100%` value. + #[inline] + pub fn hundred_percent() -> Self { + GenericBorderImageSlice { + offsets: Rect::all(NonNegativeNumberOrPercentage::hundred_percent()), + fill: false, + } + } +} + impl BorderSideWidth { + /// Returns the `0px` value. + #[inline] + pub fn zero() -> Self { + BorderSideWidth::Length(NonNegativeLength::zero()) + } + /// Parses, with quirks. pub fn parse_quirky<'i, 't>( context: &ParserContext, @@ -100,7 +117,7 @@ impl BorderSideWidth { allow_quirks: AllowQuirks, ) -> Result> { if let Ok(length) = - input.try(|i| Length::parse_non_negative_quirky(context, i, allow_quirks)) + input.try(|i| NonNegativeLength::parse_quirky(context, i, allow_quirks)) { return Ok(BorderSideWidth::Length(length)); } @@ -130,9 +147,9 @@ impl ToComputedValue for BorderSideWidth { // Spec: https://drafts.csswg.org/css-backgrounds-3/#line-width // Gecko: https://bugzilla.mozilla.org/show_bug.cgi?id=1312155#c0 match *self { - BorderSideWidth::Thin => Length::from_px(1.).to_computed_value(context), - BorderSideWidth::Medium => Length::from_px(3.).to_computed_value(context), - BorderSideWidth::Thick => Length::from_px(5.).to_computed_value(context), + BorderSideWidth::Thin => NonNegativeLength::from_px(1.).to_computed_value(context), + BorderSideWidth::Medium => NonNegativeLength::from_px(3.).to_computed_value(context), + BorderSideWidth::Thick => NonNegativeLength::from_px(5.).to_computed_value(context), BorderSideWidth::Length(ref length) => length.to_computed_value(context), } .into() @@ -140,7 +157,7 @@ impl ToComputedValue for BorderSideWidth { #[inline] fn from_computed_value(computed: &Self::ComputedValue) -> Self { - BorderSideWidth::Length(ToComputedValue::from_computed_value(&computed.0)) + BorderSideWidth::Length(ToComputedValue::from_computed_value(computed)) } } @@ -148,7 +165,7 @@ impl BorderImageSideWidth { /// Returns `1`. #[inline] pub fn one() -> Self { - GenericBorderImageSideWidth::Number(Number::new(1.)) + GenericBorderImageSideWidth::Number(NonNegativeNumber::new(1.)) } } @@ -161,11 +178,11 @@ impl Parse for BorderImageSideWidth { return Ok(GenericBorderImageSideWidth::Auto); } - if let Ok(len) = input.try(|i| LengthOrPercentage::parse_non_negative(context, i)) { + if let Ok(len) = input.try(|i| NonNegativeLengthOrPercentage::parse(context, i)) { return Ok(GenericBorderImageSideWidth::Length(len)); } - let num = Number::parse_non_negative(context, input)?; + let num = NonNegativeNumber::parse(context, input)?; Ok(GenericBorderImageSideWidth::Number(num)) } } @@ -176,14 +193,11 @@ impl Parse for BorderImageSlice { input: &mut Parser<'i, 't>, ) -> Result> { let mut fill = input.try(|i| i.expect_ident_matching("fill")).is_ok(); - let offsets = Rect::parse_with(context, input, NumberOrPercentage::parse_non_negative)?; + let offsets = Rect::parse_with(context, input, NonNegativeNumberOrPercentage::parse)?; if !fill { fill = input.try(|i| i.expect_ident_matching("fill")).is_ok(); } - Ok(GenericBorderImageSlice { - offsets: offsets, - fill: fill, - }) + Ok(GenericBorderImageSlice { offsets, fill }) } } @@ -192,9 +206,9 @@ impl Parse for BorderRadius { context: &ParserContext, input: &mut Parser<'i, 't>, ) -> Result> { - let widths = Rect::parse_with(context, input, LengthOrPercentage::parse_non_negative)?; + let widths = Rect::parse_with(context, input, NonNegativeLengthOrPercentage::parse)?; let heights = if input.try(|i| i.expect_delim('/')).is_ok() { - Rect::parse_with(context, input, LengthOrPercentage::parse_non_negative)? + Rect::parse_with(context, input, NonNegativeLengthOrPercentage::parse)? } else { widths.clone() }; @@ -213,7 +227,7 @@ impl Parse for BorderCornerRadius { context: &ParserContext, input: &mut Parser<'i, 't>, ) -> Result> { - Size::parse_with(context, input, LengthOrPercentage::parse_non_negative) + Size::parse_with(context, input, NonNegativeLengthOrPercentage::parse) .map(GenericBorderCornerRadius) } } @@ -224,7 +238,7 @@ impl Parse for BorderSpacing { input: &mut Parser<'i, 't>, ) -> Result> { Size::parse_with(context, input, |context, input| { - Length::parse_non_negative_quirky(context, input, AllowQuirks::Yes).map(From::from) + NonNegativeLength::parse_quirky(context, input, AllowQuirks::Yes).map(From::from) }) .map(GenericBorderSpacing) } diff --git a/components/style/values/specified/length.rs b/components/style/values/specified/length.rs index 13877dbe594..db5a359cacd 100644 --- a/components/style/values/specified/length.rs +++ b/components/style/values/specified/length.rs @@ -717,6 +717,16 @@ impl NonNegativeLength { pub fn from_px(px_value: CSSFloat) -> Self { Length::from_px(px_value.max(0.)).into() } + + /// Parses a non-negative length, optionally with quirks. + #[inline] + pub fn parse_quirky<'i, 't>( + context: &ParserContext, + input: &mut Parser<'i, 't>, + allow_quirks: AllowQuirks, + ) -> Result> { + Ok(NonNegative(Length::parse_non_negative_quirky(context, input, allow_quirks)?)) + } } /// Either a NonNegativeLength or the `auto` keyword. diff --git a/components/style/values/specified/mod.rs b/components/style/values/specified/mod.rs index d3df66a0eea..a73252bbeb6 100644 --- a/components/style/values/specified/mod.rs +++ b/components/style/values/specified/mod.rs @@ -359,6 +359,26 @@ impl Parse for NumberOrPercentage { } } +/// A non-negative | . +pub type NonNegativeNumberOrPercentage = NonNegative; + +impl NonNegativeNumberOrPercentage { + /// Returns the `100%` value. + #[inline] + pub fn hundred_percent() -> Self { + NonNegative(NumberOrPercentage::Percentage(Percentage::hundred())) + } +} + +impl Parse for NonNegativeNumberOrPercentage { + fn parse<'i, 't>( + context: &ParserContext, + input: &mut Parser<'i, 't>, + ) -> Result> { + Ok(NonNegative(NumberOrPercentage::parse_non_negative(context, input)?)) + } +} + #[allow(missing_docs)] #[derive(Clone, Copy, Debug, MallocSizeOf, PartialEq, PartialOrd, SpecifiedValueInfo, ToCss)] pub struct Opacity(Number);