@lilydesignsystem/angular-headless 0.1.0 → 0.2.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.
@@ -1,5 +1,5 @@
1
1
  import * as i0 from '@angular/core';
2
- import { input, ChangeDetectionStrategy, Component, model } from '@angular/core';
2
+ import { input, ChangeDetectionStrategy, Component, model, computed, ViewChild, output } from '@angular/core';
3
3
 
4
4
  /**
5
5
  * AccordionCheckbox — a checkbox option that reveals an accordion panel when checked
@@ -6793,28 +6793,100 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImpor
6793
6793
  * IconButton — a button containing only an icon with a required accessible label
6794
6794
  *
6795
6795
  * Headless Angular component. Renders the semantic HTML root with the
6796
- * kebab-case class hook `icon-button` and the consumer-provided `className`.
6797
- * Ships zero CSS; the consumer styles via the class hook.
6796
+ * kebab-case class hook `icon-button` (or `baseClass`) and the consumer-
6797
+ * provided `className`. Ships zero CSS; the consumer styles via the class
6798
+ * hook.
6799
+ *
6800
+ * The `lily-icon-button` selector tag itself is `display: contents`
6801
+ * unconditionally, on every usage — it is a semantics-free structural
6802
+ * wrapper (Angular's component selector always emits a real host element;
6803
+ * there is no Svelte-`<svelte:element>`/no-wrapper-root equivalent), so it
6804
+ * must never participate in layout or box generation. This is the same
6805
+ * "structurally required inline style" exception documented in
6806
+ * spec/headless/index.md for `ThemeProvider`, applied here for the same
6807
+ * reason: composing `<lily-icon-button>` inside a consumer's own template
6808
+ * (e.g. a `*-picker` component) must not insert a visible extra box
6809
+ * between the picker's root and its real `<button>`.
6810
+ *
6811
+ * `baseClass`, `ariaHaspopup`/`ariaExpanded`/`ariaControls`, and `focus()`
6812
+ * exist specifically so a composing consumer can reproduce an exact
6813
+ * `class="{helper}-button" aria-haspopup aria-expanded aria-controls`
6814
+ * contract and call `.focus()` on the real button — Angular has no
6815
+ * generic spread-onto-inputs mechanism (see picker-bar's own contract
6816
+ * note), so these are named inputs rather than a rest-prop spread.
6798
6817
  */
