我尝试“绝对化”先前相对的DOM元素,每次我尝试时,都会发生“跳跃”,我只是不知道我做错了什么或者如何解决这个问题。
好的,可以在http://jsfiddle.net/rhqy3/3/ 找到JS_fidle这是虚拟HTML
<html>
<body>
<br><br><h1>one</h1><br><br><br><br>
<h2>two</h2>
</body>
</html>
这是javascript(使用jquery)
jQuery.fn.absolutize = function()
{
return this.each(function()
{
var element = jQuery(this);
if (element.css('position') == 'absolute')
{
return element;
}
alert('now a jump happens, that should not happen')
element.css("position", "absolute");
element.css(element.offset());
return element;
});
}
$(document).ready(function() {
window.setTimeout(function(){$("h1, h2").absolutize()}, 2000)
});
好吧,好吧,两秒后,当我想将元素设置为它们的绝对等值时,有一个......跳跃?!?我不知道为什么。我尝试$(element).position()
代替offset()
,但没有成功。
更新:澄清 - h1保持原样,h2进行跳转。我测试了google chrome最新版本,firefox最新版本是mac os x lion。
我的目标是将元素(与绝对的jquery插件竞争)设置为真正的(不跳跃)等效的css绝对位置,怎么做? thx,我真的很感激,感谢你的时间。
更新2 :heureka,我发现了问题(仍然缺少解决方案)!问题: DOM太快。这个脚本做了什么:它获取h1元素,说:从相对上下文(正常渲染流程)中取出并将其设置为“绝对”,此时浏览器重排发生 - 因为H1不再在那里,一切都向上移动。发生了跳跃。这太快了,我们没有看到它。现在jquery函数进入h2并说“绝对”但是在这一刻h2元素已经具有“新的”相对定位,跳跃确实已经发生了。这不是每个人都看到它的原因,这是一个竞赛条件。如果浏览器要慢速触发重排,DOM仍然保留旧值。好 ,该怎么做:我们必须收集所有元素的位置值(将它们保存在某处),然后,在收集所有位置值后,我们将一个元素一个接一个地更新。不太确定如何在jquery插件的上下文中执行此操作,但我会接受它(今晚,现在重新开始工作)。
更新3 :下面的答案是这个问题的正确答案。多谢。这个问题没有解决的一件事(因为我没有要求)是一个问题,其他元素,可能取决于相对定位的元素然后做一些回流舞蹈(因为突然绝对化的元素失踪),这小jquery插件解决了这个https://gist.github.com/4051578,它是一个名为jquery.bodysnatch.js的jquery插件,因为它的目的是“用自己的绝对定位克隆替换元素的jquery插件,同时隐藏和沉默原件”很有趣。 / p>
答案 0 :(得分:3)
你走了!
(function($){
$.fn.absolutize = function() {
var elems = [];
this.each(function() {
var element = $(this);
if (element.css('position') == 'absolute') return;
var offset = element.offset();
elems.push({
el: element,
newRules: {
position: 'absolute',
top: offset.top,
left: offset.left
}
});
});
$.each(elems, function(i, obj){
obj.el.css( obj.newRules );
});
};
$(document).ready(function() {
window.setTimeout(function(){
$("h1, h2").absolutize()
}, 2000);
});
})(jQuery);
问题在于,它是通过每个传递给absolutize()的元素一次一个,获取偏移量并应用它。当它要求h2的偏移时,h1已经从文档流中移除。
可能有一种更好的方法来编码,但想法是,在更改每个位置之前缓存元素的偏移量。
答案 1 :(得分:0)
absolute
:element.css(element.offset());
element.css("position", "absolute");
答案 2 :(得分:0)
试试这个:
jQuery.fn.absolutize = function(){
return this.each(function(){
var element = $(this);
element.css("top",element.position().top);
element.css("left",element.position().left);
//alert(element.position().top);
element.css("position", "absolute");
if (element.css('position') == 'absolute'){
return element;
}
});
}
$(document).ready(function() {
window.setTimeout(function(){$("h1, h2").absolutize()}, 2000)
});