38

如果在另一个问题中回答了这个问题,我深表歉意,我找不到特定于我的问题的答案!

我正在尝试测试是否将 jQuery 可拖动对象放置在合法可放置对象之外。这通常可以通过恢复可拖动对象在 90% 的时间内解决,但我不想这样做。相反,如果将可拖动对象拖放到可拖放对象上(工作得很好!),我想做一件事,如果将其拖放到所有可能的可拖放对象之外(目前让我变得更好!),我想做另一件事。

简而言之:

jQuery('#droppable').droppable(
{
    accept: '#draggable',
    drop: function(event, ui)
    {
        // awesome code that works and handles successful drops...
    }
});

jQuery('#draggable').draggable(
{
    revert: false,
    stop: function()
    {
        // need some way to check to see if this draggable has been dropped
        // successfully or not on an appropriate droppable...
        // I wish I could comment out my headache here like this too...
    }
});

我觉得我错过了一些非常明显的东西......在此先感谢您的帮助!

4

6 回答 6

56

因为 droppable 的 drop 事件在可拖动的 stop 事件之前触发,所以我认为您可以在 drop 事件中拖动的元素上设置一个标志,如下所示:

jQuery('#droppable').droppable(
{
    accept: '#draggable',
    drop: function(event, ui)
    {
        ui.helper.data('dropped', true);
        // awesome code that works and handles successful drops...
    }
});

jQuery('#draggable').draggable(
{
    revert: false,
    start: function(event, ui) {
        ui.helper.data('dropped', false);
    },
    stop: function(event, ui)
    {
        alert('stop: dropped=' + ui.helper.data('dropped'));
        // Check value of ui.helper.data('dropped') and handle accordingly...
    }
});
于 2011-11-11T11:37:06.687 回答
9

我看到你已经得到了答案;无论如何,我今天遇到了同样的问题,我以这种方式解决了它:

var outside = 0;

// this one control if the draggable is outside the droppable area
$('#droppable').droppable({
    accept      : '.draggable',
    out         : function(){
        outside = 1;
    },
    over        : function(){
        outside = 0;
    }
});

// this one control if the draggable is dropped
$('body').droppable({
    accept      : '.draggable',
    drop        : function(event, ui){
        if(outside == 1){
            alert('Dropped outside!');
        }else{
            alert('Dropped inside!');
        }
    }
});

我需要它,因为我无法更改我的 Draggables 的选项,所以我只能使用 droppables(我需要它在很棒的FullCalendar插件中)。我想使用 droppables 的“贪婪”选项可能会出现一些问题,但在大多数情况下它应该可以工作。

PS:对不起我的英语不好。

编辑:按照建议,我使用 jQuery.data 创建了版本;可以在这里找到:jsfiddle.net/Polmonite/WZma9/

无论如何 jQuery.data 文档说:

请注意,此方法当前不为在 XML 文档上设置数据提供跨平台支持,因为 Internet Explorer 不允许通过 expando 属性附加数据。

(意味着它在 8 之前的 IE 上不起作用)

编辑 2:正如@Darin Peterson 所指出的,前面的代码不适用于多个放置区域;这应该解决这个问题:http: //jsfiddle.net/Polmonite/XJCmM/

编辑 3:编辑 2 中的示例有一个错误。如果我拖动“拖动我!” 到底部的d​​roppable,然后将“Drag me too”放到上面的droppable,然后将“Drag me too”放到外面,它会提醒“Dropped inside!” 所以,不要使用它。

编辑 4:正如@Aleksey Gor 所指出的,编辑 2 中的示例是错误的;实际上,它更像是一个示例来解释如何循环遍历所有可拖动/可拖放的,但我实际上忘记删除警报消息,所以它非常混乱。这里是更新的小提琴。

于 2012-10-23T17:04:57.007 回答
4

尝试使用可放置元素的“out”事件。

这是文档

“当一个已接受的可拖动对象被拖出(在其容差范围内)此可放置对象时,将触发此事件。” 如果我是对的,这就是你需要的。

也可以在整个页面上创建一个元素覆盖。如果元素被丢弃在那里,您将触发您的事件。不是最好的,但我认为这是唯一的方法。因为您需要一些其他“可放置”项目来触发这些事件。

于 2011-11-11T11:04:52.790 回答
1

以下示例的优点是您无需更改或了解可放置代码:

可拖动的还原属性可以具有函数(值){}。一个值作为参数传递,指示帮助器是否被拖放到元素上(放置元素),如果没有被拖放到元素上(放在外面或不被接受),则为“假”。

注意:您需要从该恢复函数返回正确的布尔值,以便告诉助手是否恢复(真/假)。True 意味着是的,通过以慢动作(开箱即用)将助手移回其原始位置。False 表示不,只是突然删除助手。将 revert 属性设置为“无效”,是一种说法

  • '是的,如果掉到外面,然后恢复助手'
  • “不,如果放在可放置元素上并被接受,则立即杀死助手”。

我的猜测是,您可以在启动事件期间将当前的 ui 助手添加到具有数据属性的可拖动容器中。然后从 data 属性的 revert 函数中选择它。然后向助手添加一个属性,指示它是否被删除。然后最终在停止事件中,检查这个数据属性值,然后做你想做的事情。

可拖动的事件/函数调用顺序:开始-恢复-停止

这可能是一个例子:

jQuery('#draggable').draggable(
{
    start: function(event, ui) {
        $(this).data('uihelper', ui.helper);
    },
    revert: function(value){
        var uiHelper = (this).data('uihelper');
        uiHelper.data('dropped', value !== false);
        if(value === false){
             return true;
        }
        return false;
    },
    stop: function(event, ui)
    {
        if(ui.helper.data('dropped') === true){
            // handle accordingly...
        }
    }
});

您甚至可以在还原函数中返回 true,而只是在停止事件期间删​​除助手,这取决于 ui.helper.remove() 中的 data('dropped') 值。或者,如果你的日子还不好过,你甚至可以用 CSS3 来爆炸它;)

于 2016-07-07T13:30:19.390 回答
0

我添加了我采用的解决方案,因为您可以从您正在移动的对象的 css 类中轻松理解这一点:

jQuery('#draggable').draggable({
  stop: function(event, ui) {
    if (ui.helper.hasClass('ui-draggable-dragging')) {
      console.log('dropped out');
    } else {
      console.log('dropped successfully');
    }
  }
});
于 2018-06-07T12:26:29.313 回答
0

老问题和老答案意味着这个“可能”是一个新的解决方案。正如问题所述,您(也许)还想知道是否将可拖动对象放置在可放置对象之外。对我来说,在至少 95% 的情况下,我真的不在乎是否,我只想让事情回到原来的样子,而不会在发生这种情况时做出任何改变。

设置revert为字符串invalid即可完成所需的行为,而无需任何额外的代码或时髦的事情要做。

$( '#draggable' ).draggable({
    revert: "invalid",
    stop: function( event, ui )
    {
       // whatever
    }
});

同样,它不会告诉您“它是否被丢弃在可放置对象之外”,但如果发生这种情况,它将恢复到初始状态。

于 2019-07-25T21:40:33.347 回答