@koobiq/components 20.1.0 → 20.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (249) hide show
  1. package/accordion/_accordion-theme.scss +6 -2
  2. package/accordion/accordion-tokens.scss +3 -0
  3. package/accordion/{accordion-trigger.component.scss → accordion-trigger.scss} +10 -0
  4. package/accordion/accordion.scss +71 -0
  5. package/accordion/index.d.ts +264 -121
  6. package/actions-panel/index.d.ts +25 -13
  7. package/alert/_alert-theme.scss +14 -0
  8. package/alert/alert.component.scss +24 -13
  9. package/alert/index.d.ts +63 -29
  10. package/app-switcher/app-switcher-dropdown-app.scss +7 -5
  11. package/app-switcher/app-switcher-dropdown-site.scss +6 -4
  12. package/app-switcher/index.d.ts +41 -4
  13. package/app-switcher/kbq-app-switcher-list-item.scss +6 -8
  14. package/autocomplete/autocomplete.scss +2 -1
  15. package/autocomplete/index.d.ts +58 -37
  16. package/badge/index.d.ts +2 -3
  17. package/breadcrumbs/index.d.ts +1 -1
  18. package/button/index.d.ts +2 -2
  19. package/button-toggle/button-toggle-tokens.scss +2 -0
  20. package/button-toggle/button-toggle.scss +9 -0
  21. package/button-toggle/index.d.ts +5 -0
  22. package/checkbox/index.d.ts +33 -29
  23. package/clamped-text/index.d.ts +3 -2
  24. package/code-block/index.d.ts +24 -19
  25. package/content-panel/index.d.ts +1 -1
  26. package/core/index.d.ts +1217 -186
  27. package/core/option/_action-container-mixins.scss +28 -0
  28. package/core/option/_option-theme.scss +24 -0
  29. package/core/option/action.scss +7 -0
  30. package/core/styles/_core.scss +2 -0
  31. package/core/styles/_koobiq-theme.scss +2 -0
  32. package/core/styles/_tokens.scss +1 -0
  33. package/core/styles/common/_animation.scss +31 -24
  34. package/core/styles/common/_connected-overlay.scss +39 -0
  35. package/core/styles/common/_select.scss +19 -2
  36. package/core/styles/common/_tokens.scss +0 -9
  37. package/core/styles/theming/_index.scss +0 -1
  38. package/core/styles/theming/_theming.scss +34 -5
  39. package/datepicker/index.d.ts +46 -15
  40. package/dl/dl.scss +26 -0
  41. package/dl/index.d.ts +8 -1
  42. package/dropdown/_dropdown-theme.scss +28 -2
  43. package/dropdown/dropdown-item.scss +29 -0
  44. package/dropdown/dropdown-tokens.scss +2 -1
  45. package/dropdown/dropdown.scss +16 -1
  46. package/dropdown/index.d.ts +331 -17
  47. package/dynamic-translation/index.d.ts +1 -1
  48. package/fesm2022/koobiq-components-accordion.mjs +480 -317
  49. package/fesm2022/koobiq-components-accordion.mjs.map +1 -1
  50. package/fesm2022/koobiq-components-actions-panel.mjs +57 -46
  51. package/fesm2022/koobiq-components-actions-panel.mjs.map +1 -1
  52. package/fesm2022/koobiq-components-alert.mjs +98 -58
  53. package/fesm2022/koobiq-components-alert.mjs.map +1 -1
  54. package/fesm2022/koobiq-components-app-switcher.mjs +233 -38
  55. package/fesm2022/koobiq-components-app-switcher.mjs.map +1 -1
  56. package/fesm2022/koobiq-components-autocomplete.mjs +89 -52
  57. package/fesm2022/koobiq-components-autocomplete.mjs.map +1 -1
  58. package/fesm2022/koobiq-components-badge.mjs +18 -17
  59. package/fesm2022/koobiq-components-badge.mjs.map +1 -1
  60. package/fesm2022/koobiq-components-breadcrumbs.mjs +25 -25
  61. package/fesm2022/koobiq-components-breadcrumbs.mjs.map +1 -1
  62. package/fesm2022/koobiq-components-button-toggle.mjs +17 -12
  63. package/fesm2022/koobiq-components-button-toggle.mjs.map +1 -1
  64. package/fesm2022/koobiq-components-button.mjs +25 -25
  65. package/fesm2022/koobiq-components-checkbox.mjs +69 -92
  66. package/fesm2022/koobiq-components-checkbox.mjs.map +1 -1
  67. package/fesm2022/koobiq-components-clamped-text.mjs +18 -13
  68. package/fesm2022/koobiq-components-clamped-text.mjs.map +1 -1
  69. package/fesm2022/koobiq-components-code-block.mjs +56 -69
  70. package/fesm2022/koobiq-components-code-block.mjs.map +1 -1
  71. package/fesm2022/koobiq-components-content-panel.mjs +29 -29
  72. package/fesm2022/koobiq-components-core.mjs +2485 -735
  73. package/fesm2022/koobiq-components-core.mjs.map +1 -1
  74. package/fesm2022/koobiq-components-datepicker.mjs +168 -126
  75. package/fesm2022/koobiq-components-datepicker.mjs.map +1 -1
  76. package/fesm2022/koobiq-components-divider.mjs +7 -7
  77. package/fesm2022/koobiq-components-dl.mjs +23 -15
  78. package/fesm2022/koobiq-components-dl.mjs.map +1 -1
  79. package/fesm2022/koobiq-components-dropdown.mjs +814 -136
  80. package/fesm2022/koobiq-components-dropdown.mjs.map +1 -1
  81. package/fesm2022/koobiq-components-dynamic-translation.mjs +13 -13
  82. package/fesm2022/koobiq-components-ellipsis-center.mjs +7 -7
  83. package/fesm2022/koobiq-components-empty-state.mjs +19 -19
  84. package/fesm2022/koobiq-components-file-upload.mjs +74 -42
  85. package/fesm2022/koobiq-components-file-upload.mjs.map +1 -1
  86. package/fesm2022/koobiq-components-filter-bar.mjs +783 -199
  87. package/fesm2022/koobiq-components-filter-bar.mjs.map +1 -1
  88. package/fesm2022/koobiq-components-flag.mjs +7 -7
  89. package/fesm2022/koobiq-components-form-field.mjs +350 -162
  90. package/fesm2022/koobiq-components-form-field.mjs.map +1 -1
  91. package/fesm2022/koobiq-components-icon.mjs +52 -25
  92. package/fesm2022/koobiq-components-icon.mjs.map +1 -1
  93. package/fesm2022/koobiq-components-inline-edit.mjs +175 -28
  94. package/fesm2022/koobiq-components-inline-edit.mjs.map +1 -1
  95. package/fesm2022/koobiq-components-input.mjs +41 -24
  96. package/fesm2022/koobiq-components-input.mjs.map +1 -1
  97. package/fesm2022/koobiq-components-link.mjs +8 -8
  98. package/fesm2022/koobiq-components-list.mjs +657 -143
  99. package/fesm2022/koobiq-components-list.mjs.map +1 -1
  100. package/fesm2022/koobiq-components-loader-overlay.mjs +16 -16
  101. package/fesm2022/koobiq-components-markdown.mjs +14 -11
  102. package/fesm2022/koobiq-components-markdown.mjs.map +1 -1
  103. package/fesm2022/koobiq-components-modal.mjs +59 -35
  104. package/fesm2022/koobiq-components-modal.mjs.map +1 -1
  105. package/fesm2022/koobiq-components-navbar.mjs +177 -67
  106. package/fesm2022/koobiq-components-navbar.mjs.map +1 -1
  107. package/fesm2022/koobiq-components-notification-center.mjs +40 -24
  108. package/fesm2022/koobiq-components-notification-center.mjs.map +1 -1
  109. package/fesm2022/koobiq-components-overflow-items.mjs +16 -17
  110. package/fesm2022/koobiq-components-overflow-items.mjs.map +1 -1
  111. package/fesm2022/koobiq-components-popover.mjs +31 -21
  112. package/fesm2022/koobiq-components-popover.mjs.map +1 -1
  113. package/fesm2022/koobiq-components-progress-bar.mjs +13 -13
  114. package/fesm2022/koobiq-components-progress-spinner.mjs +13 -13
  115. package/fesm2022/koobiq-components-radio.mjs +10 -10
  116. package/fesm2022/koobiq-components-resizer.mjs +33 -14
  117. package/fesm2022/koobiq-components-resizer.mjs.map +1 -1
  118. package/fesm2022/koobiq-components-scrollbar.mjs +10 -10
  119. package/fesm2022/koobiq-components-search-expandable.mjs +49 -14
  120. package/fesm2022/koobiq-components-search-expandable.mjs.map +1 -1
  121. package/fesm2022/koobiq-components-select.mjs +450 -146
  122. package/fesm2022/koobiq-components-select.mjs.map +1 -1
  123. package/fesm2022/koobiq-components-sidebar.mjs +14 -14
  124. package/fesm2022/koobiq-components-sidepanel.mjs +26 -26
  125. package/fesm2022/koobiq-components-skeleton.mjs +10 -10
  126. package/fesm2022/koobiq-components-split-button.mjs +10 -17
  127. package/fesm2022/koobiq-components-split-button.mjs.map +1 -1
  128. package/fesm2022/koobiq-components-splitter.mjs +17 -17
  129. package/fesm2022/koobiq-components-table.mjs +15 -13
  130. package/fesm2022/koobiq-components-table.mjs.map +1 -1
  131. package/fesm2022/koobiq-components-tabs.mjs +80 -68
  132. package/fesm2022/koobiq-components-tabs.mjs.map +1 -1
  133. package/fesm2022/koobiq-components-tags.mjs +283 -122
  134. package/fesm2022/koobiq-components-tags.mjs.map +1 -1
  135. package/fesm2022/koobiq-components-textarea.mjs +13 -8
  136. package/fesm2022/koobiq-components-textarea.mjs.map +1 -1
  137. package/fesm2022/koobiq-components-time-range.mjs +29 -24
  138. package/fesm2022/koobiq-components-time-range.mjs.map +1 -1
  139. package/fesm2022/koobiq-components-timepicker.mjs +61 -30
  140. package/fesm2022/koobiq-components-timepicker.mjs.map +1 -1
  141. package/fesm2022/koobiq-components-timezone.mjs +77 -42
  142. package/fesm2022/koobiq-components-timezone.mjs.map +1 -1
  143. package/fesm2022/koobiq-components-title.mjs +7 -7
  144. package/fesm2022/koobiq-components-toast.mjs +51 -26
  145. package/fesm2022/koobiq-components-toast.mjs.map +1 -1
  146. package/fesm2022/koobiq-components-toggle.mjs +72 -64
  147. package/fesm2022/koobiq-components-toggle.mjs.map +1 -1
  148. package/fesm2022/koobiq-components-tooltip.mjs +219 -28
  149. package/fesm2022/koobiq-components-tooltip.mjs.map +1 -1
  150. package/fesm2022/koobiq-components-top-bar.mjs +13 -13
  151. package/fesm2022/koobiq-components-tree-select.mjs +222 -80
  152. package/fesm2022/koobiq-components-tree-select.mjs.map +1 -1
  153. package/fesm2022/koobiq-components-tree.mjs +302 -81
  154. package/fesm2022/koobiq-components-tree.mjs.map +1 -1
  155. package/fesm2022/koobiq-components-username.mjs +27 -27
  156. package/file-upload/index.d.ts +25 -6
  157. package/file-upload/multiple-file-upload.component.scss +14 -0
  158. package/filter-bar/_filter-bar-theme.scss +0 -10
  159. package/filter-bar/filter-bar-tokens.scss +3 -0
  160. package/filter-bar/filters.scss +3 -2
  161. package/filter-bar/index.d.ts +281 -9
  162. package/filter-bar/pipes/base-pipe.scss +0 -11
  163. package/filter-bar/pipes/pipe-input.scss +10 -0
  164. package/filter-bar/pipes/pipe-multi-tree-select.scss +0 -6
  165. package/filter-bar/pipes/pipe-multiselect.scss +0 -6
  166. package/filter-bar/pipes/pipe-tree-select.scss +0 -6
  167. package/form-field/_form-field-theme.scss +76 -20
  168. package/form-field/fieldset.scss +10 -0
  169. package/form-field/form-field-tokens.scss +15 -1
  170. package/form-field/form-field.scss +15 -19
  171. package/form-field/index.d.ts +147 -65
  172. package/icon/icon-button.scss +3 -1
  173. package/icon/index.d.ts +45 -7
  174. package/inline-edit/index.d.ts +57 -4
  175. package/inline-edit/inline-edit.scss +10 -0
  176. package/input/index.d.ts +17 -2
  177. package/list/_list-theme.scss +42 -10
  178. package/list/index.d.ts +326 -79
  179. package/list/list-tokens.scss +43 -8
  180. package/list/list.scss +186 -12
  181. package/markdown/index.d.ts +1 -1
  182. package/modal/index.d.ts +21 -4
  183. package/modal/modal-tokens.scss +1 -1
  184. package/navbar/_navbar-item_vertical.scss +7 -5
  185. package/navbar/index.d.ts +54 -5
  186. package/navbar/navbar-brand.scss +23 -7
  187. package/navbar/vertical-navbar.scss +6 -0
  188. package/notification-center/index.d.ts +2 -1
  189. package/notification-center/notification-item.scss +6 -0
  190. package/package.json +3 -6
  191. package/popover/index.d.ts +2 -2
  192. package/prebuilt-themes/dark-theme.css +1 -1
  193. package/prebuilt-themes/light-theme.css +1 -1
  194. package/prebuilt-themes/theme.css +1 -1
  195. package/resizer/index.d.ts +12 -0
  196. package/schematics/collection.json +10 -0
  197. package/schematics/migrations/alert-signals/README.md +64 -0
  198. package/schematics/migrations/alert-signals/data.js +70 -0
  199. package/schematics/migrations/alert-signals/index.js +350 -0
  200. package/schematics/migrations/alert-signals/schema.json +20 -0
  201. package/schematics/migrations/autocomplete-panel-width-auto/README.md +68 -0
  202. package/schematics/migrations/autocomplete-panel-width-auto/index.js +70 -0
  203. package/schematics/migrations/autocomplete-panel-width-auto/schema.json +15 -0
  204. package/schematics/migrations/deprecated-icons/README.md +29 -4
  205. package/schematics/migrations/deprecated-icons/data.js +7 -0
  206. package/schematics/migrations/deprecated-icons/index.js +62 -35
  207. package/schematics/migrations/filter-bar-signals/README.md +1 -1
  208. package/schematics/migrations/new-icons-pack/README.md +37 -2
  209. package/schematics/migrations/new-icons-pack/data.js +8 -0
  210. package/schematics/migrations/new-icons-pack/index.js +144 -53
  211. package/schematics/migrations.json +11 -1
  212. package/schematics/ng-add/index.js +3 -3
  213. package/schematics/utils/angular-parsing.js +41 -14
  214. package/schematics/utils/ast.js +31 -0
  215. package/schematics/utils/icon-migration.js +530 -0
  216. package/schematics/utils/typescript.js +44 -0
  217. package/scrollbar/index.d.ts +1 -1
  218. package/search-expandable/index.d.ts +3 -0
  219. package/select/index.d.ts +212 -40
  220. package/select/select-tokens.scss +0 -1
  221. package/select/select.scss +0 -2
  222. package/splitter/index.d.ts +1 -1
  223. package/table/_table-theme.scss +4 -0
  224. package/table/index.d.ts +2 -1
  225. package/table/table.scss +8 -0
  226. package/tabs/_tabs-common.scss +60 -31
  227. package/tabs/_tabs-theme.scss +12 -0
  228. package/tabs/index.d.ts +2 -2
  229. package/tabs/tab-header.scss +14 -0
  230. package/tabs/tab-nav-bar.scss +4 -0
  231. package/tabs/tabs-tokens.scss +1 -0
  232. package/tags/index.d.ts +128 -29
  233. package/textarea/index.d.ts +5 -0
  234. package/time-range/index.d.ts +1 -1
  235. package/timepicker/index.d.ts +4 -0
  236. package/timezone/index.d.ts +10 -8
  237. package/toast/index.d.ts +26 -3
  238. package/toggle/index.d.ts +34 -14
  239. package/tooltip/index.d.ts +119 -7
  240. package/tree/_tree-theme.scss +25 -5
  241. package/tree/index.d.ts +71 -3
  242. package/tree/tree-option.scss +2 -8
  243. package/tree-select/_tree-select-theme.scss +22 -0
  244. package/tree-select/index.d.ts +127 -36
  245. package/accordion/accordion.component.scss +0 -50
  246. package/core/styles/_tokens.kbq.import.scss +0 -4
  247. package/core/styles/theming/_components-theming.scss +0 -1927
  248. package/filter-bar/pipes/pipe-select.scss +0 -5
  249. package/overflow-items/overflow-items.scss +0 -20
@@ -1,19 +1,20 @@
1
- import { trigger, state, transition, style, animate, group, query } from '@angular/animations';
1
+ import { trigger, state, style, transition, animate, group, query } from '@angular/animations';
2
2
  import { TemplatePortal, DomPortalOutlet } from '@angular/cdk/portal';
3
3
  import { DOCUMENT } from '@angular/common';
4
4
  import * as i0 from '@angular/core';
5
- import { inject, TemplateRef, ApplicationRef, Injector, ViewContainerRef, Directive, InjectionToken, ElementRef, booleanAttribute, Input, ContentChild, ViewChild, ViewEncapsulation, ChangeDetectionStrategy, Component, NgZone, contentChild, input, EventEmitter, QueryList, Output, ContentChildren, ChangeDetectorRef, Renderer2, output, numberAttribute, NgModule } from '@angular/core';
6
- import { Subject, Subscription, merge, of, asapScheduler } from 'rxjs';
5
+ import { inject, TemplateRef, ApplicationRef, Injector, ViewContainerRef, Directive, InjectionToken, ElementRef, effect, contentChild, input, booleanAttribute, signal, Input, ContentChild, ViewChild, ViewEncapsulation, ChangeDetectionStrategy, Component, NgZone, DestroyRef, contentChildren, computed, numberAttribute, EventEmitter, QueryList, untracked, Output, ContentChildren, ChangeDetectorRef, Renderer2, output, NgModule } from '@angular/core';
6
+ import { Subject, Subscription, merge, timer, of, asapScheduler } from 'rxjs';
7
7
  import { FocusMonitor } from '@angular/cdk/a11y';
8
- import { KbqComponentColors, KBQ_TITLE_TEXT_REF, FocusKeyManager, RIGHT_ARROW, LEFT_ARROW, ESCAPE, KBQ_WINDOW, ENTER, SPACE, DOWN_ARROW as DOWN_ARROW$1, defaultOffsetY } from '@koobiq/components/core';
8
+ import { TAB, UP_ARROW, DOWN_ARROW, ENTER } from '@angular/cdk/keycodes';
9
+ import { KBQ_PANEL_DEFAULT_MIN_WIDTH, KbqComponentColors, KBQ_TITLE_TEXT_REF, ESCAPE, LEFT_ARROW, RIGHT_ARROW, isPointInRect, isPointInTriangle, ActiveDescendantKeyManager, FocusKeyManager, getSafeTriangleVertices, ENTER as ENTER$1, SPACE, DOWN_ARROW as DOWN_ARROW$1, defaultOffsetY, kbqResolvePanelWidth, kbqGetPanelWidthOrigin, kbqSiblingPopupProvider } from '@koobiq/components/core';
9
10
  import { KbqIcon, KbqIconModule } from '@koobiq/components/icon';
11
+ import { KBQ_FORM_FIELD, KBQ_FORM_FIELD_DEFAULT_OPTIONS, KbqFormField } from '@koobiq/components/form-field';
10
12
  import { Directionality } from '@angular/cdk/bidi';
11
13
  import { Overlay, OverlayContainer, OverlayConfig, OverlayModule } from '@angular/cdk/overlay';
12
14
  import { normalizePassiveListenerOptions, Platform } from '@angular/cdk/platform';
13
- import { startWith, switchMap, take, filter, takeUntil, delay } from 'rxjs/operators';
15
+ import { takeUntilDestroyed, outputToObservable } from '@angular/core/rxjs-interop';
16
+ import { take, startWith, switchMap, filter, delay, map, takeUntil } from 'rxjs/operators';
14
17
  import { coerceBooleanProperty } from '@angular/cdk/coercion';
15
- import { UP_ARROW, DOWN_ARROW } from '@angular/cdk/keycodes';
16
- import { KbqFormField } from '@koobiq/components/form-field';
17
18
 
