Pai*_*ikz 6 reactjs redux material-ui react-redux
模态在 App.js 中的 hashRouter 下呈现。当其状态 isOpen 为真时显示模态。
尝试使用 react redux 显示 Modal 时出现此错误。
Warning: Function components cannot be given refs. Attempts to access this ref will fail. Did you mean to use React.forwardRef()?
Check the render method of `TrapFocus`.
in ConnectFunction (at Modal.js:41)
in TrapFocus (created by ForwardRef(Modal))
in div (created by ForwardRef(Modal))
in ForwardRef(Portal) (created by ForwardRef(Modal))
in ForwardRef(Modal) (at Modal.js:35)
in Modal (created by ConnectFunction)
in ConnectFunction (created by WithStyles(undefined))
in WithStyles(undefined) (at App.js:46)
in ThemeProvider (at App.js:24)
in App (created by WithStyles(App))
in WithStyles(App) (at src/index.js:13)
in Provider (at src/index.js:12)
Run Code Online (Sandbox Code Playgroud)
这是我的代码:
Modal.js
import React, { Component } from "react";
import { compose } from "redux";
import PropTypes from "prop-types";
import { connect } from "react-redux";
import { Modal as MaterialModal } from "@material-ui/core";
import { withStyles } from "@material-ui/styles";
import { closeModal } from "../store/actions/actions-ui";
import BasicModal from "./Modals/BasicModal";
const ModalTypes = {
BasicModal,
};
const styles = {
modal: {
display: "flex",
justifyContent: "center",
alignItems: "center",
},
};
class Modal extends Component {
handleCloseModal = () => {
const { dispatch, shouldCloseOnBackgroundTouch } = this.props;
if (shouldCloseOnBackgroundTouch) dispatch(closeModal());
};
render() {
const { modalType, data, isOpen, classes } = this.props;
if (!modalType) {
return null;
}
const ModalToRender = ModalTypes[modalType];
return (
<MaterialModal
disableAutoFocus
className={classes.modal}
open={isOpen}
onClose={this.handleCloseModal}
>
<ModalToRender {...data} />
</MaterialModal>
);
}
}
Modal.propTypes = {
dispatch: PropTypes.func.isRequired,
isOpen: PropTypes.bool.isRequired,
modalType: PropTypes.string,
// eslint-disable-next-line react/forbid-prop-types
data: PropTypes.object,
shouldCloseOnBackgroundTouch: PropTypes.bool.isRequired,
classes: PropTypes.objectOf(PropTypes.string).isRequired,
};
Modal.defaultProps = {
data: {},
modalType: "",
};
const mapStateToProps = (state) => ({
isOpen: state.ui.modalState.isOpen,
shouldCloseOnBackgroundTouch: state.ui.modalState.shouldCloseOnBackgroundTouch,
modalType: state.ui.modalState.modalType,
data: state.ui.modalState.data,
});
export default compose(
withStyles(styles),
connect(mapStateToProps)
)(Modal);
Run Code Online (Sandbox Code Playgroud)
BasicModal.js
import React, { Component } from "react";
import { connect } from "react-redux";
import PropTypes from "prop-types";
import Button from "@material-ui/core/Button";
import Typography from "@material-ui/core/Typography";
import Paper from "@material-ui/core/Paper";
import If from "../__helpers__/If";
import { closeModal } from "../../store/actions/actions-ui";
class BasicModal extends Component {
handleClose = () => {
const { dispatch } = this.props;
dispatch(closeModal());
};
render() {
const { title, text, extraBtnText, extraBtnAction } = this.props;
return (
<Paper>
<If truthy={title}>
<Typography gutterBottom variant="h4">
{title}
</Typography>
</If>
<If truthy={text}>
<Typography gutterBottom vairant="body2">
{text}
</Typography>
</If>
<Button onClick={this.handleClose}>Close</Button>
<If truthy={extraBtnAction && extraBtnText}>
<Button
onClick={() => {
extraBtnAction();
this.handleClose();
}}
>
{extraBtnText}
</Button>
</If>
</Paper>
);
}
}
BasicModal.propTypes = {
dispatch: PropTypes.func.isRequired,
title: PropTypes.string.isRequired,
text: PropTypes.string.isRequired,
extraBtnText: PropTypes.string,
extraBtnAction: PropTypes.func,
};
export default connect()(BasicModal);
Run Code Online (Sandbox Code Playgroud)
我猜问题在于我试图渲染这样的组件:
<ModalToRender {...data} />
Run Code Online (Sandbox Code Playgroud)
但我似乎无法理解它有什么问题。
任何帮助表示赞赏!
Rya*_*ell 10
对于由 Material-UI 包装的组件(例如),您需要在 connect() 中使用forwardRef 选项。BasicModalModal
例子:
export default connect(null, null, null, {forwardRef: true})(BasicModal);
Run Code Online (Sandbox Code Playgroud)
Refs提供对 React 元素的 DOM 节点的访问。Material-UI TrapFocus(由 使用Modal)使用传递给子项的 refModal来管理焦点方面。
在您的情况下,传递给的子Modal组件是connect()(BasicModal). 默认情况下,该包装器组件是一个函数组件,并且函数组件不能接受 refs,除非被forwardRef包装。
所述forwardRef的选择connect的原因它包裹使用功能部件React.forwardRef,以便它可以成功地接受其沿着给被包装分量通过一个REF(BasicModal你的情况)。
| 归档时间: |
|
| 查看次数: |
5113 次 |
| 最近记录: |