Reputation: 173
This probably seems like an odd question, but what I'm trying to do is create a simple search field in React. I don't want to make an API call every time the search field is changed, but only if a certain time e.g 500ms has passed since the last state change to ensure that the user isn't typing anymore.
I wanted to do this using the setTimeout function, but I can't find a way to find out during rendering if a state change has been made or something has been added on top of the call stack.
So is there a way to check if there is another render scheduled during rendering?
Something like this:
export default function(){
setTimeout(() => {CHECK IF THERE'S BEEN A STATE CHANGE, IF NOT FETCH API}, 500)
}
Upvotes: 0
Views: 320
Reputation: 281646
The concept used to achieve what you want is called debouncing. You can choose to implement a custom debounce function yourself or even use it from a libray.
Considering the fact that you use a functional component and assuming that you use hooks, you can implement the above like
const debounce = (fn, delay) => {
let timer = null;
return function(...args) {
// The function is called again but there isn't enough delay
// between two calls so cancel the previous call
if(timer) clearTimeout(timer);
// set up a function call timer again
timer = setTimeout(() => {
fn.apply(this, args)
}, delay);
}
}
and you can use it in your component like
const Input = () => {
const handleChange = (e) => {
// make an api call here
}
const debouncedHandleChange = useCallback(debounce(handleChange, 1000), []);
return (
<input type="text" onChange={debouncedHandleChange} />
)
}
Upvotes: 1