18
19
  /**
19
20
  * Animations used by the kbq-dropdown component.
@@ -100,10 +101,10 @@ class KbqDropdownContent {
100
101
  ngOnDestroy() {
101
102
  this.outlet?.dispose();
102
103
  }
103
- /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownContent, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
104
- /** @nocollapse */ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.25", type: KbqDropdownContent, isStandalone: true, selector: "ng-template[kbqDropdownContent]", ngImport: i0 }); }
104
+ /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownContent, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
105
+ /** @nocollapse */ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.30", type: KbqDropdownContent, isStandalone: true, selector: "ng-template[kbqDropdownContent]", ngImport: i0 }); }
105
106
  }
106
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownContent, decorators: [{
107
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownContent, decorators: [{
107
108
  type: Directive,
108
109
  args: [{
109
110
  selector: 'ng-template[kbqDropdownContent]'
@@ -138,6 +139,99 @@ function throwKbqDropdownInvalidPositionY() {
138
139
  throw Error(`yPosition value must be either 'above' or below'.
139
140
  Example: <kbq-dropdown [yPosition]="'above'" #dropdown="kbqDropdown"></kbq-dropdown>`);
140
141
  }
142
+ /**
143
+ * Throws an exception for the case when `kbqDropdownSearch` is applied to a form field that doesn't
144
+ * host a `kbqInput`.
145
+ * @docs-private
146
+ */
147
+ function throwKbqDropdownSearchMissingInputError() {
148
+ throw Error(`kbqDropdownSearch: must be applied to a kbq-form-field containing an input[kbqInput].
149
+ Example:
150
+ <kbq-form-field kbqDropdownSearch>
151
+ <input kbqInput [formControl]="control" />
152
+ </kbq-form-field>`);
153
+ }
154
+ /**
155
+ * Throws an exception for the case when `kbqDropdownSearch`'s input isn't bound to a form control, so
156
+ * there is no query to react to.
157
+ * @docs-private
158
+ */
159
+ function throwKbqDropdownSearchMissingNgControlError() {
160
+ throw Error(`kbqDropdownSearch: the input must be bound to a form control.
161
+ Example:
162
+ <kbq-form-field kbqDropdownSearch>
163
+ <input kbqInput [formControl]="control" />
164
+ </kbq-form-field>`);
165
+ }
166
+
167
+ /** @docs-private */
168
+ const KBQ_DROPDOWN_ITEM_ACTION_HOST = new InjectionToken('kbqDropdownItemAction-host');
169
+ /**
170
+ * Marks a secondary, independently-focusable/clickable element (e.g. a settings link) projected
171
+ * inside a `kbq-dropdown-item` alongside the item's own primary action. Requires the item's host
172
+ * element to be non-interactive (e.g. `<div kbq-dropdown-item>`), since interactive content
173
+ * cannot validly nest inside another interactive element.
174
+ */
175
+ class KbqDropdownItemAction {
176
+ constructor() {
177
+ this.elementRef = inject(ElementRef);
178
+ this.dropdownItem = inject(KBQ_DROPDOWN_ITEM_ACTION_HOST);
179
+ /**
180
+ * The `tabindex` this element had before `isInactive()` first forced it to `-1`, so it can be
181
+ * restored instead of left removed. Plain `[attr.tabindex]` can't do this: co-located host
182
+ * bindings for the same attribute (e.g. `KbqIconButton`'s own `tabindex`) apply in directive
183
+ * order and the last one always wins outright, so writing `null` here on the active branch
184
+ * would strip whatever tabindex the host component set, not just leave it alone.
185
+ */
186
+ this.originalTabindex = null;
187
+ effect(() => {
188
+ const el = this.elementRef.nativeElement;
189
+ if (this.isInactive()) {
190
+ if (this.originalTabindex === null)
191
+ this.originalTabindex = el.getAttribute('tabindex');
192
+ el.setAttribute('tabindex', '-1');
193
+ }
194
+ else if (this.originalTabindex !== null) {
195
+ el.setAttribute('tabindex', this.originalTabindex);
196
+ this.originalTabindex = null;
197
+ }
198
+ });
199
+ }
200
+ /** Returns the host DOM element. */
201
+ getHostElement() {
202
+ return this.elementRef.nativeElement;
203
+ }
204
+ /** `progress` takes priority over the action, same as `disabled`. */
205
+ isInactive() {
206
+ return this.dropdownItem.disabled || this.dropdownItem.progress();
207
+ }
208
+ /**
209
+ * Always stops the click from bubbling to the item's own primary click handler.
210
+ * Additionally, blocks the action's own default behavior when the parent item is
211
+ * disabled/loading — `<a>` has no native `disabled`.
212
+ */
213
+ onClick(event) {
214
+ event.stopPropagation();
215
+ if (this.isInactive()) {
216
+ event.preventDefault();
217
+ event.stopImmediatePropagation();
218
+ }
219
+ }
220
+ /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownItemAction, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
221
+ /** @nocollapse */ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.30", type: KbqDropdownItemAction, isStandalone: true, selector: "[kbqDropdownItemAction]", host: { listeners: { "click": "onClick($event)" }, properties: { "class.kbq-disabled": "isInactive()", "attr.aria-disabled": "isInactive() || null" }, classAttribute: "kbq-dropdown-item__action" }, ngImport: i0 }); }
222
+ }
223
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownItemAction, decorators: [{
224
+ type: Directive,
225
+ args: [{
226
+ selector: '[kbqDropdownItemAction]',
227
+ host: {
228
+ class: 'kbq-dropdown-item__action',
229
+ '[class.kbq-disabled]': 'isInactive()',
230
+ '[attr.aria-disabled]': 'isInactive() || null',
231
+ '(click)': 'onClick($event)'
232
+ }
233
+ }]
234
+ }], ctorParameters: () => [] });
141
235
 
142
236
  /**
143
237
  * Injection token used to provide the parent dropdown to dropdown-specific components.
@@ -157,7 +251,13 @@ function KBQ_DROPDOWN_DEFAULT_OPTIONS_FACTORY() {
157
251
  xPosition: 'after',
158
252
  yPosition: 'below',
159
253
  backdropClass: 'cdk-overlay-transparent-backdrop',
160
- hasBackdrop: false
254
+ hasBackdrop: false,
255
+ safeArea: true,
256
+ // Reproduces the pre-existing CSS-driven sizing: grow with content, never narrower than the
257
+ // trigger or `--kbq-dropdown-size-container-width-min`, capped by the token.
258
+ panelWidth: null,
259
+ panelMinWidth: KBQ_PANEL_DEFAULT_MIN_WIDTH,
260
+ panelMaxWidth: null
161
261
  };
162
262
  }
163
263
 
@@ -166,39 +266,47 @@ function KBQ_DROPDOWN_DEFAULT_OPTIONS_FACTORY() {
166
266
  * It exists mostly to set the role attribute.
167
267
  */
168
268
  class KbqDropdownItem {
269
+ // TODO: Skipped for migration because:
270
+ // Accessor inputs cannot be migrated as they are too complex.
271
+ get disabled() {
272
+ return this._disabled;
273
+ }
274
+ set disabled(value) {
275
+ if (value !== this.disabled) {
276
+ this._disabled = value;
277
+ }
278
+ }
169
279
  constructor() {
170
280
  this.elementRef = inject(ElementRef);
171
281
  this.focusMonitor = inject(FocusMonitor);
172
282
  this.parentDropdownPanel = inject(KBQ_DROPDOWN_PANEL, { optional: true });
283
+ /** Secondary, independently-focusable icon action projected into the item (e.g. a settings link). */
284
+ this.itemAction = contentChild(KbqDropdownItemAction, ...(ngDevMode ? [{ debugName: "itemAction" }] : []));
173
285
  this._disabled = false;
286
+ /** Whether the dropdown item is in a loading state. */
287
+ this.progress = input(false, ...(ngDevMode ? [{ debugName: "progress", transform: booleanAttribute }] : [{ transform: booleanAttribute }]));
174
288
  /** Stream that emits when the dropdown item is hovered. */
175
289
  this.hovered = new Subject();
176
290
  /** Stream that emits when the menu item is focused. */
177
291
  this.focused = new Subject();
178
292
  /** Whether the dropdown item is highlighted. */
179
293
  this.highlighted = false;
294
+ /** Whether the item is the panel's active item while DOM focus is held elsewhere. */
295
+ this.active = signal(false, ...(ngDevMode ? [{ debugName: "active" }] : []));
180
296
  /** Whether the dropdown item acts as a trigger for a nested dropdown. */
181
297
  this.isNested = false;
182
298
  /** @docs-private */
183
299
  this.componentColors = KbqComponentColors;
184
- }
185
- // TODO: Skipped for migration because:
186
- // Accessor inputs cannot be migrated as they are too complex.
187
- get disabled() {
188
- return this._disabled;
189
- }
190
- set disabled(value) {
191
- if (value !== this.disabled) {
192
- this._disabled = value;
193
- }
194
- }
195
- ngAfterViewInit() {
196
- if (this.focusMonitor) {
197
- // Start monitoring the element so it gets the appropriate focused classes. We want
198
- // to show the focus style for menu items only when the focus was not caused by a
199
- // mouse or touch interaction.
200
- this.focusMonitor.monitor(this.elementRef, false);
201
- }
300
+ effect(() => {
301
+ // Start monitoring the element so it gets the appropriate focused classes. We want to
302
+ // show the focus style for menu items only when the focus was not caused by a mouse or
303
+ // touch interaction. When `itemAction` is present, focus can land on it instead of the
304
+ // host, so children must be checked too for the focused classes to still be applied to
305
+ // the host. `monitor()` doesn't update `checkChildren` on an already-monitored element,
306
+ // so this restarts monitoring whenever `itemAction()` changes to keep it in sync.
307
+ this.focusMonitor.stopMonitoring(this.elementRef);
308
+ this.focusMonitor.monitor(this.elementRef, !!this.itemAction());
309
+ });
202
310
  }
203
311
  ngOnDestroy() {
204
312
  if (this.focusMonitor) {
@@ -210,15 +318,35 @@ class KbqDropdownItem {
210
318
  resetStyles() {
211
319
  this.getHostElement().classList.remove('cdk-keyboard-focused');
212
320
  }
213
- /** Focuses the dropdown item. */
321
+ /** Styles the item as active without focusing it. */
322
+ setActiveStyles() {
323
+ this.active.set(true);
324
+ }
325
+ /** Removes the styles applied by `setActiveStyles`. */
326
+ setInactiveStyles() {
327
+ this.active.set(false);
328
+ }
329
+ /**
330
+ * Focuses the dropdown item and reveals it.
331
+ *
332
+ * The reveal is explicit because the one `focus()` performs implicitly is not portable: WebKit defers
333
+ * it to a later rendering update, where it lands after — and undoes — any scrolling the reader did in
334
+ * the meantime. `preventScroll` is therefore always forced on, overriding `options`.
335
+ */
214
336
  focus(origin, options) {
215
337
  if (this.disabled)
216
338
  return;
339
+ const element = this.getHostElement();
340
+ const focusOptions = { ...options, preventScroll: true };
217
341
  if (this.focusMonitor && origin) {
218
- this.focusMonitor.focusVia(this.getHostElement(), origin, options);
342
+ this.focusMonitor.focusVia(element, origin, focusOptions);
219
343
  }
220
344
  else {
221
- this.getHostElement().focus(options);
345
+ element.focus(focusOptions);
346
+ }
347
+ // With the pointer already on this item, revealing it would shift the list out from under it.
348
+ if (origin !== 'mouse') {
349
+ element.scrollIntoView?.({ block: 'nearest', inline: 'nearest' });
222
350
  }
223
351
  this.focused.next(this);
224
352
  }
@@ -240,98 +368,227 @@ class KbqDropdownItem {
240
368
  /** Emits to the hover stream. Bound via `host` metadata. */
241
369
  handleMouseEnter() {
242
370
  this.hovered.next(this);
371
+ // In search mode the panel makes the hovered item active instead, keeping the caret in the query.
372
+ if (this.parentDropdownPanel?.inSearchMode?.())
373
+ return;
243
374
  this.focus('mouse');
244
375
  }
376
+ /**
377
+ * Lets Tab move focus between the host and `itemAction` without leaving the dropdown
378
+ * (`stopPropagation` only — the browser's native focus move still happens). Any other Tab
379
+ * press, i.e. actually leaving the item, is left untouched and still closes the dropdown via
380
+ * the panel's `FocusKeyManager.tabOut`. Bound via `host` metadata.
381
+ */
382
+ handleActionKeydown(event) {
383
+ const action = this.itemAction();
384
+ if (!action || event.keyCode !== TAB || this.disabled || this.progress())
385
+ return;
386
+ const target = event.target;
387
+ const hostEl = this.getHostElement();
388
+ const actionEl = action.getHostElement();
389
+ const movesToAction = !event.shiftKey && target === hostEl;
390
+ const movesBackToHost = event.shiftKey && target === actionEl;
391
+ if (movesToAction || movesBackToHost) {
392
+ event.stopPropagation();
393
+ }
394
+ }
245
395
  /** Gets the label to be used when determining whether the option should be focused. */
246
396
  getLabel() {
247
397
  const clone = this.getHostElement().cloneNode(true);
248
- const icons = clone.querySelectorAll('[kbq-icon], .kbq-icon');
249
- // Strip away icons so they don't show up in the text.
250
- for (let i = 0; i < icons.length; i++) {
251
- const icon = icons[i];
252
- icon.parentNode?.removeChild(icon);
398
+ const stripped = clone.querySelectorAll('[kbq-icon], .kbq-icon, [kbqDropdownItemAction]');
399
+ // Strip away icons and the action so they don't show up in the text.
400
+ for (let i = 0; i < stripped.length; i++) {
401
+ const node = stripped[i];
402
+ node.parentNode?.removeChild(node);
253
403
  }
254
404
  return clone.textContent?.trim() || '';
255
405
  }
256
406
  haltDisabledEvents(event) {
257
- if (this.disabled) {
407
+ if (this.disabled || this.progress()) {
258
408
  event.preventDefault();
259
409
  event.stopImmediatePropagation();
260
410
  event.stopPropagation();
261
411
  }
262
412
  }
263
- /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownItem, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
264
- /** @nocollapse */ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.25", type: KbqDropdownItem, isStandalone: true, selector: "kbq-dropdown-item, [kbq-dropdown-item]", inputs: { disabled: ["disabled", "disabled", booleanAttribute] }, host: { listeners: { "click": "checkDisabled($event)", "mouseenter": "handleMouseEnter()" }, properties: { "class.kbq-dropdown-item_with-icon": "icon", "class.kbq-dropdown-item_highlighted": "highlighted", "class.kbq-disabled": "disabled", "attr.disabled": "disabled || null", "attr.tabindex": "getTabIndex()" }, classAttribute: "kbq-dropdown-item" }, providers: [
265
- { provide: KBQ_TITLE_TEXT_REF, useExisting: KbqDropdownItem }
266
- ], queries: [{ propertyName: "icon", first: true, predicate: KbqIcon, descendants: true }], viewQueries: [{ propertyName: "textElement", first: true, predicate: ["kbqTitleText"], descendants: true, static: true }], exportAs: ["kbqDropdownItem"], ngImport: i0, template: "<ng-content select=\"[kbq-icon]\" />\n\n<div #kbqTitleText class=\"kbq-dropdown-item__text\">\n <ng-content />\n</div>\n\n@if (isNested) {\n <i kbq-icon=\"kbq-chevron-right-s_16\" class=\"kbq-dropdown-trigger__icon\" [color]=\"componentColors.ContrastFade\"></i>\n}\n\n<div class=\"kbq-dropdown-item-overlay\" (click)=\"haltDisabledEvents($event)\"></div>\n", styles: [".kbq-truncate-line{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-no-select{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.kbq-dropdown-item{width:100%;border-radius:var(--kbq-dropdown-item-border-radius);-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;position:relative;display:flex;flex-direction:row;align-items:center;box-sizing:border-box;outline:none;-webkit-tap-highlight-color:transparent;min-height:32px;gap:var(--kbq-size-s);border:var(--kbq-size-3xs) solid transparent;padding:var(--kbq-size-xxs) calc(var(--kbq-size-m) - var(--kbq-size-3xs))}.kbq-dropdown-item .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown-item .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown-item .kbq-list-text:empty{display:none}.kbq-dropdown-item .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown-item .kbq-list-option-caption{padding-top:var(--kbq-size-3xs)}.kbq-dropdown-item:not(.kbq-disabled){cursor:pointer}.kbq-dropdown-item{text-align:left;align-items:flex-start;text-decoration:none}.kbq-dropdown-item>.kbq-icon:first-child:before,.kbq-dropdown-item>.kbq-icon:first-child>svg{align-self:center;display:flex;height:var(--kbq-size-xl);width:16px;align-items:center}.kbq-dropdown-item .kbq-dropdown-item__caption{padding-top:var(--kbq-size-3xs)}.kbq-dropdown-item__text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown-item__text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown-item__text:empty{display:none}.kbq-dropdown-item__text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown-item-overlay{position:absolute;inset:-1px;border-radius:inherit}.kbq-dropdown__group-header{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;display:flex;flex-direction:row;align-items:center;box-sizing:border-box;min-height:32px;border-left:var(--kbq-size-3xs) solid transparent;border-right:var(--kbq-size-3xs) solid transparent;padding-top:var(--kbq-size-xs);padding-left:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-right:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-bottom:var(--kbq-size-3xs)}.kbq-dropdown__group-header .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown__group-header .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown__group-header .kbq-list-text:empty{display:none}.kbq-dropdown__group-header .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{display:flex;flex-direction:row;align-items:center;box-sizing:border-box;min-height:32px;border-left:var(--kbq-size-3xs) solid transparent;border-right:var(--kbq-size-3xs) solid transparent;padding-top:var(--kbq-size-m);padding-left:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-right:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-bottom:var(--kbq-size-xxs)}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text:empty{display:none}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}\n"], dependencies: [{ kind: "component", type: KbqIcon, selector: "[kbq-icon]", inputs: ["small", "autoColor", "kbq-icon"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
413
+ /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownItem, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
414
+ /** @nocollapse */ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.30", type: KbqDropdownItem, isStandalone: true, selector: "kbq-dropdown-item, [kbq-dropdown-item]", inputs: { disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: false, isRequired: false, transformFunction: booleanAttribute }, progress: { classPropertyName: "progress", publicName: "progress", isSignal: true, isRequired: false, transformFunction: null } }, host: { listeners: { "click": "checkDisabled($event)", "mouseenter": "handleMouseEnter()", "keydown": "handleActionKeydown($event)" }, properties: { "class.kbq-dropdown-item_with-icon": "icon", "class.kbq-dropdown-item_highlighted": "highlighted", "class.kbq-dropdown-item_active": "active()", "class.kbq-disabled": "disabled", "class.kbq-progress": "progress()", "class.kbq-dropdown-item_has-action": "!!itemAction()", "attr.disabled": "disabled || null", "attr.tabindex": "getTabIndex()" }, classAttribute: "kbq-dropdown-item" }, providers: [
415
+ { provide: KBQ_TITLE_TEXT_REF, useExisting: KbqDropdownItem },
416
+ { provide: KBQ_DROPDOWN_ITEM_ACTION_HOST, useExisting: KbqDropdownItem }
417
+ ], queries: [{ propertyName: "itemAction", first: true, predicate: KbqDropdownItemAction, descendants: true, isSignal: true }, { propertyName: "icon", first: true, predicate: KbqIcon, descendants: true }], viewQueries: [{ propertyName: "textElement", first: true, predicate: ["kbqTitleText"], descendants: true }], exportAs: ["kbqDropdownItem"], ngImport: i0, template: "<ng-content select=\"[kbq-icon]\" />\n\n<div #kbqTitleText class=\"kbq-dropdown-item__text\">\n <ng-content />\n</div>\n\n<ng-content select=\"[kbqDropdownItemAction]\" />\n\n@if (isNested) {\n <i kbq-icon=\"kbq-chevron-right-s_16\" class=\"kbq-dropdown-trigger__icon\" [color]=\"componentColors.ContrastFade\"></i>\n}\n\n<div class=\"kbq-dropdown-item-overlay\" (click)=\"haltDisabledEvents($event)\"></div>\n", styles: ["@keyframes kbq-progress{0%{background-position:0 0}to{background-position:64px 0}}.kbq-progress{position:relative}.kbq-progress:after{content:\"\";position:absolute;border-radius:inherit;inset:0;background:linear-gradient(135deg,#0000000a 12px,#ffffff1a 12px 22px,#0000000a 22px 34px,#ffffff1a 34px) repeat;background-size:32px 32px;animation:kbq-progress 1s linear infinite}@media(prefers-reduced-motion:reduce){.kbq-progress:after{animation:none}}.kbq-truncate-line{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-no-select{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.kbq-dropdown-item{width:100%;border-radius:var(--kbq-dropdown-item-border-radius);-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;position:relative;display:flex;flex-direction:row;align-items:center;box-sizing:border-box;outline:none;-webkit-tap-highlight-color:transparent;min-height:32px;gap:var(--kbq-size-s);border:var(--kbq-size-3xs) solid transparent;padding:var(--kbq-size-xxs) calc(var(--kbq-size-m) - var(--kbq-size-3xs))}.kbq-dropdown-item .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown-item .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown-item .kbq-list-text:empty{display:none}.kbq-dropdown-item .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown-item .kbq-list-option-caption{padding-top:var(--kbq-size-3xs)}.kbq-dropdown-item:not(.kbq-disabled){cursor:pointer}.kbq-dropdown-item{text-align:left;align-items:flex-start;text-decoration:none}.kbq-dropdown-item>.kbq-icon:first-child:before,.kbq-dropdown-item>.kbq-icon:first-child>svg{align-self:center;display:flex;height:var(--kbq-size-xl);width:16px;align-items:center}.kbq-dropdown-item .kbq-dropdown-item__caption{padding-top:var(--kbq-size-3xs)}.kbq-dropdown-item__text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown-item__text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown-item__text:empty{display:none}.kbq-dropdown-item__text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown-item-overlay{position:absolute;inset:-1px;border-radius:inherit}.kbq-dropdown-item_has-action{align-items:center}.kbq-dropdown-item_has-action>.kbq-dropdown-item__action{position:relative;z-index:1;flex:0 0 auto}.kbq-dropdown-item.kbq-progress .kbq-dropdown-item-overlay{content:\"\";position:absolute;border-radius:inherit;inset:0;background:linear-gradient(135deg,#0000000a 12px,#ffffff1a 12px 22px,#0000000a 22px 34px,#ffffff1a 34px) repeat;background-size:32px 32px;animation:kbq-progress 1s linear infinite;inset:calc(-1 * var(--kbq-size-3xs))}@media(prefers-reduced-motion:reduce){.kbq-dropdown-item.kbq-progress .kbq-dropdown-item-overlay{animation:none}}.kbq-dropdown__group-header{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;display:flex;flex-direction:row;align-items:center;box-sizing:border-box;min-height:32px;border-left:var(--kbq-size-3xs) solid transparent;border-right:var(--kbq-size-3xs) solid transparent;padding-top:var(--kbq-size-xs);padding-left:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-right:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-bottom:var(--kbq-size-3xs)}.kbq-dropdown__group-header .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown__group-header .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown__group-header .kbq-list-text:empty{display:none}.kbq-dropdown__group-header .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{display:flex;flex-direction:row;align-items:center;box-sizing:border-box;min-height:32px;border-left:var(--kbq-size-3xs) solid transparent;border-right:var(--kbq-size-3xs) solid transparent;padding-top:var(--kbq-size-m);padding-left:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-right:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-bottom:var(--kbq-size-xxs)}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text:empty{display:none}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}\n"], dependencies: [{ kind: "component", type: KbqIcon, selector: "[kbq-icon]", inputs: ["small", "autoColor", "kbq-icon"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
267
418
  }
268
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownItem, decorators: [{
419
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownItem, decorators: [{
269
420
  type: Component,
270
421
  args: [{ selector: 'kbq-dropdown-item, [kbq-dropdown-item]', imports: [
271
422
  KbqIcon
272
423
  ], providers: [
273
- { provide: KBQ_TITLE_TEXT_REF, useExisting: KbqDropdownItem }
424
+ { provide: KBQ_TITLE_TEXT_REF, useExisting: KbqDropdownItem },
425
+ { provide: KBQ_DROPDOWN_ITEM_ACTION_HOST, useExisting: KbqDropdownItem }
274
426
  ], changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.None, host: {
275
427
  class: 'kbq-dropdown-item',
276
428
  '[class.kbq-dropdown-item_with-icon]': 'icon',
277
429
  '[class.kbq-dropdown-item_highlighted]': 'highlighted',
430
+ '[class.kbq-dropdown-item_active]': 'active()',
278
431
  '[class.kbq-disabled]': 'disabled',
432
+ '[class.kbq-progress]': 'progress()',
433
+ '[class.kbq-dropdown-item_has-action]': '!!itemAction()',
279
434
  '[attr.disabled]': 'disabled || null',
280
435
  '[attr.tabindex]': 'getTabIndex()',
281
436
  '(click)': 'checkDisabled($event)',
282
- '(mouseenter)': 'handleMouseEnter()'
283
- }, exportAs: 'kbqDropdownItem', template: "<ng-content select=\"[kbq-icon]\" />\n\n<div #kbqTitleText class=\"kbq-dropdown-item__text\">\n <ng-content />\n</div>\n\n@if (isNested) {\n <i kbq-icon=\"kbq-chevron-right-s_16\" class=\"kbq-dropdown-trigger__icon\" [color]=\"componentColors.ContrastFade\"></i>\n}\n\n<div class=\"kbq-dropdown-item-overlay\" (click)=\"haltDisabledEvents($event)\"></div>\n", styles: [".kbq-truncate-line{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-no-select{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.kbq-dropdown-item{width:100%;border-radius:var(--kbq-dropdown-item-border-radius);-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;position:relative;display:flex;flex-direction:row;align-items:center;box-sizing:border-box;outline:none;-webkit-tap-highlight-color:transparent;min-height:32px;gap:var(--kbq-size-s);border:var(--kbq-size-3xs) solid transparent;padding:var(--kbq-size-xxs) calc(var(--kbq-size-m) - var(--kbq-size-3xs))}.kbq-dropdown-item .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown-item .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown-item .kbq-list-text:empty{display:none}.kbq-dropdown-item .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown-item .kbq-list-option-caption{padding-top:var(--kbq-size-3xs)}.kbq-dropdown-item:not(.kbq-disabled){cursor:pointer}.kbq-dropdown-item{text-align:left;align-items:flex-start;text-decoration:none}.kbq-dropdown-item>.kbq-icon:first-child:before,.kbq-dropdown-item>.kbq-icon:first-child>svg{align-self:center;display:flex;height:var(--kbq-size-xl);width:16px;align-items:center}.kbq-dropdown-item .kbq-dropdown-item__caption{padding-top:var(--kbq-size-3xs)}.kbq-dropdown-item__text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown-item__text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown-item__text:empty{display:none}.kbq-dropdown-item__text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown-item-overlay{position:absolute;inset:-1px;border-radius:inherit}.kbq-dropdown__group-header{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;display:flex;flex-direction:row;align-items:center;box-sizing:border-box;min-height:32px;border-left:var(--kbq-size-3xs) solid transparent;border-right:var(--kbq-size-3xs) solid transparent;padding-top:var(--kbq-size-xs);padding-left:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-right:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-bottom:var(--kbq-size-3xs)}.kbq-dropdown__group-header .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown__group-header .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown__group-header .kbq-list-text:empty{display:none}.kbq-dropdown__group-header .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{display:flex;flex-direction:row;align-items:center;box-sizing:border-box;min-height:32px;border-left:var(--kbq-size-3xs) solid transparent;border-right:var(--kbq-size-3xs) solid transparent;padding-top:var(--kbq-size-m);padding-left:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-right:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-bottom:var(--kbq-size-xxs)}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text:empty{display:none}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}\n"] }]
284
- }], propDecorators: { textElement: [{
437
+ '(mouseenter)': 'handleMouseEnter()',
438
+ '(keydown)': 'handleActionKeydown($event)'
439
+ }, exportAs: 'kbqDropdownItem', template: "<ng-content select=\"[kbq-icon]\" />\n\n<div #kbqTitleText class=\"kbq-dropdown-item__text\">\n <ng-content />\n</div>\n\n<ng-content select=\"[kbqDropdownItemAction]\" />\n\n@if (isNested) {\n <i kbq-icon=\"kbq-chevron-right-s_16\" class=\"kbq-dropdown-trigger__icon\" [color]=\"componentColors.ContrastFade\"></i>\n}\n\n<div class=\"kbq-dropdown-item-overlay\" (click)=\"haltDisabledEvents($event)\"></div>\n", styles: ["@keyframes kbq-progress{0%{background-position:0 0}to{background-position:64px 0}}.kbq-progress{position:relative}.kbq-progress:after{content:\"\";position:absolute;border-radius:inherit;inset:0;background:linear-gradient(135deg,#0000000a 12px,#ffffff1a 12px 22px,#0000000a 22px 34px,#ffffff1a 34px) repeat;background-size:32px 32px;animation:kbq-progress 1s linear infinite}@media(prefers-reduced-motion:reduce){.kbq-progress:after{animation:none}}.kbq-truncate-line{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-no-select{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.kbq-dropdown-item{width:100%;border-radius:var(--kbq-dropdown-item-border-radius);-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;position:relative;display:flex;flex-direction:row;align-items:center;box-sizing:border-box;outline:none;-webkit-tap-highlight-color:transparent;min-height:32px;gap:var(--kbq-size-s);border:var(--kbq-size-3xs) solid transparent;padding:var(--kbq-size-xxs) calc(var(--kbq-size-m) - var(--kbq-size-3xs))}.kbq-dropdown-item .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown-item .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown-item .kbq-list-text:empty{display:none}.kbq-dropdown-item .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown-item .kbq-list-option-caption{padding-top:var(--kbq-size-3xs)}.kbq-dropdown-item:not(.kbq-disabled){cursor:pointer}.kbq-dropdown-item{text-align:left;align-items:flex-start;text-decoration:none}.kbq-dropdown-item>.kbq-icon:first-child:before,.kbq-dropdown-item>.kbq-icon:first-child>svg{align-self:center;display:flex;height:var(--kbq-size-xl);width:16px;align-items:center}.kbq-dropdown-item .kbq-dropdown-item__caption{padding-top:var(--kbq-size-3xs)}.kbq-dropdown-item__text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown-item__text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown-item__text:empty{display:none}.kbq-dropdown-item__text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown-item-overlay{position:absolute;inset:-1px;border-radius:inherit}.kbq-dropdown-item_has-action{align-items:center}.kbq-dropdown-item_has-action>.kbq-dropdown-item__action{position:relative;z-index:1;flex:0 0 auto}.kbq-dropdown-item.kbq-progress .kbq-dropdown-item-overlay{content:\"\";position:absolute;border-radius:inherit;inset:0;background:linear-gradient(135deg,#0000000a 12px,#ffffff1a 12px 22px,#0000000a 22px 34px,#ffffff1a 34px) repeat;background-size:32px 32px;animation:kbq-progress 1s linear infinite;inset:calc(-1 * var(--kbq-size-3xs))}@media(prefers-reduced-motion:reduce){.kbq-dropdown-item.kbq-progress .kbq-dropdown-item-overlay{animation:none}}.kbq-dropdown__group-header{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;display:flex;flex-direction:row;align-items:center;box-sizing:border-box;min-height:32px;border-left:var(--kbq-size-3xs) solid transparent;border-right:var(--kbq-size-3xs) solid transparent;padding-top:var(--kbq-size-xs);padding-left:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-right:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-bottom:var(--kbq-size-3xs)}.kbq-dropdown__group-header .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown__group-header .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown__group-header .kbq-list-text:empty{display:none}.kbq-dropdown__group-header .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{display:flex;flex-direction:row;align-items:center;box-sizing:border-box;min-height:32px;border-left:var(--kbq-size-3xs) solid transparent;border-right:var(--kbq-size-3xs) solid transparent;padding-top:var(--kbq-size-m);padding-left:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-right:calc(var(--kbq-size-m) - var(--kbq-size-3xs));padding-bottom:var(--kbq-size-xxs)}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text>*{margin:0;padding:0;font-weight:400;font-size:inherit}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text{display:flex;flex-direction:column;width:100%;box-sizing:content-box;overflow:hidden}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text:empty{display:none}.kbq-dropdown__group-header.kbq-dropdown__group-header_small .kbq-list-text{display:inline-block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}\n"] }]
440
+ }], ctorParameters: () => [], propDecorators: { textElement: [{
285
441
  type: ViewChild,
286
- args: ['kbqTitleText', { static: true }]
442
+ args: ['kbqTitleText']
287
443
  }], icon: [{
288
444
  type: ContentChild,
289
445
  args: [KbqIcon]
290
- }], disabled: [{
446
+ }], itemAction: [{ type: i0.ContentChild, args: [i0.forwardRef(() => KbqDropdownItemAction), { isSignal: true }] }], disabled: [{
291
447
  type: Input,
292
448
  args: [{ transform: booleanAttribute }]
293
- }] } });
449
+ }], progress: [{ type: i0.Input, args: [{ isSignal: true, alias: "progress", required: false }] }] } });
294
450
 
451
+ /**
452
+ * Marks a `kbq-form-field` projected into a `kbq-dropdown` as the panel's search field.
453
+ *
454
+ * The panel keeps DOM focus in the field, so arrow keys move the highlighted item while the query
455
+ * stays editable.
456
+ */
457
+ class KbqDropdownSearch {
458
+ constructor() {
459
+ this.formField = inject(KBQ_FORM_FIELD);
460
+ /**
461
+ * Panel this field searches. A nested panel declared inside its parent's content shares the view with
462
+ * it, so the parent has to be able to tell which of the projected fields is its own.
463
+ * @docs-private
464
+ */
465
+ this.panel = inject(KBQ_DROPDOWN_PANEL, { optional: true });
466
+ }
467
+ /** The form control the query is bound to. */
468
+ get ngControl() {
469
+ return this.formField.control().ngControl;
470
+ }
471
+ ngAfterContentInit() {
472
+ if (this.formField.control().controlType !== 'input') {
473
+ throwKbqDropdownSearchMissingInputError();
474
+ }
475
+ if (!this.ngControl) {
476
+ throwKbqDropdownSearchMissingNgControlError();
477
+ }
478
+ }
479
+ /** Focuses the search field. */
480
+ focus() {
481
+ this.formField.focus();
482
+ }
483
+ /** Clears the search query. */
484
+ reset() {
485
+ this.ngControl?.reset();
486
+ }
487
+ /** The current search query. */
488
+ value() {
489
+ return this.formField.control().value;
490
+ }
491
+ /** @docs-private */
492
+ handleClick(event) {
493
+ event.stopPropagation();
494
+ }
495
+ /** @docs-private */
496
+ handleKeydown(event) {
497
+ // The panel owns ESCAPE: the first press clears the query, the second closes the dropdown. This
498
+ // handler runs before the cleaner's own listener on the same element, so the field is already
499
+ // empty by the time the cleaner looks at the key.
500
+ if (event.keyCode === ESCAPE && this.value()) {
501
+ this.reset();
502
+ event.stopPropagation();
503
+ return;
504
+ }
505
+ // A nested panel closes on the horizontal arrow that points back at its trigger, so the key is
506
+ // only kept while the caret still has somewhere to go — the top-level panel ignores it anyway.
507
+ if (this.movesCaret(event)) {
508
+ event.stopPropagation();
509
+ }
510
+ }
511
+ /** Whether the key still has caret to travel inside the field, rather than acting on the panel. */
512
+ movesCaret(event) {
513
+ const { keyCode, target } = event;
514
+ if (keyCode !== LEFT_ARROW && keyCode !== RIGHT_ARROW)
515
+ return false;
516
+ // The keydown starts on the input and bubbles to this host, so the target is the field itself.
517
+ const { selectionStart, selectionEnd, value } = target;
518
+ if (selectionStart === null || selectionEnd === null)
519
+ return true;
520
+ const edge = keyCode === LEFT_ARROW ? 0 : value.length;
521
+ return selectionStart !== edge || selectionEnd !== edge;
522
+ }
523
+ /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownSearch, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
524
+ /** @nocollapse */ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.30", type: KbqDropdownSearch, isStandalone: true, selector: "[kbqDropdownSearch]", host: { listeners: { "click": "handleClick($event)", "keydown": "handleKeydown($event)" } }, providers: [
525
+ {
526
+ // Merged, not replaced: the field still inherits whatever defaults the app configures.
527
+ provide: KBQ_FORM_FIELD_DEFAULT_OPTIONS,
528
+ useFactory: (() => ({
529
+ ...inject(KBQ_FORM_FIELD_DEFAULT_OPTIONS, { optional: true, skipSelf: true }),
530
+ noBorders: true,
531
+ inOverlay: true
532
+ }))
533
+ }
534
+ ], exportAs: ["kbqDropdownSearch"], ngImport: i0 }); }
535
+ }
536
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownSearch, decorators: [{
537
+ type: Directive,
538
+ args: [{
539
+ selector: '[kbqDropdownSearch]',
540
+ providers: [
541
+ {
542
+ // Merged, not replaced: the field still inherits whatever defaults the app configures.
543
+ provide: KBQ_FORM_FIELD_DEFAULT_OPTIONS,
544
+ useFactory: (() => ({
545
+ ...inject(KBQ_FORM_FIELD_DEFAULT_OPTIONS, { optional: true, skipSelf: true }),
546
+ noBorders: true,
547
+ inOverlay: true
548
+ }))
549
+ }
550
+ ],
551
+ host: {
552
+ '(click)': 'handleClick($event)',
553
+ '(keydown)': 'handleKeydown($event)'
554
+ },
555
+ exportAs: 'kbqDropdownSearch'
556
+ }]
557
+ }] });
558
+
559
+ /** Options for binding a passive event listener. */
560
+ const passiveEventListenerOptions$1 = normalizePassiveListenerOptions({ passive: true });
561
+ /**
562
+ * Grace period before switching to a different nested trigger hovered while a safe area is
563
+ * protecting the currently open submenu. Without it, sweeping the pointer down a long list of
564
+ * nested triggers on the way to the submenu would flicker each row's submenu open and closed.
565
+ */
566
+ const NESTED_HOVER_SWITCH_DELAY = 50;
567
+ /** Class applied to the panel while its safe area is protecting an open submenu, see `activateSafeArea`. */
568
+ const SAFE_AREA_ACTIVE_CLASS = 'kbq-dropdown__panel_safe-area-active';
295
569
  class KbqDropdownStaticContent {
296
- /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownStaticContent, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
297
- /** @nocollapse */ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.25", type: KbqDropdownStaticContent, isStandalone: true, selector: "[kbqDropdownStaticContent]", ngImport: i0 }); }
570
+ /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownStaticContent, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
571
+ /** @nocollapse */ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.30", type: KbqDropdownStaticContent, isStandalone: true, selector: "[kbqDropdownStaticContent]", ngImport: i0 }); }
298
572
  }
299
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownStaticContent, decorators: [{
573
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownStaticContent, decorators: [{
300
574
  type: Directive,
301
575
  args: [{
302
576
  selector: '[kbqDropdownStaticContent]'
303
577
  }]
304
578
  }] });
579
+ /** Footer that is rendered below the dropdown options panel. */
580
+ class KbqDropdownFooter {
581
+ /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownFooter, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
582
+ /** @nocollapse */ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.30", type: KbqDropdownFooter, isStandalone: true, selector: "[kbqDropdownFooter], kbq-dropdown-footer", host: { classAttribute: "kbq-dropdown-footer" }, ngImport: i0 }); }
583
+ }
584
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownFooter, decorators: [{
585
+ type: Directive,
586
+ args: [{
587
+ selector: '[kbqDropdownFooter], kbq-dropdown-footer',
588
+ host: { class: 'kbq-dropdown-footer' }
589
+ }]
590
+ }] });
305
591
  class KbqDropdown {
306
- constructor() {
307
- this.elementRef = inject(ElementRef);
308
- this.ngZone = inject(NgZone);
309
- this.defaultOptions = inject(KBQ_DROPDOWN_DEFAULT_OPTIONS);
310
- this.search = contentChild(KbqFormField, ...(ngDevMode ? [{ debugName: "search" }] : []));
311
- this.navigationWithWrap = input(false, ...(ngDevMode ? [{ debugName: "navigationWithWrap" }] : []));
312
- this._xPosition = this.defaultOptions.xPosition;
313
- this._yPosition = this.defaultOptions.yPosition;
314
- this._overlapTriggerX = this.defaultOptions.overlapTriggerX;
315
- this._overlapTriggerY = this.defaultOptions.overlapTriggerY;
316
- this._hasBackdrop = this.defaultOptions.hasBackdrop;
317
- /** Config object to be passed into the dropdown panel's `[class]` binding */
318
- this.classList = {};
319
- /** Current state of the panel animation. */
320
- this.panelAnimationState = 'void';
321
- /** Emits whenever an animation on the dropdown completes. */
322
- this.animationDone = new Subject();
323
- /** Class to be added to the backdrop element. */
324
- // TODO: Skipped for migration because:
325
- // This input overrides a field from a superclass, while the superclass field
326
- // is not migrated.
327
- this.backdropClass = this.defaultOptions.backdropClass;
328
- /** Event emitted when the dropdown is closed. */
329
- this.closed = new EventEmitter();
330
- /** Only the direct descendant menu items. */
331
- this.directDescendantItems = new QueryList();
332
- /** Subscription to tab events on the dropdown panel */
333
- this.tabSubscription = Subscription.EMPTY;
334
- }
335
592
  /** Position of the dropdown in the X axis. */
336
593
  // TODO: Skipped for migration because:
337
594
  // Accessor inputs cannot be migrated as they are too complex.
@@ -407,34 +664,258 @@ class KbqDropdown {
407
664
  // Reassign a new object reference so the native `[class]` binding picks up the change.
408
665
  this.classList = classList;
409
666
  }
667
+ constructor() {
668
+ this.elementRef = inject(ElementRef);
669
+ this.ngZone = inject(NgZone);
670
+ this.document = inject(DOCUMENT);
671
+ this.defaultOptions = inject(KBQ_DROPDOWN_DEFAULT_OPTIONS);
672
+ this.destroyRef = inject(DestroyRef);
673
+ this.panelFormField = contentChild(KbqFormField, ...(ngDevMode ? [{ debugName: "panelFormField" }] : []));
674
+ /**
675
+ * Signal content queries carry `descendants: true`, and a nested panel declared inside this one's
676
+ * content is part of the same view — so the match has to be narrowed to the fields this panel owns,
677
+ * the way `updateDirectDescendants` narrows the items.
678
+ */
679
+ this.searches = contentChildren(KbqDropdownSearch, ...(ngDevMode ? [{ debugName: "searches", descendants: true }] : [{ descendants: true }]));
680
+ this.search = computed(() => this.searches().find((search) => search.panel === this), ...(ngDevMode ? [{ debugName: "search" }] : []));
681
+ /** Whether the dropdown projects a search form-field. @docs-private */
682
+ this.hasSearch = computed(() => !!this.panelFormField(), ...(ngDevMode ? [{ debugName: "hasSearch" }] : []));
683
+ /** Whether the panel highlights the active item instead of focusing it. @docs-private */
684
+ this.inSearchMode = computed(() => !!this.search(), ...(ngDevMode ? [{ debugName: "inSearchMode" }] : []));
685
+ this.navigationWithWrap = input(false, ...(ngDevMode ? [{ debugName: "navigationWithWrap" }] : []));
686
+ this._xPosition = this.defaultOptions.xPosition;
687
+ this._yPosition = this.defaultOptions.yPosition;
688
+ this._overlapTriggerX = this.defaultOptions.overlapTriggerX;
689
+ this._overlapTriggerY = this.defaultOptions.overlapTriggerY;
690
+ this._hasBackdrop = this.defaultOptions.hasBackdrop;
691
+ /** Config object to be passed into the dropdown panel's `[class]` binding */
692
+ this.classList = {};
693
+ /** Current state of the panel animation. */
694
+ this.panelAnimationState = 'void';
695
+ /** Emits whenever an animation on the dropdown completes. */
696
+ this.animationDone = new Subject();
697
+ /** Class to be added to the backdrop element. */
698
+ // TODO: Skipped for migration because:
699
+ // This input overrides a field from a superclass, while the superclass field
700
+ // is not migrated.
701
+ this.backdropClass = this.defaultOptions.backdropClass;
702
+ /**
703
+ * Width of the panel. If set to `auto`, the panel will match the trigger width, but will never be
704
+ * narrower than `panelMinWidth`. If set to null, the panel will grow to match its content.
705
+ * Any other value is used as an exact width, and `panelMinWidth` is not applied.
706
+ */
707
+ this.panelWidth = input(this.defaultOptions.panelWidth ?? null, ...(ngDevMode ? [{ debugName: "panelWidth" }] : []));
708
+ /**
709
+ * Minimum width of the panel in pixels. The panel is never narrower than this, nor than its trigger.
710
+ */
711
+ this.panelMinWidth = input(this.defaultOptions.panelMinWidth === undefined
712
+ ? KBQ_PANEL_DEFAULT_MIN_WIDTH
713
+ : this.defaultOptions.panelMinWidth, ...(ngDevMode ? [{ debugName: "panelMinWidth", transform: numberAttribute }] : [{ transform: numberAttribute }]));
714
+ /**
715
+ * Maximum width of the panel in pixels. Caps how far the panel grows with its content — it never makes
716
+ * the panel narrower than the trigger, and never clamps an explicit `panelWidth`.
717
+ * When null, the `--kbq-dropdown-size-container-width-max` token applies.
718
+ */
719
+ this.panelMaxWidth = input(this.defaultOptions.panelMaxWidth === undefined ? null : this.defaultOptions.panelMaxWidth, ...(ngDevMode ? [{ debugName: "panelMaxWidth", transform: numberAttribute }] : [{ transform: numberAttribute }]));
720
+ /**
721
+ * Whether nested dropdowns opened from this dropdown's items use a "safe area": while the
722
+ * pointer moves from a trigger toward its open submenu, sibling items it crosses over on the way
723
+ * don't prematurely close the submenu.
724
+ */
725
+ this.safeArea = input(this.defaultOptions.safeArea ?? true, ...(ngDevMode ? [{ debugName: "safeArea", transform: booleanAttribute }] : [{ transform: booleanAttribute }]));
726
+ /**
727
+ * `panelMinWidth` rendered as a CSS length for the `--kbq-dropdown-size-container-width-min`
728
+ * token, so the panel's CSS `min-width` floor tracks the input — mirroring how `panelMaxWidth`
729
+ * drives `max-width`. Non-finite input (e.g. `null`) leaves the token's static default in place.
730
+ * @docs-private
731
+ */
732
+ this.panelMinWidthToken = computed(() => {
733
+ const minWidth = this.panelMinWidth();
734
+ return Number.isFinite(minWidth) ? `${minWidth}px` : null;
735
+ }, ...(ngDevMode ? [{ debugName: "panelMinWidthToken" }] : []));
736
+ /** Event emitted when the dropdown is closed. */
737
+ this.closed = new EventEmitter();
738
+ this.focusOrigin = 'program';
739
+ /** Only the direct descendant menu items. */
740
+ this.directDescendantItems = new QueryList();
741
+ /** Subscription to tab events on the dropdown panel */
742
+ this.tabSubscription = Subscription.EMPTY;
743
+ /** Cleans up the safe-area `mousemove` listener. `null` when no safe area is being tracked. */
744
+ this.safeAreaCleanup = null;
745
+ /** The nested trigger currently protected by the active safe area, if any. */
746
+ this.safeAreaOwner = null;
747
+ /**
748
+ * The most recently hovered item, tracked independently of the safe area so that leaving it
749
+ * straight onto a sibling's nested trigger can switch to it immediately instead of waiting for a
750
+ * `mouseenter` that already happened.
751
+ */
752
+ this.currentHovered = null;
753
+ /** Emits when the pointer reaches the panel the active safe area protects. */
754
+ this.panelReached = new Subject();
755
+ /** Emits the sibling trigger that should open once a forced switch has closed the current one. */
756
+ this.switchTarget = new Subject();
757
+ /** Watches for a forced switch to a sibling trigger while a safe area is active. */
758
+ this.switchTargetSubscription = Subscription.EMPTY;
759
+ // The search field can show up long after content init — rendered by `kbqDropdownContent` when
760
+ // the panel first opens, or revealed by a structural directive — so the key manager follows the
761
+ // mode instead of being decided once.
762
+ effect(() => {
763
+ const inSearchMode = this.inSearchMode();
764
+ if (!this.keyManager || this.keyManagerInstalledForSearch() === inSearchMode)
765
+ return;
766
+ this.initKeyManager();
767
+ // A flip while the panel is open leaves focus wherever the previous mode put it: on an item
768
+ // the new manager will not track, or on an input that is being destroyed. Hand it over the
769
+ // same way opening does, deferred so the write lands outside this change detection pass.
770
+ if (this.panelAnimationState === 'enter') {
771
+ this.ngZone.onStable.pipe(take(1)).subscribe(() => this.applyInitialFocus(this.focusOrigin));
772
+ }
773
+ });
774
+ }
410
775
  ngOnInit() {
411
776
  this.setPositionClasses();
412
777
  }
413
778
  ngAfterContentInit() {
414
779
  this.updateDirectDescendants();
415
- this.keyManager = new FocusKeyManager(this.directDescendantItems).withTypeAhead();
416
- if (this.navigationWithWrap()) {
417
- this.keyManager.withWrap();
418
- }
419
- this.tabSubscription = this.keyManager.tabOut.subscribe(() => this.closed.emit('tab'));
780
+ this.initKeyManager();
420
781
  // If a user manually (programmatically) focuses a menu item, we need to reflect that focus
421
782
  // change back to the key manager. Note that we don't need to unsubscribe here because focused
422
783
  // is internal and we know that it gets completed on destroy.
423
784
  this.directDescendantItems.changes
424
785
  .pipe(startWith(this.directDescendantItems), switchMap((items) => merge(...items.map((item) => item.focused))))
425
786
  .subscribe((focusedItem) => this.keyManager.updateActiveItem(focusedItem));
426
- this.search()?.inOverlay.set(true);
787
+ this.panelFormField()?.inOverlay.set(true);
788
+ // Driven by the item list rather than by the query, because consumers commonly debounce their
789
+ // own filtering. `delay(0)` keeps the write out of the pass that reported the new items.
790
+ this.directDescendantItems.changes
791
+ .pipe(filter(() => !!this.search()), delay(0), filter(() => this.isActiveItemStale()), takeUntilDestroyed(this.destroyRef))
792
+ .subscribe(() => {
793
+ // An item the highlight sat on is gone. With a query in the field the top result takes
794
+ // over, so that ENTER picks it; with the field cleared nothing is highlighted — but the
795
+ // stale instance still has to be dropped, or ENTER would replay a click on a detached
796
+ // element and the arrows would resume from its index.
797
+ if (this.search()?.value()) {
798
+ this.keyManager.setFirstItemActive();
799
+ }
800
+ else {
801
+ this.resetActiveItem();
802
+ }
803
+ });
804
+ // Internal and completes with the items on destroy, so no explicit unsubscribe is needed.
805
+ this.hovered().subscribe((item) => {
806
+ this.currentHovered = item;
807
+ // Hovering doesn't focus the item in search mode, so arrowing on has to resume from it.
808
+ // Disabled items are skipped, the same way the key manager skips them for the arrows.
809
+ if (this.inSearchMode() && !item.disabled) {
810
+ this.keyManager.setActiveItem(item);
811
+ }
812
+ });
427
813
  }
428
814
  ngOnDestroy() {
429
815
  this.directDescendantItems.destroy();
430
816
  this.tabSubscription.unsubscribe();
431
817
  this.closed.complete();
818
+ this.deactivateSafeArea();
819
+ this.panelReached.complete();
820
+ this.switchTarget.complete();
432
821
  }
433
822
  /** Stream that emits whenever the hovered dropdown item changes. */
434
823
  hovered() {
435
824
  const itemChanges = this.directDescendantItems.changes;
436
825
  return itemChanges.pipe(startWith(this.directDescendantItems), switchMap((items) => merge(...items.map((item) => item.hovered))));
437
826
  }
827
+ /**
828
+ * Tracks the pointer against `triangle` to protect `owner`'s open submenu, closing it via
829
+ * `onExit` if the pointer leaves the triangle without first reaching `panelRect`. Meanwhile, if a
830
+ * different nested trigger is hovered, `switchTarget()` emits it — immediately if it's outside
831
+ * the triangle, otherwise after a grace period (see `NESTED_HOVER_SWITCH_DELAY`). Replaces any
832
+ * safe area already being tracked.
833
+ * @docs-private
834
+ */
835
+ activateSafeArea(owner, triangle, panelRect, onExit) {
836
+ this.deactivateSafeArea();
837
+ this.safeAreaOwner = owner;
838
+ this.classList = { ...this.classList, [SAFE_AREA_ACTIVE_CLASS]: true };
839
+ this.safeAreaCleanup = this.ngZone.runOutsideAngular(() => {
840
+ const listener = (event) => {
841
+ const point = { x: event.clientX, y: event.clientY };
842
+ if (isPointInRect(point, panelRect)) {
843
+ this.panelReached.next();
844
+ this.deactivateSafeArea();
845
+ return;
846
+ }
847
+ if (!isPointInTriangle(point, triangle)) {
848
+ const switchTo = this.currentHovered?.isNested && this.currentHovered !== owner && !this.currentHovered.disabled
849
+ ? this.currentHovered
850
+ : null;
851
+ this.deactivateSafeArea();
852
+ this.ngZone.run(() => {
853
+ onExit();
854
+ if (switchTo) {
855
+ this.switchTarget.next(switchTo);
856
+ }
857
+ });
858
+ }
859
+ };
860
+ this.document.addEventListener('mousemove', listener, passiveEventListenerOptions$1);
861
+ return () => this.document.removeEventListener('mousemove', listener, passiveEventListenerOptions$1);
862
+ });
863
+ this.switchTargetSubscription = this.hovered()
864
+ .pipe(filter((active) => active.isNested && active !== owner && !active.disabled), switchMap((active) => timer(NESTED_HOVER_SWITCH_DELAY).pipe(map(() => active), takeUntil(this.panelReached))))
865
+ .subscribe((active) => {
866
+ this.deactivateSafeArea();
867
+ onExit();
868
+ this.switchTarget.next(active);
869
+ });
870
+ }
871
+ /**
872
+ * Stops tracking the current safe area, if any.
873
+ * @docs-private
874
+ */
875
+ deactivateSafeArea() {
876
+ this.safeAreaCleanup?.();
877
+ this.safeAreaCleanup = null;
878
+ this.safeAreaOwner = null;
879
+ this.switchTargetSubscription.unsubscribe();
880
+ this.switchTargetSubscription = Subscription.EMPTY;
881
+ if (this.classList[SAFE_AREA_ACTIVE_CLASS]) {
882
+ // The mousemove listener that can reach this runs outside the Angular zone, so re-enter it
883
+ // to make sure the `classList` update is picked up by change detection.
884
+ this.ngZone.run(() => {
885
+ this.classList = { ...this.classList, [SAFE_AREA_ACTIVE_CLASS]: false };
886
+ });
887
+ }
888
+ }
889
+ /**
890
+ * Whether a safe area is currently being tracked.
891
+ * @docs-private
892
+ */
893
+ isSafeAreaActive() {
894
+ return this.safeAreaCleanup !== null;
895
+ }
896
+ /**
897
+ * Whether `item` is the nested trigger currently protected by an active safe area.
898
+ * @docs-private
899
+ */
900
+ isSafeAreaOwner(item) {
901
+ return this.safeAreaOwner === item;
902
+ }
903
+ /**
904
+ * Stream that emits when the pointer reaches the panel the active safe area protects (as opposed
905
+ * to leaving the safe area, which closes the panel instead).
906
+ * @docs-private
907
+ */
908
+ onPanelReached() {
909
+ return this.panelReached.asObservable();
910
+ }
911
+ /**
912
+ * Stream that emits the sibling trigger that should open once a forced safe-area switch has
913
+ * closed the trigger it was protecting.
914
+ * @docs-private
915
+ */
916
+ onSwitchTarget() {
917
+ return this.switchTarget.asObservable();
918
+ }
438
919
  /** Handle a keyboard event from the dropdown, delegating to the appropriate action. */
439
920
  handleKeydown(event) {
440
921
  const keyCode = event.keyCode;
@@ -452,11 +933,29 @@ class KbqDropdown {
452
933
  this.closed.emit('keydown');
453
934
  }
454
935
  break;
936
+ case ENTER:
937
+ // The highlighted item never sees the key event itself, so replay it as a click and let
938
+ // consumer handlers and nested triggers behave exactly as they do for the mouse.
939
+ if (this.inSearchMode() && this.keyManager.activeItem) {
940
+ event.preventDefault();
941
+ // The click can close the dropdown synchronously, unregistering the overlay from the
942
+ // CDK keyboard dispatcher before this keydown reaches `body` — where it would be
943
+ // handed to whichever overlay was opened earlier.
944
+ event.stopPropagation();
945
+ this.keyManager.activeItem.getHostElement().click();
946
+ }
947
+ return;
455
948
  default:
949
+ // Only the vertical arrows move the highlight in search mode; every other key that the
950
+ // search field lets through would otherwise scroll the list back on each keystroke.
456
951
  if (keyCode === UP_ARROW || keyCode === DOWN_ARROW) {
457
- this.keyManager.setFocusOrigin('keyboard');
952
+ this.setFocusOrigin('keyboard');
953
+ this.keyManager.onKeydown(event);
954
+ this.revealActiveItem();
955
+ }
956
+ else {
957
+ this.keyManager.onKeydown(event);
458
958
  }
459
- this.keyManager.onKeydown(event);
460
959
  return;
461
960
  }
462
961
  // Don't allow the event to propagate if we've already handled it, or it may
@@ -464,7 +963,7 @@ class KbqDropdown {
464
963
  event.stopPropagation();
465
964
  }
466
965
  /**
467
- * Focus the first item in the dropdown.
966
+ * Applies the panel's initial focus, see `applyInitialFocus`.
468
967
  * @param origin Action from which the focus originated. Used to set the correct styling.
469
968
  */
470
969
  focusFirstItem(origin = 'program') {
@@ -477,28 +976,50 @@ class KbqDropdown {
477
976
  }
478
977
  }
479
978
  /**
480
- * Applies focus when the dropdown is opened. When opened by mouse or touch, the first item
481
- * should not be highlighted, so the panel itself is focused instead — keyboard events still
482
- * reach the panel and the first arrow key press will highlight the first item.
979
+ * Applies focus when the dropdown is opened.
980
+ *
981
+ * A projected search field takes the caret for every origin and keeps it: the first arrow key press
982
+ * only highlights an item. Without one, opening by mouse or touch focuses the panel rather than an
983
+ * item, so that nothing is highlighted while keyboard events still reach the panel; any other origin
984
+ * highlights the first item. A submenu of a search panel focuses nothing at all, so that hovering it
985
+ * does not pull the caret out of the query.
483
986
  */
484
987
  applyInitialFocus(origin) {
485
988
  // The origin should be set even when no item gets activated,
486
989
  // since `close` relies on it to emit the correct close reason.
487
- this.keyManager.setFocusOrigin(origin);
488
- if (origin === 'mouse' || origin === 'touch') {
990
+ this.setFocusOrigin(origin);
991
+ const search = this.search();
992
+ if (search) {
993
+ search.focus();
994
+ }
995
+ else if (this.parent?.inSearchMode?.()) {
996
+ return;
997
+ }
998
+ else if (origin === 'mouse' || origin === 'touch') {
489
999
  this.focusPanel();
490
1000
  }
491
1001
  else {
492
1002
  this.keyManager.setFirstItemActive();
493
1003
  }
494
1004
  }
1005
+ /**
1006
+ * Moves focus back into the projected search field, reporting whether there was one. A nested panel
1007
+ * restores focus through this instead of onto its trigger item, which would strand the caret outside
1008
+ * the query.
1009
+ * @docs-private
1010
+ */
1011
+ restoreFocus() {
1012
+ const search = this.search();
1013
+ search?.focus();
1014
+ return !!search;
1015
+ }
495
1016
  /** Moves DOM focus onto the dropdown panel so that keydown events keep being handled. */
496
1017
  focusPanel() {
497
1018
  // The panel is rendered into the overlay through a `TemplatePortal`, so it can't be
498
1019
  // queried with a `ViewChild`. If there are no rendered items, focus stays on the trigger,
499
1020
  // same as `setFirstItemActive` no-ops in that case.
500
1021
  const panel = this.directDescendantItems.first?.getHostElement().closest('.kbq-dropdown__panel');
501
- panel?.focus();
1022
+ panel?.focus({ preventScroll: true });
502
1023
  }
503
1024
  /**
504
1025
  * Resets the active item in the dropdown. This is used when the dropdown is opened, allowing
@@ -552,8 +1073,57 @@ class KbqDropdown {
552
1073
  }
553
1074
  }
554
1075
  close() {
555
- const focusOrigin = this.keyManager.getFocusOrigin() === 'keyboard' ? 'keydown' : 'click';
556
- this.closed.emit(focusOrigin);
1076
+ this.closed.emit(this.focusOrigin === 'keyboard' ? 'keydown' : 'click');
1077
+ }
1078
+ /**
1079
+ * With a search field the caret has to stay in the input, so the active item is only highlighted and
1080
+ * typeahead is left off — it would race the query the user is typing.
1081
+ */
1082
+ initKeyManager() {
1083
+ // The forked `ListKeyManager` subscribes to the item list in its constructor and has no teardown,
1084
+ // so a manager is built once per mode and kept — rebuilding on every switch would strand the
1085
+ // previous one, twice per open/close cycle with lazy content. The outgoing manager's highlight
1086
+ // has to go with it: the incoming one will never call `setInactiveStyles` on an item it does not
1087
+ // know about.
1088
+ if (this.keyManager) {
1089
+ this.resetActiveItem();
1090
+ }
1091
+ if (this.inSearchMode()) {
1092
+ this.activeDescendantKeyManager ??= this.configureKeyManager(new ActiveDescendantKeyManager(this.directDescendantItems));
1093
+ this.keyManager = this.activeDescendantKeyManager;
1094
+ }
1095
+ else {
1096
+ this.focusKeyManager ??= this.configureKeyManager(new FocusKeyManager(this.directDescendantItems).withTypeAhead());
1097
+ this.keyManager = this.focusKeyManager;
1098
+ }
1099
+ this.tabSubscription.unsubscribe();
1100
+ this.tabSubscription = this.keyManager.tabOut.subscribe(() => this.closed.emit('tab'));
1101
+ }
1102
+ /** Which mode the installed key manager serves; the wanted one is `inSearchMode()`. */
1103
+ keyManagerInstalledForSearch() {
1104
+ return this.keyManager === this.activeDescendantKeyManager;
1105
+ }
1106
+ configureKeyManager(keyManager) {
1107
+ return untracked(this.navigationWithWrap) ? keyManager.withWrap() : keyManager;
1108
+ }
1109
+ setFocusOrigin(origin) {
1110
+ this.focusOrigin = origin;
1111
+ if (this.keyManager instanceof FocusKeyManager) {
1112
+ this.keyManager.setFocusOrigin(origin);
1113
+ }
1114
+ }
1115
+ isActiveItemStale() {
1116
+ const activeItem = this.keyManager.activeItem;
1117
+ return !activeItem || !this.directDescendantItems.some((item) => item === activeItem);
1118
+ }
1119
+ /**
1120
+ * Reveals the highlighted item, which the browser only does on its own for real focus. Mirrors the
1121
+ * reveal `kbqFocusAndReveal` performs for focused elements.
1122
+ */
1123
+ revealActiveItem() {
1124
+ if (!this.inSearchMode())
1125
+ return;
1126
+ this.keyManager.activeItem?.getHostElement().scrollIntoView?.({ block: 'nearest', inline: 'nearest' });
557
1127
  }
558
1128
  /**
559
1129
  * Sets up a stream that will keep track of any newly-added menu items and will update the list
@@ -567,23 +1137,26 @@ class KbqDropdown {
567
1137
  this.directDescendantItems.notifyOnChanges();
568
1138
  });
569
1139
  }
570
- /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdown, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
571
- /** @nocollapse */ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.2.0", version: "20.3.25", type: KbqDropdown, isStandalone: true, selector: "kbq-dropdown", inputs: { navigationWithWrap: { classPropertyName: "navigationWithWrap", publicName: "navigationWithWrap", isSignal: true, isRequired: false, transformFunction: null }, xPosition: { classPropertyName: "xPosition", publicName: "xPosition", isSignal: false, isRequired: false, transformFunction: null }, yPosition: { classPropertyName: "yPosition", publicName: "yPosition", isSignal: false, isRequired: false, transformFunction: null }, overlapTriggerY: { classPropertyName: "overlapTriggerY", publicName: "overlapTriggerY", isSignal: false, isRequired: false, transformFunction: null }, overlapTriggerX: { classPropertyName: "overlapTriggerX", publicName: "overlapTriggerX", isSignal: false, isRequired: false, transformFunction: null }, hasBackdrop: { classPropertyName: "hasBackdrop", publicName: "hasBackdrop", isSignal: false, isRequired: false, transformFunction: null }, panelClass: { classPropertyName: "panelClass", publicName: "class", isSignal: false, isRequired: false, transformFunction: null }, backdropClass: { classPropertyName: "backdropClass", publicName: "backdropClass", isSignal: false, isRequired: false, transformFunction: null } }, outputs: { closed: "closed" }, providers: [
1140
+ /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdown, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
1141
+ /** @nocollapse */ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.2.0", version: "20.3.30", type: KbqDropdown, isStandalone: true, selector: "kbq-dropdown", inputs: { navigationWithWrap: { classPropertyName: "navigationWithWrap", publicName: "navigationWithWrap", isSignal: true, isRequired: false, transformFunction: null }, xPosition: { classPropertyName: "xPosition", publicName: "xPosition", isSignal: false, isRequired: false, transformFunction: null }, yPosition: { classPropertyName: "yPosition", publicName: "yPosition", isSignal: false, isRequired: false, transformFunction: null }, overlapTriggerY: { classPropertyName: "overlapTriggerY", publicName: "overlapTriggerY", isSignal: false, isRequired: false, transformFunction: null }, overlapTriggerX: { classPropertyName: "overlapTriggerX", publicName: "overlapTriggerX", isSignal: false, isRequired: false, transformFunction: null }, hasBackdrop: { classPropertyName: "hasBackdrop", publicName: "hasBackdrop", isSignal: false, isRequired: false, transformFunction: null }, panelClass: { classPropertyName: "panelClass", publicName: "class", isSignal: false, isRequired: false, transformFunction: null }, backdropClass: { classPropertyName: "backdropClass", publicName: "backdropClass", isSignal: false, isRequired: false, transformFunction: null }, panelWidth: { classPropertyName: "panelWidth", publicName: "panelWidth", isSignal: true, isRequired: false, transformFunction: null }, panelMinWidth: { classPropertyName: "panelMinWidth", publicName: "panelMinWidth", isSignal: true, isRequired: false, transformFunction: null }, panelMaxWidth: { classPropertyName: "panelMaxWidth", publicName: "panelMaxWidth", isSignal: true, isRequired: false, transformFunction: null }, safeArea: { classPropertyName: "safeArea", publicName: "safeArea", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { closed: "closed" }, host: { styleAttribute: "display: contents" }, providers: [
572
1142
  { provide: KBQ_DROPDOWN_PANEL, useExisting: KbqDropdown }
573
- ], queries: [{ propertyName: "search", first: true, predicate: KbqFormField, descendants: true, isSignal: true }, { propertyName: "lazyContent", first: true, predicate: KbqDropdownContent, descendants: true }, { propertyName: "items", predicate: KbqDropdownItem, descendants: true }], viewQueries: [{ propertyName: "templateRef", first: true, predicate: TemplateRef, descendants: true }], exportAs: ["kbqDropdown"], ngImport: i0, template: "<ng-template>\n <div\n tabindex=\"-1\"\n class=\"kbq-dropdown__panel\"\n [class.kbq-dropdown__panel_nested]=\"parent\"\n [class]=\"classList\"\n [@transformDropdown]=\"panelAnimationState\"\n (@transformDropdown.done)=\"onAnimationDone($event)\"\n (@transformDropdown.start)=\"onAnimationStart($event)\"\n (click)=\"close()\"\n (keydown)=\"handleKeydown($event)\"\n >\n <div class=\"kbq-dropdown__content\">\n <ng-content />\n </div>\n </div>\n</ng-template>\n\n<ng-content select=\"[kbqDropdownStaticContent]\" />\n", styles: [".kbq-dropdown-trigger.kbq-button{padding-left:calc(var(--kbq-dropdown-trigger-horizontal-padding, 10px) - var(--kbq-size-border-width));padding-right:calc(var(--kbq-dropdown-trigger-horizontal-padding, 10px) - var(--kbq-size-border-width))}.kbq-dropdown-trigger.kbq-button .kbq-icon_left{margin-right:var(--kbq-size-xs)}.kbq-dropdown-trigger.kbq-button .kbq-icon_right{margin-left:var(--kbq-size-3xs)}.kbq-dropdown-trigger.kbq-button-icon.kbq-button-icon_right.kbq-button-icon_left .kbq-icon_left{margin-right:0}.kbq-dropdown-trigger.kbq-button-icon.kbq-button-icon_right.kbq-button-icon_left .kbq-icon_right{margin-left:0}.kbq-dropdown-trigger__icon{margin-left:auto;align-self:center}.kbq-dropdown__panel{outline:none;overflow-x:hidden;overflow-y:auto;min-width:max(var(--kbq-dropdown-size-container-width-min),100%);max-width:var(--kbq-dropdown-size-container-width-max);border-radius:var(--kbq-dropdown-size-container-border-radius);box-sizing:border-box;padding:var(--kbq-size-xxs)}.kbq-dropdown__panel.ng-animating{pointer-events:none}.kbq-dropdown__panel .kbq-dropdown-item{position:relative}.kbq-dropdown__panel .kbq-dropdown-item:before,.kbq-dropdown__panel .kbq-dropdown-item:after{position:absolute;content:\"\";width:var(--kbq-size-xxs);height:calc(100% + var(--kbq-size-3xs) * 2)}.kbq-dropdown__panel .kbq-dropdown-item:before{right:calc(100% + var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item:after{left:calc(100% + var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item:before,.kbq-dropdown__panel .kbq-dropdown-item:after{top:calc(-1 * var(--kbq-size-3xs));bottom:calc(-1 * var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-divider{margin-left:calc(var(--kbq-size-xxs) * -1);margin-right:calc(var(--kbq-size-xxs) * -1)}.kbq-dropdown__content{display:flex;flex-direction:column}.kbq-dropdown__panel{box-shadow:var(--kbq-dropdown-container-shadow);background:var(--kbq-dropdown-container-background)}.kbq-dropdown-item{background:var(--kbq-list-default-container-background);color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-dropdown-item__caption{color:var(--kbq-dropdown-item-caption-color)}.kbq-dropdown-item.kbq-dropdown-item_highlighted,.kbq-dropdown-item.cdk-focused:not(.kbq-disabled){background:var(--kbq-list-states-hover-container-background);color:var(--kbq-list-states-hover-text-color)}.kbq-dropdown-item.kbq-dropdown-item_highlighted .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item),.kbq-dropdown-item.cdk-focused:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-hover-text-color)}.kbq-dropdown-item.kbq-selected{background:var(--kbq-list-states-selected-container-background);color:var(--kbq-list-states-selected-text-color)}.kbq-dropdown-item.kbq-selected .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-selected-text-color)}.kbq-dropdown-item.kbq-selected.cdk-focused:not(.kbq-disabled){background:var(--kbq-list-states-selected-hover-container-background);color:var(--kbq-list-states-selected-hover-text-color)}.kbq-dropdown-item.kbq-selected.cdk-focused:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-selected-hover-text-color)}.kbq-dropdown-item.kbq-disabled{background:var(--kbq-list-states-disabled-container-background);color:var(--kbq-list-states-disabled-text-color)}.kbq-dropdown-item.kbq-disabled .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-disabled-text-color)}.kbq-dropdown-item:is(.kbq-selected,.cdk-focused):has(+:is(.kbq-selected,.cdk-focused)){border-bottom-left-radius:0;border-bottom-right-radius:0}.kbq-dropdown-item:is(.kbq-selected,.cdk-focused)+:is(.kbq-selected,.cdk-focused){border-top-left-radius:0;border-top-right-radius:0}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{color:var(--kbq-foreground-contrast-secondary)}.kbq-dropdown-item-overlay{background:transparent}.kbq-dropdown-item,.kbq-dropdown__content{font-size:var(--kbq-typography-text-normal-font-size);font-style:var(--kbq-typography-text-normal-font-style);font-weight:var(--kbq-typography-text-normal-font-weight);line-height:var(--kbq-typography-text-normal-line-height);font-family:var(--kbq-typography-text-normal-font-family);text-transform:var(--kbq-typography-text-normal-text-transform);font-feature-settings:var(--kbq-typography-text-normal-font-feature-settings);letter-spacing:var(--kbq-typography-text-normal-letter-spacing)}.kbq-dropdown-item .kbq-dropdown-item__caption,.kbq-dropdown__content .kbq-dropdown-item__caption{font-size:var(--kbq-typography-text-compact-font-size);font-style:var(--kbq-typography-text-compact-font-style);font-weight:var(--kbq-typography-text-compact-font-weight);line-height:var(--kbq-typography-text-compact-line-height);font-family:var(--kbq-typography-text-compact-font-family);text-transform:var(--kbq-typography-text-compact-text-transform);font-feature-settings:var(--kbq-typography-text-compact-font-feature-settings);letter-spacing:var(--kbq-typography-text-compact-letter-spacing)}.kbq-dropdown__group-header{font-size:var(--kbq-typography-big-strong-font-size);font-style:var(--kbq-typography-big-strong-font-style);font-weight:var(--kbq-typography-big-strong-font-weight);line-height:var(--kbq-typography-big-strong-line-height);font-family:var(--kbq-typography-big-strong-font-family);text-transform:var(--kbq-typography-big-strong-text-transform);font-feature-settings:var(--kbq-typography-big-strong-font-feature-settings);letter-spacing:var(--kbq-typography-big-strong-letter-spacing)}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{font-size:var(--kbq-typography-caps-compact-strong-font-size);font-style:var(--kbq-typography-caps-compact-strong-font-style);font-weight:var(--kbq-typography-caps-compact-strong-font-weight);line-height:var(--kbq-typography-caps-compact-strong-line-height);font-family:var(--kbq-typography-caps-compact-strong-font-family);text-transform:var(--kbq-typography-caps-compact-strong-text-transform);font-feature-settings:var(--kbq-typography-caps-compact-strong-font-feature-settings);letter-spacing:var(--kbq-typography-caps-compact-strong-letter-spacing)}\n", ".kbq-list,.kbq-list-selection{--kbq-list-size-container-padding-left: var(--kbq-size-m);--kbq-list-size-container-padding-right: var(--kbq-size-m);--kbq-list-size-container-padding-vertical: var(--kbq-size-xs);--kbq-list-size-container-content-gap-horizontal: var(--kbq-size-s);--kbq-list-size-container-content-gap-vertical: var(--kbq-size-3xs);--kbq-list-size-container-focus-outline-width: var(--kbq-size-3xs);--kbq-list-size-header-padding-top: var(--kbq-size-s);--kbq-list-size-header-padding-bottom: var(--kbq-size-xxs);--kbq-list-size-header-padding-horizontal: var(--kbq-size-m);--kbq-list-size-subheading-padding-top: var(--kbq-size-m);--kbq-list-size-subheading-padding-bottom: var(--kbq-size-xxs);--kbq-list-size-subheading-padding-horizontal: var(--kbq-size-m);--kbq-list-default-container-background: transparent;--kbq-list-default-text-color: var(--kbq-foreground-contrast);--kbq-list-default-icon-color: var(--kbq-icon-contrast);--kbq-list-default-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-default-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-hover-container-background: var(--kbq-states-background-transparent-hover);--kbq-list-states-active-container-background: var(--kbq-states-background-transparent-active);--kbq-list-states-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-container-background: var(--kbq-background-theme-less);--kbq-list-multiple-states-selected-container-background: var(--kbq-background-contrast-less);--kbq-list-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-hover-container-background: var(--kbq-states-background-theme-less-hover);--kbq-list-multiple-states-selected-hover-container-background: var(--kbq-states-background-contrast-less-hover);--kbq-list-states-selected-active-container-background: var(--kbq-states-background-theme-less-active);--kbq-list-multiple-states-selected-active-container-background: var(--kbq-states-background-contrast-less-active);--kbq-list-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-focused-focus-outline-color: var(--kbq-states-line-focus-theme);--kbq-list-states-disabled-container-background: transparent;--kbq-list-states-disabled-text-color: var(--kbq-states-foreground-disabled);--kbq-list-states-disabled-icon-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-icon-button-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-caption-color: var(--kbq-states-foreground-disabled)}.kbq-dropdown__panel{--kbq-dropdown-size-container-width-min: 200px;--kbq-dropdown-size-container-width-max: 640px;--kbq-dropdown-size-container-padding-vertical: var(--kbq-size-xxs);--kbq-dropdown-size-container-border-radius: var(--kbq-size-s);--kbq-dropdown-container-background: var(--kbq-background-card);--kbq-dropdown-container-shadow: var(--kbq-shadow-popup);--kbq-dropdown-item-border-radius: var(--kbq-size-xs);--kbq-dropdown-item-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-default-container-background: transparent;--kbq-list-default-text-color: var(--kbq-foreground-contrast);--kbq-list-default-icon-color: var(--kbq-icon-contrast);--kbq-list-default-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-default-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-hover-container-background: var(--kbq-states-background-transparent-hover);--kbq-list-states-active-container-background: var(--kbq-states-background-transparent-active);--kbq-list-states-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-container-background: var(--kbq-background-theme-less);--kbq-list-multiple-states-selected-container-background: var(--kbq-background-contrast-less);--kbq-list-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-hover-container-background: var(--kbq-states-background-theme-less-hover);--kbq-list-multiple-states-selected-hover-container-background: var(--kbq-states-background-contrast-less-hover);--kbq-list-states-selected-active-container-background: var(--kbq-states-background-theme-less-active);--kbq-list-multiple-states-selected-active-container-background: var(--kbq-states-background-contrast-less-active);--kbq-list-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-focused-focus-outline-color: var(--kbq-states-line-focus-theme);--kbq-list-states-disabled-container-background: transparent;--kbq-list-states-disabled-text-color: var(--kbq-states-foreground-disabled);--kbq-list-states-disabled-icon-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-icon-button-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-caption-color: var(--kbq-states-foreground-disabled)}\n"], animations: [
1143
+ ], queries: [{ propertyName: "panelFormField", first: true, predicate: KbqFormField, descendants: true, isSignal: true }, { propertyName: "searches", predicate: KbqDropdownSearch, descendants: true, isSignal: true }, { propertyName: "lazyContent", first: true, predicate: KbqDropdownContent, descendants: true }, { propertyName: "items", predicate: KbqDropdownItem, descendants: true }], viewQueries: [{ propertyName: "templateRef", first: true, predicate: TemplateRef, descendants: true }], exportAs: ["kbqDropdown"], ngImport: i0, template: "<ng-template>\n <div\n tabindex=\"-1\"\n class=\"kbq-dropdown__panel\"\n [class.kbq-dropdown__panel_nested]=\"parent\"\n [class]=\"classList\"\n [style.max-width.px]=\"panelMaxWidth()\"\n [style.--kbq-dropdown-size-container-width-min]=\"panelMinWidthToken()\"\n [@transformDropdown]=\"panelAnimationState\"\n (@transformDropdown.done)=\"onAnimationDone($event)\"\n (@transformDropdown.start)=\"onAnimationStart($event)\"\n (click)=\"close()\"\n (keydown)=\"handleKeydown($event)\"\n >\n <div class=\"kbq-dropdown__content\">\n <ng-content />\n </div>\n <ng-content select=\"[kbqDropdownFooter], kbq-dropdown-footer\" />\n </div>\n</ng-template>\n\n<ng-content select=\"[kbqDropdownStaticContent]\" />\n", styles: [".kbq-dropdown-footer{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;display:flex;align-items:center;box-sizing:border-box;min-height:40px;border-top-width:1px;border-top-style:solid;padding:var(--kbq-size-xxs) var(--kbq-size-l)}.kbq-dropdown-trigger.kbq-button{padding-left:calc(var(--kbq-dropdown-trigger-horizontal-padding, 10px) - var(--kbq-size-border-width));padding-right:calc(var(--kbq-dropdown-trigger-horizontal-padding, 10px) - var(--kbq-size-border-width))}.kbq-dropdown-trigger.kbq-button .kbq-icon_left{margin-right:var(--kbq-size-xs)}.kbq-dropdown-trigger.kbq-button .kbq-icon_right{margin-left:var(--kbq-size-3xs)}.kbq-dropdown-trigger.kbq-button-icon.kbq-button-icon_right.kbq-button-icon_left .kbq-icon_left{margin-right:0}.kbq-dropdown-trigger.kbq-button-icon.kbq-button-icon_right.kbq-button-icon_left .kbq-icon_right{margin-left:0}.kbq-dropdown-trigger__icon{margin-left:auto;align-self:center}.kbq-dropdown__panel{outline:none;overflow-x:hidden;overflow-y:auto;min-width:max(var(--kbq-dropdown-size-container-width-min),100%);max-width:var(--kbq-dropdown-size-container-width-max);border-radius:var(--kbq-dropdown-size-container-border-radius);box-sizing:border-box}.kbq-dropdown__panel.ng-animating{pointer-events:none}.kbq-dropdown__panel .kbq-dropdown-item{position:relative}.kbq-dropdown__panel .kbq-dropdown-item:before,.kbq-dropdown__panel .kbq-dropdown-item:after{position:absolute;content:\"\";width:var(--kbq-size-xxs);height:calc(100% + var(--kbq-size-3xs) * 2)}.kbq-dropdown__panel .kbq-dropdown-item:before{right:calc(100% + var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item:after{left:calc(100% + var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item:before,.kbq-dropdown__panel .kbq-dropdown-item:after{top:calc(-1 * var(--kbq-size-3xs));bottom:calc(-1 * var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item.kbq-progress:after{background:none;animation:none}.kbq-dropdown__panel .kbq-divider{margin-left:calc(var(--kbq-size-xxs) * -1);margin-right:calc(var(--kbq-size-xxs) * -1)}.kbq-dropdown__content{display:flex;flex-direction:column;padding:var(--kbq-size-xxs)}.kbq-dropdown-footer{border-color:var(--kbq-line-contrast-less)}.kbq-dropdown__panel{box-shadow:var(--kbq-dropdown-container-shadow);background:var(--kbq-dropdown-container-background)}.kbq-dropdown-item{background:var(--kbq-list-default-container-background);color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-dropdown-item__caption{color:var(--kbq-dropdown-item-caption-color)}.kbq-dropdown-item.kbq-dropdown-item_highlighted,.kbq-dropdown-item.kbq-dropdown-item_active:not(.kbq-disabled),.kbq-dropdown-item.cdk-focused:not(.kbq-disabled){background:var(--kbq-list-states-hover-container-background);color:var(--kbq-list-states-hover-text-color)}.kbq-dropdown-item.kbq-dropdown-item_highlighted .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item),.kbq-dropdown-item.kbq-dropdown-item_active:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item),.kbq-dropdown-item.cdk-focused:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-hover-text-color)}.kbq-dropdown-item .kbq-dropdown__panel_safe-area-active.cdk-focused:not(.kbq-dropdown-item_highlighted,.kbq-selected,.kbq-disabled){background:var(--kbq-list-default-container-background);color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-dropdown__panel_safe-area-active.cdk-focused:not(.kbq-dropdown-item_highlighted,.kbq-selected,.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-default-text-color)}.kbq-dropdown-item:active:not(.kbq-disabled),.kbq-dropdown-item.kbq-active:not(.kbq-disabled){background:var(--kbq-list-states-active-container-background)}.kbq-dropdown-item.kbq-selected{background:var(--kbq-list-states-selected-container-background);color:var(--kbq-list-states-selected-text-color)}.kbq-dropdown-item.kbq-selected .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-selected-text-color)}.kbq-dropdown-item.kbq-selected.kbq-dropdown-item_active:not(.kbq-disabled),.kbq-dropdown-item.kbq-selected.cdk-focused:not(.kbq-disabled){background:var(--kbq-list-states-selected-hover-container-background);color:var(--kbq-list-states-selected-hover-text-color)}.kbq-dropdown-item.kbq-selected.kbq-dropdown-item_active:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item),.kbq-dropdown-item.kbq-selected.cdk-focused:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-selected-hover-text-color)}.kbq-dropdown-item.kbq-selected:active:not(.kbq-disabled),.kbq-dropdown-item.kbq-selected.kbq-active:not(.kbq-disabled){background:var(--kbq-list-states-selected-active-container-background)}.kbq-dropdown-item.kbq-disabled{background:var(--kbq-list-states-disabled-container-background);color:var(--kbq-list-states-disabled-text-color)}.kbq-dropdown-item.kbq-disabled .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-disabled-text-color)}.kbq-dropdown-item:is(.kbq-selected,.cdk-focused,.kbq-dropdown-item_active):has(+:is(.kbq-selected,.cdk-focused,.kbq-dropdown-item_active)){border-bottom-left-radius:0;border-bottom-right-radius:0}.kbq-dropdown-item:is(.kbq-selected,.cdk-focused,.kbq-dropdown-item_active)+:is(.kbq-selected,.cdk-focused,.kbq-dropdown-item_active){border-top-left-radius:0;border-top-right-radius:0}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{color:var(--kbq-foreground-contrast-secondary)}.kbq-dropdown-item-overlay{background:transparent}.kbq-dropdown-item,.kbq-dropdown__content{font-size:var(--kbq-typography-text-normal-font-size);font-style:var(--kbq-typography-text-normal-font-style);font-weight:var(--kbq-typography-text-normal-font-weight);line-height:var(--kbq-typography-text-normal-line-height);font-family:var(--kbq-typography-text-normal-font-family);text-transform:var(--kbq-typography-text-normal-text-transform);font-feature-settings:var(--kbq-typography-text-normal-font-feature-settings);letter-spacing:var(--kbq-typography-text-normal-letter-spacing)}.kbq-dropdown-item .kbq-dropdown-item__caption,.kbq-dropdown__content .kbq-dropdown-item__caption{font-size:var(--kbq-typography-text-compact-font-size);font-style:var(--kbq-typography-text-compact-font-style);font-weight:var(--kbq-typography-text-compact-font-weight);line-height:var(--kbq-typography-text-compact-line-height);font-family:var(--kbq-typography-text-compact-font-family);text-transform:var(--kbq-typography-text-compact-text-transform);font-feature-settings:var(--kbq-typography-text-compact-font-feature-settings);letter-spacing:var(--kbq-typography-text-compact-letter-spacing)}.kbq-dropdown__group-header{font-size:var(--kbq-typography-big-strong-font-size);font-style:var(--kbq-typography-big-strong-font-style);font-weight:var(--kbq-typography-big-strong-font-weight);line-height:var(--kbq-typography-big-strong-line-height);font-family:var(--kbq-typography-big-strong-font-family);text-transform:var(--kbq-typography-big-strong-text-transform);font-feature-settings:var(--kbq-typography-big-strong-font-feature-settings);letter-spacing:var(--kbq-typography-big-strong-letter-spacing)}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{font-size:var(--kbq-typography-caps-compact-strong-font-size);font-style:var(--kbq-typography-caps-compact-strong-font-style);font-weight:var(--kbq-typography-caps-compact-strong-font-weight);line-height:var(--kbq-typography-caps-compact-strong-line-height);font-family:var(--kbq-typography-caps-compact-strong-font-family);text-transform:var(--kbq-typography-caps-compact-strong-text-transform);font-feature-settings:var(--kbq-typography-caps-compact-strong-font-feature-settings);letter-spacing:var(--kbq-typography-caps-compact-strong-letter-spacing)}\n", "@charset \"UTF-8\";.kbq-list,.kbq-list-selection,.kbq-list-option.cdk-drag-preview,.kbq-list-drag-preview_text{--kbq-list-size-container-padding-left: var(--kbq-size-m);--kbq-list-size-container-padding-right: var(--kbq-size-m);--kbq-list-size-container-padding-vertical: var(--kbq-size-xxs);--kbq-list-size-container-content-gap-horizontal: var(--kbq-size-s);--kbq-list-size-container-content-gap-vertical: var(--kbq-size-3xs);--kbq-list-size-container-focus-outline-width: var(--kbq-size-3xs);--kbq-list-default-container-background: transparent;--kbq-list-default-text-color: var(--kbq-foreground-contrast);--kbq-list-default-icon-color: var(--kbq-icon-contrast);--kbq-list-default-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-default-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-hover-container-background: var(--kbq-states-background-transparent-hover);--kbq-list-states-active-container-background: var(--kbq-states-background-transparent-active);--kbq-list-states-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-selected-container-background: var(--kbq-background-theme-less);--kbq-list-multiple-states-selected-container-background: var(--kbq-background-contrast-less);--kbq-list-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-multiple-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-multiple-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-multiple-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-multiple-states-selected-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-selected-hover-container-background: var(--kbq-states-background-theme-less-hover);--kbq-list-multiple-states-selected-hover-container-background: var(--kbq-states-background-contrast-less-hover);--kbq-list-states-selected-active-container-background: var(--kbq-states-background-theme-less-active);--kbq-list-multiple-states-selected-active-container-background: var(--kbq-states-background-contrast-less-active);--kbq-list-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-multiple-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-multiple-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-multiple-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-multiple-states-selected-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-focused-focus-outline-color: var(--kbq-states-line-focus-theme);--kbq-list-states-disabled-container-background: transparent;--kbq-list-states-disabled-text-color: var(--kbq-states-foreground-disabled);--kbq-list-states-disabled-icon-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-icon-button-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-caption-color: var(--kbq-states-foreground-disabled);--kbq-list-states-dragged-container-background: var(--kbq-background-card);--kbq-list-states-dragged-container-shadow: var(--kbq-shadow-popup)}.kbq-list-selection{--kbq-list-size-dragged-indicator-thickness: var(--kbq-size-3xs);--kbq-list-states-dragged-indicator-color: var(--kbq-line-theme)}.kbq-list-drag-preview_text{--kbq-list-size-drag-preview-max-width: 480px;--kbq-list-states-drag-preview-background: color-mix( in srgb, var(--kbq-background-card) calc(var(--kbq-opacity-overlay) * 100%), transparent )}.kbq-dropdown__panel{--kbq-dropdown-size-container-width-min: 200px;--kbq-dropdown-size-container-width-max: var(--kbq-panel-size-width-max, 640px);--kbq-dropdown-size-container-padding-vertical: var(--kbq-size-xxs);--kbq-dropdown-size-container-border-radius: var(--kbq-size-s);--kbq-dropdown-container-background: var(--kbq-background-card);--kbq-dropdown-container-shadow: var(--kbq-shadow-popup);--kbq-dropdown-item-border-radius: var(--kbq-size-xs);--kbq-dropdown-item-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-default-container-background: transparent;--kbq-list-default-text-color: var(--kbq-foreground-contrast);--kbq-list-default-icon-color: var(--kbq-icon-contrast);--kbq-list-default-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-default-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-hover-container-background: var(--kbq-states-background-transparent-hover);--kbq-list-states-active-container-background: var(--kbq-states-background-transparent-active);--kbq-list-states-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-selected-container-background: var(--kbq-background-theme-less);--kbq-list-multiple-states-selected-container-background: var(--kbq-background-contrast-less);--kbq-list-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-multiple-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-multiple-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-multiple-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-multiple-states-selected-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-selected-hover-container-background: var(--kbq-states-background-theme-less-hover);--kbq-list-multiple-states-selected-hover-container-background: var(--kbq-states-background-contrast-less-hover);--kbq-list-states-selected-active-container-background: var(--kbq-states-background-theme-less-active);--kbq-list-multiple-states-selected-active-container-background: var(--kbq-states-background-contrast-less-active);--kbq-list-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-multiple-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-multiple-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-multiple-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-multiple-states-selected-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-focused-focus-outline-color: var(--kbq-states-line-focus-theme);--kbq-list-states-disabled-container-background: transparent;--kbq-list-states-disabled-text-color: var(--kbq-states-foreground-disabled);--kbq-list-states-disabled-icon-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-icon-button-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-caption-color: var(--kbq-states-foreground-disabled);--kbq-list-states-dragged-container-background: var(--kbq-background-card);--kbq-list-states-dragged-container-shadow: var(--kbq-shadow-popup)}\n"], animations: [
574
1144
  kbqDropdownAnimations.transformDropdown,
575
1145
  kbqDropdownAnimations.fadeInItems
576
1146
  ], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
577
1147
  }
