Reputation: 5782
I have four screens A (HomePage), B, C, D
Each of screens have a function that will be triggered when the screen onStart
or onResume
, I achieve it by react-redux.
countdownToFirstScreen = () => {
this.timeOut = setTimeout(()=> {
clearTimeout(this.timeOut); // clearTimeout before navigate next screen
this.props.leaveTheScreenTime(); // change for some redux store boolean
this.props.navigation.navigate('A');
}, 9000);
}
If user click <Button />
before countdown finish, I set the clearTimeout too.
<Button
onPress={() => {
clearTimeout(this.timeOut);
this.props.navigation.navigate('nextScreen');
}
/>
It is working when I just navigate between A and B and C.
My issue happens when I try to navigate from C to D.
C screen function countdownToFirstScreen
will be triggered eventhough I click the <Button />
on C screen.
Any one knows what happened with my setTimeout
and clearTimeout
?
Upvotes: 6
Views: 17287
Reputation: 6752
Using React-Hooks and Functional Components ... things are alot easier...
An effect with empty-deps []
simulates componentDidMount
, and its cleanUp-callback simulates componentWillUnmount
const timerRef = useRef(null);
useEffect(() => {
timerRef.current = setTimeout(() => {
/** Your logic goes here */
}, 9000);
return () => {
if (timerRef.current) {
clearTimeout(timerRef.current);
}
};
}, []);
Upvotes: 10
Reputation: 881
It looks like you may run into scoping issues as this
in the setTimeout
callback may have a different context than this.timeOut
and thus the timer is not being cleared. Ideally you want a setup where you track the timer in some global component like your AppComponent
which is on every screen, with a setup like:
componentWillMount () {
// Add your listener
DeviceEventEmitter.addListener('timer', this.clearTimer.bind(this));
}
componentDidMount () {
startTimer()
}
componentWillUnMount () {
clearTimer()
}
startTimer () {
this.timer = this.setTimeout(() => {
this.props.navigation.navigate('A');
},9000);
clearTimer () {
// Handle an undefined timer rather than null
this.timer !== undefined ? this.clearTimeout(this.timer) : null;
}
Upvotes: 7