script/dom/css/
cssnesteddeclarations.rs1use std::cell::RefCell;
6
7use dom_struct::dom_struct;
8use servo_arc::Arc;
9use style::shared_lock::{Locked, SharedRwLockReadGuard, ToCssWithGuard};
10use style::stylesheets::{CssRuleType, NestedDeclarationsRule};
11
12use super::cssrule::{CSSRule, SpecificCSSRule};
13use super::cssstyledeclaration::{CSSModificationAccess, CSSStyleDeclaration, CSSStyleOwner};
14use super::cssstylesheet::CSSStyleSheet;
15use crate::dom::bindings::codegen::Bindings::CSSNestedDeclarationsBinding::CSSNestedDeclarationsMethods;
16use crate::dom::bindings::inheritance::Castable;
17use crate::dom::bindings::reflector::{DomGlobal, reflect_dom_object};
18use crate::dom::bindings::root::{Dom, DomRoot, MutNullableDom};
19use crate::dom::bindings::str::DOMString;
20use crate::dom::window::Window;
21use crate::script_runtime::CanGc;
22
23#[dom_struct]
24pub(crate) struct CSSNestedDeclarations {
25 cssrule: CSSRule,
26 #[ignore_malloc_size_of = "Stylo"]
27 #[no_trace]
28 nesteddeclarationsrule: RefCell<Arc<Locked<NestedDeclarationsRule>>>,
29 style_decl: MutNullableDom<CSSStyleDeclaration>,
30}
31
32impl CSSNestedDeclarations {
33 pub(crate) fn new_inherited(
34 parent_stylesheet: &CSSStyleSheet,
35 nesteddeclarationsrule: Arc<Locked<NestedDeclarationsRule>>,
36 ) -> Self {
37 Self {
38 cssrule: CSSRule::new_inherited(parent_stylesheet),
39 nesteddeclarationsrule: RefCell::new(nesteddeclarationsrule),
40 style_decl: Default::default(),
41 }
42 }
43
44 pub(crate) fn new(
45 window: &Window,
46 parent_stylesheet: &CSSStyleSheet,
47 nesteddeclarationsrule: Arc<Locked<NestedDeclarationsRule>>,
48 can_gc: CanGc,
49 ) -> DomRoot<Self> {
50 reflect_dom_object(
51 Box::new(Self::new_inherited(
52 parent_stylesheet,
53 nesteddeclarationsrule,
54 )),
55 window,
56 can_gc,
57 )
58 }
59
60 pub(crate) fn update_rule(
61 &self,
62 nesteddeclarationsrule: Arc<Locked<NestedDeclarationsRule>>,
63 guard: &SharedRwLockReadGuard,
64 ) {
65 if let Some(ref style_decl) = self.style_decl.get() {
66 style_decl
67 .update_property_declaration_block(&nesteddeclarationsrule.read_with(guard).block);
68 }
69 *self.nesteddeclarationsrule.borrow_mut() = nesteddeclarationsrule;
70 }
71}
72
73impl SpecificCSSRule for CSSNestedDeclarations {
74 fn ty(&self) -> CssRuleType {
75 CssRuleType::NestedDeclarations
76 }
77
78 fn get_css(&self) -> DOMString {
79 let guard = self.cssrule.shared_lock().read();
80 self.nesteddeclarationsrule
81 .borrow()
82 .read_with(&guard)
83 .to_css_string(&guard)
84 .into()
85 }
86}
87
88impl CSSNestedDeclarationsMethods<crate::DomTypeHolder> for CSSNestedDeclarations {
89 fn Style(&self, can_gc: CanGc) -> DomRoot<CSSStyleDeclaration> {
91 self.style_decl.or_init(|| {
92 let guard = self.cssrule.shared_lock().read();
93 CSSStyleDeclaration::new(
94 self.global().as_window(),
95 CSSStyleOwner::CSSRule(
96 Dom::from_ref(self.upcast()),
97 RefCell::new(
98 self.nesteddeclarationsrule
99 .borrow()
100 .read_with(&guard)
101 .block
102 .clone(),
103 ),
104 ),
105 None,
106 CSSModificationAccess::ReadWrite,
107 can_gc,
108 )
109 })
110 }
111}