mirror of
				https://github.com/RGBCube/serenity
				synced 2025-10-31 19:12:43 +00:00 
			
		
		
		
	LibWeb: Keep CSS sheets sorted in document tree order
This ensures that style is applied consistently, even if the document has external CSS resources that don't always arrive in the same order.
This commit is contained in:
		
							parent
							
								
									32c99313a6
								
							
						
					
					
						commit
						524ec95bcd
					
				
					 4 changed files with 24 additions and 10 deletions
				
			
		|  | @ -141,7 +141,7 @@ void StyleComputer::for_each_stylesheet(CascadeOrigin cascade_origin, Callback c | |||
|     } | ||||
|     if (cascade_origin == CascadeOrigin::Author) { | ||||
|         for (auto const& sheet : document().style_sheets().sheets()) { | ||||
|             callback(sheet); | ||||
|             callback(*sheet); | ||||
|         } | ||||
|     } | ||||
| } | ||||
|  |  | |||
|  | @ -4,6 +4,7 @@ | |||
|  * SPDX-License-Identifier: BSD-2-Clause | ||||
|  */ | ||||
| 
 | ||||
| #include <AK/QuickSort.h> | ||||
| #include <LibWeb/Bindings/StyleSheetListPrototype.h> | ||||
| #include <LibWeb/CSS/StyleSheetList.h> | ||||
| #include <LibWeb/DOM/Document.h> | ||||
|  | @ -15,6 +16,8 @@ void StyleSheetList::add_sheet(CSSStyleSheet& sheet) | |||
|     sheet.set_style_sheet_list({}, this); | ||||
|     m_sheets.append(sheet); | ||||
| 
 | ||||
|     sort_sheets(); | ||||
| 
 | ||||
|     m_document.style_computer().invalidate_rule_cache(); | ||||
|     m_document.style_computer().load_fonts_from_sheet(sheet); | ||||
|     m_document.invalidate_style(); | ||||
|  | @ -23,7 +26,9 @@ void StyleSheetList::add_sheet(CSSStyleSheet& sheet) | |||
| void StyleSheetList::remove_sheet(CSSStyleSheet& sheet) | ||||
| { | ||||
|     sheet.set_style_sheet_list({}, nullptr); | ||||
|     m_sheets.remove_first_matching([&](auto& entry) { return &entry == &sheet; }); | ||||
|     m_sheets.remove_first_matching([&](auto& entry) { return entry.ptr() == &sheet; }); | ||||
| 
 | ||||
|     sort_sheets(); | ||||
| 
 | ||||
|     m_document.style_computer().invalidate_rule_cache(); | ||||
|     m_document.invalidate_style(); | ||||
|  | @ -45,8 +50,8 @@ void StyleSheetList::visit_edges(Cell::Visitor& visitor) | |||
| { | ||||
|     Base::visit_edges(visitor); | ||||
|     visitor.visit(m_document); | ||||
|     for (auto& sheet : m_sheets) | ||||
|         visitor.visit(&sheet); | ||||
|     for (auto sheet : m_sheets) | ||||
|         visitor.visit(sheet.ptr()); | ||||
| } | ||||
| 
 | ||||
| // https://www.w3.org/TR/cssom/#ref-for-dfn-supported-property-indices%E2%91%A1
 | ||||
|  | @ -65,7 +70,14 @@ JS::Value StyleSheetList::item_value(size_t index) const | |||
|     if (index >= m_sheets.size()) | ||||
|         return JS::js_undefined(); | ||||
| 
 | ||||
|     return &m_sheets[index]; | ||||
|     return m_sheets[index].ptr(); | ||||
| } | ||||
| 
 | ||||
| void StyleSheetList::sort_sheets() | ||||
| { | ||||
|     quick_sort(m_sheets, [](JS::NonnullGCPtr<StyleSheet> a, JS::NonnullGCPtr<StyleSheet> b) { | ||||
|         return a->owner_node()->is_before(*b->owner_node()); | ||||
|     }); | ||||
| } | ||||
| 
 | ||||
| } | ||||
|  |  | |||
|  | @ -20,14 +20,14 @@ public: | |||
|     void add_sheet(CSSStyleSheet&); | ||||
|     void remove_sheet(CSSStyleSheet&); | ||||
| 
 | ||||
|     Vector<CSSStyleSheet&> const& sheets() const { return m_sheets; } | ||||
|     Vector<CSSStyleSheet&>& sheets() { return m_sheets; } | ||||
|     Vector<JS::NonnullGCPtr<CSSStyleSheet>> const& sheets() const { return m_sheets; } | ||||
|     Vector<JS::NonnullGCPtr<CSSStyleSheet>>& sheets() { return m_sheets; } | ||||
| 
 | ||||
|     CSSStyleSheet* item(size_t index) const | ||||
|     { | ||||
|         if (index >= m_sheets.size()) | ||||
|             return {}; | ||||
|         return &const_cast<CSSStyleSheet&>(m_sheets[index]); | ||||
|         return const_cast<CSSStyleSheet*>(m_sheets[index].ptr()); | ||||
|     } | ||||
| 
 | ||||
|     size_t length() const { return m_sheets.size(); } | ||||
|  | @ -43,8 +43,10 @@ private: | |||
| 
 | ||||
|     virtual void visit_edges(Cell::Visitor&) override; | ||||
| 
 | ||||
|     void sort_sheets(); | ||||
| 
 | ||||
|     DOM::Document& m_document; | ||||
|     Vector<CSSStyleSheet&> m_sheets; | ||||
|     Vector<JS::NonnullGCPtr<CSSStyleSheet>> m_sheets; | ||||
| }; | ||||
| 
 | ||||
| } | ||||
|  |  | |||
|  | @ -1582,7 +1582,7 @@ void Document::evaluate_media_rules() | |||
| { | ||||
|     bool any_media_queries_changed_match_state = false; | ||||
|     for (auto& style_sheet : style_sheets().sheets()) { | ||||
|         if (style_sheet.evaluate_media_queries(window())) | ||||
|         if (style_sheet->evaluate_media_queries(window())) | ||||
|             any_media_queries_changed_match_state = true; | ||||
|     } | ||||
| 
 | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Andreas Kling
						Andreas Kling