2017-06-22 140 views
1

我試圖創建一個Angular 4自定義窗體控件作爲我的日期選擇器。我正在使用ngx-bootstrap,並且迄今爲止我已經使用ngx-bootstrap中的input,datepicker和popover組件設置了此自定義窗體控件。自定義控件會打開一個彈出窗口,並將日期選擇器放在焦點上,但是,我需要能夠通過與彈出窗口內容交互來更改日期,並且當Iam不與彈出窗口或輸入交互時它應該關閉。我試圖按照the ngx-bootstrap github issue進行破解。但它不適合我的情況。任何幫助,將不勝感激。ngx-bootstrap popover關閉外部點擊

日期picker.component.html

<input type="text" [value]="getDate() | date:'fullDate'" #popover="bs-popover" [placeholder]="placeholder" class="form-control" triggers="" (focus)="popover.show()" [popover]="popTemplate" container="body" required> 
<template #popTemplate> 
    <datepicker [(ngModel)]="dt" [minDate]="minDate" [showWeeks]="true" 
       [dateDisabled]="dateDisabled"></datepicker> 
</template> 

日期picker.component.ts

@Component({ 
    selector: 'app-date-picker', 
    templateUrl: './date-picker.component.html', 
    styleUrls: ['./date-picker.component.scss'], 
    providers: [ 
    { 
     provide: NG_VALUE_ACCESSOR, 
     useExisting: forwardRef(() => DatePickerComponent), 
     multi: true 
    } 
    ] 
}) 
export class DatePickerComponent implements OnInit, ControlValueAccessor { 
@ViewChild('popover') popover; 

    isOpen = false; 

    @Input('placeholder') placeholder; 
constructor(private _er: ElementRef) { 
} 

    @HostListener('click', ['$event']) onClick(event): void { 
    console.log(event); 
    if (
     this.isOpen 
     && !this._er.nativeElement.contains(event.target) 
     && !this.popover._popover!._componentRef!.location.nativeElement!.contains(event.target) 
    ) { 
     this.hide(); 
    } 
    } 

    hide() { 
    this.isOpen = false; 
    this.popover.hide(); 
    } 

    show() { 
    this.isOpen = true; 
    this.popover.show(); 
    } 
} 

此保持打開,甚至當我點擊輸入或酥料餅之外。當使用模糊事件時,我甚至無法與日曆交互。即使在我可以選擇日期之前它會關閉。 enter image description here

+0

你是什麼意思「我沒有與popover互動」?點擊外面?什麼不與@HostListener解決方案一起工作? –

+0

我已經成功地打開了彈出窗口,所以我可以更改日期值,但是當它點擊外部時它不會關閉 –

+1

您是否嘗試過@HostListener('document:click',['$ event'])而不是'@HostListener('click',['$ event'])'? –

回答

1

@HostListener修飾器在Angular API Doc中沒有描述,但它將事件偵聽器綁定到組件主機元素。在你的情況下<app-date-picker>。 但是,當您單擊彈出窗口本身之外的任何位置時,您想要隱藏彈出窗口,因此您需要將偵聽器綁定到整個頁面(文檔)。要做到這一點,必須將document:添加前綴事件名稱:

@HostListener('document:click', ['$event']) 

我不知道是否還有其他的一些支持的前綴,也許window。您可以使用Plunker(來自question)參加比賽。還有一個關於meaning of the HostListener decorator的問題。

+0

謝謝你,我欣賞 –