单击鼠标选择所有 DIV 文本

Posted

技术标签:

【中文标题】单击鼠标选择所有 DIV 文本【英文标题】:Select all DIV text with single mouse click 【发布时间】:2010-11-13 11:28:17 【问题描述】:

当用户单击 DIV 时如何突出显示/选择 DIV 标记的内容...其想法是突出显示/选择所有文本,因此用户无需手动突出显示文本鼠标并可能错过一些文本?

例如,假设我们有一个如下的 DIV:

<div id="selectable">http://example.com/page.htm</div>

...当用户单击该 URL 中的任何一个时,整个 URL 文本都会突出显示,因此他们可以轻松地在浏览器中拖动选定的文本,或者通过右键单击复制完整的 URL。

谢谢!

【问题讨论】:

【参考方案1】:

function selectText(containerid) 
    if (document.selection)  // IE
        var range = document.body.createTextRange();
        range.moveToElementText(document.getElementById(containerid));
        range.select();
     else if (window.getSelection) 
        var range = document.createRange();
        range.selectNode(document.getElementById(containerid));
        window.getSelection().removeAllRanges();
        window.getSelection().addRange(range);
    
&lt;div id="selectable" onclick="selectText('selectable')"&gt;http://example.com/page.htm&lt;/div&gt;

现在您必须将 ID 作为参数传递,在这种情况下它是“可选择的”,但它更具全局性,允许您在任何地方多次使用它,而无需像 chiborg 提到的那样使用 jQuery。

【讨论】:

顺便说一句,您可以轻松地将其转换为 jQuery 单击事件处理程序,将 document.getElementById('selectable') 替换为 this。然后,您可以不显眼地将功能添加到多个元素,例如容器中的多个 div:jQuery('#selectcontainer div').click(selectText); 这适用于 Chrome、FF、Safari (Mac) 以及 Chrome 和 IE(Windows 9+、8 未测试)。但它似乎不适用于 iPad Mini (ios6) 或 iPhone 4 上的 Safari,不确定其他 iOS 或 android 根据这篇文章,对于 Opera (quirksmode.org/dom/range_intro.html),查询 if (window.getSelection) 应该排在第一位 这个解决方案似乎不适用于 ie11。知道为什么吗? 在 Chrome 版本 36+ 中,这将返回错误“不支持不连续选择”。解决方法是在window.getSelection().addRange(range);前加window.getSelection().removeAllRanges();【参考方案2】:

2017 年更新:

选择节点的内容调用:

window.getSelection().selectAllChildren(
    document.getElementById(id)
);

这适用于所有现代浏览器,包括 IE9+(在标准模式下)。

可运行示例:

function select(id) 
  window.getSelection()
    .selectAllChildren(
      document.getElementById("target-div") 
    );
#outer-div   padding: 1rem; background-color: #fff0f0; 
#target-div  padding: 1rem; background-color: #f0fff0; 
button       margin: 1rem; 
<div id="outer-div">
  <div id="target-div">
    Some content for the 
    <br>Target DIV
  </div>
</div>

<button onclick="select(id);">Click to SELECT Contents of #target-div</button>

window.getSelection().addRange(range);has been deprecated以来,下面的原始答案已过时

原答案:

以上所有示例都使用:

    var range = document.createRange();
    range.selectNode( ... );

但问题在于它选择了节点本身,包括 DIV 标记等。

要根据您需要调用的 OP 问题选择节点的文本:

    range.selectNodeContents( ... )

所以完整的 sn-p 将是:

    function selectText( containerid ) 

        var node = document.getElementById( containerid );

        if ( document.selection ) 
            var range = document.body.createTextRange();
            range.moveToElementText( node  );
            range.select();
         else if ( window.getSelection ) 
            var range = document.createRange();
            range.selectNodeContents( node );
            window.getSelection().removeAllRanges();
            window.getSelection().addRange( range );
        
    

【讨论】:

你也可以使用this而不是根据ID获取元素,只要它在元素的click监听器中。 这就是你们都在寻找的答案。【参考方案3】:

有纯CSS4解决方案:

