【问题标题】:React hook: How to call Modal component from another component in react反应钩子:如何从反应中的另一个组件调用模态组件
【发布时间】:2021-03-13 20:55:25
【问题描述】:

我正在尝试创建一个可以从多个组件重用/调用的模式。我希望模态显示在 app.js 中,但按钮调用在另一个组件上。

一旦我能够实现一个,我可以在其他组件上按按钮并调用相同的模态,而不必为每个组件创建相同的模态

<div className="App">
      <HeroSlider />
      <HowItWorks />
      <Modal />
      <Footer />
    </div>

模态按钮在这个组件上(HeroSlider)。单击后,它将调用模态组件并将其显示在 app.js 中

import React, { useState } from "react";
import Header from './Header'

function HeroSlider(props) {
    const [show, setShow] = useState(false);
    const modalShow = () => setShow(true);
    const openIsAccount = () => {

    }
    return (

 <div className="jumbotron" id="jumbotron2" >
<button type="button" className="btn btn-primary" id="shoutBtn" onClick={modalShow}><span>Get Started</span>
</button>
 </div>
    );
}

export default HeroSlider;

这里是 Modal.js

const IsAccountOpen = (props) => {
    const [show, setShow] = useState(false);
    const handleClose = () => setShow(false);
    const handleShow = () => setShow(true);

    return (
        <>
            <Modal show={props.show} onHide={handleClose} backdrop="static" keyboard={false}>
                <Modal.Header closeButton>
                    <Modal.Title>Modal title</Modal.Title>
                </Modal.Header>
                <Modal.Body>
                    I will not close 
                 </Modal.Body>
            </Modal>
        </>
    );

};

export default IsAccountOpen

【问题讨论】:

  • 我同意@Jkartunen。您可能希望将模式的状态提取到应用程序级别,并可能使用 context 或 redux 作为全局状态容器。或者,如果您想避免使用大量回调来更改模式的状态,至少要这样做。
  • 谢谢大家,我听从了大家的建议,将模态设置为应用级别。我仍在研究它,看看它在将要调用它的其他组件上的表现如何

标签: javascript reactjs react-hooks modal-dialog


【解决方案1】:

您需要在 app.js 中添加一个函数来处理按钮的点击,因此该函数会将状态显示更改为 true,并且您会将状态传递给您的 modal,如下所示:

App.js

[showState, setShowState] = useState(false)
buttonClickedHandler = () => {
   setShowState((showState) => showState = !showState )
}

<div className="App">
      <HeroSlider buttonClicked={buttonClickedHandler} />
      <HowItWorks />
      <Modal show={showState} buttonClicked={buttonClickedHandler} />
      <Footer />
</div>

HeroSlider.js

import React, { useState } from "react";
import Header from './Header'

function HeroSlider(props) {
    const [show, setShow] = useState(false);
    const modalShow = () => setShow(true);
    const openIsAccount = () => {

    }
    return (

 <div className="jumbotron" id="jumbotron2" >
<button type="button" className="btn btn-primary" id="shoutBtn" onClick={props.buttonClicked}><span>Get Started</span>
</button>
 </div>
    );
}

导出默认 HeroSlider;

IsAccountOpen.js

const IsAccountOpen = (props) => {
    const [show, setShow] = useState(false);
    const handleClose = () => setShow(false);
    const handleShow = () => setShow(true);

    return (
        <>
            <Modal show={props.show} onHide={props.buttonClicked} backdrop="static" keyboard={false}>
                <Modal.Header closeButton>
                    <Modal.Title>Modal title</Modal.Title>
                </Modal.Header>
                <Modal.Body>
                    I will not close 
                 </Modal.Body>
            </Modal>
        </>
    );

};

export default IsAccountOpen

我认为最好的解决方案是使用 redux,因为你需要从不同的组件访问和更新状态,你不应该使用上下文 API,因为状态变化频繁,你会碰到性能。

【讨论】:

  • 我在这里使用了您的代码,但它无法使用两个关闭按钮中的任何一个来关闭它
  • 是的,您需要将功能 buttonClicked 传递给我们的模态,我编辑了答案,检查一下。
【解决方案2】:

您需要将状态提取到应用级别,以便可以将其共享给组件。您可以使用 useState 来完成此操作,或者如果您想让它变得非常干净,则可以使用上下文和自定义钩子。但首先要使用 useState。

HeroSlider 应该在它的 props 中接收 modalShow 函数。 Modal.js 应该接收显示状态作为道具。

【讨论】:

    猜你喜欢
    • 2020-04-01
    • 1970-01-01
    • 2019-03-29
    • 1970-01-01
    • 2020-10-12
    • 1970-01-01
    • 1970-01-01
    • 2019-09-17
    • 2020-11-25
    相关资源
    最近更新 更多