Modal transitions in ReactJS Tabler/Bootstrap
P粉071559609
P粉071559609 2024-02-17 19:44:05
0
1
450

I'm building a Tabler dashboard using some ReactJS components. At first I used normal HTML pages and Jinja2 templates, but I started implementing ReactJS for some components.

I don't want to use too many third-party tools like react-tabler or bootstrap-tabler because it creates a lot of extra packages that I probably don't really need. I've been able to create a beautiful Tabler dashboard using ReactJS components without the need for these packages.

The only problem I have right now is showing the modal...right now this works, but the CSS transitions don't. At least not at first. I made them work like this:

// handle button click
const handleEditClick = (row) => {
    setIsModalOpen(true);
    modalRef.current.style.display = "block";

    // delay to make sure block is set first
    setTimeout(() => {
        modalRef.current.classList.add("show");
    }, 100);
};

The problem is, I don't really like this. It feels a bit cliche.

The display modal works fine, just add the style="display:block attribute first and then the show class. This way I can do it without too much extra JavaScript or works without other content. But display:block must be set first, if not, they seem to be set at the same time, or maybe display:block is set later, so you don't You will see the conversion.

I tried adding the following event lister modalRef.current.addEventListener("transitionend", handleTransitionEnd);, but I guess this only works for the actual transition and not for changing the style.

Is there a cleaner way than a 100 millisecond timeout? Apparently I can't add display:block by default because then my app will be inaccessible due to the transparent mode that is on top of my app.

P粉071559609
P粉071559609

reply all(1)
P粉274161593

This is how I fixed it now. I used useEffect twice, this is to prevent the class "show" from being added at the same time as the display:block style.

To close the modal, I can actually use the transitionend event listener.

const MyComponent = () => {
    const [isModalOpen, setIsModalOpen] = useState(false);
    const [isButtonClicked, setIsButtonClicked] = useState(false);
    const modalRef = useRef(null);

    const [isStyleApplied, setIsStyleApplied] = useState(false);
    const [isClassApplied, setIsClassApplied] = useState(false);

    const handleEditClick = () => {
        setIsModalOpen(true);
        setIsButtonClicked(true);
    };

    useEffect(() => {
        const applyStyle = () => {
            if (modalRef.current && !isStyleApplied && isButtonClicked) {
                modalRef.current.style.display = 'block';
                setIsStyleApplied(true);
            }
        };

        applyStyle();
    }, [isButtonClicked, isStyleApplied]);

    useEffect(() => {
        const applyClass = () => {
            if (modalRef.current && isButtonClicked && isStyleApplied && !isClassApplied) {
                modalRef.current.classList.add('show');
                setIsClassApplied(true);
            }
        };

        applyClass();
    }, [isButtonClicked, isStyleApplied, isClassApplied]);


    const handleCloseModal = () => {
        setIsModalOpen(false);

        modalRef.current.addEventListener("transitionend", handleTransitionEnd);
        modalRef.current.classList.remove("show");

        function handleTransitionEnd() {
            modalRef.current.removeEventListener("transitionend", handleTransitionEnd);
            modalRef.current.style.display = "none";
        }
        setIsButtonClicked(false);
        setIsStyleApplied(false);
        setIsClassApplied(false);
    };

    return (
         handleEditClick(row)} href="#">Open Modal
        
    );
}
Latest Downloads
More>
Web Effects
Website Source Code
Website Materials
Front End Template