繁体   English   中英

Angular Observable订阅回退?

[英]Angular Observable subscription fallback?

我正在使用Angular 4,我有一个组件,它位于我的应用程序中的'player /:id'路径中。 当玩家从应用程序内导航到此路线时,我使用currentPlayerService来同步应用程序中的当前玩家。 这适用于以下代码。

this.currentPlayerService.getPlayer()
  .subscribe((player) => this.currentPlayer = player);

但是,当应用程序直接加载到'player /:id'路径(来自外部链接)时,我可以注释掉上面的内容并使用下面的代码从路径参数设置currentPlayer。

this.route.params.subscribe(params => {
  this.playerService.getPlayer(params.id)
    .subscribe((player) => {
      this.currentPlayer = player;
      this.currentPlayerService.setPlayer(player);
    });
 });

我想做的事情(并且很难找到“反应函数编程”的说法)只有当this.currentPlayerService.getPlayer()在加载时没有值时才从params加载播放器。 我很难想到在某种逻辑控制流程中使用Observable的方法,所以任何帮助都会受到赞赏。

谢谢!

可观测量本身是无国籍的。 要跟踪值(或当前值),您需要使用SubjectBehaviorSubject

currentPlayerService ,创建一个名为playerBSubjectBehaviorSubject

export class CurrentPlayerService{
  public playerBSubject: BehaviorSubject<any>;//can be type of Player if you have such type
  constructor(){
    this.playerBSubject = new BehaviorSubject({})//any value that you want to initialize
  }

  getPlayer(){
    //do your logic here, whatever that is.
    //I am using an Observable.of to mimic a http request
    Observable.of({})
      .subscribe((player)=>{
      this.playerBSubject.next(player)//this will update the subject with the latest value
    });
    return this.playerBSubject.asObservable();
  }

}

请注意, .next()方法将更新主题的值,您可以使用.asObservable()将其作为可观察对象返回。

现在,在组件控制器中,您可以检查您的BehaviourSubject存在(或具有您想要的值),并且只在需要时调用playerService.getPlayer()

this.route.params.subscribe(params => {
    //check if BehaviorSubject exist or not
    if (this.currentPlayerService.playerBSubject.getValue() === {}) {
        this.playerService.getPlayer(params.id)
            .subscribe((player) => {
                this.currentPlayer = player;
                this.currentPlayerService.setPlayer(player);
            });
    }
});

建议:

我不确定为什么你需要两个服务,即currentPlayerServiceplayerService 如果您的currentPlayerService只是为了跟踪播放器的“当前”值,那么您根本不需要它,如果您使用BehaviorSubject来跟踪当前播放器。 所有这些都可以归结成一个单一的服务。

export class PlayerService {
    public playerBSubject: BehaviorSubject<any>;

    constructor() {
        this.playerBSubject = new BehaviorSubject({})
    }

    getPlayer(id) {
        Observable.of({id}) // implement your own logic
            .subscribe((player) => {
                this.playerBSubject.next(player)
            });
        return this.playerBSubject.asObservable();
    }

    setPlayer(id) {
        return Observable.of({id})//implement your own logic
            .subscribe(newPlayer => this.playerBSubject.next(newPlayer))
    }
}

在您的控制器中,如果您想获得当前值,您可以这样做:

this.currentPlayer = this.playerService.playerBSubject.getValue();

asObservable帮助下你可以这样做:

this.playerService
    .asObservable()
    .subscribe(player => {
        if (player === {}) {
            this.route.params.subscribe(params => {
                this.playerService.getPlayer(params.id); //voila, your player is updated
            })
        }
        //remember to update the value
        this.currentPlayer = player
    })

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM