0.8.0 • Published 3 years ago
@react-cmpt/hooks v0.8.0
React Hooks
Collection of some react hooks
Usage
Installation
yarn add @react-cmpt/hooksHooks
- useAsyncClick
- useDebounce
- useDebouncedCallback
- useDebouncedClick
- useDeepCompareCache
- useDeepEffect
- useEllipsis
- useInterval
- useLoadImg
- useMountedState
- useSupportSafeArea
- useThrottle
- useThrottleFn
- useUnmount
- useUpdate
- useUpdateEffect
useAsyncClick
Click event with loading
| option | type | default | explain |
|---|---|---|---|
| asyncFunc | function | async function | |
| initState | Object | { loading: false } | initial loading |
| return | type | default | explain |
|---|---|---|---|
| callback | function | ||
| loading | boolean | ||
| error | Error | catch error |
import { useAsyncClick } from "@react-cmpt/hooks";
const asyncFn = async () => {
// do something
};
const Demo = ({ asyncFn }) => {
const { callback, loading } = useAsyncClick(asyncFn);
return <Button loading={loading} click={callback} />;
};useDebounce
| option | type | default | explain |
|---|---|---|---|
| value | any | ||
| delay | number | ||
| options | Object |
options:
| option | type | default | explain |
|---|---|---|---|
| maxWait | number | Describes the maximum time func is allowed to be delayed before it's invoked | |
| leading | boolean | This param will execute the function once immediately when called. Subsequent calls will be debounced until the timeout expires. | |
| equalityFn | function | Comparator function which shows if timeout should be started |
import { useDebounce } from "@react-cmpt/hooks";
const Demo = () => {
const [text, setText] = useState("hello");
const [value] = useDebounce(text, 1000);
return (
<div>
<input
defaultValue={"hello"}
onChange={(e) => {
setText(e.target.value);
}}
/>
<p>Actual value: {text}</p>
<p>Debounce value: {value}</p>
</div>
);
};useDebouncedCallback
| option | type | default | explain |
|---|---|---|---|
| callback | function | ||
| delay | number | ||
| options | Object |
import { useDebouncedCallback } from "@react-cmpt/hooks";
const Demo = () => {
const [value, setValue] = useState();
// Debounce callback
const debouncedCallback = useDebouncedCallback(
// function
(value) => {
setValue(value);
},
// delay in ms
1000
);
return (
<div>
<input onChange={(e) => debouncedCallback(e.target.value)} />
<p>Debounced value: {value}</p>
</div>
);
};useDebouncedClick
Click event with loading and debounce
| option | type | default | explain |
|---|---|---|---|
| asyncFunc | function | async function | |
| delay | number | 0 | useDebouncedCallbackArgs"delay" |
| options | Object | useDebouncedCallbackArgs"options" |
| return | type | default | explain |
|---|---|---|---|
| callback | function | ||
| loading | boolean | ||
| cancelDebouncedCallback | function | useDebouncedCallbackReturns"cancelDebouncedCallback" | |
| callPending | function | useDebouncedCallbackReturns"callPending" | |
| error | Error | catch error |
import { useDebouncedClick } from "@react-cmpt/hooks";
const asyncFn = async () => {
// do something
};
const Demo = ({ asyncFn }) => {
const { callback, loading } = useDebounceClick(asyncFn);
return <Button loading={loading} click={callback} />;
};useDeepCompareCache
| option | type | default | explain |
|---|---|---|---|
| value | any |
import { useDeepCompareCache } from "@react-cmpt/hooks";
const obj1 = { a: 1, b: { b1: 2 } };
const obj2 = { a: 1, b: { b1: 2 } };
const Demo = () => {
const obj = useDeepCompareCache(obj1);
console.log(obj1 === obj2); // false
console.log(obj === obj1); // true
console.log(obj === obj2); // true
// ...
};import { useDeepCompareCache } from "@react-cmpt/hooks";
const Demo = () => {
// Deep comparison React.useEffect
useEffect(() => {
// ...
}, useDeepCompareCache([A, B]));
// Deep comparison React.useCallback
const callback = useCallback(() => {
// ...
}, useDeepCompareCache([A, B]));
// ...
};useDeepEffect
Deep comparison React.useEffect
| option | type | default | explain |
|---|---|---|---|
| effect | function | Imperative function that can return a cleanup function | |
| deps | Array | If present, effect will only activate if the values in the list change. |
import { useDeepEffect } from "@react-cmpt/hooks";
const Demo = ({ value: Object }) => {
useDeepEffect(() => {
// do something
}, [value]);
// ...
};useEllipsis
Hidden overflow content and get overflow status
| option | type | default | explain |
|---|---|---|---|
| content | ReactNode | - | Overflow content. The expectation is String |
| options.lineClamp | number | string | - | The -webkit-line-clamp CSS property |
| options.debouncedWait | number | 500 | The number of milliseconds to delay. useDebouncedCallback |
| options.wrapperClassName | string | - | Wrapper element className |
| options.wrapperStyle | Object | - | Wrapper element style |
| options.wrapperProps | Object | - | Wrapper element other props |
| options.defaultOverflow | boolean | - | Default value of overflow (returns) |
| return | type | default | explain |
|---|---|---|---|
| node | JSX.Elment | Render element | |
| overflow | boolean | false | Whether overflow content |
| reObserveElement | function | Manual re-observe wrapper element | |
| recalculateEllipsis | function | Recalculate overflow content status |
import { useEllipsis } from "@react-cmpt/hooks";
const Demo = ({ text }) => {
const { node, overflow } = useEllipsis(text, { lineClamp: 2 });
return overflow ? <Tooltip content={text}>{node}</Tooltip> : node;
};Browser compatibility
-webkit-line-clamp ResizeObserver API
useInterval
Handle the setInterval timer function.
| option | type | default | explain |
|---|---|---|---|
| fn | function | - | Handle function. (setInterval callback) |
| delay | number | - | setInterval ms. |
| options.autorun | boolean | true | Runs automatically when mounted |
| return | type | default | explain |
|---|---|---|---|
| state | idle, running | idle | Operating status. |
| cancel | function | The clear timer function. | |
| run | function | Manual restart interval function. |
import { useInterval } from "@react-cmpt/hooks";
const Demo = () => {
const { state, cancel, run } = useInterval(() => {
console.log("hi");
}, 1000);
// ...
};useMountedState
Check component mount state
| option | type | default | explain |
|---|---|---|---|
| - | - | - | - |
| return | type | default | explain |
|---|---|---|---|
| callback | function | Get mount status |
import { useMountedState } from "@react-cmpt/hooks";
const Demo = () => {
const getMounted = useMountedState();
useEffect(() => {
setTimeout(() => {
if (getMounted()) {
// do...
}
}, 1000);
}, []);
// ...
};useSupportSafeArea
- check if
safe-area-inset-[top]env is supported - https://webkit.org/blog/7929/designing-websites-for-iphone-x/
| options | type | default | explain |
|---|---|---|---|
| defaultState | boolean | - | default return bool |
| position | 'top' | 'left' | 'right' | 'bottom' | top | safe-area-inset-postion |
import { useLoadImg } from "@react-cmpt/hooks";
const Demo = () => {
const supportSafeArea = useSupportSafeArea({ postion: "bottom" });
return (
<div
style={{
paddingBottom: supportSafeArea ? `env(safe-area-inset-bottom)` : "16px",
}}
>
footer
</div>
);
};constant or env
:root {
@supports (top: constant(safe-area-inset-top)) {
--safe-area-inset-top: constant(safe-area-inset-top);
--safe-area-inset-right: constant(safe-area-inset-right);
--safe-area-inset-bottom: constant(safe-area-inset-bottom);
--safe-area-inset-left: constant(safe-area-inset-left);
}
@supports (top: env(safe-area-inset-top)) {
--safe-area-inset-top: env(safe-area-inset-top);
--safe-area-inset-right: env(safe-area-inset-right);
--safe-area-inset-bottom: env(safe-area-inset-bottom);
--safe-area-inset-left: env(safe-area-inset-left);
}
}
.demo {
padding-bottom: 16px;
&[data-supportSafeArea="true"] {
padding-bottom: var(--safe-area-inset-bottom);
}
}useLoadImg
Get image loading status
| option | type | default | explain |
|---|---|---|---|
| src | string | <img /> src | |
| reqLoading | boolean | request loading | |
| className | string | ||
| style | Object | ||
| imgProps | Object | <img /> props | |
| lazy | number | 0 | Delay of done state |
| return | type | default | explain |
|---|---|---|---|
| imgNode | JSX.Element | <img /> | |
| state | loading, done, error, idle | idle | image state |
| loading | boolean | ||
| isError | boolean | image errored |
import { useLoadImg } from "@react-cmpt/hooks";
const Demo = () => {
const { imgNode, loading } = useLoadImg({
src: "[PATH]/demo.jpg",
style: { width: "100%" },
});
return <div data-loading={loading}>{imgNode}</div>;
};useThrottle
throttled value
| return | type | explain |
|---|---|---|
| value | any | Returns the new throttled value. |
| cancel | function | The clear timer function. |
| callPending | function | The callback manually function. |
import { useThrottle } from "@react-cmpt/use-throttle";
const Demo = ({ value }) => {
const [tValue, { cancel, callPending }] = useThrottle(value, 200);
// ...
};useThrottleFn
throttled function
<
| return | type | explain |
|---|---|---|
| callback | function | The new throttled function. |
| cancel | function | The clear timer function. |
| callPending | function | The callback manually function. |
import { useThrottleFn } from "@react-cmpt/use-throttle";
const Demo = () => {
const { callback, cancel, callPending } = useThrottleFn(() => {
console.log("click");
}, 200);
return <button onClick={callback}>++</button>;
};useUnmount
Unmount callback
| option | type | default | explain |
|---|---|---|---|
| fn | function |
import { useUnmount } from "@react-cmpt/hooks";
const Demo = () => {
useUnmount(() => {
console.log("Unmount");
});
// ...
};useUpdate
Re-render components
| return | type | default | explain |
|---|---|---|---|
| rerender | function | rerender callback |
import { useUpdate } from "@react-cmpt/hooks";
const Demo = () => {
const rerender = useUpdate();
return (
<>
<div>Date: {Date.now()}</div>
<button onClick={rerender}>Update</button>
</>
);
};useUpdateEffect
React.useEffect cancel the first mount trigger
| option | type | default | explain |
|---|---|---|---|
| effect | function | Imperative function that can return a cleanup function | |
| deps | Array | If present, effect will only activate if the values in the list change. |
import { useUpdateEffect, useDeepCompareCache } from "@react-cmpt/hooks";
const Demo = () => {
useUpdateEffect(() => {
console.log(value);
}, [value]);
// Deep comparison useUpdateEffect
useUpdateEffect(() => {
console.log(value);
}, useDeepCompareCache([value]));
// ...
};Dependencies
Dev
# build package
yarn build
# tests
yarn test
# lint
yarn lintLicense
0.8.0
3 years ago
0.8.0-alpha.1
3 years ago
0.8.0-alpha.0
3 years ago
0.7.1
4 years ago
0.7.1-alpha.0
4 years ago
0.7.0
4 years ago
0.6.2
4 years ago
0.6.1
4 years ago
0.6.0
4 years ago
0.5.0
5 years ago
0.4.2
5 years ago
0.4.1
5 years ago