Create-react-app scaffolding installation and start-up

Create-react-app scaffolding installation

Install with CNPM (fast download)

npm config set registry registry.npm.taobao.org

Verify the configuration by performing the following steps

npm config get registry

Mirror change succeeded

Then run sudo CNPM I -g create-react-app // to grant pipeman permission to install CNPM globally

NPM install

npm i -g create-react-app

Create-react-app –version Check whether the installation is successful (if there is a version number, it is successful)

Create projects with scaffolding

The create – react – app project name

Example Creating 01.base

create-react-app 01.base
Copy the code

NPM or YARN Start (whichever is recommended yarn) starts the project

yarn start

Write the React project page

1. Delete all files in SRC directory.

2. Create an index.js file (this is the entry file for the project)

React-dom module (create-react-app)

4. Insert the React component with the Render method of ReactDom

The index. The js code

// Project entry file
import React from 'react';
import ReactDom from 'react-dom';

const ele = <h2>hello React</h2>;
ReactDom.render(ele,document.querySelector('#root'))
Copy the code
Here #root is a tag in the index.html directory of the public directory

JSX introduction and template syntax rendering

What is the JSX

Ele in the index.js file above is a JSX object

JSX==JavaScript+Xml object virtual Dom element

Rendering of template syntax

You can use variables and functions in JSX just by enclosing them in {} (vue uses double brace interpolation)

function findPeople(user){
  return `${user.name}Your age:${user.age}`;
}
const user = {
  name:'QaQ'.age:'20'
}
const ele = <h2>hello {findPeople(user)}</h2>;
ReactDom.render(ele, document.querySelector('#root'))
Copy the code

It is also possible to use a variable or function enclosed in a closing tag for the first argument under the reactdom.render method

function findPeople(user){
  return `${user.name}Your age:${user.age}`;
}
const user = {
  name:'QaQ'.age:'20'
}
function getPeople(user){
  if(user){
    return <h1>hello,{findPeople(user)}</h1>;
  }
  return <h1>hello,stanger</h1>
}
ReactDom.render(<div>{getPeople(user)}</div>.document.querySelector('#root'))
Copy the code

When the getPeople argument has a value it will appear as if there were no arguments

React Update mechanism

React only updates what it needs to update

function tick(){
  const element = (
    <div>
      <h1>Hello React</h1>
      <h2>{new Date().toLocaleTimeString()}</h2>
    </div>
  )
  ReactDom.render(element,document.querySelector('#root'));
}

setInterval(tick, 1000);
Copy the code

React traversal binding and filtering

Traverse the binding

Create a JSX element that uses the map method to traverse the element (foreach does not return map)

Be sure to bind a key (key is a value that identifies uniqueness, see :key in VUE)

Key ={key value}

const arr = [1.2.3.4.5];
const ele = (
  <ul>{arr.map((item, index) => {// Loop bound JSX elements must have a key attribute to distinguish between different elements or return an error<li key={index}>{item}</li>
    })}
  </ul>
)
ReactDom.render(ele, document.querySelector('#root'))
Copy the code

filter

In the same way, the filter method does not provide a return value, so use the map method. We can use the ternary operator null if it does not meet the condition. You can also operate with an if statement

const goods = [
  { id: 1.price: 1000.title: 'iPhone5' },
  { id: 3.price: 1400.title: 'iPhone7' },
  { id: 5.price: 1600.title: 'iPhone9' },
  { id: 6.price: 1700.title: 'iPhone10'},]const filterEle = (
  <ul>
    {goods.map((item,index)=>{
      return (item.price > 1400) ? <li key={item.id}>{item.title} </li> : null;
    })}
  </ul>
)
ReactDom.render(filterEle, document.querySelector('#root'))
Copy the code

Two ways to create components

1. Function declaration

  • The component name must start with a capital letter, otherwise an error will be reported

  • A function declaration, also called a functional component, is essentially a function

  • There must be a return to return a JSX element

  • The first argument in reactdom.render directly specifies the component to render with < function declared component name >

  • The first argument in reactdom.render defines the property (name in the following example), which is props to receive in the function component argument, and props to be used in JSX. Property name to get the property value

function Welcome(props){
   The component declared by the current function must have a return value
   return <h2>Hello {props.name}</h2>
}
ReactDom.render(<Welcome name='Welcome'/>.document.querySelector('#root'))
Copy the code