6799
6818
  class IconButton {
6800
- /** Optional aria-label override. */
6819
+ /** Accessible label (REQUIRED for icon-only buttons in practice; enforced by convention, not the type system, to match the button's own required aria-label contract). */
6801
6820
  label = input("", /* @ts-ignore */
6802
6821
  ...(ngDevMode ? [{ debugName: "label" }] : /* istanbul ignore next */ []));
6803
- /** Extra CSS classes appended to the base class. */
6822
+ /** Extra CSS classes appended after the base class. */
6804
6823
  className = input("", /* @ts-ignore */
6805
6824
  ...(ngDevMode ? [{ debugName: "className" }] : /* istanbul ignore next */ []));
6825
+ /** Base class token, replacing `"icon-button"` outright (not appended). */
6826
+ baseClass = input("icon-button", /* @ts-ignore */
6827
+ ...(ngDevMode ? [{ debugName: "baseClass" }] : /* istanbul ignore next */ []));
6828
+ ariaHaspopup = input("", /* @ts-ignore */
6829
+ ...(ngDevMode ? [{ debugName: "ariaHaspopup" }] : /* istanbul ignore next */ []));
6830
+ ariaExpanded = input(null, /* @ts-ignore */
6831
+ ...(ngDevMode ? [{ debugName: "ariaExpanded" }] : /* istanbul ignore next */ []));
6832
+ ariaControls = input("", /* @ts-ignore */
6833
+ ...(ngDevMode ? [{ debugName: "ariaControls" }] : /* istanbul ignore next */ []));
6834
+ disabled = input(false, /* @ts-ignore */
6835
+ ...(ngDevMode ? [{ debugName: "disabled" }] : /* istanbul ignore next */ []));
6836
+ rootRef;
6837
+ ariaExpandedAttr = computed(() => {
6838
+ const v = this.ariaExpanded();
6839
+ return v === null ? null : String(v);
6840
+ }, /* @ts-ignore */
6841
+ ...(ngDevMode ? [{ debugName: "ariaExpandedAttr" }] : /* istanbul ignore next */ []));
6842
+ /** Focus the real rendered `<button>`. */
6843
+ focus(options) {
6844
+ this.rootRef?.nativeElement.focus(options);
6845
+ }
6846
+ /**
6847
+ * The real rendered `<button>` element. `focus()` covers the common
6848
+ * case; this exists for a consumer that needs the raw node itself —
6849
+ * e.g. remembering it as a focus-restoration target, or an
6850
+ * `instanceof HTMLElement` / `.contains()` check — where a behaviour
6851
+ * method alone isn't enough.
6852
+ */
6853
+ get element() {
6854
+ return this.rootRef?.nativeElement;
6855
+ }
6806
6856
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: IconButton, deps: [], target: i0.ɵɵFactoryTarget.Component });
6807
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "22.1.4", type: IconButton, isStandalone: true, selector: "lily-icon-button", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, className: { classPropertyName: "className", publicName: "className", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `<button class="icon-button {{ className() }}" type="button" [attr.aria-label]="label() || null"><ng-content /></button>`, isInline: true, changeDetection: i0.ChangeDetectionStrategy.OnPush });
6857
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "22.1.4", type: IconButton, isStandalone: true, selector: "lily-icon-button", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, className: { classPropertyName: "className", publicName: "className", isSignal: true, isRequired: false, transformFunction: null }, baseClass: { classPropertyName: "baseClass", publicName: "baseClass", isSignal: true, isRequired: false, transformFunction: null }, ariaHaspopup: { classPropertyName: "ariaHaspopup", publicName: "ariaHaspopup", isSignal: true, isRequired: false, transformFunction: null }, ariaExpanded: { classPropertyName: "ariaExpanded", publicName: "ariaExpanded", isSignal: true, isRequired: false, transformFunction: null }, ariaControls: { classPropertyName: "ariaControls", publicName: "ariaControls", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null } }, host: { styleAttribute: "display: contents" }, viewQueries: [{ propertyName: "rootRef", first: true, predicate: ["root"], descendants: true }], ngImport: i0, template: `<button
6858
+ #root
6859
+ class="{{ baseClass() }} {{ className() }}"
6860
+ type="button"
6861
+ [attr.aria-label]="label() || null"
6862
+ [attr.aria-haspopup]="ariaHaspopup() || null"
6863
+ [attr.aria-expanded]="ariaExpandedAttr()"
6864
+ [attr.aria-controls]="ariaControls() || null"
6865
+ [disabled]="disabled()"
6866
+ ><ng-content /></button>`, isInline: true, changeDetection: i0.ChangeDetectionStrategy.OnPush });
6808
6867
  }
