我在Firefox 3.6中有一个jQuery UI 1.7.2可排序列表的问题,IE7-8工作正常。当我向下滚动一点时,辅助元素似乎有一个与我相同高度的偏移量 从鼠标指针向下滚动,这使得无法看到您最初开始拖动的项目。 我该如何解决这个问题或解决这个问题?如果没有修复什么是一个非常好的替代可拖动插件?
以下是可排序的初始化参数。
$("#sortable").sortable( {placeholder: 'ui-state-highlight' } );
$("#sortable").disableSelection();
答案 0 :(得分:126)
如果您想阻止浏览器嗅探,那么仅CSS解决方案是将ul或容器样式设置为overflow: auto
。如果你通过firebug查看源代码,那就是jQuery在example中执行它的方式。
答案 1 :(得分:41)
使用overflow: auto;
对我来说不是一个选择。我能够使用此sort
事件处理程序解决此问题:
$(...).sortable({
...
sort: function(event, ui) {
var $target = $(event.target);
if (!/html|body/i.test($target.offsetParent()[0].tagName)) {
var top = event.pageY - $target.offsetParent().offset().top - (ui.helper.outerHeight(true) / 2);
ui.helper.css({'top' : top + 'px'});
}
},
...
});
它并不完美,但它不需要浏览器嗅探。在IE8,Chrome和Firefox中测试过。
编辑:这是使用jQuery 1.10.0和jQuery UI 1.10.3。
答案 2 :(得分:23)
我看到了这个问题,并且能够通过删除css规则位置来解决它:相对于我页面上包含的div之一。另见:http://forum.jquery.com/topic/sortable-offset-when-element-is-dragged-and-page-scrolled-down-ff
答案 3 :(得分:20)
我也遇到了这个问题并使用以下代码修复了它:
var wscrolltop = 0;
$sortable_elements.sortable({
start: function(event, ui) {
wscrolltop = $(window).scrollTop();
},
sort: function(event, ui) {
ui.helper.css({'top' : ui.position.top + wscrolltop + 'px'});
}
});
我发现,如果使用sortable-element滚动仍然存在问题。也许有人有解决方案吗?
更新: 修复是:
$sortable_elements.sortable({
connectWith: '#personal-favs ul.fitems',
sort: function(event, ui) {
ui.helper.css({'top' : ui.position.top + $(window).scrollTop() + 'px'});
}
});
但是仍然 - 如果您要离开列表,排序事件似乎就会停止。
答案 4 :(得分:9)
你还需要考虑这个特定于firefox的事实,这是我正在使用的片段 - 我从Harris的解决方案中得到了正确的指导。当sortable在相对定位的容器中时,我遇到了这个问题,没有使用帮助器。
var options = {
handle: '.mover',
update:updateSorting
};
var userAgent = navigator.userAgent.toLowerCase();
if(userAgent.match(/firefox/)) {
options["start"] = function (event, ui) { ui.item.css('margin-top', $(window).scrollTop() ); };
options["beforeStop"] = function (event, ui) { ui.item.css('margin-top', 0 ); };
}
$("#" + list_id+"").sortable(options);
$("#" + list_id+"").disableSelection();
您也可以在服务器上执行此检查,然后根据浏览器进行2次不同的呼叫。
答案 5 :(得分:7)
我设法找到了解决方法:
$( "items" ).sortable({
start: function (event, ui) {
if( ui.helper !== undefined )
ui.helper.css('position','absolute').css('margin-top', $(window).scrollTop() );
},
beforeStop: function (event, ui) {
if( ui.offset !== undefined )
ui.helper.css('margin-top', 0);
},
placeholder: 'placeholder-class'
});
基本上,你需要监听sortable的“start”事件,将浏览器的当前scrollTop()值添加到帮助者的位置,然后你需要监听sortable的“beforeStop”事件,在之前删除该偏移量。 item已正式回到新位置的列表中。
希望这对某人有帮助!
答案 6 :(得分:4)
我在我的网站上强制滚动条,因此在我的CSS中有html { overflow-y: scroll }
时会出现这种可滚动的偏移问题。
当我打开和关闭可滚动时,我使用以下内容来绕过它。我只在IE8,FF12和Chrome中测试过它......
turnSortingOnOff:function(e) {
e.preventDefault();
if (stopOrdering()) {
// get rid of the hacky css on the html element
$('html').css({ 'overflow-y': '' });
$('html').css({ 'margin-right': '' });
elmt.sortable('disable');
}
else if (startOrdering()) {
// if the body is smaller than the window
// then there aren't any scrollbars
// in which case, add a right hand margin of 16px
// to the html to prevent the site wobbling
if ($('body').outerHeight() <= $(window).height()) {
$('html').css({ 'margin-right': 16 });
}
// then override the { overflow-y: scroll }
// in the css by setting it to a nice, safe inherit
$('html').css({ 'overflow-y': 'inherit' });
elmt.sortable('enable');
}
}
显然它不是防弹的 - 如果文件大小在排序时发生变化,那么其他事情就必须完成。但是,根据我的经验,在这种情况下它看起来不那么奇怪。
答案 7 :(得分:1)
我使用更新的jQuery / jQuery UI版本“修复”了这个。
答案 8 :(得分:0)
设置overflow: auto
会使Firefox开始拖动指针下的元素,但它也会阻止自动滚动正常工作。您可以在jQuery Sortable示例中看到这一点,如果您使窗口足够小以至于需要滚动。
我在html标签上有overflow: scroll
,但即使删除它,(我认为)所有相对包含的元素也没有完全解决问题(意味着拖动正确启动并且自动滚动工作)。我还尝试了一个对_findRelativeOffset的mozilla-sniffing补丁(我认为就是这样),但它没有帮助。
我的用例的帮助只是拖动了一个克隆(helper: 'clone'
在可拖动的构造函数中)。为了使它看起来像克隆不存在,我添加了启动和停止方法,只是将visibilty设置为隐藏然后返回。
我上面会评论,但我还没有得分。
答案 9 :(得分:0)
有同样的问题。在我的情况下,它不可能使用“overflow:auto”-fix。所以这就是我所做的。
var pos_fixed = 1; // switch variable (the fix should only be fired ones)
$('.drag').draggable({
start: function(event, ui){
pos_fixed = 0; // we're about to start, set to not fixed yet
},
drag: function(event, ui){
if(pos_fixed == 0){ // check if the fix hasn't been fired for this instance yet
var help_pos = $(ui.helper).offset().top, // get helpers offset
targ_pos = $(event.target).offset().top, // get targets(the dragged elements) offset
marg = targ_pos-help_pos; // calculate the margin the helper has to have to put it on the same y-position as our target
$(ui.helper).css('margin-top', marg); // put our helper on the same y-position as the target
pos_fixed = 1; // we've fixed it, we don't want it to fire again
}
}
});
修复程序并不关心您使用的浏览器。当拖动开始时,它总是确保辅助对象具有与目标相同的y偏移量。
答案 10 :(得分:0)
对于有此问题的未来读者。 我从jqueryui 1.8升级到1.10.3,问题解决了,没有css修复。
我也从jquery 1.8升级到1.10.2
答案 11 :(得分:0)
对于未来的读者 我遇到了一个类似的问题,其中辅助元素在引导对话框的滚动div内拖动时有一个偏移量。当释放拖动的对象时,动画将拖动的辅助元素发送到它的新位置,而不考虑页面的滚动部分,这给用户带来了令人困惑的反馈。
为了使对象容器中的position:relative和overflow-y:auto保持一致,我的解决方案是
1-将scrollTop()偏移添加到sort start事件中辅助对象的margin-top;
2-删除beforeStop事件中的margin-top
这修复了动画在拖动后关闭的问题,但是当拖动页面中的滚动部分时,辅助对象被推到光标下方。最后一个修复是
3-在相对于指针和容器偏移量拖动(使用sort事件)的同时计算并设置辅助对象的top属性。
$(...).sortable({
...
start: function (event, ui) {
ui.helper.css('margin-top', $("#mybootstrap-dialog").scrollTop());
},
beforeStop: function (event, ui){
ui.helper.css('margin-top',0);
},
sort: function(event, ui) {
var top = event.clientY - $('#my-sortable-ul').offset().top - $("#mybootstrap-dialog").scrollTop();
ui.helper.css({'top' : top + 'px'});
}
},
...
});
帮助帮助
答案 12 :(得分:0)
总结您的努力并提供完整的解决方案。以下内容似乎适用于Chrome 40+和Firefox 30 +
var isFirefox = /firefox/.test(navigator.userAgent.toLowerCase());
$('#target').sortable({
connectWith: '#target-holder .elements',
handle: ".element-header",
start: function(ev, ui) {
if( isFirefox ) {
ui.item.css('margin-top', $(window).scrollTop() );
}
},
sort: function(ev, ui) {
if( isFirefox) {
ui.helper.css({'top' : ui.position.top - $(window).scrollTop() + 'px'});
} else {
ui.helper.css({'top' : ui.position.top + $(window).scrollTop() + 'px'});
}
},
beforeStop: function (ev, ui) {
if( isFirefox ) {
ui.item.css('margin-top', 0 );
}
}
});
答案 13 :(得分:-1)
我的解决方案:&#34; .sortable&#34;添加&#34;位置:relative&#34;
$(".sortable").sortable({
sort: function(event, ui) {
ui.position.top = ui.position.top + $(window).scrollTop();
},
});
PS使用jQuery UI 1.12.0和jQuery 2.2.4
答案 14 :(得分:-2)
sort: function(e, ui){
var tempVariable = $(ui.item.get(0));
tempVariable.css('top', (e.clientY)-(tempVariable.css("height").replace("px", "")));
}