鍍金池/ 問答/Linux  網(wǎng)絡(luò)安全  HTML/ 如何在一個(gè)指定的div中選中字段?

如何在一個(gè)指定的div中選中字段?

1.場(chǎng)景
打算用vue寫一個(gè)指令,并在使用指令的div中選中文字調(diào)用相應(yīng)的功能。想到一個(gè)問題,如果用戶選中文字跨越了該div,window.getSelection得到的是包含在該divtext以及div外的text,如何做個(gè)filter,提取我需要的text,但目前發(fā)現(xiàn)通過selection來查找有瓶頸,貌似走不通

  1. 歪路子解決辦法

指定該divuser-selectcss特性,除了該元素外的元素則指定其user-select: none,根本上避免了用戶選擇不規(guī)范。

問問大神們,有沒有其他方式來對(duì)選中的文本做一個(gè)篩選,提取自己想要的文本?

回答
編輯回答
爛人

Range API 很強(qiáng)大的, 有 compareBoundaryPoints 可以比較 range 的邊界,所以 filter 是走得通的。

關(guān)鍵API:

  • window.getSelection
  • selection.getRangeAt
  • document.createRange
  • range.selectNode
  • range.compareBoundaryPoints
  • range.setStart / range.setEnd

且看例子,按我理解的實(shí)現(xiàn)的一個(gè):

JSFiddle Range 操作示例

2017年8月9日 16:20
編輯回答
萢萢糖

之前沒接觸過,花了點(diǎn)時(shí)間研究下,以下例子已做備注,不明白再問:

html js:

<!DOCTYPE html>
<html lang="en">

<head>
  <title></title>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
</head>

<body>

  <div id="test">
    Click the text!
    <span>---span---</span>
    <div>換行</div>
  </div>
  <div>qwerasdfzxcv</div>
  <div>123456789</div>

  <script>
    document.getElementById('test').onmousedown = function (e) {
      document.body.onmouseup = mouseup //綁定在 body 上而不是在 id test 上,以免選擇超出的時(shí)候不響應(yīng)
    }
    function mouseup(e) {
      var selector = document.getSelection()
      var sRange = selector.getRangeAt(0)
      var sText = sRange.toString() //選擇的文字
      var newRange = document.createRange()
      newRange.setStart(selector.anchorNode, selector.anchorOffset) //從點(diǎn)擊開始
      newRange.setEndBefore(document.getElementById('test').nextSibling) //到本元素最后一個(gè)字符的 range
      var totalText = newRange.toString() //從點(diǎn)擊開始到本元素最后一個(gè)字符的文字

      if (totalText.indexOf(sText) === -1) { //選擇區(qū)域跨元素
        sText = totalText
      }

      if (sText.trim()) alert(sText)

      document.body.onmouseup = null //注銷,以免在其他 dom 節(jié)點(diǎn)也響應(yīng)事件,導(dǎo)致報(bào)錯(cuò)
    }
  </script>
</body>

</html>

vue指令的實(shí)現(xiàn):

Vue.directive('selection', {
  bind: function (el, binding, vnode) {
    el.onmousedown = function (e) {
      document.body.onmouseup = mouseup //綁定在 body 上而不是在 id test 上,以免選擇超出的時(shí)候不響應(yīng)
    }
    function mouseup() {
      var selector = document.getSelection()
      var sRange = selector.getRangeAt(0)
      var sText = sRange.toString() //選擇的文字
      var newRange = document.createRange()
      newRange.setStart(selector.anchorNode, selector.anchorOffset) //從點(diǎn)擊開始
      newRange.setEndBefore(el.nextSibling) //到本元素最后一個(gè)字符的 range
      var totalText = newRange.toString() //從點(diǎn)擊開始到本元素最后一個(gè)字符的文字

      if (totalText.indexOf(sText) === -1) { //選擇區(qū)域跨元素
        sText = totalText
      }

      if (sText.trim()) alert(sText)

      document.body.onmouseup = null //注銷,以免在其他 dom 節(jié)點(diǎn)也響應(yīng)事件,導(dǎo)致報(bào)錯(cuò)
    }
  }
})

其他拓展功能可在此基礎(chǔ)上拓展

2017年11月28日 04:17