一 Context概述
Context provides a way to pass data through the component tree without having to pass props down manually at every level.
Context 提供了一个无需为每层组件手动添加 props,就能在组件树间进行数据传递的方法。
二 项目结构
三 代码
1 theme-context.js
import React from 'react'; // 主题数据 export const themes = { gray: { background: 'gray', }, gold: { background: 'gold', }, }; // 创建上下文对象,参数将作为上下文对象的默认值 export const ThemeContext = React.createContext( themes.gray // default value );
2 themed-button.js
import React from 'react'; import { ThemeContext } from './theme-context'; class ThemedButton extends React.Component { // props默认是空对象{}。 // context默认是空对象{}。绑定上下文对象后,创建组件时,会传入上下文对象的值(就近原则)。 constructor(props,context){ super(props) console.log(arguments) } render() { let props = this.props; let theme = this.context; return ( <button {...props} style={{...theme}} /> ) } } // 组件类绑定上下文对象后,组件对象的context属性才能使用上下文对象的值(就近原则)。 ThemedButton.contextType = ThemeContext; export default ThemedButton;
3 app.js
import React, { Fragment } from 'react'; import { ThemeContext, themes } from './theme-context'; import ThemedButton from './themed-button'; // An intermediate component that uses the ThemedButton // 工具栏组件(中间件) function Toolbar(props) { return ( <ThemedButton onClick={props.changeTheme}> 改变上下文对象 </ThemedButton> ); } class App extends React.Component { constructor(props) { super(props); this.state = { theme: themes.gray }; this.toggleTheme = () => { this.setState(state => ({ theme: state.theme === themes.gray ? themes.gold : themes.gray })); } } render() { return ( <Fragment> {/* 在Provider中,使用Provider提供的值 */} <ThemeContext.Provider value={this.state.theme}> <Toolbar changeTheme={this.toggleTheme} /> </ThemeContext.Provider> {/* 不在Provider中,使用默认值 */} <section> <ThemedButton /> </section> </Fragment> ); } } export default App;
4 index.js
import React from 'react'; import ReactDOM from 'react-dom'; import App from './App'; ReactDOM.render(<App />, document.getElementById('root'));
四 运行效果
1 初始化
2 点击按钮