578
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdown, decorators: [{
1148
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdown, decorators: [{
579
1149
  type: Component,
580
1150
  args: [{ selector: 'kbq-dropdown', imports: [], providers: [
581
1151
  { provide: KBQ_DROPDOWN_PANEL, useExisting: KbqDropdown }
582
- ], changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.None, animations: [
1152
+ ], changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.None, host: {
1153
+ // Remove the TemplatePortal host box from layout while keeping kbqDropdownStaticContent in the document flow.
1154
+ style: 'display: contents'
1155
+ }, animations: [
583
1156
  kbqDropdownAnimations.transformDropdown,
584
1157
  kbqDropdownAnimations.fadeInItems
585
- ], exportAs: 'kbqDropdown', template: "<ng-template>\n <div\n tabindex=\"-1\"\n class=\"kbq-dropdown__panel\"\n [class.kbq-dropdown__panel_nested]=\"parent\"\n [class]=\"classList\"\n [@transformDropdown]=\"panelAnimationState\"\n (@transformDropdown.done)=\"onAnimationDone($event)\"\n (@transformDropdown.start)=\"onAnimationStart($event)\"\n (click)=\"close()\"\n (keydown)=\"handleKeydown($event)\"\n >\n <div class=\"kbq-dropdown__content\">\n <ng-content />\n </div>\n </div>\n</ng-template>\n\n<ng-content select=\"[kbqDropdownStaticContent]\" />\n", styles: [".kbq-dropdown-trigger.kbq-button{padding-left:calc(var(--kbq-dropdown-trigger-horizontal-padding, 10px) - var(--kbq-size-border-width));padding-right:calc(var(--kbq-dropdown-trigger-horizontal-padding, 10px) - var(--kbq-size-border-width))}.kbq-dropdown-trigger.kbq-button .kbq-icon_left{margin-right:var(--kbq-size-xs)}.kbq-dropdown-trigger.kbq-button .kbq-icon_right{margin-left:var(--kbq-size-3xs)}.kbq-dropdown-trigger.kbq-button-icon.kbq-button-icon_right.kbq-button-icon_left .kbq-icon_left{margin-right:0}.kbq-dropdown-trigger.kbq-button-icon.kbq-button-icon_right.kbq-button-icon_left .kbq-icon_right{margin-left:0}.kbq-dropdown-trigger__icon{margin-left:auto;align-self:center}.kbq-dropdown__panel{outline:none;overflow-x:hidden;overflow-y:auto;min-width:max(var(--kbq-dropdown-size-container-width-min),100%);max-width:var(--kbq-dropdown-size-container-width-max);border-radius:var(--kbq-dropdown-size-container-border-radius);box-sizing:border-box;padding:var(--kbq-size-xxs)}.kbq-dropdown__panel.ng-animating{pointer-events:none}.kbq-dropdown__panel .kbq-dropdown-item{position:relative}.kbq-dropdown__panel .kbq-dropdown-item:before,.kbq-dropdown__panel .kbq-dropdown-item:after{position:absolute;content:\"\";width:var(--kbq-size-xxs);height:calc(100% + var(--kbq-size-3xs) * 2)}.kbq-dropdown__panel .kbq-dropdown-item:before{right:calc(100% + var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item:after{left:calc(100% + var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item:before,.kbq-dropdown__panel .kbq-dropdown-item:after{top:calc(-1 * var(--kbq-size-3xs));bottom:calc(-1 * var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-divider{margin-left:calc(var(--kbq-size-xxs) * -1);margin-right:calc(var(--kbq-size-xxs) * -1)}.kbq-dropdown__content{display:flex;flex-direction:column}.kbq-dropdown__panel{box-shadow:var(--kbq-dropdown-container-shadow);background:var(--kbq-dropdown-container-background)}.kbq-dropdown-item{background:var(--kbq-list-default-container-background);color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-dropdown-item__caption{color:var(--kbq-dropdown-item-caption-color)}.kbq-dropdown-item.kbq-dropdown-item_highlighted,.kbq-dropdown-item.cdk-focused:not(.kbq-disabled){background:var(--kbq-list-states-hover-container-background);color:var(--kbq-list-states-hover-text-color)}.kbq-dropdown-item.kbq-dropdown-item_highlighted .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item),.kbq-dropdown-item.cdk-focused:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-hover-text-color)}.kbq-dropdown-item.kbq-selected{background:var(--kbq-list-states-selected-container-background);color:var(--kbq-list-states-selected-text-color)}.kbq-dropdown-item.kbq-selected .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-selected-text-color)}.kbq-dropdown-item.kbq-selected.cdk-focused:not(.kbq-disabled){background:var(--kbq-list-states-selected-hover-container-background);color:var(--kbq-list-states-selected-hover-text-color)}.kbq-dropdown-item.kbq-selected.cdk-focused:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-selected-hover-text-color)}.kbq-dropdown-item.kbq-disabled{background:var(--kbq-list-states-disabled-container-background);color:var(--kbq-list-states-disabled-text-color)}.kbq-dropdown-item.kbq-disabled .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-disabled-text-color)}.kbq-dropdown-item:is(.kbq-selected,.cdk-focused):has(+:is(.kbq-selected,.cdk-focused)){border-bottom-left-radius:0;border-bottom-right-radius:0}.kbq-dropdown-item:is(.kbq-selected,.cdk-focused)+:is(.kbq-selected,.cdk-focused){border-top-left-radius:0;border-top-right-radius:0}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{color:var(--kbq-foreground-contrast-secondary)}.kbq-dropdown-item-overlay{background:transparent}.kbq-dropdown-item,.kbq-dropdown__content{font-size:var(--kbq-typography-text-normal-font-size);font-style:var(--kbq-typography-text-normal-font-style);font-weight:var(--kbq-typography-text-normal-font-weight);line-height:var(--kbq-typography-text-normal-line-height);font-family:var(--kbq-typography-text-normal-font-family);text-transform:var(--kbq-typography-text-normal-text-transform);font-feature-settings:var(--kbq-typography-text-normal-font-feature-settings);letter-spacing:var(--kbq-typography-text-normal-letter-spacing)}.kbq-dropdown-item .kbq-dropdown-item__caption,.kbq-dropdown__content .kbq-dropdown-item__caption{font-size:var(--kbq-typography-text-compact-font-size);font-style:var(--kbq-typography-text-compact-font-style);font-weight:var(--kbq-typography-text-compact-font-weight);line-height:var(--kbq-typography-text-compact-line-height);font-family:var(--kbq-typography-text-compact-font-family);text-transform:var(--kbq-typography-text-compact-text-transform);font-feature-settings:var(--kbq-typography-text-compact-font-feature-settings);letter-spacing:var(--kbq-typography-text-compact-letter-spacing)}.kbq-dropdown__group-header{font-size:var(--kbq-typography-big-strong-font-size);font-style:var(--kbq-typography-big-strong-font-style);font-weight:var(--kbq-typography-big-strong-font-weight);line-height:var(--kbq-typography-big-strong-line-height);font-family:var(--kbq-typography-big-strong-font-family);text-transform:var(--kbq-typography-big-strong-text-transform);font-feature-settings:var(--kbq-typography-big-strong-font-feature-settings);letter-spacing:var(--kbq-typography-big-strong-letter-spacing)}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{font-size:var(--kbq-typography-caps-compact-strong-font-size);font-style:var(--kbq-typography-caps-compact-strong-font-style);font-weight:var(--kbq-typography-caps-compact-strong-font-weight);line-height:var(--kbq-typography-caps-compact-strong-line-height);font-family:var(--kbq-typography-caps-compact-strong-font-family);text-transform:var(--kbq-typography-caps-compact-strong-text-transform);font-feature-settings:var(--kbq-typography-caps-compact-strong-font-feature-settings);letter-spacing:var(--kbq-typography-caps-compact-strong-letter-spacing)}\n", ".kbq-list,.kbq-list-selection{--kbq-list-size-container-padding-left: var(--kbq-size-m);--kbq-list-size-container-padding-right: var(--kbq-size-m);--kbq-list-size-container-padding-vertical: var(--kbq-size-xs);--kbq-list-size-container-content-gap-horizontal: var(--kbq-size-s);--kbq-list-size-container-content-gap-vertical: var(--kbq-size-3xs);--kbq-list-size-container-focus-outline-width: var(--kbq-size-3xs);--kbq-list-size-header-padding-top: var(--kbq-size-s);--kbq-list-size-header-padding-bottom: var(--kbq-size-xxs);--kbq-list-size-header-padding-horizontal: var(--kbq-size-m);--kbq-list-size-subheading-padding-top: var(--kbq-size-m);--kbq-list-size-subheading-padding-bottom: var(--kbq-size-xxs);--kbq-list-size-subheading-padding-horizontal: var(--kbq-size-m);--kbq-list-default-container-background: transparent;--kbq-list-default-text-color: var(--kbq-foreground-contrast);--kbq-list-default-icon-color: var(--kbq-icon-contrast);--kbq-list-default-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-default-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-hover-container-background: var(--kbq-states-background-transparent-hover);--kbq-list-states-active-container-background: var(--kbq-states-background-transparent-active);--kbq-list-states-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-container-background: var(--kbq-background-theme-less);--kbq-list-multiple-states-selected-container-background: var(--kbq-background-contrast-less);--kbq-list-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-hover-container-background: var(--kbq-states-background-theme-less-hover);--kbq-list-multiple-states-selected-hover-container-background: var(--kbq-states-background-contrast-less-hover);--kbq-list-states-selected-active-container-background: var(--kbq-states-background-theme-less-active);--kbq-list-multiple-states-selected-active-container-background: var(--kbq-states-background-contrast-less-active);--kbq-list-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-focused-focus-outline-color: var(--kbq-states-line-focus-theme);--kbq-list-states-disabled-container-background: transparent;--kbq-list-states-disabled-text-color: var(--kbq-states-foreground-disabled);--kbq-list-states-disabled-icon-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-icon-button-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-caption-color: var(--kbq-states-foreground-disabled)}.kbq-dropdown__panel{--kbq-dropdown-size-container-width-min: 200px;--kbq-dropdown-size-container-width-max: 640px;--kbq-dropdown-size-container-padding-vertical: var(--kbq-size-xxs);--kbq-dropdown-size-container-border-radius: var(--kbq-size-s);--kbq-dropdown-container-background: var(--kbq-background-card);--kbq-dropdown-container-shadow: var(--kbq-shadow-popup);--kbq-dropdown-item-border-radius: var(--kbq-size-xs);--kbq-dropdown-item-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-default-container-background: transparent;--kbq-list-default-text-color: var(--kbq-foreground-contrast);--kbq-list-default-icon-color: var(--kbq-icon-contrast);--kbq-list-default-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-default-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-hover-container-background: var(--kbq-states-background-transparent-hover);--kbq-list-states-active-container-background: var(--kbq-states-background-transparent-active);--kbq-list-states-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-container-background: var(--kbq-background-theme-less);--kbq-list-multiple-states-selected-container-background: var(--kbq-background-contrast-less);--kbq-list-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-hover-container-background: var(--kbq-states-background-theme-less-hover);--kbq-list-multiple-states-selected-hover-container-background: var(--kbq-states-background-contrast-less-hover);--kbq-list-states-selected-active-container-background: var(--kbq-states-background-theme-less-active);--kbq-list-multiple-states-selected-active-container-background: var(--kbq-states-background-contrast-less-active);--kbq-list-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-focused-focus-outline-color: var(--kbq-states-line-focus-theme);--kbq-list-states-disabled-container-background: transparent;--kbq-list-states-disabled-text-color: var(--kbq-states-foreground-disabled);--kbq-list-states-disabled-icon-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-icon-button-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-caption-color: var(--kbq-states-foreground-disabled)}\n"] }]
586
- }], propDecorators: { search: [{ type: i0.ContentChild, args: [i0.forwardRef(() => KbqFormField), { isSignal: true }] }], navigationWithWrap: [{ type: i0.Input, args: [{ isSignal: true, alias: "navigationWithWrap", required: false }] }], xPosition: [{
1158
+ ], exportAs: 'kbqDropdown', template: "<ng-template>\n <div\n tabindex=\"-1\"\n class=\"kbq-dropdown__panel\"\n [class.kbq-dropdown__panel_nested]=\"parent\"\n [class]=\"classList\"\n [style.max-width.px]=\"panelMaxWidth()\"\n [style.--kbq-dropdown-size-container-width-min]=\"panelMinWidthToken()\"\n [@transformDropdown]=\"panelAnimationState\"\n (@transformDropdown.done)=\"onAnimationDone($event)\"\n (@transformDropdown.start)=\"onAnimationStart($event)\"\n (click)=\"close()\"\n (keydown)=\"handleKeydown($event)\"\n >\n <div class=\"kbq-dropdown__content\">\n <ng-content />\n </div>\n <ng-content select=\"[kbqDropdownFooter], kbq-dropdown-footer\" />\n </div>\n</ng-template>\n\n<ng-content select=\"[kbqDropdownStaticContent]\" />\n", styles: [".kbq-dropdown-footer{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;display:flex;align-items:center;box-sizing:border-box;min-height:40px;border-top-width:1px;border-top-style:solid;padding:var(--kbq-size-xxs) var(--kbq-size-l)}.kbq-dropdown-trigger.kbq-button{padding-left:calc(var(--kbq-dropdown-trigger-horizontal-padding, 10px) - var(--kbq-size-border-width));padding-right:calc(var(--kbq-dropdown-trigger-horizontal-padding, 10px) - var(--kbq-size-border-width))}.kbq-dropdown-trigger.kbq-button .kbq-icon_left{margin-right:var(--kbq-size-xs)}.kbq-dropdown-trigger.kbq-button .kbq-icon_right{margin-left:var(--kbq-size-3xs)}.kbq-dropdown-trigger.kbq-button-icon.kbq-button-icon_right.kbq-button-icon_left .kbq-icon_left{margin-right:0}.kbq-dropdown-trigger.kbq-button-icon.kbq-button-icon_right.kbq-button-icon_left .kbq-icon_right{margin-left:0}.kbq-dropdown-trigger__icon{margin-left:auto;align-self:center}.kbq-dropdown__panel{outline:none;overflow-x:hidden;overflow-y:auto;min-width:max(var(--kbq-dropdown-size-container-width-min),100%);max-width:var(--kbq-dropdown-size-container-width-max);border-radius:var(--kbq-dropdown-size-container-border-radius);box-sizing:border-box}.kbq-dropdown__panel.ng-animating{pointer-events:none}.kbq-dropdown__panel .kbq-dropdown-item{position:relative}.kbq-dropdown__panel .kbq-dropdown-item:before,.kbq-dropdown__panel .kbq-dropdown-item:after{position:absolute;content:\"\";width:var(--kbq-size-xxs);height:calc(100% + var(--kbq-size-3xs) * 2)}.kbq-dropdown__panel .kbq-dropdown-item:before{right:calc(100% + var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item:after{left:calc(100% + var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item:before,.kbq-dropdown__panel .kbq-dropdown-item:after{top:calc(-1 * var(--kbq-size-3xs));bottom:calc(-1 * var(--kbq-size-3xs))}.kbq-dropdown__panel .kbq-dropdown-item.kbq-progress:after{background:none;animation:none}.kbq-dropdown__panel .kbq-divider{margin-left:calc(var(--kbq-size-xxs) * -1);margin-right:calc(var(--kbq-size-xxs) * -1)}.kbq-dropdown__content{display:flex;flex-direction:column;padding:var(--kbq-size-xxs)}.kbq-dropdown-footer{border-color:var(--kbq-line-contrast-less)}.kbq-dropdown__panel{box-shadow:var(--kbq-dropdown-container-shadow);background:var(--kbq-dropdown-container-background)}.kbq-dropdown-item{background:var(--kbq-list-default-container-background);color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-dropdown-item__caption{color:var(--kbq-dropdown-item-caption-color)}.kbq-dropdown-item.kbq-dropdown-item_highlighted,.kbq-dropdown-item.kbq-dropdown-item_active:not(.kbq-disabled),.kbq-dropdown-item.cdk-focused:not(.kbq-disabled){background:var(--kbq-list-states-hover-container-background);color:var(--kbq-list-states-hover-text-color)}.kbq-dropdown-item.kbq-dropdown-item_highlighted .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item),.kbq-dropdown-item.kbq-dropdown-item_active:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item),.kbq-dropdown-item.cdk-focused:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-hover-text-color)}.kbq-dropdown-item .kbq-dropdown__panel_safe-area-active.cdk-focused:not(.kbq-dropdown-item_highlighted,.kbq-selected,.kbq-disabled){background:var(--kbq-list-default-container-background);color:var(--kbq-list-default-text-color)}.kbq-dropdown-item .kbq-dropdown__panel_safe-area-active.cdk-focused:not(.kbq-dropdown-item_highlighted,.kbq-selected,.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-default-text-color)}.kbq-dropdown-item:active:not(.kbq-disabled),.kbq-dropdown-item.kbq-active:not(.kbq-disabled){background:var(--kbq-list-states-active-container-background)}.kbq-dropdown-item.kbq-selected{background:var(--kbq-list-states-selected-container-background);color:var(--kbq-list-states-selected-text-color)}.kbq-dropdown-item.kbq-selected .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-selected-text-color)}.kbq-dropdown-item.kbq-selected.kbq-dropdown-item_active:not(.kbq-disabled),.kbq-dropdown-item.kbq-selected.cdk-focused:not(.kbq-disabled){background:var(--kbq-list-states-selected-hover-container-background);color:var(--kbq-list-states-selected-hover-text-color)}.kbq-dropdown-item.kbq-selected.kbq-dropdown-item_active:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item),.kbq-dropdown-item.kbq-selected.cdk-focused:not(.kbq-disabled) .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-selected-hover-text-color)}.kbq-dropdown-item.kbq-selected:active:not(.kbq-disabled),.kbq-dropdown-item.kbq-selected.kbq-active:not(.kbq-disabled){background:var(--kbq-list-states-selected-active-container-background)}.kbq-dropdown-item.kbq-disabled{background:var(--kbq-list-states-disabled-container-background);color:var(--kbq-list-states-disabled-text-color)}.kbq-dropdown-item.kbq-disabled .kbq-icon.kbq-empty:not(.kbq-icon-button,.kbq-icon-item){color:var(--kbq-list-states-disabled-text-color)}.kbq-dropdown-item:is(.kbq-selected,.cdk-focused,.kbq-dropdown-item_active):has(+:is(.kbq-selected,.cdk-focused,.kbq-dropdown-item_active)){border-bottom-left-radius:0;border-bottom-right-radius:0}.kbq-dropdown-item:is(.kbq-selected,.cdk-focused,.kbq-dropdown-item_active)+:is(.kbq-selected,.cdk-focused,.kbq-dropdown-item_active){border-top-left-radius:0;border-top-right-radius:0}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{color:var(--kbq-foreground-contrast-secondary)}.kbq-dropdown-item-overlay{background:transparent}.kbq-dropdown-item,.kbq-dropdown__content{font-size:var(--kbq-typography-text-normal-font-size);font-style:var(--kbq-typography-text-normal-font-style);font-weight:var(--kbq-typography-text-normal-font-weight);line-height:var(--kbq-typography-text-normal-line-height);font-family:var(--kbq-typography-text-normal-font-family);text-transform:var(--kbq-typography-text-normal-text-transform);font-feature-settings:var(--kbq-typography-text-normal-font-feature-settings);letter-spacing:var(--kbq-typography-text-normal-letter-spacing)}.kbq-dropdown-item .kbq-dropdown-item__caption,.kbq-dropdown__content .kbq-dropdown-item__caption{font-size:var(--kbq-typography-text-compact-font-size);font-style:var(--kbq-typography-text-compact-font-style);font-weight:var(--kbq-typography-text-compact-font-weight);line-height:var(--kbq-typography-text-compact-line-height);font-family:var(--kbq-typography-text-compact-font-family);text-transform:var(--kbq-typography-text-compact-text-transform);font-feature-settings:var(--kbq-typography-text-compact-font-feature-settings);letter-spacing:var(--kbq-typography-text-compact-letter-spacing)}.kbq-dropdown__group-header{font-size:var(--kbq-typography-big-strong-font-size);font-style:var(--kbq-typography-big-strong-font-style);font-weight:var(--kbq-typography-big-strong-font-weight);line-height:var(--kbq-typography-big-strong-line-height);font-family:var(--kbq-typography-big-strong-font-family);text-transform:var(--kbq-typography-big-strong-text-transform);font-feature-settings:var(--kbq-typography-big-strong-font-feature-settings);letter-spacing:var(--kbq-typography-big-strong-letter-spacing)}.kbq-dropdown__group-header.kbq-dropdown__group-header_small{font-size:var(--kbq-typography-caps-compact-strong-font-size);font-style:var(--kbq-typography-caps-compact-strong-font-style);font-weight:var(--kbq-typography-caps-compact-strong-font-weight);line-height:var(--kbq-typography-caps-compact-strong-line-height);font-family:var(--kbq-typography-caps-compact-strong-font-family);text-transform:var(--kbq-typography-caps-compact-strong-text-transform);font-feature-settings:var(--kbq-typography-caps-compact-strong-font-feature-settings);letter-spacing:var(--kbq-typography-caps-compact-strong-letter-spacing)}\n", "@charset \"UTF-8\";.kbq-list,.kbq-list-selection,.kbq-list-option.cdk-drag-preview,.kbq-list-drag-preview_text{--kbq-list-size-container-padding-left: var(--kbq-size-m);--kbq-list-size-container-padding-right: var(--kbq-size-m);--kbq-list-size-container-padding-vertical: var(--kbq-size-xxs);--kbq-list-size-container-content-gap-horizontal: var(--kbq-size-s);--kbq-list-size-container-content-gap-vertical: var(--kbq-size-3xs);--kbq-list-size-container-focus-outline-width: var(--kbq-size-3xs);--kbq-list-default-container-background: transparent;--kbq-list-default-text-color: var(--kbq-foreground-contrast);--kbq-list-default-icon-color: var(--kbq-icon-contrast);--kbq-list-default-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-default-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-hover-container-background: var(--kbq-states-background-transparent-hover);--kbq-list-states-active-container-background: var(--kbq-states-background-transparent-active);--kbq-list-states-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-selected-container-background: var(--kbq-background-theme-less);--kbq-list-multiple-states-selected-container-background: var(--kbq-background-contrast-less);--kbq-list-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-multiple-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-multiple-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-multiple-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-multiple-states-selected-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-selected-hover-container-background: var(--kbq-states-background-theme-less-hover);--kbq-list-multiple-states-selected-hover-container-background: var(--kbq-states-background-contrast-less-hover);--kbq-list-states-selected-active-container-background: var(--kbq-states-background-theme-less-active);--kbq-list-multiple-states-selected-active-container-background: var(--kbq-states-background-contrast-less-active);--kbq-list-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-multiple-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-multiple-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-multiple-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-multiple-states-selected-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-focused-focus-outline-color: var(--kbq-states-line-focus-theme);--kbq-list-states-disabled-container-background: transparent;--kbq-list-states-disabled-text-color: var(--kbq-states-foreground-disabled);--kbq-list-states-disabled-icon-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-icon-button-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-caption-color: var(--kbq-states-foreground-disabled);--kbq-list-states-dragged-container-background: var(--kbq-background-card);--kbq-list-states-dragged-container-shadow: var(--kbq-shadow-popup)}.kbq-list-selection{--kbq-list-size-dragged-indicator-thickness: var(--kbq-size-3xs);--kbq-list-states-dragged-indicator-color: var(--kbq-line-theme)}.kbq-list-drag-preview_text{--kbq-list-size-drag-preview-max-width: 480px;--kbq-list-states-drag-preview-background: color-mix( in srgb, var(--kbq-background-card) calc(var(--kbq-opacity-overlay) * 100%), transparent )}.kbq-dropdown__panel{--kbq-dropdown-size-container-width-min: 200px;--kbq-dropdown-size-container-width-max: var(--kbq-panel-size-width-max, 640px);--kbq-dropdown-size-container-padding-vertical: var(--kbq-size-xxs);--kbq-dropdown-size-container-border-radius: var(--kbq-size-s);--kbq-dropdown-container-background: var(--kbq-background-card);--kbq-dropdown-container-shadow: var(--kbq-shadow-popup);--kbq-dropdown-item-border-radius: var(--kbq-size-xs);--kbq-dropdown-item-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-default-container-background: transparent;--kbq-list-default-text-color: var(--kbq-foreground-contrast);--kbq-list-default-icon-color: var(--kbq-icon-contrast);--kbq-list-default-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-default-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-hover-container-background: var(--kbq-states-background-transparent-hover);--kbq-list-states-active-container-background: var(--kbq-states-background-transparent-active);--kbq-list-states-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-selected-container-background: var(--kbq-background-theme-less);--kbq-list-multiple-states-selected-container-background: var(--kbq-background-contrast-less);--kbq-list-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-multiple-states-selected-text-color: var(--kbq-foreground-contrast);--kbq-list-multiple-states-selected-icon-color: var(--kbq-icon-contrast);--kbq-list-multiple-states-selected-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-multiple-states-selected-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-selected-hover-container-background: var(--kbq-states-background-theme-less-hover);--kbq-list-multiple-states-selected-hover-container-background: var(--kbq-states-background-contrast-less-hover);--kbq-list-states-selected-active-container-background: var(--kbq-states-background-theme-less-active);--kbq-list-multiple-states-selected-active-container-background: var(--kbq-states-background-contrast-less-active);--kbq-list-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-states-selected-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-multiple-states-selected-hover-text-color: var(--kbq-foreground-contrast);--kbq-list-multiple-states-selected-hover-icon-color: var(--kbq-icon-contrast);--kbq-list-multiple-states-selected-hover-icon-button-color: var(--kbq-icon-contrast-fade);--kbq-list-multiple-states-selected-hover-caption-color: var(--kbq-foreground-contrast-secondary);--kbq-list-states-focused-focus-outline-color: var(--kbq-states-line-focus-theme);--kbq-list-states-disabled-container-background: transparent;--kbq-list-states-disabled-text-color: var(--kbq-states-foreground-disabled);--kbq-list-states-disabled-icon-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-icon-button-color: var(--kbq-states-icon-disabled);--kbq-list-states-disabled-caption-color: var(--kbq-states-foreground-disabled);--kbq-list-states-dragged-container-background: var(--kbq-background-card);--kbq-list-states-dragged-container-shadow: var(--kbq-shadow-popup)}\n"] }]
1159
+ }], ctorParameters: () => [], propDecorators: { panelFormField: [{ type: i0.ContentChild, args: [i0.forwardRef(() => KbqFormField), { isSignal: true }] }], searches: [{ type: i0.ContentChildren, args: [i0.forwardRef(() => KbqDropdownSearch), { ...{ descendants: true }, isSignal: true }] }], navigationWithWrap: [{ type: i0.Input, args: [{ isSignal: true, alias: "navigationWithWrap", required: false }] }], xPosition: [{
587
1160
  type: Input
588
1161
  }], yPosition: [{
589
1162
  type: Input
@@ -598,7 +1171,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImpo
598
1171
  args: ['class']
599
1172
  }], backdropClass: [{
600
1173
  type: Input
601
- }], templateRef: [{
1174
+ }], panelWidth: [{ type: i0.Input, args: [{ isSignal: true, alias: "panelWidth", required: false }] }], panelMinWidth: [{ type: i0.Input, args: [{ isSignal: true, alias: "panelMinWidth", required: false }] }], panelMaxWidth: [{ type: i0.Input, args: [{ isSignal: true, alias: "panelMaxWidth", required: false }] }], safeArea: [{ type: i0.Input, args: [{ isSignal: true, alias: "safeArea", required: false }] }], templateRef: [{
602
1175
  type: ViewChild,
603
1176
  args: [TemplateRef, { static: false }]
604
1177
  }], items: [{
@@ -611,8 +1184,14 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImpo
611
1184
  type: Output
612
1185
  }] } });