.selectable
    -webkit-touch-callout: all; /* iOS Safari */
    -webkit-user-select: all; /* Safari */
    -khtml-user-select: all; /* Konqueror HTML */
    -moz-user-select: all; /* Firefox */
    -ms-user-select: all; /* Internet Explorer/Edge */
    user-select: all; /* Chrome and Opera */


user-select 是 CSS Module Level 4 规范,目前是草案和非标准 CSS 属性,但浏览器很好地支持它 - 请参阅 #search=user-select。

.selectable
    -webkit-touch-callout: all; /* iOS Safari */
    -webkit-user-select: all; /* Safari */
    -khtml-user-select: all; /* Konqueror HTML */
    -moz-user-select: all; /* Firefox */
    -ms-user-select: all; /* Internet Explorer/Edge */
    user-select: all; /* Chrome and Opera */

<div class="selectable">
click and all this will be selected
</div>

阅读更多关于用户选择here on MDN 并使用它here in w3scools

【讨论】:

+1 非常棒的优雅解决方案! 2017 年 9 月测试,它在 FireFox 和 Chrome 上完美运行但不在 MICROSOFT EDGE 中!?任何想法为什么不以及如何解决这个问题?谢谢! Mino,谢谢这工作!一键选择整个元素。但是,它无法滑动选择文本的子集。 . . .你的意思是-webkit-touch-callout: none; 吗?我收到了all 的警告。无论如何,该设置在这里做什么? . . . @Sam 在 2020 年,我看到 user-select 在 MS Edge 上工作。理智的头脑可能占了上风。【参考方案4】:

Neuroxik 的回答真的很有帮助。我在 Chrome 上只有一个问题,因为当我点击一个外部 div 时,它不起作用。我可以在添加新范围之前删除旧范围来解决它:

function selectText(containerid) 
    if (document.selection) 
        var range = document.body.createTextRange();
        range.moveToElementText(document.getElementById(containerid));
        range.select();
     else if (window.getSelection()) 
        var range = document.createRange();
        range.selectNode(document.getElementById(containerid));
        window.getSelection().removeAllRanges();
        window.getSelection().addRange(range);
    

<div id="selectable" onclick="selectText('selectable')">http://example.com/page.htm</div>

【讨论】:

【参考方案5】:

对于内容可编辑的东西(不是常规输入,您需要使用 selectNodeContents(而不仅仅是 selectNode)。

注意:所有对“document.selection”和“createTextRange()”的引用都适用于 IE 8 及更低版本......如果你尝试做这样棘手的事情,你可能不需要支持那个怪物.

function selectElemText(elem) 

    //Create a range (a range is a like the selection but invisible)
    var range = document.createRange();

    // Select the entire contents of the element
    range.selectNodeContents(elem);

    // Don't select, just positioning caret:
    // In front 
    // range.collapse();
    // Behind:
    // range.collapse(false);

    // Get the selection object
    var selection = window.getSelection();

    // Remove any current selections
    selection.removeAllRanges();

    // Make the range you have just created the visible selection
    selection.addRange(range);


【讨论】:

【参考方案6】:

使用文本区域字段,您可以这样使用:(通过 Google)

<form name="select_all">

    <textarea name="text_area" rows="10" cols="80" 
    onClick="javascript:this.form.text_area.focus();this.form.text_area.select();">

    Text Goes Here 

    </textarea>
</form>

这就是我看到的大多数网站的做法。他们只是用 CSS 设置样式,所以它看起来不像文本区域。

【讨论】:

为什么不只是this.focus();this.select();【参考方案7】:

This snippet provides the functionality you require。您需要做的是向该 div 添加一个在其中激活 fnSelect 的事件。一个你完全不应该做并且可能不起作用的快速破解,看起来像这样:

document.getElementById("selectable").onclick(function()
    fnSelect("selectable");
);

显然假设已包含与 sn-p 的链接。

【讨论】:

【参考方案8】:

我发现将此函数包装为 jQuery 插件很有用:

$.fn.selectText = function () 
    return $(this).each(function (index, el) 
        if (document.selection) 
            var range = document.body.createTextRange();
            range.moveToElementText(el);
            range.select();
         else if (window.getSelection) 
            var range = document.createRange();
            range.selectNode(el);
            window.getSelection().addRange(range);
        
    );

所以,它变成了一个可重复使用的解决方案。然后你可以这样做:

<div onclick="$(this).selectText()">http://example.com/page.htm</div>

它会在 div 中选择 test。

【讨论】:

记得调用window.getSelection().removeAllRanges();就像 Josillo 的代码一样。另外:我主张将 window.getSelect 作为第一个选项,因为这是 HTML5 标准,而 document.selection 是 IE8 及更早版本的旧 IE 后备。【参考方案9】:

这个简单的解决方案怎么样? :)

