cd snabbdom-demo
npm init -y
npm install parcel-bundler -D
[](()配置 scripts
“scripts”: {
“dev”: “parcel index.html --open”,
“build”: “parcel build index.html”
}
[](()目录结构
-
snabbdom-demo
-
index.html
-
package.json
-
src(文件目录)
-
01-basicusage.js
[](()导入 Snabbdom
Snabbdom 文档
-
看文档的意义
-
学习任何一个库都要先看文档
-
通过文档了解库的作用
-
看文档中提供的实例,自己快速实现一个 demo
-
通过文档查看 API
-
Snabbdom 文档
-
https://github.com/snabbdom/snabbdom
-
当前版本 v2.1.0
-
安装 Snabbdom
-
npm i Snabbdom@2.1.0
-
导入 Snabbdom
-
Snabbdom 的两个核心函数 init 和 h()
-
init() 是一个高阶函数,赶回 patch()
-
h() 返回虚拟节点 VNode,这个函数我们在使用 Vue.js 的时候见过
import { init } from ‘snabbdom/init’
import { h } from ‘snabbdom/h’
const patch = init([])
- 实际导入的方式
import { init } from ‘snabbdom/build/package/init’
import { h } from ‘snabbdom/build/package/h’
[](()基本使用
import { init } from ‘snabbdom/build/package/init’
import { h } from ‘snabbdom/build/package/h’
// 1. 通过 h 函数创建 VNode
let vNode = h(‘div#box.container’, ‘新内容’)
// 获取挂载元素
const dom = document.querySelector(‘#app’)
// 2. 通过 init 函数 得到 patch 函数
const patch = init([])
// 3. 通过 patch,将 vNode 渲染到 DOM
let oldVNode = patch(dom, vNode)
/*
patch 接收两个参数
-
旧节点
-
新节点
存在多个 vNode 状态的时候可以做新旧节点对比
参数1 也可以传 DOM,传入 DOM 时,会先将 DOM 转换为 vNode,然后在做对比
最后返回更新以后的 vNode 值
*/
// 4. 创建新的 VNode 更新给 oldVNode
vNode = h(‘p#text.ptext’, ‘这是 P 标签的内容’)
patch(oldVNode, vNode)
[](()包含子节点
import { init } from ‘snabbdom/build/package/init’
import { h } from ‘snabbdom/build/package/h’
const patch = init([])
// 创建包含子节点的 VNode
let vNode = h(‘div#box’, [
h(‘h1’, ‘标题文本’),
h(‘p’, ‘内容文本’)
])
/*
h 函数 的第二个参数为字符串时,直接作为当前创建元素的内容
如果是数组,代表传入的是子节点的列表,内部应该传入 vNode
*/
// 获取挂载元素
const dom = document.querySelector(‘#app’)
// 渲染 vNode
const oldVNode = patch(dom, vNode)
// 生成一个注释节点,替换当前节点,用来清空节点
patch(oldVNode, h(‘!’))
[](()Snabbdom 中的模块
=======================================================================
[](()模块的作用
-
Snabbdom 的核心库并不能处理 DOM 元素的属性、样式、事件等,可以通过注册 Snabbdom 默认提供的模块来实现
-
Snabbdom 中的模块可以用来扩展 Snabbdom 的功能
-
Snabbdom 中的模块的实现是通过注册全局的钩子函数来实现的
[](()官方提供的模块
-
attributes
-
props
-
dataset
-
class
-
style
-
eventlisteners
[](()模块的使用步骤
-
导入需要的模块
-
init() 中注册模块
-
h() 函数的第二个参数处使用模块
[](()模块代码演示
import { init } from ‘snabbdom/build/package/init’
import { h } from ‘snabbdom/build/package/h’
// 1. 导入模块(注意拼写,导入的名称不要拼错)
import { styleModule } from ‘snabbdom/build/package/modules/style’
import { eventListenersModule } from ‘snabbdom/build/package/modules/eventlisteners’
// 2. 注册模块(为 patch 函数添加模块对应的能力)
const patch = init([
styleModule,
eventListenersModule
])
let vNode = h(‘div#box’, {
style: {
width: ‘200px’,
height: ‘200px’,
lineHeight: ‘100px’,
textAlign: ‘center’,
backgroundColor: ‘green’
},
on: {
click() {
console.log(‘div被点击了’)
}
}
}, [
h(‘h1.text’, {
style: {
color: ‘white’
},
on: {
click() {
console.log(‘h1被点击了’)
}
}
},‘标题文本’),
h(‘p.text’, ‘标题文本’)
] 《大厂前端面试题解析+Web核心总结学习笔记+企业项目实战源码+最新高清讲解视频》无偿开源 徽信搜索公众号【编程进阶路】 )
const dom = document.querySelector(‘#app’)
patch(dom, vNode)
[](()Snabbdom 源码解析
=======================================================================
-
如何学习源码
-
宏观了解
-
带着目标看源码
-
看源码的过程要不求甚解
-
调试
-
参考资料
-
Snabbdom 的核心
-
init() 设置模块,创建 patch() 函数
-
使用 h() 函数创建 JS 对象(VNode)描述真实 DOM
-
patch() 比较新旧两个 VNode
-
把变化的内容更新到真实 DOM 树
-
Snabbdom 源码
-
地址:https://github.com/snabbdom/snabbdom
-
当前版本:v2.1.0
-
克隆代码:
git clone -b v2.1.0 --depth=1 https://github.com/snabbdom/snabbdom.git
[](()h 函数
-
作用:创建 VNode 对象
-
Vue 中的 h 函数
new Vue({
router,
store,
render: h => h(App)
}).$mount(‘#app’)
-
函数重载
-
参数个数或参数类型不同的函数
-
JS 中没有重载的概念
-
TS 中有重载,不过重载的实现还是通过代码调整参数
function add (a: number, b: number) {
console.log(a + b)
}
function add (a: number, b: number, c: number) {
console.log(a + b + c)
}
add(1, 2)
add(1, 2, 3)
function add (a: number, b: number) {
console.log(a + b)
}
function add (a: number, b: string) {
console.log(a + b)
}
add(1, 2)
add(1, ‘2’)