Summary of React study notes (2)

1. The use of props in React


On the component, the declared property will be placed directly in the props property of the instance object.

In this way, the value passed by the external component can be called directly.

<script type="text/babel">
    // 创建组件
    class Person extends React.Component{
    
    
        render() {
    
    
            console.log(this)
            let {
    
    name,age,sex} = this.props
            return (
                <div>
                    <ul>
                        <li>姓名:{
    
    name}</li>
                        <li>性别:{
    
    age}</li>
                        <li>年龄:{
    
    sex}</li>
                    </ul>
                </div>
            );
        }
    }
    // 渲染组件到页面
    ReactDOM.render(<Person name="tom" age="18" sex="男"/>,document.getElementById('test'))
</script>

** …xxx are called spread operators: **

  • Note: Spread operator, cannot spread objects!
    insert image description here

For objects, the spread operator can be used to perform shallow copy and merge operations.
insert image description here


This can be used in React, because babel and react are capable of processing operations!

insert image description here


There are two ways to write props: (Just know, the first one has been deprecated.)

  • Note: The case of propsTypes of Person.propTypes and PropTypes.string. Easy to write wrong!
    insert image description here

2. React limits props


To limit the props of components, you need the prop-types.js function package.

Introduce prop-types.js: used to restrict component label properties.

  • Step 1: Import prop-types.js.
  • Step 2: Configure Person.propTypes = {} to define the property type, whether it is required, etc.
  • Step 3: Configure Person.defaultProps = {} default value.
<body>
    <!-- 1. 引入react核心库 -->
    <script type="text/javascript" src="../js/react.development.js"></script>

    <!-- 2. 引入react-dom,用于支持react操作DOM -->
    <script type="text/javascript" src="../js/react-dom.development.js"></script>

    <!-- 3. 引入babel,用于将jsx转为js -->
    <script type="text/javascript" src="../js/babel.min.js"></script>

    <!-- 4.引入prop-types.js:用于对组件标签属性进行限制 -->
    <script type="text/javascript" src="../js/prop-types.js"></script>

    <script type="text/babel">
        // 创建组件
        class Person extends React.Component{
    
    
            render() {
    
    
                console.log(this)
                // 调用的时候直接调用props里面的函数。
                this.props.speak()
                let {
    
    name,age,sex} = this.props
                return (
                    <div>
                        <ul>
                            <li>姓名:{
    
    name}</li>
                            <li>性别:{
    
    age + 10}</li>
                            <li>年龄:{
    
    sex}</li>
                        </ul>
                    </div>
                );
            }
        }

        // react底层会自动走propTypes,来对Person的props进行限制。
        // 可以设置类型,设置是否必须等等。
        Person.propTypes = {
    
    
            name:PropTypes.string.isRequired,
            sex:PropTypes.string,
            age:PropTypes.number,
            speak:PropTypes.func // 如果传入函数就是func
        }
        // 指定默认标签属性值,也就是设置属性默认值。
        Person.defaultProps = {
    
    
            sex: '不男不女',
        }

        function speak(){
    
    
            console.log('我说话了')
        }

        const p = {
    
    name:'老刘',age:18}
        // 渲染组件到页面
        ReactDOM.render(<Person {
    
    ...p} speak={
    
    speak}/>,document.getElementById('test'))
    </script>
</body>

3. React props are read-only (know what effect the modification is in!)


React props are read-only.

insert image description here

Understand: what does modification mean, it can be understood as the meaning of reassignment. It is the address that has changed.
insert image description here

4. React props shorthand


In fact, the following code is to add properties to Person, so it can be directly abbreviated to the Person class:

// react底层会自动走propTypes,来对Person的props进行限制。
// 可以设置类型,设置是否必须等等。
Person.propTypes = {
    
    
    name:PropTypes.string.isRequired,
    sex:PropTypes.string,
    age:PropTypes.number,
    speak:PropTypes.func // 如果传入函数就是func
}
// 指定默认标签属性值,也就是设置属性默认值。
Person.defaultProps = {
    
    
    sex: '不男不女',
}

