Auto merge of #7518 - servo:custom-properties, r=pcwalton

Initial support for CSS Custom Properties

https://drafts.csswg.org/css-variables/

Missing: 

* `var()` in shorthand property declarations.
* Correct handling of EOF in custom property declarations.

r? @pcwalton

<!-- Reviewable:start -->
[<img src="https://reviewable.io/review_button.png" height=40 alt="Review on Reviewable"/>](https://reviewable.io/reviews/servo/servo/7518)
<!-- Reviewable:end -->
This commit is contained in:
bors-servo 2015-09-03 16:09:02 -06:00
commit 05deb3dcc8
104 changed files with 961 additions and 116 deletions

View file

@ -62,7 +62,7 @@ use dom::virtualmethods::{VirtualMethods, vtable_for};
use devtools_traits::AttrInfo;
use smallvec::VecLike;
use style::legacy::{UnsignedIntegerAttribute, from_declaration};
use style::properties::DeclaredValue::SpecifiedValue;
use style::properties::DeclaredValue;
use style::properties::longhands::{self, background_image, border_spacing};
use style::properties::{PropertyDeclarationBlock, PropertyDeclaration, parse_style_attribute};
use style::values::CSSFloat;
@ -271,7 +271,7 @@ impl RawLayoutElementHelpers for Element {
if let Some(color) = bgcolor {
hints.push(from_declaration(
PropertyDeclaration::BackgroundColor(SpecifiedValue(
PropertyDeclaration::BackgroundColor(DeclaredValue::Value(
CSSColor { parsed: Color::RGBA(color), authored: None }))));
}
@ -284,7 +284,7 @@ impl RawLayoutElementHelpers for Element {
if let Some(url) = background {
hints.push(from_declaration(
PropertyDeclaration::BackgroundImage(SpecifiedValue(
PropertyDeclaration::BackgroundImage(DeclaredValue::Value(
background_image::SpecifiedValue(Some(specified::Image::Url(url)))))));
}
@ -297,7 +297,7 @@ impl RawLayoutElementHelpers for Element {
if let Some(color) = color {
hints.push(from_declaration(
PropertyDeclaration::Color(SpecifiedValue(CSSRGBA {
PropertyDeclaration::Color(DeclaredValue::Value(CSSRGBA {
parsed: color,
authored: None,
}))));
@ -313,7 +313,7 @@ impl RawLayoutElementHelpers for Element {
if let Some(cellspacing) = cellspacing {
let width_value = specified::Length::Absolute(Au::from_px(cellspacing as i32));
hints.push(from_declaration(
PropertyDeclaration::BorderSpacing(SpecifiedValue(
PropertyDeclaration::BorderSpacing(DeclaredValue::Value(
border_spacing::SpecifiedValue {
horizontal: width_value,
vertical: width_value,
@ -343,7 +343,7 @@ impl RawLayoutElementHelpers for Element {
let value = specified::Length::ServoCharacterWidth(
specified::CharacterWidth(size));
hints.push(from_declaration(
PropertyDeclaration::Width(SpecifiedValue(
PropertyDeclaration::Width(DeclaredValue::Value(
specified::LengthOrPercentageOrAuto::Length(value)))));
}
@ -367,13 +367,13 @@ impl RawLayoutElementHelpers for Element {
let width_value =
specified::LengthOrPercentageOrAuto::Percentage(specified::Percentage(percentage));
hints.push(from_declaration(
PropertyDeclaration::Width(SpecifiedValue(width_value))));
PropertyDeclaration::Width(DeclaredValue::Value(width_value))));
}
LengthOrPercentageOrAuto::Length(length) => {
let width_value = specified::LengthOrPercentageOrAuto::Length(
specified::Length::Absolute(length));
hints.push(from_declaration(
PropertyDeclaration::Width(SpecifiedValue(width_value))));
PropertyDeclaration::Width(DeclaredValue::Value(width_value))));
}
}
@ -391,13 +391,13 @@ impl RawLayoutElementHelpers for Element {
let height_value =
specified::LengthOrPercentageOrAuto::Percentage(specified::Percentage(percentage));
hints.push(from_declaration(
PropertyDeclaration::Height(SpecifiedValue(height_value))));
PropertyDeclaration::Height(DeclaredValue::Value(height_value))));
}
LengthOrPercentageOrAuto::Length(length) => {
let height_value = specified::LengthOrPercentageOrAuto::Length(
specified::Length::Absolute(length));
hints.push(from_declaration(
PropertyDeclaration::Height(SpecifiedValue(height_value))));
PropertyDeclaration::Height(DeclaredValue::Value(height_value))));
}
}
@ -420,7 +420,7 @@ impl RawLayoutElementHelpers for Element {
// https://html.spec.whatwg.org/multipage/#textarea-effective-width
let value = specified::Length::ServoCharacterWidth(specified::CharacterWidth(cols));
hints.push(from_declaration(
PropertyDeclaration::Width(SpecifiedValue(
PropertyDeclaration::Width(DeclaredValue::Value(
specified::LengthOrPercentageOrAuto::Length(value)))));
}
@ -441,7 +441,7 @@ impl RawLayoutElementHelpers for Element {
// https://html.spec.whatwg.org/multipage/#textarea-effective-height
let value = specified::Length::FontRelative(specified::FontRelativeLength::Em(rows as CSSFloat));
hints.push(from_declaration(
PropertyDeclaration::Height(SpecifiedValue(
PropertyDeclaration::Height(DeclaredValue::Value(
specified::LengthOrPercentageOrAuto::Length(value)))));
}
@ -456,16 +456,16 @@ impl RawLayoutElementHelpers for Element {
if let Some(border) = border {
let width_value = specified::Length::Absolute(Au::from_px(border as i32));
hints.push(from_declaration(
PropertyDeclaration::BorderTopWidth(SpecifiedValue(
PropertyDeclaration::BorderTopWidth(DeclaredValue::Value(
longhands::border_top_width::SpecifiedValue(width_value)))));
hints.push(from_declaration(
PropertyDeclaration::BorderLeftWidth(SpecifiedValue(
PropertyDeclaration::BorderLeftWidth(DeclaredValue::Value(
longhands::border_left_width::SpecifiedValue(width_value)))));
hints.push(from_declaration(
PropertyDeclaration::BorderBottomWidth(SpecifiedValue(
PropertyDeclaration::BorderBottomWidth(DeclaredValue::Value(
longhands::border_bottom_width::SpecifiedValue(width_value)))));
hints.push(from_declaration(
PropertyDeclaration::BorderRightWidth(SpecifiedValue(
PropertyDeclaration::BorderRightWidth(DeclaredValue::Value(
longhands::border_right_width::SpecifiedValue(width_value)))));
}
}

View file

@ -135,7 +135,7 @@ version = "0.0.1"
dependencies = [
"azure 0.1.0 (git+https://github.com/servo/rust-azure)",
"canvas_traits 0.0.1",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"gfx_traits 0.0.1",
"gleam 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)",
@ -152,7 +152,7 @@ name = "canvas_traits"
version = "0.0.1"
dependencies = [
"azure 0.1.0 (git+https://github.com/servo/rust-azure)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"gfx_traits 0.0.1",
"ipc-channel 0.1.0 (git+https://github.com/pcwalton/ipc-channel)",
@ -288,7 +288,7 @@ dependencies = [
[[package]]
name = "cssparser"
version = "0.3.5"
version = "0.3.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
@ -887,7 +887,7 @@ dependencies = [
"canvas 0.0.1",
"canvas_traits 0.0.1",
"clock_ticks 0.0.6 (git+https://github.com/tomaka/clock_ticks)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1370,7 +1370,7 @@ dependencies = [
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"canvas 0.0.1",
"canvas_traits 0.0.1",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"devtools_traits 0.0.1",
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1436,7 +1436,7 @@ version = "0.1.0"
source = "git+https://github.com/servo/rust-selectors#572353b3209af040cd3e6261978b09c7f8122844"
dependencies = [
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
"matches 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
"quickersort 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1573,7 +1573,7 @@ name = "style"
version = "0.0.1"
dependencies = [
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1597,7 +1597,7 @@ dependencies = [
name = "style_tests"
version = "0.0.1"
dependencies = [
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"selectors 0.1.0 (git+https://github.com/servo/rust-selectors)",
"string_cache 0.1.11 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1715,7 +1715,7 @@ version = "0.0.1"
dependencies = [
"azure 0.1.0 (git+https://github.com/servo/rust-azure)",
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"getopts 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)",
"html5ever 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)",

View file

@ -20,7 +20,7 @@ git = "https://github.com/servo/rust-selectors"
features = ["unstable"]
[dependencies.cssparser]
version = "0.3"
version = "0.3.6"
features = [ "serde-serialization" ]
[dependencies.url]

View file

@ -0,0 +1,386 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
use cssparser::{Parser, Token, SourcePosition};
use properties::DeclaredValue;
use std::collections::{HashMap, HashSet};
use std::sync::Arc;
use string_cache::Atom;
// Does not include the `--` prefix
pub type Name = Atom;
// https://drafts.csswg.org/css-variables/#typedef-custom-property-name
pub fn parse_name(s: &str) -> Result<Name, ()> {
if s.starts_with("--") {
Ok(Atom::from_slice(&s[2..]))
} else {
Err(())
}
}
#[derive(Clone, PartialEq)]
pub struct Value {
/// In CSS syntax
value: String,
/// Custom property names in var() functions.
references: HashSet<Name>,
}
pub struct BorrowedValue<'a> {
value: &'a str,
references: Option<&'a HashSet<Name>>,
}
pub fn parse(input: &mut Parser) -> Result<Value, ()> {
let start = input.position();
let mut references = Some(HashSet::new());
// FIXME: dont consume a top-level `!` as that would prevent parsing `!important`.
// Maybe using Parser::parse_until_before?
try!(parse_declaration_value(input, &mut references));
Ok(Value {
value: input.slice_from(start).to_owned(),
references: references.unwrap(),
})
}
/// https://drafts.csswg.org/css-syntax-3/#typedef-declaration-value
pub fn parse_declaration_value(input: &mut Parser, references: &mut Option<HashSet<Name>>)
-> Result<(), ()> {
if input.is_exhausted() {
// Need at least one token
return Err(())
}
while let Ok(token) = input.next() {
match token {
Token::BadUrl |
Token::BadString |
Token::CloseParenthesis |
Token::CloseSquareBracket |
Token::CloseCurlyBracket |
Token::Semicolon |
Token::Delim('!') => {
return Err(())
}
Token::Function(ref name) if name == "var" => {
try!(input.parse_nested_block(|input| {
parse_var_function(input, references)
}));
}
Token::Function(_) |
Token::ParenthesisBlock |
Token::CurlyBracketBlock |
Token::SquareBracketBlock => {
try!(input.parse_nested_block(|input| {
parse_declaration_value_block(input, references)
}));
}
_ => {}
}
}
Ok(())
}
/// Like parse_declaration_value,
/// but accept `!` and `;` since they are only invalid at the top level
fn parse_declaration_value_block(input: &mut Parser, references: &mut Option<HashSet<Name>>)
-> Result<(), ()> {
while let Ok(token) = input.next() {
match token {
Token::BadUrl |
Token::BadString |
Token::CloseParenthesis |
Token::CloseSquareBracket |
Token::CloseCurlyBracket => {
return Err(())
}
Token::Function(ref name) if name == "var" => {
try!(input.parse_nested_block(|input| {
parse_var_function(input, references)
}));
}
Token::Function(_) |
Token::ParenthesisBlock |
Token::CurlyBracketBlock |
Token::SquareBracketBlock => {
try!(input.parse_nested_block(|input| {
parse_declaration_value_block(input, references)
}));
}
_ => {}
}
}
Ok(())
}
// If the var function is valid, return Ok((custom_property_name, fallback))
fn parse_var_function<'i, 't>(input: &mut Parser<'i, 't>, references: &mut Option<HashSet<Name>>)
-> Result<(), ()> {
let name = try!(input.expect_ident());
let name = try!(parse_name(&name));
if input.expect_comma().is_ok() {
try!(parse_declaration_value(input, references));
}
if let Some(ref mut refs) = *references {
refs.insert(name);
}
Ok(())
}
/// Add one custom property declaration to a map,
/// unless another with the same name was already there.
pub fn cascade<'a>(custom_properties: &mut Option<HashMap<&'a Name, BorrowedValue<'a>>>,
inherited: &'a Option<Arc<HashMap<Name, String>>>,
seen: &mut HashSet<&'a Name>,
name: &'a Name,
value: &'a DeclaredValue<Value>) {
let was_not_already_present = seen.insert(name);
if was_not_already_present {
let map = match *custom_properties {
Some(ref mut map) => map,
None => {
*custom_properties = Some(match *inherited {
Some(ref inherited) => inherited.iter().map(|(key, value)| {
(key, BorrowedValue { value: &value, references: None })
}).collect(),
None => HashMap::new(),
});
custom_properties.as_mut().unwrap()
}
};
match *value {
DeclaredValue::Value(ref value) => {
map.insert(name, BorrowedValue {
value: &value.value,
references: Some(&value.references),
});
},
DeclaredValue::WithVariables { .. } => unreachable!(),
DeclaredValue::Initial => {
map.remove(&name);
}
DeclaredValue::Inherit => {} // The inherited value is what we already have.
}
}
}
pub fn finish_cascade(custom_properties: Option<HashMap<&Name, BorrowedValue>>,
inherited: &Option<Arc<HashMap<Name, String>>>)
-> Option<Arc<HashMap<Name, String>>> {
if let Some(mut map) = custom_properties {
remove_cycles(&mut map);
Some(Arc::new(substitute_all(map, inherited)))
} else {
inherited.clone()
}
}
/// https://drafts.csswg.org/css-variables/#cycles
/// The initial value of a custom property is represented by this property not being in the map.
fn remove_cycles(map: &mut HashMap<&Name, BorrowedValue>) {
let mut to_remove = HashSet::new();
{
let mut visited = HashSet::new();
let mut stack = Vec::new();
for name in map.keys() {
walk(map, name, &mut stack, &mut visited, &mut to_remove);
fn walk<'a>(map: &HashMap<&'a Name, BorrowedValue<'a>>,
name: &'a Name,
stack: &mut Vec<&'a Name>,
visited: &mut HashSet<&'a Name>,
to_remove: &mut HashSet<Name>) {
let already_visited_before = !visited.insert(name);
if already_visited_before {
return
}
if let Some(value) = map.get(name) {
if let Some(references) = value.references {
stack.push(name);
for next in references {
if let Some(position) = stack.iter().position(|&x| x == next) {
// Found a cycle
for &in_cycle in &stack[position..] {
to_remove.insert(in_cycle.clone());
}
} else {
walk(map, next, stack, visited, to_remove);
}
}
stack.pop();
}
}
}
}
}
for name in &to_remove {
map.remove(name);
}
}
/// Replace `var()` functions for all custom properties.
fn substitute_all(custom_properties: HashMap<&Name, BorrowedValue>,
inherited: &Option<Arc<HashMap<Name, String>>>)
-> HashMap<Name, String> {
let mut substituted_map = HashMap::new();
let mut invalid = HashSet::new();
for (&name, value) in &custom_properties {
// If this value is invalid at computed-time it wont be inserted in substituted_map.
// Nothing else to do.
let _ = substitute_one(
name, value, &custom_properties, inherited, None, &mut substituted_map, &mut invalid);
}
substituted_map
}
/// Replace `var()` functions for one custom property.
/// Also recursively record results for other custom properties referenced by `var()` functions.
/// Return `Err(())` for invalid at computed time.
fn substitute_one(name: &Name,
value: &BorrowedValue,
custom_properties: &HashMap<&Name, BorrowedValue>,
inherited: &Option<Arc<HashMap<Name, String>>>,
substituted: Option<&mut String>,
substituted_map: &mut HashMap<Name, String>,
invalid: &mut HashSet<Name>)
-> Result<(), ()> {
if let Some(value) = substituted_map.get(name) {
if let Some(substituted) = substituted {
substituted.push_str(value)
}
return Ok(())
}
if invalid.contains(name) {
return Err(());
}
let value = if value.references.map(|set| set.is_empty()) == Some(false) {
let mut substituted = String::new();
let mut input = Parser::new(&value.value);
let mut start = input.position();
if substitute_block(&mut input, &mut start, &mut substituted, &mut |name, substituted| {
if let Some(value) = custom_properties.get(name) {
substitute_one(name, value, custom_properties, inherited,
Some(substituted), substituted_map, invalid)
} else {
Err(())
}
}).is_ok() {
substituted.push_str(input.slice_from(start));
substituted
} else {
// Invalid at computed-value time. Use the inherited value.
if let Some(value) = inherited.as_ref().and_then(|i| i.get(name)) {
value.clone()
} else {
invalid.insert(name.clone());
return Err(())
}
}
} else {
value.value.to_owned()
};
if let Some(substituted) = substituted {
substituted.push_str(&value)
}
substituted_map.insert(name.clone(), value);
Ok(())
}
/// Replace `var()` functions in an arbitrary bit of input.
///
/// The `substitute_one` callback is called for each `var()` function in `input`.
/// If the variable has its initial value,
/// the callback should return `Err(())` and leave `substituted` unchanged.
/// Otherwise, it should push the value of the variable (with its own `var()` functions replaced)
/// to `substituted` and return `Ok(())`.
///
/// Return `Err(())` if `input` is invalid at computed-value time.
fn substitute_block<F>(input: &mut Parser,
start: &mut SourcePosition,
substituted: &mut String,
substitute_one: &mut F)
-> Result<(), ()>
where F: FnMut(&Name, &mut String) -> Result<(), ()> {
loop {
let input_slice = input.slice_from(*start);
let token = if let Ok(token) = input.next() { token } else { break };
match token {
Token::Function(ref name) if name == "var" => {
substituted.push_str(input_slice);
try!(input.parse_nested_block(|input| {
// parse_var_function() ensures neither .unwrap() will fail.
let name = input.expect_ident().unwrap();
let name = parse_name(&name).unwrap();
if substitute_one(&name, substituted).is_ok() {
// Skip over the fallback, as `parse_nested_block` would return `Err`
// if we dont consume all of `input`.
// FIXME: Add a specialized method to cssparser to do this with less work.
while let Ok(_) = input.next() {}
} else {
try!(input.expect_comma());
let mut start = input.position();
try!(substitute_block(input, &mut start, substituted, substitute_one));
substituted.push_str(input.slice_from(start));
}
Ok(())
}));
*start = input.position();
}
Token::Function(_) |
Token::ParenthesisBlock |
Token::CurlyBracketBlock |
Token::SquareBracketBlock => {
try!(input.parse_nested_block(|input| {
substitute_block(input, start, substituted, substitute_one)
}));
}
_ => {}
}
}
// FIXME: deal with things being implicitly closed at the end of the input. E.g.
// ```html
// <div style="--color: rgb(0,0,0">
// <p style="background: var(--color) var(--image) top left; --image: url('a.png"></p>
// </div>
// ```
Ok(())
}
/// Replace `var()` functions for a non-custom property.
/// Return `Err(())` for invalid at computed time.
pub fn substitute(input: &str, custom_properties: &Option<Arc<HashMap<Name, String>>>)
-> Result<String, ()> {
let empty_map;
let custom_properties = if let &Some(ref arc) = custom_properties {
&**arc
} else {
empty_map = HashMap::new();
&empty_map
};
let mut substituted = String::new();
let mut input = Parser::new(input);
let mut start = input.position();
try!(substitute_block(&mut input, &mut start, &mut substituted, &mut |name, substituted| {
if let Some(value) = custom_properties.get(name) {
substituted.push_str(value);
Ok(())
} else {
Err(())
}
}));
substituted.push_str(input.slice_from(start));
Ok(substituted)
}

View file

@ -43,6 +43,7 @@ extern crate num;
extern crate util;
mod custom_properties;
pub mod stylesheets;
pub mod parser;
pub mod selector_matching;

View file

@ -6,6 +6,7 @@
use std::ascii::AsciiExt;
use std::borrow::ToOwned;
use std::collections::{HashSet, HashMap};
use std::default::Default;
use std::fmt;
use std::fmt::Debug;
@ -22,6 +23,7 @@ use util::logical_geometry::{LogicalMargin, PhysicalSide, WritingMode};
use euclid::SideOffsets2D;
use euclid::size::Size2D;
use fnv::FnvHasher;
use string_cache::Atom;
use computed_values;
use parser::{ParserContext, log_css_error};
@ -131,9 +133,11 @@ pub mod longhands {
use properties::longhands;
use properties::property_bit_field::PropertyBitField;
use properties::{ComputedValues, PropertyDeclaration};
use std::collections::HashMap;
use std::sync::Arc;
use values::computed::ToComputedValue;
use values::{computed, specified};
use string_cache::Atom;
${caller.body()}
#[allow(unused_variables)]
pub fn cascade_property(declaration: &PropertyDeclaration,
@ -153,10 +157,12 @@ pub mod longhands {
return
}
seen.set_${property.ident}();
let computed_value = match *declared_value {
DeclaredValue::SpecifiedValue(ref specified_value) => {
let computed_value = substitute_variables(
declared_value, &style.custom_properties, |value| match *value {
DeclaredValue::Value(ref specified_value) => {
specified_value.to_computed_value(&context)
}
DeclaredValue::WithVariables { .. } => unreachable!(),
DeclaredValue::Initial => get_initial_value(),
DeclaredValue::Inherit => {
// This is a bit slow, but this is rare so it shouldn't
@ -168,7 +174,8 @@ pub mod longhands {
.${property.ident}
.clone()
}
};
}
);
Arc::make_mut(&mut style.${THIS_STYLE_STRUCT.ident}).${property.ident} =
computed_value;
@ -186,6 +193,29 @@ pub mod longhands {
% endif
}
% if derived_from is None:
pub fn substitute_variables<F, R>(value: &DeclaredValue<SpecifiedValue>,
custom_properties: &Option<Arc<HashMap<Atom, String>>>,
f: F)
-> R
where F: FnOnce(&DeclaredValue<SpecifiedValue>) -> R {
if let DeclaredValue::WithVariables { ref css, ref base_url } = *value {
f(&
::custom_properties::substitute(css, custom_properties)
.and_then(|css| {
// As of this writing, only the base URL is used for property values:
let context = ParserContext::new(
::stylesheets::Origin::Author, base_url);
parse_specified(&context, &mut Parser::new(&css))
})
.unwrap_or(
// Invalid at computed-value time.
DeclaredValue::${"Inherit" if THIS_STYLE_STRUCT.inherited else "Initial"}
)
)
} else {
f(value)
}
}
pub fn parse_declared(context: &ParserContext, input: &mut Parser)
-> Result<DeclaredValue<SpecifiedValue>, ()> {
match input.try(CSSWideKeyword::parse) {
@ -193,7 +223,21 @@ pub mod longhands {
Ok(CSSWideKeyword::InitialKeyword) => Ok(DeclaredValue::Initial),
Ok(CSSWideKeyword::UnsetKeyword) => Ok(DeclaredValue::${
"Inherit" if THIS_STYLE_STRUCT.inherited else "Initial"}),
Err(()) => parse_specified(context, input),
Err(()) => {
input.look_for_var_functions();
let start = input.position();
let specified = parse_specified(context, input);
let var = input.seen_var_functions();
if specified.is_err() && var {
input.reset(start);
try!(::custom_properties::parse_declaration_value(input, &mut None));
return Ok(DeclaredValue::WithVariables {
css: input.slice_from(start).to_owned(),
base_url: context.base_url.clone(),
})
}
specified
}
}
}
% endif
@ -207,7 +251,7 @@ pub mod longhands {
% if derived_from is None:
pub fn parse_specified(context: &ParserContext, input: &mut Parser)
-> Result<DeclaredValue<SpecifiedValue>, ()> {
parse(context, input).map(DeclaredValue::SpecifiedValue)
parse(context, input).map(DeclaredValue::Value)
}
% endif
</%self:raw_longhand>
@ -1651,7 +1695,7 @@ pub mod longhands {
Color::RGBA(rgba) => rgba,
Color::CurrentColor => return Ok(DeclaredValue::Inherit)
};
Ok(DeclaredValue::SpecifiedValue(CSSRGBA {
Ok(DeclaredValue::Value(CSSRGBA {
parsed: rgba,
authored: value.authored,
}))
@ -1664,7 +1708,6 @@ pub mod longhands {
<%self:longhand name="font-family">
use self::computed_value::FontFamily;
use string_cache::Atom;
use values::computed::ComputedValueAsSpecified;
pub use self::computed_value::T as SpecifiedValue;
@ -5610,6 +5653,7 @@ fn deduplicate_property_declarations(declarations: Vec<PropertyDeclaration>)
-> Vec<PropertyDeclaration> {
let mut deduplicated = vec![];
let mut seen = PropertyBitField::new();
let mut seen_custom = Vec::new();
for declaration in declarations.into_iter().rev() {
match declaration {
% for property in LONGHANDS:
@ -5624,6 +5668,12 @@ fn deduplicate_property_declarations(declarations: Vec<PropertyDeclaration>)
% endif
},
% endfor
PropertyDeclaration::Custom(ref name, _) => {
if seen_custom.contains(name) {
continue
}
seen_custom.push(name.clone())
}
}
deduplicated.push(declaration)
}
@ -5650,9 +5700,10 @@ impl CSSWideKeyword {
}
#[derive(Clone, PartialEq, Eq, Copy, Debug)]
#[derive(Clone, PartialEq, Eq, Debug)]
pub enum DeclaredValue<T> {
SpecifiedValue(T),
Value(T),
WithVariables { css: String, base_url: Url },
Initial,
Inherit,
// There is no Unset variant here.
@ -5663,7 +5714,8 @@ pub enum DeclaredValue<T> {
impl<T: ToCss> DeclaredValue<T> {
pub fn specified_value(&self) -> String {
match self {
&DeclaredValue::SpecifiedValue(ref inner) => inner.to_css_string(),
&DeclaredValue::Value(ref inner) => inner.to_css_string(),
&DeclaredValue::WithVariables { ref css, .. } => css.clone(),
&DeclaredValue::Initial => "initial".to_owned(),
&DeclaredValue::Inherit => "inherit".to_owned(),
}
@ -5675,6 +5727,7 @@ pub enum PropertyDeclaration {
% for property in LONGHANDS:
${property.camel_case}(DeclaredValue<longhands::${property.ident}::SpecifiedValue>),
% endfor
Custom(::custom_properties::Name, DeclaredValue<::custom_properties::Value>),
}
@ -5725,6 +5778,19 @@ impl PropertyDeclaration {
pub fn parse(name: &str, context: &ParserContext, input: &mut Parser,
result_list: &mut Vec<PropertyDeclaration>) -> PropertyDeclarationParseResult {
if let Ok(name) = ::custom_properties::parse_name(name) {
let value = match input.try(CSSWideKeyword::parse) {
Ok(CSSWideKeyword::UnsetKeyword) | // Custom properties are alawys inherited
Ok(CSSWideKeyword::InheritKeyword) => DeclaredValue::Inherit,
Ok(CSSWideKeyword::InitialKeyword) => DeclaredValue::Initial,
Err(()) => match ::custom_properties::parse(input) {
Ok(value) => DeclaredValue::Value(value),
Err(()) => return PropertyDeclarationParseResult::InvalidValue,
}
};
result_list.push(PropertyDeclaration::Custom(name, value));
return PropertyDeclarationParseResult::ValidOrIgnoredDeclaration;
}
match_ignore_ascii_case! { name,
% for property in LONGHANDS:
% if property.derived_from is None:
@ -5783,7 +5849,7 @@ impl PropertyDeclaration {
% for sub_property in shorthand.sub_properties:
result_list.push(PropertyDeclaration::${sub_property.camel_case}(
match result.${sub_property.ident} {
Some(value) => DeclaredValue::SpecifiedValue(value),
Some(value) => DeclaredValue::Value(value),
None => DeclaredValue::Initial,
}
));
@ -5832,6 +5898,7 @@ pub struct ComputedValues {
% for style_struct in STYLE_STRUCTS:
${style_struct.ident}: Arc<style_structs::${style_struct.name}>,
% endfor
custom_properties: Option<Arc<HashMap<::custom_properties::Name, String>>>,
shareable: bool,
pub writing_mode: WritingMode,
pub root_font_size: Au,
@ -6050,6 +6117,7 @@ lazy_static! {
% endif
}),
% endfor
custom_properties: None,
shareable: true,
writing_mode: WritingMode::empty(),
root_font_size: longhands::font_size::get_initial_value(),
@ -6064,6 +6132,7 @@ fn cascade_with_cached_declarations(
shareable: bool,
parent_style: &ComputedValues,
cached_style: &ComputedValues,
custom_properties: Option<Arc<HashMap<Atom, String>>>,
context: &computed::Context)
-> ComputedValues {
% for style_struct in STYLE_STRUCTS:
@ -6073,7 +6142,6 @@ fn cascade_with_cached_declarations(
let mut style_${style_struct.ident} = cached_style.${style_struct.ident}.clone();
% endif
% endfor
let mut seen = PropertyBitField::new();
// Declaration blocks are stored in increasing precedence order,
// we want them in decreasing order here.
@ -6092,8 +6160,10 @@ fn cascade_with_cached_declarations(
continue
}
seen.set_${property.ident}();
let computed_value = match *declared_value {
DeclaredValue::SpecifiedValue(ref specified_value)
let computed_value =
longhands::${property.ident}::substitute_variables(
declared_value, &custom_properties, |value| match *value {
DeclaredValue::Value(ref specified_value)
=> specified_value.to_computed_value(context),
DeclaredValue::Initial
=> longhands::${property.ident}::get_initial_value(),
@ -6106,7 +6176,9 @@ fn cascade_with_cached_declarations(
.${property.ident}
.clone()
}
};
DeclaredValue::WithVariables { .. } => unreachable!()
}
);
Arc::make_mut(&mut style_${style_struct.ident})
.${property.ident} = computed_value;
% endif
@ -6134,6 +6206,7 @@ fn cascade_with_cached_declarations(
% endif
% endfor
% endfor
PropertyDeclaration::Custom(..) => {}
}
}
}
@ -6148,6 +6221,7 @@ fn cascade_with_cached_declarations(
% for style_struct in STYLE_STRUCTS:
${style_struct.ident}: style_${style_struct.ident},
% endfor
custom_properties: custom_properties,
shareable: shareable,
root_font_size: parent_style.root_font_size,
}
@ -6211,6 +6285,24 @@ pub fn cascade(viewport_size: Size2D<Au>,
None => (true, initial_values),
};
let mut custom_properties = None;
let mut seen_custom = HashSet::new();
for sub_list in applicable_declarations.iter().rev() {
// Declarations are already stored in reverse order.
for declaration in sub_list.declarations.iter() {
match *declaration {
PropertyDeclaration::Custom(ref name, ref value) => {
::custom_properties::cascade(
&mut custom_properties, &inherited_style.custom_properties,
&mut seen_custom, name, value)
}
_ => {}
}
}
}
let custom_properties = ::custom_properties::finish_cascade(
custom_properties, &inherited_style.custom_properties);
let mut context = {
let inherited_font_style = inherited_style.get_font();
computed::Context {
@ -6241,11 +6333,16 @@ pub fn cascade(viewport_size: Size2D<Au>,
// This assumes that the computed and specified values have the same Rust type.
macro_rules! get_specified(
($style_struct_getter: ident, $property: ident, $declared_value: expr) => {
match *$declared_value {
DeclaredValue::SpecifiedValue(specified_value) => specified_value,
longhands::$property::substitute_variables(
$declared_value, &custom_properties, |value| match *value {
DeclaredValue::Value(specified_value) => specified_value,
DeclaredValue::Initial => longhands::$property::get_initial_value(),
DeclaredValue::Inherit => inherited_style.$style_struct_getter().$property.clone(),
DeclaredValue::Inherit => {
inherited_style.$style_struct_getter().$property.clone()
}
DeclaredValue::WithVariables { .. } => unreachable!()
}
)
};
);
@ -6256,8 +6353,9 @@ pub fn cascade(viewport_size: Size2D<Au>,
for declaration in sub_list.declarations.iter().rev() {
match *declaration {
PropertyDeclaration::FontSize(ref value) => {
context.font_size = match *value {
DeclaredValue::SpecifiedValue(ref specified_value) => {
context.font_size = longhands::font_size::substitute_variables(
value, &custom_properties, |value| match *value {
DeclaredValue::Value(ref specified_value) => {
match specified_value.0 {
Length::FontRelative(value) => {
value.to_computed_value(context.inherited_font_size,
@ -6271,16 +6369,21 @@ pub fn cascade(viewport_size: Size2D<Au>,
}
DeclaredValue::Initial => longhands::font_size::get_initial_value(),
DeclaredValue::Inherit => context.inherited_font_size,
DeclaredValue::WithVariables { .. } => unreachable!(),
}
);
}
PropertyDeclaration::Color(ref value) => {
context.color = match *value {
DeclaredValue::SpecifiedValue(ref specified_value) => {
context.color = longhands::color::substitute_variables(
value, &custom_properties, |value| match *value {
DeclaredValue::Value(ref specified_value) => {
specified_value.parsed
}
DeclaredValue::Initial => longhands::color::get_initial_value(),
DeclaredValue::Inherit => inherited_style.get_color().color.clone(),
};
DeclaredValue::WithVariables { .. } => unreachable!(),
}
);
}
PropertyDeclaration::Display(ref value) => {
context.display = get_specified!(get_box, display, value);
@ -6332,6 +6435,7 @@ pub fn cascade(viewport_size: Size2D<Au>,
shareable,
parent_style,
cached_style,
custom_properties,
&context), false)
}
(_, _) => {}
@ -6348,7 +6452,8 @@ pub fn cascade(viewport_size: Size2D<Au>,
% endif
.${style_struct.ident}.clone(),
% endfor
shareable: false,
custom_properties: custom_properties,
shareable: shareable,
writing_mode: WritingMode::empty(),
root_font_size: context.root_font_size,
};
@ -6364,6 +6469,9 @@ pub fn cascade(viewport_size: Size2D<Au>,
for sub_list in applicable_declarations.iter().rev() {
// Declarations are already stored in reverse order.
for declaration in sub_list.declarations.iter() {
if let PropertyDeclaration::Custom(..) = *declaration {
continue
}
let discriminant = unsafe {
intrinsics::discriminant_value(declaration) as usize
};
@ -6409,14 +6517,8 @@ pub fn cascade(viewport_size: Size2D<Au>,
compute_font_hash(&mut *Arc::make_mut(&mut style.font))
}
(ComputedValues {
writing_mode: get_writing_mode(&*style.inheritedbox),
% for style_struct in STYLE_STRUCTS:
${style_struct.ident}: style.${style_struct.ident},
% endfor
shareable: shareable,
root_font_size: context.root_font_size,
}, cacheable)
style.writing_mode = get_writing_mode(&*style.inheritedbox);
(style, cacheable)
}
/// Alters the given style to accommodate replaced content. This is called in flow construction. It

16
ports/cef/Cargo.lock generated
View file

@ -127,7 +127,7 @@ version = "0.0.1"
dependencies = [
"azure 0.1.0 (git+https://github.com/servo/rust-azure)",
"canvas_traits 0.0.1",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"gfx_traits 0.0.1",
"gleam 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)",
@ -144,7 +144,7 @@ name = "canvas_traits"
version = "0.0.1"
dependencies = [
"azure 0.1.0 (git+https://github.com/servo/rust-azure)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"gfx_traits 0.0.1",
"ipc-channel 0.1.0 (git+https://github.com/pcwalton/ipc-channel)",
@ -280,7 +280,7 @@ dependencies = [
[[package]]
name = "cssparser"
version = "0.3.5"
version = "0.3.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
@ -872,7 +872,7 @@ dependencies = [
"canvas 0.0.1",
"canvas_traits 0.0.1",
"clock_ticks 0.0.6 (git+https://github.com/tomaka/clock_ticks)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1340,7 +1340,7 @@ dependencies = [
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"canvas 0.0.1",
"canvas_traits 0.0.1",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"devtools_traits 0.0.1",
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1398,7 +1398,7 @@ version = "0.1.0"
source = "git+https://github.com/servo/rust-selectors#572353b3209af040cd3e6261978b09c7f8122844"
dependencies = [
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
"matches 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
"quickersort 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1568,7 +1568,7 @@ name = "style"
version = "0.0.1"
dependencies = [
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1696,7 +1696,7 @@ version = "0.0.1"
dependencies = [
"azure 0.1.0 (git+https://github.com/servo/rust-azure)",
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"getopts 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)",
"html5ever 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)",

16
ports/gonk/Cargo.lock generated
View file

@ -108,7 +108,7 @@ version = "0.0.1"
dependencies = [
"azure 0.1.0 (git+https://github.com/servo/rust-azure)",
"canvas_traits 0.0.1",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"gfx_traits 0.0.1",
"gleam 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)",
@ -125,7 +125,7 @@ name = "canvas_traits"
version = "0.0.1"
dependencies = [
"azure 0.1.0 (git+https://github.com/servo/rust-azure)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"gfx_traits 0.0.1",
"ipc-channel 0.1.0 (git+https://github.com/pcwalton/ipc-channel)",
@ -250,7 +250,7 @@ dependencies = [
[[package]]
name = "cssparser"
version = "0.3.5"
version = "0.3.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
@ -756,7 +756,7 @@ dependencies = [
"canvas 0.0.1",
"canvas_traits 0.0.1",
"clock_ticks 0.0.6 (git+https://github.com/tomaka/clock_ticks)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1206,7 +1206,7 @@ dependencies = [
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"canvas 0.0.1",
"canvas_traits 0.0.1",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"devtools_traits 0.0.1",
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1264,7 +1264,7 @@ version = "0.1.0"
source = "git+https://github.com/servo/rust-selectors#572353b3209af040cd3e6261978b09c7f8122844"
dependencies = [
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
"matches 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
"quickersort 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1414,7 +1414,7 @@ name = "style"
version = "0.0.1"
dependencies = [
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"encoding 0.2.32 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1531,7 +1531,7 @@ version = "0.0.1"
dependencies = [
"azure 0.1.0 (git+https://github.com/servo/rust-azure)",
"bitflags 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
"cssparser 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"euclid 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"getopts 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)",
"html5ever 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)",

View file

@ -52,7 +52,7 @@ fn test_parse_stylesheet() {
declarations: PropertyDeclarationBlock {
normal: Arc::new(vec![]),
important: Arc::new(vec![
PropertyDeclaration::Display(DeclaredValue::SpecifiedValue(
PropertyDeclaration::Display(DeclaredValue::Value(
longhands::display::SpecifiedValue::none)),
]),
},
@ -90,7 +90,7 @@ fn test_parse_stylesheet() {
],
declarations: PropertyDeclarationBlock {
normal: Arc::new(vec![
PropertyDeclaration::Display(DeclaredValue::SpecifiedValue(
PropertyDeclaration::Display(DeclaredValue::Value(
longhands::display::SpecifiedValue::block)),
]),
important: Arc::new(vec![]),
@ -123,7 +123,7 @@ fn test_parse_stylesheet() {
PropertyDeclaration::BackgroundAttachment(DeclaredValue::Initial),
PropertyDeclaration::BackgroundRepeat(DeclaredValue::Initial),
PropertyDeclaration::BackgroundPosition(DeclaredValue::Initial),
PropertyDeclaration::BackgroundColor(DeclaredValue::SpecifiedValue(
PropertyDeclaration::BackgroundColor(DeclaredValue::Value(
longhands::background_color::SpecifiedValue {
authored: Some("blue".to_owned()),
parsed: cssparser::Color::RGBA(cssparser::RGBA {

View file

@ -29,6 +29,12 @@ skip: true
skip: true
[xhtml1print]
skip: true
[css-variables-1_dev]
skip: false
[xhtml1]
skip: true
[xhtml1print]
skip: true
[cssom-1_dev]
skip: false
[xhtml1]

View file

@ -0,0 +1,3 @@
[css-vars-custom-property-inheritance.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,71 @@
[test_variable_legal_values.htm]
type: testharness
[percentage]
expected: FAIL
[number]
expected: FAIL
[length]
expected: FAIL
[time]
expected: FAIL
[function]
expected: FAIL
[nested_function]
expected: FAIL
[parentheses]
expected: FAIL
[braces]
expected: FAIL
[brackets]
expected: FAIL
[at_keyword_unknown]
expected: FAIL
[at_keyword_known]
expected: FAIL
[at_keyword_unknown_and_block]
expected: FAIL
[at_keyword_known_and_block]
expected: FAIL
[unbalanced_close_bracket_at_toplevel]
expected: FAIL
[unbalanced_close_paren_at_toplevel]
expected: FAIL
[unbalanced_close_bracket_in_something_balanced]
expected: FAIL
[unbalanced_close_paren_in_something_balanced]
expected: FAIL
[unbalanced_close_brace_in_something_balanced]
expected: FAIL
[CDO_at_top_level]
expected: FAIL
[CDC_at_top_level]
expected: FAIL
[semicolon_not_at_top_level_value_unused]
expected: FAIL
[CDO_not_at_top_level_value_unused]
expected: FAIL
[CDC_not_at_top_level_value_unused]
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-declaration-08.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-declaration-14.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-declaration-20.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-declaration-24.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-declaration-26.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-declaration-37.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-declaration-53.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-declaration-54.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-declaration-55.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-external-font-face-01.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-external-supports-01.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-font-face-01.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-font-face-02.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-03.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-04.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-13.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-14.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-15.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-18.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-19.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-20.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-26.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-27.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-36.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-reference-38.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-01.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-02.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-03.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-04.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-05.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-06.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-07.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-08.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-09.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-10.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-11.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-12.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-13.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-14.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-15.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-16.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-17.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-18.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-19.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-20.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-21.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-22.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-23.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-24.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-25.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-26.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-27.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-28.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-29.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-30.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-31.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-32.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-33.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-34.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-35.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-36.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-37.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-38.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-39.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-40.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-41.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-42.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-43.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-44.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-45.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-46.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-47.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-48.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-49.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-50.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-51.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-52.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-53.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-54.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-55.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-56.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-57.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-58.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-59.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-60.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-61.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-62.htm]
type: reftest
expected: FAIL

View file

@ -0,0 +1,3 @@
[variable-supports-63.htm]
type: reftest
expected: FAIL

Some files were not shown because too many files have changed in this diff Show more