vue explore: vue component and extend

View component extend 与 View

To understand why the principle vue registered components

When thinking form integrated solutions, we know that, when configured to generate json form components, always to find the corresponding component by component type and form one correspondence, that is, before declaring the json form type, need to be developed in advance corresponding components, assembly or dynamic loading. In the framework of vue, you want to do continuous integration, the component may be declared as global components, and then converted into json assembly's time to load the corresponding components by name. But this flaw is not dynamic to the third-party components to mount public properties and events; the design point of view, the function extension assembly converges to a unified entrance, and then with the ability to dynamically instantiate vue components, this is conducive to follow-up continuous integration, reduce the side effects on development, the development of ideas throughout the library's control.

Vue.extend

Vue.extend(extendOptions)

By calling vue.extend to return a subclass of vue

function extend(extendOptions){
    extendOptions = extendOptions || {}
    // this->vue
    const Super = this
    const SuperId = Super.cid
    // 使用父类的id作为缓存的key
    // 只要父类id相同,每次调用会返回相同的子类
    const cachedCtors = extendOptions._Ctor || (extendOptions._Ctor = {})
    if (cachedCtors[SuperId]) {
      return cachedCtors[SuperId]
    }   
    // 对name命名方式进行校验
    // /^[a-zA-Z][\w-]*/
    const name = extendOptions.name || Super.options.name
    if (process.env.NODE_ENV !== 'production' && name) {
      validateComponentName(name)
    }

    const Sub = function VueComponent (options) {
      // vue._init
      this._init(options)
    }
    // 继承父类构造函数
    Sub.prototype = Object.create(Super.prototype)
    Sub.prototype.constructor = Sub
    Sub.cid = cid++
    // 合并父类的options
    Sub.options = mergeOptions(
      Super.options,
      extendOptions
    )
    Sub['super'] = Super

    // For props and computed properties, we define the proxy getters on
    // the Vue instances at extension time, on the extended prototype. This
    // avoids Object.defineProperty calls for each instance created.
    // 初始化props
    // 将props挂载在原型对象的_props属性下
    if (Sub.options.props) {
      initProps(Sub)
    }
    // 初始化computed
    // 将初始化computed挂载在原型对象下
    if (Sub.options.computed) {
      initComputed(Sub)
    }

    // allow further extension/mixin/plugin usage
    // 复制父类的静态方法
    Sub.extend = Super.extend
    Sub.mixin = Super.mixin
    Sub.use = Super.use

    // create asset registers, so extended classes
    // can have their private assets too.
    ASSET_TYPES.forEach(function (type) {
      Sub[type] = Super[type]
    })
    // enable recursive self-lookup
    if (name) {
      Sub.options.components[name] = Sub
    }

    // keep a reference to the super options at extension time.
    // later at instantiation we can check if Super's options have
    // been updated.
    Sub.superOptions = Super.options
    Sub.extendOptions = extendOptions
    Sub.sealedOptions = extend({}, Sub.options)

    // cache constructor
    cachedCtors[SuperId] = Sub
    return Sub
  }
}
复制代码

First, to the direct calling vuea constructor to instantiate the component to compare, vue.extenddo first level cache to check at the beginning, if it extendOptionsalready exists constructor components, it will return directly to the constructor, the same components to avoid repetitive building element Builder function, while using the parent class id as the standard cache.

When a cache miss, will enter the process of creating a component generator function, first check the component names, names that start with the first letter must be uppercase and lowercase, follow-up support case underscore character (_) and line spacing (-).

After checking by name, declare a component of the constructor:

const Sub = function VueComponent (options) {
  // Vue.prototype._init
  this._init(options)
}
复制代码

Let Sub function prototype inheritance by the parent class (Vue), and passed extendOptionsto the parent class optionsmerging configuration items, and then save the constructor of the parent class to the superproperty.

When optionsthe mount propsand computedwhen other attributes, needs to be handled separately, the internal details and results of the processing in the subsequent vue探究do depth discussion articles.

When the parent class inherited by the prototype, the initialization propsand computedafter the member attributes, inherited static methods need parent class, such as mixin、extend、use、component、directive、filterand the like.

Finally, in the new subclass constructor superOptions、extendOptions、sealedOptionsto prepare instantiated when used, and then the newly generated cache subclass (assembly constructor).

Overall, vue.extend method essentially creates a Sub function, and inherits the parent (or parent components Vue constructor) associated property or method.

Vue.component

Call component registered a local or global components, and set the alias component.

// 在Vue中,component、filter、directive是混合在一起实现的,这里拆开
Vue.options['component'] = Object.create(null)

Vue.component = function(id, definition){
    if(!definition){
        return this.options['components'][id]
    }else{
        if(isPlainObject(definition)){
            definition.name = definition.name || id
            definition = Vue.extend(definition)
        }
        this.options['components'][id] = definition
        return definition
    }
}
复制代码

component method call to extend essentially method of constructing a subclass, the subclass and stores the corresponding key components of the following options, in the SFCregistration of.

The article is subject to error, please understand, I hope you can let me know

Please indicate the source

Reproduced in: https: //juejin.im/post/5cf7a951f265da1b83337c86

Guess you like

Origin blog.csdn.net/weixin_33912453/article/details/91420323