发布于 2026-01-05 4 阅读
0

如何在 React 中创建模态框?让我们来编写代码。

如何在 React 中创建模态框

让我们开始编程吧

React 中最常用的组件之一无疑是模态框,因为它们可以在不同的场景中使用,从消息传递到用户输入。

与 React 中的许多其他组件一样,可以安装依赖项来帮助完成此过程,但是我们最终总会在几个方面受到限制,其中之一就是样式。

因此,我萌生了撰写本文的想法,我们将运用我们已经掌握的 CSS、属性和钩子等知识。

让我们开始编程吧

今天我们唯一要安装的就是一个图标库,以便更方便使用(不过,如果您使用网络字体,效果也一样):

npm install react-icons
Enter fullscreen mode Exit fullscreen mode

现在我们可以立即开始工作了Modal.jsx。但首先让我们来谈谈 CSS。

我们将要开设的一个类就叫做.darkBG“模态框”,因为模态框打开后,我会添加一个背景色来稍微遮盖页面上的其他组件。这样做是为了让用户的注意力只集中在模态框上。

然后,我们的组件将分为三个区域,第一个区域是头部,您可以在这里放置模态框标题。第二个区域是内容,您可以在这里放置您想要的消息。

第三部分也是最后一部分将介绍可以在模态框中执行的操作,即取消模态框以将其关闭,以及其他操作(保存、更新、删除等)。

现在我们已经有了一些概念,您可以复制这段 CSS 代码(您可以自由修改它来自定义您的模态框):

/* @src/components/Modal.module.css */

.darkBG {
  background-color: rgba(0, 0, 0, 0.2);
  width: 100vw;
  height: 100vh;
  z-index: 0;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  position: absolute;
}

.centered {
  position: fixed;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
}

.modal {
  width: 250px;
  height: 170px;
  background: white;
  color: white;
  z-index: 10;
  border-radius: 16px;
  box-shadow: 0 5px 20px 0 rgba(0, 0, 0, 0.04);
}

.modalHeader {
  height: 50px;
  background: white;
  overflow: hidden;
  border-top-left-radius: 16px;
  border-top-right-radius: 16px;
}

.heading {
  margin: 0;
  padding: 10px;
  color: #2c3e50;
  font-weight: 500;
  font-size: 18px;
  text-align: center;
}

.modalContent {
  padding: 10px;
  font-size: 14px;
  color: #2c3e50;
  text-align: center;
}

.modalActions {
  position: absolute;
  bottom: 2px;
  margin-bottom: 10px;
  width: 100%;
}

.actionsContainer {
  display: flex;
  justify-content: space-around;
  align-items: center;
}

.closeBtn {
  cursor: pointer;
  font-weight: 500;
  padding: 4px 8px;
  border-radius: 8px;
  border: none;
  font-size: 18px;
  color: #2c3e50;
  background: white;
  transition: all 0.25s ease;
  box-shadow: 0 5px 20px 0 rgba(0, 0, 0, 0.06);
  position: absolute;
  right: 0;
  top: 0;
  align-self: flex-end;
  margin-top: -7px;
  margin-right: -7px;
}

.closeBtn:hover {
  box-shadow: 0 5px 20px 0 rgba(0, 0, 0, 0.04);
  transform: translate(-4px, 4px);
}

.deleteBtn {
  margin-top: 10px;
  cursor: pointer;
  font-weight: 500;
  padding: 11px 28px;
  border-radius: 12px;
  font-size: 0.8rem;
  border: none;
  color: #fff;
  background: #ff3e4e;
  transition: all 0.25s ease;
}

.deleteBtn:hover {
  box-shadow: 0 10px 20px -10px rgba(255, 62, 78, 0.6);
  transform: translateY(-5px);
  background: #ff3e4e;
}

.cancelBtn {
  margin-top: 10px;
  cursor: pointer;
  font-weight: 500;
  padding: 11px 28px;
  border-radius: 12px;
  font-size: 0.8rem;
  border: none;
  color: #2c3e50;
  background: #fcfcfc;
  transition: all 0.25s ease;
}

.cancelBtn:hover {
  box-shadow: none;
  transform: none;
  background: whitesmoke;
}
Enter fullscreen mode Exit fullscreen mode

