[英]How to free and garbage collect a WebGL context?
我正在為 Web 和移動開發 WebGL 應用程序。 我經常使用硬刷新來測試我的 WebGL 實現的結果。 視圖嘗試后,我收到錯誤:
Error: WebGL: Exceeded 16 live WebGL contexts for this principal, losing the least recently used one.
這不會出現在新啟動的瀏覽器上,而是在多次刷新站點后出現。 我猜 WebGL 上下文沒有正確完成、釋放、銷毀、清理、釋放。
我怎樣才能做到這一點?
Khronos Group 在此處創建了一個用於釋放和垃圾收集 WebGL 上下文的測試套件: https ://www.khronos.org/registry/webgl/sdk/tests/conformance/context/context-creation-and-destruction.html(注意:此可能會使您的瀏覽器崩潰!)
測試通過PASS
和TEST COMPLETE
運行,所以基本上測試沒有檢測到任何問題。 然而,打開 JavaScript 控制台,它會讀取 33 個實例:
Error: WebGL: Exceeded 16 live WebGL contexts for this principal, losing the least recently used one.
這是瀏覽器如何處理 WebGL 的錯誤嗎? 還是我做錯了什么? 我從沒想過釋放任何 WebGL 上下文。
我正在使用 Firefox 開發者版 48.0a2 和 Firefox 46.0.1。
如何釋放和垃圾收集 WebGL 上下文?
我想也許我誤解了你的問題
你說你正在努力刷新。 意味着您在瀏覽器中按刷新? 在這種情況下,首先我會禁用所有擴展,看看問題是否仍然存在。 如果是,我會用 Mozilla 提交一個錯誤
否則,如果您嘗試釋放畫布並創建已知的畫布並希望垃圾收集良好..這是我在重新閱讀您的問題之前寫的答案
簡短的回答是你不能強制垃圾收集。 你最好重新使用相同的畫布。
這里有一個釋放所有數據並重置畫布的解決方案
在您的特定情況下,您是否 100% 確定您沒有保留對 WebGL 上下文或畫布的某些引用? 例如,如果你這樣做
canvas.addEventListener('click', function(..) {});
你剛剛制作了一個永遠不會被垃圾收集的畫布。 它附加了一個事件偵聽器功能。 您無法刪除該函數,因為您沒有保留對它的引用。 您需要刪除所有偵聽器,這只是您可能泄漏引用的多種方式之一。
有很多方法可以不小心保留對 HTML 元素(如畫布和 WebGL 對象)的引用。 保持多個引用,它永遠不會被垃圾收集。
另一方面,如果是我,我會嘗試重新使用畫布。 為了確保我釋放了我可能調用我自己的創建/刪除函數來跟蹤所有資源的所有內容。 例子
var textures = [];
function createTexture(gl) {
var tex = gl.createTexture();
textures.push(txt);
}
function deleteTexture(gl, tex) {
gl.deleteTexture(tex);
textures.splice(textures.indexOf(tex), 1);
}
現在因為我正在跟蹤所有紋理,所以我可以輕松刪除所有剩余的紋理
while (textures.length) {
gl.deleteTexture(textures.pop());
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.