【问题标题】:Insert HTML after a selection在选择后插入 HTML
【发布时间】:2012-01-18 08:31:31
【问题描述】:

我希望能够双击以选择 div 中的一些文本,然后触发一个 JavaScript 函数,该函数在所选文本之后插入一些 HTML,很像 Google Wave 中的“编辑/回复”功能。

我已经确定了如何在双击时触发功能,它正在定位选择并随后在其后插入 HTML,这就是问题所在。

【问题讨论】:

    标签: javascript dom


    【解决方案1】:

    以下函数将在所有主流浏览器的选择末尾插入一个 DOM 节点(元素或文本节点)(请注意,Firefox 现在默认允许多选;以下仅使用第一个选择):

    function insertNodeAfterSelection(node) {
        var sel, range, html;
        if (window.getSelection) {
            sel = window.getSelection();
            if (sel.getRangeAt && sel.rangeCount) {
                range = sel.getRangeAt(0);
                range.collapse(false);
                range.insertNode(node);
            }
        } else if (document.selection && document.selection.createRange) {
            range = document.selection.createRange();
            range.collapse(false);
            html = (node.nodeType == 3) ? node.data : node.outerHTML;
            range.pasteHTML(html);
        }
    }
    

    如果您更愿意插入 HTML 字符串:

    function insertHtmlAfterSelection(html) {
        var sel, range, node;
        if (window.getSelection) {
            sel = window.getSelection();
            if (sel.getRangeAt && sel.rangeCount) {
                range = window.getSelection().getRangeAt(0);
                range.collapse(false);
    
                // Range.createContextualFragment() would be useful here but is
                // non-standard and not supported in all browsers (IE9, for one)
                var el = document.createElement("div");
                el.innerHTML = html;
                var frag = document.createDocumentFragment(), node, lastNode;
                while ( (node = el.firstChild) ) {
                    lastNode = frag.appendChild(node);
                }
                range.insertNode(frag);
            }
        } else if (document.selection && document.selection.createRange) {
            range = document.selection.createRange();
            range.collapse(false);
            range.pasteHTML(html);
        }
    }
    

    2012 年 1 月 18 日更新

    最后,这是一个插入 HTML 并保留选择的版本(即扩展选择以包括最初选择的内容和插入的内容)。

    现场演示:http://jsfiddle.net/timdown/JPb75/1/

    代码:

    function insertHtmlAfterSelection(html) {
        var sel, range, expandedSelRange, node;
        if (window.getSelection) {
            sel = window.getSelection();
            if (sel.getRangeAt && sel.rangeCount) {
                range = window.getSelection().getRangeAt(0);
                expandedSelRange = range.cloneRange();
                range.collapse(false);
    
                // Range.createContextualFragment() would be useful here but is
                // non-standard and not supported in all browsers (IE9, for one)
                var el = document.createElement("div");
                el.innerHTML = html;
                var frag = document.createDocumentFragment(), node, lastNode;
                while ( (node = el.firstChild) ) {
                    lastNode = frag.appendChild(node);
                }
                range.insertNode(frag);
    
                // Preserve the selection
                if (lastNode) {
                    expandedSelRange.setEndAfter(lastNode);
                    sel.removeAllRanges();
                    sel.addRange(expandedSelRange);
                }
            }
        } else if (document.selection && document.selection.createRange) {
            range = document.selection.createRange();
            expandedSelRange = range.duplicate();
            range.collapse(false);
            range.pasteHTML(html);
            expandedSelRange.setEndPoint("EndToEnd", range);
            expandedSelRange.select();
        }
    }
    

    【讨论】:

    • 谢谢。我试试看。
    • 插入html后是否可以保留选择?现在我插入了 html,但是选择丢失了。
    • @Towa:如何保存?您的意思是选择扩展以包含插入的内容吗?我会假设并发布修订版...
    • 你有没有机会帮助这个蒂姆? stackoverflow.com/questions/24935573/…
    【解决方案2】:

    window.getSelection() 将为您获取选定的文本 (Documentation)。 您可以使用 jQuery.after() (Documentation) 在元素后插入新的 html。

    在您选择的文本函数调用中,您必须遍历所有 DOM 元素,检查它们的 x&y 位置到当前光标位置 - 获取最近的元素并在之后插入或使用函数 .elementFromPoint(x,y) (@987654323 @)

    这是我目前能想到的最好方法。它并不完美,但它是一个开始的地方。

    【讨论】:

    • 你首先是如何获得坐标的?因为window.getSelection() 不返回任何 x,y 坐标
    【解决方案3】:

    我不知道这是否可能,但我认为是部分解决方案。

    在您的双击事件中,您可以获得event object and access the property target

    拥有目标元素you can get the selected text

    现在获取目标元素 html 并找到所选文本的索引及其长度,将您的 html 注入到 index + length 位置。

    我想你已经看到了这个问题,它可以匹配多个地方的文本。要解决它,您可能必须找到光标的位置并与元素进行比较,我不知道该怎么做...

    希望我能帮上点忙。

    【讨论】:

      猜你喜欢
      • 2014-10-17
      • 2018-06-03
      • 2018-03-20
      • 2016-09-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-01-04
      • 2016-03-31
      相关资源
      最近更新 更多