我有一些遗留的 javascript 可以冻结表格的 tfoot/thead 并让正文滚动,它工作正常,除了在 IE8 中它非常慢。
我将问题追溯到读取tfoot / thead中单元格的clientWidth属性......在ie6 / 7和FireFox 1.5-3中读取clientWidth属性大约需要3ms......在IE8中它需要超过200ms和更长的时间表格中的单元格数量增加了。
这是一个已知的错误 ?有什么解决方法或解决方案吗?
我有一些遗留的 javascript 可以冻结表格的 tfoot/thead 并让正文滚动,它工作正常,除了在 IE8 中它非常慢。
我将问题追溯到读取tfoot / thead中单元格的clientWidth属性......在ie6 / 7和FireFox 1.5-3中读取clientWidth属性大约需要3ms......在IE8中它需要超过200ms和更长的时间表格中的单元格数量增加了。
这是一个已知的错误 ?有什么解决方法或解决方案吗?
如果您仍然感兴趣,我已经解决了这个问题。解决方案相当复杂。基本上,您需要将一个简单的 HTC 附加到元素并缓存其 clientWidth/Height。
简单的 HTC 看起来像这样:
<component lightweight="true">
<script>
window.clientWidth2[uniqueID]=clientWidth;
window.clientHeight2[uniqueID]=clientHeight;
</script>
</component>
您需要使用 CSS 附加 HTC:
.my-table td {behavior: url(simple.htc);}
请记住,您只需要附加 IE8 的行为!
然后,您使用一些 JavaScript 为缓存的值创建 getter:
var WIDTH = "clientWidth",
HEIGHT = "clientHeight";
if (8 == document.documentMode) {
window.clientWidth2 = {};
Object.defineProperty(Element.prototype, "clientWidth2", {
get: function() {
return window.clientWidth2[this.uniqueID] || this.clientWidth;
}
});
window.clientHeight2 = {};
Object.defineProperty(Element.prototype, "clientHeight2", {
get: function() {
return window.clientHeight2[this.uniqueID] || this.clientHeight;
}
});
WIDTH = "clientWidth2";
HEIGHT = "clientHeight2";
}
请注意,我创建了常量 WIDTH/HEIGHT。您应该使用这些来获取元素的宽度/高度:
var width = element[WIDTH];
这很复杂,但它有效。我和你有同样的问题,访问 clientWidth 非常慢。这很好地解决了这个问题。它仍然没有IE7那么快,但它又恢复了可用。
我找不到任何文档证明这是一个已知错误。为了提高性能,为什么不缓存 clientWidth 属性并定期更新缓存呢?IE 如果你的代码是:
var someValue = someElement.clientWidth + somethingElse;
将其更改为:
// Note the following 3 lines use prototype
// To do this without prototype, create the function,
// create a closure out of it, and have the function
// repeatedly call itself using setTimeout() with a timeout of 1000
// milliseconds (or more/less depending on performance you need)
var updateCache = function() {
this. clientWidthCache = $('someElement').clientWidth;
};
new PeriodicalExecuter(updateCache.bind(this),1);
var someValue = this.clientWidthCache + somethingElse
IE 8 具有在 IE 版本之间切换的能力,并且还有一个兼容模式。您是否尝试过切换到兼容模式?这有什么区别吗?
您的问题可能与其他问题有关(不仅是 clientwidth 调用):在调用此函数时,您是否在 DOM 中更新/调整大小?
您的浏览器可能正忙于在 IE8 上进行重排,从而使客户端宽度变慢?
我虽然在读取宽度属性时也注意到性能很慢。很可能会有。
然而,我发现对我们应用程序性能的主要影响是附加到窗口的 on resize 事件的函数本身以某种方式导致了另一个导致级联效应的调整大小,尽管不是无限循环。当我看到函数的调用计数在 IE8 中比在 IE7 中大几个数量级时,我意识到了这一点(喜欢 IE 开发工具)。我认为原因是元素上的某些活动,比如设置元素宽度,现在会导致 IE8 中的重排,而在 IE7 中没有这样做。
我通过将窗口的调整大小事件设置为:resize="return myfunction();" 来修复它 而不仅仅是 resize="myfunction();" 并确保 myfunction 返回 false;
我意识到最初的问题已经存在几个月了,但我想我会发布我的发现,以防其他人受益。