Skip to content

Commit

Permalink
Auto merge of #19167 - CYBAI:font-variant-alternates-out-of-mako, r=e…
Browse files Browse the repository at this point in the history
…milio

style: Move font-variant-alternates outside of mako

This is a sub-PR of #19015
r? emilio

---
- [x] `./mach build -d` does not report any errors
- [x] `./mach test-tidy` does not report any errors
- [x] These changes fix #19166  (github issue number if applicable).
- [x] These changes do not require tests

<!-- 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/19167)
<!-- Reviewable:end -->
  • Loading branch information
bors-servo committed Nov 10, 2017
2 parents 3d888b5 + aeae311 commit 33fa728
Show file tree
Hide file tree
Showing 6 changed files with 317 additions and 205 deletions.
10 changes: 5 additions & 5 deletions components/style/properties/gecko.mako.rs
Expand Up @@ -2402,15 +2402,15 @@ fn static_assert() {
<% impl_simple_type_with_conversion("font_language_override", "mFont.languageOverride") %>

pub fn set_font_variant_alternates(&mut self,
v: longhands::font_variant_alternates::computed_value::T,
v: values::computed::font::FontVariantAlternates,
device: &Device) {
use gecko_bindings::bindings::{Gecko_ClearAlternateValues, Gecko_AppendAlternateValues};
use gecko_bindings::bindings::Gecko_nsFont_ResetFontFeatureValuesLookup;
use gecko_bindings::bindings::Gecko_nsFont_SetFontFeatureValuesLookup;
% for value in "normal swash stylistic ornaments annotation styleset character_variant historical".split():
use gecko_bindings::structs::NS_FONT_VARIANT_ALTERNATES_${value.upper()};
% endfor
use self::longhands::font_variant_alternates::VariantAlternates;
use values::specified::font::VariantAlternates;

unsafe {
Gecko_ClearAlternateValues(&mut self.gecko.mFont, v.len());
Expand Down Expand Up @@ -2471,13 +2471,13 @@ fn static_assert() {
self.copy_font_variant_alternates_from(other)
}

pub fn clone_font_variant_alternates(&self) -> longhands::font_variant_alternates::computed_value::T {
pub fn clone_font_variant_alternates(&self) -> values::computed::font::FontVariantAlternates {
use Atom;
% for value in "normal swash stylistic ornaments annotation styleset character_variant historical".split():
use gecko_bindings::structs::NS_FONT_VARIANT_ALTERNATES_${value.upper()};
% endfor
use properties::longhands::font_variant_alternates::VariantAlternates;
use properties::longhands::font_variant_alternates::VariantAlternatesList;
use values::specified::font::VariantAlternates;
use values::specified::font::VariantAlternatesList;
use values::CustomIdent;

if self.gecko.mFont.variantAlternates == NS_FONT_VARIANT_ALTERNATES_NORMAL as u16 {
Expand Down
206 changes: 8 additions & 198 deletions components/style/properties/longhand/font.mako.rs
Expand Up @@ -670,204 +670,14 @@ ${helpers.single_keyword_system("font-kerning",
flags="APPLIES_TO_FIRST_LETTER APPLIES_TO_FIRST_LINE APPLIES_TO_PLACEHOLDER",
animation_value_type="discrete")}

<%helpers:longhand name="font-variant-alternates" products="gecko" animation_value_type="discrete"
flags="APPLIES_TO_FIRST_LETTER APPLIES_TO_FIRST_LINE APPLIES_TO_PLACEHOLDER"
spec="https://drafts.csswg.org/css-fonts/#propdef-font-variant-alternates">
use properties::longhands::system_font::SystemFont;
use std::fmt;
use style_traits::ToCss;
use values::CustomIdent;


#[derive(Clone, Debug, MallocSizeOf, PartialEq)]
pub enum VariantAlternates {
Stylistic(CustomIdent),
Styleset(Box<[CustomIdent]>),
CharacterVariant(Box<[CustomIdent]>),
Swash(CustomIdent),
Ornaments(CustomIdent),
Annotation(CustomIdent),
HistoricalForms,
}

#[derive(Clone, Debug, MallocSizeOf, PartialEq)]
pub struct VariantAlternatesList(pub Box<[VariantAlternates]>);

#[derive(Clone, Debug, MallocSizeOf, PartialEq, ToCss)]
pub enum SpecifiedValue {
Value(VariantAlternatesList),
System(SystemFont)
}

<%self:simple_system_boilerplate name="font_variant_alternates"></%self:simple_system_boilerplate>

impl ToCss for VariantAlternates {
fn to_css<W>(&self, dest: &mut W) -> fmt::Result where W: fmt::Write {
match *self {
% for value in "swash stylistic ornaments annotation".split():
VariantAlternates::${to_camel_case(value)}(ref atom) => {
dest.write_str("${value}")?;
dest.write_str("(")?;
atom.to_css(dest)?;
dest.write_str(")")
},
% endfor
% for value in "styleset character-variant".split():
VariantAlternates::${to_camel_case(value)}(ref vec) => {
dest.write_str("${value}")?;
dest.write_str("(")?;
let mut iter = vec.iter();
iter.next().unwrap().to_css(dest)?;
for c in iter {
dest.write_str(", ")?;
c.to_css(dest)?;
}
dest.write_str(")")
},
% endfor
VariantAlternates::HistoricalForms => {
dest.write_str("historical-forms")
},
}
}
}

impl ToCss for VariantAlternatesList {
fn to_css<W>(&self, dest: &mut W) -> fmt::Result where W: fmt::Write {
if self.0.is_empty() {
return dest.write_str("normal");
}

let mut iter = self.0.iter();
iter.next().unwrap().to_css(dest)?;
for alternate in iter {
dest.write_str(" ")?;
alternate.to_css(dest)?;
}
Ok(())
}
}

impl VariantAlternatesList {
/// Returns the length of all variant alternates.
pub fn len(&self) -> usize {
self.0.iter().fold(0, |acc, alternate| {
match *alternate {
% for value in "Swash Stylistic Ornaments Annotation".split():
VariantAlternates::${value}(_) => {
acc + 1
},
% endfor
% for value in "Styleset CharacterVariant".split():
VariantAlternates::${value}(ref slice) => {
acc + slice.len()
}
% endfor
_ => acc,
}
})
}
}

pub mod computed_value {
pub type T = super::VariantAlternatesList;
}
#[inline]
pub fn get_initial_value() -> computed_value::T {
VariantAlternatesList(vec![].into_boxed_slice())
}
#[inline]
pub fn get_initial_specified_value() -> SpecifiedValue {
SpecifiedValue::Value(VariantAlternatesList(vec![].into_boxed_slice()))
}

bitflags! {
#[cfg_attr(feature = "servo", derive(MallocSizeOf))]
pub struct ParsingFlags: u8 {
const NORMAL = 0;
const HISTORICAL_FORMS = 0x01;
const STYLISTIC = 0x02;
const STYLESET = 0x04;
const CHARACTER_VARIANT = 0x08;
const SWASH = 0x10;
const ORNAMENTS = 0x20;
const ANNOTATION = 0x40;
}
}

/// normal |
/// [ stylistic(<feature-value-name>) ||
/// historical-forms ||
/// styleset(<feature-value-name> #) ||
/// character-variant(<feature-value-name> #) ||
/// swash(<feature-value-name>) ||
/// ornaments(<feature-value-name>) ||
/// annotation(<feature-value-name>) ]
pub fn parse<'i, 't>(_context: &ParserContext, input: &mut Parser<'i, 't>)
-> Result<SpecifiedValue, ParseError<'i>> {
let mut alternates = Vec::new();
if input.try(|input| input.expect_ident_matching("normal")).is_ok() {
return Ok(SpecifiedValue::Value(VariantAlternatesList(alternates.into_boxed_slice())));
}

let mut parsed_alternates = ParsingFlags::empty();
macro_rules! check_if_parsed(
($input:expr, $flag:path) => (
if parsed_alternates.contains($flag) {
return Err($input.new_custom_error(StyleParseErrorKind::UnspecifiedError))
}
parsed_alternates |= $flag;
)
);
while let Ok(_) = input.try(|input| {
// FIXME: remove clone() when lifetimes are non-lexical
match input.next()?.clone() {
Token::Ident(ref ident) => {
if *ident == "historical-forms" {
check_if_parsed!(input, ParsingFlags::HISTORICAL_FORMS);
alternates.push(VariantAlternates::HistoricalForms);
Ok(())
} else {
return Err(input.new_custom_error(StyleParseErrorKind::UnspecifiedError));
}
},
Token::Function(ref name) => {
input.parse_nested_block(|i| {
match_ignore_ascii_case! { &name,
% for value in "swash stylistic ornaments annotation".split():
"${value}" => {
check_if_parsed!(i, ParsingFlags::${value.upper()});
let location = i.current_source_location();
let ident = CustomIdent::from_ident(location, i.expect_ident()?, &[])?;
alternates.push(VariantAlternates::${to_camel_case(value)}(ident));
Ok(())
},
% endfor
% for value in "styleset character-variant".split():
"${value}" => {
check_if_parsed!(i, ParsingFlags:: ${to_rust_ident(value).upper()});
let idents = i.parse_comma_separated(|i| {
let location = i.current_source_location();
CustomIdent::from_ident(location, i.expect_ident()?, &[])
})?;
alternates.push(VariantAlternates::${to_camel_case(value)}(idents.into_boxed_slice()));
Ok(())
},
% endfor
_ => return Err(i.new_custom_error(StyleParseErrorKind::UnspecifiedError)),
}
})
},
_ => Err(input.new_custom_error(StyleParseErrorKind::UnspecifiedError)),
}
}) { }

if parsed_alternates.is_empty() {
return Err(input.new_custom_error(StyleParseErrorKind::UnspecifiedError));
}
Ok(SpecifiedValue::Value(VariantAlternatesList(alternates.into_boxed_slice())))
}
</%helpers:longhand>
${helpers.predefined_type("font-variant-alternates",
"FontVariantAlternates",
products="gecko",
initial_value="computed::FontVariantAlternates::get_initial_value()",
initial_specified_value="specified::FontVariantAlternates::get_initial_specified_value()",
animation_value_type="discrete",
flags="APPLIES_TO_FIRST_LETTER APPLIES_TO_FIRST_LINE APPLIES_TO_PLACEHOLDER",
spec="https://drafts.csswg.org/css-fonts/#propdef-font-variant-alternates")}

#[cfg(feature = "gecko")]
macro_rules! exclusive_value {
Expand Down
11 changes: 11 additions & 0 deletions components/style/values/computed/font.rs
Expand Up @@ -265,6 +265,17 @@ impl ToAnimatedValue for FontSizeAdjust {
}
}

/// Use VariantAlternatesList as computed type of FontVariantAlternates
pub type FontVariantAlternates = specified::VariantAlternatesList;

impl FontVariantAlternates {
#[inline]
/// Get initial value with VariantAlternatesList
pub fn get_initial_value() -> Self {
specified::VariantAlternatesList(vec![].into_boxed_slice())
}
}

impl ToComputedValue for specified::MozScriptMinSize {
type ComputedValue = MozScriptMinSize;

Expand Down
3 changes: 2 additions & 1 deletion components/style/values/computed/mod.rs
Expand Up @@ -36,7 +36,8 @@ pub use self::angle::Angle;
pub use self::background::{BackgroundSize, BackgroundRepeat};
pub use self::border::{BorderImageSlice, BorderImageWidth, BorderImageSideWidth};
pub use self::border::{BorderRadius, BorderCornerRadius, BorderSpacing};
pub use self::font::{FontSize, FontSizeAdjust, FontSynthesis, FontWeight, MozScriptLevel, MozScriptMinSize, XTextZoom};
pub use self::font::{FontSize, FontSizeAdjust, FontSynthesis, FontWeight, FontVariantAlternates};
pub use self::font::{MozScriptLevel, MozScriptMinSize, XTextZoom};
pub use self::box_::{AnimationIterationCount, AnimationName, ScrollSnapType, VerticalAlign};
pub use self::color::{Color, ColorPropertyValue, RGBAColor};
pub use self::effects::{BoxShadow, Filter, SimpleShadow};
Expand Down

0 comments on commit 33fa728

Please sign in to comment.