如何基于异步请求结果配置jQuery Droppable拖放权限?
解决自定义拖放目标的问题
我来帮你搞定这个拖放规则配置的问题!首先得修正一个关键小问题——你的HTML里有多个id="other",ID是页面元素的唯一标识,绝对不能重复,所以先把这些重复的ID改成class="other",这样我们才能正确选中目标元素。
第一步:修正HTML结构
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <script src="https://code.jquery.com/ui/1.12.0/jquery-ui.min.js" integrity="sha256-eGE6blurk5sHj+rmkfsGYeKyZx3M4bG+ZlFyA7Kns7E=" crossorigin="anonymous"></script> <div id="drag" class="ui-widget-content">drag me</div> <div id="drag2" class="ui-widget-content">drag me2</div> <div id="container"> <div id="floor">foo</div> <div class="other">bar</div> <div class="other">1</div> <div class="other">2</div> </div>
第二步:结合异步请求配置拖放规则
核心思路是利用jQuery UI的droppable的accept选项,精确指定每个拖拽元素可以放入的目标。我们在异步请求返回结果后,动态配置这些规则:
// 封装拖放配置逻辑,传入拖拽元素的ID function setupDragDrop(dragElementId) { $.getJSON("/Tickets/ChangeCardLane", { id: dragElementId }, function (cr) { // 先销毁之前的拖放实例,避免重复绑定导致冲突 $('.ui-droppable').droppable('destroy'); $('.ui-draggable').draggable('destroy'); // 初始化所有拖拽元素的基础配置 $('#drag, #drag2').draggable({ revert: 'invalid', stop: function() { alert("revert invalid: "+$(this).attr('id')); $(this).draggable('option','revert','invalid'); } }); // 根据异步返回结果配置可放置目标 if (cr == null) { // 允许拖放的场景,按拖拽元素ID设置不同规则 if (dragElementId === 'drag') { // drag可以放入#floor(显示foo)和内容为"1"的div $('#floor, .other:contains("1")').droppable({ tolerance: 'fit', accept: '#drag' // 只接受id为drag的拖拽元素 }); } else if (dragElementId === 'drag2') { // drag2仅可放入内容为"1"的div $('.other:contains("1")').droppable({ tolerance: 'fit', accept: '#drag2' // 只接受id为drag2的拖拽元素 }); } } else { // 禁止拖放的场景,不配置任何可放置目标,拖拽元素会自动返回原位置 console.log(`元素${dragElementId}暂时禁止拖放`); } }); } // 绑定触发逻辑:比如鼠标按下拖拽元素时请求配置 $('#drag, #drag2').on('mousedown', function() { setupDragDrop($(this).attr('id')); });
关键细节说明
accept选项:这是控制拖放权限的核心,它可以是选择器字符串,也可以是返回布尔值的函数,用来精确筛选允许放入的拖拽元素。:contains()选择器:用来快速选中内容为"1"的div,注意这个选择器是大小写敏感的,如果需要不区分大小写,可以自定义筛选逻辑。- 异步后的重置操作:每次请求后销毁旧的拖放实例,避免重复绑定导致的规则冲突。
revert: 'invalid':当拖拽元素放到不允许的目标上时,会自动返回原位置,完美匹配你的需求。
如果需要更灵活的动态规则切换,也可以提前初始化所有可能的放置目标,再通过异步结果动态更新accept规则:
// 提前初始化所有潜在放置目标 $('#floor, .other').droppable({ tolerance: 'fit', accept: function(draggable) { const dragId = draggable.attr('id'); const targetText = $(this).text().trim(); // 这里可以根据异步返回的全局规则动态判断 if (dragId === 'drag') { return $(this).is('#floor') || targetText === '1'; } else if (dragId === 'drag2') { return targetText === '1'; } return false; } }); // 异步请求后刷新规则 $.getJSON("/Tickets/ChangeCardLane", { id: data }, function (cr) { // 根据cr结果更新全局规则后,刷新droppable实例 $('#floor, .other').droppable('refresh'); });
内容的提问来源于stack exchange,提问作者Rilcon42
相关产品推荐
相关产品推荐

