# my-react-app **Repository Path**: UniverseKing/my-react-app ## Basic Information - **Project Name**: my-react-app - **Description**: No description available - **Primary Language**: JavaScript - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2019-01-13 - **Last Updated**: 2020-12-19 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README ## context属性传递 > 如果组件嵌套太深,`props`的传递方式会增加组件的依赖,每个组件之间最好是低耦合的,所以我们可以使用`context`属性实现组件之间数据的传递。 ### 基本使用 > 父组件中通过`getChildContext`设置需要传递的属性,同时需要使用`childContextTypes`设置传递的属性校验 ```js // 1. 定义需要传递给子孙组件的数据 getChildContext(){ return { msg:'我是需要传给孙子的数据' } } // 2. 对该数据进行属性校验 static childContextTypes = { msg: PropTypes.string, } ``` > 子组件接收传递过来的属性必须使用`contextTypes`接收,然后通过`this.context.[prop]`即可使用传递过来的属性 ```js // 3. 子组件中对父组件传过来的数据进行属性校验 static contextTypes = { msg: PropTypes.string } // 4. 使用 this.context.msg 访问父组件传过来的数据 console.log(this.context.msg) ``` ## redux > 需求:组件A和组件B时兄弟组件,组件A和组件B公用数据count,组件A修改count值,组件B里面统一被修改。 > 1. state中定义公共数据count > 2. A组件中调用store.dispatch()告诉reducer怎么修改数据,修改成什么样的数据 > 3. reducer中接收action的信息,执行真正的修改数据业务逻辑 > 4. A、B组件中使用store.getState()获取公共数据count ### 基本使用 ```js // 1. 导入redux中的ecreateStore函数 import {createStore} from 'redux' // 2. 定义一个reducer函数 const reducer = (state = {count:100},action)=>{ // 这里根据将来提交的action处理业务逻辑 return state } // 3. 根据reducer创建一个store实例 const store = createStore(reducer) // 4. 将store实例挂载到React.Component.prototype上面,保证所有组件都可以访问到store实例 React.Component.prototype.$store = store // 5. 组件中获取公共数据 this.$store.getState().count ``` ### 提交action修改数据 > action只负责告诉reducer要对数据做哪种操作,以及需要的数据,真正的操作交给reducer内部实现。 > `this.$store.dispatch({ type: 'increment' , payload: 2 })` ```js // 1. 点击添加按钮之后提交一个action increment = () => { // 调用redux的api修改state中的数据 // this.$store.dispatch({type:'increment',payload:1})提交action(要对数据做哪种操作,传给reducer的具体数据) this.$store.dispatch({ type:'increment', payload:1 }) } // 2. 在reducer中接收到action后,根据action的type分发不同的处理业务逻辑 const reducer = (state = {count:100},action)=>{ // 这里根据将来提交的action处理业务逻辑 console.log(action) switch(action.type){ // 2.1 type为increment实现数据的添加 case "increment": { return { count:state.count + action.payload } } // 2.2 type为decrement实现数据的减少 case "decrement": { return { count:state.count - action.payload } } // 2.3 默认返回初始数据 default: return state } } // 3. 通过store.subscribe监听state数据的改变(在组件中监听,拿到最新改变的数据之后渲染到界面) // 只要提交action必然会触发subscribe函数 this.$store.subscribe(()=>{ // this.$store.getState() 获取最新数据 }) ``` ### react-redux的使用 > react-redux类似vuex中的辅助函数,可以将state中的数据映射成为组件的props属性,可以将action映射成为组件的props属性(该属性是一个方法) ```js // 1. 安装react-redux yarn add react-redux // 2. 导入组件Provider,将项目的根组件包裹,将store作为属性进行传递 import { Provider } from 'react-redux' ReactDOM.render( // Provider身上绑定store属性之后,项目中所有子组件都可以访问到公共的state数据 // 利用的是context特性传值 , document.getElementById('root')); // 3. 将action映射成为组件的props属性,同时会映射成为一个函数 import { connect } from "react-redux"; // 3.1 将action映射成为方法(提交action使用this.props.addTodo()) export default connect(null,{ addTodo:(todo)=>{ return { type:'add', payload:todo } } })(AddTodo) // 3.2 将state公共数据映射成为当前组件props中的属性 // state就是reducer中定义的公共数据 export default connect((state)=>{ // 这里返回的对象中的每一个属性都会自动绑定到当前组件的props里面 return { todos:state } })(TodoList) ```