vue prop default(vue props default)

Props 名为「道具」,当外部组件给内部组件传值时,通常在这个时候使用 props 。

Props 是如何初始化的,之前文章 组件初始化流程 里,在初始化组件执行 setupComponent 方法时,我们提过一句会通过 initProps 来初始化 Props。
export function setupComponent(  instance: ComponentInternalInstance,  isSSR = false) {  //初始化 props  initProps(instance, props, isStateful, isSSR)}

代码位置:runtime-core/src/component.ts

setupComponent 函数里求值了「状态组件」和「服务端渲染」,并通过 initProps 传入了四个参数:
  • instance 组件实例;
  • props 从 instance.vnode 解构出来的 props 数据,包括属性和动态属性;
  • isStateful 是否是有状态组件;
  • isSSR 是否是服务端渲染,默认为 false;
<tree-item class=\\\"item\\\" :model=\\\"treeData\\\"></tree-item>
我们进入到 initProps 函数里,看都执行了什么。
    export function initProps(  instance: ComponentInternalInstance,  rawProps: Data | null,  isStateful: number, // result of bitwise flag comparison  isSSR = false) {    // 先定义两个空数据    const props: Data = {}    const attrs: Data = {}    // 枚举属性设置成 false    def(attrs, InternalObjectKey, 1)    // 设置 props 值    setFullProps(instance, rawProps, props, attrs)    // 验证 props    if (__DEV__) {    validateProps(props, instance)  }    // 是否是状态组件,变成响应式的    instance.props = isSSR ? props : shallowReactive(props)    // 赋值给 instance.attrs    instance.attrs = attrs}
    先定义了两个对象「props」和「attrs」,并通过 setFullProps 方法传递了进去,方法会遍历我们收集到的 props 和 attrs。
    遍历 key,如果传递的是保留字符「ref」「key」则直接退出此次循环。还会去标准化 key 的命名格式为「驼峰命名」,如果当前 key 和 emit 派发无关,并且也不是 props,那就会在 attrs 里保存一份。见详细代码:
    function setFullProps(  instance: ComponentInternalInstance,  rawProps: Data | null,  props: Data,  attrs: Data) {  //如果是 key 或者 ref 则退出此次循环  if (isReservedProp(key)) { continue }  let camelKey  //标准化 key 的命名为「驼峰样式」  if (options && hasOwn(options, (camelKey = camelize(key)))) {    props[camelKey] = value  } else if (!isEmitListener(instance.emitsOptions, key)) {    // 如果不是 Emit 相关,也不是 props ,那就保存到 attrs 里。    attrs[key] = value  }  // ...  if (needCastKeys) {    const rawCurrentProps = toRaw(props)    for (let i = 0; i < needCastKeys.length; i++) {      const key = needCastKeys[i]      props[key] = resolvePropValue(        options!,        rawCurrentProps,        key,        rawCurrentProps[key],        instance      )    }  }}

    代码位置:runtime-core/src/componentProps.ts

    setFullProps 方法执行完后,返回 initProps 执行 validateProps 方法来「验证 props」,只在开发环境验证,验证 props 数据是否合法。
      //是否必填if (required && isAbsent) {  warn(\\\'Missing required prop: \\\"\\\' + name + \\\'\\\"\\\')  return}//是否通过验证if (validator && !validator(value)) {  warn(\\\'Invalid prop: custom validator check failed for prop \\\"\\\' + name + \\\'\\\".\\\')}
      看下面两个例子:
      props: {    treeName: {        type: Number,        required: true,//是否必填    }}
      如果配置了 required ,并且没有传入值,那就会抛出警告:
      warn(\\\'Missing required prop: \\\"\\\' + name + \\\'\\\"\\\')
      再或者,在 props 中自己做了数据的验证:
        props: {    treeName: {        type: Number,        required: true,//是否必填        validator(val) {          return val >= 10        }    }}
        做了 props 的验证,并且没有通过,会抛出警告:
        warn(\\\'Invalid prop: custom validator check failed for prop \\\"\\\' + name + \\\'\\\".\\\')
        回到 initProps 方法中,接下来就是通过 shallowReactive 方法把 props 变成响应式数据:
        export function shallowReactive<T extends object>(target: T): T {  return createReactiveObject(    target,    false,    shallowReactiveHandlers,    shallowCollectionHandlers  )}
        返回的响应式数据会赋值到组件的实例上。
          instance.props = isSSR ? props : shallowReactive(props)//...instance.attrs = attrs
          这样 Props 就初始化完成了。咱们以后文章再深入去了解响应式逻辑。
          点击关注公众号,查看更多 Vue 的内容

          图片授权基于 www.pixabay.com 相关协议

          原创文章,作者:小道研究,如若转载,请注明出处:https://www.sudun.com/ask/34477.html

          (0)
          小道研究's avatar小道研究
          上一篇 2024年4月12日 上午11:23
          下一篇 2024年4月12日 上午11:25

          相关推荐

          发表回复

          您的邮箱地址不会被公开。 必填项已用 * 标注