react hook + typescript 弹窗(不带遮罩)

解释一下:createPortal

通过createPortal渲染的元素会被添加到另外的节点,同时点击事件会被触发。
而通过ReactDOM.render渲染的元素添加到新节点,但是点击事件没有触发。

弹窗 index.tsx

import React, { forwardRef, useEffect, useState } from 'react';
import styles from './index.module.less';
import close from '../../assets/images/close.png';
import classNames from 'classnames';
import { ReactNode } from 'react';
import { createPortal } from 'react-dom';

type KxModalProps = {
  title?: string;
  visible: boolean;
  onCancel?: (boo: boolean) => void;
  className?: string;
  style?: React.CSSProperties;
  children: ReactNode;
};

const KxModal = forwardRef((props: KxModalProps, ref: any) => {
  const { title, visible, onCancel, children, className, style } = props;

  // if (!visible) return null; //打开没有动画

  return createPortal(
    
{title}
onCancel!(false)} />
{children}
, document.body, ); }); export { KxModal };

弹窗 index.module.less

解释一下 .module.less: 因为用的 vite 构建工具

.modalWrap {
  position: fixed;
  top: 40%;
  left: 50%;
  z-index: 9;
  width: 945px; 
  height: 1323px;
  padding: 92px 40px 42px;
  overflow: hidden;
  color: #fff;
  font-size: 38px;
  background-image: url(../../assets/images/rightwrap-bg2.png);
  background-size: 100% 100%;
  transform: translate(-50%, -40%) scale(0);
  transition: ease-in-out 0.5s;
  .titleWrap {
    position: absolute;
    top: 0;
    left: 0;
    display: flex;
    justify-content: space-between;
    width: 100%;
    padding: 0 15px;
    font-size: 48px;

    .close {
      width: 60px;
      margin-top: 15px;
      cursor: pointer;
    }
  }
  &.visible {
    transform: translate(-50%, -50%) scale(1);
    // animation: blockModal 0.5s;
  }
}

// @keyframes blockModal {
//   0% {
//     transform: translate(-50%, -50%) scale(0);
//   }
//   100% {
//     transform: translate(-50%, -50%) scale(1);
//   }
// }

效果

1628582446(1).jpg

你可能感兴趣的:(react hook + typescript 弹窗(不带遮罩))