我正在尝试根据组件的输入变量绑定和取消绑定HostListener单击事件。
该组件是一个弹出窗口,其中包含一个名为show
的输入。此输入保持弹出窗口的活动/非活动状态。我想在整个文档上触发click事件,但仅当输入show
设置为true时才会触发。
有没有办法在我有的ngOnChanges函数中绑定和取消绑定hostlistener事件?
我目前的代码:
import {Component, OnInit, Input, ViewEncapsulation, HostListener} from '@angular/core';
@Component({
selector: 'custom-popup',
templateUrl: './popup.component.html',
styleUrls: ['./popup.component.scss'],
encapsulation: ViewEncapsulation.None
})
export class PopupComponent implements OnInit {
@Input() show: boolean = false;
constructor() {
}
ngOnInit() {
}
@HostListener('document:click', ['$event.target'])
clickHandler(targetElement) {
// Custom code to handle click event
}
ngOnChanges(show: boolean) {
if (this.show) {
// Bind Click Event
}
else {
// Unbind Click Event
}
}
}
非常感谢任何帮助和见解。
答案 0 :(得分:1)
要确保在显示弹出窗口时只设置一个主机侦听器,请引入一个新的子组件PopupBody
,其中包含主机侦听器,并@Output()
将事件传递回来到Popup
组件。
然后,在您的模板中,使用PopupBody
使*ngIf="show"
组件成为条件,然后它应该只在显示弹出窗口时绑定主机侦听器,并在弹出窗口被隐藏时取消绑定。
答案 1 :(得分:-1)
最后,我使用服务实现了一个解决方案。该服务处理文档上的单击事件,并使用observable使组件能够订阅事件。
弹出组件在打开时订阅stateService
点击observable,并在关闭时取消订阅。
弹出组件:
import {Component, OnInit, Input, ViewEncapsulation, HostListener} from '@angular/core';
import {StateService} from "../services/state.service";
import {Subscription} from "rxjs";
@Component({
selector: 'custom-popup',
templateUrl: './popup.component.html',
styleUrls: ['./popup.component.scss'],
encapsulation: ViewEncapsulation.None
})
export class PopupComponent implements OnInit {
@Input() show: boolean = false;
constructor(private stateService: StateService) {
}
ngOnInit() {
}
ngOnChanges(show: boolean) {
if (this.show) {
// Timeout to ensure subscription after initial click
setTimeout(() => {
// Subscribe to the document click service when the input opens
if (!this.clickSubscription || this.clickSubscription.closed) {
this.clickSubscription = this.stateService.documentClick$.subscribe(targetElement => {
// Logic for closing the popup
});
}
});
}
else {
// Remove the subscription when the input closes
if (this.clickSubscription && !this.clickSubscription.closed) {
this.clickSubscription.unsubscribe();
}
}
}
}
@GregL感谢您的建议