Webview 预加载方案的实现
2020-06-22 本文已影响0人
Allen_Ezail_Ive
背景说明
早期公司需要开发一款移动端App,由于原生开发成本较大,最终公司决定采用H5+cordova实现web打包App,随之而来的是不断的性能优化,这里着重讲下首屏优化,即首次打开应用消耗时间的优化。
优化思路
App应用安装时候,将首屏所需静态资源下载到本地文件中
基本概念
预初始化CordovaWebView,移除并没有用的cordova插件
预加载preload.html, 以及公共js,页面中不包含业务逻辑
预注入cordova(IOS)
当开始跳转后取出已经预加载完的preload.html, 并加载业务JS代码, 同时开始执行业务逻辑和渲染业务界面
[站外图片上传中...(image-8cb7fd-1592830410201)]
前端核心代码
(function (window) {
var deviceReady = false;
window.wdPreload = {
ready: function (success) {
if (deviceReady) {
success();
} else {
document.addEventListener(""deviceready"", function () {
deviceReady = true;
success();
}, false);
}
},
loadScript: function (url, callback) {
var script = document.createElement(""script"");
script.type = ""text/javascript"";
script.async = true;
if (script.readyState) {
script.onreadystatechange = function () {
if (script.readyState == ""loaded"" || script.readyState == ""complete"") {
script.onreadystatechange = null;
callback && callback();
}
};
} else {
script.onload = callback;
}
script.src = url;
(document.body || document.getElementsByTagName(""body"")[0] || document.documentElement).appendChild(
script);
},
formatUrl: function (url) {
var str = url.replace(/(.*\.html)?(.*?)/, '$1,$2');
var arr = str.split(',');
var indexs = [arr[1].indexOf('?'), arr[1].indexOf('#')];
var path = indexs[1] > indexs[0] ? (arr[1].slice(indexs[1], arr[1].length) + arr[1].slice(indexs[
0], indexs[1])) : arr[1];
return path;
},
appendQuery: function (url, query) {
return url + (url.indexOf('?') > -1 ? '&' : '?') + query;
},
load: function () { // 业务逻辑加载
if (location.href.indexOf('jscallback=loadScript') > -1) {
window.WDS = window.WDS || {};
wdPreload.ready(function () {
wdPreload.loadScript('index.js');
});
} else {
window.WDS = window.WDS || {};
window.WDS.nativeLoad = function (url, data) { // 此函数由APP主动调用
location.replace((location.search ? 'preload.html' : '') + wdPreload.appendQuery(wdPreload.formatUrl(
url), ""jscallback=loadScript"") + location.search.replace('?', '&'));
wdPreload.loadScript('index.js');
}
}
}
};
window.wdPreload.load();
})(window);