The short form is as follows:

class Person extends React.Component{
    
    
	// 定义props属性
    static propTypes = {
    
    
        name:PropTypes.string.isRequired,
        sex:PropTypes.string,
        age:PropTypes.number,
        speak:PropTypes.func // 如果传入函数就是func
    }
	// 定义props默认值
    static defaultProps = {
    
    
        sex: '不男不女',
    }

    render() {
    
    
        // 调用的时候直接调用props里面的函数。
        this.props.speak()
        let {
    
    name,age,sex} = this.props
        return (
            <div>
                <ul>
                    <li>姓名:{
    
    name}</li>
                    <li>性别:{
    
    age + 10}</li>
                    <li>年龄:{
    
    sex}</li>
                </ul>
            </div>
        );
    }
}

5. Notes on constructors and props in class components


The class component constructor, in react, only uses the following two cases:

  • The internal state is initialized by assigning an object to this.state.
  • Bind instance for event handler function.

be careful:

  • If the constructor does not need to be initialized, it has no effect.

  • If you need to initialize the constructor and want to access props through this in the constructor, you must accept props and implement super(props), otherwise you can't get props!

Constructors are almost never used in development!

6. Functional components use props


Three major properties: state, props, refs.

Functional components can only use props, neither of the other two.

Props are passed as parameters, and the props property can be defined directly outside.

<script type="text/babel">
    function Person(props){
    
    
        const {
    
    name,sex,age} = props
        return (
            <ul>
                <li>姓名:{
    
    name}</li>
                <li>性别:{
    
    sex}</li>
                <li>年龄:{
    
    age + 1}</li>
            </ul>
        )
    }
    Person.propType = {
    
    
        name:PropTypes.string.isRequired,
        sex:PropTypes.string,
        age:PropTypes.number
    }
    Person.defaultProps = {
    
    
        sex:'不男不女',
        age:18
    }
    ReactDOM.render(<Person name="zhangsan" age={
    
    1}/>,document.getElementById('test'))
</script>

7. The refs attribute in the form of a class component string


The passbook of the refs attribute of the class component corresponds to the ref identifier, which is similar to the id.
insert image description here

The corresponding dom node can be manipulated through the refs attribute:

<script type="text/babel">
    class Demo extends React.Component {
    
    

        // 展示左侧输入框的数据
        showData = ()=>{
    
    
            const {
    
    input1} = this.refs
            alert(input1.value)
        }
        // 展示右侧输入框的数据
        showDate2 = () => {
    
    
            const {
    
    input2} = this.refs
            alert(input2.value)
        }

        render() {
    
    
            return (
                <div>
                    <input ref="input1" type="text" placeholder="点击按钮提示数据"/>
                    <button ref="button1" onClick={
    
    this.showData}>点我提示左侧的数据</button> &nbsp;
                    <input ref="input2" onBlur={
    
    this.showDate2} type="text" placeholder="失去焦点提示数据"/>
                </div>
            );
        }
        
    }
    // 渲染组件到页面
    ReactDOM.render(<Demo/>,document.getElementById('test'))
</script>

The official explanation for refs in string form:

  • There are some efficiency issues.
    insert image description here

8. React's callback form ref


It is implemented in the form of a callback function:

// 通过回调函数的形式来给this赋值。
render() {
    
    
    return (
        <div>
            <input ref={
    
    c=>this.input1 = c} type="text" placeholder="点击按钮提示数据"/>
        </div>
    );
}

