mirror of
https://github.com/servo/servo.git
synced 2025-08-05 13:40:08 +01:00
style: Share computed and specified value representation of -moz-context-properties.
Differential Revision: https://phabricator.services.mozilla.com/D30545
This commit is contained in:
parent
2bc4c42d45
commit
bbc77e3977
6 changed files with 89 additions and 70 deletions
|
@ -53,6 +53,7 @@ macro_rules! local_name {
|
||||||
/// This is either a strong reference to a dynamic atom (an nsAtom pointer),
|
/// This is either a strong reference to a dynamic atom (an nsAtom pointer),
|
||||||
/// or an offset from gGkAtoms to the nsStaticAtom object.
|
/// or an offset from gGkAtoms to the nsStaticAtom object.
|
||||||
#[derive(Eq, PartialEq)]
|
#[derive(Eq, PartialEq)]
|
||||||
|
#[repr(C)]
|
||||||
pub struct Atom(usize);
|
pub struct Atom(usize);
|
||||||
|
|
||||||
/// An atom *without* a strong reference.
|
/// An atom *without* a strong reference.
|
||||||
|
|
|
@ -303,14 +303,14 @@ impl ${style_struct.gecko_struct_name} {
|
||||||
<%def name="impl_simple_clone(ident, gecko_ffi_name)">
|
<%def name="impl_simple_clone(ident, gecko_ffi_name)">
|
||||||
#[allow(non_snake_case)]
|
#[allow(non_snake_case)]
|
||||||
pub fn clone_${ident}(&self) -> longhands::${ident}::computed_value::T {
|
pub fn clone_${ident}(&self) -> longhands::${ident}::computed_value::T {
|
||||||
From::from(self.gecko.${gecko_ffi_name})
|
From::from(self.gecko.${gecko_ffi_name}.clone())
|
||||||
}
|
}
|
||||||
</%def>
|
</%def>
|
||||||
|
|
||||||
<%def name="impl_simple_copy(ident, gecko_ffi_name, *kwargs)">
|
<%def name="impl_simple_copy(ident, gecko_ffi_name, *kwargs)">
|
||||||
#[allow(non_snake_case)]
|
#[allow(non_snake_case)]
|
||||||
pub fn copy_${ident}_from(&mut self, other: &Self) {
|
pub fn copy_${ident}_from(&mut self, other: &Self) {
|
||||||
self.gecko.${gecko_ffi_name} = other.gecko.${gecko_ffi_name};
|
self.gecko.${gecko_ffi_name} = other.gecko.${gecko_ffi_name}.clone();
|
||||||
}
|
}
|
||||||
|
|
||||||
#[allow(non_snake_case)]
|
#[allow(non_snake_case)]
|
||||||
|
@ -4120,7 +4120,7 @@ clip-path
|
||||||
</%self:impl_trait>
|
</%self:impl_trait>
|
||||||
|
|
||||||
<%self:impl_trait style_struct_name="InheritedSVG"
|
<%self:impl_trait style_struct_name="InheritedSVG"
|
||||||
skip_longhands="paint-order stroke-dasharray -moz-context-properties">
|
skip_longhands="paint-order stroke-dasharray">
|
||||||
pub fn set_paint_order(&mut self, v: longhands::paint_order::computed_value::T) {
|
pub fn set_paint_order(&mut self, v: longhands::paint_order::computed_value::T) {
|
||||||
self.gecko.mPaintOrder = v.0;
|
self.gecko.mPaintOrder = v.0;
|
||||||
}
|
}
|
||||||
|
@ -4180,60 +4180,6 @@ clip-path
|
||||||
}
|
}
|
||||||
SVGStrokeDashArray::Values(self.gecko.mStrokeDasharray.iter().cloned().collect())
|
SVGStrokeDashArray::Values(self.gecko.mStrokeDasharray.iter().cloned().collect())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[allow(non_snake_case)]
|
|
||||||
pub fn _moz_context_properties_count(&self) -> usize {
|
|
||||||
self.gecko.mContextProps.len()
|
|
||||||
}
|
|
||||||
|
|
||||||
// FIXME(emilio): Remove by sharing representation.
|
|
||||||
#[allow(non_snake_case)]
|
|
||||||
pub fn clone__moz_context_properties(&self) -> longhands::_moz_context_properties::computed_value::T {
|
|
||||||
use crate::values::specified::svg::MozContextProperties;
|
|
||||||
let buf = self.gecko.mContextProps.iter().map(|v| {
|
|
||||||
MozContextProperties(CustomIdent(unsafe { Atom::from_raw(v.mRawPtr) }))
|
|
||||||
}).collect::<Vec<_>>();
|
|
||||||
longhands::_moz_context_properties::computed_value::List(crate::ArcSlice::from_iter(buf.into_iter()))
|
|
||||||
}
|
|
||||||
|
|
||||||
#[allow(non_snake_case)]
|
|
||||||
pub fn set__moz_context_properties<I>(&mut self, v: I)
|
|
||||||
where
|
|
||||||
I: IntoIterator<Item = longhands::_moz_context_properties::computed_value::single_value::T>,
|
|
||||||
I::IntoIter: ExactSizeIterator
|
|
||||||
{
|
|
||||||
let v = v.into_iter();
|
|
||||||
unsafe {
|
|
||||||
bindings::Gecko_nsStyleSVG_SetContextPropertiesLength(&mut *self.gecko, v.len() as u32);
|
|
||||||
}
|
|
||||||
|
|
||||||
let s = &mut *self.gecko;
|
|
||||||
s.mContextPropsBits = 0;
|
|
||||||
for (gecko, servo) in s.mContextProps.iter_mut().zip(v) {
|
|
||||||
if (servo.0).0 == atom!("fill") {
|
|
||||||
s.mContextPropsBits |= structs::NS_STYLE_CONTEXT_PROPERTY_FILL as u8;
|
|
||||||
} else if (servo.0).0 == atom!("stroke") {
|
|
||||||
s.mContextPropsBits |= structs::NS_STYLE_CONTEXT_PROPERTY_STROKE as u8;
|
|
||||||
} else if (servo.0).0 == atom!("fill-opacity") {
|
|
||||||
s.mContextPropsBits |= structs::NS_STYLE_CONTEXT_PROPERTY_FILL_OPACITY as u8;
|
|
||||||
} else if (servo.0).0 == atom!("stroke-opacity") {
|
|
||||||
s.mContextPropsBits |= structs::NS_STYLE_CONTEXT_PROPERTY_STROKE_OPACITY as u8;
|
|
||||||
}
|
|
||||||
gecko.mRawPtr = (servo.0).0.into_addrefed();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[allow(non_snake_case)]
|
|
||||||
pub fn copy__moz_context_properties_from(&mut self, other: &Self) {
|
|
||||||
unsafe {
|
|
||||||
bindings::Gecko_nsStyleSVG_CopyContextProperties(&mut *self.gecko, &*other.gecko);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[allow(non_snake_case)]
|
|
||||||
pub fn reset__moz_context_properties(&mut self, other: &Self) {
|
|
||||||
self.copy__moz_context_properties_from(other)
|
|
||||||
}
|
|
||||||
</%self:impl_trait>
|
</%self:impl_trait>
|
||||||
|
|
||||||
<%self:impl_trait style_struct_name="Color">
|
<%self:impl_trait style_struct_name="Color">
|
||||||
|
|
|
@ -194,10 +194,8 @@ ${helpers.predefined_type(
|
||||||
${helpers.predefined_type(
|
${helpers.predefined_type(
|
||||||
"-moz-context-properties",
|
"-moz-context-properties",
|
||||||
"MozContextProperties",
|
"MozContextProperties",
|
||||||
initial_value=None,
|
"computed::MozContextProperties::default()",
|
||||||
vector=True,
|
|
||||||
animation_value_type="none",
|
|
||||||
products="gecko",
|
products="gecko",
|
||||||
|
animation_value_type="none",
|
||||||
spec="Nonstandard (https://developer.mozilla.org/en-US/docs/Web/CSS/-moz-context-properties)",
|
spec="Nonstandard (https://developer.mozilla.org/en-US/docs/Web/CSS/-moz-context-properties)",
|
||||||
allow_empty=True,
|
|
||||||
)}
|
)}
|
||||||
|
|
|
@ -174,6 +174,7 @@ impl<A: Debug, B: Debug> Debug for Either<A, B> {
|
||||||
ToResolvedValue,
|
ToResolvedValue,
|
||||||
ToShmem,
|
ToShmem,
|
||||||
)]
|
)]
|
||||||
|
#[repr(C)]
|
||||||
pub struct CustomIdent(pub Atom);
|
pub struct CustomIdent(pub Atom);
|
||||||
|
|
||||||
impl CustomIdent {
|
impl CustomIdent {
|
||||||
|
|
|
@ -12,7 +12,7 @@ use crate::values::specified::AllowQuirks;
|
||||||
use crate::values::specified::LengthPercentage;
|
use crate::values::specified::LengthPercentage;
|
||||||
use crate::values::specified::{NonNegativeLengthPercentage, Opacity};
|
use crate::values::specified::{NonNegativeLengthPercentage, Opacity};
|
||||||
use crate::values::CustomIdent;
|
use crate::values::CustomIdent;
|
||||||
use cssparser::Parser;
|
use cssparser::{Parser, Token};
|
||||||
use std::fmt::{self, Write};
|
use std::fmt::{self, Write};
|
||||||
use style_traits::{CommaWithSpace, CssWriter, ParseError, Separator};
|
use style_traits::{CommaWithSpace, CssWriter, ParseError, Separator};
|
||||||
use style_traits::{StyleParseErrorKind, ToCss};
|
use style_traits::{StyleParseErrorKind, ToCss};
|
||||||
|
@ -243,11 +243,28 @@ impl ToCss for SVGPaintOrder {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bitflags! {
|
||||||
|
/// The context properties we understand.
|
||||||
|
#[derive(Default, MallocSizeOf, SpecifiedValueInfo, ToComputedValue, ToResolvedValue, ToShmem)]
|
||||||
|
#[repr(C)]
|
||||||
|
pub struct ContextPropertyBits: u8 {
|
||||||
|
/// `fill`
|
||||||
|
const FILL = 1 << 0;
|
||||||
|
/// `stroke`
|
||||||
|
const STROKE = 1 << 1;
|
||||||
|
/// `fill-opacity`
|
||||||
|
const FILL_OPACITY = 1 << 2;
|
||||||
|
/// `stroke-opacity`
|
||||||
|
const STROKE_OPACITY = 1 << 3;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// Specified MozContextProperties value.
|
/// Specified MozContextProperties value.
|
||||||
/// Nonstandard (https://developer.mozilla.org/en-US/docs/Web/CSS/-moz-context-properties)
|
/// Nonstandard (https://developer.mozilla.org/en-US/docs/Web/CSS/-moz-context-properties)
|
||||||
#[derive(
|
#[derive(
|
||||||
Clone,
|
Clone,
|
||||||
Debug,
|
Debug,
|
||||||
|
Default,
|
||||||
MallocSizeOf,
|
MallocSizeOf,
|
||||||
PartialEq,
|
PartialEq,
|
||||||
SpecifiedValueInfo,
|
SpecifiedValueInfo,
|
||||||
|
@ -256,19 +273,65 @@ impl ToCss for SVGPaintOrder {
|
||||||
ToResolvedValue,
|
ToResolvedValue,
|
||||||
ToShmem,
|
ToShmem,
|
||||||
)]
|
)]
|
||||||
pub struct MozContextProperties(pub CustomIdent);
|
#[repr(C)]
|
||||||
|
pub struct MozContextProperties {
|
||||||
|
#[css(iterable, if_empty = "none")]
|
||||||
|
#[ignore_malloc_size_of = "Arc"]
|
||||||
|
idents: crate::ArcSlice<CustomIdent>,
|
||||||
|
#[css(skip)]
|
||||||
|
bits: ContextPropertyBits,
|
||||||
|
}
|
||||||
|
|
||||||
impl Parse for MozContextProperties {
|
impl Parse for MozContextProperties {
|
||||||
fn parse<'i, 't>(
|
fn parse<'i, 't>(
|
||||||
_context: &ParserContext,
|
_context: &ParserContext,
|
||||||
input: &mut Parser<'i, 't>,
|
input: &mut Parser<'i, 't>,
|
||||||
) -> Result<MozContextProperties, ParseError<'i>> {
|
) -> Result<MozContextProperties, ParseError<'i>> {
|
||||||
|
let mut values = vec![];
|
||||||
|
let mut bits = ContextPropertyBits::empty();
|
||||||
|
loop {
|
||||||
|
{
|
||||||
let location = input.current_source_location();
|
let location = input.current_source_location();
|
||||||
let i = input.expect_ident()?;
|
let ident = input.expect_ident()?;
|
||||||
Ok(MozContextProperties(CustomIdent::from_ident(
|
|
||||||
|
if ident.eq_ignore_ascii_case("none") && values.is_empty() {
|
||||||
|
return Ok(Self::default());
|
||||||
|
}
|
||||||
|
|
||||||
|
let ident = CustomIdent::from_ident(
|
||||||
location,
|
location,
|
||||||
i,
|
ident,
|
||||||
&["all", "none", "auto"],
|
&["all", "none", "auto"],
|
||||||
)?))
|
)?;
|
||||||
|
|
||||||
|
if ident.0 == atom!("fill") {
|
||||||
|
bits.insert(ContextPropertyBits::FILL);
|
||||||
|
} else if ident.0 == atom!("stroke") {
|
||||||
|
bits.insert(ContextPropertyBits::STROKE);
|
||||||
|
} else if ident.0 == atom!("fill-opacity") {
|
||||||
|
bits.insert(ContextPropertyBits::FILL_OPACITY);
|
||||||
|
} else if ident.0 == atom!("stroke-opacity") {
|
||||||
|
bits.insert(ContextPropertyBits::STROKE_OPACITY);
|
||||||
|
}
|
||||||
|
|
||||||
|
values.push(ident);
|
||||||
|
}
|
||||||
|
|
||||||
|
let location = input.current_source_location();
|
||||||
|
match input.next() {
|
||||||
|
Ok(&Token::Comma) => continue,
|
||||||
|
Err(..) => break,
|
||||||
|
Ok(other) => return Err(location.new_unexpected_token_error(other.clone())),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if values.is_empty() {
|
||||||
|
return Err(input.new_custom_error(StyleParseErrorKind::UnspecifiedError));
|
||||||
|
}
|
||||||
|
|
||||||
|
Ok(MozContextProperties {
|
||||||
|
idents: crate::ArcSlice::from_iter(values.into_iter()),
|
||||||
|
bits,
|
||||||
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -85,6 +85,16 @@ impl<T> ArcSlice<T> {
|
||||||
mem::forget(self);
|
mem::forget(self);
|
||||||
ret
|
ret
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Leaks an empty arc slice pointer, and returns it. Only to be used to
|
||||||
|
/// construct ArcSlices from FFI.
|
||||||
|
#[inline]
|
||||||
|
pub fn leaked_empty_ptr() -> *mut std::os::raw::c_void {
|
||||||
|
let empty: ArcSlice<_> = EMPTY_ARC_SLICE.clone();
|
||||||
|
let ptr = empty.0.ptr();
|
||||||
|
std::mem::forget(empty);
|
||||||
|
ptr as *mut _
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// The inner pointer of an ArcSlice<T>, to be sent via FFI.
|
/// The inner pointer of an ArcSlice<T>, to be sent via FFI.
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue