Pārlūkot izejas kodu

LibWeb: Update `Range::set_base_and_extent()` to the latest spec text

This allows it to work with content inside shadow roots.
Tim Ledbetter 1 gadu atpakaļ
vecāks
revīzija
34741d09c6

+ 2 - 0
Tests/LibWeb/Text/expected/set-selection-inside-shadow-root.txt

@@ -0,0 +1,2 @@
+  Selection range count: 1
+Selection start offset: 0, end offset: 1

+ 21 - 0
Tests/LibWeb/Text/input/set-selection-inside-shadow-root.html

@@ -0,0 +1,21 @@
+<script src="include.js"></script>
+<div id="root"></div>
+<script>
+    function printSelectionDetails(selection) {
+        println(`Selection range count: ${selection.rangeCount}`);
+        if (selection.rangeCount > 0)
+            println(`Selection start offset: ${selection.getRangeAt(0).startOffset}, end offset: ${selection.getRangeAt(0).endOffset}`);
+    }
+
+    test(() => {
+        const rootElement = document.getElementById("root");
+        const shadowRoot = rootElement.attachShadow({ mode: "open" });
+        shadowRoot.innerHTML = "This is some text";
+        const selection = window.getSelection();
+        selection.setBaseAndExtent(shadowRoot, 0, shadowRoot, 1);
+        println(`Selection range count: ${selection.rangeCount}`);
+        println(`Selection start offset: ${selection.getRangeAt(0).startOffset}, end offset: ${selection.getRangeAt(0).endOffset}`);
+
+        shadowRoot.innerHTML = "";
+    });
+</script>

+ 2 - 5
Userland/Libraries/LibWeb/Selection/Selection.cpp

@@ -306,11 +306,8 @@ WebIDL::ExceptionOr<void> Selection::set_base_and_extent(JS::NonnullGCPtr<DOM::N
     if (focus_offset > focus_node->length())
         return WebIDL::IndexSizeError::create(realm(), "Focus offset points outside of the focus node"_fly_string);
 
-    // 2. If the roots of anchorNode or focusNode are not the document associated with this, abort these steps.
-    if (&anchor_node->root() != m_document.ptr())
-        return {};
-
-    if (&focus_node->root() != m_document.ptr())
+    // 2. If document associated with this is not a shadow-including inclusive ancestor of anchorNode or focusNode, abort these steps.
+    if (!(m_document->is_shadow_including_inclusive_ancestor_of(anchor_node) || m_document->is_shadow_including_inclusive_ancestor_of(focus_node)))
         return {};
 
     // 3. Let anchor be the boundary point (anchorNode, anchorOffset) and let focus be the boundary point (focusNode, focusOffset).