嵌套的 Ember.View dragEnter dragLeave 调用顺序错误?
Posted
技术标签:
【中文标题】嵌套的 Ember.View dragEnter dragLeave 调用顺序错误?【英文标题】:Nested Ember.View dragEnter dragLeave called in wrong order? 【发布时间】:2013-11-18 12:06:00 【问题描述】:我正在使用 html5 drag and drop api 创建日历。
我正在使用dragEnter
和dragLeave
来设置接收元素的样式并确定droppablity。
接收可放置元素有子元素,并且在拖动子元素时调用dragLeave
。这个问题知道和描述here.
我尝试的解决方案是在子级上添加dragLeave
和dragEnter
事件并将逻辑传递回父视图。
这里是代码。 http://jsbin.com/iHaNuPo/17
问题是子级上的 `dragEnter' 在父级上的 'dragLeave' 之前被调用。
这是事件的顺序。
#in from outside parent to over child
1. parent-enter
2. child-enter
3. parent-leave
#out from over child to outside parent
1. parent-enter
2. child-leave
3. parent-leave
这是一个错误吗?
任何人都知道一种 Ember'ish 方法来防止父级的 dragLeave
事件在将鼠标悬停在子级上时触发?
或者修复事件dragLeave
、dragEnter
触发顺序的方法?
我应该放弃 html5 原生拖放并使用 jquery ui draggable/droppable 吗?
编辑
根据 Woody 的回答,这是一个工作示例。
http://jsbin.com/OjAGabUj/22
【问题讨论】:
你应该放弃原生 d-n-d 吗?如果您使用具有垫片的库,它可能会确保您的兼容性。否则,无论如何它都会服从原生。 【参考方案1】:希望这可以帮助你,虽然它不是 Ember,也许你可以利用它。我有相当多的 HTML5 拖放经验,这有点令人厌烦,但如果你想要像跨窗口拖放这样酷的东西,我认为值得付出努力。
var ignoreNextLeave = false;
$("#outerDragTarget").on("dragenter", function(ev)
// not interested in dragleaves from my children...
if (ev.target !== this)
ignoreNextLeave = true;
$(this).addClass("dragover");
).on("dragleave", function(ev)
if (ignoreNextLeave)
ignoreNextLeave = false;
return;
$(this).removeClass("dragover");
);
$("#innerDragTarget").on("dragleave", function(ev)
ev.stopPropagation();
);
你可以运行它here
诀窍是取消从内部元素传播dragleaves,并注意当drag enter 在父元素上触发并且目标不是父元素时,我们将获得一个我们不感兴趣的drag Leave。不是理想,但可以考虑到您可以使用的东西。
【讨论】:
太棒了!我添加了一个实现您的方法的示例。 酷! HTML5 拖放在 IE 上有一些粗糙的边缘和不完整的支持。从 IE10 开始,事情开始有所好转,尽管仍然存在一些问题,但大多数问题都可以解决。在过去的一年里,我在工作中花了很多时间处理这些东西,所以请查看我的其他问题和答案——它们或多或少包含了我学到的所有有用的东西:) 所以简而言之,如果可以的话,我会使用 HTML5 拖放,据我所知,没有可用的拖放框架使用本机拖放。如果您想跨窗口拖放或拖入另一个应用程序,本地拖放是唯一的游戏。 是的,它有点粗糙。我只使用 webkit,所以我将坚持使用 html5。您认为事件顺序(outerEnter、innerEnter、OuterLeave)是 chrome 中的错误还是 dnd 规范的一部分?谢谢! 这是规范中的预期行为。即使它确实违反直觉并且经常出现问题:/【参考方案2】:我认为 Woody 的解决方案是正确的,但是如果您想节省几行代码并避免不得不直接摆弄子元素,您还可以使用引用计数解决方案:
$(".drop-target").on("dragenter dragleave", function (e)
var dragHoverCount = Number($(this).data("dragHoverCount")) || 0;
(e.type === "dragenter") ? dragHoverCount++ : dragHoverCount--;
$(this).data("dragHoverCount", dragHoverCount);
$(this).toggleClass("drag-hover", dragHoverCount > 0);
e.preventDefault();
);
【讨论】:
以上是关于嵌套的 Ember.View dragEnter dragLeave 调用顺序错误?的主要内容,如果未能解决你的问题,请参考以下文章
如何防止dragleave干扰嵌套dropzone元素上的dragenter事件?