diff --git a/snippets/useHash.md b/snippets/useHash.md index 5ba1eb629..692d8cbeb 100644 --- a/snippets/useHash.md +++ b/snippets/useHash.md @@ -4,7 +4,7 @@ tags: hooks,state,effect,advanced firstSeen: 2021-10-02T05:00:00-04:00 --- -Tracks the browser's location hash value, and allows changin it. +Tracks the browser's location hash value, and allows changing it. - Use the `useState()` hook to lazily get the `hash` property of the `Location` object. - Use the `useCallback()` hook to create a handler that updates the state. diff --git a/snippets/useSearchParam.md b/snippets/useSearchParam.md new file mode 100644 index 000000000..da9a861af --- /dev/null +++ b/snippets/useSearchParam.md @@ -0,0 +1,64 @@ +--- +title: useSearchParam +tags: hooks,state,effect,intermediate +firstSeen: 2021-10-13T05:00:00-04:00 +--- + +Tracks the browser's location search param. + +- Use the `useCallback()` hook to create a callback that uses `new URLSearchParams()` to get the current value of `param`. +- Use the `useState()` hook to create a state variable that holds the current value of the `param`. +- Use the `useEffect()` hook to set appropriate event listeners to update the state variable when mounting and clean them up when unmounting. + +```jsx +const useSearchParam = param => { + const getValue = React.useCallback( + () => new URLSearchParams(window.location.search).get(param), + [param] + ); + + const [value, setValue] = React.useState(getValue); + + React.useEffect(() => { + const onChange = () => { + setValue(getValue()); + }; + + window.addEventListener('popstate', onChange); + window.addEventListener('pushstate', onChange); + window.addEventListener('replacestate', onChange); + + return () => { + window.removeEventListener('popstate', onChange); + window.removeEventListener('pushstate', onChange); + window.removeEventListener('replacestate', onChange); + }; + }, []); + + return value; +}; +``` + +```jsx +const MyApp = () => { + const post = useSearchParam('post'); + + return ( + <> +
Post param value: {post || 'null'}
+ + + > + ); +}; + +ReactDOM.render(