style: Do not allow a list of strings in the @font-face src descriptor's format() function, only a single format string

This aligns with CSS Fonts 4 (rather than Fonts 3) and with behavior in other browsers;
I don't expect any significant breakage, given that specifying multiple format strings
was never supported in other engines AFAIK, and never served any useful purpose.

Depends on D154234

Differential Revision: https://phabricator.services.mozilla.com/D154235
This commit is contained in:
Jonathan Kew 2022-08-12 11:25:58 +00:00 committed by Martin Robinson
parent b43ac59344
commit 65e6e072ea

View file

@ -32,7 +32,6 @@ use cssparser::{AtRuleParser, DeclarationListParser, DeclarationParser, Parser};
use cssparser::{CowRcStr, SourceLocation}; use cssparser::{CowRcStr, SourceLocation};
use selectors::parser::SelectorParseErrorKind; use selectors::parser::SelectorParseErrorKind;
use std::fmt::{self, Write}; use std::fmt::{self, Write};
use style_traits::values::SequenceWriter;
use style_traits::{Comma, CssWriter, OneOrMoreSeparated, ParseError}; use style_traits::{Comma, CssWriter, OneOrMoreSeparated, ParseError};
use style_traits::{StyleParseErrorKind, ToCss}; use style_traits::{StyleParseErrorKind, ToCss};
@ -76,8 +75,8 @@ pub enum FontFaceSourceListComponent {
pub struct UrlSource { pub struct UrlSource {
/// The specified url. /// The specified url.
pub url: SpecifiedUrl, pub url: SpecifiedUrl,
/// The format hints specified with the `format()` function. /// The format hint specified with the `format()` function, if present.
pub format_hints: Vec<String>, pub format_hint: Option<String>,
} }
impl ToCss for UrlSource { impl ToCss for UrlSource {
@ -86,14 +85,9 @@ impl ToCss for UrlSource {
W: fmt::Write, W: fmt::Write,
{ {
self.url.to_css(dest)?; self.url.to_css(dest)?;
if !self.format_hints.is_empty() { if let Some(hint) = &self.format_hint {
dest.write_str(" format(")?; dest.write_str(" format(")?;
{ dest.write_str(&hint)?;
let mut writer = SequenceWriter::new(dest, ", ");
for hint in self.format_hints.iter() {
writer.item(hint)?;
}
}
dest.write_char(')')?; dest.write_char(')')?;
} }
Ok(()) Ok(())
@ -338,14 +332,11 @@ impl<'a> FontFace<'a> {
.rev() .rev()
.filter(|source| { .filter(|source| {
if let Source::Url(ref url_source) = **source { if let Source::Url(ref url_source) = **source {
let hints = &url_source.format_hints;
// We support only opentype fonts and truetype is an alias for // We support only opentype fonts and truetype is an alias for
// that format. Sources without format hints need to be // that format. Sources without format hints need to be
// downloaded in case we support them. // downloaded in case we support them.
hints.is_empty() || url_source.format_hint.as_ref().map_or(true,
hints.iter().any(|hint| { |hint| hint == "truetype" || hint == "opentype" || hint == "woff")
hint == "truetype" || hint == "opentype" || hint == "woff"
})
} else { } else {
true true
} }
@ -397,20 +388,20 @@ impl Parse for Source {
let url = SpecifiedUrl::parse(context, input)?; let url = SpecifiedUrl::parse(context, input)?;
// Parsing optional format() // Parsing optional format()
let format_hints = if input let format_hint = if input
.try_parse(|input| input.expect_function_matching("format")) .try_parse(|input| input.expect_function_matching("format"))
.is_ok() .is_ok()
{ {
input.parse_nested_block(|input| { input.parse_nested_block(|input| {
input.parse_comma_separated(|input| Ok(input.expect_string()?.as_ref().to_owned())) Ok(Some(input.expect_string()?.as_ref().to_owned()))
})? })?
} else { } else {
vec![] None
}; };
Ok(Source::Url(UrlSource { Ok(Source::Url(UrlSource {
url: url, url: url,
format_hints: format_hints, format_hint: format_hint,
})) }))
} }
} }