ค้นหาเว็บไซต์

javascript - ซ่อน div เมื่อคลิกภายนอก typescript, nextjs tailwindcss


ฉันมีโมดอลที่เขียนด้วย TypeScript, Next.js และ TailwindCSS ฉันต้องการซ่อนโมดอลเมื่อฉันคลิกลนอกโมดอล แต่ฉันพบข้อผิดพลาดเรื่องชนิดข้อมูลและข้อผิดพลาดอื่น ๆ ใน tsx

ใน JSX มันทำงานได้ดีแต่ใน TSX มันไม่ทำงาน ผมจะขอบคุณมากๆ ถ้าใครช่วยผมเรื่องนี้ได้ ขอบคุณล่วงหน้า

import { useRef, useEffect } from 'react';

const Backdrop = (props) => {

    const ref = useRef();
    const { onClick, children } = props;

    const handleClickOutside = (event) => {
        if (ref.current && !ref.current.contains(event.target)) {
            onClick && onClick();
        }
    };

    useEffect(() => {
        document.addEventListener("click", handleClickOutside, true);
        return () => {
            document.removeEventListener("click", handleClickOutside, true);
        };
    }, []);

    if (!children) {
        return null;
    }

    return (
        <div ref={ref}>
            {children}
        </div>
    );
}

export default Backdrop;

คำตอบ #1

สร้างไฟล์ useIsClickOut.ts คัดลอกโค้ดนี้และวาง

import { useEffect, useState, useCallback } from "react";

export const useIsClickOut = (setter: (bool: boolean) => void): [(node: any) => void] => {
    const [ele, setEle] = useState<HTMLDivElement | null>(null)
    const eleCallback = useCallback((node: HTMLDivElement) => { 
setEle(node) }, [])

useEffect(() => {
    if (ele === null) return;

    const handleClick = (e: any) => {
        if (ele.contains(e.target)) return;
        setter(false)
    }

    document.addEventListener("mousedown", handleClick);
    return () => document.removeEventListener("mousedown", handleClick);
}, [ele]);

 return [eleCallback]
};

export default useIsClickOut;

ในไฟล์ของคุณ นี่คือวิธีใช้มัน

const [open, setOpen] = useState(false)
const [eleCallBack] = useIsClickOut(setOpen)
     
return !open ? null : (
   <div ref={eleCallBack}>
      {children}
   </div>
);