@ethlete/components 0.1.0-next.12 → 0.1.0-next.14

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.
@@ -46,8 +46,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
46
46
 
47
47
  class FocusRingDirective {
48
48
  constructor() {
49
- this.disabled = input(false, { ...(ngDevMode ? { debugName: "disabled" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
50
49
  this.styleManager = injectStyleManager();
50
+ this.disabled = input(false, { ...(ngDevMode ? { debugName: "disabled" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
51
51
  this.active = signal(false, /* @ts-ignore */
52
52
  ...(ngDevMode ? [{ debugName: "active" }] : /* istanbul ignore next */ []));
53
53
  effect(() => {
@@ -1411,6 +1411,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
1411
1411
 
1412
1412
  class ChoiceFieldComponent {
1413
1413
  constructor() {
1414
+ this.support = injectFormSupport();
1414
1415
  this.errorContentRef = viewChild('errorContent', /* @ts-ignore */
1415
1416
  ...(ngDevMode ? [{ debugName: "errorContentRef" }] : /* istanbul ignore next */ []));
1416
1417
  this.hintContentRef = viewChild('hintContent', /* @ts-ignore */
@@ -1419,7 +1420,6 @@ class ChoiceFieldComponent {
1419
1420
  ...(ngDevMode ? [{ debugName: "errorAnimatableRef" }] : /* istanbul ignore next */ []));
1420
1421
  this.hintAnimatableRef = viewChild('hintAnimatable', /* @ts-ignore */
1421
1422
  ...(ngDevMode ? [{ debugName: "hintAnimatableRef" }] : /* istanbul ignore next */ []));
1422
- this.support = injectFormSupport();
1423
1423
  this.canAnimate = createCanAnimateSignal();
1424
1424
  effect(() => {
1425
1425
  this.support.errorContent.set(this.errorContentRef());
@@ -1583,6 +1583,8 @@ class FormFieldComponent {
1583
1583
  this.provideSurface = inject(ProvideSurfaceDirective);
1584
1584
  this.parentSurfaceProvider = inject(SURFACE_PROVIDER, { optional: true, skipSelf: true });
1585
1585
  this.formFieldDir = inject(FormFieldDirective);
1586
+ this.errorColorTheme = injectErrorTheme();
1587
+ this.surfaceThemes = injectSurfaceThemes({ optional: true });
1586
1588
  this.appearance = input(FORM_FIELD_APPEARANCES.BOX, /* @ts-ignore */
1587
1589
  ...(ngDevMode ? [{ debugName: "appearance" }] : /* istanbul ignore next */ []));
1588
1590
  this.fill = input(FORM_FIELD_FILLS.TRANSPARENT, /* @ts-ignore */
@@ -1601,8 +1603,6 @@ class FormFieldComponent {
1601
1603
  ...(ngDevMode ? [{ debugName: "errorAnimatable" }] : /* istanbul ignore next */ []));
1602
1604
  this.hintAnimatable = viewChild('hintAnimatable', /* @ts-ignore */
1603
1605
  ...(ngDevMode ? [{ debugName: "hintAnimatable" }] : /* istanbul ignore next */ []));
1604
- this.errorColorTheme = injectErrorTheme();
1605
- this.surfaceThemes = injectSurfaceThemes({ optional: true });
1606
1606
  this.errorDimensions = signalElementDimensions(this.errorContent);
1607
1607
  this.hintDimensions = signalElementDimensions(this.hintContent);
1608
1608
  this.prefixDimensions = signalElementDimensions(this.prefixEl);
@@ -1959,6 +1959,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
1959
1959
 
1960
1960
  const INPUT_IMPORTS = [InputComponent, InputDirective];
1961
1961
 
1962
+ const HEADING_SELECTOR = 'h1, h2, h3, h4, h5, h6';
1962
1963
  const richTextEditorDomFactory = () => {
1963
1964
  const renderer = injectRenderer();
1964
1965
  const doc = inject(DOCUMENT);
@@ -2366,6 +2367,7 @@ const richTextEditorDomFactory = () => {
2366
2367
  return null;
2367
2368
  }
2368
2369
  const node = resolveStartNode(editable.range);
2370
+ const headingEl = closestWithin(node, HEADING_SELECTOR);
2369
2371
  return {
2370
2372
  bold: !!closestWithin(node, 'strong'),
2371
2373
  italic: !!closestWithin(node, 'em'),
@@ -2373,6 +2375,7 @@ const richTextEditorDomFactory = () => {
2373
2375
  unorderedList: !!closestWithin(node, 'ul'),
2374
2376
  orderedList: !!closestWithin(node, 'ol'),
2375
2377
  link: !!closestWithin(node, 'a'),
2378
+ heading: headingEl ? Number(headingEl.tagName[1]) : null,
2376
2379
  };
2377
2380
  };
2378
2381
  // wrapInline's surroundContents fallback can leave behind an untouched sibling with the same
@@ -2544,6 +2547,70 @@ const richTextEditorDomFactory = () => {
2544
2547
  selectNodeContents(list);
2545
2548
  el.normalize();
2546
2549
  };
2550
+ // Re-tag a block-level element in place, carrying its children (including any inline marks)
2551
+ // into the new element. Used to turn a paragraph into a heading and back.
2552
+ const replaceBlockTag = (block, tag) => {
2553
+ const replacement = renderer.createElement(tag);
2554
+ while (block.firstChild) {
2555
+ renderer.appendChild(replacement, block.firstChild);
2556
+ }
2557
+ replaceWith(block, [replacement]);
2558
+ return replacement;
2559
+ };
2560
+ const toggleHeading = (tag) => {
2561
+ const editable = getSelection();
2562
+ const el = root();
2563
+ if (!el || !editable) {
2564
+ return;
2565
+ }
2566
+ const blocks = blocksInRange(editable.range);
2567
+ // An empty editor has no block to convert — start a fresh heading with an empty line box so
2568
+ // the caret has somewhere to land, mirroring toggleList's empty-editor branch.
2569
+ if (blocks.length === 0) {
2570
+ const heading = renderer.createElement(tag);
2571
+ renderer.appendChild(heading, renderer.createElement('br'));
2572
+ renderer.appendChild(el, heading);
2573
+ collapseInto(heading, 0);
2574
+ return;
2575
+ }
2576
+ const produced = [];
2577
+ blocks.forEach((block) => {
2578
+ // A heading cannot contain list items, so leave lists untouched — the heading button is a
2579
+ // no-op over a selected list rather than producing invalid markup.
2580
+ if (block instanceof HTMLElement && (block.tagName === 'UL' || block.tagName === 'OL')) {
2581
+ produced.push(block);
2582
+ return;
2583
+ }
2584
+ if (block instanceof HTMLElement && block.matches(HEADING_SELECTOR)) {
2585
+ // Same level toggles back to a paragraph; a different level re-levels the heading.
2586
+ produced.push(replaceBlockTag(block, block.tagName.toLowerCase() === tag ? 'p' : tag));
2587
+ return;
2588
+ }
2589
+ if (block instanceof HTMLElement) {
2590
+ produced.push(replaceBlockTag(block, tag));
2591
+ return;
2592
+ }
2593
+ // A bare text node (or <br>) sitting directly under the root has no wrapping block — move it
2594
+ // into a fresh heading in the same position.
2595
+ const heading = renderer.createElement(tag);
2596
+ const ref = block.nextSibling;
2597
+ renderer.removeChild(el, block);
2598
+ renderer.appendChild(heading, block);
2599
+ renderer.insertBefore(el, heading, ref);
2600
+ produced.push(heading);
2601
+ });
2602
+ const first = produced[0];
2603
+ const last = produced[produced.length - 1];
2604
+ if (first && last) {
2605
+ if (first === last) {
2606
+ selectNodeContents(first);
2607
+ }
2608
+ else {
2609
+ selectAcross(first, last);
2610
+ }
2611
+ }
2612
+ el.normalize();
2613
+ };
2547
2614
  const applyLink = (href) => {
2548
2615
  const editable = getSelection();
2549
2616
  if (!editable) {
@@ -2627,6 +2694,7 @@ const richTextEditorDomFactory = () => {
2627
2694
  markStates,
2628
2695
  toggleInline,
2629
2696
  toggleList,
2697
+ toggleHeading,
2630
2698
  applyLink,
2631
2699
  removeLink,
2632
2700
  insertToken,
@@ -2642,6 +2710,8 @@ class RichTextEditorDirective {
2642
2710
  this.formField = inject(FORM_FIELD_TOKEN, { optional: true });
2643
2711
  this.destroyRef = inject(DestroyRef);
2644
2712
  this.document = inject(DOCUMENT);
2713
+ /** @internal */
2714
+ this.editorDom = injectRichTextEditorDom();
2645
2715
  this.value = model('', /* @ts-ignore */
2646
2716
  ...(ngDevMode ? [{ debugName: "value" }] : /* istanbul ignore next */ []));
2647
2717
  this.touched = model(false, /* @ts-ignore */
@@ -2688,10 +2758,10 @@ class RichTextEditorDirective {
2688
2758
  ...(ngDevMode ? [{ debugName: "orderedListActive" }] : /* istanbul ignore next */ []));
2689
2759
  this.linkActive = signal(false, /* @ts-ignore */
2690
2760
  ...(ngDevMode ? [{ debugName: "linkActive" }] : /* istanbul ignore next */ []));
2761
+ this.headingLevel = signal(null, /* @ts-ignore */
2762
+ ...(ngDevMode ? [{ debugName: "headingLevel" }] : /* istanbul ignore next */ []));
2691
2763
  /** @internal */
2692
2764
  this.lastEmittedMarkdown = null;
2693
- /** @internal */
2694
- this.editorDom = injectRichTextEditorDom();
2695
2765
  this.formField?.registerControl(this);
2696
2766
  this.destroyRef.onDestroy(() => this.formField?.unregisterControl(this));
2697
2767
  }
@@ -2722,6 +2792,7 @@ class RichTextEditorDirective {
2722
2792
  this.unorderedListActive.set(states?.unorderedList ?? false);
2723
2793
  this.orderedListActive.set(states?.orderedList ?? false);
2724
2794
  this.linkActive.set(states?.link ?? false);
2795
+ this.headingLevel.set(states?.heading ?? null);
2725
2796
  }
2726
2797
  toggleBold() {
2727
2798
  this.runCommand(() => this.editorDom.toggleInline('strong'));
@@ -2738,6 +2809,9 @@ class RichTextEditorDirective {
2738
2809
  toggleOrderedList() {
2739
2810
  this.runCommand(() => this.editorDom.toggleList('ol'));
2740
2811
  }
2812
+ toggleHeading(level) {
2813
+ this.runCommand(() => this.editorDom.toggleHeading(`h${level}`));
2814
+ }
2741
2815
  setLink(href) {
2742
2816
  const url = href.trim();
2743
2817
  this.runCommand(() => (url ? this.editorDom.applyLink(url) : this.editorDom.removeLink()));
@@ -2950,6 +3024,36 @@ const GRID_2X2_ICON = {
2950
3024
  `,
2951
3025
  };
2952
3026
 
3027
+ // Custom icon.
3028
+ const HEADING_1_ICON = {
3029
+ name: 'et-heading-1',
3030
+ data: `
3031
+ <svg width="100%" height="100%" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">
3032
+ <text x="8" y="12" font-size="11" font-weight="700" text-anchor="middle" fill="currentColor">H1</text>
3033
+ </svg>
3034
+ `,
3035
+ };
3036
+
3037
+ // Custom icon.
3038
+ const HEADING_2_ICON = {
3039
+ name: 'et-heading-2',
3040
+ data: `
3041
+ <svg width="100%" height="100%" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">
3042
+ <text x="8" y="12" font-size="11" font-weight="700" text-anchor="middle" fill="currentColor">H2</text>
3043
+ </svg>
3044
+ `,
3045
+ };
3046
+
3047
+ // Custom icon.
3048
+ const HEADING_3_ICON = {
3049
+ name: 'et-heading-3',
3050
+ data: `
3051
+ <svg width="100%" height="100%" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">
3052
+ <text x="8" y="12" font-size="11" font-weight="700" text-anchor="middle" fill="currentColor">H3</text>
3053
+ </svg>
3054
+ `,
3055
+ };
3056
+
2953
3057
  const ICON_ERROR_CODES = {
2954
3058
  NO_ICONS_PROVIDED: 1800,
2955
3059
  ICON_NOT_FOUND: 1801,
@@ -3230,7 +3334,7 @@ class RichTextEditorFloatingToolbarComponent {
3230
3334
  this.renderer.listen(root, 'pointerdown', () => (this.pointerSelectingInContent = true)),
3231
3335
  this.renderer.listen(root, 'keyup', () => this.evaluate()),
3232
3336
  this.renderer.listen(root, 'blur', () => this.hide()),
3233
- this.renderer.listen(this.document, 'pointerup', () => this.onDocumentPointerUp()),
3337
+ this.renderer.listen(this.document, 'pointerup', () => this.finishContentPointerSelection()),
3234
3338
  this.renderer.listen(this.document, 'selectionchange', () => this.reposition()),
3235
3339
  ];
3236
3340
  onCleanup(() => listeners.forEach((off) => off()));
@@ -3242,7 +3346,7 @@ class RichTextEditorFloatingToolbarComponent {
3242
3346
  const usable = !!range && !range.collapsed && this.dir.focused() && !this.dir.disabled() && !this.dir.readonly();
3243
3347
  return usable ? range : null;
3244
3348
  }
3245
- onDocumentPointerUp() {
3349
+ finishContentPointerSelection() {
3246
3350
  if (!this.pointerSelectingInContent)
3247
3351
  return;
3248
3352
  this.pointerSelectingInContent = false;
@@ -3341,17 +3445,17 @@ class RichTextEditorComponent {
3341
3445
  this.renderExternalValue(markdown);
3342
3446
  });
3343
3447
  }
3344
- onInput() {
3448
+ syncValueFromDom() {
3345
3449
  this.dir.syncFromDom();
3346
3450
  }
3347
- onKeydown(event) {
3451
+ interceptBackspaceKey(event) {
3348
3452
  if (event.key !== 'Backspace')
3349
3453
  return;
3350
3454
  if (this.dir.handleBackspace()) {
3351
3455
  event.preventDefault();
3352
3456
  }
3353
3457
  }
3354
- onBeforeInput(event) {
3458
+ interceptFormattingCommand(event) {
3355
3459
  // Keep keyboard shortcuts (Ctrl/Cmd+B, …) running through our Selection/Range commands
3356
3460
  // instead of the browser's deprecated execCommand-backed formatting.
3357
3461
  switch (event.inputType) {
@@ -3378,13 +3482,13 @@ class RichTextEditorComponent {
3378
3482
  }
3379
3483
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: RichTextEditorComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
3380
3484
  static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.2.0", version: "22.0.5", type: RichTextEditorComponent, isStandalone: true, selector: "et-rich-text-editor", host: { listeners: { "click": "dir.activate()" }, classAttribute: "et-rich-text-editor" }, providers: [
3381
- provideIcons(BOLD_ICON, ITALIC_ICON, STRIKETHROUGH_ICON, LIST_BULLETED_ICON, LIST_NUMBERED_ICON, LINK_ICON),
3382
- ], viewQueries: [{ propertyName: "editable", first: true, predicate: ["editable"], descendants: true, isSignal: true }], hostDirectives: [{ directive: RichTextEditorDirective, inputs: ["value", "value", "disabled", "disabled", "readonly", "readonly", "hidden", "hidden", "invalid", "invalid", "errors", "errors", "required", "required", "name", "name", "placeholder", "placeholder"], outputs: ["valueChange", "valueChange", "touchedChange", "touchedChange"] }], ngImport: i0, template: "<div class=\"et-rte-toolbar\" role=\"toolbar\" aria-label=\"Text formatting\">\n <button\n [pressed]=\"dir.boldActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleBold()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Bold\"\n >\n <i etIcon=\"et-bold\"></i>\n </button>\n\n <button\n [pressed]=\"dir.italicActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleItalic()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Italic\"\n >\n <i etIcon=\"et-italic\"></i>\n </button>\n\n <button\n [pressed]=\"dir.strikeActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleStrikethrough()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Strikethrough\"\n >\n <i etIcon=\"et-strikethrough\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.unorderedListActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleUnorderedList()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Bulleted list\"\n >\n <i etIcon=\"et-list-bulleted\"></i>\n </button>\n\n <button\n [pressed]=\"dir.orderedListActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleOrderedList()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Numbered list\"\n >\n <i etIcon=\"et-list-numbered\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.linkActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.promptForLink()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Link\"\n >\n <i [allowHardcodedColor]=\"true\" etIcon=\"et-link\"></i>\n </button>\n</div>\n\n<div\n #editable\n [attr.contenteditable]=\"dir.disabled() || dir.readonly() ? 'false' : 'true'\"\n [attr.tabindex]=\"dir.disabled() ? -1 : 0\"\n [attr.data-placeholder]=\"dir.placeholder() || null\"\n [attr.aria-invalid]=\"dir.shouldDisplayError() || null\"\n [attr.aria-describedby]=\"dir.describedById() || null\"\n [attr.aria-labelledby]=\"dir.labelId() || null\"\n [attr.aria-disabled]=\"dir.disabled() || null\"\n [attr.aria-readonly]=\"dir.readonly() || null\"\n (input)=\"onInput()\"\n (beforeinput)=\"onBeforeInput($event)\"\n (keydown)=\"onKeydown($event)\"\n (focus)=\"dir.focused.set(true)\"\n (blur)=\"dir.focused.set(false); dir.touched.set(true)\"\n class=\"et-rte-content\"\n role=\"textbox\"\n aria-multiline=\"true\"\n></div>\n\n<et-rich-text-editor-floating-toolbar />\n", styles: ["@property --et-rich-text-editor-toolbar-gap{syntax: \"<length>\"; inherits: true; initial-value: 2px;}@property --et-rich-text-editor-toolbar-padding{syntax: \"<length>\"; inherits: true; initial-value: 4px;}@property --et-rich-text-editor-button-radius{syntax: \"<length>\"; inherits: true; initial-value: 4px;}@property --et-rich-text-editor-min-height{syntax: \"<length>\"; inherits: true; initial-value: 96px;}@property --et-rich-text-editor-content-gap{syntax: \"<length>\"; inherits: true; initial-value: 8px;}et-rich-text-editor{display:flex;flex:1;flex-direction:column;min-inline-size:0;color:inherit}et-rich-text-editor .et-rte-toolbar{display:flex;align-items:center;gap:var(--et-rich-text-editor-toolbar-gap);padding:var(--et-rich-text-editor-toolbar-padding);padding-inline:calc(var(--et-form-field-control-padding-inline) - var(--et-rich-text-editor-toolbar-padding));border-block-end:var(--et-form-field-control-border-width, 1px) solid color-mix(in srgb,currentColor 12%,transparent)}et-rich-text-editor .et-rte-toolbar .et-icon-button{border-radius:var(--et-rich-text-editor-button-radius)}et-rich-text-editor .et-rte-toolbar-divider{inline-size:1px;align-self:stretch;margin-block:4px;margin-inline:2px;background:color-mix(in srgb,currentColor 12%,transparent)}et-rich-text-editor .et-rte-content{display:block;flex:1;min-inline-size:0;padding-block:var(--et-form-field-control-padding-block);padding-inline:var(--et-form-field-control-padding-inline);min-block-size:var(--et-rich-text-editor-min-height);outline:none;color:inherit;caret-color:var(--et-theme-color-primary-solid, currentColor);overflow-wrap:anywhere}et-rich-text-editor .et-rte-content:empty:before{content:attr(data-placeholder);color:color-mix(in srgb,currentColor 46%,transparent);pointer-events:none}et-rich-text-editor .et-rte-content>:first-child{margin-block-start:0}et-rich-text-editor .et-rte-content>:last-child{margin-block-end:0}et-rich-text-editor .et-rte-content p{margin-block:0}et-rich-text-editor .et-rte-content p+p,et-rich-text-editor .et-rte-content ul,et-rich-text-editor .et-rte-content ol{margin-block-start:var(--et-rich-text-editor-content-gap)}et-rich-text-editor .et-rte-content ul,et-rich-text-editor .et-rte-content ol{margin-block-end:0;padding-inline-start:1.5em;list-style-position:outside}et-rich-text-editor .et-rte-content ul{list-style-type:disc}et-rich-text-editor .et-rte-content ol{list-style-type:decimal}et-rich-text-editor .et-rte-content li{margin-block:0}et-rich-text-editor .et-rte-content li::marker{color:color-mix(in srgb,currentColor 60%,transparent)}et-rich-text-editor .et-rte-content a{color:var(--et-theme-color-primary-solid, currentColor);text-decoration:underline}\n"], dependencies: [{ kind: "component", type: IconButtonComponent, selector: "[et-icon-button]", inputs: ["variant", "size"] }, { kind: "directive", type: IconDirective, selector: "[etIcon]", inputs: ["etIcon", "allowHardcodedColor"] }, { kind: "component", type: RichTextEditorFloatingToolbarComponent, selector: "et-rich-text-editor-floating-toolbar" }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
3485
+ provideIcons(BOLD_ICON, ITALIC_ICON, STRIKETHROUGH_ICON, HEADING_1_ICON, HEADING_2_ICON, HEADING_3_ICON, LIST_BULLETED_ICON, LIST_NUMBERED_ICON, LINK_ICON),
3486
+ ], viewQueries: [{ propertyName: "editable", first: true, predicate: ["editable"], descendants: true, isSignal: true }], hostDirectives: [{ directive: RichTextEditorDirective, inputs: ["value", "value", "disabled", "disabled", "readonly", "readonly", "hidden", "hidden", "invalid", "invalid", "errors", "errors", "required", "required", "name", "name", "placeholder", "placeholder"], outputs: ["valueChange", "valueChange", "touchedChange", "touchedChange"] }], ngImport: i0, template: "<div class=\"et-rte-toolbar\" role=\"toolbar\" aria-label=\"Text formatting\">\n <button\n [pressed]=\"dir.boldActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleBold()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Bold\"\n >\n <i etIcon=\"et-bold\"></i>\n </button>\n\n <button\n [pressed]=\"dir.italicActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleItalic()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Italic\"\n >\n <i etIcon=\"et-italic\"></i>\n </button>\n\n <button\n [pressed]=\"dir.strikeActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleStrikethrough()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Strikethrough\"\n >\n <i etIcon=\"et-strikethrough\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.headingLevel() === 1\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleHeading(1)\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Heading 1\"\n >\n <i etIcon=\"et-heading-1\"></i>\n </button>\n\n <button\n [pressed]=\"dir.headingLevel() === 2\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleHeading(2)\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Heading 2\"\n >\n <i etIcon=\"et-heading-2\"></i>\n </button>\n\n <button\n [pressed]=\"dir.headingLevel() === 3\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleHeading(3)\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Heading 3\"\n >\n <i etIcon=\"et-heading-3\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.unorderedListActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleUnorderedList()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Bulleted list\"\n >\n <i etIcon=\"et-list-bulleted\"></i>\n </button>\n\n <button\n [pressed]=\"dir.orderedListActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleOrderedList()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Numbered list\"\n >\n <i etIcon=\"et-list-numbered\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.linkActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.promptForLink()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Link\"\n >\n <i [allowHardcodedColor]=\"true\" etIcon=\"et-link\"></i>\n </button>\n</div>\n\n<div\n #editable\n [attr.contenteditable]=\"dir.disabled() || dir.readonly() ? 'false' : 'true'\"\n [attr.tabindex]=\"dir.disabled() ? -1 : 0\"\n [attr.data-placeholder]=\"dir.placeholder() || null\"\n [attr.aria-invalid]=\"dir.shouldDisplayError() || null\"\n [attr.aria-describedby]=\"dir.describedById() || null\"\n [attr.aria-labelledby]=\"dir.labelId() || null\"\n [attr.aria-disabled]=\"dir.disabled() || null\"\n [attr.aria-readonly]=\"dir.readonly() || null\"\n (input)=\"syncValueFromDom()\"\n (beforeinput)=\"interceptFormattingCommand($event)\"\n (keydown)=\"interceptBackspaceKey($event)\"\n (focus)=\"dir.focused.set(true)\"\n (blur)=\"dir.focused.set(false); dir.touched.set(true)\"\n class=\"et-rte-content\"\n role=\"textbox\"\n aria-multiline=\"true\"\n></div>\n\n<et-rich-text-editor-floating-toolbar />\n", styles: ["@property --et-rich-text-editor-toolbar-gap{syntax: \"<length>\"; inherits: true; initial-value: 2px;}@property --et-rich-text-editor-toolbar-padding{syntax: \"<length>\"; inherits: true; initial-value: 4px;}@property --et-rich-text-editor-button-radius{syntax: \"<length>\"; inherits: true; initial-value: 4px;}@property --et-rich-text-editor-min-height{syntax: \"<length>\"; inherits: true; initial-value: 96px;}@property --et-rich-text-editor-content-gap{syntax: \"<length>\"; inherits: true; initial-value: 8px;}et-rich-text-editor{display:flex;flex:1;flex-direction:column;min-inline-size:0;color:inherit}et-rich-text-editor .et-rte-toolbar{display:flex;flex-wrap:wrap;align-items:center;gap:var(--et-rich-text-editor-toolbar-gap);padding:var(--et-rich-text-editor-toolbar-padding);padding-inline:calc(var(--et-form-field-control-padding-inline) - var(--et-rich-text-editor-toolbar-padding));border-block-end:var(--et-form-field-control-border-width, 1px) solid color-mix(in srgb,currentColor 12%,transparent)}et-rich-text-editor .et-rte-toolbar .et-icon-button{border-radius:var(--et-rich-text-editor-button-radius)}et-rich-text-editor .et-rte-toolbar-divider{inline-size:1px;align-self:stretch;margin-block:4px;margin-inline:2px;background:color-mix(in srgb,currentColor 12%,transparent)}et-rich-text-editor .et-rte-content{display:block;flex:1;min-inline-size:0;padding-block:var(--et-form-field-control-padding-block);padding-inline:var(--et-form-field-control-padding-inline);min-block-size:var(--et-rich-text-editor-min-height);outline:none;color:inherit;caret-color:var(--et-theme-color-primary-solid, currentColor);overflow-wrap:anywhere}et-rich-text-editor .et-rte-content:empty:before{content:attr(data-placeholder);color:color-mix(in srgb,currentColor 46%,transparent);pointer-events:none}et-rich-text-editor .et-rte-content>:first-child{margin-block-start:0}et-rich-text-editor .et-rte-content>:last-child{margin-block-end:0}et-rich-text-editor .et-rte-content p{margin-block:0}et-rich-text-editor .et-rte-content p+p,et-rich-text-editor .et-rte-content ul,et-rich-text-editor .et-rte-content ol{margin-block-start:var(--et-rich-text-editor-content-gap)}et-rich-text-editor .et-rte-content h1,et-rich-text-editor .et-rte-content h2,et-rich-text-editor .et-rte-content h3,et-rich-text-editor .et-rte-content h4,et-rich-text-editor .et-rte-content h5,et-rich-text-editor .et-rte-content h6{margin-block:0;font-weight:700;line-height:1.25}et-rich-text-editor .et-rte-content :is(h1,h2,h3,h4,h5,h6)+*,et-rich-text-editor .et-rte-content *+:is(h1,h2,h3,h4,h5,h6){margin-block-start:var(--et-rich-text-editor-content-gap)}et-rich-text-editor .et-rte-content h1{font-size:2.4rem}et-rich-text-editor .et-rte-content h2{font-size:2rem}et-rich-text-editor .et-rte-content h3{font-size:1.6rem}et-rich-text-editor .et-rte-content ul,et-rich-text-editor .et-rte-content ol{margin-block-end:0;padding-inline-start:1.5em;list-style-position:outside}et-rich-text-editor .et-rte-content ul{list-style-type:disc}et-rich-text-editor .et-rte-content ol{list-style-type:decimal}et-rich-text-editor .et-rte-content li{margin-block:0}et-rich-text-editor .et-rte-content li::marker{color:color-mix(in srgb,currentColor 60%,transparent)}et-rich-text-editor .et-rte-content a{color:var(--et-theme-color-primary-solid, currentColor);text-decoration:underline}\n"], dependencies: [{ kind: "component", type: IconButtonComponent, selector: "[et-icon-button]", inputs: ["variant", "size"] }, { kind: "directive", type: IconDirective, selector: "[etIcon]", inputs: ["etIcon", "allowHardcodedColor"] }, { kind: "component", type: RichTextEditorFloatingToolbarComponent, selector: "et-rich-text-editor-floating-toolbar" }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
3383
3487
  }
3384
3488
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: RichTextEditorComponent, decorators: [{
3385
3489
  type: Component,
3386
3490
  args: [{ selector: 'et-rich-text-editor', encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.OnPush, imports: [IconButtonComponent, IconDirective, RichTextEditorFloatingToolbarComponent], providers: [
3387
- provideIcons(BOLD_ICON, ITALIC_ICON, STRIKETHROUGH_ICON, LIST_BULLETED_ICON, LIST_NUMBERED_ICON, LINK_ICON),
3491
+ provideIcons(BOLD_ICON, ITALIC_ICON, STRIKETHROUGH_ICON, HEADING_1_ICON, HEADING_2_ICON, HEADING_3_ICON, LIST_BULLETED_ICON, LIST_NUMBERED_ICON, LINK_ICON),
3388
3492
  ], hostDirectives: [
3389
3493
  {
3390
3494
  directive: RichTextEditorDirective,
@@ -3394,7 +3498,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
3394
3498
  ], host: {
3395
3499
  class: 'et-rich-text-editor',
3396
3500
  '(click)': 'dir.activate()',
3397
- }, template: "<div class=\"et-rte-toolbar\" role=\"toolbar\" aria-label=\"Text formatting\">\n <button\n [pressed]=\"dir.boldActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleBold()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Bold\"\n >\n <i etIcon=\"et-bold\"></i>\n </button>\n\n <button\n [pressed]=\"dir.italicActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleItalic()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Italic\"\n >\n <i etIcon=\"et-italic\"></i>\n </button>\n\n <button\n [pressed]=\"dir.strikeActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleStrikethrough()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Strikethrough\"\n >\n <i etIcon=\"et-strikethrough\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.unorderedListActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleUnorderedList()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Bulleted list\"\n >\n <i etIcon=\"et-list-bulleted\"></i>\n </button>\n\n <button\n [pressed]=\"dir.orderedListActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleOrderedList()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Numbered list\"\n >\n <i etIcon=\"et-list-numbered\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.linkActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.promptForLink()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Link\"\n >\n <i [allowHardcodedColor]=\"true\" etIcon=\"et-link\"></i>\n </button>\n</div>\n\n<div\n #editable\n [attr.contenteditable]=\"dir.disabled() || dir.readonly() ? 'false' : 'true'\"\n [attr.tabindex]=\"dir.disabled() ? -1 : 0\"\n [attr.data-placeholder]=\"dir.placeholder() || null\"\n [attr.aria-invalid]=\"dir.shouldDisplayError() || null\"\n [attr.aria-describedby]=\"dir.describedById() || null\"\n [attr.aria-labelledby]=\"dir.labelId() || null\"\n [attr.aria-disabled]=\"dir.disabled() || null\"\n [attr.aria-readonly]=\"dir.readonly() || null\"\n (input)=\"onInput()\"\n (beforeinput)=\"onBeforeInput($event)\"\n (keydown)=\"onKeydown($event)\"\n (focus)=\"dir.focused.set(true)\"\n (blur)=\"dir.focused.set(false); dir.touched.set(true)\"\n class=\"et-rte-content\"\n role=\"textbox\"\n aria-multiline=\"true\"\n></div>\n\n<et-rich-text-editor-floating-toolbar />\n", styles: ["@property --et-rich-text-editor-toolbar-gap{syntax: \"<length>\"; inherits: true; initial-value: 2px;}@property --et-rich-text-editor-toolbar-padding{syntax: \"<length>\"; inherits: true; initial-value: 4px;}@property --et-rich-text-editor-button-radius{syntax: \"<length>\"; inherits: true; initial-value: 4px;}@property --et-rich-text-editor-min-height{syntax: \"<length>\"; inherits: true; initial-value: 96px;}@property --et-rich-text-editor-content-gap{syntax: \"<length>\"; inherits: true; initial-value: 8px;}et-rich-text-editor{display:flex;flex:1;flex-direction:column;min-inline-size:0;color:inherit}et-rich-text-editor .et-rte-toolbar{display:flex;align-items:center;gap:var(--et-rich-text-editor-toolbar-gap);padding:var(--et-rich-text-editor-toolbar-padding);padding-inline:calc(var(--et-form-field-control-padding-inline) - var(--et-rich-text-editor-toolbar-padding));border-block-end:var(--et-form-field-control-border-width, 1px) solid color-mix(in srgb,currentColor 12%,transparent)}et-rich-text-editor .et-rte-toolbar .et-icon-button{border-radius:var(--et-rich-text-editor-button-radius)}et-rich-text-editor .et-rte-toolbar-divider{inline-size:1px;align-self:stretch;margin-block:4px;margin-inline:2px;background:color-mix(in srgb,currentColor 12%,transparent)}et-rich-text-editor .et-rte-content{display:block;flex:1;min-inline-size:0;padding-block:var(--et-form-field-control-padding-block);padding-inline:var(--et-form-field-control-padding-inline);min-block-size:var(--et-rich-text-editor-min-height);outline:none;color:inherit;caret-color:var(--et-theme-color-primary-solid, currentColor);overflow-wrap:anywhere}et-rich-text-editor .et-rte-content:empty:before{content:attr(data-placeholder);color:color-mix(in srgb,currentColor 46%,transparent);pointer-events:none}et-rich-text-editor .et-rte-content>:first-child{margin-block-start:0}et-rich-text-editor .et-rte-content>:last-child{margin-block-end:0}et-rich-text-editor .et-rte-content p{margin-block:0}et-rich-text-editor .et-rte-content p+p,et-rich-text-editor .et-rte-content ul,et-rich-text-editor .et-rte-content ol{margin-block-start:var(--et-rich-text-editor-content-gap)}et-rich-text-editor .et-rte-content ul,et-rich-text-editor .et-rte-content ol{margin-block-end:0;padding-inline-start:1.5em;list-style-position:outside}et-rich-text-editor .et-rte-content ul{list-style-type:disc}et-rich-text-editor .et-rte-content ol{list-style-type:decimal}et-rich-text-editor .et-rte-content li{margin-block:0}et-rich-text-editor .et-rte-content li::marker{color:color-mix(in srgb,currentColor 60%,transparent)}et-rich-text-editor .et-rte-content a{color:var(--et-theme-color-primary-solid, currentColor);text-decoration:underline}\n"] }]
3501
+ }, template: "<div class=\"et-rte-toolbar\" role=\"toolbar\" aria-label=\"Text formatting\">\n <button\n [pressed]=\"dir.boldActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleBold()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Bold\"\n >\n <i etIcon=\"et-bold\"></i>\n </button>\n\n <button\n [pressed]=\"dir.italicActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleItalic()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Italic\"\n >\n <i etIcon=\"et-italic\"></i>\n </button>\n\n <button\n [pressed]=\"dir.strikeActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleStrikethrough()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Strikethrough\"\n >\n <i etIcon=\"et-strikethrough\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.headingLevel() === 1\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleHeading(1)\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Heading 1\"\n >\n <i etIcon=\"et-heading-1\"></i>\n </button>\n\n <button\n [pressed]=\"dir.headingLevel() === 2\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleHeading(2)\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Heading 2\"\n >\n <i etIcon=\"et-heading-2\"></i>\n </button>\n\n <button\n [pressed]=\"dir.headingLevel() === 3\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleHeading(3)\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Heading 3\"\n >\n <i etIcon=\"et-heading-3\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.unorderedListActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleUnorderedList()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Bulleted list\"\n >\n <i etIcon=\"et-list-bulleted\"></i>\n </button>\n\n <button\n [pressed]=\"dir.orderedListActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.toggleOrderedList()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Numbered list\"\n >\n <i etIcon=\"et-list-numbered\"></i>\n </button>\n\n <span class=\"et-rte-toolbar-divider\" aria-hidden=\"true\"></span>\n\n <button\n [pressed]=\"dir.linkActive()\"\n [disabled]=\"dir.disabled() || dir.readonly()\"\n (mousedown)=\"$event.preventDefault()\"\n (click)=\"dir.promptForLink()\"\n mutedUntilPressed\n et-icon-button\n size=\"xs\"\n type=\"button\"\n aria-label=\"Link\"\n >\n <i [allowHardcodedColor]=\"true\" etIcon=\"et-link\"></i>\n </button>\n</div>\n\n<div\n #editable\n [attr.contenteditable]=\"dir.disabled() || dir.readonly() ? 'false' : 'true'\"\n [attr.tabindex]=\"dir.disabled() ? -1 : 0\"\n [attr.data-placeholder]=\"dir.placeholder() || null\"\n [attr.aria-invalid]=\"dir.shouldDisplayError() || null\"\n [attr.aria-describedby]=\"dir.describedById() || null\"\n [attr.aria-labelledby]=\"dir.labelId() || null\"\n [attr.aria-disabled]=\"dir.disabled() || null\"\n [attr.aria-readonly]=\"dir.readonly() || null\"\n (input)=\"syncValueFromDom()\"\n (beforeinput)=\"interceptFormattingCommand($event)\"\n (keydown)=\"interceptBackspaceKey($event)\"\n (focus)=\"dir.focused.set(true)\"\n (blur)=\"dir.focused.set(false); dir.touched.set(true)\"\n class=\"et-rte-content\"\n role=\"textbox\"\n aria-multiline=\"true\"\n></div>\n\n<et-rich-text-editor-floating-toolbar />\n", styles: ["@property --et-rich-text-editor-toolbar-gap{syntax: \"<length>\"; inherits: true; initial-value: 2px;}@property --et-rich-text-editor-toolbar-padding{syntax: \"<length>\"; inherits: true; initial-value: 4px;}@property --et-rich-text-editor-button-radius{syntax: \"<length>\"; inherits: true; initial-value: 4px;}@property --et-rich-text-editor-min-height{syntax: \"<length>\"; inherits: true; initial-value: 96px;}@property --et-rich-text-editor-content-gap{syntax: \"<length>\"; inherits: true; initial-value: 8px;}et-rich-text-editor{display:flex;flex:1;flex-direction:column;min-inline-size:0;color:inherit}et-rich-text-editor .et-rte-toolbar{display:flex;flex-wrap:wrap;align-items:center;gap:var(--et-rich-text-editor-toolbar-gap);padding:var(--et-rich-text-editor-toolbar-padding);padding-inline:calc(var(--et-form-field-control-padding-inline) - var(--et-rich-text-editor-toolbar-padding));border-block-end:var(--et-form-field-control-border-width, 1px) solid color-mix(in srgb,currentColor 12%,transparent)}et-rich-text-editor .et-rte-toolbar .et-icon-button{border-radius:var(--et-rich-text-editor-button-radius)}et-rich-text-editor .et-rte-toolbar-divider{inline-size:1px;align-self:stretch;margin-block:4px;margin-inline:2px;background:color-mix(in srgb,currentColor 12%,transparent)}et-rich-text-editor .et-rte-content{display:block;flex:1;min-inline-size:0;padding-block:var(--et-form-field-control-padding-block);padding-inline:var(--et-form-field-control-padding-inline);min-block-size:var(--et-rich-text-editor-min-height);outline:none;color:inherit;caret-color:var(--et-theme-color-primary-solid, currentColor);overflow-wrap:anywhere}et-rich-text-editor .et-rte-content:empty:before{content:attr(data-placeholder);color:color-mix(in srgb,currentColor 46%,transparent);pointer-events:none}et-rich-text-editor .et-rte-content>:first-child{margin-block-start:0}et-rich-text-editor .et-rte-content>:last-child{margin-block-end:0}et-rich-text-editor .et-rte-content p{margin-block:0}et-rich-text-editor .et-rte-content p+p,et-rich-text-editor .et-rte-content ul,et-rich-text-editor .et-rte-content ol{margin-block-start:var(--et-rich-text-editor-content-gap)}et-rich-text-editor .et-rte-content h1,et-rich-text-editor .et-rte-content h2,et-rich-text-editor .et-rte-content h3,et-rich-text-editor .et-rte-content h4,et-rich-text-editor .et-rte-content h5,et-rich-text-editor .et-rte-content h6{margin-block:0;font-weight:700;line-height:1.25}et-rich-text-editor .et-rte-content :is(h1,h2,h3,h4,h5,h6)+*,et-rich-text-editor .et-rte-content *+:is(h1,h2,h3,h4,h5,h6){margin-block-start:var(--et-rich-text-editor-content-gap)}et-rich-text-editor .et-rte-content h1{font-size:2.4rem}et-rich-text-editor .et-rte-content h2{font-size:2rem}et-rich-text-editor .et-rte-content h3{font-size:1.6rem}et-rich-text-editor .et-rte-content ul,et-rich-text-editor .et-rte-content ol{margin-block-end:0;padding-inline-start:1.5em;list-style-position:outside}et-rich-text-editor .et-rte-content ul{list-style-type:disc}et-rich-text-editor .et-rte-content ol{list-style-type:decimal}et-rich-text-editor .et-rte-content li{margin-block:0}et-rich-text-editor .et-rte-content li::marker{color:color-mix(in srgb,currentColor 60%,transparent)}et-rich-text-editor .et-rte-content a{color:var(--et-theme-color-primary-solid, currentColor);text-decoration:underline}\n"] }]
3398
3502
  }], ctorParameters: () => [], propDecorators: { editable: [{ type: i0.ViewChild, args: ['editable', { isSignal: true }] }] } });
3399
3503
 
3400
3504
  const RICH_TEXT_EDITOR_IMPORTS = [RichTextEditorComponent, RichTextEditorDirective];
@@ -3716,6 +3820,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
3716
3820
 
3717
3821
  class CheckboxGroupComponent {
3718
3822
  constructor() {
3823
+ this.support = injectFormSupport();
3719
3824
  this.errorContentRef = viewChild('errorContent', /* @ts-ignore */
3720
3825
  ...(ngDevMode ? [{ debugName: "errorContentRef" }] : /* istanbul ignore next */ []));
3721
3826
  this.hintContentRef = viewChild('hintContent', /* @ts-ignore */
@@ -3724,7 +3829,6 @@ class CheckboxGroupComponent {
3724
3829
  ...(ngDevMode ? [{ debugName: "errorAnimatableRef" }] : /* istanbul ignore next */ []));
3725
3830
  this.hintAnimatableRef = viewChild('hintAnimatable', /* @ts-ignore */
3726
3831
  ...(ngDevMode ? [{ debugName: "hintAnimatableRef" }] : /* istanbul ignore next */ []));
3727
- this.support = injectFormSupport();
3728
3832
  this.canAnimate = createCanAnimateSignal();
3729
3833
  effect(() => {
3730
3834
  this.support.errorContent.set(this.errorContentRef());
@@ -3778,6 +3882,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
3778
3882
 
3779
3883
  class RadioGroupComponent {
3780
3884
  constructor() {
3885
+ this.support = injectFormSupport();
3781
3886
  this.errorContentRef = viewChild('errorContent', /* @ts-ignore */
3782
3887
  ...(ngDevMode ? [{ debugName: "errorContentRef" }] : /* istanbul ignore next */ []));
3783
3888
  this.hintContentRef = viewChild('hintContent', /* @ts-ignore */
@@ -3786,7 +3891,6 @@ class RadioGroupComponent {
3786
3891
  ...(ngDevMode ? [{ debugName: "errorAnimatableRef" }] : /* istanbul ignore next */ []));
3787
3892
  this.hintAnimatableRef = viewChild('hintAnimatable', /* @ts-ignore */
3788
3893
  ...(ngDevMode ? [{ debugName: "hintAnimatableRef" }] : /* istanbul ignore next */ []));
3789
- this.support = injectFormSupport();
3790
3894
  this.canAnimate = createCanAnimateSignal();
3791
3895
  effect(() => {
3792
3896
  this.support.errorContent.set(this.errorContentRef());
@@ -3840,6 +3944,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
3840
3944
 
3841
3945
  class SegmentedButtonGroupComponent {
3842
3946
  constructor() {
3947
+ this.support = injectFormSupport();
3843
3948
  this.errorContentRef = viewChild('errorContent', /* @ts-ignore */
3844
3949
  ...(ngDevMode ? [{ debugName: "errorContentRef" }] : /* istanbul ignore next */ []));
3845
3950
  this.hintContentRef = viewChild('hintContent', /* @ts-ignore */
@@ -3848,7 +3953,6 @@ class SegmentedButtonGroupComponent {
3848
3953
  ...(ngDevMode ? [{ debugName: "errorAnimatableRef" }] : /* istanbul ignore next */ []));
3849
3954
  this.hintAnimatableRef = viewChild('hintAnimatable', /* @ts-ignore */
3850
3955
  ...(ngDevMode ? [{ debugName: "hintAnimatableRef" }] : /* istanbul ignore next */ []));
3851
- this.support = injectFormSupport();
3852
3956
  this.canAnimate = createCanAnimateSignal();
3853
3957
  effect(() => {
3854
3958
  this.support.errorContent.set(this.errorContentRef());
@@ -3995,7 +4099,7 @@ const DEFAULT_GRID_CONFIG = {
3995
4099
  registrations: [],
3996
4100
  interactiveAriaLabel: 'Interactive grid layout',
3997
4101
  readonlyAriaLabel: 'Grid layout',
3998
- dragHandleAriaLabel: 'Drag to reorder',
4102
+ removeActionAriaLabel: 'Remove item',
3999
4103
  transformer: (text) => text,
4000
4104
  };
4001
4105
  const [provideGridConfig, injectGridConfig] = createStaticRootProvider(DEFAULT_GRID_CONFIG, {
@@ -4282,6 +4386,25 @@ const deserializeGridLayout = (state, breakpointMinWidths) => {
4282
4386
  return { breakpoints, items, rowHeight: state.rowHeight };
4283
4387
  };
4284
4388
 
4389
+ const GRID_DEBUG_STORAGE_KEY = 'et-grid-debug';
4390
+ let cachedGridDebug = null;
4391
+ const isGridDebugEnabled = () => {
4392
+ if (cachedGridDebug === null) {
4393
+ try {
4394
+ cachedGridDebug = globalThis.localStorage?.getItem(GRID_DEBUG_STORAGE_KEY) === 'true';
4395
+ }
4396
+ catch {
4397
+ cachedGridDebug = false;
4398
+ }
4399
+ }
4400
+ return cachedGridDebug;
4401
+ };
4402
+ const gridDebug = (...args) => {
4403
+ if (!isGridDebugEnabled())
4404
+ return;
4405
+ const timestamp = (globalThis.performance?.now() ?? 0).toFixed(1);
4406
+ console.log(`\x1B[36m[et-grid ${timestamp}ms]\x1B[m`, ...args);
4407
+ };
4285
4408
  const positionsEqual = (a, b) => a.col === b.col && a.row === b.row && a.colSpan === b.colSpan && a.rowSpan === b.rowSpan;
4286
4409
  const layoutsEqual = (a, b) => {
4287
4410
  const aKeys = Object.keys(a);
@@ -4312,6 +4435,8 @@ const resolveItemConstraints = (id, context) => {
4312
4435
  class GridDirective {
4313
4436
  constructor() {
4314
4437
  this.injector = inject(Injector);
4438
+ this.renderer = injectRenderer();
4439
+ this.gridConfig = injectGridConfig();
4315
4440
  this.breakpoints = input(DEFAULT_BREAKPOINTS, /* @ts-ignore */
4316
4441
  ...(ngDevMode ? [{ debugName: "breakpoints" }] : /* istanbul ignore next */ []));
4317
4442
  this.rowHeight = input(100, /* @ts-ignore */
@@ -4322,7 +4447,6 @@ class GridDirective {
4322
4447
  ...(ngDevMode ? [{ debugName: "initialItems" }] : /* istanbul ignore next */ []));
4323
4448
  this.readOnly = input(false, { ...(ngDevMode ? { debugName: "readOnly" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
4324
4449
  this.layoutChange = output();
4325
- this.gridConfig = injectGridConfig();
4326
4450
  this.registrations = computed(() => this.gridConfig.registrations, /* @ts-ignore */
4327
4451
  ...(ngDevMode ? [{ debugName: "registrations" }] : /* istanbul ignore next */ []));
4328
4452
  this.dimensions = signalHostElementDimensions();
@@ -4336,7 +4460,9 @@ class GridDirective {
4336
4460
  this.resizeBaseLayout = signal(null, /* @ts-ignore */
4337
4461
  ...(ngDevMode ? [{ debugName: "resizeBaseLayout" }] : /* istanbul ignore next */ []));
4338
4462
  this.itemElements = new Map();
4463
+ this.contentElements = new Map();
4339
4464
  this.ghostElement = null;
4465
+ this.lastFlipAt = 0;
4340
4466
  this.rectSnapshot = new Map();
4341
4467
  this.containerWidth = computed(() => this.dimensions().client?.width ?? 0, /* @ts-ignore */
4342
4468
  ...(ngDevMode ? [{ debugName: "containerWidth" }] : /* istanbul ignore next */ []));
@@ -4549,8 +4675,18 @@ class GridDirective {
4549
4675
  }
4550
4676
  unregisterItem(id) {
4551
4677
  this.itemElements.delete(id);
4678
+ this.contentElements.delete(id);
4552
4679
  this.constraintsRegistry.delete(id);
4553
4680
  }
4681
+ /**
4682
+ * The item's inner content wrapper. Used by the counter-scaled resize FLIP so the
4683
+ * box can scale while the content takes the inverse scale and stays undistorted.
4684
+ */
4685
+ registerContentElement(id, el) {
4686
+ if (this.contentElements.get(id) !== el) {
4687
+ this.contentElements.set(id, el);
4688
+ }
4689
+ }
4554
4690
  setGhostElement(el) {
4555
4691
  if (this.ghostElement !== el) {
4556
4692
  this.ghostElement = el;
@@ -4575,51 +4711,116 @@ class GridDirective {
4575
4711
  }
4576
4712
  animateLayoutTransition(options) {
4577
4713
  const excludeIds = options?.excludeIds ?? new Set();
4714
+ const durationMs = options?.durationMs ?? 250;
4578
4715
  const snapshot = new Map(this.rectSnapshot);
4579
4716
  const ghostEl = this.ghostElement;
4717
+ const debug = isGridDebugEnabled();
4718
+ const scheduledAt = debug ? performance.now() : 0;
4580
4719
  afterNextRender(() => {
4720
+ const t0 = debug ? performance.now() : 0;
4721
+ // Phase 1 — read every "from" rect together (no writes in between, so the
4722
+ // browser can serve them from a single layout pass).
4723
+ // - Mid-animation elements: their snapshot (taken a frame earlier) is stale, so
4724
+ // read the actual current on-screen rect and continue from exactly there.
4725
+ // - Otherwise: use the snapshot, which holds the pre-layout-change position.
4726
+ const flips = [];
4581
4727
  for (const [id, el] of this.itemElements) {
4582
4728
  if (excludeIds.has(id))
4583
4729
  continue;
4584
- const oldRect = snapshot.get(id);
4585
- if (!oldRect)
4730
+ const running = el.getAnimations();
4731
+ const fromRect = running.length > 0 ? el.getBoundingClientRect() : snapshot.get(id);
4732
+ if (!fromRect)
4586
4733
  continue;
4587
- const newRect = el.getBoundingClientRect();
4588
- const dx = oldRect.left - newRect.left;
4589
- const dy = oldRect.top - newRect.top;
4590
- const scaleX = oldRect.width / newRect.width;
4591
- const scaleY = oldRect.height / newRect.height;
4592
- const hasMoved = Math.abs(dx) > 1 || Math.abs(dy) > 1;
4593
- const hasResized = Math.abs(scaleX - 1) > 0.01 || Math.abs(scaleY - 1) > 0.01;
4594
- if (!hasMoved && !hasResized)
4595
- continue;
4596
- el.getAnimations().forEach((a) => a.cancel());
4597
- if (hasResized) {
4598
- el.animate([
4599
- { transform: `translate(${dx}px, ${dy}px) scale(${scaleX}, ${scaleY})`, transformOrigin: 'top left' },
4600
- { transform: 'translate(0px, 0px) scale(1, 1)', transformOrigin: 'top left' },
4601
- ], { duration: 250, easing: 'cubic-bezier(0.2, 0, 0, 1)' });
4734
+ flips.push({ el, content: this.contentElements.get(id) ?? null, running, fromRect });
4735
+ }
4736
+ const ghostRunning = ghostEl ? ghostEl.getAnimations() : [];
4737
+ let ghostFrom;
4738
+ if (ghostEl) {
4739
+ ghostFrom = ghostRunning.length > 0 ? ghostEl.getBoundingClientRect() : snapshot.get('__ghost__');
4740
+ }
4741
+ const interrupted = debug ? flips.filter((f) => f.running.length > 0).length : 0;
4742
+ const t1 = debug ? performance.now() : 0;
4743
+ // Phase 2 — cancel all in-flight animations (writes only).
4744
+ for (const flip of flips) {
4745
+ flip.running.forEach((a) => a.cancel());
4746
+ flip.content?.getAnimations().forEach((a) => a.cancel());
4747
+ }
4748
+ ghostRunning.forEach((a) => a.cancel());
4749
+ const t2 = debug ? performance.now() : 0;
4750
+ // Phase 3 — read every target rect together (single layout pass).
4751
+ const targets = flips.map((flip) => flip.el.getBoundingClientRect());
4752
+ const ghostTarget = ghostEl ? ghostEl.getBoundingClientRect() : null;
4753
+ const t3 = debug ? performance.now() : 0;
4754
+ let animated = 0;
4755
+ let maxDx = 0;
4756
+ let maxDy = 0;
4757
+ // Phase 4 — start the animations (writes only).
4758
+ flips.forEach((flip, i) => {
4759
+ const { el, content, fromRect } = flip;
4760
+ const newRect = targets[i];
4761
+ if (!newRect)
4762
+ return;
4763
+ const dx = fromRect.left - newRect.left;
4764
+ const dy = fromRect.top - newRect.top;
4765
+ const scaleX = newRect.width > 0 ? fromRect.width / newRect.width : 1;
4766
+ const scaleY = newRect.height > 0 ? fromRect.height / newRect.height : 1;
4767
+ const moved = Math.abs(dx) > 1 || Math.abs(dy) > 1;
4768
+ const resized = Math.abs(scaleX - 1) > 0.01 || Math.abs(scaleY - 1) > 0.01;
4769
+ if (!moved && !resized)
4770
+ return;
4771
+ if (debug) {
4772
+ animated++;
4773
+ maxDx = Math.max(maxDx, Math.abs(dx));
4774
+ maxDy = Math.max(maxDy, Math.abs(dy));
4775
+ }
4776
+ if (resized) {
4777
+ // Counter-scaled FLIP: the box scales from its old to new size while the
4778
+ // content wrapper takes the inverse scale, so text/children never distort.
4779
+ // Easing is baked into sampled keyframes (played linearly) so the outer and
4780
+ // inner scales multiply to ~1 on every frame, not just at the endpoints.
4781
+ this.animateCounterScaled({ el, content, dx, dy, scaleX, scaleY, durationMs });
4602
4782
  }
4603
4783
  else {
4604
4784
  el.animate([{ transform: `translate(${dx}px, ${dy}px)` }, { transform: 'translate(0px, 0px)' }], {
4605
- duration: 250,
4785
+ duration: durationMs,
4786
+ easing: 'cubic-bezier(0.2, 0, 0, 1)',
4787
+ });
4788
+ }
4789
+ });
4790
+ if (ghostEl && ghostFrom && ghostTarget) {
4791
+ const dx = ghostFrom.left - ghostTarget.left;
4792
+ const dy = ghostFrom.top - ghostTarget.top;
4793
+ if (Math.abs(dx) > 1 || Math.abs(dy) > 1) {
4794
+ ghostEl.animate([{ transform: `translate(${dx}px, ${dy}px)` }, { transform: 'translate(0px, 0px)' }], {
4795
+ duration: 200,
4606
4796
  easing: 'cubic-bezier(0.2, 0, 0, 1)',
4607
4797
  });
4608
4798
  }
4609
4799
  }
4610
- if (ghostEl) {
4611
- const oldRect = snapshot.get('__ghost__');
4612
- if (oldRect) {
4613
- const newRect = ghostEl.getBoundingClientRect();
4614
- const dx = oldRect.left - newRect.left;
4615
- const dy = oldRect.top - newRect.top;
4616
- if (Math.abs(dx) > 1 || Math.abs(dy) > 1) {
4617
- ghostEl.getAnimations().forEach((a) => a.cancel());
4618
- ghostEl.animate([{ transform: `translate(${dx}px, ${dy}px)` }, { transform: 'translate(0px, 0px)' }], {
4619
- duration: 200,
4620
- easing: 'cubic-bezier(0.2, 0, 0, 1)',
4621
- });
4622
- }
4800
+ if (debug) {
4801
+ const t4 = performance.now();
4802
+ const gapSinceLast = this.lastFlipAt ? t0 - this.lastFlipAt : -1;
4803
+ this.lastFlipAt = t0;
4804
+ const round = (n) => Math.round(n * 100) / 100;
4805
+ const info = {
4806
+ items: flips.length,
4807
+ interrupted, // items already mid-animation when this FLIP started
4808
+ animated, // items that actually started a new animation
4809
+ maxDx: round(maxDx),
4810
+ maxDy: round(maxDy),
4811
+ renderDelay: round(t0 - scheduledAt), // schedule → afterNextRender gap
4812
+ readFrom: round(t1 - t0),
4813
+ cancel: round(t2 - t1),
4814
+ readTarget: round(t3 - t2),
4815
+ startAnim: round(t4 - t3),
4816
+ total: round(t4 - t0),
4817
+ gapSinceLast: round(gapSinceLast), // time between consecutive FLIPs
4818
+ };
4819
+ if (info.total > 6 || (gapSinceLast >= 0 && gapSinceLast < 12)) {
4820
+ gridDebug('flip ⚠', info);
4821
+ }
4822
+ else {
4823
+ gridDebug('flip', info);
4623
4824
  }
4624
4825
  }
4625
4826
  }, { injector: this.injector });
@@ -4936,6 +5137,38 @@ class GridDirective {
4936
5137
  emitLayoutChange() {
4937
5138
  this.layoutChange.emit(this.getSerializedState());
4938
5139
  }
5140
+ animateCounterScaled(options) {
5141
+ const { el, content, dx, dy, scaleX, scaleY, durationMs } = options;
5142
+ const steps = 14;
5143
+ const outer = [];
5144
+ const inner = [];
5145
+ for (let i = 0; i <= steps; i++) {
5146
+ const t = i / steps;
5147
+ const eased = 1 - Math.pow(1 - t, 3); // easeOutCubic — matches the translate easing feel
5148
+ const sx = scaleX + (1 - scaleX) * eased;
5149
+ const sy = scaleY + (1 - scaleY) * eased;
5150
+ const tx = dx * (1 - eased);
5151
+ const ty = dy * (1 - eased);
5152
+ outer.push({
5153
+ offset: t,
5154
+ transform: `translate(${tx}px, ${ty}px) scale(${sx}, ${sy})`,
5155
+ transformOrigin: 'top left',
5156
+ });
5157
+ inner.push({ offset: t, transform: `scale(${1 / sx}, ${1 / sy})`, transformOrigin: 'top left' });
5158
+ }
5159
+ // Clip the box for the duration. When the item grows back (scaleX/scaleY < 1) the
5160
+ // content wrapper is counter-scaled UP past the box, and browsers count transformed
5161
+ // descendants in an ancestor's scrollable overflow — so without clipping the content
5162
+ // spills out and flashes scrollbars. overflow:hidden turns it into a clean reveal.
5163
+ // Only counter-scale sets this, and nothing else touches inline overflow, so
5164
+ // restoring to '' (back to the CSS value) on finish/cancel is safe.
5165
+ this.renderer.setStyle(el, { overflow: 'hidden' });
5166
+ const restore = () => this.renderer.removeStyles(el, 'overflow');
5167
+ const outerAnim = el.animate(outer, { duration: durationMs, easing: 'linear' });
5168
+ outerAnim.onfinish = restore;
5169
+ outerAnim.oncancel = restore;
5170
+ content?.animate(inner, { duration: durationMs, easing: 'linear' });
5171
+ }
4939
5172
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
4940
5173
  static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "22.0.5", type: GridDirective, isStandalone: true, selector: "[etGrid]", inputs: { breakpoints: { classPropertyName: "breakpoints", publicName: "breakpoints", isSignal: true, isRequired: false, transformFunction: null }, rowHeight: { classPropertyName: "rowHeight", publicName: "rowHeight", isSignal: true, isRequired: false, transformFunction: null }, gap: { classPropertyName: "gap", publicName: "gap", isSignal: true, isRequired: false, transformFunction: null }, initialItems: { classPropertyName: "initialItems", publicName: "initialItems", isSignal: true, isRequired: false, transformFunction: null }, readOnly: { classPropertyName: "readOnly", publicName: "readOnly", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { layoutChange: "layoutChange" }, host: { properties: { "class.et-grid--readonly": "readOnly()" }, classAttribute: "et-grid" }, providers: [{ provide: GRID_TOKEN, useExisting: GridDirective }], exportAs: ["etGrid"], ngImport: i0 }); }
4941
5174
  }
@@ -5049,6 +5282,8 @@ class GridDragDirective {
5049
5282
  ...(ngDevMode ? [{ debugName: "dragStartClient" }] : /* istanbul ignore next */ []));
5050
5283
  this.dragPixelOffset = signal({ x: 0, y: 0 }, /* @ts-ignore */
5051
5284
  ...(ngDevMode ? [{ debugName: "dragPixelOffset" }] : /* istanbul ignore next */ []));
5285
+ this.dragMoveCount = 0;
5286
+ this.lastGhostMoveAt = 0;
5052
5287
  this.dragTransform = computed(() => {
5053
5288
  const offset = this.dragPixelOffset();
5054
5289
  return `translate(${offset.x}px, ${offset.y}px)`;
@@ -5087,20 +5322,37 @@ class GridDragDirective {
5087
5322
  return;
5088
5323
  const newCol = Math.max(0, Math.min(originPos.col + colDelta, columns - originPos.colSpan));
5089
5324
  const newRow = Math.max(0, originPos.row + rowDelta);
5090
- const currentGhost = this.grid.ghostPosition();
5091
- const ghostWillMove = !currentGhost || currentGhost.col !== newCol || currentGhost.row !== newRow;
5092
- if (ghostWillMove) {
5093
- this.grid.snapshotRects();
5094
- }
5325
+ // Gate on whether the RAW target cell changed — not on ghostPosition(), which
5326
+ // is the collision-resolved position. During a swap, resolution relocates the
5327
+ // dragged item so the resolved ghost never equals the raw target, which made
5328
+ // this fire on every pointermove and restart every neighbour's animation ~120×/s
5329
+ // (the chop). layout() is a pure function of targetPosition, so if that cell is
5330
+ // unchanged nothing needs re-animating.
5331
+ const prevTarget = this.grid.dragState()?.targetPosition;
5332
+ const targetChanged = !prevTarget || prevTarget.col !== newCol || prevTarget.row !== newRow;
5333
+ this.dragMoveCount++;
5334
+ if (!targetChanged)
5335
+ return;
5336
+ this.grid.snapshotRects();
5095
5337
  this.grid.updateDragTarget({
5096
5338
  col: newCol,
5097
5339
  row: newRow,
5098
5340
  colSpan: originPos.colSpan,
5099
5341
  rowSpan: originPos.rowSpan,
5100
5342
  });
5101
- if (ghostWillMove) {
5102
- this.grid.animateLayoutTransition({ excludeIds: new Set([this.gridItem.itemId()]) });
5343
+ if (isGridDebugEnabled()) {
5344
+ const now = performance.now();
5345
+ const sinceLast = this.lastGhostMoveAt ? Math.round((now - this.lastGhostMoveAt) * 100) / 100 : -1;
5346
+ gridDebug('ghost→', {
5347
+ col: newCol,
5348
+ row: newRow,
5349
+ movesSinceLastGhostMove: this.dragMoveCount, // raw pointermoves between cell crossings
5350
+ msSinceLastGhostMove: sinceLast,
5351
+ });
5352
+ this.lastGhostMoveAt = now;
5353
+ this.dragMoveCount = 0;
5103
5354
  }
5355
+ this.grid.animateLayoutTransition({ excludeIds: new Set([this.gridItem.itemId()]) });
5104
5356
  }), takeUntilDestroyed())
5105
5357
  .subscribe();
5106
5358
  outputToObservable(this.dragHandle.dragEnded)
@@ -5188,29 +5440,40 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
5188
5440
  }]
5189
5441
  }], ctorParameters: () => [] });
5190
5442
 
5443
+ const GROW_THRESHOLD = 0.25;
5191
5444
  class GridResizeDirective {
5192
5445
  constructor() {
5193
5446
  this.grid = inject(GRID_TOKEN);
5194
5447
  this.gridItem = inject(GridItemDirective);
5448
+ this.injector = inject(Injector);
5449
+ this.elementRef = inject(ElementRef);
5450
+ this.renderer = injectRenderer();
5195
5451
  this.isResizing = signal(false, /* @ts-ignore */
5196
5452
  ...(ngDevMode ? [{ debugName: "isResizing" }] : /* istanbul ignore next */ []));
5197
5453
  this.resizeEdges = computed(() => ['n', 'e', 's', 'w', 'ne', 'nw', 'se', 'sw'], /* @ts-ignore */
5198
5454
  ...(ngDevMode ? [{ debugName: "resizeEdges" }] : /* istanbul ignore next */ []));
5199
5455
  this.resizeStartPos = signal(null, /* @ts-ignore */
5200
5456
  ...(ngDevMode ? [{ debugName: "resizeStartPos" }] : /* istanbul ignore next */ []));
5457
+ this.liftedRect = null;
5458
+ this.lastSnap = null;
5201
5459
  }
5202
5460
  beginResize() {
5203
5461
  if (this.grid.readOnly())
5204
5462
  return;
5205
5463
  const pos = this.gridItem.currentPosition();
5206
- if (pos) {
5207
- this.resizeStartPos.set({ col: pos.col, row: pos.row, colSpan: pos.colSpan, rowSpan: pos.rowSpan });
5208
- this.isResizing.set(true);
5209
- }
5464
+ if (!pos)
5465
+ return;
5466
+ this.resizeStartPos.set({ col: pos.col, row: pos.row, colSpan: pos.colSpan, rowSpan: pos.rowSpan });
5467
+ this.lastSnap = null;
5468
+ this.isResizing.set(true);
5469
+ const rect = this.elementRef.nativeElement.getBoundingClientRect();
5470
+ this.liftedRect = { left: rect.left, top: rect.top, width: rect.width, height: rect.height };
5471
+ this.applyFixed(this.liftedRect);
5210
5472
  }
5211
5473
  updateResize(event) {
5212
5474
  const start = this.resizeStartPos();
5213
- if (!start)
5475
+ const startRect = this.liftedRect;
5476
+ if (!start || !startRect)
5214
5477
  return;
5215
5478
  const columns = this.grid.activeColumns();
5216
5479
  const containerWidth = this.grid.containerWidth();
@@ -5218,53 +5481,143 @@ class GridResizeDirective {
5218
5481
  const gap = this.grid.gap();
5219
5482
  const cellWidth = (containerWidth - gap * (columns - 1)) / columns;
5220
5483
  const cellHeight = rowHeight + gap;
5484
+ // 1. Live pixel size — the item follows the pointer 1:1, clamped to the span
5485
+ // constraints in pixels so it can't grow/shrink past its allowed size.
5486
+ const spanWidth = (span) => span * cellWidth + (span - 1) * gap;
5487
+ const spanHeight = (span) => span * rowHeight + (span - 1) * gap;
5488
+ const minW = spanWidth(this.gridItem.minColSpan());
5489
+ const maxW = spanWidth(this.gridItem.maxColSpan());
5490
+ const minH = spanHeight(this.gridItem.minRowSpan());
5491
+ const maxH = spanHeight(this.gridItem.maxRowSpan());
5492
+ const live = { ...startRect };
5493
+ if (event.edge === 'e' || event.edge === 'se' || event.edge === 'ne') {
5494
+ live.width = Math.min(maxW, Math.max(minW, startRect.width + event.dx));
5495
+ }
5496
+ if (event.edge === 'w' || event.edge === 'sw' || event.edge === 'nw') {
5497
+ const rightEdge = startRect.left + startRect.width;
5498
+ live.width = Math.min(maxW, Math.max(minW, startRect.width - event.dx));
5499
+ live.left = rightEdge - live.width;
5500
+ }
5501
+ if (event.edge === 's' || event.edge === 'se' || event.edge === 'sw') {
5502
+ live.height = Math.min(maxH, Math.max(minH, startRect.height + event.dy));
5503
+ }
5504
+ if (event.edge === 'n' || event.edge === 'ne' || event.edge === 'nw') {
5505
+ const bottomEdge = startRect.top + startRect.height;
5506
+ live.height = Math.min(maxH, Math.max(minH, startRect.height - event.dy));
5507
+ live.top = bottomEdge - live.height;
5508
+ }
5509
+ this.applyFixed(live);
5510
+ // liftedRect stays the gesture-start anchor — event.dx/dy are cumulative from start.
5511
+ // 2. Snapped span — drives neighbour reflow. The snap is biased toward the growth
5512
+ // direction (a cell is claimed once the edge is GROW_THRESHOLD into it) so
5513
+ // neighbours slide out of the way early and the growing item barely overlaps them.
5514
+ // growPos: for edges that grow with a positive delta (east/south).
5515
+ // growNeg: for edges that grow with a negative delta (west/north).
5516
+ const growPos = (px, cell) => Math.floor(px / cell + (1 - GROW_THRESHOLD));
5517
+ const growNeg = (px, cell) => Math.ceil(px / cell - (1 - GROW_THRESHOLD));
5221
5518
  let newColSpan = start.colSpan;
5222
5519
  let newRowSpan = start.rowSpan;
5223
5520
  let newCol = start.col;
5224
5521
  let newRow = start.row;
5225
- // East edges: grow/shrink span to the right
5226
5522
  if (event.edge === 'e' || event.edge === 'se' || event.edge === 'ne') {
5227
- newColSpan = Math.max(1, start.colSpan + Math.round(event.dx / cellWidth));
5523
+ newColSpan = Math.max(1, start.colSpan + growPos(event.dx, cellWidth));
5228
5524
  }
5229
- // West edges: move col left and grow span, keeping right edge fixed
5230
5525
  if (event.edge === 'w' || event.edge === 'sw' || event.edge === 'nw') {
5231
5526
  const rightEdge = start.col + start.colSpan;
5232
- const colDelta = Math.round(event.dx / cellWidth);
5233
- newCol = Math.max(0, start.col + colDelta);
5527
+ newCol = Math.max(0, start.col + growNeg(event.dx, cellWidth));
5234
5528
  newColSpan = rightEdge - newCol;
5235
- // Clamp against constraints and recalculate col to keep right edge fixed
5236
5529
  newColSpan = Math.min(this.gridItem.maxColSpan(), Math.max(this.gridItem.minColSpan(), newColSpan));
5237
5530
  newCol = rightEdge - newColSpan;
5238
5531
  }
5239
- // South edges: grow/shrink span downward
5240
5532
  if (event.edge === 's' || event.edge === 'se' || event.edge === 'sw') {
5241
- newRowSpan = Math.max(1, start.rowSpan + Math.round(event.dy / cellHeight));
5533
+ newRowSpan = Math.max(1, start.rowSpan + growPos(event.dy, cellHeight));
5242
5534
  }
5243
- // North edges: move row up and grow span, keeping bottom edge fixed
5244
5535
  if (event.edge === 'n' || event.edge === 'ne' || event.edge === 'nw') {
5245
5536
  const bottomEdge = start.row + start.rowSpan;
5246
- const rowDelta = Math.round(event.dy / cellHeight);
5247
- newRow = Math.max(0, start.row + rowDelta);
5537
+ newRow = Math.max(0, start.row + growNeg(event.dy, cellHeight));
5248
5538
  newRowSpan = bottomEdge - newRow;
5249
- // Clamp against constraints and recalculate row to keep bottom edge fixed
5250
5539
  newRowSpan = Math.min(this.gridItem.maxRowSpan(), Math.max(this.gridItem.minRowSpan(), newRowSpan));
5251
5540
  newRow = bottomEdge - newRowSpan;
5252
5541
  }
5253
- const currentPos = this.gridItem.currentPosition();
5254
- if (currentPos &&
5255
- currentPos.colSpan === newColSpan &&
5256
- currentPos.rowSpan === newRowSpan &&
5257
- currentPos.col === newCol &&
5258
- currentPos.row === newRow)
5542
+ // Gate on the raw snapped target changing — not on the resized item's resolved
5543
+ // position (which compaction can shift), so we don't re-run the reflow and restart
5544
+ // every neighbour's animation on every pointermove.
5545
+ if (this.lastSnap &&
5546
+ this.lastSnap.colSpan === newColSpan &&
5547
+ this.lastSnap.rowSpan === newRowSpan &&
5548
+ this.lastSnap.col === newCol &&
5549
+ this.lastSnap.row === newRow)
5259
5550
  return;
5551
+ this.lastSnap = { col: newCol, row: newRow, colSpan: newColSpan, rowSpan: newRowSpan };
5552
+ // The snapped span crossed into a new cell: reflow the neighbours. The resized
5553
+ // item is excluded from the FLIP because its own fixed element drives the size.
5554
+ // A shorter duration than a drag keeps pushed neighbours tracking the live-resizing
5555
+ // edge closely during a fast resize, instead of trailing it with a long glide.
5260
5556
  this.grid.snapshotRects();
5261
5557
  this.grid.resizeItem({ id: this.gridItem.itemId(), newColSpan, newRowSpan, newCol, newRow });
5262
- this.grid.animateLayoutTransition({ scaleIds: new Set([this.gridItem.itemId()]) });
5558
+ this.grid.animateLayoutTransition({ excludeIds: new Set([this.gridItem.itemId()]), durationMs: 160 });
5263
5559
  }
5264
5560
  finishResize() {
5265
5561
  this.resizeStartPos.set(null);
5562
+ this.lastSnap = null;
5266
5563
  this.isResizing.set(false);
5267
5564
  this.grid.commitResize();
5565
+ const liveRect = this.liftedRect ? this.currentFixedRect() : null;
5566
+ this.liftedRect = null;
5567
+ if (!liveRect) {
5568
+ this.releaseFixed();
5569
+ return;
5570
+ }
5571
+ // Settle: drop back into grid flow, measure the final slot, then animate the
5572
+ // fixed element from its free pixel rect to that slot. Real width/height/left/top
5573
+ // are animated (never scale) so the content stays crisp during the settle.
5574
+ afterNextRender(() => {
5575
+ const el = this.elementRef.nativeElement;
5576
+ this.releaseFixed();
5577
+ const finalRect = el.getBoundingClientRect();
5578
+ this.applyFixed({ left: finalRect.left, top: finalRect.top, width: finalRect.width, height: finalRect.height });
5579
+ el.getAnimations().forEach((a) => a.cancel());
5580
+ const moved = Math.abs(liveRect.left - finalRect.left) > 1 || Math.abs(liveRect.top - finalRect.top) > 1;
5581
+ const resized = Math.abs(liveRect.width - finalRect.width) > 1 || Math.abs(liveRect.height - finalRect.height) > 1;
5582
+ const release = () => this.releaseFixed();
5583
+ if (!moved && !resized) {
5584
+ release();
5585
+ return;
5586
+ }
5587
+ const anim = el.animate([
5588
+ {
5589
+ left: `${liveRect.left}px`,
5590
+ top: `${liveRect.top}px`,
5591
+ width: `${liveRect.width}px`,
5592
+ height: `${liveRect.height}px`,
5593
+ },
5594
+ {
5595
+ left: `${finalRect.left}px`,
5596
+ top: `${finalRect.top}px`,
5597
+ width: `${finalRect.width}px`,
5598
+ height: `${finalRect.height}px`,
5599
+ },
5600
+ ], { duration: 250, easing: 'cubic-bezier(0.2, 0, 0, 1)' });
5601
+ anim.onfinish = release;
5602
+ anim.oncancel = release;
5603
+ }, { injector: this.injector });
5604
+ }
5605
+ currentFixedRect() {
5606
+ const rect = this.elementRef.nativeElement.getBoundingClientRect();
5607
+ return { left: rect.left, top: rect.top, width: rect.width, height: rect.height };
5608
+ }
5609
+ applyFixed(rect) {
5610
+ this.renderer.setStyle(this.elementRef.nativeElement, {
5611
+ position: 'fixed',
5612
+ left: `${rect.left}px`,
5613
+ top: `${rect.top}px`,
5614
+ width: `${rect.width}px`,
5615
+ height: `${rect.height}px`,
5616
+ zIndex: '100',
5617
+ });
5618
+ }
5619
+ releaseFixed() {
5620
+ this.renderer.removeStyles(this.elementRef.nativeElement, 'position', 'left', 'top', 'width', 'height', 'zIndex');
5268
5621
  }
5269
5622
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridResizeDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
5270
5623
  static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "22.0.5", type: GridResizeDirective, isStandalone: true, selector: "[etGridResize]", host: { properties: { "class.et-grid-resize--active": "isResizing()" }, classAttribute: "et-grid-resize" }, ngImport: i0 }); }
@@ -5306,6 +5659,67 @@ const fromGridPosition = (pos) => ({
5306
5659
  rows: pos.rowSpan,
5307
5660
  });
5308
5661
 
5662
+ class GridItemToolbarComponent {
5663
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridItemToolbarComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
5664
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "22.0.5", type: GridItemToolbarComponent, isStandalone: true, selector: "et-grid-item-toolbar, [et-grid-item-toolbar]", host: { listeners: { "pointerdown": "$event.stopPropagation()" }, classAttribute: "et-grid-item-toolbar" }, ngImport: i0, template: `<ng-content />`, isInline: true, styles: [".et-grid-item-toolbar{display:inline-flex;align-items:center;gap:var(--et-grid-item-toolbar-gap, 4px);padding:var(--et-grid-item-toolbar-padding, 4px);border-radius:var(--et-grid-item-toolbar-radius, 8px);background:var(--et-grid-item-toolbar-background, transparent)}\n"], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
5665
+ }
5666
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridItemToolbarComponent, decorators: [{
5667
+ type: Component,
5668
+ args: [{ selector: 'et-grid-item-toolbar, [et-grid-item-toolbar]', template: `<ng-content />`, encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.OnPush, host: {
5669
+ class: 'et-grid-item-toolbar',
5670
+ '(pointerdown)': '$event.stopPropagation()',
5671
+ }, styles: [".et-grid-item-toolbar{display:inline-flex;align-items:center;gap:var(--et-grid-item-toolbar-gap, 4px);padding:var(--et-grid-item-toolbar-padding, 4px);border-radius:var(--et-grid-item-toolbar-radius, 8px);background:var(--et-grid-item-toolbar-background, transparent)}\n"] }]
5672
+ }] });
5673
+
5674
+ class GridItemDefaultActionsComponent {
5675
+ constructor() {
5676
+ this.grid = inject(GRID_TOKEN);
5677
+ this.gridConfig = injectGridConfig();
5678
+ this.locale = injectLocale();
5679
+ this.itemId = input.required(/* @ts-ignore */
5680
+ ...(ngDevMode ? [{ debugName: "itemId" }] : /* istanbul ignore next */ []));
5681
+ this.data = input(/* @ts-ignore */
5682
+ ...(ngDevMode ? [undefined, { debugName: "data" }] : /* istanbul ignore next */ []));
5683
+ this.removeAriaLabel = computed(() => this.gridConfig.transformer(this.gridConfig.removeActionAriaLabel, this.locale.currentLocale()), /* @ts-ignore */
5684
+ ...(ngDevMode ? [{ debugName: "removeAriaLabel" }] : /* istanbul ignore next */ []));
5685
+ }
5686
+ remove() {
5687
+ this.grid.removeItem(this.itemId());
5688
+ }
5689
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridItemDefaultActionsComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
5690
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "22.0.5", type: GridItemDefaultActionsComponent, isStandalone: true, selector: "et-grid-item-default-actions", inputs: { itemId: { classPropertyName: "itemId", publicName: "itemId", isSignal: true, isRequired: true, transformFunction: null }, data: { classPropertyName: "data", publicName: "data", isSignal: true, isRequired: false, transformFunction: null } }, providers: [provideIcons(TIMES_ICON)], ngImport: i0, template: `
5691
+ <et-grid-item-toolbar>
5692
+ <button
5693
+ [attr.aria-label]="removeAriaLabel()"
5694
+ (click)="remove()"
5695
+ class="et-grid-item-default-actions__remove"
5696
+ et-icon-button
5697
+ size="xs"
5698
+ type="button"
5699
+ >
5700
+ <i etIcon="et-times"></i>
5701
+ </button>
5702
+ </et-grid-item-toolbar>
5703
+ `, isInline: true, styles: ["et-grid-item-default-actions .et-grid-item-default-actions__remove{color:rgb(var(--et-surface-color-muted))}et-grid-item-default-actions .et-grid-item-default-actions__remove:hover{color:rgb(var(--et-surface-color))}\n"], dependencies: [{ kind: "component", type: GridItemToolbarComponent, selector: "et-grid-item-toolbar, [et-grid-item-toolbar]" }, { kind: "component", type: IconButtonComponent, selector: "[et-icon-button]", inputs: ["variant", "size"] }, { kind: "directive", type: IconDirective, selector: "[etIcon]", inputs: ["etIcon", "allowHardcodedColor"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
5704
+ }
5705
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridItemDefaultActionsComponent, decorators: [{
5706
+ type: Component,
5707
+ args: [{ selector: 'et-grid-item-default-actions', template: `
5708
+ <et-grid-item-toolbar>
5709
+ <button
5710
+ [attr.aria-label]="removeAriaLabel()"
5711
+ (click)="remove()"
5712
+ class="et-grid-item-default-actions__remove"
5713
+ et-icon-button
5714
+ size="xs"
5715
+ type="button"
5716
+ >
5717
+ <i etIcon="et-times"></i>
5718
+ </button>
5719
+ </et-grid-item-toolbar>
5720
+ `, encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.OnPush, imports: [GridItemToolbarComponent, IconButtonComponent, ...ICON_IMPORTS], providers: [provideIcons(TIMES_ICON)], styles: ["et-grid-item-default-actions .et-grid-item-default-actions__remove{color:rgb(var(--et-surface-color-muted))}et-grid-item-default-actions .et-grid-item-default-actions__remove:hover{color:rgb(var(--et-surface-color))}\n"] }]
5721
+ }], propDecorators: { itemId: [{ type: i0.Input, args: [{ isSignal: true, alias: "itemId", required: true }] }], data: [{ type: i0.Input, args: [{ isSignal: true, alias: "data", required: false }] }] } });
5722
+
5309
5723
  class GridItemComponent {
5310
5724
  constructor() {
5311
5725
  this.grid = inject(GRID_TOKEN);
@@ -5314,16 +5728,14 @@ class GridItemComponent {
5314
5728
  this.parentSurfaceProvider = inject(SURFACE_PROVIDER, { optional: true, skipSelf: true });
5315
5729
  this.gridDrag = inject(GridDragDirective);
5316
5730
  this.gridResize = inject(GridResizeDirective);
5731
+ this.surfaceThemes = injectSurfaceThemes({ optional: true });
5317
5732
  this.ariaLabel = input('Grid item', /* @ts-ignore */
5318
5733
  ...(ngDevMode ? [{ debugName: "ariaLabel" }] : /* istanbul ignore next */ []));
5319
5734
  this.removed = output();
5320
- this.surfaceThemes = injectSurfaceThemes({ optional: true });
5321
- this.gridConfig = injectGridConfig();
5322
- this.locale = injectLocale();
5735
+ this.itemContent = viewChild('itemContent', /* @ts-ignore */
5736
+ ...(ngDevMode ? [{ debugName: "itemContent" }] : /* istanbul ignore next */ []));
5323
5737
  this.isReadOnly = computed(() => this.grid.readOnly(), /* @ts-ignore */
5324
5738
  ...(ngDevMode ? [{ debugName: "isReadOnly" }] : /* istanbul ignore next */ []));
5325
- this.dragHandleAriaLabel = computed(() => this.gridConfig.transformer(this.gridConfig.dragHandleAriaLabel, this.locale.currentLocale()), /* @ts-ignore */
5326
- ...(ngDevMode ? [{ debugName: "dragHandleAriaLabel" }] : /* istanbul ignore next */ []));
5327
5739
  this.resolvedSurface = computed(() => {
5328
5740
  const themes = this.surfaceThemes;
5329
5741
  const parent = this.parentSurfaceProvider;
@@ -5341,6 +5753,17 @@ class GridItemComponent {
5341
5753
  this.provideSurface.clearForcedSurface();
5342
5754
  }
5343
5755
  });
5756
+ effect(() => {
5757
+ const el = this.itemContent()?.nativeElement;
5758
+ if (el) {
5759
+ this.grid.registerContentElement(this.gridItem.itemId(), el);
5760
+ }
5761
+ });
5762
+ }
5763
+ blockPointerDownWhenReadOnly(event) {
5764
+ if (this.isReadOnly()) {
5765
+ event.stopPropagation();
5766
+ }
5344
5767
  }
5345
5768
  applyKeyboardShortcut(event) {
5346
5769
  if (this.isReadOnly())
@@ -5374,6 +5797,7 @@ class GridItemComponent {
5374
5797
  }
5375
5798
  if (event.shiftKey) {
5376
5799
  let handled = true;
5800
+ this.grid.snapshotRects();
5377
5801
  switch (event.key) {
5378
5802
  case 'ArrowRight':
5379
5803
  this.grid.resizeItem({ id: this.gridItem.itemId(), newColSpan: pos.colSpan + 1, newRowSpan: pos.rowSpan });
@@ -5391,9 +5815,16 @@ class GridItemComponent {
5391
5815
  handled = false;
5392
5816
  }
5393
5817
  if (handled) {
5818
+ // Discrete keyboard step: animate the neighbours (translate-only) and commit
5819
+ // so the resize base doesn't carry over into the next keypress or gesture.
5820
+ this.grid.animateLayoutTransition({ excludeIds: new Set([this.gridItem.itemId()]) });
5821
+ this.grid.commitResize();
5394
5822
  event.preventDefault();
5395
5823
  event.stopPropagation();
5396
5824
  }
5825
+ else {
5826
+ this.grid.commitResize();
5827
+ }
5397
5828
  }
5398
5829
  if (event.key === 'Delete' || event.key === 'Backspace') {
5399
5830
  if (event.ctrlKey || event.metaKey) {
@@ -5404,12 +5835,8 @@ class GridItemComponent {
5404
5835
  }
5405
5836
  }
5406
5837
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridItemComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
5407
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "22.0.5", type: GridItemComponent, isStandalone: true, selector: "et-grid-item, [et-grid-item]", inputs: { ariaLabel: { classPropertyName: "ariaLabel", publicName: "ariaLabel", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { removed: "removed" }, host: { listeners: { "keydown": "applyKeyboardShortcut($event)" }, properties: { "class.et-grid-item--dragging": "!isReadOnly() && gridDrag.dragHandle.isDragging()", "class.et-grid-item--resizing": "gridResize.isResizing()", "attr.role": "\"group\"", "attr.aria-label": "ariaLabel()", "attr.tabindex": "\"0\"" }, classAttribute: "et-grid-item" }, hostDirectives: [{ directive: GridItemDirective, inputs: ["itemId", "itemId", "minColSpan", "minColSpan", "maxColSpan", "maxColSpan", "minRowSpan", "minRowSpan", "maxRowSpan", "maxRowSpan"] }, { directive: GridDragDirective }, { directive: GridResizeDirective }, { directive: i1.ProvideSurfaceDirective }], ngImport: i0, template: `
5408
- <div [attr.aria-label]="dragHandleAriaLabel()" class="et-grid-item__drag-handle">
5409
- <ng-content select="[etGridItemDragHandle]" />
5410
- </div>
5411
-
5412
- <div (pointerdown)="$event.stopPropagation()" class="et-grid-item__content">
5838
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.2.0", version: "22.0.5", type: GridItemComponent, isStandalone: true, selector: "et-grid-item, [et-grid-item]", inputs: { ariaLabel: { classPropertyName: "ariaLabel", publicName: "ariaLabel", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { removed: "removed" }, host: { listeners: { "keydown": "applyKeyboardShortcut($event)" }, properties: { "class.et-grid-item--dragging": "!isReadOnly() && gridDrag.dragHandle.isDragging()", "class.et-grid-item--resizing": "gridResize.isResizing()", "attr.role": "\"group\"", "attr.aria-label": "ariaLabel()", "attr.tabindex": "\"0\"" }, classAttribute: "et-grid-item" }, viewQueries: [{ propertyName: "itemContent", first: true, predicate: ["itemContent"], descendants: true, isSignal: true }], hostDirectives: [{ directive: GridItemDirective, inputs: ["itemId", "itemId", "minColSpan", "minColSpan", "maxColSpan", "maxColSpan", "minRowSpan", "minRowSpan", "maxRowSpan", "maxRowSpan"] }, { directive: GridDragDirective }, { directive: GridResizeDirective }, { directive: i1.ProvideSurfaceDirective }], ngImport: i0, template: `
5839
+ <div #itemContent (pointerdown)="blockPointerDownWhenReadOnly($event)" class="et-grid-item__content">
5413
5840
  <ng-content />
5414
5841
  </div>
5415
5842
 
@@ -5425,16 +5852,12 @@ class GridItemComponent {
5425
5852
  <div (pointerdown)="$event.stopPropagation()" class="et-grid-item__actions">
5426
5853
  <ng-content select="[etGridItemAction]" />
5427
5854
  </div>
5428
- `, isInline: true, styles: [".et-grid-item{position:relative;display:flex;flex-direction:column;outline:none;will-change:transform;border-radius:var(--et-grid-item-radius, 0);background:var(--et-grid-item-bg, var(--et-surface-background-solid))}.et-grid-item:is(.et-grid-item--dragging){z-index:100;cursor:grabbing;-webkit-user-select:none;user-select:none}.et-grid-item:is(.et-grid-item--resizing){z-index:100;-webkit-user-select:none;user-select:none}.et-grid-item:hover .et-resize-handle--e:after,.et-grid-item:hover .et-resize-handle--s:after,.et-grid-item:hover .et-resize-handle--w:after,.et-grid-item:hover .et-resize-handle--n:after,.et-grid-item:hover .et-resize-handle--se:after,.et-grid-item:hover .et-resize-handle--sw:after,.et-grid-item:hover .et-resize-handle--ne:after,.et-grid-item:hover .et-resize-handle--nw:after,.et-grid-item--resizing .et-resize-handle--e:after,.et-grid-item--resizing .et-resize-handle--s:after,.et-grid-item--resizing .et-resize-handle--w:after,.et-grid-item--resizing .et-resize-handle--n:after,.et-grid-item--resizing .et-resize-handle--se:after,.et-grid-item--resizing .et-resize-handle--sw:after,.et-grid-item--resizing .et-resize-handle--ne:after,.et-grid-item--resizing .et-resize-handle--nw:after{content:\"\";position:absolute;border-radius:2px;background:var(--et-grid-item-resize-handle-color, var(--et-surface-color-solid));opacity:.2}.et-grid-item:hover .et-resize-handle--e:after,.et-grid-item--resizing .et-resize-handle--e:after{right:2px;top:50%;transform:translateY(-50%);width:3px;height:24px}.et-grid-item:hover .et-resize-handle--w:after,.et-grid-item--resizing .et-resize-handle--w:after{left:2px;top:50%;transform:translateY(-50%);width:3px;height:24px}.et-grid-item:hover .et-resize-handle--s:after,.et-grid-item--resizing .et-resize-handle--s:after{bottom:2px;left:50%;transform:translate(-50%);height:3px;width:24px}.et-grid-item:hover .et-resize-handle--n:after,.et-grid-item--resizing .et-resize-handle--n:after{top:2px;left:50%;transform:translate(-50%);height:3px;width:24px}.et-grid-item:hover .et-resize-handle--se:after,.et-grid-item--resizing .et-resize-handle--se:after{bottom:3px;right:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--sw:after,.et-grid-item--resizing .et-resize-handle--sw:after{bottom:3px;left:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--ne:after,.et-grid-item--resizing .et-resize-handle--ne:after{top:3px;right:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--nw:after,.et-grid-item--resizing .et-resize-handle--nw:after{top:3px;left:3px;width:8px;height:8px;border-radius:1px}.et-grid-item__drag-handle{cursor:grab;display:flex;align-items:center;-webkit-user-select:none;user-select:none;touch-action:none}.et-grid-item--dragging .et-grid-item__drag-handle{cursor:grabbing}.et-grid-item__content{flex:1;min-height:0}.et-grid-item__actions{position:absolute;top:4px;right:4px;display:flex;gap:4px}\n"], dependencies: [{ kind: "component", type: ResizeHandlesComponent, selector: "et-resize-handles", inputs: ["edges", "disabled"], outputs: ["resizeStarted", "resizeMoved", "resizeEnded"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
5855
+ `, isInline: true, styles: [".et-grid-item{position:relative;display:flex;flex-direction:column;outline:none;will-change:transform;border-radius:var(--et-grid-item-radius, 0);background:var(--et-grid-item-bg, var(--et-surface-background-solid))}.et-grid-item:is(.et-grid-item--dragging){z-index:100;cursor:grabbing;-webkit-user-select:none;user-select:none}.et-grid-item:is(.et-grid-item--resizing){z-index:100;-webkit-user-select:none;user-select:none}.et-grid-item:hover .et-resize-handle--e:after,.et-grid-item:hover .et-resize-handle--s:after,.et-grid-item:hover .et-resize-handle--w:after,.et-grid-item:hover .et-resize-handle--n:after,.et-grid-item:hover .et-resize-handle--se:after,.et-grid-item:hover .et-resize-handle--sw:after,.et-grid-item:hover .et-resize-handle--ne:after,.et-grid-item:hover .et-resize-handle--nw:after,.et-grid-item--resizing .et-resize-handle--e:after,.et-grid-item--resizing .et-resize-handle--s:after,.et-grid-item--resizing .et-resize-handle--w:after,.et-grid-item--resizing .et-resize-handle--n:after,.et-grid-item--resizing .et-resize-handle--se:after,.et-grid-item--resizing .et-resize-handle--sw:after,.et-grid-item--resizing .et-resize-handle--ne:after,.et-grid-item--resizing .et-resize-handle--nw:after{content:\"\";position:absolute;border-radius:2px;background:var(--et-grid-item-resize-handle-color, var(--et-surface-color-solid));opacity:.2}.et-grid-item:hover .et-resize-handle--e:after,.et-grid-item--resizing .et-resize-handle--e:after{right:2px;top:50%;transform:translateY(-50%);width:3px;height:24px}.et-grid-item:hover .et-resize-handle--w:after,.et-grid-item--resizing .et-resize-handle--w:after{left:2px;top:50%;transform:translateY(-50%);width:3px;height:24px}.et-grid-item:hover .et-resize-handle--s:after,.et-grid-item--resizing .et-resize-handle--s:after{bottom:2px;left:50%;transform:translate(-50%);height:3px;width:24px}.et-grid-item:hover .et-resize-handle--n:after,.et-grid-item--resizing .et-resize-handle--n:after{top:2px;left:50%;transform:translate(-50%);height:3px;width:24px}.et-grid-item:hover .et-resize-handle--se:after,.et-grid-item--resizing .et-resize-handle--se:after{bottom:3px;right:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--sw:after,.et-grid-item--resizing .et-resize-handle--sw:after{bottom:3px;left:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--ne:after,.et-grid-item--resizing .et-resize-handle--ne:after{top:3px;right:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--nw:after,.et-grid-item--resizing .et-resize-handle--nw:after{top:3px;left:3px;width:8px;height:8px;border-radius:1px}.et-grid-item__content{flex:1;min-height:0}.et-grid:not(.et-grid--readonly) .et-grid-item__content{cursor:grab}.et-grid-item--dragging .et-grid-item__content{cursor:grabbing}.et-grid-item__actions{position:absolute;top:4px;right:4px;display:flex;gap:4px}\n"], dependencies: [{ kind: "component", type: ResizeHandlesComponent, selector: "et-resize-handles", inputs: ["edges", "disabled"], outputs: ["resizeStarted", "resizeMoved", "resizeEnded"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
5429
5856
  }
5430
5857
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridItemComponent, decorators: [{
5431
5858
  type: Component,
5432
5859
  args: [{ selector: 'et-grid-item, [et-grid-item]', template: `
5433
- <div [attr.aria-label]="dragHandleAriaLabel()" class="et-grid-item__drag-handle">
5434
- <ng-content select="[etGridItemDragHandle]" />
5435
- </div>
5436
-
5437
- <div (pointerdown)="$event.stopPropagation()" class="et-grid-item__content">
5860
+ <div #itemContent (pointerdown)="blockPointerDownWhenReadOnly($event)" class="et-grid-item__content">
5438
5861
  <ng-content />
5439
5862
  </div>
5440
5863
 
@@ -5466,21 +5889,20 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
5466
5889
  '[attr.aria-label]': 'ariaLabel()',
5467
5890
  '[attr.tabindex]': '"0"',
5468
5891
  '(keydown)': 'applyKeyboardShortcut($event)',
5469
- }, styles: [".et-grid-item{position:relative;display:flex;flex-direction:column;outline:none;will-change:transform;border-radius:var(--et-grid-item-radius, 0);background:var(--et-grid-item-bg, var(--et-surface-background-solid))}.et-grid-item:is(.et-grid-item--dragging){z-index:100;cursor:grabbing;-webkit-user-select:none;user-select:none}.et-grid-item:is(.et-grid-item--resizing){z-index:100;-webkit-user-select:none;user-select:none}.et-grid-item:hover .et-resize-handle--e:after,.et-grid-item:hover .et-resize-handle--s:after,.et-grid-item:hover .et-resize-handle--w:after,.et-grid-item:hover .et-resize-handle--n:after,.et-grid-item:hover .et-resize-handle--se:after,.et-grid-item:hover .et-resize-handle--sw:after,.et-grid-item:hover .et-resize-handle--ne:after,.et-grid-item:hover .et-resize-handle--nw:after,.et-grid-item--resizing .et-resize-handle--e:after,.et-grid-item--resizing .et-resize-handle--s:after,.et-grid-item--resizing .et-resize-handle--w:after,.et-grid-item--resizing .et-resize-handle--n:after,.et-grid-item--resizing .et-resize-handle--se:after,.et-grid-item--resizing .et-resize-handle--sw:after,.et-grid-item--resizing .et-resize-handle--ne:after,.et-grid-item--resizing .et-resize-handle--nw:after{content:\"\";position:absolute;border-radius:2px;background:var(--et-grid-item-resize-handle-color, var(--et-surface-color-solid));opacity:.2}.et-grid-item:hover .et-resize-handle--e:after,.et-grid-item--resizing .et-resize-handle--e:after{right:2px;top:50%;transform:translateY(-50%);width:3px;height:24px}.et-grid-item:hover .et-resize-handle--w:after,.et-grid-item--resizing .et-resize-handle--w:after{left:2px;top:50%;transform:translateY(-50%);width:3px;height:24px}.et-grid-item:hover .et-resize-handle--s:after,.et-grid-item--resizing .et-resize-handle--s:after{bottom:2px;left:50%;transform:translate(-50%);height:3px;width:24px}.et-grid-item:hover .et-resize-handle--n:after,.et-grid-item--resizing .et-resize-handle--n:after{top:2px;left:50%;transform:translate(-50%);height:3px;width:24px}.et-grid-item:hover .et-resize-handle--se:after,.et-grid-item--resizing .et-resize-handle--se:after{bottom:3px;right:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--sw:after,.et-grid-item--resizing .et-resize-handle--sw:after{bottom:3px;left:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--ne:after,.et-grid-item--resizing .et-resize-handle--ne:after{top:3px;right:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--nw:after,.et-grid-item--resizing .et-resize-handle--nw:after{top:3px;left:3px;width:8px;height:8px;border-radius:1px}.et-grid-item__drag-handle{cursor:grab;display:flex;align-items:center;-webkit-user-select:none;user-select:none;touch-action:none}.et-grid-item--dragging .et-grid-item__drag-handle{cursor:grabbing}.et-grid-item__content{flex:1;min-height:0}.et-grid-item__actions{position:absolute;top:4px;right:4px;display:flex;gap:4px}\n"] }]
5470
- }], ctorParameters: () => [], propDecorators: { ariaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaLabel", required: false }] }], removed: [{ type: i0.Output, args: ["removed"] }] } });
5892
+ }, styles: [".et-grid-item{position:relative;display:flex;flex-direction:column;outline:none;will-change:transform;border-radius:var(--et-grid-item-radius, 0);background:var(--et-grid-item-bg, var(--et-surface-background-solid))}.et-grid-item:is(.et-grid-item--dragging){z-index:100;cursor:grabbing;-webkit-user-select:none;user-select:none}.et-grid-item:is(.et-grid-item--resizing){z-index:100;-webkit-user-select:none;user-select:none}.et-grid-item:hover .et-resize-handle--e:after,.et-grid-item:hover .et-resize-handle--s:after,.et-grid-item:hover .et-resize-handle--w:after,.et-grid-item:hover .et-resize-handle--n:after,.et-grid-item:hover .et-resize-handle--se:after,.et-grid-item:hover .et-resize-handle--sw:after,.et-grid-item:hover .et-resize-handle--ne:after,.et-grid-item:hover .et-resize-handle--nw:after,.et-grid-item--resizing .et-resize-handle--e:after,.et-grid-item--resizing .et-resize-handle--s:after,.et-grid-item--resizing .et-resize-handle--w:after,.et-grid-item--resizing .et-resize-handle--n:after,.et-grid-item--resizing .et-resize-handle--se:after,.et-grid-item--resizing .et-resize-handle--sw:after,.et-grid-item--resizing .et-resize-handle--ne:after,.et-grid-item--resizing .et-resize-handle--nw:after{content:\"\";position:absolute;border-radius:2px;background:var(--et-grid-item-resize-handle-color, var(--et-surface-color-solid));opacity:.2}.et-grid-item:hover .et-resize-handle--e:after,.et-grid-item--resizing .et-resize-handle--e:after{right:2px;top:50%;transform:translateY(-50%);width:3px;height:24px}.et-grid-item:hover .et-resize-handle--w:after,.et-grid-item--resizing .et-resize-handle--w:after{left:2px;top:50%;transform:translateY(-50%);width:3px;height:24px}.et-grid-item:hover .et-resize-handle--s:after,.et-grid-item--resizing .et-resize-handle--s:after{bottom:2px;left:50%;transform:translate(-50%);height:3px;width:24px}.et-grid-item:hover .et-resize-handle--n:after,.et-grid-item--resizing .et-resize-handle--n:after{top:2px;left:50%;transform:translate(-50%);height:3px;width:24px}.et-grid-item:hover .et-resize-handle--se:after,.et-grid-item--resizing .et-resize-handle--se:after{bottom:3px;right:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--sw:after,.et-grid-item--resizing .et-resize-handle--sw:after{bottom:3px;left:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--ne:after,.et-grid-item--resizing .et-resize-handle--ne:after{top:3px;right:3px;width:8px;height:8px;border-radius:1px}.et-grid-item:hover .et-resize-handle--nw:after,.et-grid-item--resizing .et-resize-handle--nw:after{top:3px;left:3px;width:8px;height:8px;border-radius:1px}.et-grid-item__content{flex:1;min-height:0}.et-grid:not(.et-grid--readonly) .et-grid-item__content{cursor:grab}.et-grid-item--dragging .et-grid-item__content{cursor:grabbing}.et-grid-item__actions{position:absolute;top:4px;right:4px;display:flex;gap:4px}\n"] }]
5893
+ }], ctorParameters: () => [], propDecorators: { ariaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaLabel", required: false }] }], removed: [{ type: i0.Output, args: ["removed"] }], itemContent: [{ type: i0.ViewChild, args: ['itemContent', { isSignal: true }] }] } });
5471
5894
 
5472
5895
  class GridComponent {
5473
5896
  constructor() {
5474
5897
  this.grid = inject(GridDirective);
5475
- this.ghostRef = viewChild('ghostRef', /* @ts-ignore */
5476
- ...(ngDevMode ? [{ debugName: "ghostRef" }] : /* istanbul ignore next */ []));
5477
5898
  this.gridConfig = injectGridConfig();
5478
5899
  this.locale = injectLocale();
5479
- this.isReadOnly = computed(() => this.grid.readOnly(), /* @ts-ignore */
5480
- ...(ngDevMode ? [{ debugName: "isReadOnly" }] : /* istanbul ignore next */ []));
5481
- this.dragHandleComponent = computed(() => this.gridConfig.dragHandleComponent, /* @ts-ignore */
5482
- ...(ngDevMode ? [{ debugName: "dragHandleComponent" }] : /* istanbul ignore next */ []));
5483
- this.actionsComponent = computed(() => this.gridConfig.actionsComponent, /* @ts-ignore */
5900
+ this.ghostRef = viewChild('ghostRef', /* @ts-ignore */
5901
+ ...(ngDevMode ? [{ debugName: "ghostRef" }] : /* istanbul ignore next */ []));
5902
+ this.actionsComponent = computed(() => {
5903
+ const configured = this.gridConfig.actionsComponent;
5904
+ return configured === undefined ? GridItemDefaultActionsComponent : configured;
5905
+ }, /* @ts-ignore */
5484
5906
  ...(ngDevMode ? [{ debugName: "actionsComponent" }] : /* istanbul ignore next */ []));
5485
5907
  this.registeredItems = computed(() => {
5486
5908
  const registrations = this.gridConfig.registrations;
@@ -5506,7 +5928,7 @@ class GridComponent {
5506
5928
  });
5507
5929
  }
5508
5930
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
5509
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.5", type: GridComponent, isStandalone: true, selector: "et-grid, [et-grid]", host: { attributes: { "role": "region" }, properties: { "attr.aria-label": "ariaLabel()", "style.--_et-grid-columns": "gridColumns()", "style.--et-grid-gap": "gridGap()", "style.--et-grid-row-height": "gridRowHeight()" }, classAttribute: "et-grid" }, viewQueries: [{ propertyName: "ghostRef", first: true, predicate: ["ghostRef"], descendants: true, isSignal: true }], hostDirectives: [{ directive: GridDirective, inputs: ["breakpoints", "breakpoints", "rowHeight", "rowHeight", "gap", "gap", "initialItems", "initialItems", "readOnly", "readOnly"], outputs: ["layoutChange", "layoutChange"] }], ngImport: i0, template: `
5931
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.5", type: GridComponent, isStandalone: true, selector: "et-grid, [et-grid]", host: { attributes: { "role": "region" }, properties: { "class.et-grid--readonly": "grid.readOnly()", "attr.aria-label": "ariaLabel()", "style.--_et-grid-columns": "gridColumns()", "style.--et-grid-gap": "gridGap()", "style.--et-grid-row-height": "gridRowHeight()" }, classAttribute: "et-grid" }, viewQueries: [{ propertyName: "ghostRef", first: true, predicate: ["ghostRef"], descendants: true, isSignal: true }], hostDirectives: [{ directive: GridDirective, inputs: ["breakpoints", "breakpoints", "rowHeight", "rowHeight", "gap", "gap", "initialItems", "initialItems", "readOnly", "readOnly"], outputs: ["layoutChange", "layoutChange"] }], ngImport: i0, template: `
5510
5932
  @for (entry of registeredItems(); track entry.item.id) {
5511
5933
  <et-grid-item
5512
5934
  [itemId]="entry.item.id"
@@ -5515,16 +5937,6 @@ class GridComponent {
5515
5937
  [minRowSpan]="entry.reg.constraints?.minRowSpan ?? 1"
5516
5938
  [maxRowSpan]="entry.reg.constraints?.maxRowSpan ?? 4"
5517
5939
  >
5518
- @if (dragHandleComponent()) {
5519
- <div etGridItemDragHandle>
5520
- <ng-container
5521
- [ngComponentOutlet]="dragHandleComponent()!"
5522
- [ngComponentOutletInputs]="{ data: entry.item.data, itemId: entry.item.id }"
5523
- />
5524
- </div>
5525
- } @else {
5526
- <div etGridItemDragHandle></div>
5527
- }
5528
5940
  <ng-container [ngComponentOutlet]="entry.reg.component" [ngComponentOutletInputs]="{ data: entry.item.data }" />
5529
5941
  @if (actionsComponent()) {
5530
5942
  <div etGridItemAction>
@@ -5533,8 +5945,6 @@ class GridComponent {
5533
5945
  [ngComponentOutletInputs]="{ data: entry.item.data, itemId: entry.item.id }"
5534
5946
  />
5535
5947
  </div>
5536
- } @else if (!isReadOnly()) {
5537
- <button (click)="grid.removeItem(entry.item.id)" etGridItemAction>✕</button>
5538
5948
  }
5539
5949
  </et-grid-item>
5540
5950
  }
@@ -5547,7 +5957,7 @@ class GridComponent {
5547
5957
  class="et-grid-ghost"
5548
5958
  ></div>
5549
5959
  }
5550
- `, isInline: true, styles: ["@property --et-grid-gap{syntax: \"<length>\"; inherits: false; initial-value: 16px;}@property --et-grid-row-height{syntax: \"<length>\"; inherits: false; initial-value: 100px;}@property --et-grid-padding{syntax: \"<length>\"; inherits: false; initial-value: 0px;}.et-grid{display:grid;grid-template-columns:repeat(var(--_et-grid-columns, 12),1fr);grid-auto-rows:var(--et-grid-row-height);gap:var(--et-grid-gap);padding:var(--et-grid-padding);position:relative;min-height:0}.et-grid:has(.et-grid-item--dragging,.et-grid-item--resizing){-webkit-user-select:none;user-select:none;cursor:grabbing}.et-grid:has(.et-grid-item--resizing){cursor:nwse-resize}.et-grid-ghost{border-radius:8px;background:rgb(var(--et-surface-color, 23 23 23) / .08);border:2px dashed rgb(var(--et-surface-color, 23 23 23) / .2);pointer-events:none;transition:grid-column 0s,grid-row 0s}.et-grid--readonly .et-grid-item__drag-handle{cursor:default;pointer-events:none}.et-grid--readonly .et-grid-item__actions{display:none}.et-grid--readonly .et-grid-item:hover .et-resize-handle--e:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--s:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--w:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--n:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--se:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--sw:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--ne:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--nw:after{content:unset}\n"], dependencies: [{ kind: "component", type: GridItemComponent, selector: "et-grid-item, [et-grid-item]", inputs: ["ariaLabel"], outputs: ["removed"] }, { kind: "directive", type: NgComponentOutlet, selector: "[ngComponentOutlet]", inputs: ["ngComponentOutlet", "ngComponentOutletInputs", "ngComponentOutletInjector", "ngComponentOutletEnvironmentInjector", "ngComponentOutletContent", "ngComponentOutletNgModule"], exportAs: ["ngComponentOutlet"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
5960
+ `, isInline: true, styles: ["@property --et-grid-gap{syntax: \"<length>\"; inherits: false; initial-value: 16px;}@property --et-grid-row-height{syntax: \"<length>\"; inherits: false; initial-value: 100px;}@property --et-grid-padding{syntax: \"<length>\"; inherits: false; initial-value: 0px;}.et-grid{display:grid;grid-template-columns:repeat(var(--_et-grid-columns, 12),1fr);grid-auto-rows:var(--et-grid-row-height);gap:var(--et-grid-gap);padding:var(--et-grid-padding);position:relative;min-height:0}.et-grid:has(.et-grid-item--dragging,.et-grid-item--resizing){-webkit-user-select:none;user-select:none;cursor:grabbing}.et-grid:has(.et-grid-item--resizing){cursor:nwse-resize}.et-grid-ghost{border-radius:8px;background:rgb(var(--et-surface-color, 23 23 23) / .08);border:2px dashed rgb(var(--et-surface-color, 23 23 23) / .2);pointer-events:none;transition:grid-column 0s,grid-row 0s}.et-grid--readonly .et-grid-item__actions{display:none}.et-grid--readonly .et-grid-item:hover .et-resize-handle--e:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--s:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--w:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--n:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--se:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--sw:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--ne:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--nw:after{content:unset}\n"], dependencies: [{ kind: "component", type: GridItemComponent, selector: "et-grid-item, [et-grid-item]", inputs: ["ariaLabel"], outputs: ["removed"] }, { kind: "directive", type: NgComponentOutlet, selector: "[ngComponentOutlet]", inputs: ["ngComponentOutlet", "ngComponentOutletInputs", "ngComponentOutletInjector", "ngComponentOutletEnvironmentInjector", "ngComponentOutletContent", "ngComponentOutletNgModule"], exportAs: ["ngComponentOutlet"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
5551
5961
  }
5552
5962
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: GridComponent, decorators: [{
5553
5963
  type: Component,
@@ -5560,16 +5970,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
5560
5970
  [minRowSpan]="entry.reg.constraints?.minRowSpan ?? 1"
5561
5971
  [maxRowSpan]="entry.reg.constraints?.maxRowSpan ?? 4"
5562
5972
  >
5563
- @if (dragHandleComponent()) {
5564
- <div etGridItemDragHandle>
5565
- <ng-container
5566
- [ngComponentOutlet]="dragHandleComponent()!"
5567
- [ngComponentOutletInputs]="{ data: entry.item.data, itemId: entry.item.id }"
5568
- />
5569
- </div>
5570
- } @else {
5571
- <div etGridItemDragHandle></div>
5572
- }
5573
5973
  <ng-container [ngComponentOutlet]="entry.reg.component" [ngComponentOutletInputs]="{ data: entry.item.data }" />
5574
5974
  @if (actionsComponent()) {
5575
5975
  <div etGridItemAction>
@@ -5578,8 +5978,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
5578
5978
  [ngComponentOutletInputs]="{ data: entry.item.data, itemId: entry.item.id }"
5579
5979
  />
5580
5980
  </div>
5581
- } @else if (!isReadOnly()) {
5582
- <button (click)="grid.removeItem(entry.item.id)" etGridItemAction>✕</button>
5583
5981
  }
5584
5982
  </et-grid-item>
5585
5983
  }
@@ -5601,11 +5999,12 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
5601
5999
  ], host: {
5602
6000
  class: 'et-grid',
5603
6001
  role: 'region',
6002
+ '[class.et-grid--readonly]': 'grid.readOnly()',
5604
6003
  '[attr.aria-label]': 'ariaLabel()',
5605
6004
  '[style.--_et-grid-columns]': 'gridColumns()',
5606
6005
  '[style.--et-grid-gap]': 'gridGap()',
5607
6006
  '[style.--et-grid-row-height]': 'gridRowHeight()',
5608
- }, styles: ["@property --et-grid-gap{syntax: \"<length>\"; inherits: false; initial-value: 16px;}@property --et-grid-row-height{syntax: \"<length>\"; inherits: false; initial-value: 100px;}@property --et-grid-padding{syntax: \"<length>\"; inherits: false; initial-value: 0px;}.et-grid{display:grid;grid-template-columns:repeat(var(--_et-grid-columns, 12),1fr);grid-auto-rows:var(--et-grid-row-height);gap:var(--et-grid-gap);padding:var(--et-grid-padding);position:relative;min-height:0}.et-grid:has(.et-grid-item--dragging,.et-grid-item--resizing){-webkit-user-select:none;user-select:none;cursor:grabbing}.et-grid:has(.et-grid-item--resizing){cursor:nwse-resize}.et-grid-ghost{border-radius:8px;background:rgb(var(--et-surface-color, 23 23 23) / .08);border:2px dashed rgb(var(--et-surface-color, 23 23 23) / .2);pointer-events:none;transition:grid-column 0s,grid-row 0s}.et-grid--readonly .et-grid-item__drag-handle{cursor:default;pointer-events:none}.et-grid--readonly .et-grid-item__actions{display:none}.et-grid--readonly .et-grid-item:hover .et-resize-handle--e:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--s:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--w:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--n:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--se:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--sw:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--ne:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--nw:after{content:unset}\n"] }]
6007
+ }, styles: ["@property --et-grid-gap{syntax: \"<length>\"; inherits: false; initial-value: 16px;}@property --et-grid-row-height{syntax: \"<length>\"; inherits: false; initial-value: 100px;}@property --et-grid-padding{syntax: \"<length>\"; inherits: false; initial-value: 0px;}.et-grid{display:grid;grid-template-columns:repeat(var(--_et-grid-columns, 12),1fr);grid-auto-rows:var(--et-grid-row-height);gap:var(--et-grid-gap);padding:var(--et-grid-padding);position:relative;min-height:0}.et-grid:has(.et-grid-item--dragging,.et-grid-item--resizing){-webkit-user-select:none;user-select:none;cursor:grabbing}.et-grid:has(.et-grid-item--resizing){cursor:nwse-resize}.et-grid-ghost{border-radius:8px;background:rgb(var(--et-surface-color, 23 23 23) / .08);border:2px dashed rgb(var(--et-surface-color, 23 23 23) / .2);pointer-events:none;transition:grid-column 0s,grid-row 0s}.et-grid--readonly .et-grid-item__actions{display:none}.et-grid--readonly .et-grid-item:hover .et-resize-handle--e:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--s:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--w:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--n:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--se:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--sw:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--ne:after,.et-grid--readonly .et-grid-item:hover .et-resize-handle--nw:after{content:unset}\n"] }]
5609
6008
  }], ctorParameters: () => [], propDecorators: { ghostRef: [{ type: i0.ViewChild, args: ['ghostRef', { isSignal: true }] }] } });
5610
6009
 
5611
6010
  const posEq = (a, b) => {
@@ -5947,7 +6346,13 @@ const GRID_ERROR_CODES = {
5947
6346
  INVALID_LAYOUT_STATE: 1903,
5948
6347
  };
5949
6348
 
5950
- const GridImports = [GridComponent, GridItemComponent, GridDebugComponent];
6349
+ const GridImports = [
6350
+ GridComponent,
6351
+ GridItemComponent,
6352
+ GridItemToolbarComponent,
6353
+ GridItemDefaultActionsComponent,
6354
+ GridDebugComponent,
6355
+ ];
5951
6356
 
5952
6357
  const NOTIFICATION_ERROR_CODES = {
5953
6358
  ACTION_OUTSIDE_NOTIFICATION: 1700,
@@ -6663,6 +7068,10 @@ class OverlayContainerComponent {
6663
7068
  this.destroyRef = inject(DestroyRef);
6664
7069
  this.elementRef = inject(ElementRef);
6665
7070
  this.overlayRef = inject(OVERLAY_REF);
7071
+ this.surfaceThemes = injectSurfaceThemes({ optional: true });
7072
+ this.surfaceContextTracker = injectSurfaceContextTracker();
7073
+ this.renderer = injectRenderer();
7074
+ this.rootBoundary = injectBoundaryElement();
6666
7075
  this.component = input.required(/* @ts-ignore */
6667
7076
  ...(ngDevMode ? [{ debugName: "component" }] : /* istanbul ignore next */ []));
6668
7077
  this.componentInputs = input(undefined, /* @ts-ignore */
@@ -6672,10 +7081,6 @@ class OverlayContainerComponent {
6672
7081
  this.renderArrow = input(false, /* @ts-ignore */
6673
7082
  ...(ngDevMode ? [{ debugName: "renderArrow" }] : /* istanbul ignore next */ []));
6674
7083
  this.contentOutlet = viewChild.required('contentOutlet', { read: ViewContainerRef });
6675
- this.surfaceThemes = injectSurfaceThemes({ optional: true });
6676
- this.surfaceContextTracker = injectSurfaceContextTracker();
6677
- this.renderer = injectRenderer();
6678
- this.rootBoundary = injectBoundaryElement();
6679
7084
  this.animatedLifecycle = signal(inject(ANIMATED_LIFECYCLE_TOKEN), /* @ts-ignore */
6680
7085
  ...(ngDevMode ? [{ debugName: "animatedLifecycle" }] : /* istanbul ignore next */ []));
6681
7086
  this.contentComponentRef = signal(null, /* @ts-ignore */
@@ -8464,6 +8869,7 @@ const topSheetOverlayStrategy = (config = {}) => {
8464
8869
  class OverlayDirective {
8465
8870
  constructor() {
8466
8871
  this.destroyRef = inject(DestroyRef);
8872
+ this.overlayManager = injectOverlayManager();
8467
8873
  this.mode = input('non-modal', /* @ts-ignore */
8468
8874
  ...(ngDevMode ? [{ debugName: "mode" }] : /* istanbul ignore next */ []));
8469
8875
  this.role = input(undefined, /* @ts-ignore */
@@ -8508,7 +8914,6 @@ class OverlayDirective {
8508
8914
  ...(ngDevMode ? [{ debugName: "autoCloseIfReferenceHidden" }] : /* istanbul ignore next */ []));
8509
8915
  this.mirrorWidth = input(false, /* @ts-ignore */
8510
8916
  ...(ngDevMode ? [{ debugName: "mirrorWidth" }] : /* istanbul ignore next */ []));
8511
- this.overlayManager = injectOverlayManager();
8512
8917
  /** @internal */
8513
8918
  this.registeredAnchor = signal(null, /* @ts-ignore */
8514
8919
  ...(ngDevMode ? [{ debugName: "registeredAnchor" }] : /* istanbul ignore next */ []));
@@ -8778,9 +9183,9 @@ class OverlayBodyComponent {
8778
9183
  this.overlayRef = inject(OVERLAY_REF, { optional: true });
8779
9184
  this.elementRef = inject(ElementRef);
8780
9185
  this.scrollObserver = inject(ScrollObserverDirective);
9186
+ this.overlayManager = injectOverlayManager();
8781
9187
  this.dividers = input(false, /* @ts-ignore */
8782
9188
  ...(ngDevMode ? [{ debugName: "dividers" }] : /* istanbul ignore next */ []));
8783
- this.overlayManager = injectOverlayManager();
8784
9189
  this.dividersEnabled = computed(() => this.dividers() === 'dynamic' || this.dividers() === 'static', /* @ts-ignore */
8785
9190
  ...(ngDevMode ? [{ debugName: "dividersEnabled" }] : /* istanbul ignore next */ []));
8786
9191
  this.dynamicDividersEnabled = computed(() => this.dividers() === 'dynamic', /* @ts-ignore */
@@ -8868,12 +9273,12 @@ class OverlayCloseDirective {
8868
9273
  constructor() {
8869
9274
  this.overlayRef = inject(OVERLAY_REF, { optional: true });
8870
9275
  this.elementRef = inject(ElementRef);
9276
+ this.overlayManager = injectOverlayManager();
8871
9277
  this.ariaLabel = input(undefined, { ...(ngDevMode ? { debugName: "ariaLabel" } : /* istanbul ignore next */ {}), alias: 'aria-label' });
8872
9278
  this.type = input('button', /* @ts-ignore */
8873
9279
  ...(ngDevMode ? [{ debugName: "type" }] : /* istanbul ignore next */ []));
8874
9280
  this.closeResult = input(undefined, { ...(ngDevMode ? { debugName: "closeResult" } : /* istanbul ignore next */ {}), alias: 'etOverlayClose' });
8875
9281
  this.closeResultAlt = input(undefined, { ...(ngDevMode ? { debugName: "closeResultAlt" } : /* istanbul ignore next */ {}), alias: 'et-overlay-close' });
8876
- this.overlayManager = injectOverlayManager();
8877
9282
  applyHostListener('click', () => {
8878
9283
  const overlayRef = this.overlayRef ?? getClosestOverlay(this.elementRef, this.overlayManager.openOverlays());
8879
9284
  overlayRef?.close(this.closeResult() ?? this.closeResultAlt());
@@ -9192,8 +9597,8 @@ class OverlayMainDirective {
9192
9597
  this.parent = inject(OVERLAY_MAIN_TOKEN, { optional: true, skipSelf: true });
9193
9598
  this.elementRef = inject(ElementRef);
9194
9599
  this.overlayRef = inject(OVERLAY_REF, { optional: true });
9195
- this.enabled = input(true, { ...(ngDevMode ? { debugName: "enabled" } : /* istanbul ignore next */ {}), alias: 'etOverlayMain', transform: booleanAttribute });
9196
9600
  this.overlayManager = injectOverlayManager();
9601
+ this.enabled = input(true, { ...(ngDevMode ? { debugName: "enabled" } : /* istanbul ignore next */ {}), alias: 'etOverlayMain', transform: booleanAttribute });
9197
9602
  }
9198
9603
  ngOnInit() {
9199
9604
  this.overlayRef = resolveClosestOverlay({
@@ -9280,10 +9685,10 @@ class OverlayTitleDirective {
9280
9685
  constructor() {
9281
9686
  this.overlayRef = inject(OVERLAY_REF, { optional: true });
9282
9687
  this.elementRef = inject(ElementRef);
9283
- this.id = input(`et-overlay-title-${uniqueId++}`, /* @ts-ignore */
9284
- ...(ngDevMode ? [{ debugName: "id" }] : /* istanbul ignore next */ []));
9285
9688
  this.overlayManager = injectOverlayManager();
9286
9689
  this.renderer = injectRenderer();
9690
+ this.id = input(`et-overlay-title-${uniqueId++}`, /* @ts-ignore */
9691
+ ...(ngDevMode ? [{ debugName: "id" }] : /* istanbul ignore next */ []));
9287
9692
  }
9288
9693
  ngOnInit() {
9289
9694
  this.overlayRef = resolveClosestOverlay({
@@ -9581,8 +9986,8 @@ class OverlayBackOrCloseDirective {
9581
9986
  constructor() {
9582
9987
  this.overlayRef = inject(OVERLAY_REF);
9583
9988
  this.elementRef = inject(ElementRef);
9584
- this.disabled = input(false, { ...(ngDevMode ? { debugName: "disabled" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
9585
9989
  this.router = injectOverlayRouter();
9990
+ this.disabled = input(false, { ...(ngDevMode ? { debugName: "disabled" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
9586
9991
  fromEvent(this.elementRef.nativeElement, 'click')
9587
9992
  .pipe(filter(() => !this.disabled()), tap(() => {
9588
9993
  if (!this.router.back()) {
@@ -9619,8 +10024,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
9619
10024
  class OverlayRouteHeaderTemplateOutletComponent {
9620
10025
  constructor() {
9621
10026
  this.overlay = inject(OVERLAY_REF);
9622
- this.animatedLifecycle = viewChild.required(ANIMATED_LIFECYCLE_TOKEN);
9623
10027
  this.router = injectOverlayRouter();
10028
+ this.animatedLifecycle = viewChild.required(ANIMATED_LIFECYCLE_TOKEN);
9624
10029
  }
9625
10030
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: OverlayRouteHeaderTemplateOutletComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
9626
10031
  static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.2.0", version: "22.0.5", type: OverlayRouteHeaderTemplateOutletComponent, isStandalone: true, selector: "et-overlay-route-header-template-outlet", host: { properties: { "class.et-overlay-router-outlet-nav-dir--backward": "router.navigationDirection() === 'backward'", "class.et-overlay-router-outlet-nav-dir--forward": "router.navigationDirection() === 'forward'" }, classAttribute: "et-overlay-route-header-template-outlet-host" }, viewQueries: [{ propertyName: "animatedLifecycle", first: true, predicate: ANIMATED_LIFECYCLE_TOKEN, descendants: true, isSignal: true }], ngImport: i0, template: `
@@ -9654,11 +10059,11 @@ const OVERLAY_ROUTER_LINK_TOKEN = new InjectionToken('OVERLAY_ROUTER_LINK_TOKEN'
9654
10059
  class OverlayRouterLinkDirective {
9655
10060
  constructor() {
9656
10061
  this.elementRef = inject(ElementRef);
10062
+ this.router = injectOverlayRouter();
9657
10063
  this.path = input.required({ ...(ngDevMode ? { debugName: "path" } : /* istanbul ignore next */ {}), alias: 'etOverlayRouterLink' });
9658
10064
  this.disabled = input(false, { ...(ngDevMode ? { debugName: "disabled" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
9659
10065
  this.navigationDirection = input(null, /* @ts-ignore */
9660
10066
  ...(ngDevMode ? [{ debugName: "navigationDirection" }] : /* istanbul ignore next */ []));
9661
- this.router = injectOverlayRouter();
9662
10067
  this.isActive = computed(() => this.router.resolvePath(this.path()).route === this.router.currentRoute(), /* @ts-ignore */
9663
10068
  ...(ngDevMode ? [{ debugName: "isActive" }] : /* istanbul ignore next */ []));
9664
10069
  fromEvent(this.elementRef.nativeElement, 'click')
@@ -9867,13 +10272,13 @@ class OverlayRouterOutletComponent {
9867
10272
  this.injector = inject(Injector);
9868
10273
  this.overlayRef = inject(OVERLAY_REF, { optional: true });
9869
10274
  this.elementRef = inject(ElementRef);
10275
+ this.router = injectOverlayRouter();
10276
+ this.renderer = injectRenderer();
9870
10277
  this.disabled = input(false, { ...(ngDevMode ? { debugName: "disabled" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
9871
10278
  this.sharedRouteTemplate = contentChild(OVERLAY_SHARED_ROUTE_TEMPLATE_TOKEN, { ...(ngDevMode ? { debugName: "sharedRouteTemplate" } : /* istanbul ignore next */ {}), read: TemplateRef });
9872
10279
  this.outletDisabledTemplate = contentChild(OVERLAY_ROUTER_OUTLET_DISABLED_TEMPLATE_TOKEN, { ...(ngDevMode ? { debugName: "outletDisabledTemplate" } : /* istanbul ignore next */ {}), read: TemplateRef });
9873
10280
  this.pageWrappers = viewChildren('pageWrapper', /* @ts-ignore */
9874
10281
  ...(ngDevMode ? [{ debugName: "pageWrappers" }] : /* istanbul ignore next */ []));
9875
- this.router = injectOverlayRouter();
9876
- this.renderer = injectRenderer();
9877
10282
  this.hasSidebar = !!injectSidebarOverlay({ optional: true });
9878
10283
  this.wasDisabled = signal(false, /* @ts-ignore */
9879
10284
  ...(ngDevMode ? [{ debugName: "wasDisabled" }] : /* istanbul ignore next */ []));
@@ -10046,12 +10451,12 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
10046
10451
 
10047
10452
  class OverlaySidebarComponent {
10048
10453
  constructor() {
10454
+ this.sidebar = injectSidebarOverlay();
10049
10455
  this.pageDividers = input(false, /* @ts-ignore */
10050
10456
  ...(ngDevMode ? [{ debugName: "pageDividers" }] : /* istanbul ignore next */ []));
10051
10457
  this.sidebarContent = viewChild.required('sidebarContentTpl');
10052
10458
  this.sidebarHeaderContent = contentChild(OVERLAY_HEADER_TEMPLATE_TOKEN, /* @ts-ignore */
10053
10459
  ...(ngDevMode ? [{ debugName: "sidebarHeaderContent" }] : /* istanbul ignore next */ []));
10054
- this.sidebar = injectSidebarOverlay();
10055
10460
  syncSignal(this.sidebarContent, this.sidebar.sidebarContentTemplate, { skipSyncRead: true });
10056
10461
  syncSignal(this.sidebarHeaderContent, this.sidebar.sidebarHeaderTemplate);
10057
10462
  syncSignal(this.pageDividers, this.sidebar.sidebarPageDividers);
@@ -11532,9 +11937,9 @@ class PipBackDirective {
11532
11937
  constructor() {
11533
11938
  this.chrome = inject(PIP_CHROME_REF_TOKEN, { optional: true });
11534
11939
  this.tokenEntry = inject(PIP_ENTRY_TOKEN, { optional: true });
11940
+ this.pipManager = injectPipManager();
11535
11941
  this.entry = input(/* @ts-ignore */
11536
11942
  ...(ngDevMode ? [undefined, { debugName: "entry" }] : /* istanbul ignore next */ []));
11537
- this.pipManager = injectPipManager();
11538
11943
  }
11539
11944
  back(event) {
11540
11945
  event.stopPropagation();
@@ -12002,13 +12407,13 @@ class PipPlayerComponent {
12002
12407
  this.document = inject(DOCUMENT$1);
12003
12408
  this.el = inject(ElementRef);
12004
12409
  this.pipCell = inject(PipCellDirective, { optional: true });
12410
+ this.streamManager = injectStreamManager();
12411
+ this.pipManager = injectPipManager();
12412
+ this.renderer = injectRenderer();
12005
12413
  this.entry = input(/* @ts-ignore */
12006
12414
  ...(ngDevMode ? [undefined, { debugName: "entry" }] : /* istanbul ignore next */ []));
12007
12415
  this.showThumbnail = input(/* @ts-ignore */
12008
12416
  ...(ngDevMode ? [undefined, { debugName: "showThumbnail" }] : /* istanbul ignore next */ []));
12009
- this.streamManager = injectStreamManager();
12010
- this.pipManager = injectPipManager();
12011
- this.renderer = injectRenderer();
12012
12417
  this.isReady = signal(false, /* @ts-ignore */
12013
12418
  ...(ngDevMode ? [{ debugName: "isReady" }] : /* istanbul ignore next */ []));
12014
12419
  this.resolvedEntry = computed(() => this.entry() ?? this.pipCell?.cell().pip ?? null, /* @ts-ignore */
@@ -12104,11 +12509,11 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImpor
12104
12509
 
12105
12510
  class StreamPipChromeComponent {
12106
12511
  constructor() {
12512
+ this.pipManager = injectPipManager();
12107
12513
  this.stageRef = viewChild(PipStageDirective, { ...(ngDevMode ? { debugName: "stageRef" } : /* istanbul ignore next */ {}), read: ElementRef });
12108
12514
  this.pipWindowRef = viewChild(PipWindowComponent, /* @ts-ignore */
12109
12515
  ...(ngDevMode ? [{ debugName: "pipWindowRef" }] : /* istanbul ignore next */ []));
12110
12516
  this.gridBtnRef = viewChild(PipGridToggleDirective, { ...(ngDevMode ? { debugName: "gridBtnRef" } : /* istanbul ignore next */ {}), read: ElementRef });
12111
- this.pipManager = injectPipManager();
12112
12517
  this.state = createPipChromeState();
12113
12518
  this.animations = createPipChromeAnimations(this.state, {
12114
12519
  stageRef: this.stageRef,
@@ -12712,9 +13117,9 @@ class PipCloseDirective {
12712
13117
  this.chrome = inject(PIP_CHROME_REF_TOKEN, { optional: true });
12713
13118
  this.pipWindow = inject(PipWindowComponent, { optional: true });
12714
13119
  this.tokenEntry = inject(PIP_ENTRY_TOKEN, { optional: true });
13120
+ this.pipManager = injectPipManager();
12715
13121
  this.entry = input(/* @ts-ignore */
12716
13122
  ...(ngDevMode ? [undefined, { debugName: "entry" }] : /* istanbul ignore next */ []));
12717
- this.pipManager = injectPipManager();
12718
13123
  }
12719
13124
  close(event) {
12720
13125
  event.stopPropagation();
@@ -12759,12 +13164,12 @@ class PipSlotPlaceholderComponent {
12759
13164
  constructor() {
12760
13165
  this.slotPlayerId = inject(STREAM_SLOT_PLAYER_ID_TOKEN);
12761
13166
  this.parentSurfaceProvider = inject(SURFACE_PROVIDER, { optional: true, skipSelf: true });
12762
- this.bringBackDir = viewChild(PipBringBackDirective, /* @ts-ignore */
12763
- ...(ngDevMode ? [{ debugName: "bringBackDir" }] : /* istanbul ignore next */ []));
12764
13167
  this.pipManager = injectPipManager();
12765
13168
  this.config = injectPipSlotPlaceholderConfig();
12766
13169
  this.locale = injectLocale();
12767
13170
  this.surfaceThemes = injectSurfaceThemes({ optional: true });
13171
+ this.bringBackDir = viewChild(PipBringBackDirective, /* @ts-ignore */
13172
+ ...(ngDevMode ? [{ debugName: "bringBackDir" }] : /* istanbul ignore next */ []));
12768
13173
  this.cardSurface = computed(() => {
12769
13174
  const themes = this.surfaceThemes;
12770
13175
  if (!themes)
@@ -13159,11 +13564,11 @@ class StreamPlayerSlotDirective {
13159
13564
  this.playerComponent = inject(STREAM_PLAYER_COMPONENT_TOKEN);
13160
13565
  this.provideSurface = inject(ProvideSurfaceDirective);
13161
13566
  this.parentSurfaceProvider = inject(SURFACE_PROVIDER, { optional: true, skipSelf: true });
13567
+ this.surfaceThemes = injectSurfaceThemes({ optional: true });
13568
+ this.styleManager = injectStyleManager();
13162
13569
  this.streamSlotPriority = input(false, { ...(ngDevMode ? { debugName: "streamSlotPriority" } : /* istanbul ignore next */ {}), transform: booleanAttribute });
13163
13570
  this.streamSlotOnPipBack = input(/* @ts-ignore */
13164
13571
  ...(ngDevMode ? [undefined, { debugName: "streamSlotOnPipBack" }] : /* istanbul ignore next */ []));
13165
- this.surfaceThemes = injectSurfaceThemes({ optional: true });
13166
- this.styleManager = injectStyleManager();
13167
13572
  this.resolvedSurface = computed(() => {
13168
13573
  const themes = this.surfaceThemes;
13169
13574
  if (!themes)
@@ -16199,6 +16604,7 @@ class ToggletipComponent {
16199
16604
  this.triggerColorProvider = inject(COLOR_PROVIDER, { optional: true, skipSelf: true });
16200
16605
  this.triggerSurfaceProvider = inject(SURFACE_PROVIDER, { optional: true, skipSelf: true });
16201
16606
  this.injector = inject(Injector);
16607
+ this.surfaceThemes = injectSurfaceThemes({ optional: true });
16202
16608
  this.toggletipId = input.required(/* @ts-ignore */
16203
16609
  ...(ngDevMode ? [{ debugName: "toggletipId" }] : /* istanbul ignore next */ []));
16204
16610
  this.contentId = input.required(/* @ts-ignore */
@@ -16209,7 +16615,6 @@ class ToggletipComponent {
16209
16615
  ...(ngDevMode ? [{ debugName: "colorProvider" }] : /* istanbul ignore next */ []));
16210
16616
  this.surfaceProvider = input.required(/* @ts-ignore */
16211
16617
  ...(ngDevMode ? [{ debugName: "surfaceProvider" }] : /* istanbul ignore next */ []));
16212
- this.surfaceThemes = injectSurfaceThemes({ optional: true });
16213
16618
  this.hasTemplate = computed(() => this.content() instanceof TemplateRef, /* @ts-ignore */
16214
16619
  ...(ngDevMode ? [{ debugName: "hasTemplate" }] : /* istanbul ignore next */ []));
16215
16620
  this.contentText = computed(() => {
@@ -16270,6 +16675,7 @@ class ToggletipDirective {
16270
16675
  this.elementRef = inject(ElementRef);
16271
16676
  this.colorProvider = inject(COLOR_PROVIDER, { optional: true });
16272
16677
  this.surfaceProvider = inject(SURFACE_PROVIDER, { optional: true });
16678
+ this.overlayManager = injectOverlayManager();
16273
16679
  this.content = input(null, { ...(ngDevMode ? { debugName: "content" } : /* istanbul ignore next */ {}), alias: 'etToggletip' });
16274
16680
  this.ariaLabel = input(null, { ...(ngDevMode ? { debugName: "ariaLabel" } : /* istanbul ignore next */ {}), alias: 'etToggletipAriaLabel' });
16275
16681
  this.ariaLabelledBy = input(null, { ...(ngDevMode ? { debugName: "ariaLabelledBy" } : /* istanbul ignore next */ {}), alias: 'etToggletipAriaLabelledBy' });
@@ -16285,7 +16691,6 @@ class ToggletipDirective {
16285
16691
  ...(ngDevMode ? [{ debugName: "viewportPadding" }] : /* istanbul ignore next */ []));
16286
16692
  this.disabled = input(false, { ...(ngDevMode ? { debugName: "disabled" } : /* istanbul ignore next */ {}), alias: 'etToggletipDisabled' });
16287
16693
  this.open = model(false, { ...(ngDevMode ? { debugName: "open" } : /* istanbul ignore next */ {}), alias: 'etToggletipOpen' });
16288
- this.overlayManager = injectOverlayManager();
16289
16694
  /** @internal */
16290
16695
  this.overlayRef = signal(null, /* @ts-ignore */
16291
16696
  ...(ngDevMode ? [{ debugName: "overlayRef" }] : /* istanbul ignore next */ []));
@@ -16537,6 +16942,7 @@ class TooltipComponent {
16537
16942
  this.ownSurfaceProvider = inject(ProvideSurfaceDirective);
16538
16943
  this.triggerColorProvider = inject(COLOR_PROVIDER, { optional: true, skipSelf: true });
16539
16944
  this.triggerSurfaceProvider = inject(SURFACE_PROVIDER, { optional: true, skipSelf: true });
16945
+ this.surfaceThemes = injectSurfaceThemes({ optional: true });
16540
16946
  this.tooltipId = input.required(/* @ts-ignore */
16541
16947
  ...(ngDevMode ? [{ debugName: "tooltipId" }] : /* istanbul ignore next */ []));
16542
16948
  this.content = input.required(/* @ts-ignore */
@@ -16545,7 +16951,6 @@ class TooltipComponent {
16545
16951
  ...(ngDevMode ? [{ debugName: "colorProvider" }] : /* istanbul ignore next */ []));
16546
16952
  this.surfaceProvider = input.required(/* @ts-ignore */
16547
16953
  ...(ngDevMode ? [{ debugName: "surfaceProvider" }] : /* istanbul ignore next */ []));
16548
- this.surfaceThemes = injectSurfaceThemes({ optional: true });
16549
16954
  this.hasTemplate = computed(() => this.content() instanceof TemplateRef, /* @ts-ignore */
16550
16955
  ...(ngDevMode ? [{ debugName: "hasTemplate" }] : /* istanbul ignore next */ []));
16551
16956
  this.contentText = computed(() => {
@@ -16609,6 +17014,9 @@ class TooltipDirective {
16609
17014
  this.elementRef = inject(ElementRef);
16610
17015
  this.colorProvider = inject(COLOR_PROVIDER, { optional: true });
16611
17016
  this.surfaceProvider = inject(SURFACE_PROVIDER, { optional: true });
17017
+ this.overlayManager = injectOverlayManager();
17018
+ this.focusVisibleTracker = injectFocusVisibleTracker();
17019
+ this.renderer = injectRenderer();
16612
17020
  this.content = input(null, { ...(ngDevMode ? { debugName: "content" } : /* istanbul ignore next */ {}), alias: 'etTooltip' });
16613
17021
  this.ariaDescription = input(null, { ...(ngDevMode ? { debugName: "ariaDescription" } : /* istanbul ignore next */ {}), alias: 'etTooltipAriaDescription' });
16614
17022
  this.placement = input('top', /* @ts-ignore */
@@ -16624,9 +17032,6 @@ class TooltipDirective {
16624
17032
  this.showDelay = input(DEFAULT_TOOLTIP_DELAY, /* @ts-ignore */
16625
17033
  ...(ngDevMode ? [{ debugName: "showDelay" }] : /* istanbul ignore next */ []));
16626
17034
  this.disabled = input(false, { ...(ngDevMode ? { debugName: "disabled" } : /* istanbul ignore next */ {}), alias: 'etTooltipDisabled' });
16627
- this.overlayManager = injectOverlayManager();
16628
- this.focusVisibleTracker = injectFocusVisibleTracker();
16629
- this.renderer = injectRenderer();
16630
17035
  /** @internal */
16631
17036
  this.overlayRef = signal(null, /* @ts-ignore */
16632
17037
  ...(ngDevMode ? [{ debugName: "overlayRef" }] : /* istanbul ignore next */ []));
@@ -16830,5 +17235,5 @@ const TOOLTIP_IMPORTS = [TooltipDirective, TooltipComponent];
16830
17235
  * Generated bundle index. Do not edit.
16831
17236
  */
16832
17237
 
16833
- export { ARROW_OUT_UP_RIGHT_ICON, ARROW_RIGHT_ICON, BOLD_ICON, BUTTON_ICON_ALIGNMENTS, BUTTON_IMPORTS, BUTTON_SIZES, BUTTON_SPINNER_CONFIG, BUTTON_TYPES, BUTTON_VARIANTS, BrandLoaderComponent, ButtonComponent, ButtonDirective, ButtonStylesDirective, CHECKBOX_IMPORTS, CHEVRON_ICON, CHOICE_FIELD_IMPORTS, CLIPBOARD_CHECK_ICON, CheckboxComponent, CheckboxDirective, CheckboxGroupComponent, CheckboxOptionComponent, ChoiceFieldComponent, DAILYMOTION_PLAYER_TOKEN, DEFAULT_NOTIFICATION_MANAGER_CONFIG, DEFAULT_PIP_WINDOW_CONFIG, DEFAULT_STREAM_PLAYER_STATE, DailymotionPlayerComponent, DailymotionPlayerDirective, DailymotionPlayerParamsDirective, DailymotionPlayerSlotComponent, DescriptionComponent, FACEBOOK_PLAYER_TOKEN, FLOPPY_DISK_ICON, FOCUS_FRAME_ICON, FORM_FIELD_APPEARANCES, FORM_FIELD_CONTROL_TYPES, FORM_FIELD_ERROR_CODES, FORM_FIELD_FILLS, FORM_FIELD_IMPORTS, FORM_FIELD_LABEL_MODES, FORM_FIELD_SIZES, FORM_FIELD_TOKEN, FabComponent, FacebookPlayerComponent, FacebookPlayerDirective, FacebookPlayerParamsDirective, FacebookPlayerSlotComponent, FocusRingDirective, FormErrorComponent, FormFieldComponent, FormFieldDirective, GRID_2X2_ICON, GRID_ERROR_CODES, GRID_TOKEN, GridComponent, GridDebugComponent, GridDirective, GridDragDirective, GridImports, GridItemComponent, GridItemDirective, GridItemRef, GridResizeDirective, HintComponent, ICONS_TOKEN, ICON_DIRECTIVE_TOKEN, ICON_ERROR_CODES, ICON_IMPORTS, INPUT_IMPORTS, INPUT_TEXT_ALIGNMENTS, INPUT_TYPES, ITALIC_ICON, IconButtonComponent, IconDirective, InputComponent, InputDirective, InputPrefixDirective, InputSuffixDirective, KICK_PLAYER_TOKEN, KickPlayerComponent, KickPlayerDirective, KickPlayerParamsDirective, KickPlayerSlotComponent, LINK_ICON, LIST_BULLETED_ICON, LIST_NUMBERED_ICON, LOCK_ICON, LabelDirective, NAV_TABS_TOKEN, NOTIFICATION_ERROR_CODES, NOTIFICATION_IMPORTS, NOTIFICATION_STACK_CONTEXT_TOKEN, NOTIFICATION_STATUS, NavTabImports, NavTabLinkComponent, NavTabLinkDirective, NavTabsComponent, NavTabsDirective, NavTabsOutletComponent, NavTabsOutletDirective, NotificationActionDirective, NotificationComponent, NotificationDirective, NotificationDismissDirective, NotificationItemDirective, NotificationStackDirective, OVERLAY_BACK_OR_CLOSE_TOKEN, OVERLAY_BODY_TOKEN, OVERLAY_CONFIG_CLASS_KEYS, OVERLAY_CONTENT_IMPORTS, OVERLAY_ERROR_CODES, OVERLAY_FOOTER_TOKEN, OVERLAY_HEADER_TEMPLATE_TOKEN, OVERLAY_HEADER_TOKEN, OVERLAY_IMPORTS, OVERLAY_MAIN_TOKEN, OVERLAY_QUERY_PARAM_INPUT_NAME, OVERLAY_REF, OVERLAY_ROUTER_CONFIG_TOKEN, OVERLAY_ROUTER_LINK_TOKEN, OVERLAY_ROUTER_OUTLET_DISABLED_TEMPLATE_TOKEN, OVERLAY_ROUTER_OUTLET_TOKEN, OVERLAY_ROUTER_TOKEN, OVERLAY_SHARED_ROUTE_TEMPLATE_TOKEN, OverlayAnchorDirective, OverlayBackOrCloseDirective, OverlayBodyComponent, OverlayCloseDirective, OverlayContainerComponent, OverlayDirective, OverlayFooterDirective, OverlayHandlerLinkDirective, OverlayHeaderDirective, OverlayHeaderTemplateDirective, OverlayMainDirective, OverlayOriginCloneComponent, OverlayRouteHeaderTemplateOutletComponent, OverlayRouterLinkDirective, OverlayRouterOutletComponent, OverlayRouterOutletDisabledTemplateDirective, OverlaySharedRouteTemplateDirective, OverlaySharedRouteTemplateOutletComponent, OverlaySidebarComponent, OverlaySidebarPageComponent, OverlaySurfaceDirective, OverlayTitleDirective, OverlayTriggerDirective, PENCIL_ICON, PIP_CHROME_REF_TOKEN, PIP_ENTRY_TOKEN, PIP_WINDOW_ASPECT_RATIO_TOKEN, PLUS_ICON, PipBackDirective, PipBringBackDirective, PipCellDirective, PipCloseDirective, PipCollapseOverlayDirective, PipGridToggleDirective, PipPlayerComponent, PipSlotPlaceholderComponent, PipStageDirective, PipTitleBarDirective, PipTitleBarTemplateDirective, PipWindowComponent, PipWindowParamsDirective, ProgressBarComponent, RICH_TEXT_EDITOR_IMPORTS, RadioComponent, RadioGroupComponent, RichTextEditorComponent, RichTextEditorDirective, RichTextEditorFloatingToolbarComponent, SCROLLABLE_IMPORTS, SELECTION_LIST_MULTIPLE, SELECTION_LIST_TOKEN, SIDEBAR_OVERLAY_CONFIG, SIDEBAR_OVERLAY_TOKEN, SOOP_PLAYER_TOKEN, STREAM_CONSENT_TOKEN, STREAM_PLAYER_COMPONENT_TOKEN, STREAM_PLAYER_ERROR_CONTEXT_TOKEN, STREAM_PLAYER_ERROR_TOKEN, STREAM_PLAYER_PARAMS_TOKEN, STREAM_PLAYER_SLOT_TOKEN, STREAM_PLAYER_TOKEN, STREAM_SLOT_PLAYER_ID_TOKEN, STREAM_USER_CONSENT_PROVIDER_TOKEN, STRIKETHROUGH_ICON, SWITCH_IMPORTS, ScrollableActiveChildDirective, ScrollableButtonsDirective, ScrollableComponent, ScrollableDarkenDirective, ScrollableDirective, ScrollableDragDirective, ScrollableErrorCode, ScrollableIgnoreChildDirective, ScrollableLoadingTemplateDirective, ScrollableMasksDirective, ScrollableNavigationDirective, ScrollableSnapDirective, SegmentedButtonComponent, SegmentedButtonGroupComponent, SelectionListControlDirective, SelectionListDirective, SelectionOptionDirective, SoopPlayerComponent, SoopPlayerDirective, SoopPlayerParamsDirective, SoopPlayerSlotComponent, SpinnerComponent, StreamConsentAcceptDirective, StreamConsentComponent, StreamConsentDirective, StreamImports, StreamPipChromeComponent, StreamPlayerErrorComponent, StreamPlayerErrorDirective, StreamPlayerLoadingComponent, StreamPlayerSlotDirective, SwitchComponent, SwitchDirective, TAB_BAR_FITS, TAB_BAR_ORIENTATIONS, TAB_BAR_TOKEN, TAB_BAR_TRIGGER_TOKEN, TAB_BAR_VARIANTS, TAB_ERROR_CODES, TAB_GROUP_TOKEN, TAB_PANEL_TOKEN, TAB_SIZES, TIKTOK_PLAYER_TOKEN, TIMES_ICON, TOGGLETIP_ERROR_CODES, TOGGLETIP_IMPORTS, TOOLTIP_ERROR_CODES, TOOLTIP_IMPORTS, TRIANGLE_EXCLAMATION_ICON, TWITCH_PLAYER_TOKEN, TabBarDirective, TabBarTriggerDirective, TabBarUnderlineDirective, TabComponent, TabGroupComponent, TabGroupDirective, TabImports, TabLabelDirective, TabPanelDirective, TabTriggerDirective, TextButtonComponent, TikTokPlayerComponent, TikTokPlayerDirective, TikTokPlayerParamsDirective, TikTokPlayerSlotComponent, ToggletipCloseDirective, ToggletipComponent, ToggletipDirective, ToggletipTriggerDirective, TooltipComponent, TooltipDirective, TwitchPlayerComponent, TwitchPlayerDirective, TwitchPlayerParamsDirective, TwitchPlayerSlotComponent, VIMEO_PLAYER_TOKEN, VimeoPlayerComponent, VimeoPlayerDirective, VimeoPlayerParamsDirective, VimeoPlayerSlotComponent, WINDOW_CONTROL_BUTTON_KINDS, WINDOW_CONTROL_BUTTON_SIZES, WindowControlButtonComponent, YOUTUBE_PLAYER_SLOT_TOKEN, YOUTUBE_PLAYER_TOKEN, YoutubePlayerComponent, YoutubePlayerDirective, YoutubePlayerParamsDirective, YoutubePlayerSlotComponent, YoutubePlayerSlotDirective, abortFullscreenAnimation, anchoredDialogOverlayStrategy, anchoredOverlayStrategy, bottomSheetOverlayStrategy, buildAnchoredRuntimePositionStrategy, centeredOverlayStrategy, cleanupFullscreenAnimation, cleanupFullscreenAnimationStyles, createGridAdapter, createNotificationRef, createOverlayHandler, createOverlayHandlerWithQueryParamLifecycle, createOverlayRef, createOverlayStrategyController, createPipChromeAnimations, createPipChromeState, createStreamConfig, createStreamPlayerSlot, dialogOverlayStrategy, enableDragToDismiss, findNextRelevantHtmlElement, fromGridPosition, fullScreenDialogOverlayStrategy, getClosestOverlay, getOriginCoordinatesAndDimensions, injectAnchoredDialogStrategy, injectAnchoredDialogStrategyDefaults, injectBottomSheetStrategy, injectBottomSheetStrategyDefaults, injectDialogStrategy, injectDialogStrategyDefaults, injectFormSupport, injectFullscreenDialogStrategy, injectFullscreenDialogStrategyDefaults, injectGridConfig, injectLeftSheetStrategy, injectLeftSheetStrategyDefaults, injectNotificationManager, injectNotificationManagerConfig, injectOverlayManager, injectOverlayRouter, injectOverlayScrollBlocker, injectPipChromeManager, injectPipManager, injectPipSlotPlaceholderConfig, injectRightSheetStrategy, injectRightSheetStrategyDefaults, injectSidebarOverlay, injectStreamConfig, injectStreamConsentConfig, injectStreamManager, injectStreamPlayerErrorConfig, injectStreamPlayerLoadingConfig, injectStreamScriptLoader, injectStreamUserConsentProvider, injectTopSheetStrategy, injectTopSheetStrategyDefaults, isHtmlElement, isPointerEvent, isTouchEvent, leftSheetOverlayStrategy, mergeOverlayBreakpointConfigs, provideAnchoredDialogStrategy, provideAnchoredDialogStrategyDefaults, provideBottomSheetStrategy, provideBottomSheetStrategyDefaults, provideDialogStrategy, provideDialogStrategyDefaults, provideFormSupport, provideFullscreenDialogStrategy, provideFullscreenDialogStrategyDefaults, provideGridConfig, provideIcons, provideLeftSheetStrategy, provideLeftSheetStrategyDefaults, provideNotificationManager, provideNotificationManagerConfig, provideNotificationManagerInstance, provideOverlay, provideOverlayManager, provideOverlayRouter, provideOverlayRouterConfig, provideOverlayRouterService, provideOverlayScrollBlocker, providePipChromeManager, providePipManager, providePipSlotPlaceholderConfig, provideRightSheetStrategy, provideRightSheetStrategyDefaults, provideSidebarOverlay, provideSidebarOverlayConfig, provideSidebarOverlayService, provideStreamConfig, provideStreamConsentConfig, provideStreamManager, provideStreamPlayerErrorConfig, provideStreamPlayerLoadingConfig, provideTopSheetStrategy, provideTopSheetStrategyDefaults, resolveClosestOverlay, rightSheetOverlayStrategy, startFullscreenEnterAnimation, startFullscreenLeaveAnimation, toGridPosition, topSheetOverlayStrategy, transformingBottomSheetToDialogOverlayStrategy, transformingFullScreenDialogToDialogOverlayStrategy, transformingFullScreenDialogToRightSheetOverlayStrategy };
17238
+ export { ARROW_OUT_UP_RIGHT_ICON, ARROW_RIGHT_ICON, BOLD_ICON, BUTTON_ICON_ALIGNMENTS, BUTTON_IMPORTS, BUTTON_SIZES, BUTTON_SPINNER_CONFIG, BUTTON_TYPES, BUTTON_VARIANTS, BrandLoaderComponent, ButtonComponent, ButtonDirective, ButtonStylesDirective, CHECKBOX_IMPORTS, CHEVRON_ICON, CHOICE_FIELD_IMPORTS, CLIPBOARD_CHECK_ICON, CheckboxComponent, CheckboxDirective, CheckboxGroupComponent, CheckboxOptionComponent, ChoiceFieldComponent, DAILYMOTION_PLAYER_TOKEN, DEFAULT_NOTIFICATION_MANAGER_CONFIG, DEFAULT_PIP_WINDOW_CONFIG, DEFAULT_STREAM_PLAYER_STATE, DailymotionPlayerComponent, DailymotionPlayerDirective, DailymotionPlayerParamsDirective, DailymotionPlayerSlotComponent, DescriptionComponent, FACEBOOK_PLAYER_TOKEN, FLOPPY_DISK_ICON, FOCUS_FRAME_ICON, FORM_FIELD_APPEARANCES, FORM_FIELD_CONTROL_TYPES, FORM_FIELD_ERROR_CODES, FORM_FIELD_FILLS, FORM_FIELD_IMPORTS, FORM_FIELD_LABEL_MODES, FORM_FIELD_SIZES, FORM_FIELD_TOKEN, FabComponent, FacebookPlayerComponent, FacebookPlayerDirective, FacebookPlayerParamsDirective, FacebookPlayerSlotComponent, FocusRingDirective, FormErrorComponent, FormFieldComponent, FormFieldDirective, GRID_2X2_ICON, GRID_ERROR_CODES, GRID_TOKEN, GridComponent, GridDebugComponent, GridDirective, GridDragDirective, GridImports, GridItemComponent, GridItemDefaultActionsComponent, GridItemDirective, GridItemRef, GridItemToolbarComponent, GridResizeDirective, HEADING_1_ICON, HEADING_2_ICON, HEADING_3_ICON, HintComponent, ICONS_TOKEN, ICON_DIRECTIVE_TOKEN, ICON_ERROR_CODES, ICON_IMPORTS, INPUT_IMPORTS, INPUT_TEXT_ALIGNMENTS, INPUT_TYPES, ITALIC_ICON, IconButtonComponent, IconDirective, InputComponent, InputDirective, InputPrefixDirective, InputSuffixDirective, KICK_PLAYER_TOKEN, KickPlayerComponent, KickPlayerDirective, KickPlayerParamsDirective, KickPlayerSlotComponent, LINK_ICON, LIST_BULLETED_ICON, LIST_NUMBERED_ICON, LOCK_ICON, LabelDirective, NAV_TABS_TOKEN, NOTIFICATION_ERROR_CODES, NOTIFICATION_IMPORTS, NOTIFICATION_STACK_CONTEXT_TOKEN, NOTIFICATION_STATUS, NavTabImports, NavTabLinkComponent, NavTabLinkDirective, NavTabsComponent, NavTabsDirective, NavTabsOutletComponent, NavTabsOutletDirective, NotificationActionDirective, NotificationComponent, NotificationDirective, NotificationDismissDirective, NotificationItemDirective, NotificationStackDirective, OVERLAY_BACK_OR_CLOSE_TOKEN, OVERLAY_BODY_TOKEN, OVERLAY_CONFIG_CLASS_KEYS, OVERLAY_CONTENT_IMPORTS, OVERLAY_ERROR_CODES, OVERLAY_FOOTER_TOKEN, OVERLAY_HEADER_TEMPLATE_TOKEN, OVERLAY_HEADER_TOKEN, OVERLAY_IMPORTS, OVERLAY_MAIN_TOKEN, OVERLAY_QUERY_PARAM_INPUT_NAME, OVERLAY_REF, OVERLAY_ROUTER_CONFIG_TOKEN, OVERLAY_ROUTER_LINK_TOKEN, OVERLAY_ROUTER_OUTLET_DISABLED_TEMPLATE_TOKEN, OVERLAY_ROUTER_OUTLET_TOKEN, OVERLAY_ROUTER_TOKEN, OVERLAY_SHARED_ROUTE_TEMPLATE_TOKEN, OverlayAnchorDirective, OverlayBackOrCloseDirective, OverlayBodyComponent, OverlayCloseDirective, OverlayContainerComponent, OverlayDirective, OverlayFooterDirective, OverlayHandlerLinkDirective, OverlayHeaderDirective, OverlayHeaderTemplateDirective, OverlayMainDirective, OverlayOriginCloneComponent, OverlayRouteHeaderTemplateOutletComponent, OverlayRouterLinkDirective, OverlayRouterOutletComponent, OverlayRouterOutletDisabledTemplateDirective, OverlaySharedRouteTemplateDirective, OverlaySharedRouteTemplateOutletComponent, OverlaySidebarComponent, OverlaySidebarPageComponent, OverlaySurfaceDirective, OverlayTitleDirective, OverlayTriggerDirective, PENCIL_ICON, PIP_CHROME_REF_TOKEN, PIP_ENTRY_TOKEN, PIP_WINDOW_ASPECT_RATIO_TOKEN, PLUS_ICON, PipBackDirective, PipBringBackDirective, PipCellDirective, PipCloseDirective, PipCollapseOverlayDirective, PipGridToggleDirective, PipPlayerComponent, PipSlotPlaceholderComponent, PipStageDirective, PipTitleBarDirective, PipTitleBarTemplateDirective, PipWindowComponent, PipWindowParamsDirective, ProgressBarComponent, RICH_TEXT_EDITOR_IMPORTS, RadioComponent, RadioGroupComponent, RichTextEditorComponent, RichTextEditorDirective, RichTextEditorFloatingToolbarComponent, SCROLLABLE_IMPORTS, SELECTION_LIST_MULTIPLE, SELECTION_LIST_TOKEN, SIDEBAR_OVERLAY_CONFIG, SIDEBAR_OVERLAY_TOKEN, SOOP_PLAYER_TOKEN, STREAM_CONSENT_TOKEN, STREAM_PLAYER_COMPONENT_TOKEN, STREAM_PLAYER_ERROR_CONTEXT_TOKEN, STREAM_PLAYER_ERROR_TOKEN, STREAM_PLAYER_PARAMS_TOKEN, STREAM_PLAYER_SLOT_TOKEN, STREAM_PLAYER_TOKEN, STREAM_SLOT_PLAYER_ID_TOKEN, STREAM_USER_CONSENT_PROVIDER_TOKEN, STRIKETHROUGH_ICON, SWITCH_IMPORTS, ScrollableActiveChildDirective, ScrollableButtonsDirective, ScrollableComponent, ScrollableDarkenDirective, ScrollableDirective, ScrollableDragDirective, ScrollableErrorCode, ScrollableIgnoreChildDirective, ScrollableLoadingTemplateDirective, ScrollableMasksDirective, ScrollableNavigationDirective, ScrollableSnapDirective, SegmentedButtonComponent, SegmentedButtonGroupComponent, SelectionListControlDirective, SelectionListDirective, SelectionOptionDirective, SoopPlayerComponent, SoopPlayerDirective, SoopPlayerParamsDirective, SoopPlayerSlotComponent, SpinnerComponent, StreamConsentAcceptDirective, StreamConsentComponent, StreamConsentDirective, StreamImports, StreamPipChromeComponent, StreamPlayerErrorComponent, StreamPlayerErrorDirective, StreamPlayerLoadingComponent, StreamPlayerSlotDirective, SwitchComponent, SwitchDirective, TAB_BAR_FITS, TAB_BAR_ORIENTATIONS, TAB_BAR_TOKEN, TAB_BAR_TRIGGER_TOKEN, TAB_BAR_VARIANTS, TAB_ERROR_CODES, TAB_GROUP_TOKEN, TAB_PANEL_TOKEN, TAB_SIZES, TIKTOK_PLAYER_TOKEN, TIMES_ICON, TOGGLETIP_ERROR_CODES, TOGGLETIP_IMPORTS, TOOLTIP_ERROR_CODES, TOOLTIP_IMPORTS, TRIANGLE_EXCLAMATION_ICON, TWITCH_PLAYER_TOKEN, TabBarDirective, TabBarTriggerDirective, TabBarUnderlineDirective, TabComponent, TabGroupComponent, TabGroupDirective, TabImports, TabLabelDirective, TabPanelDirective, TabTriggerDirective, TextButtonComponent, TikTokPlayerComponent, TikTokPlayerDirective, TikTokPlayerParamsDirective, TikTokPlayerSlotComponent, ToggletipCloseDirective, ToggletipComponent, ToggletipDirective, ToggletipTriggerDirective, TooltipComponent, TooltipDirective, TwitchPlayerComponent, TwitchPlayerDirective, TwitchPlayerParamsDirective, TwitchPlayerSlotComponent, VIMEO_PLAYER_TOKEN, VimeoPlayerComponent, VimeoPlayerDirective, VimeoPlayerParamsDirective, VimeoPlayerSlotComponent, WINDOW_CONTROL_BUTTON_KINDS, WINDOW_CONTROL_BUTTON_SIZES, WindowControlButtonComponent, YOUTUBE_PLAYER_SLOT_TOKEN, YOUTUBE_PLAYER_TOKEN, YoutubePlayerComponent, YoutubePlayerDirective, YoutubePlayerParamsDirective, YoutubePlayerSlotComponent, YoutubePlayerSlotDirective, abortFullscreenAnimation, anchoredDialogOverlayStrategy, anchoredOverlayStrategy, bottomSheetOverlayStrategy, buildAnchoredRuntimePositionStrategy, centeredOverlayStrategy, cleanupFullscreenAnimation, cleanupFullscreenAnimationStyles, createGridAdapter, createNotificationRef, createOverlayHandler, createOverlayHandlerWithQueryParamLifecycle, createOverlayRef, createOverlayStrategyController, createPipChromeAnimations, createPipChromeState, createStreamConfig, createStreamPlayerSlot, dialogOverlayStrategy, enableDragToDismiss, findNextRelevantHtmlElement, fromGridPosition, fullScreenDialogOverlayStrategy, getClosestOverlay, getOriginCoordinatesAndDimensions, injectAnchoredDialogStrategy, injectAnchoredDialogStrategyDefaults, injectBottomSheetStrategy, injectBottomSheetStrategyDefaults, injectDialogStrategy, injectDialogStrategyDefaults, injectFormSupport, injectFullscreenDialogStrategy, injectFullscreenDialogStrategyDefaults, injectGridConfig, injectLeftSheetStrategy, injectLeftSheetStrategyDefaults, injectNotificationManager, injectNotificationManagerConfig, injectOverlayManager, injectOverlayRouter, injectOverlayScrollBlocker, injectPipChromeManager, injectPipManager, injectPipSlotPlaceholderConfig, injectRightSheetStrategy, injectRightSheetStrategyDefaults, injectSidebarOverlay, injectStreamConfig, injectStreamConsentConfig, injectStreamManager, injectStreamPlayerErrorConfig, injectStreamPlayerLoadingConfig, injectStreamScriptLoader, injectStreamUserConsentProvider, injectTopSheetStrategy, injectTopSheetStrategyDefaults, isHtmlElement, isPointerEvent, isTouchEvent, leftSheetOverlayStrategy, mergeOverlayBreakpointConfigs, provideAnchoredDialogStrategy, provideAnchoredDialogStrategyDefaults, provideBottomSheetStrategy, provideBottomSheetStrategyDefaults, provideDialogStrategy, provideDialogStrategyDefaults, provideFormSupport, provideFullscreenDialogStrategy, provideFullscreenDialogStrategyDefaults, provideGridConfig, provideIcons, provideLeftSheetStrategy, provideLeftSheetStrategyDefaults, provideNotificationManager, provideNotificationManagerConfig, provideNotificationManagerInstance, provideOverlay, provideOverlayManager, provideOverlayRouter, provideOverlayRouterConfig, provideOverlayRouterService, provideOverlayScrollBlocker, providePipChromeManager, providePipManager, providePipSlotPlaceholderConfig, provideRightSheetStrategy, provideRightSheetStrategyDefaults, provideSidebarOverlay, provideSidebarOverlayConfig, provideSidebarOverlayService, provideStreamConfig, provideStreamConsentConfig, provideStreamManager, provideStreamPlayerErrorConfig, provideStreamPlayerLoadingConfig, provideTopSheetStrategy, provideTopSheetStrategyDefaults, resolveClosestOverlay, rightSheetOverlayStrategy, startFullscreenEnterAnimation, startFullscreenLeaveAnimation, toGridPosition, topSheetOverlayStrategy, transformingBottomSheetToDialogOverlayStrategy, transformingFullScreenDialogToDialogOverlayStrategy, transformingFullScreenDialogToRightSheetOverlayStrategy };
16834
17239
  //# sourceMappingURL=ethlete-components.mjs.map