Case:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>jsx语法规则</title>
</head>
<body>
    <!-- 准备好一个容器 -->
    <div id="test"></div>

    <!-- 1. 引入react核心库 -->
    <script type="text/javascript" src="../js/react.development.js"></script>

    <!-- 2. 引入react-dom,用于支持react操作DOM -->
    <script type="text/javascript" src="../js/react-dom.development.js"></script>

    <!-- 3. 引入babel,用于将jsx转为js -->
    <script type="text/javascript" src="../js/babel.min.js"></script>

    <!-- 4.引入prop-types.js:用于对组件标签属性进行限制 -->
    <script type="text/javascript" src="../js/prop-types.js"></script>

    <script type="text/babel">
        class Demo extends React.Component {
      
      

            // 展示左侧输入框的数据
            showData = ()=>{
      
      
                const {
      
      input1} = this
                alert(input1.value)
            }
            // 展示右侧输入框的数据
            showDate2 = () => {
      
      
                const {
      
      input2} = this
                alert(input2.value)
            }

            // 通过回调函数的形式来给this赋值。
            render() {
      
      
                return (
                    <div>
                        <input ref={
      
      c=>this.input1 = c} type="text" placeholder="点击按钮提示数据"/>
                        <button onClick={
      
      this.showData}>点我提示左侧的数据</button> &nbsp;
                        <input onBlur={
      
      this.showDate2} ref={
      
      c=>this.input2 = c}  type="text" placeholder="失去焦点提示数据"/>
                    </div>
                );
            }

        }
        // 渲染组件到页面
        ReactDOM.render(<Demo/>,document.getElementById('test'))
    </script>
</body>
</html>

9. The comment form of jsx


Convert it to a js expression by using {} and comment it out with /**/.

render() {
    
    
    return (
        <div>
            <input ref={
    
    c=>this.input1 = c} type="text" placeholder="点击按钮提示数据"/>
            {
    
    /*<button onClick={this.showData}>点我提示左侧的数据</button> &nbsp;*/}
            <input onBlur={
    
    this.showDate2} ref={
    
    c=>this.input2 = c}  type="text" placeholder="失去焦点提示数据"/>
        </div>
    );
}

9. The number of calls of React's callback form ref


Inline functions are functions that are defined directly above the label.
insert image description here

For the inline function callback of ref, the second call that will occur when updating the dom:

  • When the page is initialized for the first time, the callback function in the ref will be called once.
  • After that, as long as the render function of the class component is called (to update the dom), the function in the ref in the update will be called twice, the first parameter c(currentNode) is null, and the second parameter c(currentNode) will be the current node. The first time it is null is because it needs to be emptied.

insert image description here


The above function has a corresponding solution, you can put the function into the this class instance object, so that you can call it directly. No need to write inline functions anymore.

insert image description here

Both are fine, but know the difference.

9. Use of createRef API


React.createRef() can return a container that can store the node identified by ref.

Note: React.createRef() can only lock one node, dedicated to special personnel!

class Demo extends React.Component {
    
    
    /*
        React.createRef()调用后可以返回一个容器,该容器可以存储被ref所标识的节点,不过它只能锁定一个节点,专人专用!。
     */
    myRef = React.createRef()
    showData = ()=>{
    
    
        console.log(this.myRef.current)
    }
    render() {
    
    
        return (
            <div>
                <input ref={
    
    this.myRef} type="text" placeholder="点击按钮提示数据"/>
                <button onClick={
    
    this.showData}>点我提示左侧的数据</button>
            </div>
        );
    }
}
// 渲染组件到页面
ReactDOM.render(<Demo/>,document.getElementById('test'))

Principle: When you go to input ref={this.myRef}, it is detected that it is a container created by React.createRef(), and its own node will be stored in it.

Currently, a form for official use is recommended. But many developers still use inline functions.

10. React's event handling process


React is by onXxx属性specifying the event handler function, pay attention to the middle case.

  • React uses custom (synthetic) events [for better compatibility] instead of using native DOM events.
  • Events in React are handled through event delegation (delegated to the outermost element of the component).
    所谓的事件委托将事件像冒泡一样委托给了最外层的元素。

11. Do not overuse Refs


Get the DOM element object where the event occurred through event.target:

The official one is given 勿过度使用Refs. In fact, event.target can be used directly to obtain the current node in many cases.

insert image description here

12. React Uncontrolled Components


Uncontrolled components are pay-as-you-go:

  • Just like the input input below, clicking on the login will take the onSubmit event of react.
