使用服务在角度组件之间调用方法不起作用
Posted
技术标签:
【中文标题】使用服务在角度组件之间调用方法不起作用【英文标题】:Calling methods between components in angular using service not working 【发布时间】:2017-11-17 19:59:19 【问题描述】:我正在尝试使用可注入服务从另一个组件调用一个组件中的方法
我的第一个组件(我正在从这个组件调用其他组件中的方法)
bottombar.component.ts
import Component, ElementRef, OnInit, ViewChild, AfterViewInit, ChangeDetectorRef, EventEmitter, Input, Output from "@angular/core";
import Router from "@angular/router";
import Label from "ui/label";
import BottomBarService from '../../services/bottombarservice/bottombar.service';
@Component(
selector: "bottom-bar",
templateUrl: "./components/bottombar/bottombar.html",
styleUrls:["./components/bottombar/bottombar-common.css", "./components/bottombar/bottombar.css"],
//providers: [BottomBarService]
)
export class bottombarComponent implements OnInit
constructor(private bottomBarService: BottomBarService)
openDrawer()
this.bottomBarService.callSideDrawerMethod();
ngOnInit()
我试图从上面的组件中调用 SideDrawerGettingStartedComponent 中的一个方法,该方法位于下面,它将触发一个打开侧抽屉的方法
我的第二个组件(其中存在被调用的方法)
sidedrawer.component.ts
import Component, ViewChild, OnInit, AfterViewInit, ChangeDetectorRef from "@angular/core";
import Page from "ui/page";
import ActionItem from "ui/action-bar";
import Observable from "data/observable";
import RadSideDrawerComponent, SideDrawerType from "nativescript-telerik-ui-pro/sidedrawer/angular";
import RadSideDrawer from 'nativescript-telerik-ui-pro/sidedrawer';
import BottomBarService from '../../services/bottombarservice/bottombar.service';
@Component(
// moduleId: module.id,
selector: "tk-sidedrawer-getting-started",
templateUrl: "./components/sidedrawer/sidedrawer.html",
styleUrls: ['./components/sidedrawer/sidedrawer.css'],
//providers: [BottomBarService]
)
export class SideDrawerGettingStartedComponent implements AfterViewInit, OnInit
private _mainContentText: string;
constructor(private _changeDetectionRef: ChangeDetectorRef,private bottomBarService: BottomBarService)
this.bottomBarService.sideDrawerMethodCalled$.subscribe(() =>
console.log("subscribed")
alert("hello")
this.openDrawer()
)
@ViewChild(RadSideDrawerComponent) public drawerComponent: RadSideDrawerComponent;
private drawer: RadSideDrawer;
ngAfterViewInit()
this.drawer = this.drawerComponent.sideDrawer;
this._changeDetectionRef.detectChanges();
ngOnInit()
this.mainContentText = "SideDrawer for NativeScript can be easily setup in the HTML definition of your page by defining tkDrawerContent and tkMainContent. The component has a default transition and position and also exposes notifications related to changes in its state. Swipe from left to open side drawer.";
get mainContentText()
return this._mainContentText;
set mainContentText(value: string)
this._mainContentText = value;
public openDrawer()
console.log("triggered openDrawer in main component")
this.drawer.showDrawer();
public onCloseDrawerTap()
this.drawer.closeDrawer();
共享服务如下
bottombar.service.ts
import Subject from 'rxjs/Subject';
import Injectable from '@angular/core';
@Injectable()
export class BottomBarService
private sideDrawerMethodSource = new Subject<any>();
sideDrawerMethodCalled$ = this.sideDrawerMethodSource.asObservable();
callSideDrawerMethod()
console.log("Inside service bottomBar")
this.sideDrawerMethodSource.next(null);
console.log("after")
问题
我有一个与 bottombar.component.ts 关联的 html,其中包含一个按钮。点击它会触发 bottombar.component.ts
中的 openDrawer() 函数我可以在我的服务文件中看到控制台值,但不知何故它没有触发 sidedrawer.component.ts
中的订阅没有错误,因此很难找到导致问题的确切原因。
另外我已经在 ngModule 的提供者中声明了我的服务以避免单例问题。
这里有什么我遗漏的吗?
提前致谢
【问题讨论】:
Angular - shared service between components doesn't work的可能重复 我尝试了在ngModule
中声明服务的解决方案,正如我在最后几行中提到的,即使在根目录提供服务后它也无法正常工作
仔细阅读答案,您仍然在@Component
注解中重新提供了服务
您确定您的sidedrawer
组件已加载吗?
@Abrar EventEmitter
仅适用于两个组件具有parent-child
关系的情况。
【参考方案1】:
在您的共享服务中,您可以传递status:boolean
,而不是在这里传递null
this.sideDrawerMethodSource.next(null)
。在你的 bottombar.service.ts -
callSideDrawerMethod(status:boolean)
this.sideDrawerMethodSource.next(status);
现在,在 bottombar.component.ts 中,在调用方法时传递一个状态 -
this.bottomBarService.callSideDrawerMethod(true);
在您的 sidedrawer.component.ts 中,传递 status
参数 -
this.bottomBarService.sideDrawerMethodCalled$.subscribe((status) =>
console.log("subscribed")
alert("hello")
this.openDrawer()
)
并且不要在构造函数中订阅,而是将代码放在ngOnInit()
生命周期钩子中。
希望这会有所帮助。
【讨论】:
这与@AmitChigadani 对问题的评论一起使用。【参考方案2】:您似乎错过了在sideDrawerMethodCalled
旁边附加'$'
试试下面的代码:
callSideDrawerMethod()
console.log("Inside service bottomBar")
this.sideDrawerMethodSource$.next(null);
console.log("after")
【讨论】:
我在私有sideDrawerMethodSource = new Subject<any>();
中的变量没有$
。所以我没有那样使用它。无论如何我尝试附加$
,仍然无法正常工作以上是关于使用服务在角度组件之间调用方法不起作用的主要内容,如果未能解决你的问题,请参考以下文章