diff --git a/Libraries/LibWeb/CSS/FontFace.cpp b/Libraries/LibWeb/CSS/FontFace.cpp index 60df8b1308e..7a259862240 100644 --- a/Libraries/LibWeb/CSS/FontFace.cpp +++ b/Libraries/LibWeb/CSS/FontFace.cpp @@ -483,6 +483,7 @@ GC::Ref FontFace::load() // FIXME: The ParsedFontFace is kind of expensive to create. We should be using a shared sub-object for the data ParsedFontFace parsed_font_face { + nullptr, font->m_family, font->m_weight.to_number(), 0, // FIXME: slope diff --git a/Libraries/LibWeb/CSS/ParsedFontFace.cpp b/Libraries/LibWeb/CSS/ParsedFontFace.cpp index e451f03d82e..5a9eda365a0 100644 --- a/Libraries/LibWeb/CSS/ParsedFontFace.cpp +++ b/Libraries/LibWeb/CSS/ParsedFontFace.cpp @@ -6,6 +6,7 @@ */ #include +#include #include #include #include @@ -38,7 +39,7 @@ Vector ParsedFontFace::sources_from_style_value(CSSStyle [&](FontSourceStyleValue::Local const& local) { sources.empend(extract_font_name(local.name), OptionalNone {}); }, - [&](::URL::URL const& url) { + [&](URL const& url) { // FIXME: tech() sources.empend(url, font_source.format()); }); @@ -171,6 +172,7 @@ ParsedFontFace ParsedFontFace::from_descriptors(CSSFontFaceDescriptors const& de } return ParsedFontFace { + descriptors.parent_rule()->parent_style_sheet(), move(font_family), move(weight), move(slope), @@ -188,8 +190,9 @@ ParsedFontFace ParsedFontFace::from_descriptors(CSSFontFaceDescriptors const& de }; } -ParsedFontFace::ParsedFontFace(FlyString font_family, Optional weight, Optional slope, Optional width, Vector sources, Vector unicode_ranges, Optional ascent_override, Optional descent_override, Optional line_gap_override, FontDisplay font_display, Optional font_named_instance, Optional font_language_override, Optional> font_feature_settings, Optional> font_variation_settings) - : m_font_family(move(font_family)) +ParsedFontFace::ParsedFontFace(GC::Ptr parent_style_sheet, FlyString font_family, Optional weight, Optional slope, Optional width, Vector sources, Vector unicode_ranges, Optional ascent_override, Optional descent_override, Optional line_gap_override, FontDisplay font_display, Optional font_named_instance, Optional font_language_override, Optional> font_feature_settings, Optional> font_variation_settings) + : m_parent_style_sheet(parent_style_sheet) + , m_font_family(move(font_family)) , m_font_named_instance(move(font_named_instance)) , m_weight(weight) , m_slope(slope) diff --git a/Libraries/LibWeb/CSS/ParsedFontFace.h b/Libraries/LibWeb/CSS/ParsedFontFace.h index 7322a64d1e9..96d6642eaa0 100644 --- a/Libraries/LibWeb/CSS/ParsedFontFace.h +++ b/Libraries/LibWeb/CSS/ParsedFontFace.h @@ -10,16 +10,16 @@ #include #include #include -#include #include #include +#include namespace Web::CSS { class ParsedFontFace { public: struct Source { - Variant local_or_url; + Variant local_or_url; // FIXME: Do we need to keep this around, or is it only needed to discard unwanted formats during parsing? Optional format; }; @@ -27,9 +27,10 @@ public: static Vector sources_from_style_value(CSSStyleValue const&); static ParsedFontFace from_descriptors(CSSFontFaceDescriptors const&); - ParsedFontFace(FlyString font_family, Optional weight, Optional slope, Optional width, Vector sources, Vector unicode_ranges, Optional ascent_override, Optional descent_override, Optional line_gap_override, FontDisplay font_display, Optional font_named_instance, Optional font_language_override, Optional> font_feature_settings, Optional> font_variation_settings); + ParsedFontFace(GC::Ptr parent_style_sheet, FlyString font_family, Optional weight, Optional slope, Optional width, Vector sources, Vector unicode_ranges, Optional ascent_override, Optional descent_override, Optional line_gap_override, FontDisplay font_display, Optional font_named_instance, Optional font_language_override, Optional> font_feature_settings, Optional> font_variation_settings); ~ParsedFontFace() = default; + GC::Ptr parent_style_sheet() const { return m_parent_style_sheet; } Optional ascent_override() const { return m_ascent_override; } Optional descent_override() const { return m_descent_override; } FontDisplay font_display() const { return m_font_display; } @@ -46,6 +47,7 @@ public: Vector const& unicode_ranges() const { return m_unicode_ranges; } private: + GC::Ptr m_parent_style_sheet; FlyString m_font_family; Optional m_font_named_instance; Optional m_weight; diff --git a/Libraries/LibWeb/CSS/Parser/ValueParsing.cpp b/Libraries/LibWeb/CSS/Parser/ValueParsing.cpp index ff2f180b179..4c7542414de 100644 --- a/Libraries/LibWeb/CSS/Parser/ValueParsing.cpp +++ b/Libraries/LibWeb/CSS/Parser/ValueParsing.cpp @@ -3813,10 +3813,6 @@ RefPtr Parser::parse_font_source_value(TokenStreamurl()); - if (!completed_url.has_value()) - return nullptr; Optional format; @@ -3859,7 +3855,7 @@ RefPtr Parser::parse_font_source_value(TokenStream#)]? transaction.commit(); - return FontSourceStyleValue::create(completed_url.release_value(), move(format)); + return FontSourceStyleValue::create(url.release_value(), move(format)); } NonnullRefPtr Parser::resolve_unresolved_style_value(ParsingParams const& context, DOM::Element& element, Optional pseudo_element, PropertyID property_id, UnresolvedStyleValue const& unresolved) diff --git a/Libraries/LibWeb/CSS/StyleComputer.cpp b/Libraries/LibWeb/CSS/StyleComputer.cpp index 7a6fc8682d3..57fce2fd892 100644 --- a/Libraries/LibWeb/CSS/StyleComputer.cpp +++ b/Libraries/LibWeb/CSS/StyleComputer.cpp @@ -187,8 +187,9 @@ StyleComputer::StyleComputer(DOM::Document& document) StyleComputer::~StyleComputer() = default; -FontLoader::FontLoader(StyleComputer& style_computer, FlyString family_name, Vector unicode_ranges, Vector<::URL::URL> urls, Function)> on_load) +FontLoader::FontLoader(StyleComputer& style_computer, GC::Ptr parent_style_sheet, FlyString family_name, Vector unicode_ranges, Vector urls, Function)> on_load) : m_style_computer(style_computer) + , m_parent_style_sheet(parent_style_sheet) , m_family_name(move(family_name)) , m_unicode_ranges(move(unicode_ranges)) , m_urls(move(urls)) @@ -225,8 +226,8 @@ void FontLoader::start_loading_next_url() // To fetch a font given a selected url for @font-face rule, fetch url, with stylesheet being rule’s parent // CSS style sheet, destination "font", CORS mode "cors", and processResponse being the following steps given // response res and null, failure or a byte stream stream: - // FIXME: Get the rule's parent style sheet from somewhere - auto maybe_fetch_controller = fetch_a_style_resource(m_urls.take_first(), GC::Ref { m_style_computer.document() }, Fetch::Infrastructure::Request::Destination::Font, CorsMode::Cors, + auto style_sheet_or_document = m_parent_style_sheet ? StyleSheetOrDocument { *m_parent_style_sheet } : StyleSheetOrDocument { m_style_computer.document() }; + auto maybe_fetch_controller = fetch_a_style_resource(m_urls.take_first(), style_sheet_or_document, Fetch::Infrastructure::Request::Destination::Font, CorsMode::Cors, [weak_loader = make_weak_ptr()](auto response, auto stream) { // NB: If the FontLoader died before this fetch completed, nobody wants the data. if (weak_loader.is_null()) @@ -3049,11 +3050,10 @@ Optional StyleComputer::load_font_face(ParsedFontFace const& font_f }; // FIXME: Pass the sources directly, so the font loader can make use of the format information, or load local fonts. - Vector<::URL::URL> urls; + Vector urls; for (auto const& source : font_face.sources()) { - // FIXME: These should be loaded relative to the stylesheet URL instead of the document URL. - if (source.local_or_url.has<::URL::URL>()) - urls.append(*m_document->encoding_parse_url(source.local_or_url.get<::URL::URL>().to_string())); + if (source.local_or_url.has()) + urls.append(source.local_or_url.get()); // FIXME: Handle local() } @@ -3063,7 +3063,7 @@ Optional StyleComputer::load_font_face(ParsedFontFace const& font_f return {}; } - auto loader = make(*this, font_face.font_family(), font_face.unicode_ranges(), move(urls), move(on_load)); + auto loader = make(*this, font_face.parent_style_sheet(), font_face.font_family(), font_face.unicode_ranges(), move(urls), move(on_load)); auto& loader_ref = *loader; auto maybe_font_loaders_list = m_loaded_fonts.get(key); if (maybe_font_loaders_list.has_value()) { diff --git a/Libraries/LibWeb/CSS/StyleComputer.h b/Libraries/LibWeb/CSS/StyleComputer.h index 9a9834d9e42..05dd8fd0a66 100644 --- a/Libraries/LibWeb/CSS/StyleComputer.h +++ b/Libraries/LibWeb/CSS/StyleComputer.h @@ -315,7 +315,7 @@ private: class FontLoader : public Weakable { public: - FontLoader(StyleComputer& style_computer, FlyString family_name, Vector unicode_ranges, Vector<::URL::URL> urls, ESCAPING Function)> on_load = {}); + FontLoader(StyleComputer& style_computer, GC::Ptr parent_style_sheet, FlyString family_name, Vector unicode_ranges, Vector urls, ESCAPING Function)> on_load = {}); virtual ~FontLoader(); @@ -333,10 +333,11 @@ private: void font_did_load_or_fail(RefPtr); StyleComputer& m_style_computer; + GC::Ptr m_parent_style_sheet; FlyString m_family_name; Vector m_unicode_ranges; RefPtr m_vector_font; - Vector<::URL::URL> m_urls; + Vector m_urls; GC::Root m_fetch_controller; Function)> m_on_load; }; diff --git a/Libraries/LibWeb/CSS/StyleValues/FontSourceStyleValue.cpp b/Libraries/LibWeb/CSS/StyleValues/FontSourceStyleValue.cpp index ee8cb1641db..eae65e1e34e 100644 --- a/Libraries/LibWeb/CSS/StyleValues/FontSourceStyleValue.cpp +++ b/Libraries/LibWeb/CSS/StyleValues/FontSourceStyleValue.cpp @@ -34,11 +34,11 @@ String FontSourceStyleValue::to_string(SerializationMode) const builder.append(')'); return builder.to_string_without_validation(); }, - [this](::URL::URL const& url) { + [this](URL const& url) { // [ format()]? [ tech( #)]? // FIXME: tech() StringBuilder builder; - serialize_a_url(builder, url.to_string()); + builder.append(url.to_string()); if (m_format.has_value()) { builder.append(" format("sv); @@ -59,8 +59,8 @@ bool FontSourceStyleValue::properties_equal(FontSourceStyleValue const& other) c } return false; }, - [&other](::URL::URL const& url) { - if (auto* other_url = other.m_source.get_pointer<::URL::URL>()) { + [&other](URL const& url) { + if (auto* other_url = other.m_source.get_pointer()) { return url == *other_url; } return false; diff --git a/Libraries/LibWeb/CSS/StyleValues/FontSourceStyleValue.h b/Libraries/LibWeb/CSS/StyleValues/FontSourceStyleValue.h index 4fa02aa9529..60fed041d8c 100644 --- a/Libraries/LibWeb/CSS/StyleValues/FontSourceStyleValue.h +++ b/Libraries/LibWeb/CSS/StyleValues/FontSourceStyleValue.h @@ -8,6 +8,7 @@ #include #include +#include namespace Web::CSS { @@ -16,7 +17,7 @@ public: struct Local { NonnullRefPtr name; }; - using Source = Variant; + using Source = Variant; static ValueComparingNonnullRefPtr create(Source source, Optional format) { diff --git a/Libraries/LibWeb/Dump.cpp b/Libraries/LibWeb/Dump.cpp index e7d140a119b..7fa222b8f42 100644 --- a/Libraries/LibWeb/Dump.cpp +++ b/Libraries/LibWeb/Dump.cpp @@ -728,12 +728,15 @@ void dump_font_face_rule(StringBuilder& builder, CSS::CSSFontFaceRule const& rul indent(builder, indent_levels + 1); builder.append("sources:\n"sv); - for (auto const& source : font_face.sources()) { + for (auto const& [local_or_url, format] : font_face.sources()) { indent(builder, indent_levels + 2); - if (source.local_or_url.has()) - builder.appendff("url={}, format={}\n", source.local_or_url.get(), source.format.value_or("???"_string)); - else - builder.appendff("local={}\n", source.local_or_url.get()); + local_or_url.visit( + [&builder, &format](CSS::URL const& url) { + builder.appendff("url={}, format={}\n", url, format.value_or("???"_string)); + }, + [&builder](FlyString const& local) { + builder.appendff("local={}\n", local); + }); } indent(builder, indent_levels + 1);