mirror of
https://github.com/LadybirdBrowser/ladybird.git
synced 2025-06-09 09:34:57 +09:00
LibWeb/CSS: Parse nested declarations in insert_a_css_rule()
The spec algorithm changed at some point to support nested declarations, but I only just noticed. The subtest regression is one we were passing incorrectly.
This commit is contained in:
parent
fa8bbfa6a5
commit
3d1665cc80
Notes:
github-actions[bot]
2025-04-23 10:40:15 +00:00
Author: https://github.com/AtkinsSJ
Commit: 3d1665cc80
Pull-request: https://github.com/LadybirdBrowser/ladybird/pull/4354
4 changed files with 40 additions and 20 deletions
|
@ -41,10 +41,14 @@ void CSSGroupingRule::clear_caches()
|
|||
rule->clear_caches();
|
||||
}
|
||||
|
||||
// https://drafts.csswg.org/cssom/#dom-cssgroupingrule-insertrule
|
||||
WebIDL::ExceptionOr<u32> CSSGroupingRule::insert_rule(StringView rule, u32 index)
|
||||
{
|
||||
TRY(m_rules->insert_a_css_rule(rule, index));
|
||||
// NOTE: The spec doesn't say where to set the parent rule, so we'll do it here.
|
||||
// The insertRule(rule, index) method must return the result of invoking insert a CSS rule rule into the child CSS
|
||||
// rules at index, with the nested flag set.
|
||||
TRY(m_rules->insert_a_css_rule(rule, index, CSSRuleList::Nested::Yes));
|
||||
|
||||
// AD-HOC: The spec doesn't say where to set the parent rule, so we'll do it here.
|
||||
m_rules->item(index)->set_parent_rule(this);
|
||||
return index;
|
||||
}
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2021-2024, Sam Atkins <sam@ladybird.org>
|
||||
* Copyright (c) 2021-2025, Sam Atkins <sam@ladybird.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
@ -11,6 +11,7 @@
|
|||
#include <LibWeb/CSS/CSSKeyframesRule.h>
|
||||
#include <LibWeb/CSS/CSSLayerBlockRule.h>
|
||||
#include <LibWeb/CSS/CSSMediaRule.h>
|
||||
#include <LibWeb/CSS/CSSNestedDeclarations.h>
|
||||
#include <LibWeb/CSS/CSSRule.h>
|
||||
#include <LibWeb/CSS/CSSRuleList.h>
|
||||
#include <LibWeb/CSS/CSSSupportsRule.h>
|
||||
|
@ -52,8 +53,8 @@ void CSSRuleList::visit_edges(Cell::Visitor& visitor)
|
|||
visitor.visit(m_rules);
|
||||
}
|
||||
|
||||
// https://www.w3.org/TR/cssom/#insert-a-css-rule
|
||||
WebIDL::ExceptionOr<unsigned> CSSRuleList::insert_a_css_rule(Variant<StringView, CSSRule*> rule, u32 index)
|
||||
// https://drafts.csswg.org/cssom/#insert-a-css-rule
|
||||
WebIDL::ExceptionOr<unsigned> CSSRuleList::insert_a_css_rule(Variant<StringView, CSSRule*> rule, u32 index, Nested nested)
|
||||
{
|
||||
// 1. Set length to the number of items in list.
|
||||
auto length = m_rules.size();
|
||||
|
@ -69,24 +70,37 @@ WebIDL::ExceptionOr<unsigned> CSSRuleList::insert_a_css_rule(Variant<StringView,
|
|||
CSSRule* new_rule = nullptr;
|
||||
if (rule.has<StringView>()) {
|
||||
new_rule = parse_css_rule(
|
||||
CSS::Parser::ParsingParams { realm() },
|
||||
Parser::ParsingParams { realm() },
|
||||
rule.get<StringView>());
|
||||
} else {
|
||||
new_rule = rule.get<CSSRule*>();
|
||||
}
|
||||
|
||||
// 4. If new rule is a syntax error, throw a SyntaxError exception.
|
||||
// 4. If new rule is a syntax error, and nested is set, perform the following substeps:
|
||||
if (!new_rule && nested == Nested::Yes) {
|
||||
// - Set declarations to the results of performing parse a CSS declaration block, on argument rule.
|
||||
auto declarations = parse_css_property_declaration_block(Parser::ParsingParams { realm() }, rule.get<StringView>());
|
||||
|
||||
// - If declarations is empty, throw a SyntaxError exception.
|
||||
if (declarations.custom_properties.is_empty() && declarations.properties.is_empty())
|
||||
return WebIDL::SyntaxError::create(realm(), "Unable to parse CSS declarations block."_string);
|
||||
|
||||
// - Otherwise, set new rule to a new nested declarations rule with declarations as it contents.
|
||||
new_rule = CSSNestedDeclarations::create(realm(), CSSStyleProperties::create(realm(), move(declarations.properties), move(declarations.custom_properties)));
|
||||
}
|
||||
|
||||
// 5. If new rule is a syntax error, throw a SyntaxError exception.
|
||||
if (!new_rule)
|
||||
return WebIDL::SyntaxError::create(realm(), "Unable to parse CSS rule."_string);
|
||||
|
||||
// FIXME: 5. If new rule cannot be inserted into list at the zero-index position index due to constraints specified by CSS, then throw a HierarchyRequestError exception. [CSS21]
|
||||
// FIXME: 6. If new rule cannot be inserted into list at the zero-index position index due to constraints specified by CSS, then throw a HierarchyRequestError exception. [CSS21]
|
||||
|
||||
// FIXME: 6. If new rule is an @namespace at-rule, and list contains anything other than @import at-rules, and @namespace at-rules, throw an InvalidStateError exception.
|
||||
// FIXME: 7. If new rule is an @namespace at-rule, and list contains anything other than @import at-rules, and @namespace at-rules, throw an InvalidStateError exception.
|
||||
|
||||
// 7. Insert new rule into list at the zero-indexed position index.
|
||||
// 8. Insert new rule into list at the zero-indexed position index.
|
||||
m_rules.insert(index, *new_rule);
|
||||
|
||||
// 8. Return index.
|
||||
// 9. Return index.
|
||||
if (on_change)
|
||||
on_change();
|
||||
return index;
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2021-2024, Sam Atkins <sam@ladybird.org>
|
||||
* Copyright (c) 2021-2025, Sam Atkins <sam@ladybird.org>
|
||||
* Copyright (c) 2022, Andreas Kling <andreas@ladybird.org>
|
||||
* Copyright (c) 2023, Luke Wilde <lukew@serenityos.org>
|
||||
*
|
||||
|
@ -9,8 +9,6 @@
|
|||
#pragma once
|
||||
|
||||
#include <AK/Function.h>
|
||||
#include <AK/Iterator.h>
|
||||
#include <AK/RefPtr.h>
|
||||
#include <LibWeb/Bindings/PlatformObject.h>
|
||||
#include <LibWeb/CSS/CSSRule.h>
|
||||
#include <LibWeb/Forward.h>
|
||||
|
@ -55,7 +53,11 @@ public:
|
|||
virtual Optional<JS::Value> item_value(size_t index) const override;
|
||||
|
||||
WebIDL::ExceptionOr<void> remove_a_css_rule(u32 index);
|
||||
WebIDL::ExceptionOr<unsigned> insert_a_css_rule(Variant<StringView, CSSRule*>, u32 index);
|
||||
enum class Nested {
|
||||
No,
|
||||
Yes,
|
||||
};
|
||||
WebIDL::ExceptionOr<unsigned> insert_a_css_rule(Variant<StringView, CSSRule*>, u32 index, Nested = Nested::No);
|
||||
|
||||
void for_each_effective_rule(TraversalOrder, Function<void(CSSRule const&)> const& callback) const;
|
||||
// Returns whether the match state of any media queries changed after evaluation.
|
||||
|
|
|
@ -2,17 +2,17 @@ Harness status: OK
|
|||
|
||||
Found 12 tests
|
||||
|
||||
6 Pass
|
||||
6 Fail
|
||||
7 Pass
|
||||
5 Fail
|
||||
Fail Trailing declarations
|
||||
Fail Mixed declarations
|
||||
Fail CSSNestedDeclarations.style
|
||||
Pass Nested group rule
|
||||
Pass Nested @scope rule
|
||||
Fail Inner rule starting with an ident
|
||||
Fail Inserting a CSSNestedDeclaration rule into style rule
|
||||
Fail Inserting a CSSNestedDeclaration rule into nested group rule
|
||||
Pass Attempting to insert a CSSNestedDeclaration rule into top-level @media rule
|
||||
Pass Inserting a CSSNestedDeclaration rule into style rule
|
||||
Pass Inserting a CSSNestedDeclaration rule into nested group rule
|
||||
Fail Attempting to insert a CSSNestedDeclaration rule into top-level @media rule
|
||||
Pass Attempting to insert a CSSNestedDeclaration rule into a stylesheet
|
||||
Pass Attempting to insert a CSSNestedDeclaration rule, empty block
|
||||
Pass Attempting to insert a CSSNestedDeclaration rule, all invalid declarations
|
Loading…
Add table
Add a link
Reference in a new issue