<input style="background-color:white; border:1px white solid;" onclick="this.select();" id="selectable" value="http://example.com/page.htm">

当然它不是 div 构造,就像你提到的那样,但它仍然对我有用。

【讨论】:

简洁的解决方案,但这不考虑输入或 textarea 字段以外的元素中的文本。【参考方案10】:

尼可莱: 这个简单的解决方案怎么样? :)

`<input style="background-color:white; border:1px white solid;" onclick="this.select();" id="selectable" value="http://example.com/page.htm">`

.....

之前的代码:

<textarea rows="20" class="codearea" style="padding:5px;" readonly="readonly">

之后的代码:

<textarea rows="20" class="codearea" style="padding:5px;" readonly="readonly" onclick="this.select();" id="selectable">

仅此部分 onclick="this.select();"我的代码中的 id="selectable" 工作正常。 一键选择我的代码框中的所有内容。

感谢 Niko Lay 的帮助!

【讨论】:

【参考方案11】:

通过将 css 属性 user-select 设置为 all 可以轻松实现。像这样:

div.anyClass 
  user-select: all;

【讨论】:

【参考方案12】:
$.fn.selectText = function () 
    return $(this).each(function (index, el) 
        if (document.selection) 
            var range = document.body.createTextRange();
            range.moveToElementText(el);
            range.select();
         else if (window.getSelection) 
            var range = document.createRange();
            range.selectNode(el);
            window.getSelection().addRange(range);
        
    );

以上答案在 Chrome 中不起作用,因为 addRange 删除了以前添加的范围。除了使用 css 进行虚假选择之外,我没有找到任何解决方案。

【讨论】:

对于某人来说,这段代码可能会有所帮助,因为我已经测试并发现它在最新版本的 Chrome 中工作:$.fn.selectText = function () return $(this).each(function (index , el) if (document.selection) var range = document.body.createTextRange(); range.moveToElementText(el); range.select(); else if (window.getSelection) var range = document.createRange (); range.selectNode(el); window.getSelection().removeAllRanges(); window.getSelection().addRange(range); ); 【参考方案13】:
export const selectText = (containerId) => 
  let selection = window.getSelection()
  let myElement = document.getElementById(containerId)

  if (selection.rangeCount > 0) 
    selection.removeAllRanges()
  

  let range = document.createRange()
  range.selectNode(myElement)
  selection.addRange(range)
**The most simplest answer works in all browsers**

【讨论】:

感谢您提供此代码 sn-p,它可能会提供一些有限的即时帮助。 proper explanation 将通过展示为什么这是解决问题的好方法,并使其对有其他类似问题的未来读者更有用,从而大大提高其长期价值。请edit您的回答添加一些解释,包括您所做的假设。 请考虑解释你的答案,以便大家更好地理解。

以上是关于单击鼠标选择所有 DIV 文本的主要内容,如果未能解决你的问题,请参考以下文章

我想用键盘在 div 上选择文本(就像我们用鼠标选择文本一样)

用鼠标发送加速器以执行文本选择

鼠标点击触发鼠标离开

HTML5 用鼠标在可拖动的 div 上选择 <input> 中的文本

如何使用鼠标单击和拖动在较小的 div 中滚动大图像?

如何使用 jQuery 在单击和鼠标悬停时使可滚动的 div 滚动