mirror of
https://github.com/mozilla/gecko-dev.git
synced 2025-02-05 22:05:40 +00:00
Bug 1619701 - Respect the cascade properly when in high-contrast mode. r=morgan
Differential Revision: https://phabricator.services.mozilla.com/D65345 --HG-- extra : moz-landing-system : lando
This commit is contained in:
parent
6e6db2f667
commit
1febc27ba3
@ -10,12 +10,12 @@
|
||||
height: 100px;
|
||||
width: 100px;
|
||||
}
|
||||
.url {
|
||||
background-image: url("green.png");
|
||||
}
|
||||
.gradient {
|
||||
background-image: linear-gradient(red, red);
|
||||
}
|
||||
.url {
|
||||
background-image: url("green.png");
|
||||
}
|
||||
.urlGradient {
|
||||
background-image: url("red.png"), linear-gradient(red, red);
|
||||
}
|
||||
|
15
layout/reftests/high-contrast/cascade-001.html
Normal file
15
layout/reftests/high-contrast/cascade-001.html
Normal file
@ -0,0 +1,15 @@
|
||||
<!doctype html>
|
||||
<style>
|
||||
body { margin: 0 }
|
||||
|
||||
div {
|
||||
width: 100vw;
|
||||
height: 100vh;
|
||||
color: transparent;
|
||||
}
|
||||
|
||||
div {
|
||||
color: black;
|
||||
}
|
||||
</style>
|
||||
<div>You should see me</div>
|
@ -35,3 +35,5 @@ pref(browser.display.document_color_use,0) needs-focus != selection-001.html sel
|
||||
|
||||
pref(browser.display.document_color_use,2) == non-themed-button-001.html non-themed-button-001-ref.html
|
||||
pref(browser.display.document_color_use,2) == non-themed-button-002.html non-themed-button-002-ref.html
|
||||
|
||||
!= cascade-001.html about:blank
|
||||
|
@ -337,94 +337,74 @@ where
|
||||
context.builder.build()
|
||||
}
|
||||
|
||||
/// How should a declaration behave when ignoring document colors?
|
||||
enum DeclarationApplication {
|
||||
/// We should apply the declaration.
|
||||
Apply,
|
||||
/// We should ignore the declaration.
|
||||
Ignore,
|
||||
/// We should apply the following declaration, only if any other declaration
|
||||
/// hasn't set it before.
|
||||
ApplyUnlessOverriden(PropertyDeclaration),
|
||||
}
|
||||
/// For ignored colors mode, we sometimes want to do something equivalent to
|
||||
/// "revert-or-initial", where we `revert` for a given origin, but then apply a
|
||||
/// given initial value if nothing in other origins did override it.
|
||||
///
|
||||
/// This is a bit of a clunky way of achieving this.
|
||||
type DeclarationsToApplyUnlessOverriden = SmallVec::<[PropertyDeclaration; 2]>;
|
||||
|
||||
fn application_when_ignoring_colors(
|
||||
fn tweak_when_ignoring_colors(
|
||||
builder: &StyleBuilder,
|
||||
longhand_id: LonghandId,
|
||||
origin: Origin,
|
||||
declaration: &PropertyDeclaration,
|
||||
) -> DeclarationApplication {
|
||||
declaration: &mut Cow<PropertyDeclaration>,
|
||||
declarations_to_apply_unless_overriden: &mut DeclarationsToApplyUnlessOverriden,
|
||||
) {
|
||||
if !longhand_id.ignored_when_document_colors_disabled() {
|
||||
return DeclarationApplication::Apply;
|
||||
return;
|
||||
}
|
||||
|
||||
let is_ua_or_user_rule = matches!(origin, Origin::User | Origin::UserAgent);
|
||||
if is_ua_or_user_rule {
|
||||
return DeclarationApplication::Apply;
|
||||
return;
|
||||
}
|
||||
|
||||
// Don't override background-color on ::-moz-color-swatch. It is set as an
|
||||
// author style (via the style attribute), but it's pretty important for it
|
||||
// to show up for obvious reasons :)
|
||||
if builder.pseudo.map_or(false, |p| p.is_color_swatch()) && longhand_id == LonghandId::BackgroundColor {
|
||||
return DeclarationApplication::Apply;
|
||||
return;
|
||||
}
|
||||
|
||||
// Treat background-color a bit differently. If the specified color is
|
||||
// anything other than a fully transparent color, convert it into the
|
||||
// Device's default background color.
|
||||
// Also: for now, we treat background-image a bit differently, too.
|
||||
// background-image is marked as ignored, but really, we only ignore
|
||||
// it when backplates are disabled (since then text may be unreadable over
|
||||
// a background image, if we're ignoring document colors).
|
||||
// Here we check backplate status to decide if ignoring background-image
|
||||
// is the right decision.
|
||||
match *declaration {
|
||||
// If we've got multiple declarations in the same block, they'll
|
||||
// get overridden at parse time. We should probably adjust this
|
||||
// to turn Ignored decls into `none`. See 1619701
|
||||
// A few special-cases ahead.
|
||||
match **declaration {
|
||||
// We honor color and background-color: transparent, and
|
||||
// "revert-or-initial" otherwise.
|
||||
PropertyDeclaration::BackgroundColor(ref color) => {
|
||||
if color.is_transparent() {
|
||||
return DeclarationApplication::Apply;
|
||||
return;
|
||||
}
|
||||
let color = builder.device.default_background_color();
|
||||
DeclarationApplication::ApplyUnlessOverriden(
|
||||
declarations_to_apply_unless_overriden.push(
|
||||
PropertyDeclaration::BackgroundColor(color.into())
|
||||
)
|
||||
}
|
||||
PropertyDeclaration::Color(ref color) => {
|
||||
// otherwise.
|
||||
if color.0.is_transparent() {
|
||||
return DeclarationApplication::Apply;
|
||||
}
|
||||
if builder.get_parent_inherited_text().clone_color().alpha != 0 {
|
||||
return DeclarationApplication::Ignore;
|
||||
return;
|
||||
}
|
||||
let color = builder.device.default_color();
|
||||
DeclarationApplication::ApplyUnlessOverriden(
|
||||
declarations_to_apply_unless_overriden.push(
|
||||
PropertyDeclaration::Color(specified::ColorPropertyValue(color.into()))
|
||||
)
|
||||
},
|
||||
// In the future, if/when we remove the backplate pref, we can remove this
|
||||
// special case along with the 'ignored_when_colors_disabled=True' mako line
|
||||
// for the "background-image" property.
|
||||
// We honor url background-images if backplating.
|
||||
#[cfg(feature = "gecko")]
|
||||
PropertyDeclaration::BackgroundImage(ref bkg) => {
|
||||
use crate::values::generics::image::Image;
|
||||
// We should only allow images to be rendered in HCM if the backplate pref
|
||||
// is enabled, and if all the images applied to the background are from URLs.
|
||||
// If one or more background images aren't from URL's (ie. gradients)
|
||||
// we should ignore all background-image styling.
|
||||
if static_prefs::pref!("browser.display.permit_backplate") {
|
||||
if bkg.0.iter().all(|image| matches!(*image, Image::Url(..))) {
|
||||
return DeclarationApplication::Apply;
|
||||
return;
|
||||
}
|
||||
return DeclarationApplication::Ignore;
|
||||
} else {
|
||||
return DeclarationApplication::Ignore;
|
||||
}
|
||||
},
|
||||
_ => DeclarationApplication::Ignore,
|
||||
_ => {},
|
||||
}
|
||||
|
||||
*declaration.to_mut() = PropertyDeclaration::css_wide_keyword(longhand_id, CSSWideKeyword::Revert);
|
||||
|
||||
}
|
||||
|
||||
struct Cascade<'a, 'b: 'a> {
|
||||
@ -502,7 +482,7 @@ impl<'a, 'b: 'a> Cascade<'a, 'b> {
|
||||
|
||||
let ignore_colors = !self.context.builder.device.use_document_colors();
|
||||
let mut declarations_to_apply_unless_overriden =
|
||||
SmallVec::<[PropertyDeclaration; 2]>::new();
|
||||
DeclarationsToApplyUnlessOverriden::new();
|
||||
|
||||
for (declaration, origin) in declarations {
|
||||
let declaration_id = declaration.id();
|
||||
@ -544,26 +524,23 @@ impl<'a, 'b: 'a> Cascade<'a, 'b> {
|
||||
continue;
|
||||
}
|
||||
|
||||
let declaration = self.substitute_variables_if_needed(declaration);
|
||||
let mut declaration = self.substitute_variables_if_needed(declaration);
|
||||
|
||||
// When document colors are disabled, do special handling of
|
||||
// properties that are marked as ignored in that mode.
|
||||
if ignore_colors {
|
||||
let application = application_when_ignoring_colors(
|
||||
tweak_when_ignoring_colors(
|
||||
&self.context.builder,
|
||||
longhand_id,
|
||||
origin,
|
||||
&declaration,
|
||||
&mut declaration,
|
||||
&mut declarations_to_apply_unless_overriden,
|
||||
);
|
||||
debug_assert_eq!(
|
||||
declaration.id(),
|
||||
PropertyDeclarationId::Longhand(longhand_id),
|
||||
"Shouldn't change the declaration id!",
|
||||
);
|
||||
|
||||
match application {
|
||||
DeclarationApplication::Ignore => continue,
|
||||
DeclarationApplication::Apply => {},
|
||||
DeclarationApplication::ApplyUnlessOverriden(decl) => {
|
||||
declarations_to_apply_unless_overriden.push(decl);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let css_wide_keyword = declaration.get_css_wide_keyword();
|
||||
|
@ -1590,10 +1590,7 @@ impl UnparsedValue {
|
||||
} else {
|
||||
CSSWideKeyword::Initial
|
||||
};
|
||||
PropertyDeclaration::CSSWideKeyword(WideKeywordDeclaration {
|
||||
id: longhand_id,
|
||||
keyword,
|
||||
})
|
||||
PropertyDeclaration::css_wide_keyword(longhand_id, keyword)
|
||||
};
|
||||
|
||||
let css = match crate::custom_properties::substitute(
|
||||
@ -1630,10 +1627,7 @@ impl UnparsedValue {
|
||||
let mut input = Parser::new(&mut input);
|
||||
input.skip_whitespace(); // Unnecessary for correctness, but may help try() rewind less.
|
||||
if let Ok(keyword) = input.try(CSSWideKeyword::parse) {
|
||||
return PropertyDeclaration::CSSWideKeyword(WideKeywordDeclaration {
|
||||
id: longhand_id,
|
||||
keyword,
|
||||
});
|
||||
return PropertyDeclaration::css_wide_keyword(longhand_id, keyword);
|
||||
}
|
||||
|
||||
let declaration = input.parse_entirely(|input| {
|
||||
@ -2239,6 +2233,12 @@ impl PropertyDeclaration {
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns a CSS-wide keyword declaration for a given property.
|
||||
#[inline]
|
||||
pub fn css_wide_keyword(id: LonghandId, keyword: CSSWideKeyword) -> Self {
|
||||
Self::CSSWideKeyword(WideKeywordDeclaration { id, keyword })
|
||||
}
|
||||
|
||||
/// Returns a CSS-wide keyword if the declaration's value is one.
|
||||
#[inline]
|
||||
pub fn get_css_wide_keyword(&self) -> Option<CSSWideKeyword> {
|
||||
@ -2367,9 +2367,7 @@ impl PropertyDeclaration {
|
||||
PropertyId::Longhand(id) => {
|
||||
input.skip_whitespace(); // Unnecessary for correctness, but may help try() rewind less.
|
||||
input.try(CSSWideKeyword::parse).map(|keyword| {
|
||||
PropertyDeclaration::CSSWideKeyword(
|
||||
WideKeywordDeclaration { id, keyword },
|
||||
)
|
||||
PropertyDeclaration::css_wide_keyword(id, keyword)
|
||||
}).or_else(|()| {
|
||||
input.look_for_var_or_env_functions();
|
||||
input.parse_entirely(|input| id.parse_value(context, input))
|
||||
@ -2403,12 +2401,7 @@ impl PropertyDeclaration {
|
||||
declarations.all_shorthand = AllShorthand::CSSWideKeyword(keyword)
|
||||
} else {
|
||||
for longhand in id.longhands() {
|
||||
declarations.push(PropertyDeclaration::CSSWideKeyword(
|
||||
WideKeywordDeclaration {
|
||||
id: longhand,
|
||||
keyword,
|
||||
},
|
||||
))
|
||||
declarations.push(PropertyDeclaration::css_wide_keyword(longhand, keyword));
|
||||
}
|
||||
}
|
||||
} else {
|
||||
@ -2550,12 +2543,7 @@ impl<'a> Iterator for AllShorthandDeclarationIterator<'a> {
|
||||
match *self.all_shorthand {
|
||||
AllShorthand::NotSet => None,
|
||||
AllShorthand::CSSWideKeyword(ref keyword) => {
|
||||
Some(PropertyDeclaration::CSSWideKeyword(
|
||||
WideKeywordDeclaration {
|
||||
id: self.longhands.next()?,
|
||||
keyword: *keyword
|
||||
}
|
||||
))
|
||||
Some(PropertyDeclaration::css_wide_keyword(self.longhands.next()?, *keyword))
|
||||
}
|
||||
AllShorthand::WithVariables(ref unparsed) => {
|
||||
Some(PropertyDeclaration::WithVariables(
|
||||
|
Loading…
x
Reference in New Issue
Block a user