6809
6868
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: IconButton, decorators: [{
6810
6869
  type: Component,
6811
6870
  args: [{
6812
6871
  selector: "lily-icon-button",
6813
6872
  standalone: true,
6814
- template: `<button class="icon-button {{ className() }}" type="button" [attr.aria-label]="label() || null"><ng-content /></button>`,
6873
+ template: `<button
6874
+ #root
6875
+ class="{{ baseClass() }} {{ className() }}"
6876
+ type="button"
6877
+ [attr.aria-label]="label() || null"
6878
+ [attr.aria-haspopup]="ariaHaspopup() || null"
6879
+ [attr.aria-expanded]="ariaExpandedAttr()"
6880
+ [attr.aria-controls]="ariaControls() || null"
6881
+ [disabled]="disabled()"
6882
+ ><ng-content /></button>`,
6883
+ host: { style: "display: contents" },
6815
6884
  changeDetection: ChangeDetectionStrategy.OnPush,
6816
6885
  }]
6817
- }], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], className: [{ type: i0.Input, args: [{ isSignal: true, alias: "className", required: false }] }] } });
6886
+ }], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], className: [{ type: i0.Input, args: [{ isSignal: true, alias: "className", required: false }] }], baseClass: [{ type: i0.Input, args: [{ isSignal: true, alias: "baseClass", required: false }] }], ariaHaspopup: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaHaspopup", required: false }] }], ariaExpanded: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaExpanded", required: false }] }], ariaControls: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaControls", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }], rootRef: [{
6887
+ type: ViewChild,
6888
+ args: ["root"]
6889
+ }] } });
6818
6890
 
6819
6891
  /**
6820
6892
  * IconList — an ordered list of icon list item components
@@ -8173,26 +8245,197 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImpor
8173
8245
  * Listbox — a list of selectable options with keyboard navigation
8174
8246
  *
8175
8247
  * Headless Angular component. Renders the semantic HTML root with the
8176
- * kebab-case class hook `listbox` and the consumer-provided `className`.
8177
- * Ships zero CSS; the consumer styles via the class hook.
8248
+ * kebab-case class hook `listbox` (or `baseClass`) and the consumer-
8249
+ * provided `className`. Ships zero CSS; the consumer styles via the class
8250
+ * hook.
8251
+ *
8252
+ * `navigation="active-descendant"` (opt-in; default `"roving-focus"` is
8253
+ * unchanged) implements the full WAI-ARIA APG listbox keyboard contract
8254
+ * via a virtual cursor: the root itself holds focus and tracks
8255
+ * `activeIndex` (a two-way `model()`, this catalog's established
8256
+ * bindable-state idiom — see `picker-bar`'s own contract note), mirrored
8257
+ * to `aria-activedescendant`. `clamp` (vs. wrap), `typeahead`, `pageSize`
8258
+ * paging, and `activate`/`escape`/`tabOut` outputs let a composing
8259
+ * consumer (e.g. a `*-picker` component) decide what "select" / "cancel"
8260
+ * / "leave" mean, the same division of responsibility as the Svelte
8261
+ * version this was ported from.
8262
+ *
8263
+ * Like `IconButton`, the `lily-listbox` selector tag itself is
8264
+ * `display: contents` unconditionally — a semantics-free structural
8265
+ * wrapper around the real `role="listbox"` element, so composing it
8266
+ * inside another component's template inserts no extra layout box. See
8267
+ * `IconButton`'s doc comment for the full `display: contents` reasoning
8268
+ * (mirrors the `ThemeProvider` precedent in spec/headless/index.md).
8178
8269
  */
