Repository: servo/servo
File: components/script/dom/node.rs (Rust)

Code before:
    }

    pub(crate) fn style(&self) -> Option<ServoArc<ComputedValues>> {
        self.owner_window().layout_reflow(QueryMsg::StyleQuery);
        self.style_data
            .borrow()
            .as_ref()
            .map(|data| data.element_data.borrow().styles.primary().clone())
    }

    /// <https://html.spec.whatwg.org/multipage/#language>
    pub(crate) fn get_lang(&self) -> Option<String> {
        self.inclusive_ancestors(ShadowIncluding::Yes)
            .find_map(|node| {
                node.downcast::<Element>().and_then(|el| {
                    el.get_attribute(&ns!(xml), &local_name!("lang"))
                        .or_else(|| el.get_attribute(&ns!(), &local_name!("lang")))
                        .map(|attr| String::from(attr.Value()))
                })
                // TODO: Check meta tags for a pragma-set default language
                // TODO: Check HTTP Content-Language header
            })
    }

    /// <https://dom.spec.whatwg.org/#assign-slotables-for-a-tree>
    pub(crate) fn assign_slottables_for_a_tree(&self, force: bool) {
        // NOTE: This method traverses all descendants of the node and is potentially very
        // expensive. If the node is neither a shadowroot nor a slot then assigning slottables
        // for it won't have any effect, so we take a fast path out.
        // In the case of node removal, we need to force re-assignment of slottables
        // even if the node is not a shadow root or slot, this allows us to clear assigned
        // slots from any slottables that were assigned to slots in the removed subtree.
        let is_shadow_root_with_slots = self
            .downcast::<ShadowRoot>()
            .is_some_and(|shadow_root| shadow_root.has_slot_descendants());
        if !is_shadow_root_with_slots && !self.is::<HTMLSlotElement>() && !force {
            return;
        }

        // > To assign slottables for a tree, given a node root, run assign slottables for each slot
        // > slot in root’s inclusive descendants, in tree order.
        for node in self.traverse_preorder(ShadowIncluding::No) {
            if let Some(slot) = node.downcast::<HTMLSlotElement>() {
                slot.assign_slottables();
            }
        }
    }

    pub(crate) fn assigned_slot(&self) -> Option<DomRoot<HTMLSlotElement>> {
        let assigned_slot = self
            .rare_data

Review comment (suggestion):
Nit: use enum with two booleans to be more descriptive. Suggestion:

```rust
enum ForceSlottableNodeRecalcilation {
  Force,
  Skip,
}
```

Code after:
                .primary()
                .get_box()
                .display
                .is_none()
        })
    }

    pub(crate) fn style(&self) -> Option<ServoArc<ComputedValues>> {
        self.owner_window().layout_reflow(QueryMsg::StyleQuery);
        self.style_data
            .borrow()
            .as_ref()
            .map(|data| data.element_data.borrow().styles.primary().clone())
    }

    /// <https://html.spec.whatwg.org/multipage/#language>
    pub(crate) fn get_lang(&self) -> Option<String> {
        self.inclusive_ancestors(ShadowIncluding::Yes)
            .find_map(|node| {
                node.downcast::<Element>().and_then(|el| {
                    el.get_attribute(&ns!(xml), &local_name!("lang"))
                        .or_else(|| el.get_attribute(&ns!(), &local_name!("lang")))
                        .map(|attr| String::from(attr.Value()))
                })
                // TODO: Check meta tags for a pragma-set default language
                // TODO: Check HTTP Content-Language header
            })
    }

    /// <https://dom.spec.whatwg.org/#assign-slotables-for-a-tree>
    pub(crate) fn assign_slottables_for_a_tree(&self, force: ForceSlottableNodeReconciliation) {
        // NOTE: This method traverses all descendants of the node and is potentially very
        // expensive. If the node is neither a shadowroot nor a slot then assigning slottables
        // for it won't have any effect, so we take a fast path out.
        // In the case of node removal, we need to force re-assignment of slottables
        // even if the node is not a shadow root or slot, this allows us to clear assigned
        // slots from any slottables that were assigned to slots in the removed subtree.
        let is_shadow_root_with_slots = self
            .downcast::<ShadowRoot>()
            .is_some_and(|shadow_root| shadow_root.has_slot_descendants());
        if !is_shadow_root_with_slots &&
            !self.is::<HTMLSlotElement>() &&
            matches!(force, ForceSlottableNodeReconciliation::Skip)
        {
            return;
        }

        // > To assign slottables for a tree, given a node root, run assign slottables for each slot
        // > slot in root’s inclusive descendants, in tree order.
        for node in self.traverse_preorder(ShadowIncluding::No) {
            if let Some(slot) = node.downcast::<HTMLSlotElement>() {