promise 中的 setInterval,在 React 中只执行一次
setInterval in a promise, only executes once in React
我正在尝试创建一个每秒滴答一秒的倒数计时器。间隔只工作一次,不执行。问题是我没有 this.state.timetill,直到服务器调用 ,然后我才能开始计时。因此,setInterval 函数必须隐藏在一个 promise 中,它只执行一个。然而,timetill 变量可以是一个常量,一旦检索它就不会改变。
componentDidMount = async () => {
const that = this;
*do stuff*
this.someFunction().finally(() => {
/*This right here, below is not working */
setInterval(that.createTimer(), 1000);
});
}
我的JSX就是这样
{this.state.setTimer}
有问题的函数,时间必须除以 1000,因为 javascript 使用毫秒
createTimer = async timerNow => {
var timerNow = (await new Date().getTime()) / 1000;
// Find the distance between now and the count down date
var distance = this.state.timeTill - timerNow;
// Time calculations for days, hours, minutes and seconds
var days = Math.floor(distance / (1000 * 60 * 60 * 24));
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance % (1000 * 60)) / 1000);
//the variable displayed
var setTimer = days + "d " + hours + "h " + minutes + "m " + seconds + "s ";
this.setState({setTimer});
};
您将 createTimer
的返回值传递给 setInterval
,而不是传递函数但不调用它
setInterval(this.createTimer, 1000)
您应该做几件事:
1. 有一个实际调用 setState
的方法
2.改变setInterval
调用一个方法reference
3. 清除任何挂起的卸载请求:
4. [可选] 你可以删除 that
private createTimer = { ... }
private setTimer = () => {
this.setState({ timer: this.createTimer() });
}
private _mounted: boolean = false;
private _intervalHandler: number | null = null;
componentDidMount = async () => {
this._mounted = true;
this.someFunction().finally(() => {
if (!this._mounted) { return; }
this._intervalHandler = setInterval(this.setTimer, 1000);
});
}
componentWillUnmoun = () => {
this._mounted = false;
if (this._intervalHandler !== null) {
clearInterval(this._intervalHandler);
}
}
这将确保您不会在卸载组件后执行状态更改。
我正在尝试创建一个每秒滴答一秒的倒数计时器。间隔只工作一次,不执行。问题是我没有 this.state.timetill,直到服务器调用 ,然后我才能开始计时。因此,setInterval 函数必须隐藏在一个 promise 中,它只执行一个。然而,timetill 变量可以是一个常量,一旦检索它就不会改变。
componentDidMount = async () => {
const that = this;
*do stuff*
this.someFunction().finally(() => {
/*This right here, below is not working */
setInterval(that.createTimer(), 1000);
});
}
我的JSX就是这样
{this.state.setTimer}
有问题的函数,时间必须除以 1000,因为 javascript 使用毫秒
createTimer = async timerNow => {
var timerNow = (await new Date().getTime()) / 1000;
// Find the distance between now and the count down date
var distance = this.state.timeTill - timerNow;
// Time calculations for days, hours, minutes and seconds
var days = Math.floor(distance / (1000 * 60 * 60 * 24));
var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
var seconds = Math.floor((distance % (1000 * 60)) / 1000);
//the variable displayed
var setTimer = days + "d " + hours + "h " + minutes + "m " + seconds + "s ";
this.setState({setTimer});
};
您将 createTimer
的返回值传递给 setInterval
,而不是传递函数但不调用它
setInterval(this.createTimer, 1000)
您应该做几件事:
1. 有一个实际调用 setState
的方法
2.改变setInterval
调用一个方法reference
3. 清除任何挂起的卸载请求:
4. [可选] 你可以删除 that
private createTimer = { ... }
private setTimer = () => {
this.setState({ timer: this.createTimer() });
}
private _mounted: boolean = false;
private _intervalHandler: number | null = null;
componentDidMount = async () => {
this._mounted = true;
this.someFunction().finally(() => {
if (!this._mounted) { return; }
this._intervalHandler = setInterval(this.setTimer, 1000);
});
}
componentWillUnmoun = () => {
this._mounted = false;
if (this._intervalHandler !== null) {
clearInterval(this._intervalHandler);
}
}
这将确保您不会在卸载组件后执行状态更改。