New bee mall open source warehouse: github.com/newbee-ltd (connotation Vue 2.x and Vue 3.x H5 mall open source code)

Vue 3.x + Vant 3.x

Writing in the front

I have been thinking about this article for a long time, and I want to explain the knowledge points about JSX and VDOM in a more vernacular form. Read a lot of related content, most of the articles are based on the source code, the content can not say bad, but at least I think for beginners front end students, the content is hard. This article takes React as the entry point to analyze and understand JSX and virtual DOM. Of course, students of Vue technology stack can also see it. After all, these two frameworks learn from each other and learn from each other.

Again, this article understands, is friendly to the novice, if the big guy is confident enough, leave it at that. After reading the students think it is helpful, you can click a like, let me have the motivation to continue to write. In the comments section of the previous articles, there were several students who wanted to know more about other knowledge. I will remember all of them and wait for me to return to my hometown for the Spring Festival.

When I study a knowledge point, I have a habit of looking for answers with questions, so this article is no exception. We look at the article with the following questions:

  • JSXWhat is?
  • Use need notJSXWhat is the impact on development?
  • virtualDOMWhat does it look like? How do you render it realDOM ?
  • virtualDOMWhat is the meaning of existence?

The question is clear is the real strength, don’t always think about hanging the interviewer, what the interviewer did wrong. (escape)

What is the JSX

It is a syntactic extension to JS. Here’s how it’s officially defined:

JSX is a syntax extension to JavaScript, but it has the full functionality of JavaScript.

In the React project we wrote JSX as follows:

const App = <div>
  test
</div>
Copy the code

React uses a virtual DOM to render pages. At this point, the virtual DOM does not seem to be visible. First, Babel will mutate JSX syntax into the React. CreateElement () form for us.

Let’s verify that the page will render properly if we write the React. CreateElement function directly. Let’s build a React base project using create-react-app and modify index.js as follows:

import React from 'react'
import ReactDOM from 'react-dom'

const App = () = > {
  return React.createElement(
    "div",
    {
      className: "app"
    },
    "father",
    React.createElement(
      "div".null."child"
    )
  )
}

ReactDOM.render(<App />.document.getElementById('root'))
Copy the code

The browser displays the following:

Let’s print App and App() in index.js to see what the difference is, as follows:

console.log('the App:, App)
console.log('App () :, App())
Copy the code

The print result is as follows:

As you can see here, when the App is not executing, it is a normal function, so we should call it “Componnet”, and the result is the virtual DOM we want. We can call it “ReactElement”.

This ReactElement object instance is essentially a description of the DOM in the form of a JavaScript object, the virtual DOM.

From the virtual DOM above, we can deduce that the real DOM looks like this:

<! -- outermost div-->
<div>
  <! -- first child -->
	father
  <! The second child node is wrapped by the div and contains the child-->
  <div>child</div>
</div>
Copy the code

So at this point we can confidently say that we can develop projects without JSX. As long as you’re invincible, use React. CreateElement to write the tag and its methods, styles, custom attributes, etc. I’m sure I’m not that invincible, but I’m a big idiot.

How to render the virtual DOM into the real DOM

Let’s continue with the demo project we built with create-react-app and modify index.js as follows:

import React from 'react'

// JSX writes the React component
const App = () = > <div>
  <div>Brother 13: What's your sign?</div>
  <div>Nick Chen: I made the reservation for you.</div>
</div>

// Custom virtual DOM to real DOM function MyRender.
// vnode: virtual DOM node; Root: the inserted parent node (note that this is not necessarily the app node in index.html).
const MyRender = (vnode, root) = > {
  // If no root node is passed in, no execution is performed.
  if(! root) {return
  }
  let element // Declare an empty variable to store the node information below.
  if(vnode.constructor ! = =Object) {
    // If the vNode type is not Object, then it is a normal character with no label wrapped, and the value element is assigned directly.
    element = document.createTextNode(vnode);
  } else {
    // Otherwise, it is a type with a tag wrapped around it. The createElement event creates a new tag with the name of the tag being the type attribute value.
    element = document.createElement(vnode.type);
  }
  // Insert the parent node root.
  root.appendChild(element)
  
  // If vnode has the children attribute, then recurse.
  if (vnode.props && vnode.props.children) {
    const childrenVNode = vnode.props.children
    // Check if it is an array, if it is, then go to the forEach loop and execute MyRender
    if (Array.isArray(childrenVNode)) {
      childrenVNode.forEach((child) = > {
        MyRender(child, element)
      })
    } else {
      // Otherwise, execute MyRender directly
      MyRender(childrenVNode, element)
    }
  }
}

// Initialize the MyRender function, noticing that the first argument is passed in the ReactElement, which is the virtual DOM.
MyRender(App(), document.getElementById('root'))
Copy the code

Code parsing has been written in the above code gaze, each line is explained, carefully read, not difficult to understand. In fact, it is to try to render the virtual DOM into the real DOM through JS method, and then insert it into the root node. Let’s run the project with NPM Run start to see if the browser can render the real DOM:

Ho! ~ ~ (shy). You can even give “thirteen brother” to the “green”, click “Nick Chen” to some methods, the code is as follows:

const App = () = > <div>
  <div className='shisan' style={{ color: 'green' }}>Brother 13: What's your sign?</div>
  <div onClick={()= >Nick Chen: I made the reservation for you.</div>
</div>.let element
if(vnode.constructor ! = =Object) {
  element = document.createTextNode(vnode)
} else {
  element = document.createElement(vnode.type)
  // Add the click event
  if (vnode.props.onClick) {
    element.addEventListener('click'.() = > {
      vnode.props.onClick()
    })
  }
  // Add styles
  if (vnode.props.style) {
    Object.keys(vnode.props.style).forEach(key= > {
      element.style[key] = vnode.props.style[key]
    })
  }
  // Add the class name
  if (vnode.props.className) {
    element.className = vnode.props.className
  }
}
...
Copy the code

The browser displays the following:

Reactdom.render is not as simple as I wrote above, and the source code involved is quite large. This is just a small use case where I simply convert the virtual DOM into the real DOM. The React event mechanism, which is implemented separately, is not as simple as described above.

Significance of the virtual DOM

This from my personal point of view, there are the following points.

Is DOM more convenient

Direct manipulation of the DOM and indirect manipulation of JS to control the virtual DOM seem to me to have their own advantages.

🤔 Think about the performance overhead associated with the browser redrawing the page, despite the frequent direct manipulation of the DOM. However, when the project reaches a certain level of complexity, the diff algorithm of the virtual DOM can also impose a performance overhead on the browser, which I don’t have the data to go by. (escape)

The development of great

But from a development experience perspective, you have to admire this new development model. You can just write a function method and render it into a page, which is an important help in modularizing and componentizing your project.

cross-platform

In my opinion, this is the place where virtual DOM can be played to the extreme. Everyone should have heard that uni-app, Taro and other third-party solutions can run a set of code multiple times, but it is the credit of virtual DOM that they are far away. In the above code, I simply convert the virtual DOM into real DOM by writing MyRender function, not simply to let you understand this ability, but through this method mapping, in fact, we can also use other complex operations to transform the virtual DOM into small programs (major platforms), App and other code forms.

conclusion

This article also works well from the perspective of Vue, so I think there is no framework for technical things. What the framework does for us is essentially the same. I’m going to say that again, front-end knowledge is so much, the key is whether you can use that knowledge to create more valuable things, such as Yuyuxi, Dan, these big guys.