Appearance
1. 接口定义
本节目标:理解“1. 接口定义”的核心思路,并能把它用于实际开发或面试表达。
说明:原 OneNote 中有图片引用,但图片未包含在导出目录中;本页保留了可用的文字与代码内容。
我们MVVM的框架接口和Vue3一模一样。
初始化需要确定视图模板数据模型模型行为 - 比如我们希望click的时候数据模型的message会会倒序排列。const App = {
// 视图
template: `
<input v-model="message"/>
<button @click='click'>{{message}}</button>
`,
setup() {
// 数据劫持
const state = new Proxy(
{
message: "Hello Vue 3!!",
},
{
set(target, key, value, receiver) {
const ret = Reflect.set(target, key, value, receiver);
// 触发函数响应
effective();
return ret;
},
}
);
const click = () => {
state.message = state.message.split("").reverse().join("");
};
return { state, click };
},
};
const { createApp } = Vue;
createApp(App).mount("#app");**2.** **程序骨架**const Vue = {
createApp(config) {
// 编译过程
const compile = (template) => (content, dom) => {
};
// 生成渲染函数
const render = compile(config.template);
return {
mount: function (container) {
const dom = document.querySelector(container);
// 实现setup函数
const setupResult = config.setup();
// 数据响应更新视图
effective = () => render(setupResult, dom);
render(setupResult, dom);
},
};
},
};**3.** **编译渲染函数**
MVVM框架中的渲染函数是会通过视图模板的编译建立的。
// 编译函数
// 输入值为视图模板
const compile = (template) => {
//渲染函数
return (observed, dom) => {
// 渲染过程
}
}简单的说就是对视图模板进行解析并生成渲染函数。
大概要处理以下三件事确定哪些值需要根据数据模型渲染// <button>{{message}}</button>
// 将数据渲染到视图
button = document.createElement('button')
button.innerText = observed.message
dom.appendChild(button)绑定模型事件// <button @click='click'>{{message}}</button>
// 绑定模型事件
button.addEventListener('click', () => {
return config.methods.click.apply(observed)
})确定哪些输入项需要双向绑定// <input v-model="message"/>
// 创建keyup事件监听输入项修改
input.addEventListener('keyup', function () {
observed.message = this.value
})完整的代码const compile = (template) => (observed, dom) => {
// 重新渲染
let input = dom.querySelector('input')
if (!input) {
input = document.createElement('input')
input.setAttribute('value', observed.message)
input.addEventListener('keyup', function () {
observed.message = this.value
})
dom.appendChild(input)
}
let button = dom.querySelector('button')
if (!button) {
console.log('create button')
button = document.createElement('button')
button.addEventListener('click', () => {
return config.methods.click.apply(observed)
})
dom.appendChild(button)
}
button.innerText = observed.message
}