64 lines
2.1 KiB
JavaScript
64 lines
2.1 KiB
JavaScript
import { IoMdArrowDropdown } from "react-icons/io";
|
|
import React, { useState, useRef, useEffect } from 'react';
|
|
import "../Popover/PopOver.scss";
|
|
|
|
const PopOver = ({ children, content, placement = 'bottom', trigger = 'click', openDelay = 300, closeDelay = 300 }) => {
|
|
const [visible, setVisible] = useState(false);
|
|
const [timeoutId, setTimeoutId] = useState(null);
|
|
const popoverRef = useRef(null);
|
|
const targetRef = useRef(null);
|
|
|
|
const handleToggle = () => {
|
|
if (trigger === 'click') {
|
|
setVisible(prevVisible => !prevVisible);
|
|
}
|
|
};
|
|
|
|
const handleMouseEnter = () => {
|
|
if (trigger === 'hover') {
|
|
clearTimeout(timeoutId);
|
|
setTimeoutId(setTimeout(() => setVisible(true), openDelay));
|
|
}
|
|
};
|
|
|
|
const handleMouseLeave = () => {
|
|
if (trigger === 'hover') {
|
|
clearTimeout(timeoutId);
|
|
setTimeoutId(setTimeout(() => setVisible(false), closeDelay));
|
|
}
|
|
};
|
|
|
|
const handleClickOutside = (e) => {
|
|
if (popoverRef.current && !popoverRef.current.contains(e.target) &&
|
|
targetRef.current && !targetRef.current.contains(e.target)) {
|
|
setVisible(false);
|
|
}
|
|
};
|
|
|
|
useEffect(() => {
|
|
document.addEventListener('mousedown', handleClickOutside);
|
|
return () => document.removeEventListener('mousedown', handleClickOutside);
|
|
}, []);
|
|
|
|
useEffect(() => {
|
|
return () => clearTimeout(timeoutId);
|
|
}, [timeoutId]);
|
|
|
|
return (
|
|
<div ref={targetRef} className="popover-container"
|
|
onClick={trigger === 'click' ? handleToggle : null}
|
|
onMouseEnter={handleMouseEnter}
|
|
onMouseLeave={handleMouseLeave}
|
|
>
|
|
|
|
{children}
|
|
<div ref={popoverRef} className={`popover-content ${visible ? 'visible' : 'hidden'}`} style={{ top: placement === 'bottom' ? '100%' : 'auto', bottom: placement === 'top' ? '100%' : 'auto' }}>
|
|
{content}
|
|
<IoMdArrowDropdown size={20} color="#FFF" className="iconarrow" />
|
|
</div>
|
|
</div>
|
|
);
|
|
};
|
|
|
|
export default PopOver;
|