【问题标题】:jQuery Draggable + Sortable - How to reject a drop into the sort?jQuery Draggable + Sortable - 如何拒绝放入排序?
【发布时间】:2011-10-30 19:04:39
【问题描述】:

我有一个可排序的视频列表和一组可拖动的视频。基本上我想确保拖入的视频不在视频的前 5 分钟。由于视频长度不同,我想在 drop 上进行测试 - 将时间加起来,如果不是 5 分钟,则恢复并显示错误。

我已经尝试连接到所有可拖动和可排序的回调(包括未记录的还原回调)来进行测试,但无论我尝试什么,dom 总是会发生变化(并且可排序调用它的更新回调)...

有人有什么建议吗?

【问题讨论】:

    标签: jquery-ui draggable jquery-ui-sortable revert


    【解决方案1】:

    您可以通过调用draggable 小部件的cancel 方法来恢复拖动操作(该方法未记录在案,但其名称不以下划线开头,这可以说使其“更安全”以可靠地使用)。不过,它仅在 start 事件期间有效,因为其他事件发生得太晚而无法触发还原动画。

    但是,sortable 小部件即使取消拖动操作仍然会注册一个放置,因此您还必须删除新添加的项目(在stop 事件期间,因为start 事件也会发生早):

    $("#yourSortable").sortable({
        start: function(event, ui) {
            if (!canDropThatVideo(ui.item)) {
                ui.sender.draggable("cancel");
            }
        },
        stop: function(event, ui) {
            if (!canDropThatVideo(ui.item)) {
                ui.item.remove();
                // Show an error...
            }
        }
    });
    

    您可以在this fiddle 中查看结果(第四项将始终还原)。

    更新:正如 John Kurlak 在 cmets 中正确指出的那样,该项目不会因为调用 draggable("cancel") 而恢复,而是因为在我们的例子中 ui.sendernull。投掷任何东西都会导致相同的行为。

    唉,我尝试的所有其他组合都导致项目在没有动画发生的情况下被还原,所以也许我们最好的选择是避免访问ui.sender,而是写如下内容:

    start: function(event, ui) {
        if (!canDropThatVideo(ui.item)) {
            throw "cancel";
        }
    }
    

    不过,未捕获的异常仍会出现在控制台中。

    【讨论】:

    • 您好,谢谢您的回答!我正在努力让它工作 - 测试(canDropThatVideo)需要找到它被丢弃在列表中的位置,以便它可以与相邻的视频进行比较。我尝试了类似的方法: // 获取相邻的 vids var nextVid = $(ui.item).next(); var prevVid = $(ui.item).prev();但这些似乎没有得到正确的 - 可能是因为它在开始事件中......应该工作吗?
    • @user612911,它更复杂,但它可以工作。您必须绑定到sort 事件而不是start 并分别使用ui.placeholder.next()ui.placeholder.prev()。您可能还必须以某种方式记住您对该项目做出的决定(可能使用data()),以便stop 处理程序知道要做什么。 (顺便说一句,您不需要在 ui 成员上调用 $():它们已经是 jQuery 对象。)
    • 太好了,我现在运行良好。我还在可拖动的start 事件中附加了一些逻辑,以将一些“cantDropHere”类添加到无效放置空间的元素中,然后从可排序中排除这些类。谢谢!
    • ui.sender 在您的代码示例和 JSFiddle 中似乎为空...我认为当元素来自可拖动而不是另一个可排序时它为空。
    • @FrédéricHamidi 它有效,但仍然抛出错误。我认为当发生错误时,可拖动事件会取消事件(或者某些代码不会执行以允许放置它)。我会检查 jQuery 源代码。您可以轻松地将ui.sender.draggable("cancel"); 替换为blah,它仍然有效。
    【解决方案2】:

    我找到了另一种方式。如果你不介意让它的动画飘回原来的位置,你可以随时使用它

    .droppable({
        drop: function (event, ui) {
    
            var canDrop = false;
    
            //if you need more calculations for
            //validation, like me, put them here
    
            if (/*your validation here*/)
                canDrop = true;
    
            if (!canDrop) {
                ui.draggable.remove();
            }
            else{
                //you can put whatever else you need here
                //in case you needed the drop anyway
            }
        }
    }).sortable({
        //your choice of sortable options
    });
    

    我使用这个是因为我需要 drop 事件。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-01-14
      • 1970-01-01
      • 2011-09-18
      • 1970-01-01
      • 1970-01-01
      • 2011-05-05
      • 2011-07-26
      • 1970-01-01
      相关资源
      最近更新 更多