如您所见,这些 CSS 类都非常简单,现在我们可以开始着手我们的工作了Modal.jsx

// @src/components/Modal.jsx

import React from "react";

const Modal = () => {
  return <h1>Hello Modal</h1>;
};

export default Modal;
Enter fullscreen mode Exit fullscreen mode

我们首先要添加的内容之一就是样式,在本文中,我们将使用 CSS 模块。

// @src/components/Modal.jsx

import React from "react";
import styles from "./Modal.module.css";

const Modal = () => {
  return <h1>Hello Modal</h1>;
};

export default Modal;
Enter fullscreen mode Exit fullscreen mode

我们的模态框中需要一个关闭按钮,为此我们需要图标,下面我们将导入要使用的图标:

// @src/components/Modal.jsx

import React from "react";
import styles from "./Modal.module.css";
import { RiCloseLine } from "react-icons/ri";

const Modal = () => {
  return <h1>Hello Modal</h1>;
};

export default Modal;
Enter fullscreen mode Exit fullscreen mode

有一点需要注意的是,我们需要接收 props,以便在模态框打开后立即将其关闭。因此,我们将接收一个名为 `close` 的函数作为 props setIsOpen()

// @src/components/Modal.jsx

import React from "react";
import styles from "./Modal.module.css";
import { RiCloseLine } from "react-icons/ri";

const Modal = ({ setIsOpen }) => {
  return <h1>Hello Modal</h1>;
};

export default Modal;
Enter fullscreen mode Exit fullscreen mode

完成以上步骤后,我们就可以开始制作模板了。首先,我们将添加深色背景,以便在模态框打开时更加醒目。

当用户点击深色背景时,我们希望关闭模态框,因此我们将添加onClickReact 事件并将一个布尔值作为函数的唯一参数传递setIsOpen()(在本例中为false)。

// @src/components/Modal.jsx

import React from "react";
import styles from "./Modal.module.css";
import { RiCloseLine } from "react-icons/ri";

const Modal = ({ setIsOpen }) => {
  return (
    <>
      <div className={styles.darkBG} onClick={() => setIsOpen(false)} />
      // ...
    </>
  );
};

export default Modal;
Enter fullscreen mode Exit fullscreen mode

现在我们要开始制作模态框了,所以我们要添加一个包装器,使模态框在屏幕上居中(.centered),以及模态框的主体(.modal)和它的标题(.modalHeader)。

// @src/components/Modal.jsx

import React from "react";
import styles from "./Modal.module.css";
import { RiCloseLine } from "react-icons/ri";

const Modal = ({ setIsOpen }) => {
  return (
    <>
      <div className={styles.darkBG} onClick={() => setIsOpen(false)} />
      <div className={styles.centered}>
        <div className={styles.modal}>
          <div className={styles.modalHeader}>
            <h5 className={styles.heading}>Dialog</h5>
          </div>
          // ...
        </div>
      </div>
    </>
  );
};

export default Modal;
Enter fullscreen mode Exit fullscreen mode

现在我们可以添加一个按钮,其中包含用于关闭模态框的图标,该按钮还将包含一个onClick事件,并将setIsOpen()函数传递给该事件,false以便在单击此按钮时立即关闭模态框。

// @src/components/Modal.jsx

import React from "react";
import styles from "./Modal.module.css";
import { RiCloseLine } from "react-icons/ri";

const Modal = ({ setIsOpen }) => {
  return (
    <>
      <div className={styles.darkBG} onClick={() => setIsOpen(false)} />
      <div className={styles.centered}>
        <div className={styles.modal}>
          <div className={styles.modalHeader}>
            <h5 className={styles.heading}>Dialog</h5>
          </div>
          <button className={styles.closeBtn} onClick={() => setIsOpen(false)}>
            <RiCloseLine style={{ marginBottom: "-3px" }} />
          </button>
          // ...
        </div>
      </div>
    </>
  );
};

export default Modal;
Enter fullscreen mode Exit fullscreen mode

现在我们可以添加模态框的内容(.modalContent)并添加一条消息。

// @src/components/Modal.jsx

import React from "react";
import styles from "./Modal.module.css";
import { RiCloseLine } from "react-icons/ri";

