6
6
* found in the LICENSE file at https://angular.io/license
7
7
*/
8
8
9
+
9
10
export type OpenAction = 'focus' | 'click' | 'downKey' | 'toggle' ;
10
11
export type OpenActionInput = OpenAction | OpenAction [ ] | string | null | undefined ;
11
12
@@ -14,7 +15,7 @@ import {
14
15
Directive ,
15
16
ElementRef ,
16
17
EventEmitter , HostListener ,
17
- Input ,
18
+ Input , isDevMode ,
18
19
OnDestroy ,
19
20
Optional ,
20
21
Output , ViewContainerRef
@@ -32,16 +33,18 @@ import {Directionality} from '@angular/cdk/bidi';
32
33
import { BooleanInput , coerceBooleanProperty , coerceArray } from '@angular/cdk/coercion' ;
33
34
import { DOWN_ARROW , ESCAPE } from '@angular/cdk/keycodes' ;
34
35
36
+ const allowedOpenActions = [ 'focus' , 'click' , 'downKey' , 'toggle' ] ;
35
37
36
38
@Directive ( {
37
39
selector : '[cdkCombobox]' ,
38
40
exportAs : 'cdkCombobox' ,
39
41
host : {
40
42
'role' : 'combobox' ,
41
43
'class' : 'cdk-combobox' ,
42
- '(click)' : 'onClick( )' ,
43
- '(focus)' : 'onFocus( )' ,
44
+ '(click)' : '_handleInteractions("click" )' ,
45
+ '(focus)' : '_handleInteractions("focus" )' ,
44
46
'(keydown)' : 'keydown($event)' ,
47
+ '(document:click)' : '_attemptClose($event)' ,
45
48
'[attr.aria-disabled]' : 'disabled' ,
46
49
'[attr.aria-owns]' : 'contentId' ,
47
50
'[attr.aria-haspopup]' : 'contentType' ,
@@ -109,22 +112,6 @@ export class CdkCombobox<T = unknown> implements OnDestroy, AfterContentInit {
109
112
this . panelValueChanged . complete ( ) ;
110
113
}
111
114
112
- onClick ( ) {
113
- if ( this . _openActions . indexOf ( 'toggle' ) !== - 1 ) {
114
- this . toggle ( ) ;
115
- } else if ( this . _openActions . indexOf ( 'click' ) !== - 1 ) {
116
- this . open ( ) ;
117
- }
118
- }
119
-
120
- onFocus ( ) {
121
- if ( this . _openActions . indexOf ( 'focus' ) === - 1 ) {
122
- return ;
123
- }
124
-
125
- this . open ( ) ;
126
- }
127
-
128
115
keydown ( event : KeyboardEvent ) {
129
116
const { keyCode} = event ;
130
117
@@ -136,7 +123,20 @@ export class CdkCombobox<T = unknown> implements OnDestroy, AfterContentInit {
136
123
}
137
124
}
138
125
139
- @HostListener ( 'document:click' , [ '$event' ] )
126
+ _handleInteractions ( interaction : string ) {
127
+ if ( interaction === 'click' ) {
128
+ if ( this . _openActions . indexOf ( 'toggle' ) !== - 1 ) {
129
+ this . toggle ( ) ;
130
+ } else if ( this . _openActions . indexOf ( 'click' ) !== - 1 ) {
131
+ this . open ( ) ;
132
+ }
133
+ } else if ( interaction === 'focus' ) {
134
+ if ( this . _openActions . indexOf ( 'focus' ) !== - 1 ) {
135
+ this . open ( ) ;
136
+ }
137
+ }
138
+ }
139
+
140
140
_attemptClose ( event : MouseEvent ) {
141
141
if ( this . isOpen ( ) ) {
142
142
let target = event . composedPath ? event . composedPath ( ) [ 0 ] : event . target ;
@@ -240,21 +240,11 @@ export class CdkCombobox<T = unknown> implements OnDestroy, AfterContentInit {
240
240
}
241
241
242
242
private _coerceOpenActionProperty ( input : string | OpenAction [ ] ) : OpenAction [ ] {
243
- let actions : OpenAction [ ] = [ ] ;
244
- const viableActions = [ 'focus' , 'click' , 'downKey' , 'toggle' ] ;
245
-
246
- if ( typeof input === 'string' ) {
247
- const tokens = input . trim ( ) . split ( / [ , ] + / ) ;
248
- for ( const token of tokens ) {
249
- if ( viableActions . indexOf ( token ) === - 1 ) {
250
- throw Error ( `${ token } is not a supported open action` ) ;
251
- }
252
- actions . push ( token as OpenAction ) ;
253
- }
254
- } else {
255
- actions = coerceArray ( input ) ;
243
+ let actions = typeof input === 'string' ? input . trim ( ) . split ( / [ , ] + / ) : input ;
244
+ if ( isDevMode ( ) && actions . some ( a => allowedOpenActions . indexOf ( a ) === - 1 ) ) {
245
+ throw Error ( `${ input } is not a support open action for CdkCombobox` ) ;
256
246
}
257
- return actions ;
247
+ return actions as OpenAction [ ] ;
258
248
}
259
249
260
250
static ngAcceptInputType_openActions : OpenActionInput ;
0 commit comments