7

如果在已触发的元素之外释放鼠标按钮,则不会触发Javascriptonmouseup事件。onmousedown

这会导致 JQuery UI 中的拖放错误:当鼠标按钮在其容器外释放时,JQuery可拖动元素不会停止拖动(因为元素在到达其父边界时将停止移动)。重现步骤:

  • 转到http://jqueryui.com/draggable/
  • 向下拖动可拖动对象,直到鼠标离开周围的容器
  • 释放鼠标按钮(此时没有按下鼠标按钮)
  • 将鼠标移回容器
  • 而且draggable仍在被拖动。我希望一旦我释放鼠标按钮,拖动就会停止 -无论它在哪里释放。

我在最新的 Chrome 和 IE 中看到了这种行为。

有什么解决方法吗?

我知道我们可以停止在mouseoutor上拖动容器mouseleave,但我想继续拖动,即使我在父容器之外,就像在谷歌地图中一样(无论你在哪里释放鼠标,它总是停止拖动地图)。

4

2 回答 2

4

我找到了解决方案:只需将mouseup事件处理程序附加到document。然后它总是会取消,即使您在浏览器之外释放鼠标按钮。当然,这不是一个很好的解决方案,但显然,这是让拖动正常工作的唯一方法。

尝试以下解决方案:

  • 您将看到“Drag END”总是会发生,无论您在何处释放光标。
  • 另外,为了防止在拖动时选择文本,我添加了一个unselectable

let dragging = false;
const dragEl = document.querySelector('div');
const logEl = document.querySelector('pre');

dragEl.addEventListener('mousedown touchstart', (evt) => {
  dragging = true;
  dragEl.classList.add('unselectable');
  logEl.textContent += 'drag START\n';
});
document.addEventListener('mouseup touchend', (evt) => {
  if (dragging) {
    event.preventDefault();
    dragEl.classList.remove('unselectable');
    dragging = false;
    logEl.textContent += 'drag END\n';
  }
});
div {
  background: red;
}

.unselectable {
  -webkit-user-select: none; /* Safari */        
  -moz-user-select: none; /* Firefox */
  -ms-user-select: none; /* IE10+/Edge */
  user-select: none; /* Standard */
}
<div>drag me</div>
<hr>
LOG:
<p><pre></pre></p>

于 2014-01-12T11:11:41.483 回答
2

处理此问题的最佳方法是检查 mousemove 事件处理程序中的当前按钮状态。如果按钮不再向下,请停止拖动。

如果您将 mouseup 事件放在文档上,那么您只需将问题向上移动,如果您在文档之外(甚至在浏览器窗口之外)释放按钮,原始问题仍然会出现。

例如使用 jQuery

$div.on("mousedown", function (evt) {
        dragging = true;
  }).on("mouseup", function (evt) {
        dragging = false;
  }).on("mousemove", function (evt) {
        if (dragging && evt.button == 0) {
            //Catch case where button released outside of div
            dragging = false;
        }
        if (dragging) {
          //handle dragging here
        }
  });

您可以跳过 mouseup 事件处理程序,因为它会被 mousemove 捕获,但我认为它仍然存在时更具可读性。

于 2014-12-03T16:30:38.830 回答