<script type="text/babel">
    // 创建组件
    class Login extends React.Component{
    
    

        handlerSubmit = (event)=>{
    
    
            const {
    
    username,password} = this
            alert(`${
      
      username.value},${
      
      password.value}`)
            // 阻止form表单提交
            event.preventDefault() //组织form表单默认事件。
        }

        render() {
    
    
            return (
                <div>
                    <form action="http://www.itholmes.com" onSubmit={
    
    this.handlerSubmit}>
                        用户名:<input ref={
    
    c => this.username = c} type="text" name="username"/>
                        密码:<input ref={
    
    c => this.password = c} type="password" name="password"/>
                        <button>登录</button>
                    </form>
                </div>
            );
        }
    }
    // 渲染组件
    ReactDOM.render(<Login/>,document.getElementById('test'))
</script>

13. Controlled Components in React


In fact, the controlled component is a bit like the two-way binding effect of vue, just like the following figure is bound to the state through the onChange event of react:

insert image description here

<script type="text/babel">
    // 创建组件
    class Login extends React.Component{
    
    

        // 初始化状态
        state = {
    
    
            username:'',
            password:''
        }

        saveUsername = (event)=>{
    
    
            this.setState({
    
    username : this.username.value})
        }

        savePassword = (event)=>{
    
    
            this.setState({
    
    password:this.password.value})
        }

        handlerSubmit = (event)=>{
    
    
            // 阻止form表单提交
            event.preventDefault() //组织form表单默认事件。
            const {
    
    username,password} = this.state
            console.log(`${
      
      username},${
      
      password}`)
        }

        render() {
    
    
            return (
                <div>
                    <form action="http://www.itholmes.com" onSubmit={
    
    this.handlerSubmit}>
                        用户名:<input onChange={
    
    this.saveUsername} ref={
    
    c => this.username = c} type="text" name="username"/>
                        密码:<input onChange={
    
    this.savePassword} ref={
    
    c => this.password = c} type="password" name="password"/>
                        <button>登录</button>
                    </form>
                </div>
            );
        }
    }
    // 渲染组件
    ReactDOM.render(<Login/>,document.getElementById('test'))
</script>

It is recommended to use controlled components. Controlled components rarely use the ref attribute and are convenient.

14. Higher-order functions and currying

14.1 Higher-order functions and the concept of currying


insert image description here

Parameters like Promise, setTimeout, arr.map(), etc. are all functions, so they are all higher-order functions!

insert image description here
The following react code is implemented by currying.


Implementation without currying:
insert image description here

14.2 Code simplification for react


Note: The two forms below the event are different!

  • Without parentheses, a function is given to the onChange event.
  • Adding parentheses is to give the return value of a function to the onChange event, which is a misunderstanding!
    insert image description here

For the above reasons, events can be assigned by return function in the future, and the code can be simplified:
insert image description here

<script type="text/babel">
    // 创建组件
    class Login extends React.Component{
    
    

        // 初始化状态
        state = {
    
    
            username:'',
            password:''
        }

        // 通过return函数来赋值给onChange事件,
        saveFormData = (dataType)=>{
    
    
            console.log(dataType)
            return (event)=>{
    
    
                // fixme [dataType] 读取对象dataType的值,对象的基本用法!!
                this.setState({
    
    [dataType]:event.target.value})
                console.log('dataType',dataType)
                console.log('value',event.target.value)
            }
        }

        handlerSubmit = (event)=>{
    
    
            // 阻止form表单提交
            event.preventDefault() //组织form表单默认事件。
            const {
    
    username,password} = this.state
            console.log(`${
      
      username},${
      
      password}`)
        }

        render() {
    
    
            return (
                <div>
                    <form action="http://www.itholmes.com" onSubmit={
    
    this.handlerSubmit}>
                        用户名:<input onChange={
    
    this.saveFormData('username')} type="text" name="username"/>
                        密码:<input onChange={
    
    this.saveFormData('password')} type="password" name="password"/>
                        <button>登录</button>
                    </form>
                </div>
            );
        }
    }
    // 渲染组件
    ReactDOM.render(<Login/>,document.getElementById('test'))
</script>

Guess you like

Origin blog.csdn.net/IT_Holmes/article/details/126904218