redux 实现弹出框案例

实现效果,点击显示按钮出现弹出框,点击关闭按钮隐藏弹出框

  1. 新建弹出框组件 src/components/Modal.js, 在index.js中引入app组件,在app中去显示计数器和弹出框组件
function Modal ({ showState, show, hide }) {
const styles = {
width: 200,
height: 200,
position: 'absolute',
top: '50%',
left: '50%',
marginTop: -100,
marginLeft: -100,
backgroundColor: 'skyblue',
}
return <div>
<button>显示</button>
<button>隐藏</button>
<div style={styles}></div>
</div>
}
  1. 弹出框组件显示隐藏是一个状态,所以我们存储到store中,命名为show,因为需要出发action来修改store中的状态所系我们需要创建modal.actions.js文件,来存储控制显示隐藏的action,我们还是把显示与隐藏aciton的type定义为常量方便导入使用
// src/store/const/modal.const.js
export const SHOWMODAL = 'showModal'
export const HIDEMODAL = 'hideModal' // src/store/actions/modal.actions.js
import { SHOWMODAL, HIDEMODAL} from './../const/modal.const' export const show = () => ({type: SHOWMODAL})
export const hide = () => ({type: HIDEMODAL}) // src/store/reducers/counter.reducers.js
import { INCREMENT, DECREMENT } from './../const/counter.const'
import { SHOWMODAL, HIDEMODAL } from './../const/modal.const' const initialState = {
count: 0,
// 增加控制modal 显示隐藏显示的状态,默认为隐藏状态
show: false
}
// eslint-disable-next-line import/no-anonymous-default-export
export default (state = initialState, action) => {
switch (action.type) {
case INCREMENT:
return {
count: state.count + action.payload
}
case DECREMENT:
return {
count: state.count - action.payload
}
case SHOWMODAL:
return {
show: true
}
case HIDEMODAL:
return {
show: false
} default:
return state
}
}
  1. 弹框的显示隐藏状态用display属性控制所以我们需要把状态映射到props属性中,因为show状态与show显示方法重名了,所以给show状态起一个别名,利用 bindActionCreators 方法把 执行 dispatch 提交actions的方法映射到props中
import React from 'react'
import { connect } from 'react-redux'
import * as modalActions from './../store/actions/modal.actions'
import { bindActionCreators } from 'redux' function Modal ({ showState, show, hide }) {
const styles = {
width: 200,
height: 200,
position: 'absolute',
top: '50%',
left: '50%',
marginTop: -100,
marginLeft: -100,
backgroundColor: 'skyblue',
// 增加控制显示隐藏的css样式
display: showState ? 'block' : 'none'
}
return <div>
<button onClick={show}>显示</button>
<button onClick={hide}>隐藏</button>
<div style={styles}></div>
</div>
}
// 映射显示英藏状态到props中
const mapStateToProps = state => {
return {
showState: state.show
}
}
// 把提交actions方法映射到组件props中
const mapDispacthToProps = dispatch => bindActionCreators(modalActions, dispatch)
export default connect(mapStateToProps,mapDispacthToProps)(Modal)

通过上面我们发现在点击显示与隐藏之后计数器组件中的数字不见了,因为我们在执行显示与隐藏的方法中并没有返回 计数器的状态所以这个状态丢失掉了,我们需要在更改状态的时候去补上原有的状态

  1. 补上原有状态
export default (state = initialState, action) => {
switch (action.type) {
case INCREMENT:
return {
...state,
count: state.count + action.payload
}
case DECREMENT:
return {
...state,
count: state.count - action.payload
}
case SHOWMODAL:
return {
...state,
show: true
}
case HIDEMODAL:
return {
...state,
show: false
} default:
return state
}
}

这个时候我们的计数器与弹出框组件都已经正常了,但是我们发现reducer函数随着actions动作越来越多变的越来越臃肿,在状态越来越多以后将会变得无法维护

拆分reducer 函数

在计数器与弹出框案例中,在reducer函数中,我们既匹配到了计数器案例中的actions,又匹配到了弹出框案例中的actions 这样reducer中的代码将会越来越庞大,越来越臃肿,所以我们接下来拆分reducer,拆分reducer我们需要用到 combineReducers 方法,这个方法要求我们传递一个对象 这个对象是状态对象,返回值是合并后的reducer

  1. 创建 src/store/reducers/modal.reducers.js 文件,把弹出框的reducer抽离出来
import { SHOWMODAL, HIDEMODAL } from './../const/modal.const'

const initialState = {
show: false
} // eslint-disable-next-line import/no-anonymous-default-export
export default (state = initialState, action) => {
switch (action.type) { case SHOWMODAL:
return {
...state,
show: true
}
case HIDEMODAL:
return {
...state,
show: false
} default:
return state
}
}
  1. 创建src/store/reducers/root.reducers.js 文件,用于合并计数器与弹出框的reducer
import { combineReducers } from 'redux'
import CounterReducers from './counter.reducers'
import ModalReducers from './modal.reducers' // 要求我们传递一个对象 这个对象是状态对象
// 这样写了之后 状态的结构将是这样 counter: { count: 0 } modaler: { show: false }
export default combineReducers({
counter: CounterReducers,
modaler: ModalReducers
})
  1. 因为使用 combineReducers 合并reducer的时候改变了state的结构所以我们需要在组件中去更改获取state的方式