613
1186
 
614
- /** Injection token that determines the scroll handling while the dropdown is open. */
615
- const KBQ_DROPDOWN_SCROLL_STRATEGY = new InjectionToken('kbq-dropdown-scroll-strategy');
1187
+ /**
1188
+ * Injection token that determines the scroll handling while the dropdown is open. The root default keeps the
1189
+ * trigger usable outside `KbqDropdownModule`'s injector; providing the token anywhere still wins over it.
1190
+ */
1191
+ const KBQ_DROPDOWN_SCROLL_STRATEGY = new InjectionToken('kbq-dropdown-scroll-strategy', {
1192
+ providedIn: 'root',
1193
+ factory: () => KBQ_DROPDOWN_SCROLL_STRATEGY_FACTORY(inject(Overlay))
1194
+ });
616
1195
  /** @docs-private */
617
1196
  function KBQ_DROPDOWN_SCROLL_STRATEGY_FACTORY(overlay) {
618
1197
  return () => overlay.scrollStrategies.reposition();
@@ -693,6 +1272,16 @@ class KbqDropdownTrigger {
693
1272
  get opened() {
694
1273
  return this._opened;
695
1274
  }
1275
+ /**
1276
+ * Whether the dropdown overlay is currently attached. Part of the `KbqSiblingPopup` contract.
1277
+ *
1278
+ * `opened` is set synchronously right after the overlay is attached and, on close, only once the exit
1279
+ * animation is done — i.e. it stays `true` for the whole time the trigger is busy with its panel,
1280
+ * including the moment `destroy()` restores focus to the trigger.
1281
+ */
1282
+ get isAttached() {
1283
+ return this._opened;
1284
+ }
696
1285
  constructor() {
697
1286
  this.overlay = inject(Overlay);
698
1287
  this.elementRef = inject(ElementRef);
@@ -705,8 +1294,8 @@ class KbqDropdownTrigger {
705
1294
  this.focusMonitor = inject(FocusMonitor);
706
1295
  this.overlayContainer = inject(OverlayContainer);
707
1296
  this.renderer = inject(Renderer2);
1297
+ this.ngZone = inject(NgZone);
708
1298
  this.isBrowser = inject(Platform).isBrowser;
709
- this.window = inject(KBQ_WINDOW);
710
1299
  this.host = inject(KBQ_DROPDOWN_HOST, { optional: true });
711
1300
  // TODO: Skipped for migration because:
712
1301
  // Your application code writes to the input. This prevents migration.
@@ -735,10 +1324,13 @@ class KbqDropdownTrigger {
735
1324
  * KBQ_OPTION_ACTION_PARENT contract, which an `OutputEmitterRef` does not support — see #DS-5079.
736
1325
  */
737
1326
  this.dropdownClosed = new EventEmitter();
1327
+ /** Emits `true` when the dropdown opens and `false` when it closes. Part of the `KbqSiblingPopup` contract. */
1328
+ this.openedChange = merge(outputToObservable(this.dropdownOpened).pipe(map(() => true)), this.dropdownClosed.pipe(map(() => false)));
738
1329
  this._opened = false;
739
1330
  this.overlayRef = null;
740
1331
  this.closeSubscription = Subscription.EMPTY;
741
1332
  this.hoverSubscription = Subscription.EMPTY;
1333
+ this.widthLockSubscription = Subscription.EMPTY;
742
1334
  this.classAddedToOverlayContainer = false;
743
1335
  /**
744
1336
  * Handles touch start events on the trigger.
@@ -785,6 +1377,11 @@ class KbqDropdownTrigger {
785
1377
  const overlayConfig = overlayRef.getConfig();
786
1378
  this.setPosition(overlayConfig.positionStrategy);
787
1379
  overlayConfig.hasBackdrop = this.dropdown.hasBackdrop ? !this.isNested() : this.dropdown.hasBackdrop;
1380
+ // The overlay is created once and reused, so the trigger has to be re-measured on every open
1381
+ // to keep up with layout changes between them.
1382
+ if (this.shouldMatchTriggerWidth) {
1383
+ overlayRef.updateSize(this.getOverlaySize());
1384
+ }
788
1385
  overlayRef.attach(this.getPortal());
789
1386
  if (this.dropdown.lazyContent) {
790
1387
  this.dropdown.lazyContent.detach();
@@ -796,6 +1393,7 @@ class KbqDropdownTrigger {
796
1393
  this.dropdown.startAnimation();
797
1394
  }
798
1395
  this.addClassToOverlayContainer();
1396
+ this.lockOverlayWidthForSearch();
799
1397
  }
800
1398
  /** Closes the dropdown. */
801
1399
  close() {
@@ -806,6 +1404,10 @@ class KbqDropdownTrigger {
806
1404
  * Focuses the dropdown trigger.
807
1405
  */
808
1406
  focus(origin, options) {
1407
+ // The trigger of a nested panel is an item of a search panel: the caret belongs to the query,
1408
+ // not to the item, so hand it back to the field instead of focusing this element.
1409
+ if (this.isNested() && this.parent.restoreFocus?.())
1410
+ return;
809
1411
  if (this.focusMonitor && origin) {
810
1412
  this.focusMonitor.focusVia(this.elementRef.nativeElement, origin, options);
811
1413
  }
@@ -825,10 +1427,22 @@ class KbqDropdownTrigger {
825
1427
  event.preventDefault();
826
1428
  }
827
1429
  }
1430
+ /**
1431
+ * Starts safe-area protection when the pointer leaves a trigger whose submenu is open, so a
1432
+ * sibling item crossed on the way to the submenu doesn't prematurely close it.
1433
+ */
1434
+ handleMouseLeave(event) {
1435
+ if (!this.isNested() || !this._opened || !this.isBrowser || !this.parent.safeArea() || !this.overlayRef) {
1436
+ return;
1437
+ }
1438
+ const panelRect = this.overlayRef.overlayElement.getBoundingClientRect();
1439
+ const triangle = getSafeTriangleVertices({ x: event.clientX, y: event.clientY }, panelRect);
1440
+ this.parent.activateSafeArea(this.dropdownItemInstance, triangle, panelRect, () => this.close());
1441
+ }
828
1442
  /** Handles key presses on the trigger. */
829
1443
  handleKeydown(event) {
830
1444
  const keyCode = event.keyCode;
831
- if (keyCode === ENTER || keyCode === SPACE) {
1445
+ if (keyCode === ENTER$1 || keyCode === SPACE) {
832
1446
  this.openedBy = 'keyboard';
833
1447
  event.preventDefault();
834
1448
  if (this.isNested()) {
@@ -865,8 +1479,12 @@ class KbqDropdownTrigger {
865
1479
  return;
866
1480
  }
867
1481
  this.lastDestroyReason = reason;
1482
+ if (this.isNested()) {
1483
+ this.parent.deactivateSafeArea();
1484
+ }
868
1485
  this.dropdown.resetActiveItem();
869
1486
  this.closeSubscription.unsubscribe();
1487
+ this.widthLockSubscription.unsubscribe();
870
1488
  this.overlayRef.detach();
871
1489
  if (this.restoreFocus && (reason === 'keydown' || !this.openedBy || !this.isNested())) {
872
1490
  this.focus(this.openedBy);
@@ -956,12 +1574,16 @@ class KbqDropdownTrigger {
956
1574
  }
957
1575
  return this.overlayRef;
958
1576
  }
1577
+ /** Whether the panel should be at least as wide as its trigger. */
1578
+ get shouldMatchTriggerWidth() {
1579
+ const isVerticalTrigger = this.dropdown.overlapTriggerY && !this.dropdown.overlapTriggerX;
1580
+ return !this.isNested() && !isVerticalTrigger;
1581
+ }
959
1582
  /**
960
1583
  * This method builds the configuration object needed to create the overlay, the OverlayState.
961
1584
  * @returns OverlayConfig
962
1585
  */
963
1586
  getOverlayConfig() {
964
- const isVerticalTrigger = this.dropdown.overlapTriggerY && !this.dropdown.overlapTriggerX;
965
1587
  return new OverlayConfig({
966
1588
  positionStrategy: this.overlay
967
1589
  .position()
@@ -971,7 +1593,7 @@ class KbqDropdownTrigger {
971
1593
  backdropClass: this.dropdown.backdropClass || 'cdk-overlay-transparent-backdrop',
972
1594
  scrollStrategy: this.scrollStrategy(),
973
1595
  direction: this.dir,
974
- ...(!this.isNested() && !isVerticalTrigger && { minWidth: this.getWidth() })
1596
+ ...(this.shouldMatchTriggerWidth && this.getOverlaySize())
975
1597
  });
976
1598
  }
977
1599
  /**
@@ -1055,6 +1677,7 @@ class KbqDropdownTrigger {
1055
1677
  cleanUpSubscriptions() {
1056
1678
  this.closeSubscription.unsubscribe();
1057
1679
  this.hoverSubscription.unsubscribe();
1680
+ this.widthLockSubscription.unsubscribe();
1058
1681
  }
1059
1682
  /** Returns a stream that emits whenever an action that should close the dropdown occurs. */
1060
1683
  closingActions() {
@@ -1063,7 +1686,13 @@ class KbqDropdownTrigger {
1063
1686
  const detachments = this.overlayRef.detachments();
1064
1687
  const parentClose = this.parent ? this.parent.closed : of();
1065
1688
  const hover = this.parent
1066
- ? this.parent.hovered().pipe(filter((active) => active !== this.dropdownItemInstance), filter(() => this._opened))
1689
+ ? this.parent.hovered().pipe(filter((active) => active !== this.dropdownItemInstance), filter(() => this._opened),
1690
+ // While a safe area protects this dropdown, closing is driven by the safe area
1691
+ // itself instead: either it resolves on its own (see `handleMouseLeave()`), or a
1692
+ // forced switch to a different nested trigger closes this one via `onExit` — always
1693
+ // before the new trigger opens, so the two don't race over animation state shared by
1694
+ // triggers pointing at the same dropdown (see `KbqDropdown.activateSafeArea()`).
1695
+ filter(() => !this.parent.isSafeAreaActive()))
1067
1696
  : of();
1068
1697
  return merge(backdrop, outsidePointerEvents, parentClose, hover, detachments);
1069
1698
  }
@@ -1073,13 +1702,21 @@ class KbqDropdownTrigger {
1073
1702
  if (!this.isNested()) {
1074
1703
  return;
1075
1704
  }
1076
- this.hoverSubscription = this.parent
1077
- .hovered()
1705
+ this.hoverSubscription = merge(this.parent.hovered().pipe(filter((active) => active === this.dropdownItemInstance && !active.disabled),
1706
+ // While a *different* trigger's safe area is active, opening is deferred to
1707
+ // `onSwitchTarget()` below, which only fires once that trigger has actually closed.
1708
+ // Hovering the trigger that owns the active safe area (coming back to it) still
1709
+ // passes through immediately — `open()` is a no-op there, but it lets the safe area be
1710
+ // cancelled below.
1711
+ filter(() => !this.parent.isSafeAreaActive() || this.parent.isSafeAreaOwner(this.dropdownItemInstance))), this.parent.onSwitchTarget().pipe(filter((active) => active === this.dropdownItemInstance)))
1078
1712
  // Since we might have multiple competing triggers for the same dropdown (e.g. a nested dropdown
1079
1713
  // with different data and triggers), we have to delay it by a tick to ensure that
1080
1714
  // it won't be closed immediately after it is opened.
1081
- .pipe(filter((active) => active === this.dropdownItemInstance && !active.disabled), delay(0, asapScheduler))
1715
+ .pipe(delay(0, asapScheduler))
1082
1716
  .subscribe(() => {
1717
+ // Coming back to this trigger cancels any safe-area protection left over from a
1718
+ // previous `mouseleave`.
1719
+ this.parent.deactivateSafeArea();
1083
1720
  this.openedBy = 'mouse';
1084
1721
  // If the same dropdown is used between multiple triggers, it might still be animating
1085
1722
  // while the new trigger tries to re-open it. Wait for the animation to finish
@@ -1107,12 +1744,40 @@ class KbqDropdownTrigger {
1107
1744
  }
1108
1745
  return this.portal;
1109
1746
  }
1110
- getWidth() {
1111
- if (!this.isBrowser)
1112
- return '';
1113
- const nativeElement = this.elementRef.nativeElement;
1114
- const { width, borderRightWidth, borderLeftWidth } = this.window.getComputedStyle(nativeElement);
1115
- return `${parseInt(width) - parseInt(borderRightWidth) - parseInt(borderLeftWidth)}px`;
1747
+ getOverlaySize() {
1748
+ return kbqResolvePanelWidth(this.dropdown.panelWidth?.(), this.dropdown.panelMinWidth?.(), this.isBrowser ? kbqGetPanelWidthOrigin(this.widthOrigin ?? this.elementRef) : 0);
1749
+ }
1750
+ /**
1751
+ * When the panel hosts a search field, its content-sized width would jump as the field's cleaner
1752
+ * appears or options are filtered. Freeze the width at the opened (empty) state so it stays stable
1753
+ * — mirrors `KbqAbstractSelect.lockOverlayWidthForSearch`.
1754
+ */
1755
+ lockOverlayWidthForSearch() {
1756
+ if (!this.isBrowser ||
1757
+ !this.shouldMatchTriggerWidth ||
1758
+ !(this.dropdown instanceof KbqDropdown) ||
1759
+ !this.dropdown.hasSearch()) {
1760
+ return;
1761
+ }
1762
+ this.widthLockSubscription = this.ngZone.onStable
1763
+ .asObservable()
1764
+ .pipe(take(1))
1765
+ .subscribe(() => this.pinOverlayWidth());
1766
+ }
1767
+ /** Freezes the overlay pane at its rendered width. */
1768
+ pinOverlayWidth() {
1769
+ if (!this._opened || !this.overlayRef)
1770
+ return;
1771
+ // An explicit or `'auto'` panelWidth already fixes the pane; only pin content-sized panels.
1772
+ if (this.getOverlaySize().width !== '')
1773
+ return;
1774
+ // Measure the pane, not `.kbq-dropdown__panel`: the panel scales in via `@transformDropdown`,
1775
+ // so its `getBoundingClientRect()` can read a mid-animation (scaled) width. The pane is
1776
+ // transform-immune and the panel fills it.
1777
+ const width = this.overlayRef.overlayElement.getBoundingClientRect().width;
1778
+ if (width) {
1779
+ this.overlayRef.updateSize({ width });
1780
+ }
1116
1781
  }
1117
1782
  addClassToOverlayContainer() {
1118
1783
  if (!this.demoteOverlay)
@@ -1128,17 +1793,19 @@ class KbqDropdownTrigger {
1128
1793
  this.renderer.removeClass(this.overlayContainer.getContainerElement(), 'cdk-overlay-container_dropdown');
1129
1794
  }
1130
1795
  }
1131
- /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownTrigger, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
1132
- /** @nocollapse */ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "16.1.0", version: "20.3.25", type: KbqDropdownTrigger, isStandalone: true, selector: "[kbqDropdownTriggerFor]", inputs: { offsetX: ["offsetX", "offsetX", numberAttribute], offsetY: ["offsetY", "offsetY", numberAttribute], data: ["kbqDropdownTriggerData", "data"], openByArrowDown: "openByArrowDown", demoteOverlay: ["demoteOverlay", "demoteOverlay", booleanAttribute], restoreFocus: ["kbqDropdownTriggerRestoreFocus", "restoreFocus"], dropdown: ["kbqDropdownTriggerFor", "dropdown"] }, outputs: { dropdownOpened: "dropdownOpened", dropdownClosed: "dropdownClosed" }, host: { listeners: { "mousedown": "handleMousedown($event)", "keydown": "handleKeydown($event)", "click": "handleClick($event)" }, properties: { "class.kbq-pressed": "opened" }, classAttribute: "kbq-dropdown-trigger" }, exportAs: ["kbqDropdownTrigger"], ngImport: i0 }); }
1796
+ /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownTrigger, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
1797
+ /** @nocollapse */ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "16.1.0", version: "20.3.30", type: KbqDropdownTrigger, isStandalone: true, selector: "[kbqDropdownTriggerFor]", inputs: { offsetX: ["offsetX", "offsetX", numberAttribute], offsetY: ["offsetY", "offsetY", numberAttribute], data: ["kbqDropdownTriggerData", "data"], openByArrowDown: "openByArrowDown", demoteOverlay: ["demoteOverlay", "demoteOverlay", booleanAttribute], restoreFocus: ["kbqDropdownTriggerRestoreFocus", "restoreFocus"], dropdown: ["kbqDropdownTriggerFor", "dropdown"] }, outputs: { dropdownOpened: "dropdownOpened", dropdownClosed: "dropdownClosed" }, host: { listeners: { "mousedown": "handleMousedown($event)", "mouseleave": "handleMouseLeave($event)", "keydown": "handleKeydown($event)", "click": "handleClick($event)" }, properties: { "class.kbq-pressed": "opened" }, classAttribute: "kbq-dropdown-trigger" }, providers: [kbqSiblingPopupProvider(KbqDropdownTrigger)], exportAs: ["kbqDropdownTrigger"], ngImport: i0 }); }
1133
1798
  }
1134
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownTrigger, decorators: [{
1799
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownTrigger, decorators: [{
1135
1800
  type: Directive,
1136
1801
  args: [{
1137
1802
  selector: `[kbqDropdownTriggerFor]`,
1803
+ providers: [kbqSiblingPopupProvider(KbqDropdownTrigger)],
1138
1804
  host: {
1139
1805
  class: 'kbq-dropdown-trigger',
1140
1806
  '[class.kbq-pressed]': 'opened',
1141
1807
  '(mousedown)': 'handleMousedown($event)',
1808
+ '(mouseleave)': 'handleMouseLeave($event)',
1142
1809
  '(keydown)': 'handleKeydown($event)',
1143
1810
  '(click)': 'handleClick($event)'
1144
1811
  },
@@ -1169,23 +1836,29 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImpo
1169
1836
  }] } });
1170
1837
 
1171
1838
  class KbqDropdownModule {
1172
- /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule }); }
1173
- /** @nocollapse */ static { this.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownModule, imports: [OverlayModule,
1839
+ /** @nocollapse */ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule }); }
1840
+ /** @nocollapse */ static { this.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownModule, imports: [OverlayModule,
1174
1841
  KbqIconModule,
1175
1842
  KbqDropdownStaticContent,
1176
1843
  KbqDropdown,
1177
1844
  KbqDropdownItem,
1845
+ KbqDropdownItemAction,
1178
1846
  KbqDropdownTrigger,
1179
- KbqDropdownContent], exports: [KbqDropdown,
1847
+ KbqDropdownContent,
1848
+ KbqDropdownFooter,
1849
+ KbqDropdownSearch], exports: [KbqDropdown,
1180
1850
  KbqDropdownItem,
1851
+ KbqDropdownItemAction,
1181
1852
  KbqDropdownTrigger,
1182
1853
  KbqDropdownContent,
1183
- KbqDropdownStaticContent] }); }
1184
- /** @nocollapse */ static { this.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownModule, providers: [KBQ_DROPDOWN_SCROLL_STRATEGY_FACTORY_PROVIDER], imports: [OverlayModule,
1854
+ KbqDropdownStaticContent,
1855
+ KbqDropdownFooter,
1856
+ KbqDropdownSearch] }); }
1857
+ /** @nocollapse */ static { this.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownModule, imports: [OverlayModule,
1185
1858
  KbqIconModule,
1186
1859
  KbqDropdownItem] }); }
1187
1860
  }
