H5頁面在IOS微信中跳轉時,會出現底部工具欄,遮擋頁面底部內容

問題描述:
在IOS微信中打開H5頁面,當瀏覽器內出現跳轉產生url歷史記錄時,頁面底部會出現一個帶有前進和後退按鈕的工具欄,會遮擋頁面底部的內容。css

分析緣由:
頁面跳轉時,微信瀏覽器經過window.history讀取到瀏覽的歷史記錄,此時便會在頁面底部顯示出前進後退按鈕的工具欄,形成頁面底部內容遮擋。但刷新一下該頁面,就不會遮擋了。底部的工具欄是在頁面完成渲染以後才渲染的。html

解決方案:ios

不產生歷史記錄讓底部工具欄不出現

因爲未受權代碼沒法清除會話歷史(session History),也不能禁用回退/前進功能。最快捷的可用方式是使location.replace()方法,提供指定的URL來替換當前的會話歷史(session history)。segmentfault

  1. 用replace替代push指第一個頁面到第二個頁面push->replace,其餘頁面不變。瀏覽器

    實際應有中IOS跳轉應用商店使用的是中間頁和tencent/camp-launch-app的插件,使用的是window.location.href = url跳轉,未採用。
  2. 在第一個界面產生歷史記錄:能夠在跳轉到第一個頁面前再加一個頁面,此頁面不須要內容直接跳轉便可。緩存

    在實際應用中在第一個頁面產生歷史記錄不是最優解決方案,未採用。
  3. 在頁面加載以前經過主動添加空的歷史記錄,觸發瀏覽器的history監聽機制,讓瀏覽器先於頁面調出底部工具欄,從而解決遮擋問題。微信

    在路由守衛中增長對 window.history 的處理:
router.beforeEach((to, from, next) => {
    window.history.replaceState(null, null, window.location.href);
    next();
});

replaceState 是替換瀏覽歷史中的上一條記錄,用當前頁面的地址替換上一條記錄,本質上瀏覽歷史是不變的。
經測試僅IOS 6 Plus生效。session

緣由:IOS微信中調整到下一頁面後並未將上一頁面修改的url保持在歷史記錄中。
eg: 返回上一頁並未返回到 http://www.a.com?time=xxx,而... http://www.a.com 中。app

底部工具欄出現後,再獲取頁面高度或從新定位

IOS底部導航欄出現會致使頁面高度改變,能夠利用onresize監聽頁面大小變化,在高度改變後從新設置非正常佈局流元素便可解決。工具

function resizeHeight(e, delay = 200){ // delay = 200ms僅供參考,若還出現問題可增長時間延遲
    let resizeTimeout;
    if (!resizeTimeout) {
        resizeTimeout = setTimeout(function() {
            resizeTimeout = null;
            let navBar = document.getElementsByClassName("component-tab-bar-box")[0]; //此類即爲非正常佈局流元素
            let bottom = navBar.style.bottom;
            navBar.style.bottom = parseInt(bottom) ? 0 : 1 + 'px';
        }, delay);
    }
}
window.onresize = resizeHeight;

但delay時間很差肯定,未採用。

在IOS微信中經過pageshow事件決定是否須要刷新頁面

H5頁面在IOS微信內置瀏覽器中點擊返回按鈕返回上一頁時,上一頁面不會被刷新。在瀏覽器緩存機制中,在返回上一頁的操做中, html/js/css/接口等動靜態資源不會從新請求,可是js會從新加載。但在IOS微信頁面中js也會保存上一頁面最後執行的狀態,不會從新執行js。

瀏覽器前進/後退緩存(Backward/Forward Cache,簡稱BF Cache)是一種瀏覽器優化,HTML標準並未指定其如何進行緩存,所以緩存行爲是各瀏覽器實現不盡相同。

pageshow:當一條會話歷史記錄被執行的時候將會觸發頁面顯示(pageshow)事件。(這包括了後退/前進按鈕操做,同時也會在onload 事件觸發後初始化頁面時觸發)。

window.addEventListener('pageshow', function(event) {
    // event.persisted: Boolean類型,表示網頁是不是來自緩存。
});

pageshow兼容性:

Feature Chrome Firefox (Gecko) Internet Explorer Opera Safari
Basic support 4 1.5 (1.8) 11 15 5
Feature Android Firefox Mobile (Gecko) IE Mobile Opera Mobile Safari Mobile
Basic support 2.3 ? 11 35 5.1

performance.navigation的type值爲2,頁面經過歷史記錄和前進後退訪問時。
即:window.performance.navigation.type === 2

performance.navigation兼容性:

Feature Chrome Edge Firefox Internet Explorer Opera Safari
Basic support 10 12 7 9 15 8
Feature WebView Android Chrome Android Firefox for Android Opera Android Safari on ios Samsung Internet
Basic support <= 37 18 7 No 9 1.0
if (isWxH5 && Utils.isIos()) {
    window.onpageshow = function(e) {
        if(e.persisted || (window.performance && window.performance.navigation.type == 2)) {
            window.location.reload()
        }
    }
}

pageShow事件在頁面顯示即會觸發,不管頁面是否來自BF Cache。經過檢測persisted屬性便可判斷是否存在 BF Cache 行爲。IOS中的微信頁面,支持pageShow方法、persisted屬性以及performance.navigation屬性。

參考文章:

  1. IOS微信下問題1 底部導航欄致使標籤位置偏移
  2. iOS新版微信底部工具欄遮擋問題完美解決
  3. Ios中微信頁面返回上一頁去除緩存幾種常見思路
  4. iOS設備 微信h5頁面回退 內容不刷新的問題
  5. iOS微信底部返回橫條問題
  6. h5返回到上一頁ios手機頁面不刷新
  7. 微信頁面入口文件被緩存解決方案
相關文章
相關標籤/搜索