AtteanX-Endpoint

 view release on metacpan or  search on metacpan

share/endpoint/www/js/select.js  view on Meta::CPAN

      }

      var range = rangeAt(from);
      if (to && to != from)
        range.setEndPoint("EndToEnd", rangeAt(to));
      range.select();
    }

    // Some hacks for storing and re-storing the selection when the editor loses and regains focus.
    select.getBookmark = function (container) {
      var from = select.cursorPos(container, true), to = select.cursorPos(container, false);
      if (from && to) return {from: from, to: to};
    };

    // Restore a stored selection.
    select.setBookmark = function(container, mark) {
      if (!mark) return;
      select.setCursorPos(container, mark.from, mark.to);
    };
  }
  // W3C model
  else {
    // Find the node right at the cursor, not one of its
    // ancestors with a suitable offset. This goes down the DOM tree
    // until a 'leaf' is reached (or is it *up* the DOM tree?).
    function innerNode(node, offset) {
      while (node.nodeType != 3 && !isBR(node)) {
        var newNode = node.childNodes[offset] || node.nextSibling;
        offset = 0;
        while (!newNode && node.parentNode) {
          node = node.parentNode;
          newNode = node.nextSibling;
        }
        node = newNode;
        if (!newNode) break;
      }
      return {node: node, offset: offset};
    }

    // Store start and end nodes, and offsets within these, and refer
    // back to the selection object from those nodes, so that this
    // object can be updated when the nodes are replaced before the
    // selection is restored.
    select.markSelection = function () {
      var selection = window.getSelection();
      if (!selection || selection.rangeCount == 0)
        return (currentSelection = null);
      var range = selection.getRangeAt(0);

      currentSelection = {
        start: innerNode(range.startContainer, range.startOffset),
        end: innerNode(range.endContainer, range.endOffset),
        changed: false
      };
    };

    select.selectMarked = function () {
      var cs = currentSelection;
      // on webkit-based browsers, it is apparently possible that the
      // selection gets reset even when a node that is not one of the
      // endpoints get messed with. the most common situation where
      // this occurs is when a selection is deleted or overwitten. we
      // check for that here.
      function focusIssue() {
        if (cs.start.node == cs.end.node && cs.start.offset == cs.end.offset) {
          var selection = window.getSelection();
          if (!selection || selection.rangeCount == 0) return true;
          var range = selection.getRangeAt(0), point = innerNode(range.startContainer, range.startOffset);
          return cs.start.node != point.node || cs.start.offset != point.offset;
        }
      }
      if (!cs || !(cs.changed || (webkit && focusIssue()))) return;
      var range = document.createRange();

      function setPoint(point, which) {
        if (point.node) {
          // Some magic to generalize the setting of the start and end
          // of a range.
          if (point.offset == 0)
            range["set" + which + "Before"](point.node);
          else
            range["set" + which](point.node, point.offset);
        }
        else {
          range.setStartAfter(document.body.lastChild || document.body);
        }
      }

      setPoint(cs.end, "End");
      setPoint(cs.start, "Start");
      selectRange(range);
    };

    // Helper for selecting a range object.
    function selectRange(range) {
      var selection = window.getSelection();
      if (!selection) return;
      selection.removeAllRanges();
      selection.addRange(range);
    }
    function selectionRange() {
      var selection = window.getSelection();
      if (!selection || selection.rangeCount == 0)
        return false;
      else
        return selection.getRangeAt(0);
    }

    // Finding the top-level node at the cursor in the W3C is, as you
    // can see, quite an involved process.
    select.selectionTopNode = function(container, start) {
      var range = selectionRange();
      if (!range) return false;

      var node = start ? range.startContainer : range.endContainer;
      var offset = start ? range.startOffset : range.endOffset;
      // Work around (yet another) bug in Opera's selection model.
      if (window.opera && !start && range.endContainer == container && range.endOffset == range.startOffset + 1 &&
          container.childNodes[range.startOffset] && isBR(container.childNodes[range.startOffset]))
        offset--;



( run in 0.617 second using v1.01-cache-2.11-cpan-98e64b0badf )