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运行时代码解读一 (页面初始化加载)的更多相关文章

  1. webpack学习笔记--提取公共代码

    为什么需要提取公共代码 大型网站通常会由多个页面组成,每个页面都是一个独立的单页应用. 但由于所有页面都采用同样的技术栈,以及使用同一套样式代码,这导致这些页面之间有很多相同的代码. 如果每个页面的代 ...

  2. 如何将oc代码转换成运行时代码

    // 运行时 其实就是oc的底层  平时写的代码 最终都是转成底层的运行时代码以下面程序为例子: 如果我们想要看我们的main.m文件底层转换成了怎样的运行时代码 ,我们可以这样做. 1.打开终端  ...

  3. 《Secrets of the JavaScript Ninja》:JavaScript 之运行时代码

    最近,在阅读 jQuery 之父 John Resig 力作:Secrets of the JavaScript Ninja(JavaScript忍者秘籍).关于第九章提及的 JavaScript 之 ...

  4. webpack 代码拆分,按需加载

    转自:https://segmentfault.com/a/1190000007649417?utm_source=weekly&utm_medium=email&utm_campai ...

  5. webpack中dev-server不写contentBase时如何设置可以显示页面并且加载js

    今天学习了dev-server这个配置,中间遇到疑惑,我写了contentBase是可以走通,可以再localhost:8080看到页面并且正确加载bundle.js的,但是这个contentBase ...

  6. 使用Webpack的代码分离实现Vue懒加载(译文)

    当一个Vue的项目体积变得十分庞大的时候,使用Webpack的代码分离功能将Vue Components,routes或Vuex的代码进行分离并按需加载,会极大的提高App的首屏加载速度. 在Vue的 ...

  7. 使用Webpack的代码分离实现Vue懒加载

    当一个Vue的项目体积变得十分庞大的时候,使用Webpack的代码分离功能将Vue Components,routes或Vuex的代码进行分离并按需加载,会极大的提高App的首屏加载速度. 在Vue的 ...

  8. VSTO学习笔记(三) 开发Office 2010 64位COM加载项

    原文:VSTO学习笔记(三) 开发Office 2010 64位COM加载项 一.加载项简介 Office提供了多种用于扩展Office应用程序功能的模式,常见的有: 1.Office 自动化程序(A ...

  9. 插件化框架解读之so 文件加载机制(四)

    阿里P7移动互联网架构师进阶视频(每日更新中)免费学习请点击:https://space.bilibili.com/474380680 提问 本文的结论是跟着 System.loadlibrary() ...

随机推荐

  1. LeetCode1238循环码排列

    题目 给你两个整数 n 和 start.你的任务是返回任意 (0,1,2,,...,2n-1) 的排列 p,并且满足: p[0] = start p[i] 和 p[i+1] 的二进制表示形式只有一位不 ...

  2. Rikka with Graph(hdu5631)

    Rikka with Graph  Accepts: 123  Submissions: 525  Time Limit: 2000/1000 MS (Java/Others)  Memory Lim ...

  3. codeforces 624C Graph and String

    C. Graph and String time limit per test 2 seconds memory limit per test 256 megabytes input standard ...

  4. How Many Sets I(zoj3556)

    How Many Sets I Time Limit: 2 Seconds      Memory Limit: 65536 KB Give a set S, |S| = n, then how ma ...

  5. Jmeter环境变量配置你不得不知道的事情

    在安装Jmeter的过程中大家肯定需要配置环境,但是为什么要配置JDK的环境变量呢?大家有没有好奇过,有没有仔细去像一下呢,其实在安装Jmeter前,大家应该都知道Jmeter是我们JAVA开发的,J ...

  6. CS5265低成本替代RTD2172|CS5265替代兼容RTD2172|替代RTD2172

    瑞昱RTD2172是TYPEC转HDMI4K60HZ音视频数据转换器芯片.CS5265可以替代兼容RTD2172,除了实现同等的转换功能外且整体方案成本和性价比方面比RTD2172要高,且外围器件较少 ...

  7. 一键抠除路人甲,昇腾CANN带你识破神秘的“AI消除术”

    摘要:都说人工智能改变了生活,你感觉到了么?AI的魔力就在你抠去路人甲的一瞬间来到了你身边.今天就跟大家聊聊--神秘的"AI消除术". 引语 旅途归来,重温美好却被秀丽河山前的路人 ...

  8. Sentry 企业级数据安全解决方案 - Relay 配置选项

    Relay 的配置记录在文件 .relay/config.yml 中.要更改此位置,请将 --config 选项传递给任何 Relay 命令: ❯ ./relay run --config /path ...

  9. [转]webpack配置本地服务器

    亲测,webpack打包vue项目之后生成的dist文件可以部署到 express 服务器上运行. 我的vue项目结构如下: 1. 进入该vue项目目录,打开git bash,执行:npm run b ...

  10. x86-3-段式管理(segmentation)

    x86-3-段式管理(segmentation) 3.1 段式管理概述: 从8086CPU开始,为了让程序在内存中能自由浮动而又不影响它的正常执行,CPU将内存划分成逻辑上的段来给程序使用. x86继 ...