网络营销的作用和意义,成都seo推广,南京定制网站,建设适应连锁行业网站黑马React: 基础1
Date: November 15, 2023 Sum: React介绍、JSX、事件绑定、组件、useState、B站评论 React介绍
概念: React由Meta公司研发#xff0c;是一个用于 构建Web和原生交互界面的库 优势: 1-组件化的开发方式 2-优秀的性能 3-丰富的生态 4-跨平台开发 开发环境搭…黑马React: 基础1
Date: November 15, 2023 Sum: React介绍、JSX、事件绑定、组件、useState、B站评论 React介绍
概念: React由Meta公司研发是一个用于 构建Web和原生交互界面的库 优势: 1-组件化的开发方式 2-优秀的性能 3-丰富的生态 4-跨平台开发 开发环境搭建
使用create-react-app快速搭建开发环境
create-react-app是一个快速 创建React开发环境的工具底层由Webpack构建封装了配置细节开箱即用
执行命令
npx create-react-app react-basicnpx Node.js工具命令查找并执行后续的包命令create-react-app 核心包固定写法用于创建React项目react-basic React项目的名称可以自定义
之后切入到文件夹下, 使用 npm start启动项目 创建React项目的更多方式: https://zh-hans.react.dev/learn/start-a-new-react-project
工作方式: 理解:
index.js项目入口App.js项目的根组件index.htmlhtml文件
项目的根组件以React组件的方式渲染到index.html中 Code: index.js 简化后的内容 // 项目的入口 从这里开始// React必要的两个核心包
import React from react;
import ReactDOM from react-dom/client;// 导入项目的根组件
import App from ./App;// 把App根组件渲染到id为root的dom节点上
const root ReactDOM.createRoot(document.getElementById(root));
root.render(App /
);JSX基础-概念和本质
什么是JSX
**概念**JSX是JavaScript和XMLHTML的缩写表示在JS代码中编写HTML模版结构,它是React中编写UI模版的方式 优势
HTML的声明式模版写法 2. JS的可编程能力 JSX的本质
JSX并不是标准的JS语法它是JS的语法扩展浏览器本身不能识别需要通过解析工具做解析之后才能在浏览器中运行 JSX基础-高频场景
JSX中使用JS表达式
在JSX中可以通过 大括号语法{} 识别 JavaScript中的表达式比如常见的变量、函数调用、方法调用等等
使用引号传递字符串使用JavaScript变量函数调用和方法调用使用JavaScript对象
注意if语句、switch语句、变量声明属于语句不是表达式不能出现在{}中
案例: Code: // 项目的根组件
// App - index.js - public/index.html(root)const count 100function getName() {return jack
}function App() {return (div classNameAppthis is App{/* 使用引号传递字符串 */}{this is message}{/* 识别js变量 */}{count}{/* 函数调用 */}{getName()}{/* 方法调用 */}{new Date().getDate()}{/* 使用js对象 */}div style{{ color: red}}this is div/div/div)
}export default App效果: JSX中实现列表渲染
**语法**在JSX中可以使用原生JS中的map方法遍历渲染列表 案例:
const list [{ id: 1001, name: Vue},{ id: 1002, name: React},{ id: 1003, name: Angular}
]function App() {return (div classNameAppthis is App{/* 渲染列表 */}ul{/* { list.map(item liVue/li) } */}{ list.map(item li key{item.id}{ item.name }/li) }/ul/div)
}export default App效果: 要点:
1-key值绑定
作用: 提升性能
方式: 每一项要加上一个独一无二的key值 JSX中实现条件渲染 **语法**在React中可以通过逻辑与运算符、三元表达式?:实现基础的条件渲染
案例:
const isLogin truefunction App() {return (div classNameApp{/* 逻辑与 */}{ isLogin spanthis is span/span}{/* 三目运算符 */}{ isLogin ? spanthis is span/span : divthis is div/div}{/* 逻辑或 || */}{ isLogin || spanthis is span/span}/div)
}export default App效果:
this is spanthis is span JSX中实现复杂条件渲染 需求列表中需要根据文章状态适配三种情况单图三图和无图三种模式
解决方案自定义函数 if判断语句
案例:
// 定义文章类型
const articleType 3 // 0 1 3// 定义核心函数根据文章类型返回不同的JSX模版function getArticleTem () {if (articleType 0) {return div我是无图文章/div} else if (articleType 1) {return div我是单图模式/div} else {return div我是三图模式/div}
}function App () {return (div classNameApp{/* 调用函数渲染不同的模版 */}{getArticleTem()}/div)
}export default App效果:
我是三图模式 React中的事件绑定
React 基础事件绑定
**语法**on 事件名称 { 事件处理程序 }整体上遵循驼峰命名法
Code:
function App() {const handleClick () {console.log(button被点击了);}return (div classNameAppbutton onClick{handleClick}Click/button/div)
}export default AppRes: 使用事件对象参数
语法在事件回调函数中设置形参e
Code: function App() {const handleClick (e) {console.log(button被点击了, e);}return (div classNameAppbutton onClick{handleClick}Click/button/div)
}export default AppRes: 传递自定义参数
语法事件绑定的位置改成箭头函数的写法在执行clickHandler实际处理业务函数的时候传递实参
Code:
function App() {const handleClick (name) {console.log(button被点击了, name);}return (div classNameAppbutton onClick{() handleClick(jack)}Click/button/div)
}export default AppRes: 注意不能直接写函数调用这里事件绑定需要一个函数引用 同时传递事件对象和自定义参数
语法在事件绑定的位置传递事件实参e和自定义参数clickHandler中声明形参注意顺序对应
Code:
function App() {const handleClick (name, e) {console.log(button被点击了, name, e);}return (div classNameAppbutton onClick{(e) handleClick(jack, e)}Click/button/div)
}export default AppRes: React中的组件
组件是什么
概念一个组件就是用户界面的一部分它可以有自己的逻辑和外观组件之间可以互相嵌套也可以复用多次 组件化开发可以让开发者像搭积木一样构建一个完整的庞大的应用 React组件
在React中一个组件就是首字母大写的函数内部存放了组件的逻辑和视图UI, 渲染组件只需要把组件当成标签书写即可
Code:
function Button() {return buttonclick me!/button
}function App() {return (div classNameApp{/* 自闭合 */}Button /{/* 成对标签 */}Button/Button/div)
}export default AppRes: useState
useState基础使用
概念:
useState 是一个 React Hook函数它允许我们向组件添加一个状态变量, 从而控制影响组件的渲染结果 本质和普通变量不同的是状态变量一旦发生变化组件的视图UI也会跟着变化数据驱动视图
const [count, setCount] useState(0)1- useState是一个函数, 返回值是一个数组
2-数组中的第一个参数是状态变量, 第二个参数是set函数用来修改状态变量
3-useState的参数将作为count的初始值
Case:
func: 点击按钮, 数值不断增加
Code:
import { useState } from reactfunction App() {// 1. 调用 useState 添加一个状态变量// count 状态变量// setCount 修改状态变量的方法const [count, setCount] useState(0)// 2. 点击事件const handleClick () {setCount(count 1)}return (div classNameAppbutton onClick{ () handleClick()}Add-{count}/button/div)
}export default AppRes: 修改状态的规则
状态不可变
在React中状态被认为是只读的我们应该始终替换它而不是修改它直接修改状态不能引发视图更新 Case:
Code:
import { useState } from reactfunction App() {// 1. 调用 useState 添加一个状态变量// count 状态变量// setCount 修改状态变量的方法const [count, setCount] useState(0)// 2. 点击事件const handleClick () {setCount(count 1)}return (div classNameAppbutton onClick{ () handleClick()}Add-{count}/button/div)
}export default App修改对象状态
规则对于对象类型的状态变量应该始终传给set方法一个全新的对象来进行修改
直接修改原对象不引发视图变化 调用set传入新对象用于修改 理解: 这里先用展开运算符做个拷贝, 然后再用后面重复属性进行替换即可.
Case:
func: 点击按变换名字
Code:
import { useState } from reactfunction App() {const [form, setForm] useState({ name: jack })const handleClick () {setForm({...form,name: rose})}return (div classNameAppbutton onClick{ () handleClick()}Add-{form.name}/button/div)
}export default AppRes: 复习知识点:
1-…展开匀速符: 深浅拷贝问题
展开运算符使用的对象如果只是针对简单的一级基础数据就是深拷贝 展开运算符使用的对象内容包含二级或更多的复杂的数据那就是浅拷贝 组件的样式处理
组件基础样式方案
React组件基础的样式控制有俩种方式
行内样式不推荐 class类名控制 Case:
Code:
index.js
import ./css/index.cssconst style {color: red,fontSize: 20px
}function App() {return (div classNameApp{/* 行内样式控制 */}div style{{ color: red}}this is span/div{/* 内部样式控制 */}div style{style}this is span/div{/* 外部样式控制 */}span classNameouterthis is span/span/div)
}export default Appindex.css
.outer {background-color: blue;
}案例B站评论
效果展示: 渲染评论列表删除评论实现渲染导航Tab和高亮实现评论列表排序功能实现 渲染评论列表
核心思路
使用useState维护评论列表使用map方法对列表数据进行遍历渲染别忘了加key
key Code:
const [commentList, setCommentList] useState([])div classNamereply-list{/* 评论项 */}{commentList.map(item Item key{item.id} item{item} onDel{handleDel} /)}/div
/div实现评论删除
需求
只有自己的评论才显示删除按钮点击删除按钮删除当前评论列表中不再显示
核心思路
删除显示 - 条件渲染 2. 删除功能 - 拿到当前项id以id为条件对评论列表做filter过滤
handleDel实现列表过滤
// 删除功能
const handleDel (id) {console.log(id)// 对commentList做过滤处理setCommentList(commentList.filter(item item.rpid ! id))
}匹配删除 onDel
{/* 条件user.id item.user.id */}
{user.uid item.user.uid
span classNamedelete-btn onClick{() onDel(item.rpid)}删除
/span}渲染Tab点击高亮实现
需求点击哪个tab项哪个做高亮处理
核心思路
点击谁就把谁的type独一无二的标识记录下来然后和遍历时的每一项的type做匹配谁匹配到就设置负责高亮的类名
Code:
// 导航 Tab 数组
const tabs [{ type: hot, text: 最热 },{ type: time, text: 最新 },
]...// tab切换功能
// 1. 点击谁就把谁的type记录下来
// 2. 通过记录的type和每一项遍历时的type做匹配 控制激活类名的显示
const [type, setType] useState(hot)
const handleTabChange (type) {console.log(type)setType(type)// 基于列表的排序if (type hot) {// 根据点赞数量排序 // lodashsetCommentList(_.orderBy(commentList, like, desc))} else {// 根据创建时间排序setCommentList(_.orderBy(commentList, ctime, desc))}
}...li classNamenav-sort{/* 高亮类名 active */}{tabs.map(item spankey{item.type}onClick{() handleTabChange(item.type)}className{classNames(nav-item, { active: type item.type })}{item.text}/span)}
/li排序功能实现 需求
点击最新评论列表按照创建时间倒序排列新的在前点击最热按照点赞数排序多的在前
**核心思路**把评论列表状态数据进行不同的排序处理当成新值传给set函数重新渲染视图UI
Code:
method: 采用 lodash 来进行排序处理
// 基于列表的排序
if (type hot) {// 根据点赞数量排序 // lodashsetCommentList(_.orderBy(commentList, like, desc))
} else {// 根据创建时间排序setCommentList(_.orderBy(commentList, ctime, desc))
}classnames优化类名控制
classnames是一个简单的JS库可以非常方便的通过条件动态控制class类名的显示 现在的问题字符串的拼接方式不够直观也容易出错 理解: classNames 是一个可以执行的方法, key用来控制类型, value用来控制条件 参考:
React
React入门到实战导学课程_哔哩哔哩_bilibili