How to compare oldValues and newValues on React Hooks useEffect?
You can write a custom hook to provide you a previous props using useRef
function usePrevious(value) { const ref = useRef(); useEffect(() => { ref.current = value; }); return ref.current;}
and then use it in useEffect
const Component = (props) => { const {receiveAmount, sendAmount } = props const prevAmount = usePrevious({receiveAmount, sendAmount}); useEffect(() => { if(prevAmount.receiveAmount !== receiveAmount) { // process here } if(prevAmount.sendAmount !== sendAmount) { // process here } }, [receiveAmount, sendAmount])}
However its clearer and probably better and clearer to read and understand if you use two useEffect
separately for each change id you want to process them separately
Incase anybody is looking for a TypeScript version of usePrevious:
In a .tsx
module:
import { useEffect, useRef } from "react";const usePrevious = <T extends unknown>(value: T): T | undefined => { const ref = useRef<T>(); useEffect(() => { ref.current = value; }); return ref.current;};
Or in a .ts
module:
import { useEffect, useRef } from "react";const usePrevious = <T>(value: T): T | undefined => { const ref = useRef<T>(); useEffect(() => { ref.current = value; }); return ref.current;};
Option 1 - run useEffect when value changes
const Component = (props) => { useEffect(() => { console.log("val1 has changed"); }, [val1]); return <div>...</div>;};
Option 2 - useHasChanged hook
Comparing a current value to a previous value is a common pattern, and justifies a custom hook of it's own that hides implementation details.
const Component = (props) => { const hasVal1Changed = useHasChanged(val1) useEffect(() => { if (hasVal1Changed ) { console.log("val1 has changed"); } }); return <div>...</div>;};const useHasChanged= (val: any) => { const prevVal = usePrevious(val) return prevVal !== val}const usePrevious = (value) => { const ref = useRef(); useEffect(() => { ref.current = value; }); return ref.current;}