作者数次强调,redux和React没有关系(明明当初就是为了管理react的state才弄出来的吧),它可以和其他插件如 Angular, Ember, jQuery一起使用。好啦好啦知道啦。Redux的初衷就是为了管理UI的状态,触发state的更新作为对action的回应。

文档举的例子是一个todo App。

安装react-redux:

npm install --save react-redux redux

Presentational and Container Components:

React bindings for Redux embrace the idea of separating presentational and container components. If you're not familiar with these terms, read about them first, and then come back. They are important, so we'll wait!

当我们想把redux应用到react中时,要接受一种思想:app中的组件可以分为两类

一类是用于展示内容的组件(P):负责结构和样式,与redux无关,响应props的数据,调用props的方法,组件由开发者设计

一类是作为容器的组件(C):负责数据获取和状态更新,与redux有关,响应state更新,能dispatch action,由react redux生成

C组件能和redux store联系,它是P组件与redux store的桥梁。但不一定要在组件树的顶层。如果C组件太复杂,建议引入另一些C组件来拆分它的逻辑,像split reducer一样。

注意:尽管开发者也可以使用store.subscribe()手写C组件,但是作者并不建议,他更推荐我们通过react redux 的  connect() function 来生成C组件,因为通过react redux生成的C组件可以实现性能最优化,这是手写不容易达到的。

举的是todolist的例子

设计组件的层级:

复习一下Thinking in React

设计展示组建:

  • TodoList is a list showing visible todos.

    • todos: Array is an array of todo items with { id, text, completed } shape.
    • onTodoClick(id: number) is a callback to invoke when a todo is clicked.
  • Todo is a single todo item.
    • text: string is the text to show.
    • completed: boolean is whether todo should appear crossed out.
    • onClick() is a callback to invoke when a todo is clicked.
  • Link is a link with a callback.
    • onClick() is a callback to invoke when link is clicked.
  • Footer is where we let the user change currently visible todos.
  • App is the root component that renders everything else.

P组件只负责渲染视图,并不关心数据从哪来的,也不关系数据怎么变更。

Designing Container Components:

  • VisibleTodoList filters the todos according to the current visibility filter and renders a TodoList.
  • FilterLink gets the current visibility filter and renders a Link.
    • filter: string is the visibility filter it represents.

C组件负责将P组件和Redux 联系起来。用户可以通过C组件触发state更新,P组件通过容器获取变更的数据并重新渲染视图。

Designing Other Components:

作者承认有时候很难界定一个组件属于P还是C,对于很简单的组件,如一个todolist的输入框,没必要将其分解。但随着组件的复杂度增大,不难将之分解成P和C两部分。

组件的实现:

1.实现P组件:

http://redux.js.org/docs/basics/UsageWithReact.html#componentstodojs

由于P组件的意义只是渲染DOM,因此P组件其实是没有状态的,只有从父组件/容器组件获取的props,所以可以使用function组件直接返回JSX而不使用Class组件

2.实现C组件:

C组件可以通过subscribe()获取Redux store state树的一部分,作为P组件的props。

作者再次强调使用Redux插件的 connect()构造容器组件。connect方法的意义在于将P组件和C组件连接起来。

使用connet()方法时,需要定义一个名为mapStateToProps 的特殊函数,这个函数描述了怎么把当前的redux store state转换为P组件需要的props:

 const getVisibleTodos = (todos, filter) => {
switch (filter) {
case 'SHOW_ALL':
return todos
case 'SHOW_COMPLETED':
return todos.filter(t => t.completed)
case 'SHOW_ACTIVE':
return todos.filter(t => !t.completed)
}
} const mapStateToProps = state => {
return {
todos: getVisibleTodos(state.todos, state.visibilityFilter)
}
}

如上,getVisibleTodos函数是不是很像Reducer中被解构成更小功能的单位,其实就是个内部逻辑单元而已。

只是获取state作为P组件的props还不够。C组件还得能触发dispatch以更新state,所以还有另一个特殊函数mapDispatchToProps,它的参数是dispatch()函数

 const mapDispatchToProps = dispatch => {
return {
onTodoClick: id => {
dispatch(toggleTodo(id))
}
}
}

有了这两个函数之后,容器组件的方法才算基本完善,调用connect()将之作为参数传进去:

 import { connect } from 'react-redux'

 const VisibleTodoList = connect(
mapStateToProps,
mapDispatchToProps
)(TodoList) export default VisibleTodoList

这是connect()生成容器组件的基本套路,connect()的返回值是个函数,再执行一次返回容器。第二个括号中的传参是个P组件,表示生成的C组件是该P组件的容器。

访问store:

在应用程序中,往往有多个层级的组件,使用react redux后当我们的容器想访问store时,一种方法是将store作为props传下去,让子组件可以访问它。但是这样太麻烦了,因为你必须每一级都把它传递下去。一种推荐的做法是,使用<Provider>组件。我们只需要在根组件渲染时使用它:

 import React from 'react'
import { render } from 'react-dom'
import { Provider } from 'react-redux'
import { createStore } from 'redux'
import todoApp from './reducers'
import App from './components/App' let store = createStore(todoApp) render(
<Provider store={store}>
<App />
</Provider>,
document.getElementById('root')
)

总结:

1.在设计应用的组件时,先理清应用的模块的划分,然后对每个模块进行实现。

2.对应用划分好模块之后,针对每个模块,先设计好它的state的结构,知道哪些state是负责处理data的,哪些是负责UI渲染的。

