Skip to content
Permalink
Browse files

Implement parsing of an @Viewport rule

  • Loading branch information...
luniv committed Mar 23, 2015
1 parent c303e9d commit 3b14c0705133cc014f44c612072fe8b80878b3a8
@@ -50,6 +50,7 @@ pub mod media_queries;
pub mod font_face;
pub mod legacy;
pub mod animation;
pub mod viewport;

macro_rules! reexport_computed_values {
( $( $name: ident )+ ) => {
@@ -63,4 +64,3 @@ macro_rules! reexport_computed_values {
}
}
longhand_properties_idents!(reexport_computed_values);

@@ -11,6 +11,7 @@ use log;
use stylesheets::Origin;

pub struct ParserContext<'a> {
pub stylesheet_origin: Origin,
pub base_url: &'a Url,
pub selector_context: SelectorParserContext,
}
@@ -20,6 +21,7 @@ impl<'a> ParserContext<'a> {
let mut selector_context = SelectorParserContext::new();
selector_context.in_user_agent_stylesheet = stylesheet_origin == Origin::UserAgent;
ParserContext {
stylesheet_origin: stylesheet_origin,
base_url: base_url,
selector_context: selector_context,
}
@@ -19,6 +19,7 @@ use properties::{PropertyDeclarationBlock, parse_property_declaration_list};
use media_queries::{Device, MediaQueryList, parse_media_query_list};
use font_face::{FontFaceRule, parse_font_face_block};
use util::smallvec::SmallVec2;
use viewport::ViewportRule;


/// Each style rule has an origin, which determines where it enters the cascade.
@@ -53,6 +54,7 @@ pub enum CSSRule {
Style(StyleRule),
Media(MediaRule),
FontFace(FontFaceRule),
Viewport(ViewportRule),
}

#[derive(Debug, PartialEq)]
@@ -216,6 +218,7 @@ pub mod rule_filter {
use std::marker::PhantomData;
use super::{CSSRule, MediaRule, StyleRule};
use super::super::font_face::FontFaceRule;
use super::super::viewport::ViewportRule;

macro_rules! rule_filter {
($variant:ident -> $value:ty) => {
@@ -259,6 +262,7 @@ pub mod rule_filter {
rule_filter!(FontFace -> FontFaceRule);
rule_filter!(Media -> MediaRule);
rule_filter!(Style -> StyleRule);
rule_filter!(Viewport -> ViewportRule);
}

/// Extension methods for `CSSRule` iterators.
@@ -271,6 +275,9 @@ pub trait CSSRuleIteratorExt<'a>: Iterator<Item=&'a CSSRule> {

/// Yield only style rules.
fn style(self) -> rule_filter::Style<'a, Self>;

/// Yield only @viewport rules.
fn viewport(self) -> rule_filter::Viewport<'a, Self>;
}

impl<'a, I> CSSRuleIteratorExt<'a> for I where I: Iterator<Item=&'a CSSRule> {
@@ -288,6 +295,11 @@ impl<'a, I> CSSRuleIteratorExt<'a> for I where I: Iterator<Item=&'a CSSRule> {
fn style(self) -> rule_filter::Style<'a, I> {
rule_filter::Style::new(self)
}

#[inline]
fn viewport(self) -> rule_filter::Viewport<'a, I> {
rule_filter::Viewport::new(self)
}
}

fn parse_nested_rules(context: &ParserContext, input: &mut Parser) -> Vec<CSSRule> {
@@ -324,6 +336,7 @@ enum State {
enum AtRulePrelude {
FontFace,
Media(MediaQueryList),
Viewport,
}


@@ -414,6 +427,9 @@ impl<'a, 'b> AtRuleParser for NestedRuleParser<'a, 'b> {
},
"font-face" => {
Ok(AtRuleType::WithBlock(AtRulePrelude::FontFace))
},
"viewport" => {
Ok(AtRuleType::WithBlock(AtRulePrelude::Viewport))
}
_ => Err(())
}
@@ -430,6 +446,9 @@ impl<'a, 'b> AtRuleParser for NestedRuleParser<'a, 'b> {
rules: parse_nested_rules(self.context, input),
}))
}
AtRulePrelude::Viewport => {
ViewportRule::parse(input, self.context).map(CSSRule::Viewport)
}
}
}
}
@@ -86,6 +86,22 @@ pub mod specified {
use util::geometry::Au;
use super::CSSFloat;

#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub enum AllowedNumericType {
All,
NonNegative
}

impl AllowedNumericType {
#[inline]
pub fn is_ok(&self, value: f32) -> bool {
match self {
&AllowedNumericType::All => true,
&AllowedNumericType::NonNegative => value >= 0.,
}
}
}

#[derive(Clone, PartialEq, Debug)]
pub struct CSSColor {
pub parsed: cssparser::Color,
@@ -397,33 +413,32 @@ pub mod specified {
}
}
}

impl LengthOrPercentageOrAuto {
fn parse_internal(input: &mut Parser, negative_ok: bool)
-> Result<LengthOrPercentageOrAuto, ()> {
fn parse_internal(input: &mut Parser, context: &AllowedNumericType)
-> Result<LengthOrPercentageOrAuto, ()>
{
match try!(input.next()) {
Token::Dimension(ref value, ref unit) if negative_ok || value.value >= 0. => {
Token::Dimension(ref value, ref unit) if context.is_ok(value.value) => {
Length::parse_dimension(value.value, unit)
.map(LengthOrPercentageOrAuto::Length)
}
Token::Percentage(ref value) if negative_ok || value.unit_value >= 0. => {
Ok(LengthOrPercentageOrAuto::Percentage(value.unit_value))
}
Token::Number(ref value) if value.value == 0. => {
Ok(LengthOrPercentageOrAuto::Length(Length::Absolute(Au(0))))
}
Token::Ident(ref value) if value.eq_ignore_ascii_case("auto") => {
Ok(LengthOrPercentageOrAuto::Auto)
.map(LengthOrPercentageOrAuto::Length)
}
Token::Percentage(ref value) if context.is_ok(value.unit_value) =>
Ok(LengthOrPercentageOrAuto::Percentage(value.unit_value)),
Token::Number(ref value) if context.is_ok(value.value) =>
Ok(LengthOrPercentageOrAuto::Length(Length::Absolute(Au(0)))),
Token::Ident(ref value) if value.eq_ignore_ascii_case("auto") =>
Ok(LengthOrPercentageOrAuto::Auto),
_ => Err(())
}
}
#[inline]
pub fn parse(input: &mut Parser) -> Result<LengthOrPercentageOrAuto, ()> {
LengthOrPercentageOrAuto::parse_internal(input, /* negative_ok = */ true)
LengthOrPercentageOrAuto::parse_internal(input, &AllowedNumericType::All)
}
#[inline]
pub fn parse_non_negative(input: &mut Parser) -> Result<LengthOrPercentageOrAuto, ()> {
LengthOrPercentageOrAuto::parse_internal(input, /* negative_ok = */ false)
LengthOrPercentageOrAuto::parse_internal(input, &AllowedNumericType::NonNegative)
}
}

Oops, something went wrong.

0 comments on commit 3b14c07

Please sign in to comment.
You can’t perform that action at this time.