1188
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImport: i0, type: KbqDropdownModule, decorators: [{
1861
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.30", ngImport: i0, type: KbqDropdownModule, decorators: [{
1189
1862
  type: NgModule,
1190
1863
  args: [{
1191
1864
  imports: [
@@ -1194,16 +1867,21 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImpo
1194
1867
  KbqDropdownStaticContent,
1195
1868
  KbqDropdown,
1196
1869
  KbqDropdownItem,
1870
+ KbqDropdownItemAction,
1197
1871
  KbqDropdownTrigger,
1198
- KbqDropdownContent
1872
+ KbqDropdownContent,
1873
+ KbqDropdownFooter,
1874
+ KbqDropdownSearch
1199
1875
  ],
1200
- providers: [KBQ_DROPDOWN_SCROLL_STRATEGY_FACTORY_PROVIDER],
1201
1876
  exports: [
1202
1877
  KbqDropdown,
1203
1878
  KbqDropdownItem,
1879
+ KbqDropdownItemAction,
1204
1880
  KbqDropdownTrigger,
1205
1881
  KbqDropdownContent,
1206
- KbqDropdownStaticContent
1882
+ KbqDropdownStaticContent,
1883
+ KbqDropdownFooter,
1884
+ KbqDropdownSearch
1207
1885
  ]
1208
1886
  }]
1209
1887
  }] });
