github.com/tilt-dev/tilt@v0.33.15-0.20240515162809-0a22ed45d8a0/web/src/selection.ts (about)

     1  function allNodes(selection: Selection): Node[] {
     2    let result = []
     3    for (let i = 0; i < selection.rangeCount; i++) {
     4      let range = selection.getRangeAt(i)
     5      let start = range?.startContainer
     6      let end = range?.endContainer
     7      if (start) {
     8        result.push(start)
     9      }
    10      if (end) {
    11        result.push(end)
    12      }
    13    }
    14    return result
    15  }
    16  
    17  // When you have unselectable elements in your selection,
    18  // Firefox represents this as a series of small ranges.
    19  //
    20  // This code doesn't need to be efficient so we just look at all
    21  // the ranges and get the earliest node in document-space.
    22  function startNode(selection: Selection): Node | null {
    23    let startNode = selection.focusNode
    24    allNodes(selection).forEach((candidate) => {
    25      if (startNode == null) return
    26      if (
    27        startNode?.compareDocumentPosition(candidate) &
    28        Node.DOCUMENT_POSITION_PRECEDING
    29      ) {
    30        startNode = candidate
    31      }
    32    })
    33    return startNode
    34  }
    35  
    36  // When you have unselectable elements in your selection,
    37  // Firefox represents this as a series of small ranges.
    38  //
    39  // This code doesn't need to be efficient so we just look at all
    40  // the ranges and get the last node in document-space.
    41  function endNode(selection: Selection): Node | null {
    42    let endNode = selection.focusNode
    43    allNodes(selection).forEach((candidate) => {
    44      if (endNode == null) return
    45      if (
    46        candidate.compareDocumentPosition(endNode) &
    47        Node.DOCUMENT_POSITION_PRECEDING
    48      ) {
    49        endNode = candidate
    50      }
    51    })
    52    return endNode
    53  }
    54  
    55  export default { startNode, endNode }