【问题标题】:Prevent Observable from Running Again Until Complete防止 Observable 再次运行直到完成
【发布时间】:2017-04-23 02:12:32
【问题描述】:

在使用可观察对象的 Angular4/Ionic3 环境中。页面上带有幻灯片的滑块。当一个人滑动移动到下一张幻灯片时,会触发一个多步、长时间运行的 observable。目前,当一个人再次滑动时,第二个 observable 实例会运行(在第一个实例完成之前)。

如何让第二个 observable 等待第一个 observable 完成?我不想阻止此人滑动。 swipe 事件应该简单地将下一个 observable 排队。

当前时间线

  1. 滑动1
  2. 可观察的实例 1 = 开始
  3. 滑动2
  4. 可观察实例2 = 开始
  5. 可观察实例 1 = 结束
  6. 可观察的实例 2 = 结束

所需时间线

  1. 滑动1
  2. 可观察的实例 1 = 开始
  3. 可观察实例 1 = 结束
  4. 滑动2
  5. 可观察实例2 = 开始
  6. 可观察的实例 2 = 结束

当前可观察的伪代码

private slideNextStart(event) {

    // Don't let this Observable be called again until it finishes.
    Observable.of(null)
    .flatMap(() => {
        console.log('start');
        // Do something.
    })
    .flatMap(() => {
        // Do something else.
    })
    .flatMap(() => {
        // Do another something else.
    })
    .subscribe(() => { console.log('end'); });

来自 Julia 答案的 Angular2 翻译代码

import { Observable } from 'rxjs/Rx';
import { Subject } from 'rxjs/Subject';

let subject = new Subject();
subject.asObservable()
    .concatMap((x: Observable<any>) => { return x })
    .subscribe(x => console.log(x));

// request 1
subject.next(Observable
    .timer(4000)
    .map(() => { console.log('req1') })
    .mapTo('req1'));

// request 2
subject.next(Observable.of('req2'));

【问题讨论】:

  • 您不想阻止某人进行第二次滑动,但第二次交换的效果是否与第一次不同?似乎您想让 observables 同步,这不是它们的目的。如果人们第三次、第四次、第五次滑动会发生什么?不确定情况,但也许一些加载菜单会是更好的选择(它会覆盖屏幕直到第一次滑动可观察完成)

标签: angular observable


【解决方案1】:

Observable.concatMap 就是为此而设计的。 “将每个源值投影到一个 Observable 中,该 Observable 合并到输出 Observable 中,以序列化的方式等待每个源值完成,然后再合并下一个。” concatMap

// subject to emit observables
let subject = new Rx.Subject();

// do concatMap to sequence the requests
subject.asObservable()
 .concatMap(x=>x)
 .subscribe(x=>console.log(x))

// request 1
subject.next(Rx.Observable
    .timer(4000)
    .mapTo('req1'));

// request 2
subject.next(Rx.Observable.of('req2'));

【讨论】:

  • 完美!但是,我无法让它在 Angular2 环境中正常工作。请求正在输出到控制台,但请求本身并未运行。我的 console.log('req1') 没有输出。控制台记录两项 (1) Observable {_isScalar: false, source: Observable, operator: MapToOperator} (2) ScalarObservable {_isScalar: true, value: "req2", scheduler: null}。
  • 我的 Angular2/TypeScript 代码错误。已更新问题以更正代码。
猜你喜欢
  • 1970-01-01
  • 2020-02-04
  • 1970-01-01
  • 2018-02-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-09-21
  • 1970-01-01
相关资源
最近更新 更多