Ionic2,将NavController注入Injectable Service

Posted

技术标签:

【中文标题】Ionic2,将NavController注入Injectable Service【英文标题】:Ionic2, inject NavController to Injectable Service 【发布时间】:2016-10-16 10:46:59 【问题描述】:

我在使用 Ionic2 框架的 Angular2 中的 Injectable Service 存在问题。

我的服务如下所示:

import Injectable from '@angular/core';
import NavController from 'ionic-angular';

@Injectable()
export class ViewStackController 
  static get parameters() 
    return [[NavController]];
  

  constructor(nav) 
  

我收到错误No provider for NavController。这很奇怪,因为在 它正在工作的任何 Page 类,尽管它有 @Component,也许这就是问题所在。

编辑#1:

我在ionicBootstrap提供这项服务,像这样:

ionicBootstrap(MyApp, [ViewStackController], );

【问题讨论】:

【参考方案1】:

您可以看到here,@mhartington(来自 ionic 团队)说:

只是为了插话,你不应该注入 ViewController 或 NavController 进入服务。这不是他们的预期目的。

服务不应该负责显示警报/加载/或 任何需要通过导航激活的组件。服务应该只是 用于获取和返回数据。

其他任何事情都应该在组件内完成。

话虽如此,您可以通过以下方式获得导航

var nav = this.app.getActiveNav();

如你所见here。

================================================ ==

编辑:正如另一位用户所说:

从服务更改视图是不好的做法(损坏的 MVC)。 但是,您可以将事件从服务发送到主控制器, 控制器可以使用 NavController (最好的方式),或者你可以发送 NavController 像属性一样为您的服务提供服务(不错的方式......)。要么 您可能需要创建一个组件而不是使用该服务。

所以,一个更好的方法是:

首先,在您的服务中添加一个observable,以了解何时应该调用dismiss

import Injectable from '@angular/core';
import Platform from 'ionic-angular';
import Observable from 'rxjs/Observable';

@Injectable()
export class MyCustomService 

  // Observables we're going to use
  private dismissObserver: any;
  public dismiss: any;

  constructor(private platform: Platform)
    // Your stuff
    // ...

    this.dismissObserver = null;
    this.dismiss = Observable.create(observer => 
        this.dismissObserver = observer;
    );
  

  public yourMethod(...):void 
    // Here we send the order to go back to the home page
    this.dismissObserver.next(true);
  

然后,在您的app.ts(或您最顶层的组件中):

 initializeApp(): void 
    this.platform.ready().then(() => 
      // Okay, so the platform is ready and our plugins are available.
      // Here you can do any higher level native things you might need.
      StatusBar.styleDefault();

      // We subscribe to the dismiss observable of the service
      this.myCustomService.dismiss.subscribe((value) => 
        this.navController.setRoot(HomePage);
      );
    );
  

记得将它添加到您应用的ionicBootstrap 中:

ionicBootstrap(MyApp, [MyCustomService, ...], 
  //statusbarPadding: true
);

或者,在Angular2 Style Guide 之后,将其作为provider 添加到最顶层的组件(本例中为MyApp):

@Component(
  templateUrl: 'build/app.html',
  directives: [...],
  providers: [MyCustomService]
)
class MyApp 
  // ...

【讨论】:

或者(根据场景/服务使用情况)将页面导航作为参数传递给服务 这个答案很好,在这种情况下我会选择经典作文。 嗯,有什么想法吗? browser_adapter.js:84 TypeError: Cannot read property 'next' of null 在我的服务中可观察到。 var nav = this.app.getActiveNav(); - 这对我不起作用 @Sam 你已经用 this answer 试过了吗?

以上是关于Ionic2,将NavController注入Injectable Service的主要内容,如果未能解决你的问题,请参考以下文章

Ionic 2:例外:没有 NavController 的提供者

Ionic 2:自定义提供程序导致“无法解析所有参数”

Ionic 2禁用没有导航栏的向后滑动

ionic2 手风琴效果

使用带有 Firebase 的 Ionic2 切换

Ionic2 渐变隐藏导航栏|标题栏