I have created a custom modal hook that extending react-modal
library, but I have a problem to work with inputs when it has onChange prop on the input, for some reason, it rerenders useModalHook component every time when input change happened. I am new to hooks, but is there a way to pass a hook wrapper that doesn't rerender the component and leaves it as is. My goals are to wrap any component or content that I pass through my custom modal so that it has a custom layout as I needed.
import * as React from "react";
import Modal from "react-modal";
import styles from "../styles.scss";
export const useModalHook = (
{
title = "",
modalType = MODAL_TYPE.small,
closeIcon = true,
}
) => {
const [ getOpenModal, setOpenModal ] = React
.useState<boolean>(false);
React.useEffect(() => {
if (state) {
setOpenModal(!state);
}
return () => setOpenModal(false);
}, [ state ]);
const handleOnRequestClose = (force = false) => setOpenModal(force);
return {
Modal: ({ children }) => getOpenModal && (
<Modal
isOpen={getOpenModal}
onRequestClose={() => handleOnRequestClose()}
contentLabel={title}
appElement={document.getElementById("__next")}
>
<div className={styles.modalWrapper}>
<div className={styles.modalTitle}>
{title !== "" ? <h2>{title}</h2> : null}
{closeIcon ? (
<button
className={styles.closeModal}
onClick={() => setOpenModal(!getOpenModal)}
>x</button>
) : null}
</div>
{children}
</div>
</Modal>
),
closeModal: () => setOpenModal(false),
toggleModal: () => setOpenModal(!getOpenModal),
modalOpen: getOpenModal,
};
};
Usage of the useModalHook
in component
import * as React from "react";
import { useModalHook } from "components/UI/Hooks/useModalHook";
const Component = () => {
const initialData = { Test: "" };
const { Modal, toggleModal, modalOpen, closeModal } = useModalHook({
title: "Cool Modal"
});
const handleOnChange = e => {
return setData({
...getData,
[ name ]: value
});
};
React.useEffect(() => {
setData(initialData);
}, [ modalOpen ]);
return (
<>
<button onClick={toggleModal}>Show</button>
<Modal>
<div className="modal_content">
<input type="text" onChange={handleOnChange} value={getData.Test} name="Test"/>
</div>
</Modal>
</>
);
};
export default Component;