原理
合并配置
function normalizeProps (options: Object, vm: ?Component) {
const props = options.props
if (!props) return
const res = {}
let i, val, name
if (Array.isArray(props)) {
i = props.length
while (i--) {
val = props[i]
if (typeof val === 'string') {
name = camelize(val)
res[name] = { type: null }
} else if (process.env.NODE_ENV !== 'production') {
warn('props must be strings when using array syntax.')
}
}
} else if (isPlainObject(props)) {
for (const key in props) {
val = props[key]
name = camelize(key)
res[name] = isPlainObject(val)
? val
: { type: val }
}
}
}判断props 是不是数组, 在进行驼峰化, 数组形式我们 type 都设置为null
初始化
主要做三件事情, 校验props 生成响应式 defineReactive
只针对对象和数组类型的 prop,要求必须是一个工厂函数,它的值是工厂函数返回的值,所以要执行。 对于函数类型的 prop,那么它的值就是这个函数本身,所以不需要执行。 如果直接返回对象,那么多个组件实例的相应的默认 prop 值会共享这个对象,一旦修改这个对象,则会影响所有实例,是不符合预期的。
子组件重新渲染 分为props发生改变 或者内部属性发生变动
在构造函数初始化过程中进行proxy
props 更新
子组件创建的时候会触发 prepatch 方法
接着我们看 lifecycle 里面的
因为data 初始化数据会保护props, 所以在extend 的时候 props 是不会参与初始化求值的, 所以不能在 extend 的时候 proxy
vue 的优化 只递归父 props 对象 defineReactive, 没有处理子 props。
toggleObserving 在响应式中的优化
defineReactive(props)是为了给值类型用哦? 值类型props变化触发重新渲染执行 patchVnode ==>updateComponent,改变值类型props值触发setter。 对象类型props属性变化不会触发父组件的重新渲染也就不会触发updateComponent,直接通过访问的对象属性dep通知子组件watcher更新了
最后更新于
这有帮助吗?