webpack学习:uni运行时代码解读一 (页面初始化加载)
uni的vue代码是如何在微信小程序里面执行的,对此比较感兴趣所以去调试学习了一波.
准备工作
// 在vue.config.js里打开非压缩的代码
module.exports = {
configureWebpack: config => {
config.devtool = 'none'
config.mode = 'development'
}
}
// 运行时代码路径 node_modules\@dcloudio\uni-mp-weixin\dist\index.js
// uni修改过后的vue代码路径 node_modules\@dcloudio\vue-cli-plugin-uni\packages\mp-vue\dist\mp.runtime.esm.js
页面初始化
不管是页面还是组件,uni都是通过微信提供的全局component方法来实现的,uni在原生的conponent基础上做了一层代理
const MPPage = Page;
const MPComponent = Component;
if (!MPPage.__$wrappered) {
MPPage.__$wrappered = true;
// page 也做了代理,但是没有使用(至少正常配置没有使用)
Page = function (options = {}) {
initHook('onLoad', options);
return MPPage(options)
};
Page.after = MPPage.after;
Component = function (options = {}) {
initHook('created', options);
return MPComponent(options)
};
}
对外暴露了createComponent, createPage 这2个方法,在生成的vue文件里会调用这2个方法,这2个方法的核心都是parseComponent
function createPage (vuePageOptions) {
{
// Component 是被包裹一次的wx原生方法
return Component(parsePage(vuePageOptions))
}
}
function parsePage (vuePageOptions) {
return parseBasePage(vuePageOptions, {
isPage,
initRelation
})
}
function createComponent (vueOptions) {
{
return Component(parseComponent(vueOptions))
}
}
function parseBasePage (vuePageOptions, {
isPage,
initRelation
}) {
const pageOptions = parseComponent(vuePageOptions);
initHooks(pageOptions.methods, hooks$1, vuePageOptions);
pageOptions.methods.onLoad = function (query) {
this.options = query;
const copyQuery = Object.assign({}, query);
delete copyQuery.__id__;
this.$page = {
fullPath: '/' + (this.route || this.is) + stringifyQuery(copyQuery)
};
this.$vm.$mp.query = query; // 兼容 mpvue
this.$vm.__call_hook('onLoad', query);
};
return pageOptions
}
parseComponent的parseBaseComponent方法是把vue配置初始化为微信的配置文件(上面的代码贴出来不看都无所谓这里才真正的开始),把你vue的配置转换为微信小程序的配置
function parseComponent (vueComponentOptions) {
return parseBaseComponent(vueComponentOptions, {
isPage,
initRelation
})
}
function parseBaseComponent (vueComponentOptions, {
isPage,
initRelation
} = {}) {
// Vue.extend(vueComponentOptions); 核心就是通过vue的extend方法生成一个构造器
const [VueComponent, vueOptions] = initVueComponent(Vue, vueComponentOptions);
const options = {
multipleSlots: true,
addGlobalClass: true,
...(vueOptions.options || {})
};
// 这个option就是微信用来生成组件的option
const componentOptions = {
options,
// vue的data和methods都会合并然后放在wx的data里
data: initData(vueOptions, Vue.prototype),
// vue的mixins extends behaviors都合并然后变成wx的behaviors
behaviors: initBehaviors(vueOptions, initBehavior),
// vue的props转换而成
properties: initProperties(vueOptions.props, false, vueOptions.__file),
lifetimes: {
attached () {
// 获取到微信实例的props
const properties = this.properties;
const options = {
mpType: isPage.call(this) ? 'page' : 'component',
mpInstance: this,
propsData: properties
};
// 初始化 vue 实例
this.$vm = new VueComponent(options);
// 执行vue实例的mount,这一步很特别,vue实例其实是没有任何的render,因为vue的template
// 已经在打包的过程中变成wxml,给wx实例使用了,所以这个vue的实例的页面内容其实是空的,
// 那如何处理vue的渲染watch呢,uni对vue的源码做了处理,在patch的时候,新建了一个空对象
// 然后把data和computed里面的所有属性都复制给了新对象,从而达到了渲染watch的监听效果
// 也就是说在uni里面的vue,所有的data和computed都是在渲染watch里面使用了的,可能对排除
// 某些问题有所帮助
this.$vm.$mount();
},
ready () {
// 当组件 props 默认值为 true,初始化时传入 false 会导致 created,ready 触发, 但 attached 不触发
// https://developers.weixin.qq.com/community/develop/doc/00066ae2844cc0f8eb883e2a557800
if (this.$vm) {
this.$vm._isMounted = true;
// 在微信实例的ready钩子里 触发vue的挂载钩子
this.$vm.__call_hook('mounted');
this.$vm.__call_hook('onReady');
}
},
detached () {
this.$vm && this.$vm.$destroy();
}
},
pageLifetimes: {
show (args) {
this.$vm && this.$vm.__call_hook('onPageShow', args);
},
hide () {
this.$vm && this.$vm.__call_hook('onPageHide');
},
resize (size) {
this.$vm && this.$vm.__call_hook('onPageResize', size);
}
},
methods: {
__l: handleLink,
__e: handleEvent
}
};
if (isPage) {
return componentOptions
}
return [componentOptions, VueComponent]
}
用一张图来快速理解