3.设计好一个模块的state之后,创建需要的action对象,并创建对应的reducer函数,然后生成store。

4.创建展示组件,负责渲染内容。

5.利用connect()方法生成容器组件,包含mapstate和mapdispatch方法,用以获取当前state、触发state更新。

6.在最顶层index页面ReactDOM.render渲染应用时,组件最外层被<Provider store={store}></Provider>包裹,以全局提供store的引用。

Redux:with React(一)的更多相关文章

  1. Redux 和React 结合

    当Redux 和React 相接合,就是使用Redux进行状态管理,使用React 开发页面UI.相比传统的html, 使用React 开发页面,确实带来了很多好处,组件化,代码复用,但是和Redux ...

  2. redux在react项目中的应用

    今天想跟大家分享一下redux在react项目中的简单使用 1 1.redux使用相关的安装 yarn add redux yarn add react-redux(连接react和redux) 2. ...

  3. 使用Redux管理React数据流要点浅析

    在图中,使用Redux管理React数据流的过程如图所示,Store作为唯一的state树,管理所有组件的state.组件所有的行为通过Actions来触发,然后Action更新Store中的stat ...

  4. [Redux] Adding React Router to the Project

    We will learn how to add React Router to a Redux project and make it render our root component. Inst ...

  5. Redux和React

    export app class Compo1 extends Component{ } Compo1.propType = { a:PropTypes.string, fn:PropTypes.fu ...

  6. Redux 管理React Native数据

    现在让我们看看大致的流程: React 可以触发 Action,比如按钮点击按钮. Action 是对象,包含一个类型以及相关的数据,通过 Store 的 dispatch() 函数发送到 Store ...

  7. redux【react】

    首先介绍一下redux就是Flux的一种进阶实现.它是一个应用数据流框架,主要作用应用状态的管理 一.设计思想: (1).web应用就是一个状态机,视图和状态一一对应 (2).所有的状态保存在一个对象 ...

  8. react+redux教程(八)连接数据库的redux程序

    前面所有的教程都是解读官方的示例代码,是时候我们自己写个连接数据库的redux程序了! 例子 这个例子代码,是我自己写的程序,一个非常简单的todo,但是包含了redux插件的用法,中间件的用法,连接 ...

  9. 实例讲解react+react-router+redux

    前言 总括: 本文采用react+redux+react-router+less+es6+webpack,以实现一个简易备忘录(todolist)为例尽可能全面的讲述使用react全家桶实现一个完整应 ...

  10. react+redux教程(二)redux的单一状态树完全替代了react的状态机?

    上篇react+redux教程,我们讲解了官方计数器的代码实现,react+redux教程(一).我们发现我们没有用到react组件本身的state,而是通过props来导入数据和操作的. 我们知道r ...

随机推荐

  1. C语言字符数组超细讲解

    看到标题,有不少朋友会想:字符数组不也是数组吗?为什么要单独拿出来讲哩?莫非它是朵奇葩? 哈哈,确实,一起来认识一下这朵数组界的奇葩吧! 一.字符数组的定义.引用.初始化 大家好!我是字符数组,看我的 ...

  2. Python selenium Chrome正在受到自动软件的控制 disable-infobars无效 的解决方法

    问题解决 前两天更新了google浏览器版本,今天运行以前的脚本,发现options一个参数的配置不生效了. 运行了几次都发现该参数没有生效,也检查了自己的代码参数,没有写错,于是就有了这一波“网中寻 ...

  3. scrollview 和 listview滑动冲突解决

    http://blog.csdn.net/wanghao200906/article/details/51084975 http://www.cnblogs.com/shitianzeng/artic ...

  4. 【Inno Setup】查看是否安装了VC++ 2015 Redistributeable

    可能有必要先测一下注册表的这一项是否存在 if RegValueExists(HKLM, 'SOFTWARE\WOW6432Node\Microsoft\VisualStudio\14.0\VC\Ru ...

  5. 日志分析工具ELK(五)

    八.Kibana实践 选择绝对时间和相对时间 搜索 还可以添加相关信息 自动刷新页面时间,也可以关闭 创建图像,可视化 编辑Markdown,创建一个值班联系表 值班联系表 保存 再创建一个饼图;查看 ...

  6. 定了,这个vue.js开源项目,面试时,一定会考问

     因为现在的网店,都是用的商城系统, 而实体店都是入座后,扫码打开网上商城进行选购(餐饮,超市等),所以,vue.js迅速开发网上购物商城系统成为了香饽饽, 本人开源2020年4月开发的购物商城系统, ...

  7. mysql备份及恢复

    第四章:MySQL数据库的备份与恢复                            2016-09-30 00:58:05 标签:数据库备份 工作原理 数据库表 mysql source 原创 ...

  8. 《C Primer Plus(第6版)中文版》一1.12 复习题

    本节书摘来自异步社区<C Primer Plus(第6版)中文版>一书中的第1章,第1.12节,作者 傅道坤,更多章节内容可以访问云栖社区"异步社区"公众号查看. 1. ...

  9. .NET Micro Framework 4.2 beta 源码探析

    .NET Micro Framework 4.2 beta发布已经有一段时间了,一直没有腾出时间研究,昨天因为LWIP协议栈的原因(感觉上一个版本有点问题)刚 下了代码,所以抽空研究了一下.      ...

  10. python-函数变量与方法公有、私有整理

    关于函数与方法的区别: 函数: def funname(): 括号里面可以有形参,也可以没有,为空 在函数里面的参数整理: 方法: def funcname(self): 括号里面必须有个self,因 ...