// src/components/Count.js
const mapStateProps = ({ counter }) => ({
count: counter.count,
a: '1'
})
// src/components/Modal.js
const mapStateToProps = ({ modaler }) => {
return {
showState: modaler.show
}
}

使用react+redux实现弹出框案例的更多相关文章

  1. JavaScript插件——弹出框

    (JavaScript插件——弹出框) 前言 阅读之前您也可以到Bootstrap3.0入门学习系列导航中进行查看http://www.cnblogs.com/aehyok/p/3404867.htm ...

  2. bootstrap中popover.js(弹出框)使用总结+案例

    bootstrap中popover.js(弹出框)使用总结+案例 *转载请注明出处: 作者:willingtolove: http://www.cnblogs.com/willingtolove/p/ ...

  3. 尝试用React写几个通用组件 - 带搜索功能的下拉列表,开关切换按钮,弹出框

    尝试用React写几个通用组件 - 带搜索功能的下拉列表,开关切换按钮,弹出框 近期正在逐步摸索学习React的用法,尝试着写几个通用型的组件,整体项目还是根据webpack+react+css-me ...

  4. react native仿微信性别选择-自定义弹出框

    简述 要实现微信性别选择需要使用两部分的技术: 第一.是自定义弹出框: 第二.单选框控件使用: 效果 实现 一.配置弹出框 弹出框用的是:react-native-popup-dialog(Git地址 ...

  5. [RN] React Native 封装选择弹出框(ios&android)

    之前看到react-native-image-picker中自带了一个选择器,可以选择拍照还是图库,但我们的项目中有多处用到这个选择弹出框,所以就自己写了一下,最最重要的是ios和Android通用. ...

  6. React native 的弹出层(输入)效果

    /*弹出层测试*/ import React,{Component} from 'react'; import { StyleSheet, View, Image, Text, TouchableOp ...

  7. 在ASP.NET MVC4中实现同页面增删改查,无弹出框01,Repository的搭建

    通常,在同一个页面上实现增删改查,会通过弹出框实现异步的添加和修改,这很好.但有些时候,是不希望在页面上弹出框的,我们可能会想到Knockoutjs,它能以MVVM模式实现同一个页面上的增删改查,再辅 ...

  8. Bootstrap popover弹出框

    popover被挤压.遮挡的问题: 弹出框显示的时候如果贴近一个列的边沿,就会很窄或被遮挡,解决起来很简单,只需在初始化的时候添加一个container属性就可以了: $(function (){ $ ...

  9. Selenium+java - 弹出框处理

    一.弹出框分类: 弹出框分为两种,一种基于原生JavaScript写出来的弹窗,另一种是自定义封装好的样式的弹出框,本文重点介绍原生JavaScript写出来的弹窗,另一种弹窗用click()基本就能 ...

随机推荐

  1. SingleSphere类定义

    针对于单个球体的碰撞,其实和多个球体一样的,只是我修改了书上的代码,定义了这么多类,终于到头了.马上就要展示奇迹的时候了. 类定义: #pragma once #ifndef __SINGLESPHE ...

  2. 宜宾市黑烟车电子抓拍系统App

    2020.11 - 2021.06负责手机App开发 项目说明:    主要用于管理人员的移动办公,通过与管理平台共享数据库,实现:人工审核.推送交警.账户管理.信息查询.数据统计.点位电子地图.设备 ...

  3. LuoguP2254 [NOI2005]瑰丽华尔兹 (单调队列优化DP)(用记忆化过了。。。)

    记忆化 #include <cstdio> #include <iostream> #include <cstring> #include <algorith ...

  4. pydantic 支持Dotenv 文件设置变量

    1. 安装 pip install pydantic pip install pydantic[dotenv] 注意: 安装pip install pydantic[dotenv]时会提示no mat ...

  5. 【java】学习路径38-数学模型分析:不同方式复制文件所需的时间

    测试文件:一段72kb的文本.约5.6MB大小的pdf论文.约38.9MB大小的无损音频文件. demo001 论<到灯塔去>的凝视主题.pdf irreplaceable.movpkg ...

  6. Prometheus教程

    Prometheus介绍 主要特征 使用时间序列数据(tsdb)的多维度数据模型 灵活的查询语言(PromQL) 不依赖分布式存储,单个节点是自主的 通过http请求拉取(pull)时间序列数据(ts ...

  7. python进阶__用socket封装TCP

    想要理解socket协议,点击链接,出门左转 一.TCP 通信的服务器端编程的基本步骤: 服务器端先创建一个 socket 对象. 服务器端 socket 将自己绑定到指定 IP 地址和端口. 服务器 ...

  8. 记pyautogui使用方法

    记录学习过程,本人喜欢简洁不啰嗦: 控制鼠标 1 pyautogui.moveTo(w - 100, h - 100, duration=0.25) # 立即移动到指定x, y位置坐标, durati ...

  9. 第一章 kubernetes概述

    一.Kubernetes概述 1.官网地址:https://kubernetes.io 2.GuiHub:https://github.com/kubernetes/kubernetes 3.又来:谷 ...

  10. Taurus.MVC-Java 版本打包上传到Maven中央仓库(详细过程):1、JIRA账号注册

    文章目录: Taurus.MVC-Java 版本打包上传到Maven中央仓库(详细过程):1.JIRA账号注册 Taurus.MVC-Java 版本打包上传到Maven中央仓库(详细过程):2.PGP ...