“This is the ninth day of my participation in the First Challenge 2022. For details: First Challenge 2022”

CreateElm function

Path: the core/vdom/patch. Js

The createElm function converts the VNode to the corresponding DOM Element, storing the DOM Element in the Element property of the object, but does not mount the created DOM Element to the node.

This function can be divided internally into three processes

Process 1

Execute the user-set init hook function

Code snippet

// Execute the user-set init hook function
    let i: any
    let data = vnode.data
    if(data ! = =undefined) {
      constinit = data.hook? .initif (isDef(init)) {
        init(vnode)
        data = vnode.data
      }
    }
Copy the code

parsing

  • Vnode. data This is the argument passed in when we create a vnode using the h function

    • Like this:vnode = h('div#container.xxx', 'Hello WorldAAAAAA')
    • Or this:h('p', {on: {click: eventHandler }}, 'World')

    And for h, you can look at the analysis of h that I wrote earlier

  • data.hook? Init is also something that we pass as users

    • hook? .initthe?isES chain judgment operator?
    data.hook? .init/ / equivalent to the
    data.hook && data.hook.init;
    Copy the code
  • IsDef (init) so that’s pretty simple, to determine if the user has anything to define init

  • Init (vNode) The init hook function allows users to make changes to the VNode, such as changing styles and other properties, before creating the actual DOM

Process 2

Convert the VNode to a real DOM object (instead of rendering to the page, the created object is mounted to the Element property of the VNode)

The code fragment

const children = vnode.children
const sel = vnode.sel
if (sel === '! ') {
      if (isUndef(vnode.text)) {
        vnode.text = ' '
      }
      vnode.elm = api.createComment(vnode.text!)
} else if(sel ! = =undefined) {... Middle omit}else {
  vnode.elm = api.createTextNode(vnode.text!)
}
Copy the code

parsing

  • childrenVariables are children of vNodes
  • selThe selector is
  • sel === '! 'The judgment here is a little bit weird
    • First let’s take a look at the format of our comments in HTML<! 1 - - - >
    • So that makes it clear that ifsel === '! 'The next step is to create the annotation node
  • sel ! == undefinedThe corresponding DOM element is created
  • elseCreate a text node

The process of 3

Procedure 3 is the simplest, returning vNode. elem directly, which returns the newly created DOM

conclusion

  • If the current element is a comment node, createComment is called to create a comment node, which is then mounted to vNode.elm

  • If there is no selector and just plain text, call createTextNode to create the text and mount it to vNode.elm

  • If there is a selector, the selector is parsed to get tag, ID, and class,

    1. Call createElement or createElementNS to generate the node and mount it to vnode.elm.

    2. Call create hook on Module, if there are children, iterate over all child nodes and create dom recursively with createElm. Mount the DOM to the current ELM through appendChild. If no children exists but text does, create text using createTextNode.

    3. Finally call create hook on the calling element and vNode that holds the Insert hook, because the insert hook will not be called until the DOM is actually mounted on the document. Using an array saves you from having to traverse the vNode tree when you actually need to call it.