8179
8270
  class Listbox {
8180
8271
  label = input("", /* @ts-ignore */
8181
8272
  ...(ngDevMode ? [{ debugName: "label" }] : /* istanbul ignore next */ []));
8182
8273
  className = input("", /* @ts-ignore */
8183
8274
  ...(ngDevMode ? [{ debugName: "className" }] : /* istanbul ignore next */ []));
8275
+ /** Base class token, replacing `"listbox"` outright (not appended). */
8276
+ baseClass = input("listbox", /* @ts-ignore */
8277
+ ...(ngDevMode ? [{ debugName: "baseClass" }] : /* istanbul ignore next */ []));
8278
+ /** `id` for the real inner `role="listbox"` element — named `elementId`, not `id`, because the host tag's own native `id` attribute (set directly on `<lily-listbox id="...">` by a consumer) is a separate, unrelated thing once `display: contents` puts a real wrapper element between the host and the inner listbox. Needed so a composing consumer's `aria-controls`/`document.getElementById` can reach the real element. */
8279
+ elementId = input("", /* @ts-ignore */
8280
+ ...(ngDevMode ? [{ debugName: "elementId" }] : /* istanbul ignore next */ []));
8281
+ /** Sets `hidden` on the real inner element. Angular has no generic spread-onto-inputs mechanism (see `IconButton`'s doc comment), so this is a named input rather than a rest-prop spread. */
8282
+ hidden = input(false, /* @ts-ignore */
8283
+ ...(ngDevMode ? [{ debugName: "hidden" }] : /* istanbul ignore next */ []));
8284
+ navigation = input("roving-focus", /* @ts-ignore */
8285
+ ...(ngDevMode ? [{ debugName: "navigation" }] : /* istanbul ignore next */ []));
8286
+ /** Arrow keys clamp instead of wrap (active-descendant mode only). */
8287
+ clamp = input(false, /* @ts-ignore */
8288
+ ...(ngDevMode ? [{ debugName: "clamp" }] : /* istanbul ignore next */ []));
8289
+ /** Printable-character typeahead (active-descendant mode only). */
8290
+ typeahead = input(false, /* @ts-ignore */
8291
+ ...(ngDevMode ? [{ debugName: "typeahead" }] : /* istanbul ignore next */ []));
8292
+ /** PageUp/PageDown step size (active-descendant mode only). */
8293
+ pageSize = input(10, /* @ts-ignore */
8294
+ ...(ngDevMode ? [{ debugName: "pageSize" }] : /* istanbul ignore next */ []));
8295
+ /** Virtual cursor position. Two-way bindable via `[(activeIndex)]`. -1 = none. */
8296
+ activeIndex = model(-1, /* @ts-ignore */
8297
+ ...(ngDevMode ? [{ debugName: "activeIndex" }] : /* istanbul ignore next */ []));
8298
+ /** Enter/Space on the active option (active-descendant mode only). */
8299
+ activate = output();
8300
+ /** Escape pressed (active-descendant mode only). */
8301
+ escape = output();
8302
+ /** Tab pressed, emitted before the key is processed — never prevented, so the consumer can move focus first (e.g. to a trigger button) before the browser's default Tab computes its target (active-descendant mode only). */
8303
+ tabOut = output();
8304
+ rootRef;
8305
+ typeaheadBuffer = "";
8306
+ typeaheadTimer;
8307
+ options() {
8308
+ return this.rootRef
8309
+ ? Array.from(this.rootRef.nativeElement.querySelectorAll("[role='option']"))
8310
+ : [];
8311
+ }
8312
+ activeId = computed(() => {
8313
+ if (this.navigation() !== "active-descendant")
8314
+ return null;
8315
+ const i = this.activeIndex();
8316
+ if (i < 0)
8317
+ return null;
8318
+ return this.options()[i]?.id || null;
8319
+ }, /* @ts-ignore */
8320
+ ...(ngDevMode ? [{ debugName: "activeId" }] : /* istanbul ignore next */ []));
8321
+ /** Focus the root (active-descendant mode: the listbox itself holds focus). */
8322
+ focus(options) {
8323
+ this.rootRef?.nativeElement.focus(options);
8324
+ }
8325
+ moveActive(delta) {
8326
+ const count = this.options().length;
8327
+ if (count === 0)
8328
+ return;
8329
+ const next = this.activeIndex() + delta;
8330
+ this.activeIndex.set(this.clamp() ? Math.min(Math.max(next, 0), count - 1) : ((next % count) + count) % count);
8331
+ }
8332
+ runTypeahead(char) {
8333
+ const opts = this.options();
8334
+ if (opts.length === 0)
8335
+ return;
8336
+ const lower = char.toLowerCase();
8337
+ const sameCharRun = this.typeaheadBuffer === "" || [...this.typeaheadBuffer].every((c) => c === lower);
8338
+ this.typeaheadBuffer += lower;
8339
+ clearTimeout(this.typeaheadTimer);
8340
+ this.typeaheadTimer = setTimeout(() => (this.typeaheadBuffer = ""), 500);
8341
+ const query = sameCharRun ? lower : this.typeaheadBuffer;
8342
+ const anchor = this.activeIndex() < 0 ? 0 : this.activeIndex();
8343
+ const start = sameCharRun ? anchor + 1 : anchor;
8344
+ for (let n = 0; n < opts.length; n++) {
8345
+ const i = (start + n) % opts.length;
8346
+ if ((opts[i].textContent ?? "").trim().toLowerCase().startsWith(query)) {
8347
+ this.activeIndex.set(i);
8348
+ return;
8349
+ }
8350
+ }
8351
+ }
8352
+ onKeydown(event) {
8353
+ if (this.navigation() !== "active-descendant")
8354
+ return;
8355
+ switch (event.key) {
8356
+ case "ArrowDown":
8357
+ event.preventDefault();
8358
+ this.moveActive(1);
8359
+ break;
8360
+ case "ArrowUp":
8361
+ event.preventDefault();
8362
+ this.moveActive(-1);
8363
+ break;
8364
+ case "Home":
8365
+ event.preventDefault();
8366
+ this.activeIndex.set(this.options().length ? 0 : -1);
8367
+ break;
8368
+ case "End":
8369
+ event.preventDefault();
8370
+ this.activeIndex.set(this.options().length - 1);
8371
+ break;
8372
+ case "PageDown":
8373
+ event.preventDefault();
8374
+ this.moveActive(this.pageSize());
8375
+ break;
8376
+ case "PageUp":
8377
+ event.preventDefault();
8378
+ this.moveActive(-this.pageSize());
8379
+ break;
8380
+ case "Enter":
8381
+ case " ":
8382
+ event.preventDefault();
8383
+ if (this.activeIndex() >= 0)
8384
+ this.activate.emit(this.activeIndex());
8385
+ break;
8386
+ case "Escape":
8387
+ event.preventDefault();
8388
+ this.escape.emit();
8389
+ break;
8390
+ case "Tab":
8391
+ this.tabOut.emit(event);
8392
+ break;
8393
+ default:
8394
+ if (this.typeahead() &&
8395
+ event.key.length === 1 &&
8396
+ !event.ctrlKey &&
8397
+ !event.metaKey &&
8398
+ !event.altKey) {
8399
+ this.runTypeahead(event.key);
8400
+ }
8401
+ }
8402
+ }
8184
8403
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: Listbox, deps: [], target: i0.ɵɵFactoryTarget.Component });
8185
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "22.1.4", type: Listbox, isStandalone: true, selector: "lily-listbox", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, className: { classPropertyName: "className", publicName: "className", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `<div class="listbox {{ className() }}" [attr.aria-label]="label() || null"><ng-content /></div>`, isInline: true, changeDetection: i0.ChangeDetectionStrategy.OnPush });
8404
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "22.1.4", type: Listbox, isStandalone: true, selector: "lily-listbox", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, className: { classPropertyName: "className", publicName: "className", isSignal: true, isRequired: false, transformFunction: null }, baseClass: { classPropertyName: "baseClass", publicName: "baseClass", isSignal: true, isRequired: false, transformFunction: null }, elementId: { classPropertyName: "elementId", publicName: "elementId", isSignal: true, isRequired: false, transformFunction: null }, hidden: { classPropertyName: "hidden", publicName: "hidden", isSignal: true, isRequired: false, transformFunction: null }, navigation: { classPropertyName: "navigation", publicName: "navigation", isSignal: true, isRequired: false, transformFunction: null }, clamp: { classPropertyName: "clamp", publicName: "clamp", isSignal: true, isRequired: false, transformFunction: null }, typeahead: { classPropertyName: "typeahead", publicName: "typeahead", isSignal: true, isRequired: false, transformFunction: null }, pageSize: { classPropertyName: "pageSize", publicName: "pageSize", isSignal: true, isRequired: false, transformFunction: null }, activeIndex: { classPropertyName: "activeIndex", publicName: "activeIndex", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { activeIndex: "activeIndexChange", activate: "activate", escape: "escape", tabOut: "tabOut" }, host: { styleAttribute: "display: contents" }, viewQueries: [{ propertyName: "rootRef", first: true, predicate: ["root"], descendants: true }], ngImport: i0, template: `<div
8405
+ #root
8406
+ [id]="elementId() || null"
8407
+ class="{{ baseClass() }} {{ className() }}"
8408
+ role="listbox"
8409
+ [attr.aria-label]="label() || null"
8410
+ [attr.tabindex]="navigation() === 'active-descendant' ? -1 : null"
8411
+ [attr.aria-activedescendant]="activeId()"
8412
+ [attr.hidden]="hidden() ? '' : null"
8413
+ (keydown)="onKeydown($event)"
8414
+ ><ng-content /></div>`, isInline: true, changeDetection: i0.ChangeDetectionStrategy.OnPush });
8186
8415
  }
