This is the 6th day of my participation in the August More Text Challenge

There are two options for implementing the React dialog:

  • Use a UI component library: such as Antd’s component — Modal
  • Native React Portals

In actual development, we mostly choose to use Antd dialogs directly. In fact, Antd dialogs are also implemented on the basis of React Portals, so it can give us a wider path on the floating layer.

React PortalsWhat is?

React maintains a Virtual Dom Tree in memory. This Tree maps to real Dom nodes. Portal interrupts this mapping. It provides an excellent solution for rendering child nodes to DOM nodes that exist outside of the parent component, solving the problem of floating layers at a stroke: Dialog, Tooltip, etc.

usage

ReactDOM.createPortal(child, container);
Copy the code

The first argument (child) is any renderable React child, such as an element, string, or fragment. The second argument (container) is a DOM element.

Note that although the Child appears to be on a different Dom tree, it is actually the same child in the Virtual Dom, as you will see in the following example.

The Dialog Antd

According to the official website documentation, getting started is very easy

import React, { useState } from 'react';
import { Modal, Button } from 'antd';

const DialogPage = () = > {
  const [isModalVisible, setIsModalVisible] = useState(false);

  const showModal = () = > {
    setIsModalVisible(true);
  };

  const handleOk = () = > {
    setIsModalVisible(false);
  };

  const handleCancel = () = > {
    setIsModalVisible(false);
  };

  return (
    <>
      <Button type="primary" onClick={showModal}>
        Open Antd Modal
      </Button>
      <Modal
        title="Basic Modal"
        visible={isModalVisible}
        onOk={handleOk}
        onCancel={handleCancel}
      >
        <p>Some contents...</p>
        <p>Some contents...</p>
        <p>Some contents...</p>
      </Modal>
    </>
  );
};

export default DialogPage;
Copy the code

Portals of the Dialog

In index.html, create a dialog container element:

<div id="root"></div>
<div id="dialog-root"></div>
Copy the code

Control Dialog rendering via component internal state (visible) :

{
  visible
    ? createPortal(
        <div className="portal-sample">
          {children}
          <Button onClick={onHide}>close</Button>
        </div>.document.getElementById('dialog-root')) :null;
}
Copy the code

React Components: PortalDialog and DialogPage still exist:

The complete code

pages/dialog.js

import React, { useState } from 'react';
import { Button } from 'antd';
import PortalDialog from '@/components/PortalDialog';

const DialogPage = () = > {
  const [isPortalVisible, setIsPortalVisible] = useState(false);

  const showPortal = () = > {
    setIsPortalVisible(true);
  };

  const hidePortal = () = > {
    setIsPortalVisible(false);
  };

  return (
    <>
      <Button style={{ marginLeft: '20px'}}onClick={showPortal}>React Portals</Button>
      <PortalDialog visible={isPortalVisible} onHide={hidePortal}>
        <div>dialog-children</div>
      </PortalDialog>
    </>
  );
};

export default DialogPage;
Copy the code

components/PortalDialog/index.js

import { createPortal } from 'react-dom';
import { Button } from 'antd';
import './style.css';

const PortalDialog = (props) = > {
  const { visible, children, onHide } = props;
  return visible
    ? createPortal(
        <div className="portal-sample">
          {children}
          <Button onClick={onHide}>close</Button>
        </div>.document.getElementById('dialog-root')) :null;
};

export default PortalDialog;
Copy the code

components/PortalDialog/style.css

.portal-sample {
  position: absolute;
  padding: 20px;
  width: 500px;
  height: 300px;
  left: 50%;
  top: 50%;
  transform: translate(-50%, -50%);
  background-color: #fff;
  border-radius: 10px;
  border: 1px solid #ddd;
  box-shadow: 0px 0px 20px 2px #ddd;
}
Copy the code

React Best Practices

  • React Best practice: Create a drag-and-drop list by hand
  • React Best Practice: Integrating third-party Libraries (d3.js)
  • React Best Practices: How to Implement Native Portals
  • React best practice: Drag-and-drop sidebar
  • React best practice: Implement step-by-step operations based on routes
  • React best practice: Work with multiple data sources
  • React best practice: Complete a list of requirements
  • React best practice: Dynamic forms