2009-04-29 36 views
6

我有一些傳統的JavaScript,凍結表的tfoot/thead,並讓身體滾動,它工作正常,除非在IE8中它非常緩慢。在IE8中的clientWidth性能

我追溯到讀取tfoot/thead中的單元格的clientWidth屬性在ie6/7和FireFox 1.5-3大約需要3ms讀取clientWidth屬性...在IE8它接管當表格中的單元數量增加時,200ms或更長。

這是一個已知的錯誤嗎?有什麼解決辦法嗎?

回答

2

我無法找到任何文件,這是一個已知的錯誤。爲了提高性能,爲什麼不緩存clientWidth屬性並定期更新緩存?也就是說,如果你的代碼是:

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 
0

你的問題可能與其他的東西(而不僅是clientwidth調用):是你更新/調整anyhting在DOM同時調用這個函數?

您的瀏覽器可能是IE8上的busy doing reflow,從而使客戶端寬度變慢?

0

IE 8有能力在IE版本之間切換,並且還有兼容模式。 您是否嘗試切換到兼容模式?這有什麼區別嗎?

+0

是的切換到兼容模式使其性能更好,但是它破壞了我的用戶界面的其他部分,因爲它不像IE7那樣渲染。希望有一個不涉及兼容性的解決方案,但它可能是唯一的選擇。 – Element 2009-07-29 01:31:51

+0

我不是說這是你的情況的問題,但上次我有渲染IE7和IE8之間的差異,我發現我的代碼特別是HTML/CSS有錯誤。兼容模式似乎解決了這個問題,但我並不想接受這一點。所以我可能會開始通過驗證器來運行代碼。誰知道,你可能錯過了一些東西。 - 我做到了。 ;) – 2009-07-29 10:00:39

6

如果你還有興趣,我已經解決了這個問題。解決方案非常複雜。基本上,你需要附加一個簡單的宏達元素和緩存其clientWidth /高度。

簡單的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用於緩存值創建干將:

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"; 
} 

請注意,我創建的常量寬度/高度。你應該使用這些來獲得你的元素的寬度/高度:

var width = element[WIDTH]; 

它很複雜,但它的工作原理。我遇到同樣的問題,訪問clientWidth的速度非常慢。這很好地解決了這個問題。它仍然不像IE7那麼快,但它又回到了可用狀態。

0

雖然我發現讀取寬度屬性時性能也很差。而且很可能有。

但是,我發現在我們的應用程序中對性能的主要影響是附加到窗口的resize事件的函數本身不知何故導致另一個調整大小,從而導致級聯效應,儘管不是無限循環。我意識到這一點,當我看到函數的調用次數在IE8中比在IE7中大得多(喜歡IE開發工具)。我認爲原因在於元素上的一些活動,比如設置元素寬度,現在可能導致IE8中的重排,IE7中沒有這樣做。

我通過設置窗口的resize事件來修復它:resize =「return myfunction();」而不是隻調整大小=「myfunction();」並確保我的函數返回false;

我意識到原來的問題是幾個月大,但我想我會張貼我的調查結果,以防其他人受益。