【问题标题】:Allow select text on a HTML 5 draggable child element允许在 HTML 5 可拖动子元素上选择文本
【发布时间】:2017-12-04 22:21:31
【问题描述】:

有一个包含可拖动行的表格,其中每一行都是draggable=true,用户如何仍然能够从列中选择文本

<table>
 <thead>..</thead>
 <tbody>
  ..
  <tr draggable="true">
   <td>..</td>
   <td>Cool text but you can't select me</td>
   <td>..</td>
  </tr>
  ..
</tbody>
</table>

另一个简单的例子 (https://codepen.io/anon/pen/qjoBXV)

div {
  padding: 20px;
  margin: 20px;
  background: #eee;
}

.all-copy p {  
  -webkit-user-select: all;  /* Chrome all / Safari all */
  -moz-user-select: all;     /* Firefox all */
  -ms-user-select: all;      /* IE 10+ */
  user-select: all;          /* Likely future */   
}    
<div class="all-copy" draggable="true">
      <p>Select me as text</p>
    </div>

【问题讨论】:

  • 不知道是不是只有Mac浏览器,不过还是可以通过右键元素选择文字。
  • 另外,我主观上认为最好有一个清晰且视觉上区分的元素来处理拖放,而不是在您还需要选择文本时允许拖动整行。可拖动区域至少需要与可选文本不同的光标。
  • 是的,不确定在 Windows 中运行的浏览器。 Mozilla 文档说按 Alt 浏览器应该允许选择文本,但从来没有奏效。同意处理程序。我只是遵循规范。

标签: html css html5-draggable


【解决方案1】:

我们需要做两件事。

  • 一件事是限制拖动事件仅在指定区域触发,例如拖动手柄。

  • 另外一点是我们只设置了content类的div上的文字可以选择。我们这样做的原因是已经设置为可拖动的元素,在哪个浏览器上会添加一个默认规则user-select: none

const itemEl = document.querySelector('.item');
const handleEl = document.querySelector('.handle');

let mouseDownEl;

itemEl.onmousedown = function(evt) {
  mouseDownEl = evt.target;
}

itemEl.ondragstart = function(evt) {
  // only the handle div can be picked up to trigger the drag event
  if (mouseDownEl.matches('.handle')) {
    // ...code
  } else {
    evt.preventDefault();
  }
}
.item {
  width: 70px;
  border: 1px solid black;
  text-align: center;
}

.content {
  border-top: 1px solid gray;
  user-select: text;
}
<div class="item" draggable="true">
  <div class='handle'>handle</div>
  <div class='content'>content</div>
</div>

【讨论】:

    【解决方案2】:

    我可以看到这项工作的唯一方法是实际检查哪个元素触发了事件

    if (e.target === this) {...}
    

    堆栈sn-p

    (function (elem2drag) {
      var x_pos = 0, y_pos = 0, x_elem = 0, y_elem = 0;  
      
      document.querySelector('#draggable').addEventListener('mousemove', function(e) {
        x_pos = e.pageX;
        y_pos = e.pageY;
        if (elem2drag !== null) {
            elem2drag.style.left = (x_pos - x_elem) + 'px';
            elem2drag.style.top = (y_pos - y_elem) + 'px';
        }  
      })
    
      document.querySelector('#draggable').addEventListener('mousedown', function(e) {
        if (e.target === this) {
          elem2drag = this;
          x_elem = x_pos - elem2drag.offsetLeft;
          y_elem = y_pos - elem2drag.offsetTop;
          return false;
        }  
      })
      
      document.querySelector('#draggable').addEventListener('mouseup', function(e) {
        elem2drag = null;
      })
    })(null);
    #draggable {
      display: inline-block;
      background: lightgray;
      padding:15px;
      cursor:move;
      position:relative;
    }
    span {
      background: white;
      line-height: 25px;
      cursor:auto;  
    }
    <div id="draggable">
      <span>Select me as text will work<br>when the mouse is over the text</span>
    </div>

    由于Firefox has issue with draggable="true",我使用了不同的拖动方式。

    【讨论】:

      猜你喜欢
      • 2012-09-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-01-23
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多