Search code examples
javascriptcursor-positionrte

Javascript Rich Text Editor with get AND set cursor position support


Are there any javascript Rich Text Editors that support getting and setting the cursor position?


Solution

  • I won't explain the gruesome details, but this will work:

    function getTextNodesIn(node) {
      var textNodes = [];
    
      if (node.nodeType == 3) {
        textNodes.push(node);
      } else {
        var children = node.childNodes;
    
        for (var i = 0, len = children.length; i < len; ++i) {
          textNodes.push.apply(textNodes, getTextNodesIn(children[i]));
        }
      }
    
      return textNodes;
    }
    
    function setSelectionRange(el, start, end) {
      if (document.createRange && window.getSelection) {
        var range = document.createRange();
        range.selectNodeContents(el);
    
        var textNodes = getTextNodesIn(el);
        var foundStart = false;
        var charCount = 0, endCharCount;
    
        for (var i = 0, textNode; textNode = textNodes[i++]; ) {
          endCharCount = charCount + textNode.length;
    
          if (!foundStart && start >= charCount && (start < endCharCount || (start == endCharCount && i < textNodes.length))) {
            range.setStart(textNode, start - charCount);
            foundStart = true;
          }
    
          if (foundStart && end <= endCharCount) {
            range.setEnd(textNode, end - charCount);
            break;
          }
    
          charCount = endCharCount;
        }
    
        var sel = window.getSelection();
    
        sel.removeAllRanges();
        sel.addRange(range);
      } else if (document.selection && document.body.createTextRange) {
        var textRange = document.body.createTextRange();
    
        textRange.moveToElementText(el);
        textRange.collapse(true);
        textRange.moveEnd('character', end);
        textRange.moveStart('character', start);
        textRange.select();
      }
    }
    

    Now you just get your element and select stuff:

    setSelectionRange(document.getElementById('dijitEditorBody'), 10, 50);