2. Class declarations (most commonly used in real projects)

  • Extends React.Component{}

  • React.componentit is a base class from which components declared by utility classes must inherit

  • There must be a render function that returns a JSX element

  • Use the this.props. Property name to get the property value defined in the first parameter of reactdom. render

  • If constructor must have props and super must inherit the props property

class App extends React.Component {
  // If constructor must have props and super must inherit the props attribute
  // constructor(props){
  // super(props);
  // }
  // You must use the render function to render the virtual DOM into the real DOM
  render() {
    // It passes the properties received by JSX to the component as a single object, called props
    return <h2>App {this.props.name}</h2>}}Copy the code

Import components from other files

Create app.js at the same level as index.js. Here’s an example of creating a component using the class method above

  • React.component.react module because react.component.react module can also directly deconstruct Component {Component}
  • Throw the component with Export Default
import React,{Component} from 'react'
export default class App extends Component {
  render() {
    return <h2>App {this.props.name}</h2>}}Copy the code

Introduce the APP module under index.js

import App from './App' 
Copy the code

You can then directly render the App component

Reusable components

What is a reusable component

    1. Consolidation of multiple components, such as calling the same component twice or more
    1. When the structure is very complex, components need to be broken down into small parts
    1. There will be parent-child data transfer

Use of reusable components

  1. If you have a button button that needs to be reused, write a MyBtn component to return a button label
  2. Use a reusable component as a label in JSX for the component that needs it
  3. If you want to get the value of the parent component, you can mount properties in the child tag of the parent component
  4. The child component gets the property value using the this.props. Property name
import React,{Component} from 'react'
class MyBtn extends Component {
  render() {
    return (
      <div>
        <button>{this.props.title}</button>
      </div>); }}export default class App extends Component {
  render() {
    return (
      <div>
        <h2>App {this.props.name}</h2>
        <MyBtn title='submit'></MyBtn>
        <MyBtn title='change'></MyBtn>
        <MyBtn title='delete'></MyBtn>
      </div>)}}Copy the code

How do I split components in React projects

If there is an App component with a comment block (comment), which contains the user information block (userinfo), userinfo has the username block (username), so the App component will look very long, we need to split the component for later maintenance. As shown below

// APP=>Comment=>userinfo=>username
export default class App extends Component {
  // If constructor must have props and super must inherit the props attribute
  constructor(props){
    super(props);
    this.user = {
      name:'qlq'.content:'Here's the React component.'.date:new Date().toLocaleTimeString()
    }
  }
  render() {
    return (
      <div>
        <div className="comment">
          <div className="userinfo">
            <div className="username">Name: {this. User. The name}</div>
          </div>
          <div className="comment-content">{this.user.content}</div>
          <div className="conmment-date">{this.user.date}</div>
        </div>
      </div>)}}Copy the code
  • Break it down from large to small and the largest div here is comment so let’s create a comment component
  • Use the this.props. User. Property name to get the required property value
class Comment extends Component {
  render() {
    return (
      <div className="comment">
        <div className="userinfo">
          <div className="username">Name: {this. Props. User. The name}</div>
        </div>
        <div className="comment-content">{this.props.user.content}</div>
        <div className="conmment-date">{this.props.user.date}</div>
      </div>); }}export default class App extends Component {
  constructor(props){
    super(props);
    this.user = {
      name:'qlq'.content:'Here's the React component.'.date:new Date().toLocaleTimeString()
    }
  }
  render() {
    return (
      <div>
        <Comment user={this.user}></Comment>
      </div>)}}Copy the code

Continue to disassemble components by following these steps until they cannot be disassembled (the real situation does not need to be disassembled to such detail).

class MyBtn extends Component {
  render() {
    return (
      <div>
        <button>{this.props.title}</button>
      </div>); }}// APP=>Comment=>userinfo=>username
class CommentDate extends Component {
  render() {
    return (
      <div className="conmment-date">{this.props.user.date}</div>); }}class CommentContent extends Component {
  render() {
    return (
      <div className="comment-content">{this.props. Content}</div>); }}class Username extends Component {
  render() {
    return (
      <div className="username">Name: {this. Props. The name}</div>); }}class UserInfo extends Component {
  render() {
    return (
      <div className="userinfo">
        <Username name={this.props.user.name}></Username>
      </div>); }}class Comment extends Component {
  render() {
    return (
      <div className="comment">
        <UserInfo user={this.props.user}></UserInfo>
        <CommentContent {. this.props.user} ></CommentContent>
        <CommentDate user={this.props.user}></CommentDate>
      </div>); }}export default class App extends Component {
  constructor(props){
    super(props);
    this.user = {
      name:'qlq'.content:'Here's the React component.'.date:new Date().toLocaleTimeString()
    }
  }
  render() {
    return (
      <div>
        <Comment user={this.user}></Comment>
      </div>)}}Copy the code