const Modal = ({ setIsOpen }) => {
  return (
    <>
      <div className={styles.darkBG} onClick={() => setIsOpen(false)} />
      <div className={styles.centered}>
        <div className={styles.modal}>
          <div className={styles.modalHeader}>
            <h5 className={styles.heading}>Dialog</h5>
          </div>
          <button className={styles.closeBtn} onClick={() => setIsOpen(false)}>
            <RiCloseLine style={{ marginBottom: "-3px" }} />
          </button>
          <div className={styles.modalContent}>
            Are you sure you want to delete the item?
          </div>
          // ...
        </div>
      </div>
    </>
  );
};

export default Modal;
Enter fullscreen mode Exit fullscreen mode

我们现在就可以开始编写操作步骤了。这样,我们就可以添加包装样式及其按钮。

// @src/components/Modal.jsx

import React from "react";
import styles from "./Modal.module.css";
import { RiCloseLine } from "react-icons/ri";

const Modal = ({ setIsOpen }) => {
  return (
    <>
      <div className={styles.darkBG} onClick={() => setIsOpen(false)} />
      <div className={styles.centered}>
        <div className={styles.modal}>
          <div className={styles.modalHeader}>
            <h5 className={styles.heading}>Dialog</h5>
          </div>
          <button className={styles.closeBtn} onClick={() => setIsOpen(false)}>
            <RiCloseLine style={{ marginBottom: "-3px" }} />
          </button>
          <div className={styles.modalContent}>
            Are you sure you want to delete the item?
          </div>
          <div className={styles.modalActions}>
            <div className={styles.actionsContainer}>
              <button className={styles.deleteBtn} onClick={() => setIsOpen(false)}>
                Delete
              </button>
              <button
                className={styles.cancelBtn}
                onClick={() => setIsOpen(false)}
              >
                Cancel
              </button>
            </div>
          </div>
        </div>
      </div>
    </>
  );
};

export default Modal;
Enter fullscreen mode Exit fullscreen mode

现在模态框组件已经完成,只需将其添加到我们的页面即可。App.jsx但首先,让我们创建以下样式,以便在页面上添加一个更方便的按钮:

/* @src/App.module.css */

.primaryBtn {
  margin: 20px 10px;
  cursor: pointer;
  font-weight: 500;
  padding: 13px 25px;
  border-radius: 15px;
  font-size: 0.8rem;
  border: none;
  color: white;
  background: #185adb;
  transition: all 0.25s ease;
}

.primaryBtn:hover {
  transform: translateY(-5px);
  box-shadow: 0 10px 20px -10px rgba(24, 90, 219, 0.6);
}
Enter fullscreen mode Exit fullscreen mode

现在我们可以开始着手开发了App.jsx。首先,我们将导入相关库useState(),并创建一个名为 isOpen 的状态和 setIsOpen 函数。

// @src/App.jsx

import React, { useState } from "react";
import styles from "./App.module.css";

const App = () => {
  const [isOpen, setIsOpen] = useState(false);
  return (
    <main>
      <button className={styles.primaryBtn} onClick={() => setIsOpen(true)}>
        Open Modal
      </button>
      // ...
    </main>
  );
};

export default App;
Enter fullscreen mode Exit fullscreen mode

然后我们进行条件渲染,仅当 isOpen 状态为 true 时才显示模态框。同样,我们会将该setIsOpen()函数作为 prop 传递。

// @src/App.jsx

import React, { useState } from "react";
import styles from "./App.module.css";

import Modal from "./components/Modal";

const App = () => {
  const [isOpen, setIsOpen] = useState(false);
  return (
    <main>
      <button className={styles.primaryBtn} onClick={() => setIsOpen(true)}>
        Open Modal
      </button>
      {isOpen && <Modal setIsOpen={setIsOpen} />}
    </main>
  );
};

export default App;
Enter fullscreen mode Exit fullscreen mode

你应该会得到类似这样的结果:

最终应用程序

结论

和往常一样,希望您觉得这篇文章有趣。如果您发现文章中有任何错误,请在评论区指出。🤩

祝你今天过得愉快!🪗 🙌

文章来源:https://dev.to/franciscomendes10866/how-to-create-a-modal-in-react-3coc