@fluent-windows/hooks
Version:
Fluent-Windows React hooks.
70 lines (66 loc) • 1.88 kB
JavaScript
/**
* Toast using functional calls
*
* Demo
* import { useMessage } from '@fluent-windows/hooks'
*
const [handleOpen, handleClose] = useMessage(
(visible, content, close) => (
<Toast
visible={visible}
actions={
<IconButton onClick={close}>
<Icon.Cancel />
</IconButton>
}
>
{content}
</Toast>
),
0
)
function handleClick() {
handleOpen('hello world!')
}
return (
<>
<Button onClick={handleClick}>open</Button>
<Button onClick={handleClose}>close</Button>
</>
)
*/
import * as React from 'react';
import * as ReactDOM from 'react-dom';
import useGlobal from '../useGlobal';
function useMessage(functionContainer, duration = 3000) {
const [visible, setVisible] = React.useState(false);
const [content, setContent] = React.useState('');
const handleClose = React.useCallback(() => {
setVisible(false);
}, []);
const global = useGlobal();
const ref = React.useRef(global && global.document && global.document.createElement('div'));
React.useEffect(() => {
if (visible === true) {
global.document.body.appendChild(ref.current);
ReactDOM.render(functionContainer(visible, content, handleClose), ref.current);
duration && setTimeout(() => {
handleClose();
}, duration);
}
}, [duration, visible, content]); // eslint-disable-line
React.useEffect(() => {
if (visible === false) {
const unmountResult = ReactDOM.unmountComponentAtNode(ref.current);
if (unmountResult && ref.current.parentNode) {
ref.current.parentNode.removeChild(ref.current);
}
}
}, [duration, visible]);
const handleOpen = React.useCallback(_content => {
setContent(_content);
setVisible(true);
}, []);
return [handleOpen, handleClose];
}
export default useMessage;