react中context傳值和生命周期詳解
假設(shè):
項(xiàng)目中存在復(fù)雜組件樹:

context傳值用途
數(shù)據(jù)是通過 props 屬性自上而下(由父及子)進(jìn)行傳遞的,但這種做法對(duì)于某些類型的屬性而言是極其繁瑣的(例如:地區(qū)偏好,UI 主題),這些屬性是應(yīng)用程序中許多組件都需要的。
Context傳值優(yōu)點(diǎn)
Context 提供了一種在組件之間共享此類值的方式,而不必顯式地通過組件樹的逐層傳遞 props。
何時(shí)使用 Context
Context 設(shè)計(jì)目的是為了共享那些對(duì)于一個(gè)組件樹而言是“全局”的數(shù)據(jù),例如當(dāng)前認(rèn)證的用戶、主題或首選語言。
ContextAPI
1.React.createContext API
功能:
創(chuàng)建一個(gè) Context 對(duì)象。
//代碼
//創(chuàng)建context對(duì)象的
import React from 'react'
let context=React.createContext();
export default context;
2.Context.Provider API
功能:
Provider 是context對(duì)象提供的內(nèi)置組件 限定在某個(gè)作用域中使用context傳值。
限定作用域傳值。
3.Context.Consumer
context對(duì)象的內(nèi)置組件
<MyContext.Consumer>
{value => /* 基于 context 值進(jìn)行渲染*/}
</MyContext.Consumer>
作用:監(jiān)聽訂閱的context變更,
這個(gè)函數(shù)接收當(dāng)前的 context 值,返回一個(gè) React 節(jié)點(diǎn)。項(xiàng)目案例:主題色切換。
1.創(chuàng)建context.js文件 創(chuàng)建context對(duì)象 用來做context傳值。 //創(chuàng)建context對(duì)象的 import React from 'react' export default React.createContext();
2。使用context找到限定范圍使用內(nèi)置組件Provider
{/* 使用Provider 內(nèi)置組件限定context范圍 */}
{/* value 必填 context傳遞的值 */}
<ThemeContext.Provider>
<div className="Admin">
<div className="LeftMenu">
<LeftMenu></LeftMenu>
</div>
<div className="RightContent">
<div className="RightContent-top">
<TopHeader></TopHeader>
</div>
<div className="RightContent-bottom">
<Dashborder></Dashborder>
</div>
</div>
</ThemeContext.Provider>瀏覽器報(bào)錯(cuò):

3.在使用context的組件中進(jìn)行訂閱
左側(cè)菜單組件
import React, { Component } from "react";
console.log(Component);
//引入context對(duì)象
import ThemeContext from "../components/context";
class LeftMenu extends Component {
constructor(props) {
super(props);
this.state = {};
}
render() {
return (
<>
<div>左側(cè)菜單</div>
</>
);
}
}
//class類組件存在contextType 綁定context對(duì)象
LeftMenu.contextType = ThemeContext;組件中綁定context之后使用:

