mirror of
https://github.com/servo/servo.git
synced 2025-08-06 06:00:15 +01:00
Auto merge of #18239 - servo:derive-all-the-things, r=emilio
Refactor how we handle trait bounds in style_derive <!-- Reviewable:start --> This change is [<img src="https://reviewable.io/review_button.svg" height="34" align="absmiddle" alt="Reviewable"/>](https://reviewable.io/reviews/servo/servo/18239) <!-- Reviewable:end -->
This commit is contained in:
commit
a266e96d28
27 changed files with 673 additions and 868 deletions
|
@ -139,21 +139,6 @@ impl ToAnimatedValue for ComputedTextShadowList {
|
|||
}
|
||||
}
|
||||
|
||||
// FIXME(nox): This could be derived if we implement Animate for bool.
|
||||
impl Animate for BoxShadow {
|
||||
#[inline]
|
||||
fn animate(&self, other: &Self, procedure: Procedure) -> Result<Self, ()> {
|
||||
if self.inset != other.inset {
|
||||
return Err(());
|
||||
}
|
||||
Ok(BoxShadow {
|
||||
base: self.base.animate(&other.base, procedure)?,
|
||||
spread: self.spread.animate(&other.spread, procedure)?,
|
||||
inset: self.inset,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
impl ComputeSquaredDistance for BoxShadow {
|
||||
#[inline]
|
||||
fn compute_squared_distance(&self, other: &Self) -> Result<SquaredDistance, ()> {
|
||||
|
@ -167,17 +152,6 @@ impl ComputeSquaredDistance for BoxShadow {
|
|||
}
|
||||
}
|
||||
|
||||
impl ToAnimatedZero for BoxShadow {
|
||||
#[inline]
|
||||
fn to_animated_zero(&self) -> Result<Self, ()> {
|
||||
Ok(BoxShadow {
|
||||
base: self.base.to_animated_zero()?,
|
||||
spread: self.spread.to_animated_zero()?,
|
||||
inset: self.inset,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
impl ToAnimatedValue for ComputedFilterList {
|
||||
type AnimatedValue = FilterList;
|
||||
|
||||
|
|
|
@ -28,7 +28,19 @@ use values::specified::url::SpecifiedUrl;
|
|||
pub mod color;
|
||||
pub mod effects;
|
||||
|
||||
/// Animating from one value to another.
|
||||
/// Animate from one value to another.
|
||||
///
|
||||
/// This trait is derivable with `#[derive(Animate)]`. The derived
|
||||
/// implementation uses a `match` expression with identical patterns for both
|
||||
/// `self` and `other`, calling `Animate::animate` on each fields of the values.
|
||||
/// If a field is annotated with `#[animation(constant)]`, the two values should
|
||||
/// be equal or an error is returned.
|
||||
///
|
||||
/// If a variant is annotated with `#[animation(error)]`, the corresponding
|
||||
/// `match` arm is not generated.
|
||||
///
|
||||
/// If the two values are not similar, an error is returned unless a fallback
|
||||
/// function has been specified through `#[animate(fallback)]`.
|
||||
pub trait Animate: Sized {
|
||||
/// Animate a value towards another one, given an animation procedure.
|
||||
fn animate(&self, other: &Self, procedure: Procedure) -> Result<Self, ()>;
|
||||
|
@ -51,6 +63,8 @@ pub enum Procedure {
|
|||
/// Conversion between computed values and intermediate values for animations.
|
||||
///
|
||||
/// Notably, colors are represented as four floats during animations.
|
||||
///
|
||||
/// This trait is derivable with `#[derive(ToAnimatedValue)]`.
|
||||
pub trait ToAnimatedValue {
|
||||
/// The type of the animated value.
|
||||
type AnimatedValue;
|
||||
|
@ -66,6 +80,13 @@ pub trait ToAnimatedValue {
|
|||
pub trait AnimatedValueAsComputed {}
|
||||
|
||||
/// Returns a value similar to `self` that represents zero.
|
||||
///
|
||||
/// This trait is derivable with `#[derive(ToAnimatedValue)]`. If a field is
|
||||
/// annotated with `#[animation(constant)]`, a clone of its value will be used
|
||||
/// instead of calling `ToAnimatedZero::to_animated_zero` on it.
|
||||
///
|
||||
/// If a variant is annotated with `#[animation(error)]`, the corresponding
|
||||
/// `match` arm is not generated.
|
||||
pub trait ToAnimatedZero: Sized {
|
||||
/// Returns a value that, when added with an underlying value, will produce the underlying
|
||||
/// value. This is used for SMIL animation's "by-animation" where SMIL first interpolates from
|
||||
|
|
|
@ -12,8 +12,10 @@ use values::animated::{Animate, Procedure};
|
|||
use values::distance::{ComputeSquaredDistance, SquaredDistance};
|
||||
|
||||
/// A computed angle.
|
||||
#[animate(fallback = "Self::animate_fallback")]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf, Deserialize, Serialize))]
|
||||
#[derive(Clone, Copy, Debug, HasViewportPercentage, PartialEq, PartialOrd, ToAnimatedZero)]
|
||||
#[derive(Animate, Clone, Copy, Debug, HasViewportPercentage, PartialEq)]
|
||||
#[derive(PartialOrd, ToAnimatedZero)]
|
||||
pub enum Angle {
|
||||
/// An angle with degree unit.
|
||||
Degree(CSSFloat),
|
||||
|
@ -62,26 +64,11 @@ impl Angle {
|
|||
pub fn zero() -> Self {
|
||||
Angle::Radian(0.0)
|
||||
}
|
||||
}
|
||||
|
||||
/// https://drafts.csswg.org/css-transitions/#animtype-number
|
||||
impl Animate for Angle {
|
||||
/// https://drafts.csswg.org/css-transitions/#animtype-number
|
||||
#[inline]
|
||||
fn animate(&self, other: &Self, procedure: Procedure) -> Result<Self, ()> {
|
||||
match (self, other) {
|
||||
(&Angle::Degree(ref this), &Angle::Degree(ref other)) => {
|
||||
Ok(Angle::Degree(this.animate(other, procedure)?))
|
||||
},
|
||||
(&Angle::Gradian(ref this), &Angle::Gradian(ref other)) => {
|
||||
Ok(Angle::Gradian(this.animate(other, procedure)?))
|
||||
},
|
||||
(&Angle::Turn(ref this), &Angle::Turn(ref other)) => {
|
||||
Ok(Angle::Turn(this.animate(other, procedure)?))
|
||||
},
|
||||
_ => {
|
||||
Ok(Angle::from_radians(self.radians().animate(&other.radians(), procedure)?))
|
||||
},
|
||||
}
|
||||
fn animate_fallback(&self, other: &Self, procedure: Procedure) -> Result<Self, ()> {
|
||||
Ok(Angle::from_radians(self.radians().animate(&other.radians(), procedure)?))
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
|
||||
use properties::animated_properties::RepeatableListAnimatable;
|
||||
use properties::longhands::background_size::computed_value::T as BackgroundSizeList;
|
||||
use values::animated::{Animate, Procedure, ToAnimatedValue, ToAnimatedZero};
|
||||
use values::animated::{ToAnimatedValue, ToAnimatedZero};
|
||||
use values::computed::length::LengthOrPercentageOrAuto;
|
||||
use values::generics::background::BackgroundSize as GenericBackgroundSize;
|
||||
|
||||
|
@ -15,23 +15,6 @@ pub type BackgroundSize = GenericBackgroundSize<LengthOrPercentageOrAuto>;
|
|||
|
||||
impl RepeatableListAnimatable for BackgroundSize {}
|
||||
|
||||
impl Animate for BackgroundSize {
|
||||
fn animate(&self, other: &Self, procedure: Procedure) -> Result<Self, ()> {
|
||||
match (self, other) {
|
||||
(
|
||||
&GenericBackgroundSize::Explicit { width: self_width, height: self_height },
|
||||
&GenericBackgroundSize::Explicit { width: other_width, height: other_height },
|
||||
) => {
|
||||
Ok(GenericBackgroundSize::Explicit {
|
||||
width: self_width.animate(&other_width, procedure)?,
|
||||
height: self_height.animate(&other_height, procedure)?,
|
||||
})
|
||||
}
|
||||
_ => Err(()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl ToAnimatedZero for BackgroundSize {
|
||||
#[inline]
|
||||
fn to_animated_zero(&self) -> Result<Self, ()> { Err(()) }
|
||||
|
|
|
@ -18,8 +18,7 @@ use values::generics::image::{CompatMode, ColorStop as GenericColorStop, EndingS
|
|||
use values::generics::image::{Gradient as GenericGradient, GradientItem as GenericGradientItem};
|
||||
use values::generics::image::{Image as GenericImage, GradientKind as GenericGradientKind};
|
||||
use values::generics::image::{LineDirection as GenericLineDirection, MozImageRect as GenericMozImageRect};
|
||||
use values::specified::image::{Gradient as SpecifiedGradient, LineDirection as SpecifiedLineDirection};
|
||||
use values::specified::image::{GradientKind as SpecifiedGradientKind};
|
||||
use values::specified::image::LineDirection as SpecifiedLineDirection;
|
||||
use values::specified::position::{X, Y};
|
||||
|
||||
/// A computed image layer.
|
||||
|
@ -181,55 +180,3 @@ impl ToComputedValue for SpecifiedLineDirection {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl ToComputedValue for SpecifiedGradient {
|
||||
type ComputedValue = Gradient;
|
||||
|
||||
fn to_computed_value(&self, context: &Context) -> Self::ComputedValue {
|
||||
Self::ComputedValue {
|
||||
kind: self.kind.to_computed_value(context),
|
||||
items: self.items.to_computed_value(context),
|
||||
repeating: self.repeating,
|
||||
compat_mode: self.compat_mode
|
||||
}
|
||||
}
|
||||
|
||||
fn from_computed_value(computed: &Self::ComputedValue) -> Self {
|
||||
Self {
|
||||
kind: SpecifiedGradientKind::from_computed_value(&computed.kind),
|
||||
items: ToComputedValue::from_computed_value(&computed.items),
|
||||
repeating: computed.repeating,
|
||||
compat_mode: computed.compat_mode
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl ToComputedValue for SpecifiedGradientKind {
|
||||
type ComputedValue = GradientKind;
|
||||
|
||||
fn to_computed_value(&self, context: &Context) -> Self::ComputedValue {
|
||||
match self {
|
||||
&GenericGradientKind::Linear(ref line_direction) => {
|
||||
GenericGradientKind::Linear(line_direction.to_computed_value(context))
|
||||
},
|
||||
&GenericGradientKind::Radial(ref ending_shape, ref position, ref angle) => {
|
||||
GenericGradientKind::Radial(ending_shape.to_computed_value(context),
|
||||
position.to_computed_value(context),
|
||||
angle.map(|angle| angle.to_computed_value(context)))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn from_computed_value(computed: &Self::ComputedValue) -> Self {
|
||||
match *computed {
|
||||
GenericGradientKind::Linear(line_direction) => {
|
||||
GenericGradientKind::Linear(SpecifiedLineDirection::from_computed_value(&line_direction))
|
||||
},
|
||||
GenericGradientKind::Radial(ending_shape, position, angle) => {
|
||||
GenericGradientKind::Radial(ToComputedValue::from_computed_value(&ending_shape),
|
||||
ToComputedValue::from_computed_value(&position),
|
||||
angle.map(|angle| ToComputedValue::from_computed_value(&angle)))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -11,7 +11,7 @@ use style_traits::ToCss;
|
|||
use style_traits::values::specified::AllowedLengthType;
|
||||
use super::{Number, ToComputedValue, Context, Percentage};
|
||||
use values::{Auto, CSSFloat, Either, ExtremumLength, None_, Normal, specified};
|
||||
use values::animated::ToAnimatedZero;
|
||||
use values::animated::{Animate, Procedure, ToAnimatedZero};
|
||||
use values::computed::{NonNegativeAu, NonNegativeNumber};
|
||||
use values::distance::{ComputeSquaredDistance, SquaredDistance};
|
||||
use values::generics::NonNegative;
|
||||
|
@ -64,26 +64,16 @@ impl ToComputedValue for specified::Length {
|
|||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Copy, Debug, PartialEq)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[allow(missing_docs)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Copy, Debug, PartialEq, ToAnimatedZero)]
|
||||
pub struct CalcLengthOrPercentage {
|
||||
#[animation(constant)]
|
||||
pub clamping_mode: AllowedLengthType,
|
||||
length: Au,
|
||||
pub percentage: Option<Percentage>,
|
||||
}
|
||||
|
||||
impl ToAnimatedZero for CalcLengthOrPercentage {
|
||||
#[inline]
|
||||
fn to_animated_zero(&self) -> Result<Self, ()> {
|
||||
Ok(CalcLengthOrPercentage {
|
||||
clamping_mode: self.clamping_mode,
|
||||
length: self.length.to_animated_zero()?,
|
||||
percentage: self.percentage.to_animated_zero()?,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
impl ComputeSquaredDistance for CalcLengthOrPercentage {
|
||||
#[inline]
|
||||
fn compute_squared_distance(&self, other: &Self) -> Result<SquaredDistance, ()> {
|
||||
|
@ -285,28 +275,47 @@ impl ToComputedValue for specified::CalcLengthOrPercentage {
|
|||
}
|
||||
|
||||
#[allow(missing_docs)]
|
||||
#[animate(fallback = "Self::animate_fallback")]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Copy, PartialEq, ToAnimatedZero, ToCss)]
|
||||
#[css(derive_debug)]
|
||||
#[derive(Animate, Clone, ComputeSquaredDistance, Copy, PartialEq)]
|
||||
#[derive(ToAnimatedZero, ToCss)]
|
||||
#[distance(fallback = "Self::compute_squared_distance_fallback")]
|
||||
pub enum LengthOrPercentage {
|
||||
Length(Au),
|
||||
Percentage(Percentage),
|
||||
Calc(CalcLengthOrPercentage),
|
||||
}
|
||||
|
||||
impl ComputeSquaredDistance for LengthOrPercentage {
|
||||
#[inline]
|
||||
fn compute_squared_distance(&self, other: &Self) -> Result<SquaredDistance, ()> {
|
||||
match (self, other) {
|
||||
(&LengthOrPercentage::Length(ref this), &LengthOrPercentage::Length(ref other)) => {
|
||||
this.compute_squared_distance(other)
|
||||
},
|
||||
(&LengthOrPercentage::Percentage(ref this), &LengthOrPercentage::Percentage(ref other)) => {
|
||||
this.compute_squared_distance(other)
|
||||
},
|
||||
(this, other) => {
|
||||
CalcLengthOrPercentage::compute_squared_distance(&(*this).into(), &(*other).into())
|
||||
}
|
||||
impl LengthOrPercentage {
|
||||
/// https://drafts.csswg.org/css-transitions/#animtype-lpcalc
|
||||
fn animate_fallback(
|
||||
&self,
|
||||
other: &Self,
|
||||
procedure: Procedure,
|
||||
) -> Result<Self, ()> {
|
||||
// Special handling for zero values since these should not require calc().
|
||||
if self.is_definitely_zero() {
|
||||
return other.to_animated_zero()?.animate(other, procedure);
|
||||
}
|
||||
if other.is_definitely_zero() {
|
||||
return self.animate(&self.to_animated_zero()?, procedure);
|
||||
}
|
||||
|
||||
let this = CalcLengthOrPercentage::from(*self);
|
||||
let other = CalcLengthOrPercentage::from(*other);
|
||||
Ok(LengthOrPercentage::Calc(this.animate(&other, procedure)?))
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn compute_squared_distance_fallback(
|
||||
&self,
|
||||
other: &Self,
|
||||
) -> Result<SquaredDistance, ()> {
|
||||
CalcLengthOrPercentage::compute_squared_distance(
|
||||
&(*self).into(),
|
||||
&(*other).into(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -379,16 +388,6 @@ impl LengthOrPercentage {
|
|||
}
|
||||
}
|
||||
|
||||
impl fmt::Debug for LengthOrPercentage {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
LengthOrPercentage::Length(length) => write!(f, "{:?}", length),
|
||||
LengthOrPercentage::Percentage(percentage) => write!(f, "{}%", percentage.0 * 100.),
|
||||
LengthOrPercentage::Calc(calc) => write!(f, "{:?}", calc),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl ToComputedValue for specified::LengthOrPercentage {
|
||||
type ComputedValue = LengthOrPercentage;
|
||||
|
||||
|
@ -426,8 +425,11 @@ impl ToComputedValue for specified::LengthOrPercentage {
|
|||
}
|
||||
|
||||
#[allow(missing_docs)]
|
||||
#[animate(fallback = "Self::animate_fallback")]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Copy, PartialEq, ToCss)]
|
||||
#[css(derive_debug)]
|
||||
#[derive(Animate, Clone, ComputeSquaredDistance, Copy, PartialEq, ToCss)]
|
||||
#[distance(fallback = "Self::compute_squared_distance_fallback")]
|
||||
pub enum LengthOrPercentageOrAuto {
|
||||
Length(Au),
|
||||
Percentage(Percentage),
|
||||
|
@ -435,20 +437,29 @@ pub enum LengthOrPercentageOrAuto {
|
|||
Calc(CalcLengthOrPercentage),
|
||||
}
|
||||
|
||||
impl ComputeSquaredDistance for LengthOrPercentageOrAuto {
|
||||
impl LengthOrPercentageOrAuto {
|
||||
/// https://drafts.csswg.org/css-transitions/#animtype-lpcalc
|
||||
fn animate_fallback(
|
||||
&self,
|
||||
other: &Self,
|
||||
procedure: Procedure,
|
||||
) -> Result<Self, ()> {
|
||||
let this = <Option<CalcLengthOrPercentage>>::from(*self);
|
||||
let other = <Option<CalcLengthOrPercentage>>::from(*other);
|
||||
Ok(LengthOrPercentageOrAuto::Calc(
|
||||
this.animate(&other, procedure)?.ok_or(())?,
|
||||
))
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn compute_squared_distance(&self, other: &Self) -> Result<SquaredDistance, ()> {
|
||||
match (self, other) {
|
||||
(&LengthOrPercentageOrAuto::Length(ref this), &LengthOrPercentageOrAuto::Length(ref other)) => {
|
||||
this.compute_squared_distance(other)
|
||||
},
|
||||
(&LengthOrPercentageOrAuto::Percentage(ref this), &LengthOrPercentageOrAuto::Percentage(ref other)) => {
|
||||
this.compute_squared_distance(other)
|
||||
},
|
||||
(this, other) => {
|
||||
<Option<CalcLengthOrPercentage>>::compute_squared_distance(&(*this).into(), &(*other).into())
|
||||
}
|
||||
}
|
||||
fn compute_squared_distance_fallback(
|
||||
&self,
|
||||
other: &Self,
|
||||
) -> Result<SquaredDistance, ()> {
|
||||
<Option<CalcLengthOrPercentage>>::compute_squared_distance(
|
||||
&(*self).into(),
|
||||
&(*other).into(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -467,17 +478,6 @@ impl LengthOrPercentageOrAuto {
|
|||
}
|
||||
}
|
||||
|
||||
impl fmt::Debug for LengthOrPercentageOrAuto {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
LengthOrPercentageOrAuto::Length(length) => write!(f, "{:?}", length),
|
||||
LengthOrPercentageOrAuto::Percentage(percentage) => write!(f, "{}%", percentage.0 * 100.),
|
||||
LengthOrPercentageOrAuto::Auto => write!(f, "auto"),
|
||||
LengthOrPercentageOrAuto::Calc(calc) => write!(f, "{:?}", calc),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl ToComputedValue for specified::LengthOrPercentageOrAuto {
|
||||
type ComputedValue = LengthOrPercentageOrAuto;
|
||||
|
||||
|
@ -521,8 +521,11 @@ impl ToComputedValue for specified::LengthOrPercentageOrAuto {
|
|||
}
|
||||
|
||||
#[allow(missing_docs)]
|
||||
#[animate(fallback = "Self::animate_fallback")]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Copy, PartialEq, ToCss)]
|
||||
#[css(derive_debug)]
|
||||
#[derive(Animate, Clone, ComputeSquaredDistance, Copy, PartialEq, ToCss)]
|
||||
#[distance(fallback = "Self::compute_squared_distance_fallback")]
|
||||
pub enum LengthOrPercentageOrNone {
|
||||
Length(Au),
|
||||
Percentage(Percentage),
|
||||
|
@ -530,20 +533,28 @@ pub enum LengthOrPercentageOrNone {
|
|||
None,
|
||||
}
|
||||
|
||||
impl ComputeSquaredDistance for LengthOrPercentageOrNone {
|
||||
#[inline]
|
||||
fn compute_squared_distance(&self, other: &Self) -> Result<SquaredDistance, ()> {
|
||||
match (self, other) {
|
||||
(&LengthOrPercentageOrNone::Length(ref this), &LengthOrPercentageOrNone::Length(ref other)) => {
|
||||
this.compute_squared_distance(other)
|
||||
},
|
||||
(&LengthOrPercentageOrNone::Percentage(ref this), &LengthOrPercentageOrNone::Percentage(ref other)) => {
|
||||
this.compute_squared_distance(other)
|
||||
},
|
||||
(this, other) => {
|
||||
<Option<CalcLengthOrPercentage>>::compute_squared_distance(&(*this).into(), &(*other).into())
|
||||
}
|
||||
}
|
||||
impl LengthOrPercentageOrNone {
|
||||
/// https://drafts.csswg.org/css-transitions/#animtype-lpcalc
|
||||
fn animate_fallback(
|
||||
&self,
|
||||
other: &Self,
|
||||
procedure: Procedure,
|
||||
) -> Result<Self, ()> {
|
||||
let this = <Option<CalcLengthOrPercentage>>::from(*self);
|
||||
let other = <Option<CalcLengthOrPercentage>>::from(*other);
|
||||
Ok(LengthOrPercentageOrNone::Calc(
|
||||
this.animate(&other, procedure)?.ok_or(())?,
|
||||
))
|
||||
}
|
||||
|
||||
fn compute_squared_distance_fallback(
|
||||
&self,
|
||||
other: &Self,
|
||||
) -> Result<SquaredDistance, ()> {
|
||||
<Option<CalcLengthOrPercentage>>::compute_squared_distance(
|
||||
&(*self).into(),
|
||||
&(*other).into(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -559,17 +570,6 @@ impl LengthOrPercentageOrNone {
|
|||
}
|
||||
}
|
||||
|
||||
impl fmt::Debug for LengthOrPercentageOrNone {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
LengthOrPercentageOrNone::Length(length) => write!(f, "{:?}", length),
|
||||
LengthOrPercentageOrNone::Percentage(percentage) => write!(f, "{}%", percentage.0 * 100.),
|
||||
LengthOrPercentageOrNone::Calc(calc) => write!(f, "{:?}", calc),
|
||||
LengthOrPercentageOrNone::None => write!(f, "none"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl ToComputedValue for specified::LengthOrPercentageOrNone {
|
||||
type ComputedValue = LengthOrPercentageOrNone;
|
||||
|
||||
|
@ -695,28 +695,14 @@ pub type NonNegativeLengthOrNumber = Either<NonNegativeLength, NonNegativeNumber
|
|||
/// See values/specified/length.rs for more details.
|
||||
#[allow(missing_docs)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Copy, Debug, PartialEq, ToCss)]
|
||||
#[derive(Animate, Clone, ComputeSquaredDistance, Copy, Debug, PartialEq)]
|
||||
#[derive(ToAnimatedZero, ToCss)]
|
||||
pub enum MozLength {
|
||||
LengthOrPercentageOrAuto(LengthOrPercentageOrAuto),
|
||||
#[animation(error)]
|
||||
ExtremumLength(ExtremumLength),
|
||||
}
|
||||
|
||||
impl ComputeSquaredDistance for MozLength {
|
||||
#[inline]
|
||||
fn compute_squared_distance(&self, other: &Self) -> Result<SquaredDistance, ()> {
|
||||
match (self, other) {
|
||||
(&MozLength::LengthOrPercentageOrAuto(ref this), &MozLength::LengthOrPercentageOrAuto(ref other)) => {
|
||||
this.compute_squared_distance(other)
|
||||
},
|
||||
_ => {
|
||||
// FIXME(nox): Should this return `Ok(SquaredDistance::Value(1.))`
|
||||
// when `self` and `other` are the same extremum value?
|
||||
Err(())
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl MozLength {
|
||||
/// Returns the `auto` value.
|
||||
pub fn auto() -> Self {
|
||||
|
@ -755,28 +741,13 @@ impl ToComputedValue for specified::MozLength {
|
|||
/// See values/specified/length.rs for more details.
|
||||
#[allow(missing_docs)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Copy, Debug, PartialEq, ToCss)]
|
||||
#[derive(Animate, Clone, ComputeSquaredDistance, Copy, Debug, PartialEq, ToCss)]
|
||||
pub enum MaxLength {
|
||||
LengthOrPercentageOrNone(LengthOrPercentageOrNone),
|
||||
#[animation(error)]
|
||||
ExtremumLength(ExtremumLength),
|
||||
}
|
||||
|
||||
impl ComputeSquaredDistance for MaxLength {
|
||||
#[inline]
|
||||
fn compute_squared_distance(&self, other: &Self) -> Result<SquaredDistance, ()> {
|
||||
match (self, other) {
|
||||
(&MaxLength::LengthOrPercentageOrNone(ref this), &MaxLength::LengthOrPercentageOrNone(ref other)) => {
|
||||
this.compute_squared_distance(other)
|
||||
},
|
||||
_ => {
|
||||
// FIXME(nox): Should this return `Ok(SquaredDistance::Value(1.))`
|
||||
// when `self` and `other` are the same extremum value?
|
||||
Err(())
|
||||
},
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl MaxLength {
|
||||
/// Returns the `none` value.
|
||||
pub fn none() -> Self {
|
||||
|
|
|
@ -199,6 +199,11 @@ impl<'a, 'cx, 'cx_a: 'cx, S: ToComputedValue + 'a> Iterator for ComputedVecIter<
|
|||
}
|
||||
|
||||
/// A trait to represent the conversion between computed and specified values.
|
||||
///
|
||||
/// This trait is derivable with `#[derive(ToComputedValue)]`. The derived
|
||||
/// implementation just calls `ToComputedValue::to_computed_value` on each field
|
||||
/// of the passed value, or `Clone::clone` if the field is annotated with
|
||||
/// `#[compute(clone)]`.
|
||||
pub trait ToComputedValue {
|
||||
/// The computed value type we're going to be converted to.
|
||||
type ComputedValue;
|
||||
|
@ -327,6 +332,7 @@ impl<T> ToComputedValue for T
|
|||
|
||||
impl ComputedValueAsSpecified for Atom {}
|
||||
impl ComputedValueAsSpecified for bool {}
|
||||
impl ComputedValueAsSpecified for f32 {}
|
||||
|
||||
impl ComputedValueAsSpecified for specified::BorderStyle {}
|
||||
|
||||
|
|
|
@ -10,6 +10,17 @@ use std::iter::Sum;
|
|||
use std::ops::Add;
|
||||
|
||||
/// A trait to compute squared distances between two animatable values.
|
||||
///
|
||||
/// This trait is derivable with `#[derive(ComputeSquaredDistance)]`. The derived
|
||||
/// implementation uses a `match` expression with identical patterns for both
|
||||
/// `self` and `other`, calling `ComputeSquaredDistance::compute_squared_distance`
|
||||
/// on each fields of the values.
|
||||
///
|
||||
/// If a variant is annotated with `#[animation(error)]`, the corresponding
|
||||
/// `match` arm is not generated.
|
||||
///
|
||||
/// If the two values are not similar, an error is returned unless a fallback
|
||||
/// function has been specified through `#[distance(fallback)]`.
|
||||
pub trait ComputeSquaredDistance {
|
||||
/// Computes the squared distance between two animatable values.
|
||||
fn compute_squared_distance(&self, other: &Self) -> Result<SquaredDistance, ()>;
|
||||
|
|
|
@ -5,8 +5,9 @@
|
|||
//! Generic types for CSS values related to backgrounds.
|
||||
|
||||
/// A generic value for the `background-size` property.
|
||||
#[derive(Clone, ComputeSquaredDistance, Copy, Debug, HasViewportPercentage, PartialEq, ToComputedValue, ToCss)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Animate, Clone, ComputeSquaredDistance, Copy, Debug)]
|
||||
#[derive(HasViewportPercentage, PartialEq, ToComputedValue, ToCss)]
|
||||
pub enum BackgroundSize<LengthOrPercentageOrAuto> {
|
||||
/// `<width> <height>`
|
||||
Explicit {
|
||||
|
@ -16,8 +17,10 @@ pub enum BackgroundSize<LengthOrPercentageOrAuto> {
|
|||
height: LengthOrPercentageOrAuto
|
||||
},
|
||||
/// `cover`
|
||||
#[animation(error)]
|
||||
Cover,
|
||||
/// `contain`
|
||||
#[animation(error)]
|
||||
Contain,
|
||||
}
|
||||
|
||||
|
|
|
@ -44,11 +44,18 @@ add_impls_for_keyword_enum!(ShapeBox);
|
|||
/// A shape source, for some reference box.
|
||||
#[allow(missing_docs)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, PartialEq, ToComputedValue, ToCss)]
|
||||
#[derive(Animate, Clone, Debug, PartialEq, ToComputedValue, ToCss)]
|
||||
pub enum ShapeSource<BasicShape, ReferenceBox, Url> {
|
||||
#[animation(error)]
|
||||
Url(Url),
|
||||
Shape(BasicShape, Option<ReferenceBox>),
|
||||
Shape(
|
||||
BasicShape,
|
||||
#[animation(constant)]
|
||||
Option<ReferenceBox>,
|
||||
),
|
||||
#[animation(error)]
|
||||
Box(ReferenceBox),
|
||||
#[animation(error)]
|
||||
None,
|
||||
}
|
||||
|
||||
|
@ -94,10 +101,13 @@ pub struct Ellipse<H, V, LengthOrPercentage> {
|
|||
/// https://drafts.csswg.org/css-shapes/#typedef-shape-radius
|
||||
#[allow(missing_docs)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, ComputeSquaredDistance, Copy, Debug, PartialEq, ToComputedValue, ToCss)]
|
||||
#[derive(Animate, Clone, ComputeSquaredDistance, Copy, Debug, PartialEq)]
|
||||
#[derive(ToComputedValue, ToCss)]
|
||||
pub enum ShapeRadius<LengthOrPercentage> {
|
||||
Length(LengthOrPercentage),
|
||||
#[animation(error)]
|
||||
ClosestSide,
|
||||
#[animation(error)]
|
||||
FarthestSide,
|
||||
}
|
||||
|
||||
|
@ -123,29 +133,6 @@ define_css_keyword_enum!(FillRule:
|
|||
);
|
||||
add_impls_for_keyword_enum!(FillRule);
|
||||
|
||||
// FIXME(nox): This should be derivable, but we need to implement Animate
|
||||
// on the T types.
|
||||
impl<B, T, U> Animate for ShapeSource<B, T, U>
|
||||
where
|
||||
B: Animate,
|
||||
T: Clone + PartialEq,
|
||||
{
|
||||
fn animate(&self, other: &Self, procedure: Procedure) -> Result<Self, ()> {
|
||||
match (self, other) {
|
||||
(
|
||||
&ShapeSource::Shape(ref this, ref this_box),
|
||||
&ShapeSource::Shape(ref other, ref other_box),
|
||||
) if this_box == other_box => {
|
||||
Ok(ShapeSource::Shape(
|
||||
this.animate(other, procedure)?,
|
||||
this_box.clone(),
|
||||
))
|
||||
},
|
||||
_ => Err(()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// FIXME(nox): Implement ComputeSquaredDistance for T types and stop
|
||||
// using PartialEq here, this will let us derive this impl.
|
||||
impl<B, T, U> ComputeSquaredDistance for ShapeSource<B, T, U>
|
||||
|
@ -191,20 +178,6 @@ impl<L> ToCss for InsetRect<L>
|
|||
}
|
||||
}
|
||||
|
||||
impl<L> Animate for ShapeRadius<L>
|
||||
where
|
||||
L: Animate,
|
||||
{
|
||||
fn animate(&self, other: &Self, procedure: Procedure) -> Result<Self, ()> {
|
||||
match (self, other) {
|
||||
(&ShapeRadius::Length(ref this), &ShapeRadius::Length(ref other)) => {
|
||||
Ok(ShapeRadius::Length(this.animate(other, procedure)?))
|
||||
},
|
||||
_ => Err(()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<L> Default for ShapeRadius<L> {
|
||||
#[inline]
|
||||
fn default() -> Self { ShapeRadius::ClosestSide }
|
||||
|
|
|
@ -11,13 +11,15 @@ use values::specified::url::SpecifiedUrl;
|
|||
|
||||
/// A generic value for a single `box-shadow`.
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, HasViewportPercentage, PartialEq, ToAnimatedValue)]
|
||||
#[derive(Animate, Clone, Debug, HasViewportPercentage, PartialEq)]
|
||||
#[derive(ToAnimatedValue, ToAnimatedZero)]
|
||||
pub struct BoxShadow<Color, SizeLength, BlurShapeLength, ShapeLength> {
|
||||
/// The base shadow.
|
||||
pub base: SimpleShadow<Color, SizeLength, BlurShapeLength>,
|
||||
/// The spread radius.
|
||||
pub spread: ShapeLength,
|
||||
/// Whether this is an inset box shadow.
|
||||
#[animation(constant)]
|
||||
pub inset: bool,
|
||||
}
|
||||
|
||||
|
|
|
@ -10,7 +10,7 @@ use parser::{Parse, ParserContext};
|
|||
use std::{fmt, mem, usize};
|
||||
use style_traits::{ToCss, ParseError, StyleParseError};
|
||||
use values::{CSSFloat, CustomIdent, serialize_dimension};
|
||||
use values::computed::{ComputedValueAsSpecified, Context, ToComputedValue};
|
||||
use values::computed::ComputedValueAsSpecified;
|
||||
use values::specified::Integer;
|
||||
use values::specified::grid::parse_line_names;
|
||||
|
||||
|
@ -137,13 +137,14 @@ define_css_keyword_enum!{ TrackKeyword:
|
|||
"max-content" => MaxContent,
|
||||
"min-content" => MinContent
|
||||
}
|
||||
impl ComputedValueAsSpecified for TrackKeyword {}
|
||||
|
||||
#[derive(Clone, Debug, PartialEq)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
/// A track breadth for explicit grid track sizing. It's generic solely to
|
||||
/// avoid re-implementing it for the computed type.
|
||||
///
|
||||
/// https://drafts.csswg.org/css-grid/#typedef-track-breadth
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, PartialEq, ToComputedValue)]
|
||||
pub enum TrackBreadth<L> {
|
||||
/// The generic type is almost always a non-negative `<length-percentage>`
|
||||
Breadth(L),
|
||||
|
@ -176,35 +177,12 @@ impl<L: ToCss> ToCss for TrackBreadth<L> {
|
|||
}
|
||||
}
|
||||
|
||||
impl<L: ToComputedValue> ToComputedValue for TrackBreadth<L> {
|
||||
type ComputedValue = TrackBreadth<L::ComputedValue>;
|
||||
|
||||
#[inline]
|
||||
fn to_computed_value(&self, context: &Context) -> Self::ComputedValue {
|
||||
match *self {
|
||||
TrackBreadth::Breadth(ref lop) => TrackBreadth::Breadth(lop.to_computed_value(context)),
|
||||
TrackBreadth::Flex(fr) => TrackBreadth::Flex(fr),
|
||||
TrackBreadth::Keyword(k) => TrackBreadth::Keyword(k),
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn from_computed_value(computed: &Self::ComputedValue) -> Self {
|
||||
match *computed {
|
||||
TrackBreadth::Breadth(ref lop) =>
|
||||
TrackBreadth::Breadth(ToComputedValue::from_computed_value(lop)),
|
||||
TrackBreadth::Flex(fr) => TrackBreadth::Flex(fr),
|
||||
TrackBreadth::Keyword(k) => TrackBreadth::Keyword(k),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// A `<track-size>` type for explicit grid track sizing. Like `<track-breadth>`, this is
|
||||
/// generic only to avoid code bloat. It only takes `<length-percentage>`
|
||||
///
|
||||
/// https://drafts.csswg.org/css-grid/#typedef-track-size
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, HasViewportPercentage, PartialEq)]
|
||||
#[derive(Clone, Debug, HasViewportPercentage, PartialEq, ToComputedValue)]
|
||||
pub enum TrackSize<L> {
|
||||
/// A flexible `<track-breadth>`
|
||||
Breadth(TrackBreadth<L>),
|
||||
|
@ -286,39 +264,6 @@ impl<L: ToCss> ToCss for TrackSize<L> {
|
|||
}
|
||||
}
|
||||
|
||||
impl<L: ToComputedValue> ToComputedValue for TrackSize<L> {
|
||||
type ComputedValue = TrackSize<L::ComputedValue>;
|
||||
|
||||
#[inline]
|
||||
fn to_computed_value(&self, context: &Context) -> Self::ComputedValue {
|
||||
match *self {
|
||||
TrackSize::Breadth(ref b) => match *b {
|
||||
// <flex> outside `minmax()` expands to `mimmax(auto, <flex>)`
|
||||
// https://drafts.csswg.org/css-grid/#valdef-grid-template-columns-flex
|
||||
TrackBreadth::Flex(f) =>
|
||||
TrackSize::Minmax(TrackBreadth::Keyword(TrackKeyword::Auto), TrackBreadth::Flex(f)),
|
||||
_ => TrackSize::Breadth(b.to_computed_value(context)),
|
||||
},
|
||||
TrackSize::Minmax(ref b_1, ref b_2) =>
|
||||
TrackSize::Minmax(b_1.to_computed_value(context), b_2.to_computed_value(context)),
|
||||
TrackSize::FitContent(ref lop) => TrackSize::FitContent(lop.to_computed_value(context)),
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn from_computed_value(computed: &Self::ComputedValue) -> Self {
|
||||
match *computed {
|
||||
TrackSize::Breadth(ref b) =>
|
||||
TrackSize::Breadth(ToComputedValue::from_computed_value(b)),
|
||||
TrackSize::Minmax(ref b_1, ref b_2) =>
|
||||
TrackSize::Minmax(ToComputedValue::from_computed_value(b_1),
|
||||
ToComputedValue::from_computed_value(b_2)),
|
||||
TrackSize::FitContent(ref lop) =>
|
||||
TrackSize::FitContent(ToComputedValue::from_computed_value(lop)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Helper function for serializing identifiers with a prefix and suffix, used
|
||||
/// for serializing <line-names> (in grid).
|
||||
pub fn concat_serialize_idents<W>(prefix: &str, suffix: &str,
|
||||
|
@ -382,8 +327,8 @@ no_viewport_percentage!(RepeatCount);
|
|||
///
|
||||
/// It can also hold `repeat()` function parameters, which expands into the respective
|
||||
/// values in its computed form.
|
||||
#[derive(Clone, Debug, PartialEq)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, PartialEq, ToComputedValue)]
|
||||
pub struct TrackRepeat<L> {
|
||||
/// The number of times for the value to be repeated (could also be `auto-fit` or `auto-fill`)
|
||||
pub count: RepeatCount,
|
||||
|
@ -392,6 +337,7 @@ pub struct TrackRepeat<L> {
|
|||
/// If there's no `<line-names>`, then it's represented by an empty vector.
|
||||
/// For N `<track-size>` values, there will be N+1 `<line-names>`, and so this vector's
|
||||
/// length is always one value more than that of the `<track-size>`.
|
||||
#[compute(clone)]
|
||||
pub line_names: Box<[Box<[CustomIdent]>]>,
|
||||
/// `<track-size>` values.
|
||||
pub track_sizes: Vec<TrackSize<L>>,
|
||||
|
@ -479,31 +425,6 @@ impl<L: Clone> TrackRepeat<L> {
|
|||
}
|
||||
}
|
||||
}
|
||||
impl<L: ToComputedValue> ToComputedValue for TrackRepeat<L> {
|
||||
type ComputedValue = TrackRepeat<L::ComputedValue>;
|
||||
|
||||
#[inline]
|
||||
fn to_computed_value(&self, context: &Context) -> Self::ComputedValue {
|
||||
TrackRepeat {
|
||||
count: self.count,
|
||||
track_sizes: self.track_sizes.iter()
|
||||
.map(|val| val.to_computed_value(context))
|
||||
.collect(),
|
||||
line_names: self.line_names.clone(),
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn from_computed_value(computed: &Self::ComputedValue) -> Self {
|
||||
TrackRepeat {
|
||||
count: computed.count,
|
||||
track_sizes: computed.track_sizes.iter()
|
||||
.map(ToComputedValue::from_computed_value)
|
||||
.collect(),
|
||||
line_names: computed.line_names.clone(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// The type of a `<track-list>` as determined during parsing.
|
||||
///
|
||||
|
@ -533,8 +454,8 @@ impl ComputedValueAsSpecified for TrackListType {}
|
|||
/// A grid `<track-list>` type.
|
||||
///
|
||||
/// https://drafts.csswg.org/css-grid/#typedef-track-list
|
||||
#[derive(Clone, Debug, PartialEq)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, PartialEq, ToComputedValue)]
|
||||
pub struct TrackList<T> {
|
||||
/// The type of this `<track-list>` (auto, explicit or general).
|
||||
///
|
||||
|
@ -548,6 +469,7 @@ pub struct TrackList<T> {
|
|||
/// If there's no `<line-names>`, then it's represented by an empty vector.
|
||||
/// For N values, there will be N+1 `<line-names>`, and so this vector's
|
||||
/// length is always one value more than that of the `<track-size>`.
|
||||
#[compute(clone)]
|
||||
pub line_names: Box<[Box<[CustomIdent]>]>,
|
||||
/// `<auto-repeat>` value. There can only be one `<auto-repeat>` in a TrackList.
|
||||
pub auto_repeat: Option<TrackRepeat<T>>,
|
||||
|
@ -698,8 +620,8 @@ no_viewport_percentage!(LineNameList);
|
|||
/// Variants for `<grid-template-rows> | <grid-template-columns>`
|
||||
/// Subgrid deferred to Level 2 spec due to lack of implementation.
|
||||
/// But it's implemented in gecko, so we have to as well.
|
||||
#[derive(Clone, Debug, PartialEq, ToCss)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, PartialEq, ToComputedValue, ToCss)]
|
||||
pub enum GridTemplateComponent<L> {
|
||||
/// `none` value.
|
||||
None,
|
||||
|
|
|
@ -35,16 +35,18 @@ pub enum Image<Gradient, MozImageRect, ImageUrl> {
|
|||
|
||||
/// A CSS gradient.
|
||||
/// https://drafts.csswg.org/css-images/#gradients
|
||||
#[derive(Clone, Debug, HasViewportPercentage, PartialEq)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, HasViewportPercentage, PartialEq, ToComputedValue)]
|
||||
pub struct Gradient<LineDirection, Length, LengthOrPercentage, Position, Color, Angle> {
|
||||
/// Gradients can be linear or radial.
|
||||
pub kind: GradientKind<LineDirection, Length, LengthOrPercentage, Position, Angle>,
|
||||
/// The color stops and interpolation hints.
|
||||
pub items: Vec<GradientItem<Color, LengthOrPercentage>>,
|
||||
/// True if this is a repeating gradient.
|
||||
#[compute(clone)]
|
||||
pub repeating: bool,
|
||||
/// Compatibility mode.
|
||||
#[compute(clone)]
|
||||
pub compat_mode: CompatMode,
|
||||
}
|
||||
|
||||
|
@ -61,8 +63,8 @@ pub enum CompatMode {
|
|||
}
|
||||
|
||||
/// A gradient kind.
|
||||
#[derive(Clone, Copy, Debug, HasViewportPercentage, PartialEq)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Copy, Debug, HasViewportPercentage, PartialEq, ToComputedValue)]
|
||||
pub enum GradientKind<LineDirection, Length, LengthOrPercentage, Position, Angle> {
|
||||
/// A linear gradient.
|
||||
Linear(LineDirection),
|
||||
|
|
|
@ -16,7 +16,8 @@ use values::distance::{ComputeSquaredDistance, SquaredDistance};
|
|||
///
|
||||
/// https://www.w3.org/TR/SVG2/painting.html#SpecifyingPaint
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, PartialEq, ToAnimatedValue, ToComputedValue, ToCss)]
|
||||
#[derive(Animate, Clone, ComputeSquaredDistance, Debug, PartialEq)]
|
||||
#[derive(ToAnimatedValue, ToComputedValue, ToCss)]
|
||||
pub struct SVGPaint<ColorType, UrlPaintServer> {
|
||||
/// The paint source
|
||||
pub kind: SVGPaintKind<ColorType, UrlPaintServer>,
|
||||
|
@ -30,13 +31,15 @@ pub struct SVGPaint<ColorType, UrlPaintServer> {
|
|||
/// to have a fallback, Gecko lets the context
|
||||
/// properties have a fallback as well.
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[derive(Clone, Debug, PartialEq, ToAnimatedValue, ToComputedValue, ToCss)]
|
||||
#[derive(Animate, Clone, ComputeSquaredDistance, Debug, PartialEq)]
|
||||
#[derive(ToAnimatedValue, ToAnimatedZero, ToComputedValue, ToCss)]
|
||||
pub enum SVGPaintKind<ColorType, UrlPaintServer> {
|
||||
/// `none`
|
||||
None,
|
||||
/// `<color>`
|
||||
Color(ColorType),
|
||||
/// `url(...)`
|
||||
#[animation(error)]
|
||||
PaintServer(UrlPaintServer),
|
||||
/// `context-fill`
|
||||
ContextFill,
|
||||
|
|
|
@ -11,7 +11,6 @@ use std::ascii::AsciiExt;
|
|||
use std::mem;
|
||||
use style_traits::{HasViewportPercentage, ParseError, StyleParseError};
|
||||
use values::{CSSFloat, CustomIdent};
|
||||
use values::computed::{self, Context, ToComputedValue};
|
||||
use values::generics::grid::{GridTemplateComponent, RepeatCount, TrackBreadth, TrackKeyword, TrackRepeat};
|
||||
use values::generics::grid::{LineNameList, TrackSize, TrackList, TrackListType};
|
||||
use values::specified::LengthOrPercentage;
|
||||
|
@ -286,42 +285,6 @@ impl HasViewportPercentage for TrackList<LengthOrPercentage> {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
impl ToComputedValue for TrackList<LengthOrPercentage> {
|
||||
type ComputedValue = TrackList<computed::LengthOrPercentage>;
|
||||
|
||||
#[inline]
|
||||
fn to_computed_value(&self, context: &Context) -> Self::ComputedValue {
|
||||
let mut values = Vec::with_capacity(self.values.len() + 1);
|
||||
for value in self.values.iter().map(|val| val.to_computed_value(context)) {
|
||||
values.push(value);
|
||||
}
|
||||
|
||||
TrackList {
|
||||
list_type: self.list_type.to_computed_value(context),
|
||||
values: values,
|
||||
line_names: self.line_names.clone(),
|
||||
auto_repeat: self.auto_repeat.clone().map(|repeat| repeat.to_computed_value(context)),
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn from_computed_value(computed: &Self::ComputedValue) -> Self {
|
||||
let mut values = Vec::with_capacity(computed.values.len() + 1);
|
||||
for value in computed.values.iter().map(ToComputedValue::from_computed_value) {
|
||||
values.push(value);
|
||||
}
|
||||
|
||||
TrackList {
|
||||
list_type: computed.list_type,
|
||||
values: values,
|
||||
line_names: computed.line_names.clone(),
|
||||
auto_repeat: computed.auto_repeat.clone().map(|ref repeat| TrackRepeat::from_computed_value(repeat)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
impl Parse for GridTemplateComponent<LengthOrPercentage> {
|
||||
// FIXME: Derive Parse (probably with None_)
|
||||
fn parse<'i, 't>(context: &ParserContext, input: &mut Parser<'i, 't>) -> Result<Self, ParseError<'i>> {
|
||||
|
@ -354,27 +317,3 @@ impl HasViewportPercentage for GridTemplateComponent<LengthOrPercentage> {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl ToComputedValue for GridTemplateComponent<LengthOrPercentage> {
|
||||
type ComputedValue = GridTemplateComponent<computed::LengthOrPercentage>;
|
||||
|
||||
#[inline]
|
||||
fn to_computed_value(&self, context: &Context) -> Self::ComputedValue {
|
||||
match *self {
|
||||
GridTemplateComponent::None => GridTemplateComponent::None,
|
||||
GridTemplateComponent::TrackList(ref l) => GridTemplateComponent::TrackList(l.to_computed_value(context)),
|
||||
GridTemplateComponent::Subgrid(ref n) => GridTemplateComponent::Subgrid(n.to_computed_value(context)),
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn from_computed_value(computed: &Self::ComputedValue) -> Self {
|
||||
match *computed {
|
||||
GridTemplateComponent::None => GridTemplateComponent::None,
|
||||
GridTemplateComponent::TrackList(ref l) =>
|
||||
GridTemplateComponent::TrackList(ToComputedValue::from_computed_value(l)),
|
||||
GridTemplateComponent::Subgrid(ref n) =>
|
||||
GridTemplateComponent::Subgrid(ToComputedValue::from_computed_value(n)),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue