CSS-3D 加速致使微信手Q閃退

筆者常常與微信手Q平臺打交道,偶爾會遇到 H5 頁面致使 iOS 下微信手Q程序閃退(崩潰)的狀況。
致使微信手Q閃退的緣由筆者遇到的大概有如下幾種:css

  • CSS-3D 加速過多;
  • 帶滾動條的結構過多;
  • webGL 繪製圖像過多

本文僅討論「CSS-3D」加速形成微信手Q閃退的必要條件」。
科普一下「CSS-3D加速」也叫「CSS硬件加速」,它的原理是利用 GPU加速圖像渲染。每個帶有 3D 屬性的 DOM 節點都會在 GPU 生成一個對應的紋理,而這個紋理能夠被快速地操做(如:移動、縮放和旋轉)。GPU紋理會佔用必定的內存,而微信手Q分配給內嵌 webview 的 GPU 內存是固定的,一旦GPU紋理超過了這個內存就將致使所在環境閃退(崩潰)。html

微信手Q分配給 GPU 紋理的內存是多少?
老實說,筆者不瞭解微信手Q的內核,因此回答不了。不過,既然GPU紋理超過指定內存就會閃退,那麼能夠經過實驗的方法推導出閃退的臨界值。git

帶 3d 樣式的 DOM 節點與 GPU 紋理的面積大小是一一對應的,因此筆者直接用 「width * height px2」 描述 GPU 紋理的大小。github

安全值實驗

爲了方便計算,筆者使用尺寸爲 100px * 100px 的 div 做爲實驗對象,樣式以下:web

.rect {
    width: 100px; 
    height: 100px; 
    transform: translateZ(0);
}

具體的實驗案例筆者放在:https://leeenx.github.io/demo...。二維碼以下:安全

二維碼

筆者手頭上只有 iPhone6 & iPhone6+,測試的數據以下:微信

設備 APP環境 rect 數量 描述
iPhone6 手Q 1400 ~ 2700 第一次進入不閃退,刷新當前頁面閃退
iPhone6 手Q >2700 進入直接閃退
iPhone6+ 手Q 700 ~ 1400 第一次進入不閃退,刷新當前頁面閃退
iPhone6+ 手Q >1400 進入直接閃退
iPhone6 微信(UIWebview) 1400 ~ 2700 第一次進入不閃退,刷新當前頁面閃退
iPhone6 微信(UIWebview) >2700 進入直接閃退
iPhone6+ 微信(UIWebview) 700 ~ 1400 第一次進入不閃退,刷新當前頁面閃退
iPhone6+ 微信(UIWebview) >1400 進入直接閃退
iPhone6 微信(WKWebview) 100000+ 不閃退
iPhone6+ 微信(WKWebview) 10000+ 不閃退

注意事項:iphone

  1. 測試頁面的「生成」按鈕會刷新後從新生成對應個數的 rect
  2. UIWebview 是指微信舊的webview,具體能夠參見:iOS網頁開發適配指南

微信環境下有個利好的消息:測試

微信iOS客戶端將於2017年3月1日前逐步升級爲WKWebview內核spa

也就是說「3d加速」已經不會形成新版微信閃退了。壞消息是手Q仍然有閃退的風險。

經過上面的數據其實能夠找到 iPhone6/6+ 的閃退臨界值爲:1400 * 100 * 100 px2 與 700 * 100 * 100 px2

可是其實咱們可能須要的是安全值而不是臨界值,筆者根據自身經驗定了一個安全值:

  • iPhone6 3D加速的安全面積: 1000 * 100 * 100 px2
  • iPhone6+ 3D加速的安全面積: 500 * 100 * 100 px2

因爲咱們的頁面都會在 iPhone6 & iPhone6+ 上運行,因此真正的 「安全值是 500 * 100 * 100 px2

500 * 100 * 100 px2 有多大?
iPhone6+ 的 webview 尺寸是:414 * 736,那麼「500 * 100 * 100 / 414 * 736 ≈ 16」。也就是說「3d加速的安全面積是16個手機屏幕」。這個尺寸並不大,因此加速需當心,安全最重要。

可能會有人會想iPhone6+閃退的門檻比 iPhone6 低這麼多?
iPhone6 和 iPhone6+ 官方配置上除了屏幕以外,其它硬件是一樣的配置,因此有這樣的疑問其實很正常。很明顯 iPhone6 與 iPhone6+ 閃退門檻的差別源自物理屏幕。

iPhone6 的 dpr = 2, iphone6+ 的 dpr = 3;而 GPU 紋理是按物理分辨率存儲的。假設一個帶
3D 樣式的 div 的尺寸爲 100px2,那麼這個節點在 iPhone6 對應的 GPU 紋理爲 「2 * 2 * 100px2」,在 iPhone6+ 對應的 GPU 紋理爲 「3 * 3 * 100 px2」。

很容易能夠獲得如下的數字:
3 * 3 * 100 px2 / 2 * 2 * 100px2 = 2.25

2.25 就是 iPhone6 與 iPhone6+ 的 GPU 加速的門檻差,其實經過上面的數據也反映了相似的比率。

結語

本文出示的數據是非生產環境下得出來的,真實的生產環境會受其它外因的影響估計數據要再打一下折。

感謝耐心閱讀完本文章的讀者。本文僅表明筆者的我的觀點,若有不妥之處請不吝賜教。

相關文章
相關標籤/搜索