Angular 2 - 如何在没有模板的情况下监听事件?
Angular 2 - How to listen to event without a template?
问题
通常,在 Angular 2 中,人们会通过以下语法侦听事件:
<my-elem (customEvent)="customEventProcessor"></my-elem>
但是当我使用路由器时,该主机 - <my-elem>
- 在任何模板中都不存在。相反,有一个 <router-outlet>
,我的组件在导航时加载。因此,我的问题的症结在于,如何在不依赖模板的情况下强制我的主机收听我的自定义事件?
可选详细信息
假设我有一些元素 list-view
,它是我的根组件的子元素。 list-view
通过正常语法侦听自定义事件:
<list-view (customEvent)="customEventProcessor()"></list-view>
为了完整起见,发出事件的 list-view
组件也有一个可预测的结构:
<button (click)="onDetailsClick(propertyOfInterest)">Click here</button>
list-view
通过观察将事件发送给父级。
class ListView {
...
public onDetailsClick(property: string): void {
this.customEvent.next({ value: property });
}
}
并且该事件触发了 customEventProcessor()
函数。到目前为止,一切都很好。但是,当我使用路由器控制 list-view
是否存在时,我无法(据我所知)插入命令来监视某些事件。
我不确定处理这种情况的最佳方法是什么。
此问题尚未解决(参见this github issue). Here is one of the possible solutions at this moment (see this plunk):
@Component({
selector: 'my-app',
directives: [RouterOutlet, RouterLink],
template: `
<h1>{{ message }}</h1>
<a [router-link]="['./MyElem1']">MyElem1</a>
<a [router-link]="['./MyElem2']">MyElem2</a>
<router-outlet></router-outlet>
`
})
@RouteConfig([
{ path: '/', redirectTo: '/my-elem1' },
{ path: '/my-elem1', name: 'MyElem1', component: MyElem1 },
{ path: '/my-elem2', name: 'MyElem2', component: MyElem2 },
])
export class App {
message: string = 'Click on the button';
@ViewChild(MyElem1) myElem1: MyElem1;
@ViewChild(MyElem2) myElem2: MyElem2;
constructor(router: Router) {
let subs = null;
router.subscribe(() => {
if (subs) { subs.unsubscribe(); subs = null; }
if (this.myElem1) {
subs = this.myElem1.customEvent1.subscribe(m=>this.processCustomEvent(m));
}
if (this.myElem2) {
subs = this.myElem2.customEvent2.subscribe(m=>this.processCustomEvent(m));
}
});
}
processCustomEvent(message) { this.message = message }
}
问题
通常,在 Angular 2 中,人们会通过以下语法侦听事件:
<my-elem (customEvent)="customEventProcessor"></my-elem>
但是当我使用路由器时,该主机 - <my-elem>
- 在任何模板中都不存在。相反,有一个 <router-outlet>
,我的组件在导航时加载。因此,我的问题的症结在于,如何在不依赖模板的情况下强制我的主机收听我的自定义事件?
可选详细信息
假设我有一些元素 list-view
,它是我的根组件的子元素。 list-view
通过正常语法侦听自定义事件:
<list-view (customEvent)="customEventProcessor()"></list-view>
为了完整起见,发出事件的 list-view
组件也有一个可预测的结构:
<button (click)="onDetailsClick(propertyOfInterest)">Click here</button>
list-view
通过观察将事件发送给父级。
class ListView {
...
public onDetailsClick(property: string): void {
this.customEvent.next({ value: property });
}
}
并且该事件触发了 customEventProcessor()
函数。到目前为止,一切都很好。但是,当我使用路由器控制 list-view
是否存在时,我无法(据我所知)插入命令来监视某些事件。
我不确定处理这种情况的最佳方法是什么。
此问题尚未解决(参见this github issue). Here is one of the possible solutions at this moment (see this plunk):
@Component({
selector: 'my-app',
directives: [RouterOutlet, RouterLink],
template: `
<h1>{{ message }}</h1>
<a [router-link]="['./MyElem1']">MyElem1</a>
<a [router-link]="['./MyElem2']">MyElem2</a>
<router-outlet></router-outlet>
`
})
@RouteConfig([
{ path: '/', redirectTo: '/my-elem1' },
{ path: '/my-elem1', name: 'MyElem1', component: MyElem1 },
{ path: '/my-elem2', name: 'MyElem2', component: MyElem2 },
])
export class App {
message: string = 'Click on the button';
@ViewChild(MyElem1) myElem1: MyElem1;
@ViewChild(MyElem2) myElem2: MyElem2;
constructor(router: Router) {
let subs = null;
router.subscribe(() => {
if (subs) { subs.unsubscribe(); subs = null; }
if (this.myElem1) {
subs = this.myElem1.customEvent1.subscribe(m=>this.processCustomEvent(m));
}
if (this.myElem2) {
subs = this.myElem2.customEvent2.subscribe(m=>this.processCustomEvent(m));
}
});
}
processCustomEvent(message) { this.message = message }
}