uni的和vue的区别
一 computed是立即执行,且所有data和computed都会成为渲染依赖
二 vue的组件其实是没有任何页面的,页面都是微信组件的
三 wx的实例是通过微信的component来生成的,不是page方法
webpack学习:uni运行时代码解读一 (页面初始化加载)的更多相关文章
- webpack学习笔记--提取公共代码
为什么需要提取公共代码 大型网站通常会由多个页面组成,每个页面都是一个独立的单页应用. 但由于所有页面都采用同样的技术栈,以及使用同一套样式代码,这导致这些页面之间有很多相同的代码. 如果每个页面的代 ...
- 如何将oc代码转换成运行时代码
// 运行时 其实就是oc的底层 平时写的代码 最终都是转成底层的运行时代码以下面程序为例子: 如果我们想要看我们的main.m文件底层转换成了怎样的运行时代码 ,我们可以这样做. 1.打开终端 ...
- 《Secrets of the JavaScript Ninja》:JavaScript 之运行时代码
最近,在阅读 jQuery 之父 John Resig 力作:Secrets of the JavaScript Ninja(JavaScript忍者秘籍).关于第九章提及的 JavaScript 之 ...
- webpack 代码拆分,按需加载
转自:https://segmentfault.com/a/1190000007649417?utm_source=weekly&utm_medium=email&utm_campai ...
- webpack中dev-server不写contentBase时如何设置可以显示页面并且加载js
今天学习了dev-server这个配置,中间遇到疑惑,我写了contentBase是可以走通,可以再localhost:8080看到页面并且正确加载bundle.js的,但是这个contentBase ...
- 使用Webpack的代码分离实现Vue懒加载(译文)
当一个Vue的项目体积变得十分庞大的时候,使用Webpack的代码分离功能将Vue Components,routes或Vuex的代码进行分离并按需加载,会极大的提高App的首屏加载速度. 在Vue的 ...
- 使用Webpack的代码分离实现Vue懒加载
当一个Vue的项目体积变得十分庞大的时候,使用Webpack的代码分离功能将Vue Components,routes或Vuex的代码进行分离并按需加载,会极大的提高App的首屏加载速度. 在Vue的 ...
- VSTO学习笔记(三) 开发Office 2010 64位COM加载项
原文:VSTO学习笔记(三) 开发Office 2010 64位COM加载项 一.加载项简介 Office提供了多种用于扩展Office应用程序功能的模式,常见的有: 1.Office 自动化程序(A ...
- 插件化框架解读之so 文件加载机制(四)
阿里P7移动互联网架构师进阶视频(每日更新中)免费学习请点击:https://space.bilibili.com/474380680 提问 本文的结论是跟着 System.loadlibrary() ...
随机推荐
- 【LeetCode】767. Reorganize String 解题报告(Python)
作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.me/ 题目地址:https://leetcode.com/problems/reorganiz ...
- C++函数参数的传递顺序
C++编译器默认使用的是 __cdecl 模式,参数是通过栈传递的,因此是从右到左的传参顺序. int f(int a, int b, int c) { return 0; } int main(){ ...
- [linux]ubuntu18.04 屏幕分辨率不适应问题
今天换了新显示器,发现更大的屏幕不适应原有的屏幕分辨率,看起来特别变扭. 在设置处查看最高分辨率仅为1024*748,没有与屏幕相适应的1920*1080(16:9). 解决方式: 1. 终端输入命令 ...
- 关于linux的一点好奇心(一):linux启动过程
一直很好奇,操作系统是如何工作的?我们知道平时编程,是如何让代码跑起来的,但那些都是比较高层次的东西.越往后,你会越觉得,像是空中楼阁,或者说只是有人帮你铺平了许多道理,而你却对此一无所知. 1. 操 ...
- SpringBoot集成Log4j2框架
1.说明 本文详细介绍Spring Boot集成Log4j2框架的方法, 基于已经创建好的Spring Boot工程, 由于Spring Boot默认使用的是Logback框架, 需要先排除掉Logb ...
- Hbase集群安装Version1.1.5
Hbase集群安装,基于版本1.1.5, 使用hbase-1.1.5.tar.gz安装包. 1.安装说明 使用外部Zookeeper集群而非Hbase自带zookeeper, 使用Hadoop文件系统 ...
- 初识python: 继承
继承:可以使用现有类的所有功能,并在无需重新编写原来的类的情况下对这些功能进行扩展. 通过继承创建的新类称为"子类"或"派生类". 被继承的类称为"基 ...
- 力扣 - 剑指 Offer 49. 丑数
题目 剑指 Offer 49. 丑数 思路1 丑数是只包含 2.3.5 这三个质因子的数字,同时 1 也是丑数.要计算出 n 之前全部的丑数,就必须将 n 之前的每个丑数都乘以 2.3.5,选取出最小 ...
- CSS-选择器的使用
* 默认选择器,这个符号能匹配所有样式,所以如果没有额外定义就默认为这个样式,一般用于消除页面与浏览器的内外边距 <style> *{ padding:0; // 所有标签默认消除内边距 ...
- Android官方文档翻译 十一 2.4Overlaying the Action Bar
Overlaying the Action Bar 叠加菜单栏 This lesson teaches you to 这节课教给你: Enable Overlay Mode 启用叠加模式 For An ...