react-use/src/createGlobalState.ts
2020-01-13 09:42:56 +08:00

32 lines
888 B
TypeScript

import { useLayoutEffect, useState } from 'react';
import useEffectOnce from './useEffectOnce';
export function createGlobalState<S = any>(initialState?: S) {
const store: { state: S | undefined; setState: (state: S) => void; setters: any[] } = {
state: initialState,
setState(state: S) {
store.state = state;
store.setters.forEach(setter => setter(store.state));
},
setters: [],
};
return (): [S | undefined, (state: S) => void] => {
const [globalState, stateSetter] = useState<S | undefined>(store.state);
useEffectOnce(() => () => {
store.setters = store.setters.filter(setter => setter !== stateSetter);
});
useLayoutEffect(() => {
if (!store.setters.includes(stateSetter)) {
store.setters.push(stateSetter);
}
});
return [globalState, store.setState];
};
}
export default createGlobalState;