Two techniques for passing values (detailed in the previous code)

  1. User ={this.props. User} {this.props. User} {this.props.

    Name ={this.props.user.name} on the parent component so that {this.props. Name} on the child component

  2. The same example can be used with destruct assignment {… This.props. User} so that {this.props. Name} can also be used directly in the child component.

Ps: The second technique works better

Component styles

Using the Comment component above as an example, if you want to style a div whose name is commet, you can create a style file: app.css

.comment{
  width: 500px;
  height:300px;
  border: 1px solid #eee;
}
Copy the code

Then import the style file in app.js

import './App.css'
Copy the code

The same goes for importing external images

Place the image in a directory and use imoort XXX form ‘path’ to use XXX

Parent and child components pass values

React value transfer rule: A one-way data flow rule that does not modify the values in the props being passed

The father the son

How does a parent component pass a value to a child component

Summary: Define the values to pass in the child tag of the parent component, which passes this.props. Property name Gets the property value

Child the parent

  1. The parent component defines a method to handle the value passed by the child component (add())
  2. In the parent component’s child tag, define methods to pass values to the child (add={this.add}).
  3. The child component defines an event-binding function (handleClick = ()=>{}) using this.props. Add (‘ value to pass ‘) to pass the value.
  4. JSX in the child component has an event binding function such as onClick={this.handleclick}

Ps: the event binding function in the child component must pay attention to the this pointer. Use the arrow function this to point to the context object to point to the child component. If you use the normal function, an error will be reported

Example: Get the value of the Comment component in the App component

class Comment extends Component {
  // Use the arrow function to point this to Comment or undefined
  handleClick = () = > {
    this.props.add('This is the value in the child component');
  }
  render() {
    return (
      <div className="comment">
        <button onClick={this.handleClick} >Child the parent</button>
      </div>); }}export default class App extends Component {
  constructor(props) {
    super(props);
  }
  add(val) {
    alert(val);
  }
  render() {
    return (
      <div>
        <Comment user={this.user} add={this.add}></Comment>
      </div>)}}Copy the code

The value passed by the alert child component when the button button is clicked

React state and change the method this points to

If the component is rendered and you want to modify the data in the view, change the state and rerender the component

Elsewhere than constructor, the only way to modify state is to call this.setState()

import React, { Component } from 'react'
export default class App extends Component {
  constructor(props){
    super(props);
    this.state = {
      count:0}}add(){
    // The only way to change the state is to call this.setState()
    this.setState({
      count:this.state.count+1})}render() {
    return (
      <div>
        <h2>{this.state.count}</h2>
        <button onClick={this.add}>Am I</button>
      </div>)}}Copy the code

But this will get an error because the “this” point in add refers to the Button tag, and the setState method is in the App component, so you need to change the “this” point

Modify this to point to

1. Constructor passes this to (in this case App) to this.add using the bind function

  constructor(props){...// Change this to point to App, pass to add, so this in add refers to App, otherwise this is undefined
    this.add = this.add.bind(this)}Copy the code

2. Use this.add.bind(this) for event-bound functions in tags.

<button onClick={this.add.bind(this> +)}1</button>
Copy the code

3. Use the arrow function in the function that binds the event (use the arrow function this to point, just like the this pointer in the parent component).

add = () = > {
      this.setState({
      count:this.state.count+1})}Copy the code

4. Use arrow functions in labels

<button onClick={(e) = >this. The add (e)} > I < / button >Copy the code

This method can also receive event objects in Add (e)

Use of the setState() method

SetState is an asynchronous operation that retrieves data before the operation, but not after the operation, in the same submethod. I can write it as a function

This.setstate ((prevState,prevProps)=>({object}),()=>(To operate on object after operation)

PrevState: indicates the previous status

PrevProps: Previous property

export default class App extends Component {
  constructor(props){
    super(props);
    this.state = {count:0}}add(e){
    this.setState((prevState,prevProps) = >({
      count: prevState.count + 1 
    }),() = >{
      // is a callback function that is executed after a state change
      console.log(this.state.count);
    })}
  render() {
    return (
      <div>
        <h2>{this.state.count}</h2>
        <button onClick={(e)= >This. The add (e)} > me</button>
      </div>)}}Copy the code

React lifecycle

1. Static defaultProps/constructor(props) {super(); This.state} initializes the default loading state

2.componentWillMount() The parent component will be mounted

3. The parent component is render

4.componentDidMount() Parent component is mounted

In the current method, make an Ajax request to get a data-driven view of the data

ShouldComponentUpdate (nextProps, nextState) Whether the component should be updated

Updated properties, status

Performance optimization points are important

Retrun true updates return false does not

The 6.componentWillUpdate() component will be updated

7. Render () parent component

The 8.componentDidUpdate() component has been updated

9.componentWillUnmount() component is uninstalled

If you have child components

ComponentWillReceiveProps (newProps) child components will accept the new properties

Implementation of controlled components

Controlled component: a component that is controlled by the state and needs to be bound to the state. Example: Input A value in the input box. Click the submit button to generate the corresponding value in the list

1. Set the default values

Set the default value this.state in constructor

  constructor(props){
    super(props);
    this.state = {
      val: ' '.// Enter the value of the box
      data: [] // The value of the form to render}}Copy the code

2. Bind values in labels

The input tag is bound with val

3. Use the (onChange) event to make a state change

Bind the onChange method

render() {
    return (
      <div>
        <input type="text" val={this.state.val} onChange={this.handleChange}/>
        <button onClick={this.handleClick}>Submit the val</button>
        <ul>
          {
            this.state.data && this.state.data.map((item,index)=>{
              return (
                <li key={index}>{item}</li>)})}</ul>
      </div>)}Copy the code

4. Inside the onChange method, change the default value val with this.setState

You can use e.target.value to get the value in the input field

  handleChange = (e) = >{
    let val = e.target.value;
    this.setState({
      val:val,
    })}
Copy the code

2. You can also get it by ref

  1. Add ref = ‘a’ to input tag
  2. Use this.refs.a.value in the handleChange method to get the value in the input box
  handleChange = (e) = >{
    // let val = e.target.value;

    let val = this.refs.a.value;
    this.setState({
      val:val,
    })}
Copy the code

5. HandleClick internal form update method

Check whether the input box has a value (this.state.val)

Create a new array with… This.state. data retrieves the previous data

New array push(this.state.val)

4. Use this.setState to change the data value in the state

  handleClick=() = >{
    if(this.state.val){
      let newArr = [...this.state.data];
      newArr.push(this.state.val);
      this.setState({
        data:newArr
      })
    }}
Copy the code

Use of forms

import React, { Component } from 'react';
class FormSimple extends Component {
  constructor(props){
    super(props);
    this.state ={
      username:' '.password:' '.selectArr:' '
    }
  }
  handleChange = (e) = >{
    this.setState({
      username:e.target.value
    })
  }
  handlePwd = (e) = > {
    this.setState({
       password: e.target.value
    })
  }
  handleSubmit = (e) = >{
    // Block the default event
    e.preventDefault();
    if(this.state.username && this.state.password && this.state.selectArr){
      // Send an Ajax request
      alert('Current user name:The ${this.state.username}Current user password:The ${this.state.password}Current hobbies:The ${this.state.selectArr}`)}else{
      alert(Please fill in the complete information);
    }
  }
  handleSelect = (e) = >{
    let newArr = [...this.state.selectArr];
    newArr.push(e.target.value);
    this.setState({
      selectArr:newArr
    })
  }
  render() {
    return (
      <form onSubmit={this.handleSubmit}>
        <p className="username">
          <label htmlFor="name">User name:</label>
          <input type="text" value={this.state.username} onChange={this.handleChange} id='name'/>
        </p>
        <p className="password">
          <label htmlFor="pwd">Password:</label>
          <input type="password" value={this.state.password} onChange={this.handlePwd} id='pwd'/>
        </p>My hobbies:<select value={this.state.selectArr} onChange={this.handleSelect}>
          <option value="Smoking">smoking</option>
          <option value="Drinking">drinking</option>
          <option value="Permed hair">Permed hair</option>
        </select>
        <br/>
        <input type="submit" value="Login" />
      </form>); }}export default FormSimple;
Copy the code