* Returns {start, end} where `start` is the character/codepoint index of * (anchorNode, anchorOffset) within the textContent of `outerNode`, and * `end` is the index of (focusNode, focusOffset). * * Returns null if you pass in garbage input but we should probably just crash. * * Ex
(outerNode, anchorNode, anchorOffset, focusNode, focusOffset)
| 6886 | */ |
| 6887 | |
| 6888 | function getModernOffsetsFromPoints(outerNode, anchorNode, anchorOffset, focusNode, focusOffset) { |
| 6889 | var length = 0; |
| 6890 | var start = -1; |
| 6891 | var end = -1; |
| 6892 | var indexWithinAnchor = 0; |
| 6893 | var indexWithinFocus = 0; |
| 6894 | var node = outerNode; |
| 6895 | var parentNode = null; |
| 6896 | |
| 6897 | outer: while (true) { |
| 6898 | var next = null; |
| 6899 | |
| 6900 | while (true) { |
| 6901 | if (node === anchorNode && (anchorOffset === 0 || node.nodeType === TEXT_NODE)) { |
| 6902 | start = length + anchorOffset; |
| 6903 | } |
| 6904 | |
| 6905 | if (node === focusNode && (focusOffset === 0 || node.nodeType === TEXT_NODE)) { |
| 6906 | end = length + focusOffset; |
| 6907 | } |
| 6908 | |
| 6909 | if (node.nodeType === TEXT_NODE) { |
| 6910 | length += node.nodeValue.length; |
| 6911 | } |
| 6912 | |
| 6913 | if ((next = node.firstChild) === null) { |
| 6914 | break; |
| 6915 | } // Moving from `node` to its first child `next`. |
| 6916 | |
| 6917 | |
| 6918 | parentNode = node; |
| 6919 | node = next; |
| 6920 | } |
| 6921 | |
| 6922 | while (true) { |
| 6923 | if (node === outerNode) { |
| 6924 | // If `outerNode` has children, this is always the second time visiting |
| 6925 | // it. If it has no children, this is still the first loop, and the only |
| 6926 | // valid selection is anchorNode and focusNode both equal to this node |
| 6927 | // and both offsets 0, in which case we will have handled above. |
| 6928 | break outer; |
| 6929 | } |
| 6930 | |
| 6931 | if (parentNode === anchorNode && ++indexWithinAnchor === anchorOffset) { |
| 6932 | start = length; |
| 6933 | } |
| 6934 | |
| 6935 | if (parentNode === focusNode && ++indexWithinFocus === focusOffset) { |
| 6936 | end = length; |
| 6937 | } |
| 6938 | |
| 6939 | if ((next = node.nextSibling) !== null) { |
| 6940 | break; |
| 6941 | } |
| 6942 | |
| 6943 | node = parentNode; |
| 6944 | parentNode = node.parentNode; |
| 6945 | } // Moving from `node` to its next sibling `next`. |