React学习教程,介绍,基础概念,简介

时间:2024-12-18 22:20:48

格式化配置

目标任务: 基于vscode配置格式化工具,提高开发效率

  1. 安装vsCode prettier插件
  2. 修改配置文件
{
  "": true,
  // 修改注释颜色
  "": {
    "comments": {
      "fontStyle": "bold",
      "foreground": "#82e0aa"
    }
  },
  // 配置文件类型识别
  "": {
    "*.js": "javascript",
    "*.json": "jsonc",
    "*.cjson": "jsonc",
    "*.wxss": "css",
    "*.wxs": "javascript"
  },
  "": false,
  "": {
    "**/.DS_Store": true,
    "**/.git": true,
    "**/.hg": true,
    "**/.svn": true,
    "**/CVS": true,
    "**/node_modules": false,
    "**/tmp": true
  },
  // "": true,
  "": false,
  "": "prompt",
  "": false,
  "": 2,
  "": "500",
  "[json]": {},
  "": "on",
  "": true,
  "": "Monaco, 'Courier New', monospace, Meslo LG M for Powerline",
  "[html]": {
    "": "-language-features"
  },
  "": 16,
  "": 14,
  "": true,
  "": true,
  "": [
    ""
  ],
  // vue eslint start 保存时自动格式化代码
  "": true,
  // eslint配置项,保存时自动修复错误
  "": {
    "": true
  },
  "": true,
  // 让vetur使用vs自带的js格式化工具
  // uni-app和vue 项目使用
  "": "vscode-typescript",
  "": "remove",
  // // 指定 *.vue 文件的格式化工具为vetur
  "[vue]": {
    "": ""
  },
  // // 指定 *.js 文件的格式化工具为vscode自带
  "[javascript]": {
    "": "-language-features"
  },
  // // 默认使用prettier格式化支持的文件
  "": "-vscode",
  "": true,
  // 函数前面加个空格
  "": true,
  "": true,
  "": false,
  // eslint end
  // react
  // 当按tab键的时候,会自动提示
  "": true,
  "": true,
  "": {
    // jsx的提示
    "javascript": "javascriptreact",
    "vue-html": "html",
    "vue": "html",
    "wxml": "html"
  },
  // end
  "[jsonc]": {
    "": "-language-features"
  },
  // @路径提示
  "": {
    "@": "${workspaceRoot}/src"
  },
  "": "open",
  "": true,
  "": 1
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97

阶段小练习

在这里插入图片描述

React组件基础

组件概念
在这里插入图片描述

函数组件

目标任务: 能够独立使用函数完成react组件的创建和渲染

概念
使用 JS 的函数(或箭头函数)创建的组件,就叫做函数组件

组件定义与渲染

// 定义函数组件
function HelloFn () {
  return <div>这是我的第一个函数组件!</div>
}

// 定义类组件
function App () {
  return (
    <div className="App">
      {/* 渲染函数组件 */}
      <HelloFn />
      <HelloFn></HelloFn>
    </div>
  )
}
export default App
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16

约定说明

  1. 组件的名称必须首字母大写,react内部会根据这个来判断是组件还是普通的HTML标签
  2. 函数组件必须有返回值,表示该组件的 UI 结构;如果不需要渲染任何内容,则返回 null
  3. 组件就像 HTML 标签一样可以被渲染到页面中。组件表示的是一段结构内容,对于函数组件来说,渲染的内容是函数的返回值就是对应的内容
  4. 使用函数名称作为组件标签名称,可以成对出现也可以自闭合

类组件

目标任务: 能够独立完成类组件的创建和渲染
使用 ES6 的 class 创建的组件,叫做类(class)组件
组件定义与渲染

// 引入React
import React from 'react'

// 定义类组件
class HelloC extends  {
  render () {
    return <div>这是我的第一个类组件!</div>
  }
}

function App () {
  return (
    <div className="App">
      {/* 渲染类组件 */}
      <HelloC />
      <HelloC></HelloC>
    </div>
  )
}
export default App
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20

约定说明

  1. 类名称也必须以大写字母开头
  2. 类组件应该继承 父类,从而使用父类中提供的方法或属性
  3. 类组件必须提供 render 方法render 方法必须有返回值,表示该组件的 UI 结构
    函数组件的事件绑定
    目标任务: 能够独立绑定任何事件并能获取到事件对象e
  4. 如何绑定事件
    ● 语法
    on + 事件名称 = { 事件处理程序 } ,比如:<div onClick={ onClick }>
    ● 注意点
    react事件采用驼峰命名法,比如:onMouseEnter、onFocus
    ● 样例
// 函数组件
function HelloFn () {
  // 定义事件回调函数
  const clickHandler = () => {
    ('事件被触发了')
  }
  return (
    // 绑定事件
    <button onClick={clickHandler}>click me!</button>
  )
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  1. 获取事件对象
    获取事件对象e只需要在 事件的回调函数中 补充一个形参e即可拿到
// 函数组件
function HelloFn () {
  // 定义事件回调函数
  const clickHandler = (e) => {
    ('事件被触发了', e)
  }
  return (
    // 绑定事件
    <button onClick={clickHandler}>click me!</button>
  )
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

总结:
编写组件其实就是编写原生js类或者函数
定义状态必须通过state实例属性二等方法提供一个对象名称是state
修该state当中的人恶化属性都不可以直接赋值必须通过setState方法来自于继承得到
这里的this关键词很容易出现指向错误的问题
3. 传递额外参数
解决思路: 改造事件绑定为箭头函数 在箭头函数中完成参数的传递


import React from "react"

// 如何获取额外的参数?
// onClick={ onDel } -> onClick={ () => onDel(id) }
// 注意: 一定不要在模板中写出函数调用的代码 onClick = { onDel(id) }  bad!!!!!!

const TestComponent = () => {
  const list = [
    {
      id: 1001,
      name: 'react'
    },
    {
      id: 1002,
      name: 'vue'
    }
  ]
  const onDel = (e, id) => {
    (e, id)
  }
  return (
      <ul>
        {(item =><li key={}>
                {}
                <button onClick={(e) => onDel(e, )}>x</button>
           </li>
        ))}
      </ul>
  )
}

function App () {
  return (
    <div>
      <TestComponent />
    </div>
  )
}


export default App
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43

类组件的事件绑定

// 类组件中的事件绑定
// 整体的套路都是一致的 和函数组件没有太多不同
// 唯一需要注意的 因为处于class 类环境下 所以定义事件回调函数 以及 绑定它写法上有不同
// 定义的时候: class Fields语法  
// 使用的时候: 需要借助this关键词获取


// 注意事项: 之所以要采取class Fields写法是为了保证this的指向正确 永远指向当前的组件实例

import React from "react"
class CComponent extends  {
  // class Fields
  clickHandler = (e, num) => {
    // 这里的this指向的是正确的当前的组件实例对象 
    // 可以非常方便的通过this关键词拿到组件实例身上的其他属性或者方法
    (this)
  }

  clickHandler1 () {
    // 这里的this 不指向当前的组件实例对象  undefined 存在this丢失问题
    (this)
  }

  render () {
    return (
      <div>
        <button onClick={(e) => (e, '123')}>click me</button>
        <button onClick={this.clickHandler1}>click me</button>
      </div>
    )
  }
}

function App () {
  return (
    <div>
      <CComponent />
    </div>
  )
}

export default App

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43

组件状态

目标任务: 能够为组件添加状态和修改状态的值
一个前提:在React hook出来之前,函数式组件是没有自己的状态的,所以我们统一通过类组件来讲解
在这里插入图片描述

1. 初始化状态

● 通过class的实例属性state来初始化
● state的值是一个对象结构,表示一个组件可以有多个数据状态

class Counter extends  {
  // 初始化状态
  state = {
    count: 0
  }
  render() {
    return <button>计数器</button>
  }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  1. 读取状态
    ● 通过来获取状态
class Counter extends  {
  // 初始化状态
  state = {
    count: 0
  }
  render() {
    // 读取状态
    return <button>计数器{}</button>
  }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  1. 修改状态
    ● 语法
    ({ 要修改的部分数据 })
    ● setState方法作用
    a. 修改state中的数据状态
    b. 更新UI
    ● 思想
    数据驱动视图,也就是只要修改数据状态,那么页面就会自动刷新,无需手动操作dom
    ● 注意事项
    不要直接修改state中的值,必须通过setState方法进行修改
class Counter extends  {
  // 定义数据
  state = {
    count: 0
  }
  // 定义修改数据的方法
  setCount = () => {
    ({
      count:  + 1
    })
  }
  // 使用数据 并绑定事件
  render () {
    return <button onClick={}>{}</button>
  }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16

this问题说明
在这里插入图片描述
这里我们作为了解内容,随着js标准的发展,主流的写法已经变成了class fields,无需考虑太多this问题

React的状态不可变

目标任务: 能够理解不可变的意义并且知道在实际开发中如何修改状态
概念:不要直接修改状态的值,而是基于当前状态创建新的状态值

  1. 错误的直接修改
state = {
  count : 0,
  list: [1,2,3],
  person: {
     name:'jack',
     age:18
  }
}
// 直接修改简单类型Number
++
++
 += 1
 = 1

// 直接修改数组
(123)
(1,1)

// 直接修改对象
 = 'rose'
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  1. 基于当前状态创建新值
({
    count:  + 1
    list: [..., 4],
    person: {
       ...,
       // 覆盖原来的属性 就可以达到修改对象中属性的目的
       name: 'rose'
    }
})
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

表单处理

目标任务: 能够使用受控组件的方式获取文本框的值

使用React处理表单元素,一般有俩种方式:

  1. 受控组件 (推荐使用)
  2. 非受控组件 (了解)
  3. 受控表单组件
    什么是受控组件? input框自己的状态被React组件状态控制
    React组件的状态的地方是在state中,input表单元素也有自己的状态是在value中,React将state与表单元素的值(value)绑定到一起,由state的值来控制表单元素的值,从而保证单一数据源特性

实现步骤
以获取文本框的值为例,受控组件的使用步骤如下:

  1. 在组件的state中声明一个组件的状态数据
  2. 将状态数据设置为input标签元素的value属性的值
  3. 为input添加change事件,在事件处理程序中,通过事件对象e获取到当前文本框的值(即用户当前输入的值)
  4. 调用setState方法,将文本框的值作为state状态的最新值

代码落地

import React from 'react'

class InputComponent extends  {
  // 声明组件状态
  state = {
    message: 'this is message',
  }
  // 声明事件回调函数
  changeHandler = (e) => {
    ({ message:  })
  }
  render () {
    return (
      <div>
        {/* 绑定value 绑定事件*/}
        <input value={} onChange={} />
      </div>
    )
  }
}


function App () {
  return (
    <div className="App">
      <InputComponent />
    </div>
  )
}
export default App
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30

2. 非受控表单组件

什么是非受控组件?
非受控组件就是通过手动操作dom的方式获取文本框的值,文本框的状态不受react组件的state中的状态控制,直接通过原生dom获取输入框的值

实现步骤

  1. 导入createRef 函数
  2. 调用createRef函数,创建一个ref对象,存储到名为msgRef的实例属性中
  3. 为input添加ref属性,值为msgRef
  4. 在按钮的事件处理程序中,通过即可拿到input对应的dom元素,而其中拿到的就是文本框的值

代码落地

import React, { createRef } from 'react'

class InputComponent extends  {
  // 使用createRef产生一个存放dom的对象容器
  msgRef = createRef()

  changeHandler = () => {
    ()
  }

  render() {
    return (
      <div>
        {/* ref绑定 获取真实dom */}
        <input ref={} />
        <button onClick={}>click</button>
      </div>
    )
  }
}

function App () {
  return (
    <div className="App">
      <InputComponent />
    </div>
  )
}
export default App
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29

组件通信的意义

目标任务: 了解为什么需要组件通信

组件是独立且封闭的单元,默认情况下组件只能使用自己的数据(state)
组件化开发的过程中,完整的功能会拆分多个组件,在这个过程中不可避免的需要互相传递一些数据
为了能让各组件之间可以进行互相沟通,数据传递,这个过程就是组件通信

  1. 父子关系 - 最重要的
  2. 兄弟关系 - 自定义事件模式产生技术方法 eventBus / 通过共同的父组件通信
  3. 其它关系 - mobx / redux / zustand

父传子实现

目标任务: 实现父子通信中的父传子,把父组件中的数据传给子组件

实现步骤

  1. 父组件提供要传递的数据 - state
  2. 给子组件标签添加属性值为 state中的数据
  3. 子组件中通过 props 接收父组件中传过来的数据
    a. 类组件使用获取props对象
    b. 函数式组件直接通过参数获取props对象
    在这里插入图片描述
    子传父:子组件调用父组件传递过来的函数并且把想要传递的数据当作函数的实参

兄弟组件的传递

先把b当中的数据通过子传父传递给app
再把app接受到的som当中的通过父传子
Context
上层组件和下层组件的关系是相对的,通过我们会通过app作为数据的提供方
value提供数据,获取数据的时候{value=>}
props:children
普通文本标签元素,函数,jsx
高阶组件
const List=props=>{
const arr=;
const lils=((item,index=><li
组件名.propTypes={}
函数组件默认值:1.使用defaultProps函数参数默认值(推荐的方案)
render函数当中不能调用setState()操作的
render每次组件渲染都会触发渲染ui
componentDidUpdate组件更新之后dom渲染完毕dom操作恶意获取到更新后的dom内容,不要直接调用setState
卸载阶段
componentWillUnmount
如果数据是组件的状态需要去影响视图,定义到state当中,如果我们需要的数据状态不和视图绑定,定义成一个普通的实例
在这里插入图片描述
在这里插入图片描述
context机制跨组件通信,顶层向任意的底层的传递数据
调用createContext得到provider和consumer
通过provider包裹顶层组件value属性扳道工数据
通过consumer包裹底层的数据value=。消费数据
antDesign,\

Hooks概念理解

本节任务: 能够理解hooks的概念及解决的问题

  1. 什么是hooks
    Hooks的本质:一套能够使函数组件更强大,更灵活的“钩子”

React体系里组件分为 类组件 和 函数组件
经过多年的实战,函数组件是一个更加匹配React的设计理念 UI = f(data),也更有利于逻辑拆分与重用的组件表达形式,而先前的函数组件是不可以有自己的状态的,为了能让函数组件可以拥有自己的状态,所以从react v16.8开始,Hooks应运而生

注意点:

  1. 有了hooks之后,为了兼容老版本,class类组件并没有被移除,俩者都可以使用
  2. 有了hooks之后,不能在把函数成为无状态组件了,因为hooks为函数组件提供了状态
  3. hooks只能在函数组件中使用

2. Hooks解决了什么问题

Hooks的出现解决了俩个问题 1. 组件的状态逻辑复用 组件自身的问题

  1. 组件的逻辑复用
    在hooks出现之前,react先后尝试了 mixins混入,HOC高阶组件,render-props等模式
    但是都有各自的问题,比如mixin的数据来源不清晰,高阶组件的嵌套问题等等
  2. class组件自身的问题
    class组件就像一个厚重的‘战舰’ 一样,大而全,提供了很多东西,有不可忽视的学习成本,比如各种生命周期,this指向问题等等,而我们更多时候需要的是一个轻快灵活的’快艇’

useState

  1. 基础使用
    本节任务: 能够学会useState的基础用法
    作用
    useState为函数组件提供状态(state)
    使用步骤
    导入 useState 函数
    调用 useState 函数,并传入状态的初始值
    从useState函数的返回值中,拿到状态和修改状态的方法
    在JSX中展示状态
    调用修改状态的方法更新状态
    代码实现
import { useState } from 'react'

function App() {
  // 参数:状态初始值比如,传入 0 表示该状态的初始值为 0
  // 返回值:数组,包含两个值:1 状态值(state) 2 修改该状态的函数(setState)
  const [count, setCount] = useState(0)
  return (
    <button onClick={() => { setCount(count + 1) }}>{count}</button>
  )
}
export default App
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

2. 状态的读取和修改

本节任务: 能够理解useState下状态的读取和修改
读取状态
该方式提供的状态,是函数内部的局部变量,可以在函数内的任意位置使用
修改状态
setCount是一个函数,参数表示最新的状态值
调用该函数后,将使用新值替换旧值
修改状态后,由于状态发生变化,会引起视图变化
注意事项
修改状态的时候,一定要使用新的状态替换旧的状态,不能直接修改旧的状态,尤其是引用类型
3. 组件的更新过程
本节任务: 能够理解使用hook之后组件的更新情况
函数组件使用 useState hook 后的执行过程,以及状态值的变化
组件第一次渲染
从头开始执行该组件中的代码逻辑
调用 useState(0) 将传入的参数作为状态初始值,即:0
渲染组件,此时,获取到的状态 count 值为: 0
组件第二次渲染
点击按钮,调用 setCount(count + 1) 修改状态,因为状态发生改变,所以,该组件会重新渲染
组件重新渲染时,会再次执行该组件中的代码逻辑
再次调用 useState(0),此时 React 内部会拿到最新的状态值而非初始值,比如,该案例中最新的状态值为 1
再次渲染组件,此时,获取到的状态 count 值为:1
注意:useState 的初始值(参数)只会在组件第一次渲染时生效。也就是说,以后的每次渲染,useState 获取到都是最新的状态值,React 组件会记住每次最新的状态值

在这里插入图片描述
setCount作用用来修改count依旧保持不能直接修改原址韩式生成一个新知用来替换原值
setCount基于原址计算得到新址
组件的更新
当调用setCount的时候更新的过程
首先渲染

更新渲染
初始值只会在首次渲染的时候生效的,app组件会再次渲染这个函数会再次执行的
setCount都会更新的useState再次执行得到的新的count的值不是0而是修改之后的1模板会用新知渲染
useState初始值只会在首次渲染生效,后续只要调用setCount整个app当中的代码都会执行的
更新渲染setCount都会更新
app组件会再次渲染,这个函数会再次执行的useState再次执行的得到的新的count的值不是0而是修改之后的1,模板会用新知渲染

React介绍

目标任务: 了解什么是React以及它的特点
React是什么
一个专注于构建用户界面JavaScript 库,和vue和angular并称前端三大框架,不夸张的说,react引领了很多新思想,世界范围内是最流行的js前端框架,最新版本已经到了18,加入了许多很棒的新特性
React英文文档(/)
React中文文档 (/)
React新文档(/)(开发中…)

React有什么特点

1- 声明式UI(JSX)
写UI就和写普通的HTML一样,抛弃命令式的繁琐实现
2- 组件化

组件是react中最重要的内容,组件可以通过搭积木的方式拼成一个完整的页面,通过组件的抽象可以增加复用能力和提高可维护性

环境初始化

目标任务: 能够独立使用React脚手架创建一个react项目

1. 使用脚手架创建项目

打开命令行窗口
执行命令

$ npx create-react-app react-basic
  • 1

npx create-react-app react-bassic
说明:
a. npx create-react-app 是固定命令,create-react-app是React脚手架的名称
b. react-basic表示项目名称,可以自定义,保持语义化
c. npx 命令会帮助我们临时安装create-react-app包,然后初始化项目完成之后会自自动删掉,所以不需要全局安装create-react-app
● 启动项目

$ yarn start
or
$ npm start
  • 1
  • 2
  • 3

yarn tartnpm start

2. 项目目录说明调整

目录说明
src 目录是我们写代码进行项目开发的目录
中俩个核心库:react 、react-dom
目录调整
删除src目录下自带的所有文件,只保留根组件和
创建文件作为项目的入口文件,在这个文件中书写react代码即可
入口文件说明

import React from 'react'
import ReactDOM from 'react-dom'
import './'
// 引入根组件App
import App from './App'
// 通过调用ReactDOM的render方法渲染App根组件到id为root的dom节点上
(
  <>
    <App />
  </>,
  ('root')
)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

JSX基础

1. JSX介绍

目标任务: 能够理解什么是JSX,JSX的底层是什么

概念:JSX是 JavaScript XML(HTML)的缩写,表示在 JS 代码中书写 HTML 结构
作用:在React中创建HTML结构(页面UI结构)
优势:

  1. 采用类似于HTML的语法,降低学习成本,会HTML就会JSX
  2. 充分利用JS自身的可编程能力创建HTML结构

注意:JSX 并不是标准的 JS 语法,是 JS 的语法扩展,浏览器默认是不识别的,脚手架中内置的 @babel/plugin-transform-react-jsx 包,用来解析该语法
在这里插入图片描述

2. JSX中使用js表达式

目标任务: 能够在JSX中使用表达式
语法
{ JS 表达式 }

const name = '柴柴'

<h1>你好,我叫{name}</h1>   //    <h1>你好,我叫柴柴</h1>
  • 1
  • 2
  • 3

可以使用的表达式

  1. 字符串、数值、布尔值、null、undefined、object( [] / {} )
  2. 1 + 2、‘abc’.split(‘’)、[‘a’, ‘b’].join(‘-’)
  3. fn()

特别注意
if 语句/ switch-case 语句/ 变量声明语句,这些叫做语句,不是表达式,不能出现在 {} 中!!
if/switch-casse/变量声明语句,语句不是表达式

3. JSX列表渲染

目标任务: 能够在JSX中实现列表渲染
页面的构建离不开重复的列表结构,比如歌曲列表,商品列表等,我们知道vue中用的是v-for,react这边如何实现呢?

实现:使用数组的map 方法

// 来个列表
const songs = [
  { id: 1, name: '痴心绝对' },
  { id: 2, name: '像我这样的人' },
  { id: 3, name: '南山南' }
]

function App() {
  return (
    <div className="App">
      <ul>
        {
          (item => <li>{}</li>)
        }
      </ul>
    </div>
  )
}

export default App
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20

constsongs=
{id:1,name:'痴心绝对},{id:2,name:‘像我这样的人’},{id:3,name:'南山南}]
function App(){return (<,div class Name=app">{(item=>

  • {}
  • )}
    注意点:需要为遍历项添加 key 属性
    在这里插入图片描述
    1. key 在 HTML 结构中是看不到的,是 React 内部用来进行性能优化时使用
    2. key 在当前列表中要唯一的字符串或者数值(String/Number)
    3. 如果列表中有像 id 这种的唯一值,就用 id 来作为 key 值
    4. 如果列表中没有像 id 这种的唯一值,就可以使用 index(下标)来作为 key 值
      React内部用来进行性能优化的时候使用的,

    4. JSX条件渲染

    目标任务: 能够在JSX中实现条件渲染

    作用:根据是否满足条件生成HTML结构,比如Loading效果
    实现:可以使用 三元运算符 或 逻辑与(&&)运算符

    // 来个布尔值
    const flag = true
    function App() {
      return (
        <div className="App">
          {/* 条件渲染字符串 */}
          {flag ? 'react真有趣' : 'vue真有趣'}
          {/* 条件渲染标签/组件 */}
          {flag ? <span>this is span</span> : null}
        </div>
      )
    }
    export default App
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13

    5. JSX样式处理

    目标任务: 能够在JSX中实现css样式处理
    行内样式 - style

    function App() {
      return (
        <div className="App">
          <div style={{ color: 'red' }}>this is a div</div>
        </div>
      )
    }
    
    export default App
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9

    行内样式 - style - 更优写法

    const styleObj = {
        color:red
    }
    
    function App() {
      return (
        <div className="App">
          <div style={ styleObj }>this is a div</div>
        </div>
      )
    }
    
    export default App
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13

    const styleObj=coor:red}
    类名 - className(推荐)

    .title {
      font-size: 30px;
      color: blue;
    }
    
    • 1
    • 2
    • 3
    • 4