猿问

使用可观察量为顺序动画制作可取消的 setTimeouts

我有一个对象数组,根据对象的类型键代表不同的动画。我使用setTimeout. 我正在反应组件的函数内运行下面的代码。


animations.forEach((animation, index) => {

      switch (animation.type) {


        case "animation-type": {


          setTimeout(() => {

            //change the style of some elements

          }, index * 1000);


          break;

        }


        ...


        default:

          break;

      }

});

上面的整个过程按预期正常运行,只是一旦开始我就无法停止。我希望能够出于某种原因在某个时刻停止该过程,并取消等待轮到的剩余动画。


我正在寻找一种简单的方法来以声明方式执行此操作,我能想到的唯一选择是使用 rxjs 中的可观察量来使该过程可取消。然而,我很难调整上面的过程来使用可观察量,因为我对 rxjs 还很陌生。


长话短说,我想让这个过程可以取消。


慕丝7291255
浏览 136回答 2
2回答

MMMHUHU

下面的流zip创建每 1000 毫秒向订阅的 lambda 发送一个对象。一旦不再有任何对象,它就会结束。takeUntil是可用于控制流何时结束的更通用的运算符之一。在这种情况下,当cancel$发出一个值时,整个流就结束了。const cancel$ = new Subject();zip(  from(animations),   interval(1000)).pipe(  takeUntil(cancel$),  map(([x,y]) => x)).subscribe(animation => {  switch (animation.type) {    case "animation-type": {      //change the style of some elements      ...    default:      break;  }});然后,如果您需要停止它,您可以运行此行cancel$.next();当然,您可以传入一个观察者对象,而不是使用 lambda 函数进行订阅。).subscribe({  next: animation => {    switch (animation.type) {      case "animation-type": {        //change the style of some elements        ...      default:        break;    }  },  complete: () => {    // Final touches/ reset the animation/ whatever  },  error: err => {    console.log("Got an error: " + err.message);    throw(err);  }})

梵蒂冈之花

您可以存储超时函数:    const timeouts = [];    animations.forEach((animation, index) => {          switch (animation.type) {                case "animation-type": {                  timeouts[index] = setTimeout(() => {                //change the style of some elements              }, index * 1000);                  break;            }                ...                default:              break;          }    });然后:timeouts.map(timer=> clearTimeout(timer));如果您正在使用 React 项目,则可以使用useRef钩子    const timeouts = useRef([]);    animations.forEach((animation, index) => {          switch (animation.type) {                case "animation-type": {                  timeouts.current[index] = setTimeout(() => {                //change the style of some elements              }, index * 1000);                  break;            }                ...                default:              break;          }    });并清除超时:timeouts.current.map(timer=> clearTimeout(timer));
随时随地看视频慕课网APP

相关分类

JavaScript
我要回答