@@ -1212,5 +1890,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.25", ngImpo
1212
1890
  * Generated bundle index. Do not edit.
1213
1891
  */
1214
1892
 
1215
- export { KBQ_DROPDOWN_DEFAULT_OPTIONS, KBQ_DROPDOWN_DEFAULT_OPTIONS_FACTORY, KBQ_DROPDOWN_HOST, KBQ_DROPDOWN_PANEL, KBQ_DROPDOWN_SCROLL_STRATEGY, KBQ_DROPDOWN_SCROLL_STRATEGY_FACTORY, KBQ_DROPDOWN_SCROLL_STRATEGY_FACTORY_PROVIDER, KbqDropdown, KbqDropdownContent, KbqDropdownItem, KbqDropdownModule, KbqDropdownStaticContent, KbqDropdownTrigger, NESTED_PANEL_LEFT_PADDING, NESTED_PANEL_TOP_PADDING, fadeInItems, kbqDropdownAnimations, throwKbqDropdownInvalidPositionX, throwKbqDropdownInvalidPositionY, throwKbqDropdownMissingError, transformDropdown };
1893
+ export { KBQ_DROPDOWN_DEFAULT_OPTIONS, KBQ_DROPDOWN_DEFAULT_OPTIONS_FACTORY, KBQ_DROPDOWN_HOST, KBQ_DROPDOWN_PANEL, KBQ_DROPDOWN_SCROLL_STRATEGY, KBQ_DROPDOWN_SCROLL_STRATEGY_FACTORY, KBQ_DROPDOWN_SCROLL_STRATEGY_FACTORY_PROVIDER, KbqDropdown, KbqDropdownContent, KbqDropdownFooter, KbqDropdownItem, KbqDropdownItemAction, KbqDropdownModule, KbqDropdownSearch, KbqDropdownStaticContent, KbqDropdownTrigger, NESTED_HOVER_SWITCH_DELAY, NESTED_PANEL_LEFT_PADDING, NESTED_PANEL_TOP_PADDING, fadeInItems, kbqDropdownAnimations, throwKbqDropdownInvalidPositionX, throwKbqDropdownInvalidPositionY, throwKbqDropdownMissingError, throwKbqDropdownSearchMissingInputError, throwKbqDropdownSearchMissingNgControlError, transformDropdown };
1216
1894
  //# sourceMappingURL=koobiq-components-dropdown.mjs.map