我正在尝试在缓慢的用户界面中修复一些效果不佳的javascript,并且我将主要原因缩小为jQuery .width()
调用,用于查看{{1}的实际像素大小响应式布局中的元素,在需要经常响应用户操作的过程中。
我添加了基于时间戳的测量结果,他们发现它仅占滞后时间的33%左右,这使得用户界面感觉锐利且用户界面感觉迟钝之间存在差异。删除这一行,用户界面感觉很快 - 但是,它把事情放错了地方......
似乎well established that .width()
is relatively slow in jQuery > 1.8主要有两个原因:
It forces reflow while calculating the element size。来自When does reflow happen in a DOM environment?引用的文章:
[当您检索必须计算的度量时发生回流,例如访问offsetWidth,clientHeight或任何计算的CSS值(通过DOM兼容浏览器中的getComputedStyle()或IE中的currentStyle)
...实际上,对于像IE和Firefox这样的浏览器,为了避免相互矛盾的变化(例如在同一个函数调用中隐藏和显示),将DOM更改延迟到最后一刻,people sometimes add unnecessary state getters in order to force reflow to occur。
还需要检查元素的边框状态。 From their blog:
jQuery 1.8现在需要在使用.width()时检查box-sizing属性,以便它可以决定是否需要减去填充和边框宽度。这可能是昂贵的 - 在Chrome上高达100倍!
我的代码width: 100%
调用的目的是查看响应式设计是否缩减以及缩小了多少。它需要查看一个widget的包装元素,它有width()
(但可能在列或其他容器中,具体取决于它所在的站点/页面),并且需要查看该包装器的最大宽度%实际上正在展示。
基于不同坐标系统的其他代码为我提供了标签的位置(以像素为单位),然后我需要使用缩放系数(基本上为width: 100%;
)来缩小位置,以便例如,如果在狭窄的窗口/设备中查看页面并且包装器是其最大大小的50%,则标签的顶部和左侧偏移量是其默认值的50%。
有什么办法可以访问这些数据,了解%-width元素在不引起重排的情况下缩小了多少以及其他使= $wrapper.width() / maxWidth;
调用变慢的事情?
我尝试或排除过的事情:
.width()
与.outerWidth()
.width()
(纯Javascript /非Jquery选项)也几乎和.get(0).clientWidth
一样慢(据推测,它是重新流动的罪魁祸首).width()
后跟.get(0).clientWidth
),那么第一次调用之后非常快(约20倍)。大概是因为刚刚完成了重排并且刚刚访问了元素属性,所以它们以某种方式被缓存。但是效果不适用于重复调用函数,仅在一个函数调用中。 .outerHeight()
显然没用,因为它只会在所有情况下给我.css("width")
[ 更新 ]我想到我找到了一种绕过我解决问题的方法的方法,并且无需访问我的标签元素的缩放:因为我已经有像素的100%
变量和像素的偏移量,所以我有足够的数据来计算maxWidth
标签的百分比偏移量和leftOffset_px / maxWidth_px
,然后topOffset_px / maxHeight_px
并将 作为每个标签的CSS + '%'
和top
偏移量。这是荒谬更快 - 现在不到1毫秒,所以我的基于时间戳的功能很快就无法测量它!
不幸的是,我还有另一个功能,它检查具有固定宽度的标签是否不会溢出响应容器,为此,我做需要考虑到容器的当前像素宽度或其比例因子。
答案 0 :(得分:1)
不确定改进的程度有多大,但您可以尝试在窗口小部件的根目录中添加一个不包含子项的绝对定位元素,其唯一目的是读取其宽度。我认为绝对定位的元素只能让它的孩子重生:
.root {
position: relative;
}
.ruler {
position: absolute;
width: 100%;
}
_
<div class="root>
...
<div class="ruler"></div>
</div>
-
var updatedWidth = $('.ruler').width()
(虽然我同意评论说你应该尝试用CSS解决)