意味著訂閱context組件的內(nèi)部使用this.context獲取。
render() {
//獲取context
let theme = this.context;
return (
<>
<div className={theme}>左側(cè)菜單</div>
</>
);
}固定主體修改為動(dòng)態(tài)主體
修改了context文件代碼
//定義默認(rèn)主體色
export const themes = {
dark: {
backgroundColor: "#000",
color: "#fff",
},
light: {
backgroundColor: "#fff",
color: "#000",
},
};
//創(chuàng)建context對(duì)象的
import React from "react";
export const ThemeContext = React.createContext();app.js文件中獲取主題,動(dòng)態(tài)切換主題。使用主題變量
constructor(props) {
super(props);
this.state = {
//將固定的主體設(shè)置為state狀態(tài)
themeType: "dark",//控制主體切換
nowTheme: themes["dark"],//獲取當(dāng)前默認(rèn)主體
};
}
render() {
//解構(gòu)獲取
let { nowTheme } = this.state;
return (
<>
{/* 使用Provider 內(nèi)置組件限定context范圍 */}
{/* value 必填 context傳遞的值 */}
<ThemeContext.Provider value={nowTheme}>訂閱組件中使用this.context獲取訂閱

render() {
//獲取context
let { backgroundColor, color } = this.context;
return (
<>
//直接綁定行內(nèi)css
<div style={{ backgroundColor: backgroundColor, color: color }}>
左側(cè)菜單
</div>
</>
);
}
用戶點(diǎn)擊其他組件修改主題的按鈕來變更主題
注意:不能直接使用this.context修改變量值
//可以在provider組件上 value中攜帶修改函數(shù)傳遞。在訂閱組件中獲取修改方法,執(zhí)行反向傳遞值。
//修改主題變量方法
changeTheme(type) {
console.log("測試", type);
this.setState({ themeType: type, nowTheme: themes[type] });
}
render() {
//解構(gòu)獲取
let { nowTheme } = this.state;
return (
<>
{/* 使用Provider 內(nèi)置組件限定context范圍 */}
{/* value 必填 context傳遞的值 */}
<ThemeContext.Provider
value={{ ...nowTheme, handler: this.changeTheme.bind(this) }}
>
<div className="Admin">
<div className="LeftMenu">
<LeftMenu></LeftMenu>
</div>
<div className="RightContent">
<div className="RightContent-top">
<TopHeader></TopHeader>
</div>
<div className="RightContent-bottom">
<Dashborder></Dashborder>
</div>
</div>
</div>
</ThemeContext.Provider>
</>
);
//在訂閱組件中直接使用
//修改主題的方法
change(themeType) {
console.log(themeType);
//獲取provider傳遞方法
let { handler } = this.context;
handler(themeType);
}
render() {
let { themeButton } = this.state;
return (
<>
<div>
<span>主題色:</span>
<div>
{/* 控制左側(cè)菜單和上header背景色 */}
{themeButton.map((item, index) => {
return (
<button key={index} onClick={this.change.bind(this, item.type)}>
{item.name}
</button>
);
})}
</div>
</div>
</>
);
添加自定義顏色
{/* 顏色選擇器 */}
背景色:
<input
type="color"
name="selectbgColor"
value={selectbgColor}
onChange={this.changeColor.bind(this)}
/>
字體色:
<input
type="color"
name="selectColor"
value={selectColor}
onChange={this.changeColor.bind(this)}
/>
<button onClick={this.yesHandler.bind(this)}>確認(rèn)</button>
//代碼區(qū)域操作事件向父級(jí)傳遞參數(shù)
//確認(rèn)修改
yesHandler() {
let { myhandler } = this.context;
let { selectbgColor, selectColor } = this.state;
console.log(selectbgColor, selectColor);
myhandler(selectbgColor, selectColor);
}添加監(jiān)聽context變化
{/*監(jiān)聽context value值*/}
<ThemeContext.Consumer>
{(value) => {
let { backgroundColor, color } = value;
return (
<>
<span>背景色:{backgroundColor}</span>
<span>文字色:{color}</span>
</>
);
}}
</ThemeContext.Consumer>
類組件的生命周期
組件生命周期解釋:組件初始化到銷毀整個(gè)過程。
生命周期三類:
- Mounting(掛載):已插入真實(shí) DOM
- Updating(更新):正在被重新渲染
- Unmounting(卸載):已移出真實(shí) DOM
第一個(gè)階段:
代碼演示第一個(gè)階段初始化掛載階段
import React, { Component } from "react";
class App extends Component {
constructor(props) {
super(props);
this.state = {};
console.log("初始化");
}
componentDidMount() {
console.log("掛載完成");
}
render() {
console.log("渲染");
return (
<>
<div>測試</div>
</>
);
}
}
export default App;
添加了掛載之前周期

UNSAFE_componentWillMount() {
console.log("掛載之前");
}
//18.x 版本中UNSAFE_ 前綴
第二個(gè)階段:更新階段 能觸發(fā)類組件更新 props state


添加了更新之前周期
componentWillUpdate() {
console.log("更新之前");
}

第三階段卸載:

//卸載周期
componentWillUnmount() {
console.log("組件卸載");
}常用周期:

測試完成之后:18版本直接使用周期以上三個(gè)。
react推薦網(wǎng)絡(luò)請(qǐng)求在componentDidMount 卸載清除副作用 componentWillUnmount
確認(rèn)當(dāng)前組件是否更新周期
//確認(rèn)是否更新周期
//必須帶返回值 true false
//提升性能
shouldComponentUpdate(nextProps, nextState, nextContext) {
console.log(nextProps);
if (nextProps.name == this.props.name) return false;
else return true;
}
不寫該周期默認(rèn)是執(zhí)行更新1.componentWillMount() - 在染之前執(zhí)行,在客戶端和服務(wù)器端都會(huì)執(zhí)行. 2.componentDidMount() - 是掛在完成之后執(zhí)行一次 3.componentWillReceiveProps() - 當(dāng)從父類接收到 props 并且在調(diào)用另一個(gè)渲染器器之前調(diào)用。4.shouldComponentUpdatel) -根據(jù)特定條件返回 true 或 false如果你希望更新組件,請(qǐng)返回true 否則返它返回 false。 5.componentWillUpdate() - 是當(dāng)前組件state和props發(fā)生變化之前執(zhí)行 6.componentDidUpdate()-是當(dāng)前組件state和props發(fā)生變化執(zhí)行 7.componentWillUnmount0) - 從 DOM 卸載組件后調(diào)用。用于清理內(nèi)存空間


到此這篇關(guān)于react中context傳值和生命周期的文章就介紹到這了,更多相關(guān)react context傳值和生命周期內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
React系列useSyncExternalStore學(xué)習(xí)詳解
這篇文章主要為大家介紹了React系列useSyncExternalStore的學(xué)習(xí)及示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-07-07
react使用CSS實(shí)現(xiàn)react動(dòng)畫功能示例
這篇文章主要介紹了react使用CSS實(shí)現(xiàn)react動(dòng)畫功能,結(jié)合實(shí)例形式分析了react使用CSS實(shí)現(xiàn)react動(dòng)畫功能具體步驟與實(shí)現(xiàn)方法,需要的朋友可以參考下2020-05-05
React18+TS通用后臺(tái)管理系統(tǒng)解決方案落地實(shí)戰(zhàn)示例
這篇文章主要為大家介紹了React18+TS通用后臺(tái)管理系統(tǒng)解決方案落地實(shí)戰(zhàn)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-08-08
Electron打包React生成桌面應(yīng)用方法詳解
這篇文章主要介紹了React+Electron快速創(chuàng)建并打包成桌面應(yīng)用,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)吧2022-12-12
react-redux集中式狀態(tài)管理及基本使用與優(yōu)化
react-redux把組件分為兩類,一類叫做UI組件,一類叫做容器組件,這篇文章主要介紹了集中式狀態(tài)管理<react-redux>基本使用與優(yōu)化,需要的朋友可以參考下2022-08-08
react簡單實(shí)現(xiàn)防抖和節(jié)流
在日常開發(fā)中,我們經(jīng)常會(huì)有防抖和節(jié)流的需要,可以減小服務(wù)器端壓力,提升用戶體驗(yàn),本文就詳細(xì)的介紹了react簡單實(shí)現(xiàn)防抖和節(jié)流,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2022-05-05