8187
8416
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: Listbox, decorators: [{
8188
8417
  type: Component,
8189
8418
  args: [{
8190
8419
  selector: "lily-listbox",
8191
8420
  standalone: true,
8192
- template: `<div class="listbox {{ className() }}" [attr.aria-label]="label() || null"><ng-content /></div>`,
8193
- changeDetection: ChangeDetectionStrategy.OnPush,
8194
- }]
8195
- }], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], className: [{ type: i0.Input, args: [{ isSignal: true, alias: "className", required: false }] }] } });
8421
+ template: `<div
8422
+ #root
8423
+ [id]="elementId() || null"
8424
+ class="{{ baseClass() }} {{ className() }}"
8425
+ role="listbox"
8426
+ [attr.aria-label]="label() || null"
8427
+ [attr.tabindex]="navigation() === 'active-descendant' ? -1 : null"
8428
+ [attr.aria-activedescendant]="activeId()"
8429
+ [attr.hidden]="hidden() ? '' : null"
8430
+ (keydown)="onKeydown($event)"
8431
+ ><ng-content /></div>`,
8432
+ host: { style: "display: contents" },
8433
+ changeDetection: ChangeDetectionStrategy.OnPush,
8434
+ }]
8435
+ }], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], className: [{ type: i0.Input, args: [{ isSignal: true, alias: "className", required: false }] }], baseClass: [{ type: i0.Input, args: [{ isSignal: true, alias: "baseClass", required: false }] }], elementId: [{ type: i0.Input, args: [{ isSignal: true, alias: "elementId", required: false }] }], hidden: [{ type: i0.Input, args: [{ isSignal: true, alias: "hidden", required: false }] }], navigation: [{ type: i0.Input, args: [{ isSignal: true, alias: "navigation", required: false }] }], clamp: [{ type: i0.Input, args: [{ isSignal: true, alias: "clamp", required: false }] }], typeahead: [{ type: i0.Input, args: [{ isSignal: true, alias: "typeahead", required: false }] }], pageSize: [{ type: i0.Input, args: [{ isSignal: true, alias: "pageSize", required: false }] }], activeIndex: [{ type: i0.Input, args: [{ isSignal: true, alias: "activeIndex", required: false }] }, { type: i0.Output, args: ["activeIndexChange"] }], activate: [{ type: i0.Output, args: ["activate"] }], escape: [{ type: i0.Output, args: ["escape"] }], tabOut: [{ type: i0.Output, args: ["tabOut"] }], rootRef: [{
8436
+ type: ViewChild,
8437
+ args: ["root"]
8438
+ }] } });
8196
8439
 
8197
8440
  /**
8198
8441
  * Loading — a loading indicator, such as text, or image, or animation