ng-hub-ui-panels 22.17.0 → 22.18.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -40,6 +40,7 @@ This library is part of the **ng-hub-ui** ecosystem:
40
40
  - [**ng-hub-ui-portal**](https://www.npmjs.com/package/ng-hub-ui-portal)
41
41
  - [**ng-hub-ui-skeleton**](https://www.npmjs.com/package/ng-hub-ui-skeleton)
42
42
  - [**ng-hub-ui-sortable**](https://www.npmjs.com/package/ng-hub-ui-sortable)
43
+ - [**ng-hub-ui-spreadsheet**](https://www.npmjs.com/package/ng-hub-ui-spreadsheet)
43
44
  - [**ng-hub-ui-stepper**](https://www.npmjs.com/package/ng-hub-ui-stepper)
44
45
  - [**ng-hub-ui-utils**](https://www.npmjs.com/package/ng-hub-ui-utils)
45
46
 
@@ -113,7 +114,7 @@ its own.
113
114
  - **Non-modal side panel** — `<hub-side-panel>` docks to one edge of a `<hub-side-panel-container>` and either narrows the content (`side`) or floats over its edge (`over`), with no backdrop, scroll lock or focus trap, so the page stays usable while it is open.
114
115
  - **Card layout & standalone** — `type="card"` renders every panel as an always-visible card; a single `<hub-panel>` also works on its own, outside any container.
115
116
  - **Content header/footer slots** — `hubPanelHeader` and `hubPanelFooter` mark header/footer bands that render in every view (distinct from the `hubPanelHeading` nav label).
116
- - **Semantic alerts** — `appearance="alert"` with a `variant` turns a panel into a themed callout (`role="alert"`) driven by the design-system semantic tokens, no per-colour CSS.
117
+ - **Semantic alerts** — `appearance="alert"` with a `variant` turns a panel into a themed callout driven by the design-system semantic tokens, no per-colour CSS. `danger` and `warning` callouts are `role="alert"` (announced at once); every other variant is `role="status"`, so a screen reader reads it without interrupting.
117
118
  - **Strip accent** — `<hub-panels variant>` recolours the navigation strip (active/hover tab, active pill, active accordion header) from a single semantic accent; built-in variants use the exact design-system tints and any custom accent is picked up automatically.
118
119
  - **Forms** — implements `ControlValueAccessor`; bind the active panel(s) to a `FormControl` or `ngModel` (single or `multiple`), with `bindValue` and `compareWith`.
119
120
  - **Routing** — a panel with a `routerLink` turns the content area into a `<router-outlet>` that follows the URL.
@@ -961,6 +961,13 @@ class HubPanelComponent {
961
961
  */
962
962
  alertView = computed(() => this.appearance() === 'alert' && this.cardView(), /* @ts-ignore */
963
963
  ...(ngDevMode ? [{ debugName: "alertView" }] : /* istanbul ignore next */ []));
964
+ /**
965
+ * Only a `danger` or `warning` alert interrupts a screen reader (`role="alert"`, assertive).
966
+ * Any other variant, or none, is advisory and waits its turn (`role="status"`, polite):
967
+ * announcing an info note as urgent cuts off whatever the person was listening to.
968
+ */
969
+ alertRole = computed(() => this.variant() === 'danger' || this.variant() === 'warning' ? 'alert' : 'status', /* @ts-ignore */
970
+ ...(ngDevMode ? [{ debugName: "alertRole" }] : /* istanbul ignore next */ []));
964
971
  /**
965
972
  * Inline accent fed to the alert styles, resolved from the `variant` input so
966
973
  * ANY colour works. A bareword (a semantic name, a registered accent or a CSS
@@ -1115,14 +1122,14 @@ class HubPanelComponent {
1115
1122
  this.tabset?.removePanelAndRefocus(this);
1116
1123
  }
1117
1124
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.8", ngImport: i0, type: HubPanelComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
1118
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.8", type: HubPanelComponent, isStandalone: true, selector: "hub-panel, [hub-panel]", inputs: { heading: { classPropertyName: "heading", publicName: "heading", isSignal: true, isRequired: false, transformFunction: null }, appearance: { classPropertyName: "appearance", publicName: "appearance", isSignal: true, isRequired: false, transformFunction: null }, variant: { classPropertyName: "variant", publicName: "variant", isSignal: true, isRequired: false, transformFunction: null }, fill: { classPropertyName: "fill", publicName: "fill", isSignal: true, isRequired: false, transformFunction: null }, flush: { classPropertyName: "flush", publicName: "flush", isSignal: true, isRequired: false, transformFunction: null }, id: { classPropertyName: "id", publicName: "id", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, removable: { classPropertyName: "removable", publicName: "removable", isSignal: true, isRequired: false, transformFunction: null }, removeLabel: { classPropertyName: "removeLabel", publicName: "removeLabel", isSignal: true, isRequired: false, transformFunction: null }, pathMatch: { classPropertyName: "pathMatch", publicName: "pathMatch", isSignal: true, isRequired: false, transformFunction: null }, routerLink: { classPropertyName: "routerLink", publicName: "routerLink", isSignal: true, isRequired: false, transformFunction: null }, queryParams: { classPropertyName: "queryParams", publicName: "queryParams", isSignal: true, isRequired: false, transformFunction: null }, customClass: { classPropertyName: "customClass", publicName: "customClass", isSignal: true, isRequired: false, transformFunction: null }, value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: false, transformFunction: null }, active: { classPropertyName: "active", publicName: "active", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { active: "activeChange", selectPanel: "selectPanel", deselectPanel: "deselectPanel", removed: "removed" }, host: { properties: { "attr.id": "accordionView() || cardView() ? null : id()", "attr.role": "alertView() ? 'alert' : (accordionView() || cardView() ? null : 'tabpanel')", "attr.aria-labelledby": "accordionView() || cardView() ? null : id() + '-link'", "attr.data-variant": "cardView() ? (variant() ?? null) : null", "style.--hub-panels-alert-accent": "alertAccent()", "style.--hub-panels-card-accent": "cardAccent()", "class.hub-panels__panel--active": "active()", "class.hub-panels__panel--accordion": "accordionView()", "class.hub-panels__panel--toggle-start": "toggleAtStart()", "class.hub-panels__panel--card": "cardView() && !alertView()", "class.hub-panels__panel--alert": "alertView()", "class.hub-panels__panel--fill": "fill()", "class.hub-panels__panel--flush": "flush()" }, classAttribute: "hub-panels__panel" }, providers: [{ provide: HUB_PANEL, useExisting: forwardRef(() => HubPanelComponent) }], exportAs: ["hubPanel"], ngImport: i0, template: "@if (accordionView()) {\n\t<h2 class=\"hub-panels__accordion-header\" [class.hub-panels__accordion-header--expanded]=\"active()\">\n\t\t<button\n\t\t\ttype=\"button\"\n\t\t\tclass=\"hub-panels__accordion-btn\"\n\t\t\t[class.hub-panels__accordion-btn--collapsed]=\"!active()\"\n\t\t\t[id]=\"id() + '-link'\"\n\t\t\t[disabled]=\"disabled() || tabset?.formDisabled()\"\n\t\t\t[attr.aria-expanded]=\"active()\"\n\t\t\t[attr.aria-controls]=\"id()\"\n\t\t\t(click)=\"onAccordionHeaderClick()\"\n\t\t\t(keydown)=\"onAccordionHeaderKeydown($event)\"\n\t\t>\n\t\t\t@if (headingRef(); as headingTemplate) {\n\t\t\t\t<ng-container [ngTemplateOutlet]=\"headingTemplate\" />\n\t\t\t} @else {\n\t\t\t\t{{ heading() }}\n\t\t\t}\n\t\t</button>\n\n\t\t<!-- Row affordances live OUTSIDE the disclosure button: a control nested\n\t\t\t in another control is invalid and unreachable by keyboard. They stay\n\t\t\t visible while the row is collapsed, unlike `hubPanelHeader`. The \u2715\n\t\t\t remove control is a real button here for the same reason \u2014 focusable,\n\t\t\t keyboard operable and labelled for assistive technologies. -->\n\t\t@if (removable() || headingActionsRef()) {\n\t\t\t<span class=\"hub-panels__accordion-actions\">\n\t\t\t\t@if (headingActionsRef(); as actionsTemplate) {\n\t\t\t\t\t<ng-container [ngTemplateOutlet]=\"actionsTemplate\" />\n\t\t\t\t}\n\t\t\t\t@if (removable()) {\n\t\t\t\t\t<button\n\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\tclass=\"hub-panels__remove-btn\"\n\t\t\t\t\t\t[disabled]=\"disabled() || tabset?.formDisabled()\"\n\t\t\t\t\t\t[attr.aria-label]=\"removeLabel()\"\n\t\t\t\t\t\t(click)=\"removeSelf()\"\n\t\t\t\t\t>\n\t\t\t\t\t\t&times;\n\t\t\t\t\t</button>\n\t\t\t\t}\n\t\t\t</span>\n\t\t}\n\t</h2>\n}\n\n<!-- Projection slots for every view. In the strip views the wrappers are plain\n\t pass-throughs; in the accordion view they become the animated collapse\n\t region. The header/footer `select` slots and the default `<ng-content>` are\n\t all UNCONDITIONAL \u2014 never wrapped in `@if` \u2014 to avoid the lost-projection\n\t bug that conditional slots cause. Header/footer render in every view; the\n\t `card` view styles them as the card's header and footer bands. -->\n<div\n\tclass=\"hub-panels__panel-collapse\"\n\t[class.hub-panels__accordion-collapse]=\"accordionView()\"\n\t[class.hub-panels__accordion-collapse--collapsed]=\"accordionView() && !active()\"\n\t[attr.role]=\"accordionView() ? 'region' : null\"\n\t[attr.id]=\"accordionView() ? id() : null\"\n\t[attr.aria-labelledby]=\"accordionView() ? id() + '-link' : null\"\n\t[attr.aria-hidden]=\"accordionView() ? !active() : null\"\n\t[attr.inert]=\"accordionView() && !active() ? '' : null\"\n>\n\t<div class=\"hub-panels__panel-region\" [class.hub-panels__accordion-body]=\"accordionView()\">\n\t\t<ng-content select=\"[hubPanelHeader]\" />\n\t\t<div class=\"hub-panels__panel-body\">\n\t\t\t<ng-content />\n\t\t</div>\n\t\t<ng-content select=\"[hubPanelFooter]\" />\n\t</div>\n</div>\n", styles: [":where(.hub-panels__panel--card){--hub-panels-card-bg: var(--hub-sys-surface-page, #fff);--hub-panels-card-color: var(--hub-sys-text-primary, #212529);--hub-panels-card-border-width: var(--hub-ref-border-width, 1px);--hub-panels-card-border-style: solid;--hub-panels-card-border-color: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-card-border-radius: var(--hub-ref-radius-md, .375rem);--hub-panels-card-accent: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-card-padding-x: var(--hub-ref-space-4, 1.5rem);--hub-panels-card-padding-y: var(--hub-ref-space-3, 1rem);--hub-panels-body-gap: 0}:where(.hub-panels__panel-header,.hub-panels__panel-footer){--hub-panels-panel-header-color: var(--hub-sys-text-primary, #212529);--hub-panels-panel-header-padding-x: var(--hub-ref-space-4, 1.5rem);--hub-panels-panel-header-padding-y: var(--hub-ref-space-3, 1rem);--hub-panels-panel-header-font-weight: var(--hub-ref-font-weight-semibold, 600);--hub-panels-panel-header-border-width: var(--hub-ref-border-width, 1px);--hub-panels-panel-header-border-color: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-panel-header-content-direction: row;--hub-panels-panel-header-content-align: center;--hub-panels-panel-header-content-justify: flex-start;--hub-panels-panel-footer-content-justify: flex-end;--hub-panels-panel-header-content-gap: var(--hub-sys-gap-3, .75rem)}.hub-panels__panel-header{display:flex;flex-direction:var(--hub-panels-panel-header-content-direction);align-items:var(--hub-panels-panel-header-content-align);justify-content:var(--hub-panels-panel-header-content-justify);gap:var(--hub-panels-panel-header-content-gap);padding:var(--hub-panels-panel-header-padding-y) var(--hub-panels-panel-header-padding-x);color:var(--hub-panels-panel-header-color);background:var(--hub-panels-panel-header-bg, var(--hub-sys-surface-elevated, #f8f9fa));font-weight:var(--hub-panels-panel-header-font-weight);border-bottom:var(--hub-panels-panel-header-border-width) solid var(--hub-panels-panel-header-border-color)}.hub-panels__panel-header>:last-child:not(:only-child){margin-inline-start:auto}.hub-panels__panel-footer{display:flex;flex-direction:var(--hub-panels-panel-header-content-direction);align-items:var(--hub-panels-panel-header-content-align);justify-content:var(--hub-panels-panel-footer-content-justify);gap:var(--hub-panels-panel-header-content-gap);padding:var(--hub-panels-panel-header-padding-y) var(--hub-panels-panel-header-padding-x);color:var(--hub-panels-panel-header-color);background:var(--hub-panels-panel-header-bg, var(--hub-sys-surface-elevated, #f8f9fa));border-top:var(--hub-panels-panel-header-border-width) solid var(--hub-panels-panel-header-border-color)}.hub-panels__panel-footer>:first-child:not(:only-child){margin-inline-end:auto}.hub-panels__panel.hub-panels__panel--card{display:flex;flex-direction:column;color:var(--hub-panels-card-color);background:var(--hub-panels-card-bg);border:var(--hub-panels-card-border-width) var(--hub-panels-card-border-style) var(--hub-panels-card-border-color);border-radius:var(--hub-panels-card-border-radius);box-shadow:var(--hub-panels-card-box-shadow, var(--hub-sys-shadow-sm, 0 .125rem .25rem rgba(0, 0, 0, .075)));overflow:hidden}.hub-panels__panel.hub-panels__panel--card .hub-panels__panel-body{padding:var(--hub-panels-card-padding-y) var(--hub-panels-card-padding-x)}.hub-panels__panel--flush{--hub-panels-card-padding-x: 0;--hub-panels-card-padding-y: 0}.hub-panels__panel--card.hub-panels__panel--fill{flex:1 1 auto;min-height:0}.hub-panels__panel--card.hub-panels__panel--fill .hub-panels__panel-collapse,.hub-panels__panel--card.hub-panels__panel--fill .hub-panels__panel-region{display:flex;flex-direction:column;flex:1 1 auto;min-height:0}.hub-panels__panel--card.hub-panels__panel--fill .hub-panels__panel-body{flex:1 1 auto;min-height:0;overflow:auto;display:flex;flex-direction:column;gap:var(--hub-panels-body-gap)}:where(.hub-panels__panel--alert){--hub-panels-alert-bg: var(--hub-sys-surface-elevated, #f8f9fa);--hub-panels-alert-color: var(--hub-sys-text-primary, #212529);--hub-panels-alert-border-color: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-alert-accent: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-alert-padding-x: var(--hub-ref-space-4, 1.5rem);--hub-panels-alert-padding-y: var(--hub-ref-space-3, 1rem);--hub-panels-alert-border-radius: var(--hub-ref-radius-md, .375rem);--hub-panels-alert-accent-width: .25rem;--hub-panels-alert-content-direction: row;--hub-panels-alert-content-align: flex-start;--hub-panels-alert-content-justify: flex-start;--hub-panels-alert-content-gap: var(--hub-sys-gap-2, .5rem)}:where(.hub-panels__panel--alert[data-variant]){--hub-panels-alert-bg: color-mix(in oklch, var(--hub-panels-alert-accent) 12%, var(--hub-sys-surface-page, #ffffff));--hub-panels-alert-color: oklch( from var(--hub-panels-alert-accent) clamp(var(--hub-sys-emphasis-lightness-min, 0), l, var(--hub-sys-emphasis-lightness-max, .45)) c h );--hub-panels-alert-border-color: color-mix(in oklch, var(--hub-panels-alert-accent) 30%, transparent)}:where(.hub-panels__panel--alert[data-variant=primary]){--hub-panels-alert-bg: var(--hub-sys-color-primary-subtle);--hub-panels-alert-color: var(--hub-sys-color-primary-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-primary-border-subtle)}:where(.hub-panels__panel--alert[data-variant=secondary]){--hub-panels-alert-bg: var(--hub-sys-color-secondary-subtle);--hub-panels-alert-color: var(--hub-sys-color-secondary-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-secondary-border-subtle)}:where(.hub-panels__panel--alert[data-variant=success]){--hub-panels-alert-bg: var(--hub-sys-color-success-subtle);--hub-panels-alert-color: var(--hub-sys-color-success-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-success-border-subtle)}:where(.hub-panels__panel--alert[data-variant=danger]){--hub-panels-alert-bg: var(--hub-sys-color-danger-subtle);--hub-panels-alert-color: var(--hub-sys-color-danger-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-danger-border-subtle)}:where(.hub-panels__panel--alert[data-variant=warning]){--hub-panels-alert-bg: var(--hub-sys-color-warning-subtle);--hub-panels-alert-color: var(--hub-sys-color-warning-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-warning-border-subtle)}:where(.hub-panels__panel--alert[data-variant=info]){--hub-panels-alert-bg: var(--hub-sys-color-info-subtle);--hub-panels-alert-color: var(--hub-sys-color-info-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-info-border-subtle)}:where(.hub-panels__panel--alert[data-variant=neutral]){--hub-panels-alert-bg: var(--hub-sys-color-neutral-subtle);--hub-panels-alert-color: var(--hub-sys-color-neutral-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-neutral-border-subtle)}:where(.hub-panels__panel--alert[data-variant=light]){--hub-panels-alert-bg: var(--hub-sys-color-light-subtle);--hub-panels-alert-color: var(--hub-sys-color-light-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-light-border-subtle)}:where(.hub-panels__panel--alert[data-variant=dark]){--hub-panels-alert-bg: var(--hub-sys-color-dark-subtle);--hub-panels-alert-color: var(--hub-sys-color-dark-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-dark-border-subtle)}:where(.hub-panels__panel--card[data-variant]){--hub-panels-card-bg: color-mix(in oklch, var(--hub-panels-card-accent) 12%, var(--hub-sys-surface-page, #ffffff));--hub-panels-card-color: oklch( from var(--hub-panels-card-accent) clamp(var(--hub-sys-emphasis-lightness-min, 0), l, var(--hub-sys-emphasis-lightness-max, .45)) c h );--hub-panels-card-border-color: color-mix(in oklch, var(--hub-panels-card-accent) 30%, transparent)}:where(.hub-panels__panel--card[data-variant]) :where(.hub-panels__panel-header,.hub-panels__panel-footer){background:color-mix(in oklch,var(--hub-panels-card-accent) 22%,var(--hub-sys-surface-page, #ffffff));--hub-panels-panel-header-color: oklch( from var(--hub-panels-card-accent) clamp(var(--hub-sys-emphasis-lightness-min, 0), l, var(--hub-sys-emphasis-lightness-max, .45)) c h );--hub-panels-panel-header-border-color: color-mix(in oklch, var(--hub-panels-card-accent) 40%, transparent)}:where(.hub-panels__panel--card[data-variant=primary]){--hub-panels-card-bg: var(--hub-sys-color-primary-subtle);--hub-panels-card-color: var(--hub-sys-color-primary-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-primary-border-subtle)}:where(.hub-panels__panel--card[data-variant=secondary]){--hub-panels-card-bg: var(--hub-sys-color-secondary-subtle);--hub-panels-card-color: var(--hub-sys-color-secondary-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-secondary-border-subtle)}:where(.hub-panels__panel--card[data-variant=success]){--hub-panels-card-bg: var(--hub-sys-color-success-subtle);--hub-panels-card-color: var(--hub-sys-color-success-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-success-border-subtle)}:where(.hub-panels__panel--card[data-variant=danger]){--hub-panels-card-bg: var(--hub-sys-color-danger-subtle);--hub-panels-card-color: var(--hub-sys-color-danger-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-danger-border-subtle)}:where(.hub-panels__panel--card[data-variant=warning]){--hub-panels-card-bg: var(--hub-sys-color-warning-subtle);--hub-panels-card-color: var(--hub-sys-color-warning-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-warning-border-subtle)}:where(.hub-panels__panel--card[data-variant=info]){--hub-panels-card-bg: var(--hub-sys-color-info-subtle);--hub-panels-card-color: var(--hub-sys-color-info-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-info-border-subtle)}:where(.hub-panels__panel--card[data-variant=neutral]){--hub-panels-card-bg: var(--hub-sys-color-neutral-subtle);--hub-panels-card-color: var(--hub-sys-color-neutral-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-neutral-border-subtle)}:where(.hub-panels__panel--card[data-variant=light]){--hub-panels-card-bg: var(--hub-sys-color-light-subtle);--hub-panels-card-color: var(--hub-sys-color-light-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-light-border-subtle)}:where(.hub-panels__panel--card[data-variant=dark]){--hub-panels-card-bg: var(--hub-sys-color-dark-subtle);--hub-panels-card-color: var(--hub-sys-color-dark-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-dark-border-subtle)}.hub-panels__panel.hub-panels__panel--alert{display:flex;flex-direction:column;color:var(--hub-panels-alert-color, var(--hub-sys-text-primary, #212529));background:var(--hub-panels-alert-bg, var(--hub-sys-surface-elevated, #f8f9fa));border:var(--hub-ref-border-width, 1px) solid var(--hub-panels-alert-border-color, var(--hub-sys-border-color-default, #dee2e6));border-inline-start:var(--hub-panels-alert-accent-width) solid var(--hub-panels-alert-accent, var(--hub-sys-border-color-default, #dee2e6));border-radius:var(--hub-panels-alert-border-radius);overflow:hidden}.hub-panels__panel.hub-panels__panel--alert .hub-panels__panel-body{display:flex;flex-direction:var(--hub-panels-alert-content-direction);align-items:var(--hub-panels-alert-content-align);justify-content:var(--hub-panels-alert-content-justify);gap:var(--hub-panels-alert-content-gap);padding:var(--hub-panels-alert-padding-y) var(--hub-panels-alert-padding-x)}\n"], dependencies: [{ kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
1125
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.0.8", type: HubPanelComponent, isStandalone: true, selector: "hub-panel, [hub-panel]", inputs: { heading: { classPropertyName: "heading", publicName: "heading", isSignal: true, isRequired: false, transformFunction: null }, appearance: { classPropertyName: "appearance", publicName: "appearance", isSignal: true, isRequired: false, transformFunction: null }, variant: { classPropertyName: "variant", publicName: "variant", isSignal: true, isRequired: false, transformFunction: null }, fill: { classPropertyName: "fill", publicName: "fill", isSignal: true, isRequired: false, transformFunction: null }, flush: { classPropertyName: "flush", publicName: "flush", isSignal: true, isRequired: false, transformFunction: null }, id: { classPropertyName: "id", publicName: "id", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, removable: { classPropertyName: "removable", publicName: "removable", isSignal: true, isRequired: false, transformFunction: null }, removeLabel: { classPropertyName: "removeLabel", publicName: "removeLabel", isSignal: true, isRequired: false, transformFunction: null }, pathMatch: { classPropertyName: "pathMatch", publicName: "pathMatch", isSignal: true, isRequired: false, transformFunction: null }, routerLink: { classPropertyName: "routerLink", publicName: "routerLink", isSignal: true, isRequired: false, transformFunction: null }, queryParams: { classPropertyName: "queryParams", publicName: "queryParams", isSignal: true, isRequired: false, transformFunction: null }, customClass: { classPropertyName: "customClass", publicName: "customClass", isSignal: true, isRequired: false, transformFunction: null }, value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: false, transformFunction: null }, active: { classPropertyName: "active", publicName: "active", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { active: "activeChange", selectPanel: "selectPanel", deselectPanel: "deselectPanel", removed: "removed" }, host: { properties: { "attr.id": "accordionView() || cardView() ? null : id()", "attr.role": "alertView() ? alertRole() : (accordionView() || cardView() ? null : 'tabpanel')", "attr.aria-labelledby": "accordionView() || cardView() ? null : id() + '-link'", "attr.data-variant": "cardView() ? (variant() ?? null) : null", "style.--hub-panels-alert-accent": "alertAccent()", "style.--hub-panels-card-accent": "cardAccent()", "class.hub-panels__panel--active": "active()", "class.hub-panels__panel--accordion": "accordionView()", "class.hub-panels__panel--toggle-start": "toggleAtStart()", "class.hub-panels__panel--card": "cardView() && !alertView()", "class.hub-panels__panel--alert": "alertView()", "class.hub-panels__panel--fill": "fill()", "class.hub-panels__panel--flush": "flush()" }, classAttribute: "hub-panels__panel" }, providers: [{ provide: HUB_PANEL, useExisting: forwardRef(() => HubPanelComponent) }], exportAs: ["hubPanel"], ngImport: i0, template: "@if (accordionView()) {\n\t<h2 class=\"hub-panels__accordion-header\" [class.hub-panels__accordion-header--expanded]=\"active()\">\n\t\t<button\n\t\t\ttype=\"button\"\n\t\t\tclass=\"hub-panels__accordion-btn\"\n\t\t\t[class.hub-panels__accordion-btn--collapsed]=\"!active()\"\n\t\t\t[id]=\"id() + '-link'\"\n\t\t\t[disabled]=\"disabled() || tabset?.formDisabled()\"\n\t\t\t[attr.aria-expanded]=\"active()\"\n\t\t\t[attr.aria-controls]=\"id()\"\n\t\t\t(click)=\"onAccordionHeaderClick()\"\n\t\t\t(keydown)=\"onAccordionHeaderKeydown($event)\"\n\t\t>\n\t\t\t@if (headingRef(); as headingTemplate) {\n\t\t\t\t<ng-container [ngTemplateOutlet]=\"headingTemplate\" />\n\t\t\t} @else {\n\t\t\t\t{{ heading() }}\n\t\t\t}\n\t\t</button>\n\n\t\t<!-- Row affordances live OUTSIDE the disclosure button: a control nested\n\t\t\t in another control is invalid and unreachable by keyboard. They stay\n\t\t\t visible while the row is collapsed, unlike `hubPanelHeader`. The \u2715\n\t\t\t remove control is a real button here for the same reason \u2014 focusable,\n\t\t\t keyboard operable and labelled for assistive technologies. -->\n\t\t@if (removable() || headingActionsRef()) {\n\t\t\t<span class=\"hub-panels__accordion-actions\">\n\t\t\t\t@if (headingActionsRef(); as actionsTemplate) {\n\t\t\t\t\t<ng-container [ngTemplateOutlet]=\"actionsTemplate\" />\n\t\t\t\t}\n\t\t\t\t@if (removable()) {\n\t\t\t\t\t<button\n\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\tclass=\"hub-panels__remove-btn\"\n\t\t\t\t\t\t[disabled]=\"disabled() || tabset?.formDisabled()\"\n\t\t\t\t\t\t[attr.aria-label]=\"removeLabel()\"\n\t\t\t\t\t\t(click)=\"removeSelf()\"\n\t\t\t\t\t>\n\t\t\t\t\t\t&times;\n\t\t\t\t\t</button>\n\t\t\t\t}\n\t\t\t</span>\n\t\t}\n\t</h2>\n}\n\n<!-- Projection slots for every view. In the strip views the wrappers are plain\n\t pass-throughs; in the accordion view they become the animated collapse\n\t region. The header/footer `select` slots and the default `<ng-content>` are\n\t all UNCONDITIONAL \u2014 never wrapped in `@if` \u2014 to avoid the lost-projection\n\t bug that conditional slots cause. Header/footer render in every view; the\n\t `card` view styles them as the card's header and footer bands. -->\n<div\n\tclass=\"hub-panels__panel-collapse\"\n\t[class.hub-panels__accordion-collapse]=\"accordionView()\"\n\t[class.hub-panels__accordion-collapse--collapsed]=\"accordionView() && !active()\"\n\t[attr.role]=\"accordionView() ? 'region' : null\"\n\t[attr.id]=\"accordionView() ? id() : null\"\n\t[attr.aria-labelledby]=\"accordionView() ? id() + '-link' : null\"\n\t[attr.aria-hidden]=\"accordionView() ? !active() : null\"\n\t[attr.inert]=\"accordionView() && !active() ? '' : null\"\n>\n\t<div class=\"hub-panels__panel-region\" [class.hub-panels__accordion-body]=\"accordionView()\">\n\t\t<ng-content select=\"[hubPanelHeader]\" />\n\t\t<div class=\"hub-panels__panel-body\">\n\t\t\t<ng-content />\n\t\t</div>\n\t\t<ng-content select=\"[hubPanelFooter]\" />\n\t</div>\n</div>\n", styles: [":where(.hub-panels__panel--card){--hub-panels-card-bg: var(--hub-sys-surface-page, #fff);--hub-panels-card-color: var(--hub-sys-text-primary, #212529);--hub-panels-card-border-width: var(--hub-ref-border-width, 1px);--hub-panels-card-border-style: solid;--hub-panels-card-border-color: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-card-border-radius: var(--hub-ref-radius-md, .375rem);--hub-panels-card-accent: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-card-padding-x: var(--hub-ref-space-4, 1.5rem);--hub-panels-card-padding-y: var(--hub-ref-space-3, 1rem);--hub-panels-body-gap: 0}:where(.hub-panels__panel-header,.hub-panels__panel-footer){--hub-panels-panel-header-color: var(--hub-sys-text-primary, #212529);--hub-panels-panel-header-padding-x: var(--hub-ref-space-4, 1.5rem);--hub-panels-panel-header-padding-y: var(--hub-ref-space-3, 1rem);--hub-panels-panel-header-font-weight: var(--hub-ref-font-weight-semibold, 600);--hub-panels-panel-header-border-width: var(--hub-ref-border-width, 1px);--hub-panels-panel-header-border-color: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-panel-header-content-direction: row;--hub-panels-panel-header-content-align: center;--hub-panels-panel-header-content-justify: flex-start;--hub-panels-panel-footer-content-justify: flex-end;--hub-panels-panel-header-content-gap: var(--hub-sys-gap-3, .75rem)}.hub-panels__panel-header{display:flex;flex-direction:var(--hub-panels-panel-header-content-direction);align-items:var(--hub-panels-panel-header-content-align);justify-content:var(--hub-panels-panel-header-content-justify);gap:var(--hub-panels-panel-header-content-gap);padding:var(--hub-panels-panel-header-padding-y) var(--hub-panels-panel-header-padding-x);color:var(--hub-panels-panel-header-color);background:var(--hub-panels-panel-header-bg, var(--hub-sys-surface-elevated, #f8f9fa));font-weight:var(--hub-panels-panel-header-font-weight);border-bottom:var(--hub-panels-panel-header-border-width) solid var(--hub-panels-panel-header-border-color)}.hub-panels__panel-header>:last-child:not(:only-child){margin-inline-start:auto}.hub-panels__panel-footer{display:flex;flex-direction:var(--hub-panels-panel-header-content-direction);align-items:var(--hub-panels-panel-header-content-align);justify-content:var(--hub-panels-panel-footer-content-justify);gap:var(--hub-panels-panel-header-content-gap);padding:var(--hub-panels-panel-header-padding-y) var(--hub-panels-panel-header-padding-x);color:var(--hub-panels-panel-header-color);background:var(--hub-panels-panel-header-bg, var(--hub-sys-surface-elevated, #f8f9fa));border-top:var(--hub-panels-panel-header-border-width) solid var(--hub-panels-panel-header-border-color)}.hub-panels__panel-footer>:first-child:not(:only-child){margin-inline-end:auto}.hub-panels__panel.hub-panels__panel--card{display:flex;flex-direction:column;color:var(--hub-panels-card-color);background:var(--hub-panels-card-bg);border:var(--hub-panels-card-border-width) var(--hub-panels-card-border-style) var(--hub-panels-card-border-color);border-radius:var(--hub-panels-card-border-radius);box-shadow:var(--hub-panels-card-box-shadow, var(--hub-sys-shadow-sm, 0 .125rem .25rem rgba(0, 0, 0, .075)));overflow:hidden}.hub-panels__panel.hub-panels__panel--card .hub-panels__panel-body{padding:var(--hub-panels-card-padding-y) var(--hub-panels-card-padding-x)}.hub-panels__panel--flush{--hub-panels-card-padding-x: 0;--hub-panels-card-padding-y: 0}.hub-panels__panel--card.hub-panels__panel--fill{flex:1 1 auto;min-height:0}.hub-panels__panel--card.hub-panels__panel--fill .hub-panels__panel-collapse,.hub-panels__panel--card.hub-panels__panel--fill .hub-panels__panel-region{display:flex;flex-direction:column;flex:1 1 auto;min-height:0}.hub-panels__panel--card.hub-panels__panel--fill .hub-panels__panel-body{flex:1 1 auto;min-height:0;overflow:auto;display:flex;flex-direction:column;gap:var(--hub-panels-body-gap)}:where(.hub-panels__panel--alert){--hub-panels-alert-bg: var(--hub-sys-surface-elevated, #f8f9fa);--hub-panels-alert-color: var(--hub-sys-text-primary, #212529);--hub-panels-alert-border-color: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-alert-accent: var(--hub-sys-border-color-default, #dee2e6);--hub-panels-alert-padding-x: var(--hub-ref-space-4, 1.5rem);--hub-panels-alert-padding-y: var(--hub-ref-space-3, 1rem);--hub-panels-alert-border-radius: var(--hub-ref-radius-md, .375rem);--hub-panels-alert-accent-width: .25rem;--hub-panels-alert-content-direction: row;--hub-panels-alert-content-align: flex-start;--hub-panels-alert-content-justify: flex-start;--hub-panels-alert-content-gap: var(--hub-sys-gap-2, .5rem)}:where(.hub-panels__panel--alert[data-variant]){--hub-panels-alert-bg: color-mix(in oklch, var(--hub-panels-alert-accent) 12%, var(--hub-sys-surface-page, #ffffff));--hub-panels-alert-color: oklch( from var(--hub-panels-alert-accent) clamp(var(--hub-sys-emphasis-lightness-min, 0), l, var(--hub-sys-emphasis-lightness-max, .45)) c h );--hub-panels-alert-border-color: color-mix(in oklch, var(--hub-panels-alert-accent) 30%, transparent)}:where(.hub-panels__panel--alert[data-variant=primary]){--hub-panels-alert-bg: var(--hub-sys-color-primary-subtle);--hub-panels-alert-color: var(--hub-sys-color-primary-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-primary-border-subtle)}:where(.hub-panels__panel--alert[data-variant=secondary]){--hub-panels-alert-bg: var(--hub-sys-color-secondary-subtle);--hub-panels-alert-color: var(--hub-sys-color-secondary-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-secondary-border-subtle)}:where(.hub-panels__panel--alert[data-variant=success]){--hub-panels-alert-bg: var(--hub-sys-color-success-subtle);--hub-panels-alert-color: var(--hub-sys-color-success-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-success-border-subtle)}:where(.hub-panels__panel--alert[data-variant=danger]){--hub-panels-alert-bg: var(--hub-sys-color-danger-subtle);--hub-panels-alert-color: var(--hub-sys-color-danger-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-danger-border-subtle)}:where(.hub-panels__panel--alert[data-variant=warning]){--hub-panels-alert-bg: var(--hub-sys-color-warning-subtle);--hub-panels-alert-color: var(--hub-sys-color-warning-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-warning-border-subtle)}:where(.hub-panels__panel--alert[data-variant=info]){--hub-panels-alert-bg: var(--hub-sys-color-info-subtle);--hub-panels-alert-color: var(--hub-sys-color-info-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-info-border-subtle)}:where(.hub-panels__panel--alert[data-variant=neutral]){--hub-panels-alert-bg: var(--hub-sys-color-neutral-subtle);--hub-panels-alert-color: var(--hub-sys-color-neutral-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-neutral-border-subtle)}:where(.hub-panels__panel--alert[data-variant=light]){--hub-panels-alert-bg: var(--hub-sys-color-light-subtle);--hub-panels-alert-color: var(--hub-sys-color-light-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-light-border-subtle)}:where(.hub-panels__panel--alert[data-variant=dark]){--hub-panels-alert-bg: var(--hub-sys-color-dark-subtle);--hub-panels-alert-color: var(--hub-sys-color-dark-emphasis);--hub-panels-alert-border-color: var(--hub-sys-color-dark-border-subtle)}:where(.hub-panels__panel--card[data-variant]){--hub-panels-card-bg: color-mix(in oklch, var(--hub-panels-card-accent) 12%, var(--hub-sys-surface-page, #ffffff));--hub-panels-card-color: oklch( from var(--hub-panels-card-accent) clamp(var(--hub-sys-emphasis-lightness-min, 0), l, var(--hub-sys-emphasis-lightness-max, .45)) c h );--hub-panels-card-border-color: color-mix(in oklch, var(--hub-panels-card-accent) 30%, transparent)}:where(.hub-panels__panel--card[data-variant]) :where(.hub-panels__panel-header,.hub-panels__panel-footer){background:color-mix(in oklch,var(--hub-panels-card-accent) 22%,var(--hub-sys-surface-page, #ffffff));--hub-panels-panel-header-color: oklch( from var(--hub-panels-card-accent) clamp(var(--hub-sys-emphasis-lightness-min, 0), l, var(--hub-sys-emphasis-lightness-max, .45)) c h );--hub-panels-panel-header-border-color: color-mix(in oklch, var(--hub-panels-card-accent) 40%, transparent)}:where(.hub-panels__panel--card[data-variant=primary]){--hub-panels-card-bg: var(--hub-sys-color-primary-subtle);--hub-panels-card-color: var(--hub-sys-color-primary-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-primary-border-subtle)}:where(.hub-panels__panel--card[data-variant=secondary]){--hub-panels-card-bg: var(--hub-sys-color-secondary-subtle);--hub-panels-card-color: var(--hub-sys-color-secondary-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-secondary-border-subtle)}:where(.hub-panels__panel--card[data-variant=success]){--hub-panels-card-bg: var(--hub-sys-color-success-subtle);--hub-panels-card-color: var(--hub-sys-color-success-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-success-border-subtle)}:where(.hub-panels__panel--card[data-variant=danger]){--hub-panels-card-bg: var(--hub-sys-color-danger-subtle);--hub-panels-card-color: var(--hub-sys-color-danger-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-danger-border-subtle)}:where(.hub-panels__panel--card[data-variant=warning]){--hub-panels-card-bg: var(--hub-sys-color-warning-subtle);--hub-panels-card-color: var(--hub-sys-color-warning-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-warning-border-subtle)}:where(.hub-panels__panel--card[data-variant=info]){--hub-panels-card-bg: var(--hub-sys-color-info-subtle);--hub-panels-card-color: var(--hub-sys-color-info-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-info-border-subtle)}:where(.hub-panels__panel--card[data-variant=neutral]){--hub-panels-card-bg: var(--hub-sys-color-neutral-subtle);--hub-panels-card-color: var(--hub-sys-color-neutral-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-neutral-border-subtle)}:where(.hub-panels__panel--card[data-variant=light]){--hub-panels-card-bg: var(--hub-sys-color-light-subtle);--hub-panels-card-color: var(--hub-sys-color-light-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-light-border-subtle)}:where(.hub-panels__panel--card[data-variant=dark]){--hub-panels-card-bg: var(--hub-sys-color-dark-subtle);--hub-panels-card-color: var(--hub-sys-color-dark-emphasis);--hub-panels-card-border-color: var(--hub-sys-color-dark-border-subtle)}.hub-panels__panel.hub-panels__panel--alert{display:flex;flex-direction:column;color:var(--hub-panels-alert-color, var(--hub-sys-text-primary, #212529));background:var(--hub-panels-alert-bg, var(--hub-sys-surface-elevated, #f8f9fa));border:var(--hub-ref-border-width, 1px) solid var(--hub-panels-alert-border-color, var(--hub-sys-border-color-default, #dee2e6));border-inline-start:var(--hub-panels-alert-accent-width) solid var(--hub-panels-alert-accent, var(--hub-sys-border-color-default, #dee2e6));border-radius:var(--hub-panels-alert-border-radius);overflow:hidden}.hub-panels__panel.hub-panels__panel--alert .hub-panels__panel-body{display:flex;flex-direction:var(--hub-panels-alert-content-direction);align-items:var(--hub-panels-alert-content-align);justify-content:var(--hub-panels-alert-content-justify);gap:var(--hub-panels-alert-content-gap);padding:var(--hub-panels-alert-padding-y) var(--hub-panels-alert-padding-x)}\n"], dependencies: [{ kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
1119
1126
  }
1120
1127
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.8", ngImport: i0, type: HubPanelComponent, decorators: [{
1121
1128
  type: Component,
1122
1129
  args: [{ selector: 'hub-panel, [hub-panel]', providers: [{ provide: HUB_PANEL, useExisting: forwardRef(() => HubPanelComponent) }], exportAs: 'hubPanel', imports: [NgTemplateOutlet], encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.OnPush, host: {
1123
1130
  class: 'hub-panels__panel',
1124
1131
  '[attr.id]': 'accordionView() || cardView() ? null : id()',
1125
- '[attr.role]': "alertView() ? 'alert' : (accordionView() || cardView() ? null : 'tabpanel')",
1132
+ '[attr.role]': "alertView() ? alertRole() : (accordionView() || cardView() ? null : 'tabpanel')",
1126
1133
  '[attr.aria-labelledby]': "accordionView() || cardView() ? null : id() + '-link'",
1127
1134
  '[attr.data-variant]': 'cardView() ? (variant() ?? null) : null',
1128
1135
  '[style.--hub-panels-alert-accent]': 'alertAccent()',
@@ -1 +1 @@
1
- {"version":3,"file":"ng-hub-ui-panels.mjs","sources":["../../../projects/panels/src/lib/services/panels-config.service.ts","../../../projects/panels/src/lib/utils/content-box-width.ts","../../../projects/panels/src/lib/utils/read-by-path.ts","../../../projects/panels/src/lib/components/panel/panel.token.ts","../../../projects/panels/src/lib/components/panels/panels.component.ts","../../../projects/panels/src/lib/components/panels/panels.component.html","../../../projects/panels/src/lib/components/panel/panel.component.ts","../../../projects/panels/src/lib/components/panel/panel.component.html","../../../projects/panels/src/lib/directives/panel-heading.directive.ts","../../../projects/panels/src/lib/directives/panel-heading-actions.directive.ts","../../../projects/panels/src/lib/directives/panel-header.directive.ts","../../../projects/panels/src/lib/directives/panel-footer.directive.ts","../../../projects/panels/src/lib/components/tab-nav/tab-nav.component.ts","../../../projects/panels/src/lib/components/tab-nav/tab-nav.component.html","../../../projects/panels/src/lib/components/side-panel/side-panel-container.component.ts","../../../projects/panels/src/lib/components/side-panel/side-panel-container.component.html","../../../projects/panels/src/lib/components/side-panel/side-panel.component.ts","../../../projects/panels/src/lib/components/side-panel/side-panel.component.html","../../../projects/panels/src/public-api.ts","../../../projects/panels/src/ng-hub-ui-panels.ts"],"sourcesContent":["import { Injectable } from '@angular/core';\n\nimport type { HubPanelsTogglePosition, PanelsType } from '../models/panels.types';\n\n/**\n * Injectable defaults for every `<hub-panels>` in the application.\n *\n * Override at any injector level to change the defaults globally or for a\n * feature subtree:\n *\n * ```ts\n * providers: [{ provide: HubPanelsConfig, useValue: { ...new HubPanelsConfig(), type: 'pills' } }]\n * ```\n */\n@Injectable({ providedIn: 'root' })\nexport class HubPanelsConfig {\n\t/** Default navigation style — `'tabs'`, `'pills'` or `'accordion'`. */\n\ttype: PanelsType = 'tabs';\n\n\t/** Whether keyboard navigation (arrows / Home / End / Delete) is enabled. */\n\tisKeysAllowed = true;\n\n\t/** Accordion view: default side of the header row for the disclosure chevron. */\n\ttogglePosition: HubPanelsTogglePosition = 'end';\n\n\t/** Accessible label announced for the panel list. */\n\tariaLabel = 'Tabs';\n\n\t/** Accessible label for the backward scroll button (scrollable mode). */\n\tscrollBackwardAriaLabel = 'Scroll tabs backward';\n\n\t/** Accessible label for the forward scroll button (scrollable mode). */\n\tscrollForwardAriaLabel = 'Scroll tabs forward';\n}\n","/**\n * Usable inner width of an element: `offsetWidth` minus horizontal paddings\n * and borders. Used by the scrollable strip to size its scroll steps.\n */\nexport function contentBoxWidth(element: HTMLElement): number {\n\tconst style = getComputedStyle(element);\n\treturn (\n\t\telement.offsetWidth -\n\t\tparseFloat(style.paddingLeft) -\n\t\tparseFloat(style.paddingRight) -\n\t\tparseFloat(style.borderLeftWidth) -\n\t\tparseFloat(style.borderRightWidth)\n\t);\n}\n","/**\n * Reads a nested value from an object using dot-notation path syntax\n * (e.g. `id`, `meta.key`). Returns `undefined` when the path cannot be\n * resolved. Used by the panels' `bindValue` form-value mapping.\n */\nexport function readByPath(source: unknown, path: string): unknown {\n\tif (source == null || !path) {\n\t\treturn undefined;\n\t}\n\treturn path.split('.').reduce((currentValue: unknown, segment) => {\n\t\tif (currentValue == null) {\n\t\t\treturn undefined;\n\t\t}\n\t\treturn (currentValue as Record<string, unknown>)[segment];\n\t}, source);\n}\n","import { InjectionToken } from '@angular/core';\n\nimport type { HubPanelComponent } from './panel.component';\n\n/**\n * Stands in for `HubPanelComponent` where importing the class would close a cycle.\n *\n * The panel injects its container and the container queries its panels, so one of the two\n * directions has to be type-only. This token is that direction: the panel provides itself under\n * it, and the container queries the token.\n */\nexport const HUB_PANEL = new InjectionToken<HubPanelComponent>('HUB_PANEL');\n","import { NgTemplateOutlet } from '@angular/common';\nimport {\n\tcontentChildren,\n\tafterNextRender,\n\tbooleanAttribute,\n\tChangeDetectionStrategy,\n\tComponent,\n\tcomputed,\n\tDestroyRef,\n\tElementRef,\n\tforwardRef,\n\tinject,\n\tinput,\n\toutput,\n\tRenderer2,\n\tRendererStyleFlags2,\n\tsignal,\n\tviewChild,\n\tviewChildren,\n\tViewEncapsulation\n} from '@angular/core';\nimport { takeUntilDestroyed } from '@angular/core/rxjs-interop';\nimport { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms';\nimport { NavigationEnd, Router, RouterOutlet } from '@angular/router';\nimport { filter } from 'rxjs';\n\nimport type { HubPanelsTogglePosition, HubPanelVariant, PanelChangeEvent, PanelsType } from '../../models/panels.types';\nimport { HubPanelsConfig } from '../../services/panels-config.service';\nimport { contentBoxWidth } from '../../utils/content-box-width';\nimport { readByPath } from '../../utils/read-by-path';\nimport { resolveHubAccent } from 'ng-hub-ui-utils';\nimport type { HubPanelComponent } from '../panel/panel.component';\n\ninterface MultipleHeaderGroup {\n\tactivePanel?: HubPanelComponent;\n\theaders: HubPanelComponent[];\n}\n\n/**\n * Content-panels container — the hub `panels` primitive.\n *\n * Projects `<hub-panel>` panes and renders them in one of three views:\n *\n * - **`tabs` / `pills`** — an accessible `tablist` of clickable headers\n * (roving tabindex, arrow/Home/End/Delete keys) above the active pane.\n * Panels with a `routerLink` switch the content area to a `<router-outlet>`\n * and the active panel follows the URL. With `scrollable`, overflowing\n * headers get backward/forward scroll buttons.\n * - **`accordion`** — each panel renders as a stacked disclosure panel with an\n * animated collapse: clicking an open header closes it, `multiple` allows\n * several panels open at once and `flush` removes the outer chrome. All\n * panels start collapsed unless a panel is marked `[active]` or a form value\n * is bound. Routed panels are not supported in this view.\n *\n * The container implements `ControlValueAccessor`, so the active panel(s) can\n * be bound as a form value (`ngModel` / `formControl`): each panel contributes\n * its `value` (or its `id` by default), optionally narrowed with `bindValue`\n * and compared with `compareWith`. With `multiple` the form value is an array.\n *\n * Theming is driven entirely by the `--hub-panels-*` CSS custom properties\n * (see `panels.variables.scss`); the accordion view also honours the\n * `--hub-accordion-*` ng-hub-ui contract as a compatibility fallback.\n *\n * @example\n * ```html\n * <hub-panels type=\"accordion\" multiple [formControl]=\"openPanels\">\n * <hub-panel heading=\"Fields\" value=\"fields\">…</hub-panel>\n * <hub-panel heading=\"Validations\" value=\"validations\">…</hub-panel>\n * </hub-panels>\n * ```\n */\nimport { HUB_PANEL } from '../panel/panel.token';\n\n@Component({\n\tselector: 'hub-panels',\n\timports: [NgTemplateOutlet, RouterOutlet],\n\ttemplateUrl: './panels.component.html',\n\t// Split by concern (token contract / strip views / accordion view) so each\n\t// sheet stays inside the `anyComponentStyle` budget.\n\tstyleUrls: ['./panels.variables.scss', './panels.component.scss', './panels.accordion.scss'],\n\t// Library-style global stylesheet: rules are namespaced under `.hub-panels*`\n\t// and must reach the projected `hub-panel` panes (host-bound classes).\n\tencapsulation: ViewEncapsulation.None,\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\tproviders: [\n\t\t{\n\t\t\tprovide: NG_VALUE_ACCESSOR,\n\t\t\tuseExisting: forwardRef(() => HubPanelsComponent),\n\t\t\tmulti: true\n\t\t}\n\t],\n\thost: {\n\t\tclass: 'hub-panels',\n\t\t'[class.hub-panels--tabs]': \"type() === 'tabs'\",\n\t\t'[class.hub-panels--pills]': \"type() === 'pills'\",\n\t\t'[class.hub-panels--card]': 'isCardView()',\n\t\t'[class.hub-panels--vertical]': 'vertical() && !isAccordionView() && !isCardView()',\n\t\t'[class.hub-panels--accordion]': 'isAccordionView()',\n\t\t'[class.hub-panels--toggle-start]': \"isAccordionView() && togglePosition() === 'start'\",\n\t\t'[class.hub-panels--flush]': 'isAccordionView() && flush()',\n\t\t'[class.hub-panels--multiple]': 'multiple()',\n\t\t'[attr.data-variant]': 'variant() ?? null',\n\t\t'[style.--hub-panels-accent]': 'groupAccent()',\n\t\t'(window:resize)': 'onWindowResize()'\n\t}\n})\nexport class HubPanelsComponent implements ControlValueAccessor {\n\treadonly #router = inject(Router);\n\treadonly #renderer = inject(Renderer2);\n\treadonly #elementRef = inject<ElementRef<HTMLElement>>(ElementRef);\n\treadonly #destroyRef = inject(DestroyRef);\n\n\t/** Container-wide defaults (aria labels, default type, keyboard toggle). */\n\tprotected readonly config = inject(HubPanelsConfig);\n\n\t/** Scrollable container hosting the panel headers (`tabs` / `pills` views). */\n\treadonly navScroller = viewChild<ElementRef<HTMLElement>>('navScroller');\n\n\t/** Backward scroll button (only rendered while it can scroll back). */\n\treadonly prevBtn = viewChild<ElementRef<HTMLElement>>('prevBtn');\n\n\t/** Forward scroll button (only rendered while it can scroll forward). */\n\treadonly nextBtn = viewChild<ElementRef<HTMLElement>>('nextBtn');\n\n\t/** Parking lot that owns the projected panel hosts before they are placed. */\n\treadonly contentRoot = viewChild<ElementRef<HTMLElement>>('contentRoot');\n\n\t/** Visible block hosts used by `multiple` tabs / pills. */\n\treadonly multiplePaneHosts = viewChildren<ElementRef<HTMLElement>>('multiplePaneHost');\n\n\t/** Visible grouped blocks used by `multiple` tabs / pills. */\n\treadonly multipleBlocks = viewChildren<ElementRef<HTMLElement>>('multipleBlock');\n\n\t/** Emitted when the user activates (opens) a different panel. */\n\treadonly panelChange = output<PanelChangeEvent>();\n\n\t/** Whether the panel list is stacked beside the content (`tabs` / `pills`). */\n\treadonly vertical = input(false, { transform: booleanAttribute });\n\n\t/** Whether panel headers stretch to share the available width equally. */\n\treadonly justified = input(false, { transform: booleanAttribute });\n\n\t/** Visualization — `'tabs'` (default), `'pills'` or `'accordion'`. */\n\treadonly type = input<PanelsType>(this.config.type);\n\n\t/** Whether keyboard navigation is enabled. */\n\treadonly isKeysAllowed = input(this.config.isKeysAllowed, {\n\t\ttransform: booleanAttribute\n\t});\n\n\t/** Whether overflowing headers get backward/forward scroll buttons. */\n\treadonly scrollable = input(false, { transform: booleanAttribute });\n\n\t/** Accordion view: whether several panels may be expanded at once. */\n\treadonly multiple = input(false, { transform: booleanAttribute });\n\n\t/** Accordion view: edge-to-edge panels without outer borders or radius. */\n\treadonly flush = input(false, { transform: booleanAttribute });\n\n\t/**\n\t * Accordion view: which side of the header row the disclosure chevron sits\n\t * on — `'end'` (default) trails the heading, `'start'` leads it. Purely\n\t * visual: the DOM order never changes, and the placement is expressed with\n\t * logical properties, so it mirrors automatically under `dir=\"rtl\"`.\n\t */\n\treadonly togglePosition = input<HubPanelsTogglePosition>(this.config.togglePosition);\n\n\t/**\n\t * Semantic accent applied to the navigation strip — the active/hover tab, the\n\t * active pill and the active accordion header all follow it. The built-in\n\t * values (`primary` / `success` / `danger` / `warning` / `info`) render with\n\t * the design-system tints; any other string is also accepted, since the strip\n\t * reads `--hub-sys-color-<variant>` from the host application, so a custom\n\t * accent palette interconnects with no changes to this library. Defaults to\n\t * `primary` when omitted.\n\t */\n\treadonly variant = input<HubPanelVariant | (string & {}) | undefined>(undefined);\n\n\t/**\n\t * Dot-notation path applied to each panel's `value` to obtain the emitted\n\t * form value (e.g. `'meta.key'`). Empty by default — the raw value is used.\n\t */\n\treadonly bindValue = input<string | undefined>(undefined);\n\n\t/** Equality used to match form values against panel values. `===` by default. */\n\treadonly compareWith = input<(a: unknown, b: unknown) => boolean>((a, b) => a === b);\n\n\t/**\n\t * Panels projected into this container, in the order the consumer wrote them.\n\t *\n\t * A content query rather than self-registration, because a panel adding itself from its own\n\t * constructor is never seen when it is created inside a control-flow block: an `@if` that turns\n\t * true produced a pane in the DOM and no tab at all. The query also fixes the order for free —\n\t * registration order is creation order, which a conditional panel breaks the moment its\n\t * condition flips.\n\t *\n\t * The boundary is exactly right: content children reach through `@if` and `@for` in the\n\t * consumer's template, and stop at another component's own view, so a panel nested inside a\n\t * component projected into a pane is still not captured as a hidden tab.\n\t */\n\tprotected readonly projectedPanels = contentChildren(HUB_PANEL, { descendants: true });\n\n\t/**\n\t * Panels a consumer removed through the strip's own close button. Removal is an action, not a\n\t * shape the template describes, so it cannot come from the query: the panel is still written in\n\t * the consumer's template and the query keeps returning it.\n\t */\n\treadonly #removedPanels = signal<ReadonlySet<HubPanelComponent>>(new Set());\n\n\t/** Panels the strip presents, in the order the consumer wrote them. */\n\treadonly panels = computed(() =>\n\t\tthis.projectedPanels().filter((panel) => !panel.standalone && !this.#removedPanels().has(panel))\n\t);\n\n\t/** Currently active panel, if any (the first one, under `multiple`). */\n\treadonly activePanel = computed(() => this.panels().find((panel) => panel.active()));\n\n\t/** Panel index lookup used by the strip templates and keyboard navigation. */\n\treadonly panelIndexMap = computed(() => new Map(this.panels().map((panel, index) => [panel, index])));\n\n\t/** Whether the container renders the accordion visualization. */\n\treadonly isAccordionView = computed(() => this.type() === 'accordion');\n\n\t/**\n\t * Whether the container renders the chromeless `card` visualization: no\n\t * navigation strip and every panel always visible, each styled as a card.\n\t */\n\treadonly isCardView = computed(() => this.type() === 'card');\n\n\t/**\n\t * Inline accent fed to the strip styles, resolved from the `variant` input so\n\t * ANY colour works. A bareword (a semantic name, a registered accent or a CSS\n\t * named colour) resolves to `var(--hub-sys-color-<variant>, <variant>)` — the\n\t * design-system token with the word itself as the raw fallback; a literal\n\t * (`#hex` / `rgb()` / `oklch()` / `var()`) is passed through unchanged. Returns\n\t * `null` to keep the `primary` default. The built-in semantic variants\n\t * additionally pick up their exact ds tints through the SCSS `@each`.\n\t */\n\tprotected readonly groupAccent = computed(() => resolveHubAccent(this.variant()));\n\n\t/**\n\t * Whether more than one panel may be active at once. Driven by `multiple`\n\t * for every view, and always enabled in the `card` view, where all panels\n\t * stay visible at once and must not deactivate one another.\n\t */\n\treadonly allowsMultipleActive = computed(() => this.multiple() || this.isCardView());\n\n\t/** Whether the bound form control disabled the whole container. */\n\treadonly formDisabled = signal(false);\n\n\t/**\n\t * Whether the active panel routes its content through a `<router-outlet>`.\n\t * Never true in the accordion view, where routed panels are not supported.\n\t */\n\tprotected readonly activePanelHasRouter = computed(\n\t\t() => !this.isAccordionView() && !this.allowsMultipleActive() && !!this.activePanel()?.routerUrl()\n\t);\n\n\t/**\n\t * In `multiple` tabs/pills, headers are partitioned into blocks. Every\n\t * active panel starts a block; following inactive headers stay visible in\n\t * that same block until the next active panel starts a new one.\n\t */\n\tprotected readonly multipleHeaderGroups = computed<MultipleHeaderGroup[]>(() => {\n\t\tif (!this.allowsMultipleActive() || this.isAccordionView()) {\n\t\t\treturn [];\n\t\t}\n\t\tconst panels = this.panels();\n\t\tif (!panels.length) {\n\t\t\treturn [];\n\t\t}\n\t\tconst activeIndices = panels.map((panel, index) => (panel.active() ? index : -1)).filter((index) => index !== -1);\n\t\tif (!activeIndices.length) {\n\t\t\treturn [{ headers: panels }];\n\t\t}\n\t\treturn activeIndices.map((activeIndex, groupIndex) => {\n\t\t\tconst startIndex = groupIndex === 0 ? 0 : activeIndex;\n\t\t\tconst endIndex = activeIndices[groupIndex + 1] ?? panels.length;\n\t\t\treturn {\n\t\t\t\tactivePanel: panels[activeIndex],\n\t\t\t\theaders: panels.slice(startIndex, endIndex)\n\t\t\t};\n\t\t});\n\t});\n\n\t/** Whether the strip cannot scroll further backward. */\n\treadonly backwardIsDisabled = signal(true);\n\n\t/** Whether the strip cannot scroll further forward. */\n\treadonly forwardIsDisabled = signal(false);\n\n\t#isDestroyed = false;\n\t#syncScheduled = false;\n\t#viewInitialised = false;\n\t#placementScheduled = false;\n\t#multipleBlockSizingScheduled = false;\n\n\t/** Last value written by the bound form control; `null` when no form. */\n\t#formValue: unknown[] | null = null;\n\n\t#onChange: (value: unknown) => void = () => undefined;\n\t#onTouched: () => void = () => undefined;\n\n\tconstructor() {\n\t\tthis.#destroyRef.onDestroy(() => {\n\t\t\tthis.#isDestroyed = true;\n\t\t});\n\n\t\tafterNextRender(() => {\n\t\t\tthis.#viewInitialised = true;\n\t\t\tthis.updateScrollButtons();\n\t\t\tthis.setActivePanel();\n\t\t\t// Re-apply any form value written before the panels' inputs were bound.\n\t\t\tthis.#applyFormValue();\n\t\t\tthis.#ensureActivePanel();\n\t\t\tthis.#schedulePanelPlacement();\n\t\t\tthis.#scheduleMultipleBlockSizing();\n\t\t\tthis.#router.events\n\t\t\t\t.pipe(\n\t\t\t\t\tfilter((event) => event instanceof NavigationEnd),\n\t\t\t\t\ttakeUntilDestroyed(this.#destroyRef)\n\t\t\t\t)\n\t\t\t\t.subscribe(() => this.setActivePanel());\n\t\t});\n\t}\n\n\t/**\n\t * Kept so a panel built against an older release still compiles. Panels are discovered by\n\t * content query now, so joining the container is nothing a panel has to ask for.\n\t *\n\t * @deprecated Does nothing. Removed under this name in **23.0.0**.\n\t */\n\tregisterPanel(_panel: HubPanelComponent): void {\n\t\t// Intentionally empty.\n\t}\n\n\t/**\n\t * Removes a panel from the container. `reselect` activates the closest enabled neighbour when\n\t * the removed panel was active; `emit` fires the panel's `removed` output; `track` records the\n\t * removal so the content query stops presenting the panel.\n\t *\n\t * A panel on its way out of the DOM passes `track: false`: the query drops it by itself, and\n\t * remembering it would hold the reference alive for nothing.\n\t */\n\tremovePanel(panel: HubPanelComponent, options: { reselect?: boolean; emit?: boolean; track?: boolean } = {}): void {\n\t\tconst { reselect = true, emit = true, track = true } = options;\n\t\tconst panels = this.panels();\n\t\tconst index = panels.indexOf(panel);\n\t\tif (index === -1 || this.#isDestroyed) {\n\t\t\treturn;\n\t\t}\n\n\t\tif (reselect && panel.active() && !this.isAccordionView()) {\n\t\t\tconst closestIndex = this.#closestEnabledIndex(index);\n\t\t\tif (closestIndex !== -1) {\n\t\t\t\tpanels[closestIndex].active.set(true);\n\t\t\t}\n\t\t}\n\t\tif (emit) {\n\t\t\tpanel.removed.emit(panel);\n\t\t}\n\n\t\tif (track) {\n\t\t\t// Prune as we go: a panel removed and then destroyed would otherwise stay in the set for\n\t\t\t// the lifetime of the container.\n\t\t\tthis.#removedPanels.update((current) => {\n\t\t\t\tconst live = new Set(this.projectedPanels());\n\t\t\t\tconst next = new Set([...current].filter((candidate) => live.has(candidate)));\n\t\t\t\tnext.add(panel);\n\t\t\t\treturn next;\n\t\t\t});\n\t\t}\n\n\t\t// Detach the projected pane: the consumer template still owns the node,\n\t\t// so removing the header alone would leave the pane content behind.\n\t\tconst paneElement = panel.elementRef.nativeElement;\n\t\tif (paneElement.parentNode) {\n\t\t\tthis.#renderer.removeChild(paneElement.parentNode, paneElement);\n\t\t}\n\t\tif (panel.active()) {\n\t\t\tpanel.active.set(false);\n\t\t\tthis.#emitFormValue();\n\t\t}\n\t\tthis.#scheduleSync();\n\t}\n\n\t/**\n\t * Removes a panel on behalf of the user (the ✕ button or the Delete key)\n\t * and returns keyboard focus to the closest remaining header — strip link\n\t * or accordion button — so focus never falls back to `<body>` when the\n\t * focused control disappears with its panel.\n\t */\n\tremovePanelAndRefocus(panel: HubPanelComponent): void {\n\t\tconst index = this.panels().indexOf(panel);\n\t\tif (index === -1) {\n\t\t\treturn;\n\t\t}\n\t\tthis.removePanel(panel);\n\t\tqueueMicrotask(() => this.#focusPanelAt(Math.min(index, this.panels().length - 1)));\n\t}\n\n\t/**\n\t * Activates a panel on behalf of the user (`tabs` / `pills` views): marks it\n\t * active, navigates when routed, and emits `panelChange`. In `multiple` mode\n\t * clicking an active panel toggles it off (the panes render side by side);\n\t * otherwise an already-active panel no-ops. Disabled panels always no-op.\n\t */\n\tselectPanel(panel: HubPanelComponent): void {\n\t\tif (panel.disabled() || this.formDisabled()) {\n\t\t\treturn;\n\t\t}\n\t\tif (this.allowsMultipleActive()) {\n\t\t\tif (panel.active()) {\n\t\t\t\tpanel.active.set(false);\n\t\t\t} else {\n\t\t\t\tpanel.active.set(true);\n\t\t\t\tpanel.navigate();\n\t\t\t\tthis.panelChange.emit({ prev: undefined, current: panel });\n\t\t\t}\n\t\t\tthis.#emitFormValue();\n\t\t\tthis.#onTouched();\n\t\t\tthis.#schedulePanelPlacement();\n\t\t\treturn;\n\t\t}\n\t\tif (panel.active()) {\n\t\t\treturn;\n\t\t}\n\t\tconst previousPanel = this.activePanel();\n\t\t// Deactivate the previously active panel up front so the emitted form\n\t\t// value reflects only the newly selected panel. The per-panel effect that\n\t\t// enforces single-active runs asynchronously, so relying on it here would\n\t\t// emit a stale value that still includes the previous panel.\n\t\tif (previousPanel && previousPanel !== panel) {\n\t\t\tpreviousPanel.active.set(false);\n\t\t}\n\t\tpanel.active.set(true);\n\t\tpanel.navigate();\n\t\tthis.panelChange.emit({ prev: previousPanel, current: panel });\n\t\tthis.#emitFormValue();\n\t\tthis.#onTouched();\n\t\tthis.#schedulePanelPlacement();\n\t}\n\n\t/**\n\t * Toggles a panel on behalf of the user (accordion view): an open panel\n\t * closes, a closed one opens — closing the others unless `multiple`.\n\t * Emits `panelChange` when a panel opens.\n\t */\n\ttogglePanel(panel: HubPanelComponent): void {\n\t\tif (panel.disabled() || this.formDisabled()) {\n\t\t\treturn;\n\t\t}\n\t\tif (panel.active()) {\n\t\t\tpanel.active.set(false);\n\t\t} else {\n\t\t\tconst previousPanel = this.allowsMultipleActive() ? undefined : this.activePanel();\n\t\t\tpanel.active.set(true);\n\t\t\tthis.panelChange.emit({ prev: previousPanel, current: panel });\n\t\t}\n\t\tthis.#emitFormValue();\n\t\tthis.#onTouched();\n\t\tthis.#schedulePanelPlacement();\n\t}\n\n\t/**\n\t * Marks the routed panel matching the current URL as active. Does not\n\t * navigate — activation through this path is URL-driven. No-op in the\n\t * accordion view, where routed panels are not supported.\n\t */\n\tsetActivePanel(): void {\n\t\tif (this.isAccordionView()) {\n\t\t\treturn;\n\t\t}\n\t\tconst [route, queryString] = this.#router.url.split('?');\n\t\tfor (const panel of this.panels()) {\n\t\t\tif (!panel.routerUrl()) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tlet matches: boolean;\n\t\t\tif (panel.pathMatch() === 'full') {\n\t\t\t\tconst currentUrl = queryString?.trim() ? `${route}?${queryString.trim()}` : route;\n\t\t\t\tmatches = currentUrl === panel.getFullRoute();\n\t\t\t} else {\n\t\t\t\tmatches = route === panel.getRoute();\n\t\t\t}\n\t\t\tif (matches) {\n\t\t\t\tif (!panel.active()) {\n\t\t\t\t\tpanel.active.set(true);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\t// ── ControlValueAccessor ────────────────────────────────────────────────\n\n\t/**\n\t * Writes the form value into the container: panels whose (`bindValue`-mapped)\n\t * value matches are activated, the rest are deactivated. With `multiple` an\n\t * array is expected; otherwise a single value.\n\t */\n\twriteValue(value: unknown): void {\n\t\tif (value == null) {\n\t\t\tthis.#formValue = [];\n\t\t} else if (this.multiple()) {\n\t\t\tthis.#formValue = Array.isArray(value) ? [...value] : [value];\n\t\t} else {\n\t\t\tthis.#formValue = Array.isArray(value) ? value.slice(0, 1) : [value];\n\t\t}\n\t\tthis.#applyFormValue();\n\t}\n\n\t/** Registers the form-control change callback. */\n\tregisterOnChange(onChange: (value: unknown) => void): void {\n\t\tthis.#onChange = onChange;\n\t}\n\n\t/** Registers the form-control touched callback. */\n\tregisterOnTouched(onTouched: () => void): void {\n\t\tthis.#onTouched = onTouched;\n\t}\n\n\t/** Enables/disables every panel header on behalf of the form control. */\n\tsetDisabledState(isDisabled: boolean): void {\n\t\tthis.formDisabled.set(isDisabled);\n\t}\n\n\t/** Keyboard navigation for the panel strip (arrows / Home / End / Delete). */\n\tprotected onPanelKeydown(event: KeyboardEvent, index: number): void {\n\t\tif (!this.isKeysAllowed()) {\n\t\t\treturn;\n\t\t}\n\t\tswitch (event.key) {\n\t\t\tcase 'ArrowRight':\n\t\t\tcase 'ArrowDown':\n\t\t\t\tif (event.key === 'ArrowDown' && !this.vertical()) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.#stepEnabledIndex(index, 1));\n\t\t\t\treturn;\n\t\t\tcase 'ArrowLeft':\n\t\t\tcase 'ArrowUp':\n\t\t\t\tif (event.key === 'ArrowUp' && !this.vertical()) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.#stepEnabledIndex(index, -1));\n\t\t\t\treturn;\n\t\t\tcase 'Home':\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.panels().findIndex((panel) => !panel.disabled()));\n\t\t\t\treturn;\n\t\t\tcase 'End': {\n\t\t\t\tevent.preventDefault();\n\t\t\t\tconst panels = this.panels();\n\t\t\t\tthis.#focusPanelAt(panels.length - 1 - [...panels].reverse().findIndex((panel) => !panel.disabled()));\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tcase 'Delete': {\n\t\t\t\tconst panel = this.panels()[index];\n\t\t\t\tif (panel?.removable()) {\n\t\t\t\t\tthis.removePanelAndRefocus(panel);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Keyboard navigation between accordion headers (arrows / Home / End /\n\t * Delete). Enter and Space toggle natively through the button click.\n\t */\n\tonAccordionKeydown(event: KeyboardEvent, panel: HubPanelComponent): void {\n\t\tif (!this.isKeysAllowed()) {\n\t\t\treturn;\n\t\t}\n\t\tconst index = this.panels().indexOf(panel);\n\t\tswitch (event.key) {\n\t\t\tcase 'ArrowDown':\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.#stepEnabledIndex(index, 1));\n\t\t\t\treturn;\n\t\t\tcase 'ArrowUp':\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.#stepEnabledIndex(index, -1));\n\t\t\t\treturn;\n\t\t\tcase 'Home':\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.panels().findIndex((candidate) => !candidate.disabled()));\n\t\t\t\treturn;\n\t\t\tcase 'End': {\n\t\t\t\tevent.preventDefault();\n\t\t\t\tconst panels = this.panels();\n\t\t\t\tthis.#focusPanelAt(panels.length - 1 - [...panels].reverse().findIndex((candidate) => !candidate.disabled()));\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tcase 'Delete': {\n\t\t\t\tif (panel.removable()) {\n\t\t\t\t\tthis.removePanelAndRefocus(panel);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Recomputes the enabled/disabled state of the scroll buttons. */\n\tprotected updateScrollButtons(): void {\n\t\tif (!this.scrollable() || this.isAccordionView()) {\n\t\t\treturn;\n\t\t}\n\t\tconst scroller = this.navScroller()?.nativeElement;\n\t\tif (!scroller) {\n\t\t\treturn;\n\t\t}\n\t\tconst { scrollLeft, scrollWidth } = scroller;\n\t\tthis.backwardIsDisabled.set(scrollLeft <= 0);\n\t\tthis.forwardIsDisabled.set(scrollLeft + contentBoxWidth(scroller) + 1 >= scrollWidth);\n\t}\n\n\t/** Re-syncs scroll controls and multiple-block sizing on window resize. */\n\tprotected onWindowResize(): void {\n\t\tthis.updateScrollButtons();\n\t\tthis.#scheduleMultipleBlockSizing();\n\t}\n\n\t/** Updates the scroll buttons as the strip scrolls. */\n\tprotected onScroll(): void {\n\t\tthis.updateScrollButtons();\n\t}\n\n\t/** Global index of a panel within the projected strip order. */\n\tprotected panelIndex(panel: HubPanelComponent): number {\n\t\treturn this.panelIndexMap().get(panel) ?? -1;\n\t}\n\n\t/** Scrolls the panel headers one viewport backward. */\n\tprotected navBackward(): void {\n\t\tconst scroller = this.navScroller()?.nativeElement;\n\t\tif (!scroller) {\n\t\t\treturn;\n\t\t}\n\t\tconst step = contentBoxWidth(scroller) - this.#visibleScrollButtonsWidth();\n\t\tscroller.scrollLeft = Math.max(scroller.scrollLeft - step, 0);\n\t}\n\n\t/** Scrolls the panel headers one viewport forward. */\n\tprotected navForward(): void {\n\t\tconst scroller = this.navScroller()?.nativeElement;\n\t\tif (!scroller) {\n\t\t\treturn;\n\t\t}\n\t\tconst step = contentBoxWidth(scroller) - this.#visibleScrollButtonsWidth();\n\t\tconst lastPosition = scroller.scrollWidth - step;\n\t\tscroller.scrollLeft = Math.min(scroller.scrollLeft + step, lastPosition);\n\t}\n\n\t/** Width currently taken by the visible scroll buttons. */\n\t#visibleScrollButtonsWidth(): number {\n\t\treturn [this.prevBtn()?.nativeElement, this.nextBtn()?.nativeElement].reduce(\n\t\t\t(total, button) => (button ? total + contentBoxWidth(button) : total),\n\t\t\t0\n\t\t);\n\t}\n\n\t/** Index of the enabled panel closest to `index`, or `-1` when none exists. */\n\t#closestEnabledIndex(index: number): number {\n\t\tconst panels = this.panels();\n\t\tfor (let step = 1; step <= panels.length; step += 1) {\n\t\t\tconst previous = panels[index - step];\n\t\t\tif (previous && !previous.disabled()) {\n\t\t\t\treturn index - step;\n\t\t\t}\n\t\t\tconst next = panels[index + step];\n\t\t\tif (next && !next.disabled()) {\n\t\t\t\treturn index + step;\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\n\t/** Next enabled panel index from `index` in `direction`, wrapping around. */\n\t#stepEnabledIndex(index: number, direction: 1 | -1): number {\n\t\tconst panels = this.panels();\n\t\tfor (let step = 1; step <= panels.length; step += 1) {\n\t\t\tconst candidate = (index + direction * step + panels.length * step) % panels.length;\n\t\t\tif (!panels[candidate].disabled()) {\n\t\t\t\treturn candidate;\n\t\t\t}\n\t\t}\n\t\treturn index;\n\t}\n\n\t/** Moves DOM focus to the panel header at `index` (strip link or accordion button). */\n\t#focusPanelAt(index: number): void {\n\t\tif (index < 0) {\n\t\t\treturn;\n\t\t}\n\t\tconst selector = this.isAccordionView() ? '.hub-panels__accordion-btn' : '.hub-panels__nav-link';\n\t\tconst headers = this.#elementRef.nativeElement.querySelectorAll<HTMLElement>(selector);\n\t\theaders[index]?.focus();\n\t}\n\n\t/**\n\t * Coalesces post-registration/removal housekeeping into one microtask:\n\t * re-applies the bound form value to the current panels, guarantees an\n\t * active panel (non-routed `tabs` / `pills` containers without a bound\n\t * form) and refreshes the scroll buttons after the strip changed size.\n\t * Skipped until the first render — before it the projected panels' inputs\n\t * are not bound yet, and the constructor's `afterNextRender` performs the\n\t * initial pass instead.\n\t */\n\t#scheduleSync(): void {\n\t\tif (this.#syncScheduled || this.#isDestroyed) {\n\t\t\treturn;\n\t\t}\n\t\tthis.#syncScheduled = true;\n\t\tqueueMicrotask(() => {\n\t\t\tthis.#syncScheduled = false;\n\t\t\tif (this.#isDestroyed || !this.#viewInitialised) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tthis.#applyFormValue();\n\t\t\tthis.#ensureActivePanel();\n\t\t\tthis.#schedulePanelPlacement();\n\t\t\tthis.updateScrollButtons();\n\t\t});\n\t}\n\n\t/** Coalesces DOM moves for the projected `hub-panel` hosts. */\n\t#schedulePanelPlacement(): void {\n\t\tif (this.#placementScheduled || this.#isDestroyed) {\n\t\t\treturn;\n\t\t}\n\t\tthis.#placementScheduled = true;\n\t\trequestAnimationFrame(() => {\n\t\t\tthis.#placementScheduled = false;\n\t\t\tif (this.#isDestroyed || !this.#viewInitialised) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tthis.#runPanelPlacementPass();\n\t\t\trequestAnimationFrame(() => {\n\t\t\t\tif (this.#isDestroyed || !this.#viewInitialised) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tthis.#runPanelPlacementPass();\n\t\t\t});\n\t\t});\n\t}\n\n\t/** Performs one projected-panel placement pass plus dependent sizing. */\n\t#runPanelPlacementPass(): void {\n\t\tthis.#placeProjectedPanels();\n\t\tthis.#scheduleMultipleBlockSizing();\n\t}\n\n\t/** Coalesces the DOM measurements needed by `multiple + vertical`. */\n\t#scheduleMultipleBlockSizing(): void {\n\t\tif (this.#multipleBlockSizingScheduled || this.#isDestroyed) {\n\t\t\treturn;\n\t\t}\n\t\tthis.#multipleBlockSizingScheduled = true;\n\t\trequestAnimationFrame(() => {\n\t\t\tthis.#multipleBlockSizingScheduled = false;\n\t\t\tif (this.#isDestroyed || !this.#viewInitialised) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tthis.#syncMultipleBlockSizing();\n\t\t});\n\t}\n\n\t/** Moves projected panel hosts into their visible multiple-block container. */\n\t#placeProjectedPanels(): void {\n\t\tconst contentRoot = this.contentRoot()?.nativeElement;\n\t\tif (!contentRoot) {\n\t\t\treturn;\n\t\t}\n\t\tif (!this.allowsMultipleActive() || this.isAccordionView()) {\n\t\t\tfor (const panel of this.panels()) {\n\t\t\t\tconst panelElement = panel.elementRef.nativeElement;\n\t\t\t\tif (panelElement.parentElement !== contentRoot) {\n\t\t\t\t\tthis.#renderer.appendChild(contentRoot, panelElement);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn;\n\t\t}\n\t\tconst hostMap = new Map(\n\t\t\tArray.from(\n\t\t\t\tthis.#elementRef.nativeElement.querySelectorAll<HTMLElement>(\n\t\t\t\t\t'.hub-panels__multiple-layout .hub-panels__multiple-pane-host'\n\t\t\t\t)\n\t\t\t).map((host) => [host.dataset['panelId'] ?? '', host] as const)\n\t\t);\n\t\tfor (const panel of this.panels()) {\n\t\t\tconst panelElement = panel.elementRef.nativeElement;\n\t\t\tconst targetHost = hostMap.get(panel.id()) ?? contentRoot;\n\t\t\tif (panelElement.parentElement !== targetHost) {\n\t\t\t\tthis.#renderer.appendChild(targetHost, panelElement);\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Updates the minimum content width for each `multiple + vertical` block. */\n\t#syncMultipleBlockSizing(): void {\n\t\tfor (const blockRef of this.multipleBlocks()) {\n\t\t\tconst block = blockRef.nativeElement;\n\t\t\tthis.#renderer.removeStyle(block, '--hub-panels-multiple-vertical-panel-min-width', RendererStyleFlags2.DashCase);\n\t\t\tif (!this.vertical() || !this.allowsMultipleActive() || this.isAccordionView()) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tconst header = block.querySelector(':scope > .hub-panels__header');\n\t\t\tif (!(header instanceof HTMLElement)) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tconst headerStackHeight = Math.ceil(header.getBoundingClientRect().height);\n\t\t\tthis.#renderer.setStyle(\n\t\t\t\tblock,\n\t\t\t\t'--hub-panels-multiple-vertical-panel-min-width',\n\t\t\t\t`${headerStackHeight}px`,\n\t\t\t\tRendererStyleFlags2.DashCase\n\t\t\t);\n\t\t}\n\t}\n\n\t/**\n\t * Activates the first enabled panel when none is active. Skipped for the\n\t * accordion view (panels start collapsed), for routed containers (the URL\n\t * is the single source of truth) and when a form value is bound (the form\n\t * is).\n\t */\n\t#ensureActivePanel(): void {\n\t\tif (this.isAccordionView() || this.#formValue !== null) {\n\t\t\treturn;\n\t\t}\n\t\tif (this.allowsMultipleActive()) {\n\t\t\treturn;\n\t\t}\n\t\tconst panels = this.panels();\n\t\tif (!panels.length || panels.some((panel) => panel.active())) {\n\t\t\treturn;\n\t\t}\n\t\tif (panels.some((panel) => !!panel.routerUrl())) {\n\t\t\treturn;\n\t\t}\n\t\tpanels.find((panel) => !panel.disabled())?.active.set(true);\n\t}\n\n\t/** Activates/deactivates panels so they mirror the bound form value. */\n\t#applyFormValue(): void {\n\t\tif (this.#formValue === null) {\n\t\t\treturn;\n\t\t}\n\t\tconst compare = this.compareWith();\n\t\tfor (const panel of this.panels()) {\n\t\t\tconst panelValue = this.#comparableValue(panel);\n\t\t\tconst matches = this.#formValue.some((selectedValue) => compare(selectedValue, panelValue));\n\t\t\tif (panel.active() !== matches) {\n\t\t\t\tpanel.active.set(matches);\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Emits the current selection through the form-control callback. */\n\t#emitFormValue(): void {\n\t\tconst compare = this.compareWith();\n\t\tconst activeValues = this.panels()\n\t\t\t.filter((panel) => panel.active())\n\t\t\t.map((panel) => this.#comparableValue(panel));\n\t\tif (this.#formValue !== null) {\n\t\t\tthis.#formValue = [...activeValues];\n\t\t}\n\t\t// Deduplicate defensively when several panels share the same value.\n\t\tconst uniqueValues = activeValues.filter(\n\t\t\t(value, index) => activeValues.findIndex((candidate) => compare(candidate, value)) === index\n\t\t);\n\t\tthis.#onChange(this.multiple() ? uniqueValues : (uniqueValues[0] ?? null));\n\t}\n\n\t/** Form value of a panel with the `bindValue` path applied. */\n\t#comparableValue(panel: HubPanelComponent): unknown {\n\t\tconst rawValue = panel.formValue();\n\t\tconst bindPath = this.bindValue();\n\t\treturn bindPath ? readByPath(rawValue, bindPath) : rawValue;\n\t}\n}\n","@if (!isAccordionView() && !isCardView()) {\n\t@if (multiple()) {\n\t\t<div class=\"hub-panels__multiple-layout\">\n\t\t\t@for (group of multipleHeaderGroups(); track group.activePanel ?? group.headers[0]) {\n\t\t\t\t<div\n\t\t\t\t\t#multipleBlock\n\t\t\t\t\tclass=\"hub-panels hub-panels__multiple-block\"\n\t\t\t\t\t[class.hub-panels--tabs]=\"type() === 'tabs'\"\n\t\t\t\t\t[class.hub-panels--pills]=\"type() === 'pills'\"\n\t\t\t\t\t[class.hub-panels--vertical]=\"vertical()\"\n\t\t\t\t>\n\t\t\t\t\t<div class=\"hub-panels__header\">\n\t\t\t\t\t\t<ul\n\t\t\t\t\t\t\tclass=\"hub-panels__nav\"\n\t\t\t\t\t\t\trole=\"tablist\"\n\t\t\t\t\t\t\t[attr.aria-label]=\"config.ariaLabel\"\n\t\t\t\t\t\t\t[attr.aria-orientation]=\"vertical() ? 'vertical' : null\"\n\t\t\t\t\t\t\t[class.hub-panels__nav--tabs]=\"type() === 'tabs'\"\n\t\t\t\t\t\t\t[class.hub-panels__nav--pills]=\"type() === 'pills'\"\n\t\t\t\t\t\t\t[class.hub-panels__nav--vertical]=\"vertical()\"\n\t\t\t\t\t\t\t[class.hub-panels__nav--justified]=\"justified()\"\n\t\t\t\t\t\t>\n\t\t\t\t\t\t\t@for (panel of group.headers; track panel) {\n\t\t\t\t\t\t\t\t<li\n\t\t\t\t\t\t\t\t\tclass=\"hub-panels__nav-item\"\n\t\t\t\t\t\t\t\t\t[class]=\"panel.customClass()\"\n\t\t\t\t\t\t\t\t\t[class.hub-panels__nav-item--active]=\"panel.active()\"\n\t\t\t\t\t\t\t\t\t[class.hub-panels__nav-item--disabled]=\"panel.disabled()\"\n\t\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t\t<button\n\t\t\t\t\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\t\t\t\t\tclass=\"hub-panels__nav-link\"\n\t\t\t\t\t\t\t\t\t\trole=\"tab\"\n\t\t\t\t\t\t\t\t\t\t[id]=\"panel.id() + '-link'\"\n\t\t\t\t\t\t\t\t\t\t[class.hub-panels__nav-link--active]=\"panel.active()\"\n\t\t\t\t\t\t\t\t\t\t[class.hub-panels__nav-link--disabled]=\"panel.disabled()\"\n\t\t\t\t\t\t\t\t\t\t[disabled]=\"panel.disabled() || formDisabled()\"\n\t\t\t\t\t\t\t\t\t\t[attr.aria-controls]=\"panel.id()\"\n\t\t\t\t\t\t\t\t\t\t[attr.aria-selected]=\"panel.active()\"\n\t\t\t\t\t\t\t\t\t\t[attr.tabindex]=\"\n\t\t\t\t\t\t\t\t\t\t\tpanel.active() || (!activePanel() && panelIndex(panel) === 0) ? null : -1\n\t\t\t\t\t\t\t\t\t\t\"\n\t\t\t\t\t\t\t\t\t\t(click)=\"selectPanel(panel)\"\n\t\t\t\t\t\t\t\t\t\t(keydown)=\"onPanelKeydown($event, panelIndex(panel))\"\n\t\t\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t\t\t@if (panel.headingRef(); as headingRef) {\n\t\t\t\t\t\t\t\t\t\t\t<ng-container [ngTemplateOutlet]=\"headingRef\" />\n\t\t\t\t\t\t\t\t\t\t} @else {\n\t\t\t\t\t\t\t\t\t\t\t{{ panel.heading() }}\n\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t</button>\n\t\t\t\t\t\t\t\t\t<!-- Real sibling button: a control nested inside the tab\n\t\t\t\t\t\t\t\t\t\t button would be invalid HTML and unreachable by keyboard.\n\t\t\t\t\t\t\t\t\t\t It overlays the tab's reserved end padding, so the ✕ keeps\n\t\t\t\t\t\t\t\t\t\t its visual spot inside the tab chrome. -->\n\t\t\t\t\t\t\t\t\t@if (panel.removable()) {\n\t\t\t\t\t\t\t\t\t\t<button\n\t\t\t\t\t\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\t\t\t\t\t\tclass=\"hub-panels__remove-btn\"\n\t\t\t\t\t\t\t\t\t\t\t[disabled]=\"panel.disabled() || formDisabled()\"\n\t\t\t\t\t\t\t\t\t\t\t[attr.aria-label]=\"panel.removeLabel()\"\n\t\t\t\t\t\t\t\t\t\t\t(click)=\"removePanelAndRefocus(panel)\"\n\t\t\t\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t\t\t\t&times;\n\t\t\t\t\t\t\t\t\t\t</button>\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t</li>\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t</ul>\n\t\t\t\t\t\t@if (!justified() && type() !== 'pills' && !vertical()) {\n\t\t\t\t\t\t\t<div class=\"hub-panels__spacer\"></div>\n\t\t\t\t\t\t}\n\t\t\t\t\t</div>\n\n\t\t\t\t\t@if (group.activePanel) {\n\t\t\t\t\t\t<div class=\"hub-panels__content\" [class.hub-panels__content--pills]=\"type() === 'pills'\">\n\t\t\t\t\t\t\t<div\n\t\t\t\t\t\t\t\t#multiplePaneHost\n\t\t\t\t\t\t\t\tclass=\"hub-panels__multiple-pane-host\"\n\t\t\t\t\t\t\t\t[attr.data-panel-id]=\"group.activePanel.id()\"\n\t\t\t\t\t\t\t></div>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t}\n\t\t\t\t</div>\n\t\t\t}\n\t\t</div>\n\t} @else {\n\t\t<div class=\"hub-panels__header\">\n\t\t\t@if (scrollable() && !backwardIsDisabled()) {\n\t\t\t\t<button\n\t\t\t\t\t#prevBtn\n\t\t\t\t\ttype=\"button\"\n\t\t\t\t\tclass=\"hub-panels__scroll-btn hub-panels__scroll-btn--backward\"\n\t\t\t\t\t[attr.aria-label]=\"config.scrollBackwardAriaLabel\"\n\t\t\t\t\t(click)=\"navBackward()\"\n\t\t\t\t></button>\n\t\t\t}\n\n\t\t\t<div #navScroller class=\"hub-panels__nav-scroller\" (scroll)=\"onScroll()\">\n\t\t\t\t<ul\n\t\t\t\t\tclass=\"hub-panels__nav\"\n\t\t\t\t\trole=\"tablist\"\n\t\t\t\t\t[attr.aria-label]=\"config.ariaLabel\"\n\t\t\t\t\t[attr.aria-orientation]=\"vertical() ? 'vertical' : null\"\n\t\t\t\t\t[class.hub-panels__nav--tabs]=\"type() === 'tabs'\"\n\t\t\t\t\t[class.hub-panels__nav--pills]=\"type() === 'pills'\"\n\t\t\t\t\t[class.hub-panels__nav--vertical]=\"vertical()\"\n\t\t\t\t\t[class.hub-panels__nav--justified]=\"justified()\"\n\t\t\t\t>\n\t\t\t\t\t@for (panel of panels(); track panel; let index = $index) {\n\t\t\t\t\t\t<li\n\t\t\t\t\t\t\tclass=\"hub-panels__nav-item\"\n\t\t\t\t\t\t\t[class]=\"panel.customClass()\"\n\t\t\t\t\t\t\t[class.hub-panels__nav-item--active]=\"panel.active()\"\n\t\t\t\t\t\t\t[class.hub-panels__nav-item--disabled]=\"panel.disabled()\"\n\t\t\t\t\t\t>\n\t\t\t\t\t\t\t<button\n\t\t\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\t\t\tclass=\"hub-panels__nav-link\"\n\t\t\t\t\t\t\t\trole=\"tab\"\n\t\t\t\t\t\t\t\t[id]=\"panel.id() + '-link'\"\n\t\t\t\t\t\t\t\t[class.hub-panels__nav-link--active]=\"panel.active()\"\n\t\t\t\t\t\t\t\t[class.hub-panels__nav-link--disabled]=\"panel.disabled()\"\n\t\t\t\t\t\t\t\t[disabled]=\"panel.disabled() || formDisabled()\"\n\t\t\t\t\t\t\t\t[attr.aria-controls]=\"panel.id()\"\n\t\t\t\t\t\t\t\t[attr.aria-selected]=\"panel.active()\"\n\t\t\t\t\t\t\t\t[attr.tabindex]=\"panel.active() || (!activePanel() && index === 0) ? null : -1\"\n\t\t\t\t\t\t\t\t(click)=\"selectPanel(panel)\"\n\t\t\t\t\t\t\t\t(keydown)=\"onPanelKeydown($event, index)\"\n\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t@if (panel.headingRef(); as headingRef) {\n\t\t\t\t\t\t\t\t\t<ng-container [ngTemplateOutlet]=\"headingRef\" />\n\t\t\t\t\t\t\t\t} @else {\n\t\t\t\t\t\t\t\t\t{{ panel.heading() }}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t</button>\n\t\t\t\t\t\t\t<!-- Real sibling button: a control nested inside the tab\n\t\t\t\t\t\t\t\t button would be invalid HTML and unreachable by keyboard.\n\t\t\t\t\t\t\t\t It overlays the tab's reserved end padding, so the ✕ keeps\n\t\t\t\t\t\t\t\t its visual spot inside the tab chrome. -->\n\t\t\t\t\t\t\t@if (panel.removable()) {\n\t\t\t\t\t\t\t\t<button\n\t\t\t\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\t\t\t\tclass=\"hub-panels__remove-btn\"\n\t\t\t\t\t\t\t\t\t[disabled]=\"panel.disabled() || formDisabled()\"\n\t\t\t\t\t\t\t\t\t[attr.aria-label]=\"panel.removeLabel()\"\n\t\t\t\t\t\t\t\t\t(click)=\"removePanelAndRefocus(panel)\"\n\t\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t\t&times;\n\t\t\t\t\t\t\t\t</button>\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t</li>\n\t\t\t\t\t}\n\t\t\t\t</ul>\n\t\t\t\t@if (!justified() && type() !== 'pills') {\n\t\t\t\t\t<div class=\"hub-panels__spacer\"></div>\n\t\t\t\t}\n\t\t\t</div>\n\n\t\t\t@if (scrollable() && !forwardIsDisabled()) {\n\t\t\t\t<button\n\t\t\t\t\t#nextBtn\n\t\t\t\t\ttype=\"button\"\n\t\t\t\t\tclass=\"hub-panels__scroll-btn hub-panels__scroll-btn--forward\"\n\t\t\t\t\t[attr.aria-label]=\"config.scrollForwardAriaLabel\"\n\t\t\t\t\t(click)=\"navForward()\"\n\t\t\t\t></button>\n\t\t\t}\n\t\t</div>\n\t}\n}\n\n<div\n\t#contentRoot\n\tclass=\"hub-panels__content\"\n\t[class.hub-panels__content--pills]=\"type() === 'pills'\"\n\t[class.hub-panels__content--accordion]=\"isAccordionView()\"\n\t[class.hub-panels__content--multiple-parking]=\"!isAccordionView() && multiple()\"\n>\n\t@if (activePanelHasRouter()) {\n\t\t<router-outlet />\n\t} @else {\n\t\t<ng-content />\n\t}\n</div>\n","import { NgTemplateOutlet } from '@angular/common';\nimport {\n\tforwardRef,\n\tbooleanAttribute,\n\tChangeDetectionStrategy,\n\tComponent,\n\tcomputed,\n\teffect,\n\tElementRef,\n\tinject,\n\tinput,\n\tmodel,\n\tOnDestroy,\n\toutput,\n\tRenderer2,\n\tsignal,\n\tTemplateRef,\n\tViewEncapsulation\n} from '@angular/core';\nimport { Params, Router } from '@angular/router';\n\nimport { HubPanelAppearance, HubPanelVariant } from '../../models/panels.types';\nimport { resolveHubAccent } from 'ng-hub-ui-utils';\nimport { HubPanelsComponent } from '../panels/panels.component';\n\n/** Monotonic counter backing the auto-generated accessibility ids. */\nlet nextPanelId = 0;\n\n/**\n * One content panel inside a `<hub-panels>` container.\n *\n * In the `tabs` / `pills` views the host element is the tab *panel*\n * (`role=\"tabpanel\"`) and the clickable header is rendered by\n * {@link HubPanelsComponent} in the strip. In the `accordion` view this component\n * renders its own disclosure header plus an animated collapse wrapper around\n * the projected content. In every view the header comes from `heading` or from\n * a `<ng-template hubPanelHeading>` projected inside this element.\n *\n * Panels can be plain content panes or routed: when `routerLink` is set, the\n * container renders a `<router-outlet>` instead of the projected panels and\n * the active panel follows the current URL (`tabs` / `pills` views only).\n *\n * @example\n * ```html\n * <hub-panels>\n * <hub-panel heading=\"Fields\">…</hub-panel>\n * <hub-panel>\n * <ng-template hubPanelHeading>Validations <span class=\"badge\">3</span></ng-template>\n * …\n * </hub-panel>\n * </hub-panels>\n * ```\n */\nimport { HUB_PANEL } from './panel.token';\n\n@Component({\n\tselector: 'hub-panel, [hub-panel]',\n\tproviders: [{ provide: HUB_PANEL, useExisting: forwardRef(() => HubPanelComponent) }],\n\texportAs: 'hubPanel',\n\timports: [NgTemplateOutlet],\n\ttemplateUrl: './panel.component.html',\n\t// The `card` view styles (and the projected header/footer bands) live here so\n\t// a standalone `<hub-panel>` — used outside any `<hub-panels>` container, which\n\t// would otherwise be the only source of the global styles — is styled too.\n\t// `ViewEncapsulation.None` is required so the rules reach the projected,\n\t// consumer-owned `[hubPanelHeader]` / `[hubPanelFooter]` elements.\n\tstyleUrl: './panel.component.scss',\n\tencapsulation: ViewEncapsulation.None,\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\thost: {\n\t\tclass: 'hub-panels__panel',\n\t\t'[attr.id]': 'accordionView() || cardView() ? null : id()',\n\t\t'[attr.role]': \"alertView() ? 'alert' : (accordionView() || cardView() ? null : 'tabpanel')\",\n\t\t'[attr.aria-labelledby]': \"accordionView() || cardView() ? null : id() + '-link'\",\n\t\t'[attr.data-variant]': 'cardView() ? (variant() ?? null) : null',\n\t\t'[style.--hub-panels-alert-accent]': 'alertAccent()',\n\t\t'[style.--hub-panels-card-accent]': 'cardAccent()',\n\t\t'[class.hub-panels__panel--active]': 'active()',\n\t\t'[class.hub-panels__panel--accordion]': 'accordionView()',\n\t\t'[class.hub-panels__panel--toggle-start]': 'toggleAtStart()',\n\t\t'[class.hub-panels__panel--card]': 'cardView() && !alertView()',\n\t\t'[class.hub-panels__panel--alert]': 'alertView()',\n\t\t'[class.hub-panels__panel--fill]': 'fill()',\n\t\t'[class.hub-panels__panel--flush]': 'flush()'\n\t}\n})\nexport class HubPanelComponent implements OnDestroy {\n\t/** Host element reference — exposed so the container can detach removed panes. */\n\treadonly elementRef = inject<ElementRef<HTMLElement>>(ElementRef);\n\n\treadonly #renderer = inject(Renderer2);\n\treadonly #router = inject(Router);\n\n\t/**\n\t * Owning panels container, or `null` when the panel is used standalone\n\t * (outside any `<hub-panels>`), in which case it renders as a card.\n\t * Exposed to the template for the accordion header.\n\t *\n\t * Resolved with `host: true`, so a panel only binds to a group declared in\n\t * the SAME template (its direct container). Without the host boundary the\n\t * lookup walks the whole ancestor injector tree, and a standalone panel\n\t * inside a component projected into a tab pane would register itself as a\n\t * hidden tab of the outer group instead of rendering as a card.\n\t */\n\tprotected readonly tabset = inject(HubPanelsComponent, { optional: true, host: true });\n\n\t/**\n\t * Opts a standalone `<hub-panel>` OUT of an ancestor `<hub-panels>` group so it\n\t * renders as a plain card even when nested inside a tabs / pills / accordion\n\t * container (otherwise hierarchical DI would capture it as a hidden 0×0 tab).\n\t *\n\t * Must be a STATIC attribute (`<hub-panel standalone>`): the opt-out is decided\n\t * when the panel is created — before dynamic inputs are applied — so it is read\n\t * from the host attribute rather than a reactive input.\n\t */\n\treadonly standalone = this.elementRef.nativeElement.hasAttribute('standalone');\n\n\t/** Plain-text panel header. Ignored when a `hubPanelHeading` template exists. */\n\treadonly heading = input<string | undefined>(undefined);\n\n\t/**\n\t * Visual appearance of a standalone panel: a plain `card` (default) or a\n\t * semantic `alert` callout. Only meaningful when the panel renders as a\n\t * card (used standalone or inside a `card` container); ignored in the\n\t * tabs / pills / accordion strip views.\n\t */\n\treadonly appearance = input<HubPanelAppearance>('card');\n\n\t/**\n\t * Semantic colour applied when `appearance` is `alert`. The built-in values\n\t * (`primary` / `success` / `danger` / `warning` / `info`) render with the\n\t * design-system tints. Any other string is also accepted: the alert reads\n\t * `--hub-sys-color-<variant>` from the host application, so a custom accent\n\t * palette interconnects with no changes to this library. Omit for a neutral\n\t * alert.\n\t */\n\treadonly variant = input<HubPanelVariant | (string & {}) | undefined>(undefined);\n\n\t/**\n\t * Makes a card panel fill its parent's height and lets an inner scroll region\n\t * work: the host, both content wrappers and the body become a flex column\n\t * (`flex: 1; min-height: 0`) and the body scrolls. Opt-in; off by default so\n\t * existing layouts are byte-identical. Card view only.\n\t */\n\treadonly fill = input(false, { transform: booleanAttribute });\n\n\t/**\n\t * Removes the card body padding (`--hub-panels-card-padding-x/-y` → 0) so a card\n\t * can host a flush element (a table, a list, a media block) edge-to-edge. Opt-in;\n\t * card view only.\n\t */\n\treadonly flush = input(false, { transform: booleanAttribute });\n\n\t/**\n\t * Unique id used for the `tab` / `tabpanel` (or accordion header / region)\n\t * ARIA pairing. Auto-generated (`hub-panel-<n>`) when not provided.\n\t */\n\treadonly id = input<string>(`hub-panel-${nextPanelId++}`);\n\n\t/** Whether the panel cannot be activated. */\n\treadonly disabled = input(false, { transform: booleanAttribute });\n\n\t/** Whether the panel shows a remove affordance (✕ and the Delete key). */\n\treadonly removable = input(false, { transform: booleanAttribute });\n\n\t/**\n\t * Accessible name announced for the ✕ remove button (`removable` panels).\n\t * The visible glyph is decorative, so this label is what assistive\n\t * technologies read; override it to localize the control.\n\t */\n\treadonly removeLabel = input<string>('Remove panel');\n\n\t/**\n\t * URL comparison used to mark routed panels active: `'route'` compares the\n\t * path only, `'full'` also compares query params.\n\t */\n\treadonly pathMatch = input<'route' | 'full'>('route');\n\n\t/** Navigation target that turns this panel into a routed panel. */\n\treadonly routerLink = input<string | string[] | null | undefined>(undefined);\n\n\t/** Query params appended when navigating to `routerLink`. */\n\treadonly queryParams = input<Params | null | undefined>(undefined);\n\n\t/** Extra CSS classes applied to both the nav item and this pane. */\n\treadonly customClass = input<string | undefined>(undefined);\n\n\t/**\n\t * Value this panel contributes when the container is used as a form control\n\t * (see {@link HubPanelsComponent} `ControlValueAccessor`). Defaults to `id`.\n\t */\n\treadonly value = input<unknown>(undefined);\n\n\t/** Whether the panel is currently active (expanded, in the accordion view). */\n\treadonly active = model(false);\n\n\t/** Emitted when the panel becomes active. */\n\treadonly selectPanel = output<HubPanelComponent>();\n\n\t/** Emitted when the panel stops being active. */\n\treadonly deselectPanel = output<HubPanelComponent>();\n\n\t/** Emitted when the panel is removed through the ✕ button or the Delete key. */\n\treadonly removed = output<HubPanelComponent>();\n\n\t/** Custom header template registered by `HubPanelHeadingDirective`. */\n\treadonly headingRef = signal<TemplateRef<unknown> | undefined>(undefined);\n\n\t/**\n\t * Header actions template registered by `HubPanelHeadingActionsDirective`.\n\t * Rendered beside the accordion disclosure button — never inside it — so\n\t * real `<button>`s stay valid and reachable while the row is collapsed.\n\t */\n\treadonly headingActionsRef = signal<TemplateRef<unknown> | undefined>(undefined);\n\n\t/** Whether the owning container renders the accordion visualization. */\n\tprotected readonly accordionView = computed(() => !this.standalone && (this.tabset?.isAccordionView() ?? false));\n\n\t/**\n\t * Whether this panel's disclosure chevron leads the header row.\n\t *\n\t * Resolved on the PANEL, not on the container: a nested accordion is a DOM descendant of\n\t * the outer one, so a descendant selector on the container would leak the outer chevron\n\t * placement into every accordion inside its panels.\n\t */\n\tprotected readonly toggleAtStart = computed(() => this.accordionView() && this.tabset?.togglePosition() === 'start');\n\n\t/**\n\t * Whether this panel renders as a card: either inside a `<hub-panels\n\t * type=\"card\">` container or standalone (no owning container at all).\n\t */\n\tprotected readonly cardView = computed(() => this.standalone || !this.tabset || this.tabset.isCardView());\n\n\t/**\n\t * Whether this panel renders as a semantic alert: `appearance=\"alert\"` while\n\t * in a card-capable context (standalone or inside a `card` container). In the\n\t * strip / accordion views the alert appearance is ignored.\n\t */\n\tprotected readonly alertView = computed(() => this.appearance() === 'alert' && this.cardView());\n\n\t/**\n\t * Inline accent fed to the alert styles, resolved from the `variant` input so\n\t * ANY colour works. A bareword (a semantic name, a registered accent or a CSS\n\t * named colour) resolves to `var(--hub-sys-color-<variant>, <variant>)` — the\n\t * design-system token with the word itself as the raw fallback; a literal\n\t * (`#hex` / `rgb()` / `oklch()` / `var()`) is passed through unchanged. Returns\n\t * `null` for a neutral alert / non-alert view. The built-in semantic variants\n\t * additionally pick up their exact ds tints through the SCSS `@each`.\n\t */\n\tprotected readonly alertAccent = computed(() => {\n\t\tif (!this.alertView()) {\n\t\t\treturn null;\n\t\t}\n\t\treturn resolveHubAccent(this.variant());\n\t});\n\n\t/**\n\t * Inline accent fed to the card variant tint, resolved from the `variant` input\n\t * exactly like {@link alertAccent}: a bareword becomes\n\t * `var(--hub-sys-color-<variant>, <variant>)` and a literal colour is passed\n\t * through unchanged. Returns `null` for an alert or non-card view, keeping the\n\t * card variant set open with no colour values living in this library.\n\t */\n\tprotected readonly cardAccent = computed(() => {\n\t\tif (!this.cardView() || this.alertView()) {\n\t\t\treturn null;\n\t\t}\n\t\treturn resolveHubAccent(this.variant());\n\t});\n\n\t/** Form value resolved for this panel: the explicit `value` or the panel id. */\n\treadonly formValue = computed(() => (this.value() !== undefined ? this.value() : this.id()));\n\n\t/** `routerLink` normalised to a segments array, or `null` when not routed. */\n\treadonly routerUrl = computed<string[] | null>(() => {\n\t\tconst link = this.routerLink();\n\t\tif (!link) {\n\t\t\treturn null;\n\t\t}\n\t\treturn Array.isArray(link) ? link : [link];\n\t});\n\n\t/** Last activation state seen by the effect — avoids emitting on init. */\n\t#wasActive = false;\n\n\tconstructor() {\n\t\t// A standalone panel (no container, or explicitly `standalone` inside one)\n\t\t// renders as a card and skips registration so it never becomes a hidden tab.\n\t\tif (!this.standalone) {\n\t\t\tthis.tabset?.registerPanel(this);\n\t\t}\n\n\t\t// Mirror `customClass` onto the pane host element.\n\t\teffect((onCleanup) => {\n\t\t\tconst classes = (this.customClass() ?? '')\n\t\t\t\t.split(' ')\n\t\t\t\t.map((cssClass) => cssClass.trim())\n\t\t\t\t.filter((cssClass) => cssClass.length > 0);\n\t\t\tfor (const cssClass of classes) {\n\t\t\t\tthis.#renderer.addClass(this.elementRef.nativeElement, cssClass);\n\t\t\t}\n\t\t\tonCleanup(() => {\n\t\t\t\tfor (const cssClass of classes) {\n\t\t\t\t\tthis.#renderer.removeClass(this.elementRef.nativeElement, cssClass);\n\t\t\t\t}\n\t\t\t});\n\t\t});\n\n\t\t// Activation side effects: emit outputs and enforce single-active-panel\n\t\t// (unless the container allows multiple expanded panels — accordion mode).\n\t\teffect(() => {\n\t\t\tconst isActive = this.active();\n\t\t\tif (isActive && this.disabled()) {\n\t\t\t\tthis.active.set(false);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tif (isActive === this.#wasActive) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tthis.#wasActive = isActive;\n\t\t\tif (isActive) {\n\t\t\t\tthis.selectPanel.emit(this);\n\t\t\t\tif (this.tabset && !this.tabset.allowsMultipleActive()) {\n\t\t\t\t\tfor (const panel of this.tabset.panels()) {\n\t\t\t\t\t\tif (panel !== this) {\n\t\t\t\t\t\t\tpanel.active.set(false);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthis.deselectPanel.emit(this);\n\t\t\t}\n\t\t});\n\t}\n\n\tngOnDestroy(): void {\n\t\tif (!this.standalone) {\n\t\t\tthis.tabset?.removePanel(this, { reselect: false, emit: false, track: false });\n\t\t}\n\t}\n\n\t/** Route path plus query string, or `null` when the panel is not routed. */\n\tgetFullRoute(): string | null {\n\t\tconst route = this.getRoute();\n\t\tif (!route) {\n\t\t\treturn null;\n\t\t}\n\t\tconst queryString = this.getQueryParamsString();\n\t\treturn queryString ? `${route}?${queryString}` : route;\n\t}\n\n\t/** Normalised absolute route path, or `null` when the panel is not routed. */\n\tgetRoute(): string | null {\n\t\tconst routerUrl = this.routerUrl();\n\t\tif (!routerUrl) {\n\t\t\treturn null;\n\t\t}\n\t\tlet route = routerUrl.join('/').replace(/\\/\\/+/g, '/');\n\t\tif (route.charAt(0) === '.') {\n\t\t\troute = route.substring(1);\n\t\t}\n\t\tif (route.charAt(0) !== '/') {\n\t\t\troute = `/${route}`;\n\t\t}\n\t\treturn route;\n\t}\n\n\t/** `queryParams` serialised as `key=value&…`, or `null` when empty. */\n\tgetQueryParamsString(): string | null {\n\t\tconst params = this.queryParams();\n\t\tif (!params || !Object.keys(params).length) {\n\t\t\treturn null;\n\t\t}\n\t\treturn Object.entries(params)\n\t\t\t.map(([key, value]) => `${key}=${value}`)\n\t\t\t.join('&');\n\t}\n\n\t/** Navigates to the panel's route. No-op for non-routed panels. */\n\tnavigate(): void {\n\t\tconst routerUrl = this.routerUrl();\n\t\tif (routerUrl) {\n\t\t\tthis.#router.navigate(routerUrl, { queryParams: this.queryParams() ?? {} });\n\t\t}\n\t}\n\n\t/** Accordion header click — toggles this panel through the container. */\n\tprotected onAccordionHeaderClick(): void {\n\t\tthis.tabset?.togglePanel(this);\n\t}\n\n\t/** Accordion header keyboard navigation, delegated to the container. */\n\tprotected onAccordionHeaderKeydown(event: KeyboardEvent): void {\n\t\tthis.tabset?.onAccordionKeydown(event, this);\n\t}\n\n\t/**\n\t * Removes this panel through the accordion header's ✕ button, handing\n\t * keyboard focus to the closest remaining header afterwards.\n\t */\n\tprotected removeSelf(): void {\n\t\tthis.tabset?.removePanelAndRefocus(this);\n\t}\n}\n","@if (accordionView()) {\n\t<h2 class=\"hub-panels__accordion-header\" [class.hub-panels__accordion-header--expanded]=\"active()\">\n\t\t<button\n\t\t\ttype=\"button\"\n\t\t\tclass=\"hub-panels__accordion-btn\"\n\t\t\t[class.hub-panels__accordion-btn--collapsed]=\"!active()\"\n\t\t\t[id]=\"id() + '-link'\"\n\t\t\t[disabled]=\"disabled() || tabset?.formDisabled()\"\n\t\t\t[attr.aria-expanded]=\"active()\"\n\t\t\t[attr.aria-controls]=\"id()\"\n\t\t\t(click)=\"onAccordionHeaderClick()\"\n\t\t\t(keydown)=\"onAccordionHeaderKeydown($event)\"\n\t\t>\n\t\t\t@if (headingRef(); as headingTemplate) {\n\t\t\t\t<ng-container [ngTemplateOutlet]=\"headingTemplate\" />\n\t\t\t} @else {\n\t\t\t\t{{ heading() }}\n\t\t\t}\n\t\t</button>\n\n\t\t<!-- Row affordances live OUTSIDE the disclosure button: a control nested\n\t\t\t in another control is invalid and unreachable by keyboard. They stay\n\t\t\t visible while the row is collapsed, unlike `hubPanelHeader`. The ✕\n\t\t\t remove control is a real button here for the same reason — focusable,\n\t\t\t keyboard operable and labelled for assistive technologies. -->\n\t\t@if (removable() || headingActionsRef()) {\n\t\t\t<span class=\"hub-panels__accordion-actions\">\n\t\t\t\t@if (headingActionsRef(); as actionsTemplate) {\n\t\t\t\t\t<ng-container [ngTemplateOutlet]=\"actionsTemplate\" />\n\t\t\t\t}\n\t\t\t\t@if (removable()) {\n\t\t\t\t\t<button\n\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\tclass=\"hub-panels__remove-btn\"\n\t\t\t\t\t\t[disabled]=\"disabled() || tabset?.formDisabled()\"\n\t\t\t\t\t\t[attr.aria-label]=\"removeLabel()\"\n\t\t\t\t\t\t(click)=\"removeSelf()\"\n\t\t\t\t\t>\n\t\t\t\t\t\t&times;\n\t\t\t\t\t</button>\n\t\t\t\t}\n\t\t\t</span>\n\t\t}\n\t</h2>\n}\n\n<!-- Projection slots for every view. In the strip views the wrappers are plain\n\t pass-throughs; in the accordion view they become the animated collapse\n\t region. The header/footer `select` slots and the default `<ng-content>` are\n\t all UNCONDITIONAL — never wrapped in `@if` — to avoid the lost-projection\n\t bug that conditional slots cause. Header/footer render in every view; the\n\t `card` view styles them as the card's header and footer bands. -->\n<div\n\tclass=\"hub-panels__panel-collapse\"\n\t[class.hub-panels__accordion-collapse]=\"accordionView()\"\n\t[class.hub-panels__accordion-collapse--collapsed]=\"accordionView() && !active()\"\n\t[attr.role]=\"accordionView() ? 'region' : null\"\n\t[attr.id]=\"accordionView() ? id() : null\"\n\t[attr.aria-labelledby]=\"accordionView() ? id() + '-link' : null\"\n\t[attr.aria-hidden]=\"accordionView() ? !active() : null\"\n\t[attr.inert]=\"accordionView() && !active() ? '' : null\"\n>\n\t<div class=\"hub-panels__panel-region\" [class.hub-panels__accordion-body]=\"accordionView()\">\n\t\t<ng-content select=\"[hubPanelHeader]\" />\n\t\t<div class=\"hub-panels__panel-body\">\n\t\t\t<ng-content />\n\t\t</div>\n\t\t<ng-content select=\"[hubPanelFooter]\" />\n\t</div>\n</div>\n","import { Directive, inject, TemplateRef } from '@angular/core';\n\nimport { HubPanelComponent } from '../components/panel/panel.component';\n\n/**\n * Marks an `<ng-template>` inside a `hub-panel` as that panel's custom header\n * (strip link in `tabs`/`pills` view, disclosure button in `accordion` view),\n * replacing the plain-text `heading` input.\n *\n * @example\n * ```html\n * <hub-panel>\n * <ng-template hubPanelHeading><em>Rich</em> heading</ng-template>\n * Panel content\n * </hub-panel>\n * ```\n */\n@Directive({ selector: '[hubPanelHeading]' })\nexport class HubPanelHeadingDirective {\n\tconstructor() {\n\t\tinject(HubPanelComponent).headingRef.set(inject(TemplateRef));\n\t}\n}\n","import { Directive, inject, TemplateRef } from '@angular/core';\n\nimport { HubPanelComponent } from '../components/panel/panel.component';\n\n/**\n * Marks an `<ng-template>` inside a `hub-panel` as that panel's header\n * **actions** slot, rendered in the `accordion` view as a sibling of the\n * disclosure button — inside the header row, outside the button.\n *\n * This is the slot for row affordances that must stay reachable while the\n * panel is collapsed (edit, delete, a menu). They cannot live in\n * `hubPanelHeading`, which projects *inside* the disclosure `<button>`: a\n * `<button>` nested in another button is invalid HTML and is not reachable\n * with the keyboard. Nor can they live in `hubPanelHeader`, which projects\n * inside the collapse region and therefore disappears when the row closes.\n *\n * Clicks on the actions never toggle the panel — the slot sits outside the\n * button, so no `stopPropagation` is needed. In the `tabs` / `pills` / `card`\n * views the slot renders nothing (those views have no header row of their own).\n *\n * @example\n * ```html\n * <hub-panels type=\"accordion\" multiple>\n * <hub-panel>\n * <ng-template hubPanelHeading>Shipping address</ng-template>\n * <ng-template hubPanelHeadingActions>\n * <button type=\"button\" (click)=\"edit()\">Edit</button>\n * <button type=\"button\" (click)=\"remove()\">Delete</button>\n * </ng-template>\n * Panel content\n * </hub-panel>\n * </hub-panels>\n * ```\n */\n@Directive({ selector: '[hubPanelHeadingActions]' })\nexport class HubPanelHeadingActionsDirective {\n\tconstructor() {\n\t\tinject(HubPanelComponent).headingActionsRef.set(inject(TemplateRef));\n\t}\n}\n","import { Directive } from '@angular/core';\n\n/**\n * Marks an element inside a `hub-panel` as the panel's content **header** band,\n * projected at the top of the panel body (above `<ng-content>`).\n *\n * Unlike `hubPanelHeading` — which renders the navigational label in the\n * `tabs`/`pills` strip or the `accordion` disclosure button — this header lives\n * inside the panel body and renders in **every** view (`tabs`, `pills`,\n * `accordion`, `card`). It is the natural title slot for the `card` format.\n *\n * @example\n * ```html\n * <hub-panel>\n * <div hubPanelHeader>Card title</div>\n * Card content\n * <div hubPanelFooter>Actions</div>\n * </hub-panel>\n * ```\n */\n@Directive({\n\tselector: '[hubPanelHeader]',\n\thost: { class: 'hub-panels__panel-header' }\n})\nexport class HubPanelHeaderDirective {}\n","import { Directive } from '@angular/core';\n\n/**\n * Marks an element inside a `hub-panel` as the panel's content **footer** band,\n * projected at the bottom of the panel body (below `<ng-content>`).\n *\n * Renders in **every** view (`tabs`, `pills`, `accordion`, `card`); it is the\n * natural actions/footer slot for the `card` format.\n *\n * @example\n * ```html\n * <hub-panel>\n * <div hubPanelHeader>Card title</div>\n * Card content\n * <div hubPanelFooter>Actions</div>\n * </hub-panel>\n * ```\n */\n@Directive({\n\tselector: '[hubPanelFooter]',\n\thost: { class: 'hub-panels__panel-footer' }\n})\nexport class HubPanelFooterDirective {}\n","import {\n\tbooleanAttribute,\n\tChangeDetectionStrategy,\n\tComponent,\n\tcomputed,\n\tElementRef,\n\tinject,\n\tinput,\n\tmodel,\n\tViewEncapsulation\n} from '@angular/core';\n\nimport type { HubTabNavAppearance, HubTabNavItem } from './tab-nav.types';\n\n/**\n * Lightweight, value-bound tab strip — the hub `tab-nav` primitive.\n *\n * Where `<hub-panels type=\"tabs\">` couples the strip to projected\n * `<hub-panel>` content (lazy render, accordion / card modes, routing, forms),\n * `<hub-tab-nav>` is a **content-less** controlled strip: it renders an\n * accessible `role=\"tablist\"` of `role=\"tab\"` buttons from a plain `items`\n * array and emits the selected `value` through the two-way `active` model. The\n * consumer owns the view and renders it themselves based on `active()` /\n * `(activeChange)` — a segmented control, a filter switch or a manual\n * tabs-with-external-content layout.\n *\n * It reuses the `<hub-panels>` strip look through the same\n * `--hub-panels-*` theming tokens (picked up automatically when nested in a\n * themed panels subtree, literal fallbacks otherwise) and exposes two\n * strip-local tokens: `--hub-tabs-indicator-color` (the active underline / pill\n * fill) and `--hub-tabs-gap` (the inter-tab gap).\n *\n * Keyboard: arrow keys move focus and activate the neighbour (roving\n * `tabindex`), `Home` / `End` jump to the first / last enabled tab. Disabled\n * tabs are skipped by pointer and keyboard.\n *\n * @example\n * ```html\n * <hub-tab-nav\n * \t[items]=\"[{ value: 'all', label: 'All' }, { value: 'open', label: 'Open' }]\"\n * \t[(active)]=\"filter\"\n * \tappearance=\"pills\"\n * />\n * <!-- consumer renders its own view based on `filter` -->\n * ```\n */\n@Component({\n\tselector: 'hub-tab-nav',\n\texportAs: 'hubTabNav',\n\ttemplateUrl: './tab-nav.component.html',\n\tstyleUrl: './tab-nav.component.scss',\n\t// Library-style global stylesheet: rules stay namespaced under\n\t// `.hub-tab-nav*` and reach the projected `<button>` headers.\n\tencapsulation: ViewEncapsulation.None,\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\thost: {\n\t\tclass: 'hub-tab-nav',\n\t\t'[class.hub-tab-nav--vertical]': 'vertical()'\n\t}\n})\nexport class HubTabNavComponent {\n\treadonly #host = inject<ElementRef<HTMLElement>>(ElementRef);\n\n\t/** The selectable tabs, in render order. */\n\treadonly items = input<HubTabNavItem[]>([]);\n\n\t/** Two-way selected value; `activeChange` fires whenever it changes. */\n\treadonly active = model<unknown>();\n\n\t/** Visual appearance — underlined `'tabs'` (default) or rounded `'pills'`. */\n\treadonly appearance = input<HubTabNavAppearance>('tabs');\n\n\t/** Whether the tabs stretch to share the available width equally. */\n\treadonly justified = input(false, { transform: booleanAttribute });\n\n\t/** Whether the strip stacks vertically instead of in a row. */\n\treadonly vertical = input(false, { transform: booleanAttribute });\n\n\t/** Index of the item whose value matches `active`, or `-1` when none does. */\n\treadonly activeIndex = computed(() => {\n\t\tconst active = this.active();\n\t\treturn this.items().findIndex((item) => item.value === active);\n\t});\n\n\t/** Whether the given item is the active one. */\n\tprotected isActive(item: HubTabNavItem): boolean {\n\t\treturn item.value === this.active();\n\t}\n\n\t/** ARIA id of a tab button — the item's own `id` or a deterministic fallback. */\n\tprotected itemId(item: HubTabNavItem, index: number): string {\n\t\treturn item.id ?? `hub-tab-nav-${index}`;\n\t}\n\n\t/**\n\t * Roving `tabindex` for the tab at `index`: `0` for the active tab (or the\n\t * first enabled tab when none is active), `-1` for the rest — so the strip\n\t * is a single tab stop and arrow keys move within it.\n\t */\n\tprotected tabIndexFor(index: number): number {\n\t\tconst activeIndex = this.activeIndex();\n\t\tif (activeIndex >= 0) {\n\t\t\treturn index === activeIndex ? 0 : -1;\n\t\t}\n\t\treturn index === this.items().findIndex((item) => !item.disabled) ? 0 : -1;\n\t}\n\n\t/**\n\t * Activates a tab on behalf of the user: sets `active` to its value (which\n\t * emits `activeChange`). Disabled tabs and re-selecting the active tab\n\t * no-op.\n\t */\n\tselect(item: HubTabNavItem): void {\n\t\tif (item.disabled || this.isActive(item)) {\n\t\t\treturn;\n\t\t}\n\t\tthis.active.set(item.value);\n\t}\n\n\t/** Keyboard navigation for the strip (arrows / Home / End). */\n\tprotected onKeydown(event: KeyboardEvent, index: number): void {\n\t\tlet target: number;\n\t\tswitch (event.key) {\n\t\t\tcase 'ArrowRight':\n\t\t\tcase 'ArrowDown':\n\t\t\t\ttarget = this.#stepEnabledIndex(index, 1);\n\t\t\t\tbreak;\n\t\t\tcase 'ArrowLeft':\n\t\t\tcase 'ArrowUp':\n\t\t\t\ttarget = this.#stepEnabledIndex(index, -1);\n\t\t\t\tbreak;\n\t\t\tcase 'Home':\n\t\t\t\ttarget = this.items().findIndex((item) => !item.disabled);\n\t\t\t\tbreak;\n\t\t\tcase 'End': {\n\t\t\t\tconst items = this.items();\n\t\t\t\ttarget = items.length - 1 - [...items].reverse().findIndex((item) => !item.disabled);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tdefault:\n\t\t\t\treturn;\n\t\t}\n\t\tif (target < 0) {\n\t\t\treturn;\n\t\t}\n\t\tevent.preventDefault();\n\t\tconst item = this.items()[target];\n\t\tif (item && !item.disabled) {\n\t\t\tthis.active.set(item.value);\n\t\t\tthis.#focusAt(target);\n\t\t}\n\t}\n\n\t/** Next enabled tab index from `index` in `direction`, wrapping around. */\n\t#stepEnabledIndex(index: number, direction: 1 | -1): number {\n\t\tconst items = this.items();\n\t\tconst count = items.length;\n\t\tif (!count) {\n\t\t\treturn -1;\n\t\t}\n\t\tfor (let step = 1; step <= count; step += 1) {\n\t\t\tconst candidate = (((index + direction * step) % count) + count) % count;\n\t\t\tif (!items[candidate].disabled) {\n\t\t\t\treturn candidate;\n\t\t\t}\n\t\t}\n\t\treturn index;\n\t}\n\n\t/** Moves DOM focus to the tab button at `index`. */\n\t#focusAt(index: number): void {\n\t\tconst buttons = this.#host.nativeElement.querySelectorAll<HTMLElement>('.hub-tab-nav__nav-link');\n\t\tbuttons[index]?.focus();\n\t}\n}\n","<ul\n\tclass=\"hub-tab-nav__nav\"\n\trole=\"tablist\"\n\t[attr.aria-orientation]=\"vertical() ? 'vertical' : 'horizontal'\"\n\t[class.hub-tab-nav__nav--tabs]=\"appearance() === 'tabs'\"\n\t[class.hub-tab-nav__nav--pills]=\"appearance() === 'pills'\"\n\t[class.hub-tab-nav__nav--vertical]=\"vertical()\"\n\t[class.hub-tab-nav__nav--justified]=\"justified()\"\n>\n\t@for (item of items(); track item.value; let i = $index) {\n\t\t<li\n\t\t\tclass=\"hub-tab-nav__nav-item\"\n\t\t\t[class.hub-tab-nav__nav-item--active]=\"isActive(item)\"\n\t\t\t[class.hub-tab-nav__nav-item--disabled]=\"!!item.disabled\"\n\t\t>\n\t\t\t<button\n\t\t\t\ttype=\"button\"\n\t\t\t\tclass=\"hub-tab-nav__nav-link\"\n\t\t\t\trole=\"tab\"\n\t\t\t\t[id]=\"itemId(item, i)\"\n\t\t\t\t[class.hub-tab-nav__nav-link--active]=\"isActive(item)\"\n\t\t\t\t[class.hub-tab-nav__nav-link--disabled]=\"!!item.disabled\"\n\t\t\t\t[disabled]=\"!!item.disabled\"\n\t\t\t\t[attr.aria-selected]=\"isActive(item)\"\n\t\t\t\t[attr.tabindex]=\"tabIndexFor(i)\"\n\t\t\t\t(click)=\"select(item)\"\n\t\t\t\t(keydown)=\"onKeydown($event, i)\"\n\t\t\t>\n\t\t\t\t{{ item.label }}\n\t\t\t</button>\n\t\t</li>\n\t}\n</ul>\n","import { afterNextRender, ChangeDetectionStrategy, Component, DestroyRef, ElementRef, inject, signal } from '@angular/core';\n\n/**\n * Layout parent of one or more `<hub-side-panel>` elements.\n *\n * A docked (`side`) panel can only narrow the content if something lays the two out together, so\n * the container is a flex row that holds the page content in its own scrolling area and the\n * panels as direct children. It also measures its own inline size, which is what a panel compares\n * with its `breakpoint` to decide whether it still has room to dock or has to float over the\n * content instead. Measuring the container rather than the viewport keeps that decision right when\n * the container is not full width (a shell with a navigation rail, an embedded demo).\n *\n * A panel declared with a static `position=\"start\"` attribute is projected before the content and\n * every other panel after it, so the DOM order (and therefore the tab order) follows the visual\n * order in the common case. A panel whose `position` is bound is projected after the content and\n * placed visually by CSS `order`.\n *\n * Give the container a block size (`height: 100dvh` in an app shell, a fixed height in a card):\n * the content area scrolls inside it, and an `over` panel spans the container's full height.\n *\n * @example\n * ```html\n * <hub-side-panel-container class=\"app-shell\">\n * \t<main>…the page…</main>\n * \t<hub-side-panel [(open)]=\"assistantOpen\" ariaLabel=\"Assistant\">…</hub-side-panel>\n * </hub-side-panel-container>\n * ```\n */\n@Component({\n\tselector: 'hub-side-panel-container',\n\texportAs: 'hubSidePanelContainer',\n\ttemplateUrl: './side-panel-container.component.html',\n\tstyleUrl: './side-panel-container.component.scss',\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\thost: {\n\t\tclass: 'hub-side-panel-container'\n\t}\n})\nexport class HubSidePanelContainerComponent {\n\treadonly #inlineSize = signal<number | null>(null);\n\n\t/**\n\t * Measured inline size of the container in CSS pixels, or `null` before the first measurement\n\t * and wherever `ResizeObserver` does not exist (server rendering). Panels read it to apply their\n\t * `breakpoint`; `null` means \"assume there is room\", so the server renders the requested mode.\n\t */\n\treadonly inlineSize = this.#inlineSize.asReadonly();\n\n\tconstructor() {\n\t\tconst host = inject<ElementRef<HTMLElement>>(ElementRef).nativeElement;\n\t\tconst destroyRef = inject(DestroyRef);\n\n\t\tafterNextRender(() => {\n\t\t\tif (typeof ResizeObserver === 'undefined') {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t// `borderBoxSize` is logical, so the value stays the inline size in vertical writing\n\t\t\t// modes too; `contentRect.width` is only the fallback for engines that lack it.\n\t\t\tconst observer = new ResizeObserver(([entry]) => {\n\t\t\t\tthis.#inlineSize.set(entry.borderBoxSize?.[0]?.inlineSize ?? entry.contentRect.width);\n\t\t\t});\n\t\t\tobserver.observe(host);\n\t\t\tdestroyRef.onDestroy(() => observer.disconnect());\n\t\t});\n\t}\n}\n","<ng-content select=\"hub-side-panel[position=start]\" />\n<div class=\"hub-side-panel-container__content\"><ng-content /></div>\n<ng-content select=\"hub-side-panel\" />\n","import {\n\tafterNextRender,\n\tbooleanAttribute,\n\tChangeDetectionStrategy,\n\tComponent,\n\tcomputed,\n\tDOCUMENT,\n\teffect,\n\tElementRef,\n\tinject,\n\tInjector,\n\tinput,\n\tmodel,\n\tnumberAttribute,\n\tuntracked\n} from '@angular/core';\n\nimport { HubSidePanelContainerComponent } from './side-panel-container.component';\nimport type { HubSidePanelMode, HubSidePanelPosition, HubSidePanelRole } from './side-panel.types';\n\n/** Elements that can take keyboard focus, in the order a first-focus search should try them. */\nconst TABBABLE =\n\t'a[href], button:not([disabled]), input:not([disabled]):not([type=\"hidden\"]), select:not([disabled]), ' +\n\t'textarea:not([disabled]), [contenteditable=\"true\"], [tabindex]:not([tabindex=\"-1\"])';\n\n/**\n * Non-modal panel docked to one inline edge of a `<hub-side-panel-container>`.\n *\n * `ng-hub-ui-modal` in offcanvas mode is a real dialog: it covers the viewport, locks the body\n * scroll and traps focus, which is right for a task that must be finished before the page is\n * used again and wrong for a companion that lives beside the page (an assistant, an inspector, a\n * detail pane). This panel is that companion: no backdrop, no scroll lock, no focus trap and no\n * `aria-modal`, so the page stays usable while it is open.\n *\n * - `mode=\"side\"` takes its width from the container row, and the content narrows to make room.\n * Below `breakpoint` (measured on the container) it falls back to `over`, because a docked panel\n * on a phone would leave the content a sliver.\n * - `mode=\"over\"` floats over the content edge. Only the strip the panel covers is unusable.\n *\n * Both modes animate the same property: a closed panel keeps its width and sits just beyond the\n * container edge through a negative logical margin, and opening animates that margin to zero. In\n * the docked row that one transition slides the panel in and narrows the content in the same\n * frames; for the floating panel it is a slide. Logical margins keep it right under `dir=\"rtl\"`\n * without a physical transform. `prefers-reduced-motion` turns the transition off.\n *\n * **Content is never destroyed by closing.** Projected content belongs to the consumer's view and\n * lives as long as the `<hub-side-panel>` element does; closing hides it (`visibility: hidden`\n * once the slide ends, and `inert` straight away, so nothing inside can be focused or read while\n * it is shut) and opening shows the same instances again. A chat keeps its thread and its draft.\n * A consumer who wants the content torn down on close wraps it in `@if (panel.open())`.\n *\n * Focus: nothing moves on open unless `autoFocus` is set, in which case the first `[autofocus]`\n * element, else the first tabbable element, else the panel itself takes it. On close, if focus was\n * inside the panel, it goes back to the element that had it when the panel opened, so closing\n * from inside (Escape, a close button) never drops the reader on `<body>`.\n *\n * @example\n * ```html\n * <hub-side-panel-container style=\"height: 100dvh\">\n * \t<main>…the page…</main>\n *\n * \t<hub-side-panel #assistant [(open)]=\"assistantOpen\" ariaLabel=\"Assistant\" autoFocus>\n * \t\t<header hubSidePanelHeader>\n * \t\t\tAssistant <button type=\"button\" (click)=\"assistant.close()\">Close</button>\n * \t\t</header>\n * \t\t<app-chat-thread />\n * \t\t<footer hubSidePanelFooter><textarea autofocus></textarea></footer>\n * \t</hub-side-panel>\n * </hub-side-panel-container>\n * ```\n */\n@Component({\n\tselector: 'hub-side-panel',\n\texportAs: 'hubSidePanel',\n\ttemplateUrl: './side-panel.component.html',\n\tstyleUrl: './side-panel.component.scss',\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\thost: {\n\t\tclass: 'hub-side-panel',\n\t\ttabindex: '-1',\n\t\t'[attr.role]': 'role()',\n\t\t'[attr.aria-label]': 'ariaLabel() || null',\n\t\t'[attr.aria-labelledby]': 'ariaLabelledBy() || null',\n\t\t'[attr.inert]': \"open() ? null : ''\",\n\t\t'[class.hub-side-panel--open]': 'open()',\n\t\t'[class.hub-side-panel--side]': \"effectiveMode() === 'side'\",\n\t\t'[class.hub-side-panel--over]': \"effectiveMode() === 'over'\",\n\t\t'[class.hub-side-panel--start]': \"position() === 'start'\",\n\t\t'[class.hub-side-panel--end]': \"position() === 'end'\",\n\t\t'(keydown.escape)': 'onEscape($event)'\n\t}\n})\nexport class HubSidePanelComponent {\n\treadonly #host = inject<ElementRef<HTMLElement>>(ElementRef);\n\treadonly #document = inject(DOCUMENT);\n\treadonly #injector = inject(Injector);\n\treadonly #container = inject(HubSidePanelContainerComponent, { optional: true });\n\n\t/** Element that held focus when the panel last opened, where focus returns on close. */\n\t#returnFocusTo: HTMLElement | null = null;\n\n\t/** Docked beside the content (`'side'`) or floating over its edge (`'over'`). */\n\treadonly mode = input<HubSidePanelMode>('side');\n\n\t/** Inline edge of the container the panel sits on; logical, so `'end'` is the left edge in RTL. */\n\treadonly position = input<HubSidePanelPosition>('end');\n\n\t/** Two-way open state; `openChange` fires whenever it changes, whoever changed it. */\n\treadonly open = model(false);\n\n\t/** Whether Escape pressed inside the panel closes it. Escape pressed elsewhere is never taken. */\n\treadonly closeOnEscape = input(true, { transform: booleanAttribute });\n\n\t/**\n\t * Container inline size in CSS pixels below which a `side` panel renders as `over`. The default\n\t * matches `--hub-sys-breakpoint-md`. `0` keeps the panel docked at any width.\n\t */\n\treadonly breakpoint = input(768, { transform: numberAttribute });\n\n\t/** Whether opening moves focus into the panel. Off by default: a companion should not steal focus. */\n\treadonly autoFocus = input(false, { transform: booleanAttribute });\n\n\t/** Landmark role; use `'region'` when the panel sits inside the page's `<main>`. */\n\treadonly role = input<HubSidePanelRole>('complementary');\n\n\t/** Accessible name of the landmark. Give it this or `ariaLabelledBy`: an unnamed landmark is noise. */\n\treadonly ariaLabel = input<string>();\n\n\t/** Id of the element that names the landmark, typically the heading in the header slot. */\n\treadonly ariaLabelledBy = input<string>();\n\n\t/**\n\t * The mode actually rendered: `mode`, except that a `side` panel whose container is narrower\n\t * than `breakpoint` floats instead. Outside a container, or before the container has measured\n\t * itself, the requested mode is used.\n\t */\n\treadonly effectiveMode = computed<HubSidePanelMode>(() => {\n\t\tif (this.mode() === 'over') {\n\t\t\treturn 'over';\n\t\t}\n\t\tconst inlineSize = this.#container?.inlineSize();\n\t\tconst breakpoint = this.breakpoint();\n\t\treturn inlineSize != null && breakpoint > 0 && inlineSize < breakpoint ? 'over' : 'side';\n\t});\n\n\tconstructor() {\n\t\t// Focus handling reacts to transitions of `open`, not to its value: the first run only\n\t\t// records the initial state, so a panel rendered open never grabs focus on page load.\n\t\tlet previous: boolean | undefined;\n\t\teffect(() => {\n\t\t\tconst open = this.open();\n\t\t\tuntracked(() => {\n\t\t\t\tif (previous !== undefined && previous !== open) {\n\t\t\t\t\tif (open) {\n\t\t\t\t\t\tthis.#onOpened();\n\t\t\t\t\t} else {\n\t\t\t\t\t\tthis.#onClosed();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tprevious = open;\n\t\t\t});\n\t\t});\n\t}\n\n\t/**\n\t * Opens or closes the panel.\n\t *\n\t * @param force - `true` to open, `false` to close; omitted, the state flips.\n\t */\n\ttoggle(force?: boolean): void {\n\t\tthis.open.set(force ?? !this.open());\n\t}\n\n\t/** Closes the panel. Focus, if it was inside, returns to where it was before the panel opened. */\n\tclose(): void {\n\t\tthis.open.set(false);\n\t}\n\n\t/**\n\t * Closes on Escape. A handler inside the panel that already consumed the key (a select closing\n\t * its list calls `preventDefault()`) keeps the panel open; the key is marked consumed here in\n\t * turn, so an ancestor listening for Escape does not close as well.\n\t */\n\tprotected onEscape(event: Event): void {\n\t\tif (!this.open() || !this.closeOnEscape() || event.defaultPrevented) {\n\t\t\treturn;\n\t\t}\n\t\tevent.preventDefault();\n\t\tthis.close();\n\t}\n\n\t/** Remembers where focus was, and moves it inside once the open state has rendered. */\n\t#onOpened(): void {\n\t\tconst active = this.#document.activeElement as HTMLElement | null;\n\t\tthis.#returnFocusTo =\n\t\t\tactive && active !== this.#document.body && !this.#host.nativeElement.contains(active) ? active : null;\n\n\t\tif (this.autoFocus()) {\n\t\t\t// After render, not now: the host is still `inert` until the open state reaches the DOM.\n\t\t\tafterNextRender(() => this.#focusInitial(), { injector: this.#injector });\n\t\t}\n\t}\n\n\t/**\n\t * Hands focus back when it was inside the panel. Checked now, while the element that has focus\n\t * is still inside: once `inert` lands the browser blurs it to `<body>`.\n\t */\n\t#onClosed(): void {\n\t\tconst target = this.#returnFocusTo;\n\t\tthis.#returnFocusTo = null;\n\n\t\tconst active = this.#document.activeElement;\n\t\tif (active && this.#host.nativeElement.contains(active) && target?.isConnected) {\n\t\t\ttarget.focus();\n\t\t}\n\t}\n\n\t/**\n\t * Focuses the first `[autofocus]` element, else the first tabbable one, else the panel. The\n\t * scroll is prevented because the container clips a panel that is still sliding in, and a\n\t * focus-driven scroll would shift the whole row sideways.\n\t */\n\t#focusInitial(): void {\n\t\tif (!this.open()) {\n\t\t\treturn;\n\t\t}\n\t\tconst host = this.#host.nativeElement;\n\t\tconst target = host.querySelector<HTMLElement>('[autofocus]') ?? host.querySelector<HTMLElement>(TABBABLE) ?? host;\n\t\ttarget.focus({ preventScroll: true });\n\t}\n}\n","<div class=\"hub-side-panel__header\"><ng-content select=\"[hubSidePanelHeader]\" /></div>\n<div class=\"hub-side-panel__body\"><ng-content /></div>\n<div class=\"hub-side-panel__footer\"><ng-content select=\"[hubSidePanelFooter]\" /></div>\n","/*\n * Public API Surface of ng-hub-ui-panels\n */\n\nexport { HubPanelHeadingDirective } from './lib/directives/panel-heading.directive';\nexport { HubPanelHeadingActionsDirective } from './lib/directives/panel-heading-actions.directive';\nexport { HubPanelHeaderDirective } from './lib/directives/panel-header.directive';\nexport { HubPanelFooterDirective } from './lib/directives/panel-footer.directive';\nexport { HubPanelComponent } from './lib/components/panel/panel.component';\nexport { HubPanelsComponent } from './lib/components/panels/panels.component';\nexport { HubTabNavComponent } from './lib/components/tab-nav/tab-nav.component';\nexport { HubSidePanelContainerComponent } from './lib/components/side-panel/side-panel-container.component';\nexport { HubSidePanelComponent } from './lib/components/side-panel/side-panel.component';\nexport { HubPanelsConfig } from './lib/services/panels-config.service';\nexport type {\n\tHubPanelAppearance,\n\tHubPanelsTogglePosition,\n\tHubPanelVariant,\n\tPanelChangeEvent,\n\tPanelsType\n} from './lib/models/panels.types';\nexport type { HubTabNavAppearance, HubTabNavItem } from './lib/components/tab-nav/tab-nav.types';\nexport type { HubSidePanelMode, HubSidePanelPosition, HubSidePanelRole } from './lib/components/side-panel/side-panel.types';\n\n// ─── Deprecated aliases ───────────────────────────────────────────────────────\n// Every class in the family carries the `Hub` prefix, so a consumer importing several\n// packages into one file cannot end up with two `PanelComponent`s. The classes behind\n// these aliases are unchanged; only the exported names move.\n\n/** @deprecated Renamed to `HubPanelHeadingDirective`, and removed under this name in **23.0.0**. */\nexport { HubPanelHeadingDirective as PanelHeadingDirective } from './lib/directives/panel-heading.directive';\n/** @deprecated Renamed to `HubPanelHeadingActionsDirective`, and removed under this name in **23.0.0**. */\nexport { HubPanelHeadingActionsDirective as PanelHeadingActionsDirective } from './lib/directives/panel-heading-actions.directive';\n/** @deprecated Renamed to `HubPanelHeaderDirective`, and removed under this name in **23.0.0**. */\nexport { HubPanelHeaderDirective as PanelHeaderDirective } from './lib/directives/panel-header.directive';\n/** @deprecated Renamed to `HubPanelFooterDirective`, and removed under this name in **23.0.0**. */\nexport { HubPanelFooterDirective as PanelFooterDirective } from './lib/directives/panel-footer.directive';\n/** @deprecated Renamed to `HubPanelComponent`, and removed under this name in **23.0.0**. */\nexport { HubPanelComponent as PanelComponent } from './lib/components/panel/panel.component';\n/** @deprecated Renamed to `HubPanelsComponent`, and removed under this name in **23.0.0**. */\nexport { HubPanelsComponent as PanelsComponent } from './lib/components/panels/panels.component';\n/** @deprecated Renamed to `HubPanelsConfig`, and removed under this name in **23.0.0**. */\nexport { HubPanelsConfig as PanelsConfig } from './lib/services/panels-config.service';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"ng-hub-ui-panels.mjs","sources":["../../../projects/panels/src/lib/services/panels-config.service.ts","../../../projects/panels/src/lib/utils/content-box-width.ts","../../../projects/panels/src/lib/utils/read-by-path.ts","../../../projects/panels/src/lib/components/panel/panel.token.ts","../../../projects/panels/src/lib/components/panels/panels.component.ts","../../../projects/panels/src/lib/components/panels/panels.component.html","../../../projects/panels/src/lib/components/panel/panel.component.ts","../../../projects/panels/src/lib/components/panel/panel.component.html","../../../projects/panels/src/lib/directives/panel-heading.directive.ts","../../../projects/panels/src/lib/directives/panel-heading-actions.directive.ts","../../../projects/panels/src/lib/directives/panel-header.directive.ts","../../../projects/panels/src/lib/directives/panel-footer.directive.ts","../../../projects/panels/src/lib/components/tab-nav/tab-nav.component.ts","../../../projects/panels/src/lib/components/tab-nav/tab-nav.component.html","../../../projects/panels/src/lib/components/side-panel/side-panel-container.component.ts","../../../projects/panels/src/lib/components/side-panel/side-panel-container.component.html","../../../projects/panels/src/lib/components/side-panel/side-panel.component.ts","../../../projects/panels/src/lib/components/side-panel/side-panel.component.html","../../../projects/panels/src/public-api.ts","../../../projects/panels/src/ng-hub-ui-panels.ts"],"sourcesContent":["import { Injectable } from '@angular/core';\n\nimport type { HubPanelsTogglePosition, PanelsType } from '../models/panels.types';\n\n/**\n * Injectable defaults for every `<hub-panels>` in the application.\n *\n * Override at any injector level to change the defaults globally or for a\n * feature subtree:\n *\n * ```ts\n * providers: [{ provide: HubPanelsConfig, useValue: { ...new HubPanelsConfig(), type: 'pills' } }]\n * ```\n */\n@Injectable({ providedIn: 'root' })\nexport class HubPanelsConfig {\n\t/** Default navigation style — `'tabs'`, `'pills'` or `'accordion'`. */\n\ttype: PanelsType = 'tabs';\n\n\t/** Whether keyboard navigation (arrows / Home / End / Delete) is enabled. */\n\tisKeysAllowed = true;\n\n\t/** Accordion view: default side of the header row for the disclosure chevron. */\n\ttogglePosition: HubPanelsTogglePosition = 'end';\n\n\t/** Accessible label announced for the panel list. */\n\tariaLabel = 'Tabs';\n\n\t/** Accessible label for the backward scroll button (scrollable mode). */\n\tscrollBackwardAriaLabel = 'Scroll tabs backward';\n\n\t/** Accessible label for the forward scroll button (scrollable mode). */\n\tscrollForwardAriaLabel = 'Scroll tabs forward';\n}\n","/**\n * Usable inner width of an element: `offsetWidth` minus horizontal paddings\n * and borders. Used by the scrollable strip to size its scroll steps.\n */\nexport function contentBoxWidth(element: HTMLElement): number {\n\tconst style = getComputedStyle(element);\n\treturn (\n\t\telement.offsetWidth -\n\t\tparseFloat(style.paddingLeft) -\n\t\tparseFloat(style.paddingRight) -\n\t\tparseFloat(style.borderLeftWidth) -\n\t\tparseFloat(style.borderRightWidth)\n\t);\n}\n","/**\n * Reads a nested value from an object using dot-notation path syntax\n * (e.g. `id`, `meta.key`). Returns `undefined` when the path cannot be\n * resolved. Used by the panels' `bindValue` form-value mapping.\n */\nexport function readByPath(source: unknown, path: string): unknown {\n\tif (source == null || !path) {\n\t\treturn undefined;\n\t}\n\treturn path.split('.').reduce((currentValue: unknown, segment) => {\n\t\tif (currentValue == null) {\n\t\t\treturn undefined;\n\t\t}\n\t\treturn (currentValue as Record<string, unknown>)[segment];\n\t}, source);\n}\n","import { InjectionToken } from '@angular/core';\n\nimport type { HubPanelComponent } from './panel.component';\n\n/**\n * Stands in for `HubPanelComponent` where importing the class would close a cycle.\n *\n * The panel injects its container and the container queries its panels, so one of the two\n * directions has to be type-only. This token is that direction: the panel provides itself under\n * it, and the container queries the token.\n */\nexport const HUB_PANEL = new InjectionToken<HubPanelComponent>('HUB_PANEL');\n","import { NgTemplateOutlet } from '@angular/common';\nimport {\n\tcontentChildren,\n\tafterNextRender,\n\tbooleanAttribute,\n\tChangeDetectionStrategy,\n\tComponent,\n\tcomputed,\n\tDestroyRef,\n\tElementRef,\n\tforwardRef,\n\tinject,\n\tinput,\n\toutput,\n\tRenderer2,\n\tRendererStyleFlags2,\n\tsignal,\n\tviewChild,\n\tviewChildren,\n\tViewEncapsulation\n} from '@angular/core';\nimport { takeUntilDestroyed } from '@angular/core/rxjs-interop';\nimport { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms';\nimport { NavigationEnd, Router, RouterOutlet } from '@angular/router';\nimport { filter } from 'rxjs';\n\nimport type { HubPanelsTogglePosition, HubPanelVariant, PanelChangeEvent, PanelsType } from '../../models/panels.types';\nimport { HubPanelsConfig } from '../../services/panels-config.service';\nimport { contentBoxWidth } from '../../utils/content-box-width';\nimport { readByPath } from '../../utils/read-by-path';\nimport { resolveHubAccent } from 'ng-hub-ui-utils';\nimport type { HubPanelComponent } from '../panel/panel.component';\n\ninterface MultipleHeaderGroup {\n\tactivePanel?: HubPanelComponent;\n\theaders: HubPanelComponent[];\n}\n\n/**\n * Content-panels container — the hub `panels` primitive.\n *\n * Projects `<hub-panel>` panes and renders them in one of three views:\n *\n * - **`tabs` / `pills`** — an accessible `tablist` of clickable headers\n * (roving tabindex, arrow/Home/End/Delete keys) above the active pane.\n * Panels with a `routerLink` switch the content area to a `<router-outlet>`\n * and the active panel follows the URL. With `scrollable`, overflowing\n * headers get backward/forward scroll buttons.\n * - **`accordion`** — each panel renders as a stacked disclosure panel with an\n * animated collapse: clicking an open header closes it, `multiple` allows\n * several panels open at once and `flush` removes the outer chrome. All\n * panels start collapsed unless a panel is marked `[active]` or a form value\n * is bound. Routed panels are not supported in this view.\n *\n * The container implements `ControlValueAccessor`, so the active panel(s) can\n * be bound as a form value (`ngModel` / `formControl`): each panel contributes\n * its `value` (or its `id` by default), optionally narrowed with `bindValue`\n * and compared with `compareWith`. With `multiple` the form value is an array.\n *\n * Theming is driven entirely by the `--hub-panels-*` CSS custom properties\n * (see `panels.variables.scss`); the accordion view also honours the\n * `--hub-accordion-*` ng-hub-ui contract as a compatibility fallback.\n *\n * @example\n * ```html\n * <hub-panels type=\"accordion\" multiple [formControl]=\"openPanels\">\n * <hub-panel heading=\"Fields\" value=\"fields\">…</hub-panel>\n * <hub-panel heading=\"Validations\" value=\"validations\">…</hub-panel>\n * </hub-panels>\n * ```\n */\nimport { HUB_PANEL } from '../panel/panel.token';\n\n@Component({\n\tselector: 'hub-panels',\n\timports: [NgTemplateOutlet, RouterOutlet],\n\ttemplateUrl: './panels.component.html',\n\t// Split by concern (token contract / strip views / accordion view) so each\n\t// sheet stays inside the `anyComponentStyle` budget.\n\tstyleUrls: ['./panels.variables.scss', './panels.component.scss', './panels.accordion.scss'],\n\t// Library-style global stylesheet: rules are namespaced under `.hub-panels*`\n\t// and must reach the projected `hub-panel` panes (host-bound classes).\n\tencapsulation: ViewEncapsulation.None,\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\tproviders: [\n\t\t{\n\t\t\tprovide: NG_VALUE_ACCESSOR,\n\t\t\tuseExisting: forwardRef(() => HubPanelsComponent),\n\t\t\tmulti: true\n\t\t}\n\t],\n\thost: {\n\t\tclass: 'hub-panels',\n\t\t'[class.hub-panels--tabs]': \"type() === 'tabs'\",\n\t\t'[class.hub-panels--pills]': \"type() === 'pills'\",\n\t\t'[class.hub-panels--card]': 'isCardView()',\n\t\t'[class.hub-panels--vertical]': 'vertical() && !isAccordionView() && !isCardView()',\n\t\t'[class.hub-panels--accordion]': 'isAccordionView()',\n\t\t'[class.hub-panels--toggle-start]': \"isAccordionView() && togglePosition() === 'start'\",\n\t\t'[class.hub-panels--flush]': 'isAccordionView() && flush()',\n\t\t'[class.hub-panels--multiple]': 'multiple()',\n\t\t'[attr.data-variant]': 'variant() ?? null',\n\t\t'[style.--hub-panels-accent]': 'groupAccent()',\n\t\t'(window:resize)': 'onWindowResize()'\n\t}\n})\nexport class HubPanelsComponent implements ControlValueAccessor {\n\treadonly #router = inject(Router);\n\treadonly #renderer = inject(Renderer2);\n\treadonly #elementRef = inject<ElementRef<HTMLElement>>(ElementRef);\n\treadonly #destroyRef = inject(DestroyRef);\n\n\t/** Container-wide defaults (aria labels, default type, keyboard toggle). */\n\tprotected readonly config = inject(HubPanelsConfig);\n\n\t/** Scrollable container hosting the panel headers (`tabs` / `pills` views). */\n\treadonly navScroller = viewChild<ElementRef<HTMLElement>>('navScroller');\n\n\t/** Backward scroll button (only rendered while it can scroll back). */\n\treadonly prevBtn = viewChild<ElementRef<HTMLElement>>('prevBtn');\n\n\t/** Forward scroll button (only rendered while it can scroll forward). */\n\treadonly nextBtn = viewChild<ElementRef<HTMLElement>>('nextBtn');\n\n\t/** Parking lot that owns the projected panel hosts before they are placed. */\n\treadonly contentRoot = viewChild<ElementRef<HTMLElement>>('contentRoot');\n\n\t/** Visible block hosts used by `multiple` tabs / pills. */\n\treadonly multiplePaneHosts = viewChildren<ElementRef<HTMLElement>>('multiplePaneHost');\n\n\t/** Visible grouped blocks used by `multiple` tabs / pills. */\n\treadonly multipleBlocks = viewChildren<ElementRef<HTMLElement>>('multipleBlock');\n\n\t/** Emitted when the user activates (opens) a different panel. */\n\treadonly panelChange = output<PanelChangeEvent>();\n\n\t/** Whether the panel list is stacked beside the content (`tabs` / `pills`). */\n\treadonly vertical = input(false, { transform: booleanAttribute });\n\n\t/** Whether panel headers stretch to share the available width equally. */\n\treadonly justified = input(false, { transform: booleanAttribute });\n\n\t/** Visualization — `'tabs'` (default), `'pills'` or `'accordion'`. */\n\treadonly type = input<PanelsType>(this.config.type);\n\n\t/** Whether keyboard navigation is enabled. */\n\treadonly isKeysAllowed = input(this.config.isKeysAllowed, {\n\t\ttransform: booleanAttribute\n\t});\n\n\t/** Whether overflowing headers get backward/forward scroll buttons. */\n\treadonly scrollable = input(false, { transform: booleanAttribute });\n\n\t/** Accordion view: whether several panels may be expanded at once. */\n\treadonly multiple = input(false, { transform: booleanAttribute });\n\n\t/** Accordion view: edge-to-edge panels without outer borders or radius. */\n\treadonly flush = input(false, { transform: booleanAttribute });\n\n\t/**\n\t * Accordion view: which side of the header row the disclosure chevron sits\n\t * on — `'end'` (default) trails the heading, `'start'` leads it. Purely\n\t * visual: the DOM order never changes, and the placement is expressed with\n\t * logical properties, so it mirrors automatically under `dir=\"rtl\"`.\n\t */\n\treadonly togglePosition = input<HubPanelsTogglePosition>(this.config.togglePosition);\n\n\t/**\n\t * Semantic accent applied to the navigation strip — the active/hover tab, the\n\t * active pill and the active accordion header all follow it. The built-in\n\t * values (`primary` / `success` / `danger` / `warning` / `info`) render with\n\t * the design-system tints; any other string is also accepted, since the strip\n\t * reads `--hub-sys-color-<variant>` from the host application, so a custom\n\t * accent palette interconnects with no changes to this library. Defaults to\n\t * `primary` when omitted.\n\t */\n\treadonly variant = input<HubPanelVariant | (string & {}) | undefined>(undefined);\n\n\t/**\n\t * Dot-notation path applied to each panel's `value` to obtain the emitted\n\t * form value (e.g. `'meta.key'`). Empty by default — the raw value is used.\n\t */\n\treadonly bindValue = input<string | undefined>(undefined);\n\n\t/** Equality used to match form values against panel values. `===` by default. */\n\treadonly compareWith = input<(a: unknown, b: unknown) => boolean>((a, b) => a === b);\n\n\t/**\n\t * Panels projected into this container, in the order the consumer wrote them.\n\t *\n\t * A content query rather than self-registration, because a panel adding itself from its own\n\t * constructor is never seen when it is created inside a control-flow block: an `@if` that turns\n\t * true produced a pane in the DOM and no tab at all. The query also fixes the order for free —\n\t * registration order is creation order, which a conditional panel breaks the moment its\n\t * condition flips.\n\t *\n\t * The boundary is exactly right: content children reach through `@if` and `@for` in the\n\t * consumer's template, and stop at another component's own view, so a panel nested inside a\n\t * component projected into a pane is still not captured as a hidden tab.\n\t */\n\tprotected readonly projectedPanels = contentChildren(HUB_PANEL, { descendants: true });\n\n\t/**\n\t * Panels a consumer removed through the strip's own close button. Removal is an action, not a\n\t * shape the template describes, so it cannot come from the query: the panel is still written in\n\t * the consumer's template and the query keeps returning it.\n\t */\n\treadonly #removedPanels = signal<ReadonlySet<HubPanelComponent>>(new Set());\n\n\t/** Panels the strip presents, in the order the consumer wrote them. */\n\treadonly panels = computed(() =>\n\t\tthis.projectedPanels().filter((panel) => !panel.standalone && !this.#removedPanels().has(panel))\n\t);\n\n\t/** Currently active panel, if any (the first one, under `multiple`). */\n\treadonly activePanel = computed(() => this.panels().find((panel) => panel.active()));\n\n\t/** Panel index lookup used by the strip templates and keyboard navigation. */\n\treadonly panelIndexMap = computed(() => new Map(this.panels().map((panel, index) => [panel, index])));\n\n\t/** Whether the container renders the accordion visualization. */\n\treadonly isAccordionView = computed(() => this.type() === 'accordion');\n\n\t/**\n\t * Whether the container renders the chromeless `card` visualization: no\n\t * navigation strip and every panel always visible, each styled as a card.\n\t */\n\treadonly isCardView = computed(() => this.type() === 'card');\n\n\t/**\n\t * Inline accent fed to the strip styles, resolved from the `variant` input so\n\t * ANY colour works. A bareword (a semantic name, a registered accent or a CSS\n\t * named colour) resolves to `var(--hub-sys-color-<variant>, <variant>)` — the\n\t * design-system token with the word itself as the raw fallback; a literal\n\t * (`#hex` / `rgb()` / `oklch()` / `var()`) is passed through unchanged. Returns\n\t * `null` to keep the `primary` default. The built-in semantic variants\n\t * additionally pick up their exact ds tints through the SCSS `@each`.\n\t */\n\tprotected readonly groupAccent = computed(() => resolveHubAccent(this.variant()));\n\n\t/**\n\t * Whether more than one panel may be active at once. Driven by `multiple`\n\t * for every view, and always enabled in the `card` view, where all panels\n\t * stay visible at once and must not deactivate one another.\n\t */\n\treadonly allowsMultipleActive = computed(() => this.multiple() || this.isCardView());\n\n\t/** Whether the bound form control disabled the whole container. */\n\treadonly formDisabled = signal(false);\n\n\t/**\n\t * Whether the active panel routes its content through a `<router-outlet>`.\n\t * Never true in the accordion view, where routed panels are not supported.\n\t */\n\tprotected readonly activePanelHasRouter = computed(\n\t\t() => !this.isAccordionView() && !this.allowsMultipleActive() && !!this.activePanel()?.routerUrl()\n\t);\n\n\t/**\n\t * In `multiple` tabs/pills, headers are partitioned into blocks. Every\n\t * active panel starts a block; following inactive headers stay visible in\n\t * that same block until the next active panel starts a new one.\n\t */\n\tprotected readonly multipleHeaderGroups = computed<MultipleHeaderGroup[]>(() => {\n\t\tif (!this.allowsMultipleActive() || this.isAccordionView()) {\n\t\t\treturn [];\n\t\t}\n\t\tconst panels = this.panels();\n\t\tif (!panels.length) {\n\t\t\treturn [];\n\t\t}\n\t\tconst activeIndices = panels.map((panel, index) => (panel.active() ? index : -1)).filter((index) => index !== -1);\n\t\tif (!activeIndices.length) {\n\t\t\treturn [{ headers: panels }];\n\t\t}\n\t\treturn activeIndices.map((activeIndex, groupIndex) => {\n\t\t\tconst startIndex = groupIndex === 0 ? 0 : activeIndex;\n\t\t\tconst endIndex = activeIndices[groupIndex + 1] ?? panels.length;\n\t\t\treturn {\n\t\t\t\tactivePanel: panels[activeIndex],\n\t\t\t\theaders: panels.slice(startIndex, endIndex)\n\t\t\t};\n\t\t});\n\t});\n\n\t/** Whether the strip cannot scroll further backward. */\n\treadonly backwardIsDisabled = signal(true);\n\n\t/** Whether the strip cannot scroll further forward. */\n\treadonly forwardIsDisabled = signal(false);\n\n\t#isDestroyed = false;\n\t#syncScheduled = false;\n\t#viewInitialised = false;\n\t#placementScheduled = false;\n\t#multipleBlockSizingScheduled = false;\n\n\t/** Last value written by the bound form control; `null` when no form. */\n\t#formValue: unknown[] | null = null;\n\n\t#onChange: (value: unknown) => void = () => undefined;\n\t#onTouched: () => void = () => undefined;\n\n\tconstructor() {\n\t\tthis.#destroyRef.onDestroy(() => {\n\t\t\tthis.#isDestroyed = true;\n\t\t});\n\n\t\tafterNextRender(() => {\n\t\t\tthis.#viewInitialised = true;\n\t\t\tthis.updateScrollButtons();\n\t\t\tthis.setActivePanel();\n\t\t\t// Re-apply any form value written before the panels' inputs were bound.\n\t\t\tthis.#applyFormValue();\n\t\t\tthis.#ensureActivePanel();\n\t\t\tthis.#schedulePanelPlacement();\n\t\t\tthis.#scheduleMultipleBlockSizing();\n\t\t\tthis.#router.events\n\t\t\t\t.pipe(\n\t\t\t\t\tfilter((event) => event instanceof NavigationEnd),\n\t\t\t\t\ttakeUntilDestroyed(this.#destroyRef)\n\t\t\t\t)\n\t\t\t\t.subscribe(() => this.setActivePanel());\n\t\t});\n\t}\n\n\t/**\n\t * Kept so a panel built against an older release still compiles. Panels are discovered by\n\t * content query now, so joining the container is nothing a panel has to ask for.\n\t *\n\t * @deprecated Does nothing. Removed under this name in **23.0.0**.\n\t */\n\tregisterPanel(_panel: HubPanelComponent): void {\n\t\t// Intentionally empty.\n\t}\n\n\t/**\n\t * Removes a panel from the container. `reselect` activates the closest enabled neighbour when\n\t * the removed panel was active; `emit` fires the panel's `removed` output; `track` records the\n\t * removal so the content query stops presenting the panel.\n\t *\n\t * A panel on its way out of the DOM passes `track: false`: the query drops it by itself, and\n\t * remembering it would hold the reference alive for nothing.\n\t */\n\tremovePanel(panel: HubPanelComponent, options: { reselect?: boolean; emit?: boolean; track?: boolean } = {}): void {\n\t\tconst { reselect = true, emit = true, track = true } = options;\n\t\tconst panels = this.panels();\n\t\tconst index = panels.indexOf(panel);\n\t\tif (index === -1 || this.#isDestroyed) {\n\t\t\treturn;\n\t\t}\n\n\t\tif (reselect && panel.active() && !this.isAccordionView()) {\n\t\t\tconst closestIndex = this.#closestEnabledIndex(index);\n\t\t\tif (closestIndex !== -1) {\n\t\t\t\tpanels[closestIndex].active.set(true);\n\t\t\t}\n\t\t}\n\t\tif (emit) {\n\t\t\tpanel.removed.emit(panel);\n\t\t}\n\n\t\tif (track) {\n\t\t\t// Prune as we go: a panel removed and then destroyed would otherwise stay in the set for\n\t\t\t// the lifetime of the container.\n\t\t\tthis.#removedPanels.update((current) => {\n\t\t\t\tconst live = new Set(this.projectedPanels());\n\t\t\t\tconst next = new Set([...current].filter((candidate) => live.has(candidate)));\n\t\t\t\tnext.add(panel);\n\t\t\t\treturn next;\n\t\t\t});\n\t\t}\n\n\t\t// Detach the projected pane: the consumer template still owns the node,\n\t\t// so removing the header alone would leave the pane content behind.\n\t\tconst paneElement = panel.elementRef.nativeElement;\n\t\tif (paneElement.parentNode) {\n\t\t\tthis.#renderer.removeChild(paneElement.parentNode, paneElement);\n\t\t}\n\t\tif (panel.active()) {\n\t\t\tpanel.active.set(false);\n\t\t\tthis.#emitFormValue();\n\t\t}\n\t\tthis.#scheduleSync();\n\t}\n\n\t/**\n\t * Removes a panel on behalf of the user (the ✕ button or the Delete key)\n\t * and returns keyboard focus to the closest remaining header — strip link\n\t * or accordion button — so focus never falls back to `<body>` when the\n\t * focused control disappears with its panel.\n\t */\n\tremovePanelAndRefocus(panel: HubPanelComponent): void {\n\t\tconst index = this.panels().indexOf(panel);\n\t\tif (index === -1) {\n\t\t\treturn;\n\t\t}\n\t\tthis.removePanel(panel);\n\t\tqueueMicrotask(() => this.#focusPanelAt(Math.min(index, this.panels().length - 1)));\n\t}\n\n\t/**\n\t * Activates a panel on behalf of the user (`tabs` / `pills` views): marks it\n\t * active, navigates when routed, and emits `panelChange`. In `multiple` mode\n\t * clicking an active panel toggles it off (the panes render side by side);\n\t * otherwise an already-active panel no-ops. Disabled panels always no-op.\n\t */\n\tselectPanel(panel: HubPanelComponent): void {\n\t\tif (panel.disabled() || this.formDisabled()) {\n\t\t\treturn;\n\t\t}\n\t\tif (this.allowsMultipleActive()) {\n\t\t\tif (panel.active()) {\n\t\t\t\tpanel.active.set(false);\n\t\t\t} else {\n\t\t\t\tpanel.active.set(true);\n\t\t\t\tpanel.navigate();\n\t\t\t\tthis.panelChange.emit({ prev: undefined, current: panel });\n\t\t\t}\n\t\t\tthis.#emitFormValue();\n\t\t\tthis.#onTouched();\n\t\t\tthis.#schedulePanelPlacement();\n\t\t\treturn;\n\t\t}\n\t\tif (panel.active()) {\n\t\t\treturn;\n\t\t}\n\t\tconst previousPanel = this.activePanel();\n\t\t// Deactivate the previously active panel up front so the emitted form\n\t\t// value reflects only the newly selected panel. The per-panel effect that\n\t\t// enforces single-active runs asynchronously, so relying on it here would\n\t\t// emit a stale value that still includes the previous panel.\n\t\tif (previousPanel && previousPanel !== panel) {\n\t\t\tpreviousPanel.active.set(false);\n\t\t}\n\t\tpanel.active.set(true);\n\t\tpanel.navigate();\n\t\tthis.panelChange.emit({ prev: previousPanel, current: panel });\n\t\tthis.#emitFormValue();\n\t\tthis.#onTouched();\n\t\tthis.#schedulePanelPlacement();\n\t}\n\n\t/**\n\t * Toggles a panel on behalf of the user (accordion view): an open panel\n\t * closes, a closed one opens — closing the others unless `multiple`.\n\t * Emits `panelChange` when a panel opens.\n\t */\n\ttogglePanel(panel: HubPanelComponent): void {\n\t\tif (panel.disabled() || this.formDisabled()) {\n\t\t\treturn;\n\t\t}\n\t\tif (panel.active()) {\n\t\t\tpanel.active.set(false);\n\t\t} else {\n\t\t\tconst previousPanel = this.allowsMultipleActive() ? undefined : this.activePanel();\n\t\t\tpanel.active.set(true);\n\t\t\tthis.panelChange.emit({ prev: previousPanel, current: panel });\n\t\t}\n\t\tthis.#emitFormValue();\n\t\tthis.#onTouched();\n\t\tthis.#schedulePanelPlacement();\n\t}\n\n\t/**\n\t * Marks the routed panel matching the current URL as active. Does not\n\t * navigate — activation through this path is URL-driven. No-op in the\n\t * accordion view, where routed panels are not supported.\n\t */\n\tsetActivePanel(): void {\n\t\tif (this.isAccordionView()) {\n\t\t\treturn;\n\t\t}\n\t\tconst [route, queryString] = this.#router.url.split('?');\n\t\tfor (const panel of this.panels()) {\n\t\t\tif (!panel.routerUrl()) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tlet matches: boolean;\n\t\t\tif (panel.pathMatch() === 'full') {\n\t\t\t\tconst currentUrl = queryString?.trim() ? `${route}?${queryString.trim()}` : route;\n\t\t\t\tmatches = currentUrl === panel.getFullRoute();\n\t\t\t} else {\n\t\t\t\tmatches = route === panel.getRoute();\n\t\t\t}\n\t\t\tif (matches) {\n\t\t\t\tif (!panel.active()) {\n\t\t\t\t\tpanel.active.set(true);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\t// ── ControlValueAccessor ────────────────────────────────────────────────\n\n\t/**\n\t * Writes the form value into the container: panels whose (`bindValue`-mapped)\n\t * value matches are activated, the rest are deactivated. With `multiple` an\n\t * array is expected; otherwise a single value.\n\t */\n\twriteValue(value: unknown): void {\n\t\tif (value == null) {\n\t\t\tthis.#formValue = [];\n\t\t} else if (this.multiple()) {\n\t\t\tthis.#formValue = Array.isArray(value) ? [...value] : [value];\n\t\t} else {\n\t\t\tthis.#formValue = Array.isArray(value) ? value.slice(0, 1) : [value];\n\t\t}\n\t\tthis.#applyFormValue();\n\t}\n\n\t/** Registers the form-control change callback. */\n\tregisterOnChange(onChange: (value: unknown) => void): void {\n\t\tthis.#onChange = onChange;\n\t}\n\n\t/** Registers the form-control touched callback. */\n\tregisterOnTouched(onTouched: () => void): void {\n\t\tthis.#onTouched = onTouched;\n\t}\n\n\t/** Enables/disables every panel header on behalf of the form control. */\n\tsetDisabledState(isDisabled: boolean): void {\n\t\tthis.formDisabled.set(isDisabled);\n\t}\n\n\t/** Keyboard navigation for the panel strip (arrows / Home / End / Delete). */\n\tprotected onPanelKeydown(event: KeyboardEvent, index: number): void {\n\t\tif (!this.isKeysAllowed()) {\n\t\t\treturn;\n\t\t}\n\t\tswitch (event.key) {\n\t\t\tcase 'ArrowRight':\n\t\t\tcase 'ArrowDown':\n\t\t\t\tif (event.key === 'ArrowDown' && !this.vertical()) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.#stepEnabledIndex(index, 1));\n\t\t\t\treturn;\n\t\t\tcase 'ArrowLeft':\n\t\t\tcase 'ArrowUp':\n\t\t\t\tif (event.key === 'ArrowUp' && !this.vertical()) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.#stepEnabledIndex(index, -1));\n\t\t\t\treturn;\n\t\t\tcase 'Home':\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.panels().findIndex((panel) => !panel.disabled()));\n\t\t\t\treturn;\n\t\t\tcase 'End': {\n\t\t\t\tevent.preventDefault();\n\t\t\t\tconst panels = this.panels();\n\t\t\t\tthis.#focusPanelAt(panels.length - 1 - [...panels].reverse().findIndex((panel) => !panel.disabled()));\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tcase 'Delete': {\n\t\t\t\tconst panel = this.panels()[index];\n\t\t\t\tif (panel?.removable()) {\n\t\t\t\t\tthis.removePanelAndRefocus(panel);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Keyboard navigation between accordion headers (arrows / Home / End /\n\t * Delete). Enter and Space toggle natively through the button click.\n\t */\n\tonAccordionKeydown(event: KeyboardEvent, panel: HubPanelComponent): void {\n\t\tif (!this.isKeysAllowed()) {\n\t\t\treturn;\n\t\t}\n\t\tconst index = this.panels().indexOf(panel);\n\t\tswitch (event.key) {\n\t\t\tcase 'ArrowDown':\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.#stepEnabledIndex(index, 1));\n\t\t\t\treturn;\n\t\t\tcase 'ArrowUp':\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.#stepEnabledIndex(index, -1));\n\t\t\t\treturn;\n\t\t\tcase 'Home':\n\t\t\t\tevent.preventDefault();\n\t\t\t\tthis.#focusPanelAt(this.panels().findIndex((candidate) => !candidate.disabled()));\n\t\t\t\treturn;\n\t\t\tcase 'End': {\n\t\t\t\tevent.preventDefault();\n\t\t\t\tconst panels = this.panels();\n\t\t\t\tthis.#focusPanelAt(panels.length - 1 - [...panels].reverse().findIndex((candidate) => !candidate.disabled()));\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tcase 'Delete': {\n\t\t\t\tif (panel.removable()) {\n\t\t\t\t\tthis.removePanelAndRefocus(panel);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Recomputes the enabled/disabled state of the scroll buttons. */\n\tprotected updateScrollButtons(): void {\n\t\tif (!this.scrollable() || this.isAccordionView()) {\n\t\t\treturn;\n\t\t}\n\t\tconst scroller = this.navScroller()?.nativeElement;\n\t\tif (!scroller) {\n\t\t\treturn;\n\t\t}\n\t\tconst { scrollLeft, scrollWidth } = scroller;\n\t\tthis.backwardIsDisabled.set(scrollLeft <= 0);\n\t\tthis.forwardIsDisabled.set(scrollLeft + contentBoxWidth(scroller) + 1 >= scrollWidth);\n\t}\n\n\t/** Re-syncs scroll controls and multiple-block sizing on window resize. */\n\tprotected onWindowResize(): void {\n\t\tthis.updateScrollButtons();\n\t\tthis.#scheduleMultipleBlockSizing();\n\t}\n\n\t/** Updates the scroll buttons as the strip scrolls. */\n\tprotected onScroll(): void {\n\t\tthis.updateScrollButtons();\n\t}\n\n\t/** Global index of a panel within the projected strip order. */\n\tprotected panelIndex(panel: HubPanelComponent): number {\n\t\treturn this.panelIndexMap().get(panel) ?? -1;\n\t}\n\n\t/** Scrolls the panel headers one viewport backward. */\n\tprotected navBackward(): void {\n\t\tconst scroller = this.navScroller()?.nativeElement;\n\t\tif (!scroller) {\n\t\t\treturn;\n\t\t}\n\t\tconst step = contentBoxWidth(scroller) - this.#visibleScrollButtonsWidth();\n\t\tscroller.scrollLeft = Math.max(scroller.scrollLeft - step, 0);\n\t}\n\n\t/** Scrolls the panel headers one viewport forward. */\n\tprotected navForward(): void {\n\t\tconst scroller = this.navScroller()?.nativeElement;\n\t\tif (!scroller) {\n\t\t\treturn;\n\t\t}\n\t\tconst step = contentBoxWidth(scroller) - this.#visibleScrollButtonsWidth();\n\t\tconst lastPosition = scroller.scrollWidth - step;\n\t\tscroller.scrollLeft = Math.min(scroller.scrollLeft + step, lastPosition);\n\t}\n\n\t/** Width currently taken by the visible scroll buttons. */\n\t#visibleScrollButtonsWidth(): number {\n\t\treturn [this.prevBtn()?.nativeElement, this.nextBtn()?.nativeElement].reduce(\n\t\t\t(total, button) => (button ? total + contentBoxWidth(button) : total),\n\t\t\t0\n\t\t);\n\t}\n\n\t/** Index of the enabled panel closest to `index`, or `-1` when none exists. */\n\t#closestEnabledIndex(index: number): number {\n\t\tconst panels = this.panels();\n\t\tfor (let step = 1; step <= panels.length; step += 1) {\n\t\t\tconst previous = panels[index - step];\n\t\t\tif (previous && !previous.disabled()) {\n\t\t\t\treturn index - step;\n\t\t\t}\n\t\t\tconst next = panels[index + step];\n\t\t\tif (next && !next.disabled()) {\n\t\t\t\treturn index + step;\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\n\t/** Next enabled panel index from `index` in `direction`, wrapping around. */\n\t#stepEnabledIndex(index: number, direction: 1 | -1): number {\n\t\tconst panels = this.panels();\n\t\tfor (let step = 1; step <= panels.length; step += 1) {\n\t\t\tconst candidate = (index + direction * step + panels.length * step) % panels.length;\n\t\t\tif (!panels[candidate].disabled()) {\n\t\t\t\treturn candidate;\n\t\t\t}\n\t\t}\n\t\treturn index;\n\t}\n\n\t/** Moves DOM focus to the panel header at `index` (strip link or accordion button). */\n\t#focusPanelAt(index: number): void {\n\t\tif (index < 0) {\n\t\t\treturn;\n\t\t}\n\t\tconst selector = this.isAccordionView() ? '.hub-panels__accordion-btn' : '.hub-panels__nav-link';\n\t\tconst headers = this.#elementRef.nativeElement.querySelectorAll<HTMLElement>(selector);\n\t\theaders[index]?.focus();\n\t}\n\n\t/**\n\t * Coalesces post-registration/removal housekeeping into one microtask:\n\t * re-applies the bound form value to the current panels, guarantees an\n\t * active panel (non-routed `tabs` / `pills` containers without a bound\n\t * form) and refreshes the scroll buttons after the strip changed size.\n\t * Skipped until the first render — before it the projected panels' inputs\n\t * are not bound yet, and the constructor's `afterNextRender` performs the\n\t * initial pass instead.\n\t */\n\t#scheduleSync(): void {\n\t\tif (this.#syncScheduled || this.#isDestroyed) {\n\t\t\treturn;\n\t\t}\n\t\tthis.#syncScheduled = true;\n\t\tqueueMicrotask(() => {\n\t\t\tthis.#syncScheduled = false;\n\t\t\tif (this.#isDestroyed || !this.#viewInitialised) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tthis.#applyFormValue();\n\t\t\tthis.#ensureActivePanel();\n\t\t\tthis.#schedulePanelPlacement();\n\t\t\tthis.updateScrollButtons();\n\t\t});\n\t}\n\n\t/** Coalesces DOM moves for the projected `hub-panel` hosts. */\n\t#schedulePanelPlacement(): void {\n\t\tif (this.#placementScheduled || this.#isDestroyed) {\n\t\t\treturn;\n\t\t}\n\t\tthis.#placementScheduled = true;\n\t\trequestAnimationFrame(() => {\n\t\t\tthis.#placementScheduled = false;\n\t\t\tif (this.#isDestroyed || !this.#viewInitialised) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tthis.#runPanelPlacementPass();\n\t\t\trequestAnimationFrame(() => {\n\t\t\t\tif (this.#isDestroyed || !this.#viewInitialised) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tthis.#runPanelPlacementPass();\n\t\t\t});\n\t\t});\n\t}\n\n\t/** Performs one projected-panel placement pass plus dependent sizing. */\n\t#runPanelPlacementPass(): void {\n\t\tthis.#placeProjectedPanels();\n\t\tthis.#scheduleMultipleBlockSizing();\n\t}\n\n\t/** Coalesces the DOM measurements needed by `multiple + vertical`. */\n\t#scheduleMultipleBlockSizing(): void {\n\t\tif (this.#multipleBlockSizingScheduled || this.#isDestroyed) {\n\t\t\treturn;\n\t\t}\n\t\tthis.#multipleBlockSizingScheduled = true;\n\t\trequestAnimationFrame(() => {\n\t\t\tthis.#multipleBlockSizingScheduled = false;\n\t\t\tif (this.#isDestroyed || !this.#viewInitialised) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tthis.#syncMultipleBlockSizing();\n\t\t});\n\t}\n\n\t/** Moves projected panel hosts into their visible multiple-block container. */\n\t#placeProjectedPanels(): void {\n\t\tconst contentRoot = this.contentRoot()?.nativeElement;\n\t\tif (!contentRoot) {\n\t\t\treturn;\n\t\t}\n\t\tif (!this.allowsMultipleActive() || this.isAccordionView()) {\n\t\t\tfor (const panel of this.panels()) {\n\t\t\t\tconst panelElement = panel.elementRef.nativeElement;\n\t\t\t\tif (panelElement.parentElement !== contentRoot) {\n\t\t\t\t\tthis.#renderer.appendChild(contentRoot, panelElement);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn;\n\t\t}\n\t\tconst hostMap = new Map(\n\t\t\tArray.from(\n\t\t\t\tthis.#elementRef.nativeElement.querySelectorAll<HTMLElement>(\n\t\t\t\t\t'.hub-panels__multiple-layout .hub-panels__multiple-pane-host'\n\t\t\t\t)\n\t\t\t).map((host) => [host.dataset['panelId'] ?? '', host] as const)\n\t\t);\n\t\tfor (const panel of this.panels()) {\n\t\t\tconst panelElement = panel.elementRef.nativeElement;\n\t\t\tconst targetHost = hostMap.get(panel.id()) ?? contentRoot;\n\t\t\tif (panelElement.parentElement !== targetHost) {\n\t\t\t\tthis.#renderer.appendChild(targetHost, panelElement);\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Updates the minimum content width for each `multiple + vertical` block. */\n\t#syncMultipleBlockSizing(): void {\n\t\tfor (const blockRef of this.multipleBlocks()) {\n\t\t\tconst block = blockRef.nativeElement;\n\t\t\tthis.#renderer.removeStyle(block, '--hub-panels-multiple-vertical-panel-min-width', RendererStyleFlags2.DashCase);\n\t\t\tif (!this.vertical() || !this.allowsMultipleActive() || this.isAccordionView()) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tconst header = block.querySelector(':scope > .hub-panels__header');\n\t\t\tif (!(header instanceof HTMLElement)) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tconst headerStackHeight = Math.ceil(header.getBoundingClientRect().height);\n\t\t\tthis.#renderer.setStyle(\n\t\t\t\tblock,\n\t\t\t\t'--hub-panels-multiple-vertical-panel-min-width',\n\t\t\t\t`${headerStackHeight}px`,\n\t\t\t\tRendererStyleFlags2.DashCase\n\t\t\t);\n\t\t}\n\t}\n\n\t/**\n\t * Activates the first enabled panel when none is active. Skipped for the\n\t * accordion view (panels start collapsed), for routed containers (the URL\n\t * is the single source of truth) and when a form value is bound (the form\n\t * is).\n\t */\n\t#ensureActivePanel(): void {\n\t\tif (this.isAccordionView() || this.#formValue !== null) {\n\t\t\treturn;\n\t\t}\n\t\tif (this.allowsMultipleActive()) {\n\t\t\treturn;\n\t\t}\n\t\tconst panels = this.panels();\n\t\tif (!panels.length || panels.some((panel) => panel.active())) {\n\t\t\treturn;\n\t\t}\n\t\tif (panels.some((panel) => !!panel.routerUrl())) {\n\t\t\treturn;\n\t\t}\n\t\tpanels.find((panel) => !panel.disabled())?.active.set(true);\n\t}\n\n\t/** Activates/deactivates panels so they mirror the bound form value. */\n\t#applyFormValue(): void {\n\t\tif (this.#formValue === null) {\n\t\t\treturn;\n\t\t}\n\t\tconst compare = this.compareWith();\n\t\tfor (const panel of this.panels()) {\n\t\t\tconst panelValue = this.#comparableValue(panel);\n\t\t\tconst matches = this.#formValue.some((selectedValue) => compare(selectedValue, panelValue));\n\t\t\tif (panel.active() !== matches) {\n\t\t\t\tpanel.active.set(matches);\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Emits the current selection through the form-control callback. */\n\t#emitFormValue(): void {\n\t\tconst compare = this.compareWith();\n\t\tconst activeValues = this.panels()\n\t\t\t.filter((panel) => panel.active())\n\t\t\t.map((panel) => this.#comparableValue(panel));\n\t\tif (this.#formValue !== null) {\n\t\t\tthis.#formValue = [...activeValues];\n\t\t}\n\t\t// Deduplicate defensively when several panels share the same value.\n\t\tconst uniqueValues = activeValues.filter(\n\t\t\t(value, index) => activeValues.findIndex((candidate) => compare(candidate, value)) === index\n\t\t);\n\t\tthis.#onChange(this.multiple() ? uniqueValues : (uniqueValues[0] ?? null));\n\t}\n\n\t/** Form value of a panel with the `bindValue` path applied. */\n\t#comparableValue(panel: HubPanelComponent): unknown {\n\t\tconst rawValue = panel.formValue();\n\t\tconst bindPath = this.bindValue();\n\t\treturn bindPath ? readByPath(rawValue, bindPath) : rawValue;\n\t}\n}\n","@if (!isAccordionView() && !isCardView()) {\n\t@if (multiple()) {\n\t\t<div class=\"hub-panels__multiple-layout\">\n\t\t\t@for (group of multipleHeaderGroups(); track group.activePanel ?? group.headers[0]) {\n\t\t\t\t<div\n\t\t\t\t\t#multipleBlock\n\t\t\t\t\tclass=\"hub-panels hub-panels__multiple-block\"\n\t\t\t\t\t[class.hub-panels--tabs]=\"type() === 'tabs'\"\n\t\t\t\t\t[class.hub-panels--pills]=\"type() === 'pills'\"\n\t\t\t\t\t[class.hub-panels--vertical]=\"vertical()\"\n\t\t\t\t>\n\t\t\t\t\t<div class=\"hub-panels__header\">\n\t\t\t\t\t\t<ul\n\t\t\t\t\t\t\tclass=\"hub-panels__nav\"\n\t\t\t\t\t\t\trole=\"tablist\"\n\t\t\t\t\t\t\t[attr.aria-label]=\"config.ariaLabel\"\n\t\t\t\t\t\t\t[attr.aria-orientation]=\"vertical() ? 'vertical' : null\"\n\t\t\t\t\t\t\t[class.hub-panels__nav--tabs]=\"type() === 'tabs'\"\n\t\t\t\t\t\t\t[class.hub-panels__nav--pills]=\"type() === 'pills'\"\n\t\t\t\t\t\t\t[class.hub-panels__nav--vertical]=\"vertical()\"\n\t\t\t\t\t\t\t[class.hub-panels__nav--justified]=\"justified()\"\n\t\t\t\t\t\t>\n\t\t\t\t\t\t\t@for (panel of group.headers; track panel) {\n\t\t\t\t\t\t\t\t<li\n\t\t\t\t\t\t\t\t\tclass=\"hub-panels__nav-item\"\n\t\t\t\t\t\t\t\t\t[class]=\"panel.customClass()\"\n\t\t\t\t\t\t\t\t\t[class.hub-panels__nav-item--active]=\"panel.active()\"\n\t\t\t\t\t\t\t\t\t[class.hub-panels__nav-item--disabled]=\"panel.disabled()\"\n\t\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t\t<button\n\t\t\t\t\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\t\t\t\t\tclass=\"hub-panels__nav-link\"\n\t\t\t\t\t\t\t\t\t\trole=\"tab\"\n\t\t\t\t\t\t\t\t\t\t[id]=\"panel.id() + '-link'\"\n\t\t\t\t\t\t\t\t\t\t[class.hub-panels__nav-link--active]=\"panel.active()\"\n\t\t\t\t\t\t\t\t\t\t[class.hub-panels__nav-link--disabled]=\"panel.disabled()\"\n\t\t\t\t\t\t\t\t\t\t[disabled]=\"panel.disabled() || formDisabled()\"\n\t\t\t\t\t\t\t\t\t\t[attr.aria-controls]=\"panel.id()\"\n\t\t\t\t\t\t\t\t\t\t[attr.aria-selected]=\"panel.active()\"\n\t\t\t\t\t\t\t\t\t\t[attr.tabindex]=\"\n\t\t\t\t\t\t\t\t\t\t\tpanel.active() || (!activePanel() && panelIndex(panel) === 0) ? null : -1\n\t\t\t\t\t\t\t\t\t\t\"\n\t\t\t\t\t\t\t\t\t\t(click)=\"selectPanel(panel)\"\n\t\t\t\t\t\t\t\t\t\t(keydown)=\"onPanelKeydown($event, panelIndex(panel))\"\n\t\t\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t\t\t@if (panel.headingRef(); as headingRef) {\n\t\t\t\t\t\t\t\t\t\t\t<ng-container [ngTemplateOutlet]=\"headingRef\" />\n\t\t\t\t\t\t\t\t\t\t} @else {\n\t\t\t\t\t\t\t\t\t\t\t{{ panel.heading() }}\n\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t</button>\n\t\t\t\t\t\t\t\t\t<!-- Real sibling button: a control nested inside the tab\n\t\t\t\t\t\t\t\t\t\t button would be invalid HTML and unreachable by keyboard.\n\t\t\t\t\t\t\t\t\t\t It overlays the tab's reserved end padding, so the ✕ keeps\n\t\t\t\t\t\t\t\t\t\t its visual spot inside the tab chrome. -->\n\t\t\t\t\t\t\t\t\t@if (panel.removable()) {\n\t\t\t\t\t\t\t\t\t\t<button\n\t\t\t\t\t\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\t\t\t\t\t\tclass=\"hub-panels__remove-btn\"\n\t\t\t\t\t\t\t\t\t\t\t[disabled]=\"panel.disabled() || formDisabled()\"\n\t\t\t\t\t\t\t\t\t\t\t[attr.aria-label]=\"panel.removeLabel()\"\n\t\t\t\t\t\t\t\t\t\t\t(click)=\"removePanelAndRefocus(panel)\"\n\t\t\t\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t\t\t\t&times;\n\t\t\t\t\t\t\t\t\t\t</button>\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t</li>\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t</ul>\n\t\t\t\t\t\t@if (!justified() && type() !== 'pills' && !vertical()) {\n\t\t\t\t\t\t\t<div class=\"hub-panels__spacer\"></div>\n\t\t\t\t\t\t}\n\t\t\t\t\t</div>\n\n\t\t\t\t\t@if (group.activePanel) {\n\t\t\t\t\t\t<div class=\"hub-panels__content\" [class.hub-panels__content--pills]=\"type() === 'pills'\">\n\t\t\t\t\t\t\t<div\n\t\t\t\t\t\t\t\t#multiplePaneHost\n\t\t\t\t\t\t\t\tclass=\"hub-panels__multiple-pane-host\"\n\t\t\t\t\t\t\t\t[attr.data-panel-id]=\"group.activePanel.id()\"\n\t\t\t\t\t\t\t></div>\n\t\t\t\t\t\t</div>\n\t\t\t\t\t}\n\t\t\t\t</div>\n\t\t\t}\n\t\t</div>\n\t} @else {\n\t\t<div class=\"hub-panels__header\">\n\t\t\t@if (scrollable() && !backwardIsDisabled()) {\n\t\t\t\t<button\n\t\t\t\t\t#prevBtn\n\t\t\t\t\ttype=\"button\"\n\t\t\t\t\tclass=\"hub-panels__scroll-btn hub-panels__scroll-btn--backward\"\n\t\t\t\t\t[attr.aria-label]=\"config.scrollBackwardAriaLabel\"\n\t\t\t\t\t(click)=\"navBackward()\"\n\t\t\t\t></button>\n\t\t\t}\n\n\t\t\t<div #navScroller class=\"hub-panels__nav-scroller\" (scroll)=\"onScroll()\">\n\t\t\t\t<ul\n\t\t\t\t\tclass=\"hub-panels__nav\"\n\t\t\t\t\trole=\"tablist\"\n\t\t\t\t\t[attr.aria-label]=\"config.ariaLabel\"\n\t\t\t\t\t[attr.aria-orientation]=\"vertical() ? 'vertical' : null\"\n\t\t\t\t\t[class.hub-panels__nav--tabs]=\"type() === 'tabs'\"\n\t\t\t\t\t[class.hub-panels__nav--pills]=\"type() === 'pills'\"\n\t\t\t\t\t[class.hub-panels__nav--vertical]=\"vertical()\"\n\t\t\t\t\t[class.hub-panels__nav--justified]=\"justified()\"\n\t\t\t\t>\n\t\t\t\t\t@for (panel of panels(); track panel; let index = $index) {\n\t\t\t\t\t\t<li\n\t\t\t\t\t\t\tclass=\"hub-panels__nav-item\"\n\t\t\t\t\t\t\t[class]=\"panel.customClass()\"\n\t\t\t\t\t\t\t[class.hub-panels__nav-item--active]=\"panel.active()\"\n\t\t\t\t\t\t\t[class.hub-panels__nav-item--disabled]=\"panel.disabled()\"\n\t\t\t\t\t\t>\n\t\t\t\t\t\t\t<button\n\t\t\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\t\t\tclass=\"hub-panels__nav-link\"\n\t\t\t\t\t\t\t\trole=\"tab\"\n\t\t\t\t\t\t\t\t[id]=\"panel.id() + '-link'\"\n\t\t\t\t\t\t\t\t[class.hub-panels__nav-link--active]=\"panel.active()\"\n\t\t\t\t\t\t\t\t[class.hub-panels__nav-link--disabled]=\"panel.disabled()\"\n\t\t\t\t\t\t\t\t[disabled]=\"panel.disabled() || formDisabled()\"\n\t\t\t\t\t\t\t\t[attr.aria-controls]=\"panel.id()\"\n\t\t\t\t\t\t\t\t[attr.aria-selected]=\"panel.active()\"\n\t\t\t\t\t\t\t\t[attr.tabindex]=\"panel.active() || (!activePanel() && index === 0) ? null : -1\"\n\t\t\t\t\t\t\t\t(click)=\"selectPanel(panel)\"\n\t\t\t\t\t\t\t\t(keydown)=\"onPanelKeydown($event, index)\"\n\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t@if (panel.headingRef(); as headingRef) {\n\t\t\t\t\t\t\t\t\t<ng-container [ngTemplateOutlet]=\"headingRef\" />\n\t\t\t\t\t\t\t\t} @else {\n\t\t\t\t\t\t\t\t\t{{ panel.heading() }}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t</button>\n\t\t\t\t\t\t\t<!-- Real sibling button: a control nested inside the tab\n\t\t\t\t\t\t\t\t button would be invalid HTML and unreachable by keyboard.\n\t\t\t\t\t\t\t\t It overlays the tab's reserved end padding, so the ✕ keeps\n\t\t\t\t\t\t\t\t its visual spot inside the tab chrome. -->\n\t\t\t\t\t\t\t@if (panel.removable()) {\n\t\t\t\t\t\t\t\t<button\n\t\t\t\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\t\t\t\tclass=\"hub-panels__remove-btn\"\n\t\t\t\t\t\t\t\t\t[disabled]=\"panel.disabled() || formDisabled()\"\n\t\t\t\t\t\t\t\t\t[attr.aria-label]=\"panel.removeLabel()\"\n\t\t\t\t\t\t\t\t\t(click)=\"removePanelAndRefocus(panel)\"\n\t\t\t\t\t\t\t\t>\n\t\t\t\t\t\t\t\t\t&times;\n\t\t\t\t\t\t\t\t</button>\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t</li>\n\t\t\t\t\t}\n\t\t\t\t</ul>\n\t\t\t\t@if (!justified() && type() !== 'pills') {\n\t\t\t\t\t<div class=\"hub-panels__spacer\"></div>\n\t\t\t\t}\n\t\t\t</div>\n\n\t\t\t@if (scrollable() && !forwardIsDisabled()) {\n\t\t\t\t<button\n\t\t\t\t\t#nextBtn\n\t\t\t\t\ttype=\"button\"\n\t\t\t\t\tclass=\"hub-panels__scroll-btn hub-panels__scroll-btn--forward\"\n\t\t\t\t\t[attr.aria-label]=\"config.scrollForwardAriaLabel\"\n\t\t\t\t\t(click)=\"navForward()\"\n\t\t\t\t></button>\n\t\t\t}\n\t\t</div>\n\t}\n}\n\n<div\n\t#contentRoot\n\tclass=\"hub-panels__content\"\n\t[class.hub-panels__content--pills]=\"type() === 'pills'\"\n\t[class.hub-panels__content--accordion]=\"isAccordionView()\"\n\t[class.hub-panels__content--multiple-parking]=\"!isAccordionView() && multiple()\"\n>\n\t@if (activePanelHasRouter()) {\n\t\t<router-outlet />\n\t} @else {\n\t\t<ng-content />\n\t}\n</div>\n","import { NgTemplateOutlet } from '@angular/common';\nimport {\n\tforwardRef,\n\tbooleanAttribute,\n\tChangeDetectionStrategy,\n\tComponent,\n\tcomputed,\n\teffect,\n\tElementRef,\n\tinject,\n\tinput,\n\tmodel,\n\tOnDestroy,\n\toutput,\n\tRenderer2,\n\tsignal,\n\tTemplateRef,\n\tViewEncapsulation\n} from '@angular/core';\nimport { Params, Router } from '@angular/router';\n\nimport { HubPanelAppearance, HubPanelVariant } from '../../models/panels.types';\nimport { resolveHubAccent } from 'ng-hub-ui-utils';\nimport { HubPanelsComponent } from '../panels/panels.component';\n\n/** Monotonic counter backing the auto-generated accessibility ids. */\nlet nextPanelId = 0;\n\n/**\n * One content panel inside a `<hub-panels>` container.\n *\n * In the `tabs` / `pills` views the host element is the tab *panel*\n * (`role=\"tabpanel\"`) and the clickable header is rendered by\n * {@link HubPanelsComponent} in the strip. In the `accordion` view this component\n * renders its own disclosure header plus an animated collapse wrapper around\n * the projected content. In every view the header comes from `heading` or from\n * a `<ng-template hubPanelHeading>` projected inside this element.\n *\n * Panels can be plain content panes or routed: when `routerLink` is set, the\n * container renders a `<router-outlet>` instead of the projected panels and\n * the active panel follows the current URL (`tabs` / `pills` views only).\n *\n * @example\n * ```html\n * <hub-panels>\n * <hub-panel heading=\"Fields\">…</hub-panel>\n * <hub-panel>\n * <ng-template hubPanelHeading>Validations <span class=\"badge\">3</span></ng-template>\n * …\n * </hub-panel>\n * </hub-panels>\n * ```\n */\nimport { HUB_PANEL } from './panel.token';\n\n@Component({\n\tselector: 'hub-panel, [hub-panel]',\n\tproviders: [{ provide: HUB_PANEL, useExisting: forwardRef(() => HubPanelComponent) }],\n\texportAs: 'hubPanel',\n\timports: [NgTemplateOutlet],\n\ttemplateUrl: './panel.component.html',\n\t// The `card` view styles (and the projected header/footer bands) live here so\n\t// a standalone `<hub-panel>` — used outside any `<hub-panels>` container, which\n\t// would otherwise be the only source of the global styles — is styled too.\n\t// `ViewEncapsulation.None` is required so the rules reach the projected,\n\t// consumer-owned `[hubPanelHeader]` / `[hubPanelFooter]` elements.\n\tstyleUrl: './panel.component.scss',\n\tencapsulation: ViewEncapsulation.None,\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\thost: {\n\t\tclass: 'hub-panels__panel',\n\t\t'[attr.id]': 'accordionView() || cardView() ? null : id()',\n\t\t'[attr.role]': \"alertView() ? alertRole() : (accordionView() || cardView() ? null : 'tabpanel')\",\n\t\t'[attr.aria-labelledby]': \"accordionView() || cardView() ? null : id() + '-link'\",\n\t\t'[attr.data-variant]': 'cardView() ? (variant() ?? null) : null',\n\t\t'[style.--hub-panels-alert-accent]': 'alertAccent()',\n\t\t'[style.--hub-panels-card-accent]': 'cardAccent()',\n\t\t'[class.hub-panels__panel--active]': 'active()',\n\t\t'[class.hub-panels__panel--accordion]': 'accordionView()',\n\t\t'[class.hub-panels__panel--toggle-start]': 'toggleAtStart()',\n\t\t'[class.hub-panels__panel--card]': 'cardView() && !alertView()',\n\t\t'[class.hub-panels__panel--alert]': 'alertView()',\n\t\t'[class.hub-panels__panel--fill]': 'fill()',\n\t\t'[class.hub-panels__panel--flush]': 'flush()'\n\t}\n})\nexport class HubPanelComponent implements OnDestroy {\n\t/** Host element reference — exposed so the container can detach removed panes. */\n\treadonly elementRef = inject<ElementRef<HTMLElement>>(ElementRef);\n\n\treadonly #renderer = inject(Renderer2);\n\treadonly #router = inject(Router);\n\n\t/**\n\t * Owning panels container, or `null` when the panel is used standalone\n\t * (outside any `<hub-panels>`), in which case it renders as a card.\n\t * Exposed to the template for the accordion header.\n\t *\n\t * Resolved with `host: true`, so a panel only binds to a group declared in\n\t * the SAME template (its direct container). Without the host boundary the\n\t * lookup walks the whole ancestor injector tree, and a standalone panel\n\t * inside a component projected into a tab pane would register itself as a\n\t * hidden tab of the outer group instead of rendering as a card.\n\t */\n\tprotected readonly tabset = inject(HubPanelsComponent, { optional: true, host: true });\n\n\t/**\n\t * Opts a standalone `<hub-panel>` OUT of an ancestor `<hub-panels>` group so it\n\t * renders as a plain card even when nested inside a tabs / pills / accordion\n\t * container (otherwise hierarchical DI would capture it as a hidden 0×0 tab).\n\t *\n\t * Must be a STATIC attribute (`<hub-panel standalone>`): the opt-out is decided\n\t * when the panel is created — before dynamic inputs are applied — so it is read\n\t * from the host attribute rather than a reactive input.\n\t */\n\treadonly standalone = this.elementRef.nativeElement.hasAttribute('standalone');\n\n\t/** Plain-text panel header. Ignored when a `hubPanelHeading` template exists. */\n\treadonly heading = input<string | undefined>(undefined);\n\n\t/**\n\t * Visual appearance of a standalone panel: a plain `card` (default) or a\n\t * semantic `alert` callout. Only meaningful when the panel renders as a\n\t * card (used standalone or inside a `card` container); ignored in the\n\t * tabs / pills / accordion strip views.\n\t */\n\treadonly appearance = input<HubPanelAppearance>('card');\n\n\t/**\n\t * Semantic colour applied when `appearance` is `alert`. The built-in values\n\t * (`primary` / `success` / `danger` / `warning` / `info`) render with the\n\t * design-system tints. Any other string is also accepted: the alert reads\n\t * `--hub-sys-color-<variant>` from the host application, so a custom accent\n\t * palette interconnects with no changes to this library. Omit for a neutral\n\t * alert.\n\t */\n\treadonly variant = input<HubPanelVariant | (string & {}) | undefined>(undefined);\n\n\t/**\n\t * Makes a card panel fill its parent's height and lets an inner scroll region\n\t * work: the host, both content wrappers and the body become a flex column\n\t * (`flex: 1; min-height: 0`) and the body scrolls. Opt-in; off by default so\n\t * existing layouts are byte-identical. Card view only.\n\t */\n\treadonly fill = input(false, { transform: booleanAttribute });\n\n\t/**\n\t * Removes the card body padding (`--hub-panels-card-padding-x/-y` → 0) so a card\n\t * can host a flush element (a table, a list, a media block) edge-to-edge. Opt-in;\n\t * card view only.\n\t */\n\treadonly flush = input(false, { transform: booleanAttribute });\n\n\t/**\n\t * Unique id used for the `tab` / `tabpanel` (or accordion header / region)\n\t * ARIA pairing. Auto-generated (`hub-panel-<n>`) when not provided.\n\t */\n\treadonly id = input<string>(`hub-panel-${nextPanelId++}`);\n\n\t/** Whether the panel cannot be activated. */\n\treadonly disabled = input(false, { transform: booleanAttribute });\n\n\t/** Whether the panel shows a remove affordance (✕ and the Delete key). */\n\treadonly removable = input(false, { transform: booleanAttribute });\n\n\t/**\n\t * Accessible name announced for the ✕ remove button (`removable` panels).\n\t * The visible glyph is decorative, so this label is what assistive\n\t * technologies read; override it to localize the control.\n\t */\n\treadonly removeLabel = input<string>('Remove panel');\n\n\t/**\n\t * URL comparison used to mark routed panels active: `'route'` compares the\n\t * path only, `'full'` also compares query params.\n\t */\n\treadonly pathMatch = input<'route' | 'full'>('route');\n\n\t/** Navigation target that turns this panel into a routed panel. */\n\treadonly routerLink = input<string | string[] | null | undefined>(undefined);\n\n\t/** Query params appended when navigating to `routerLink`. */\n\treadonly queryParams = input<Params | null | undefined>(undefined);\n\n\t/** Extra CSS classes applied to both the nav item and this pane. */\n\treadonly customClass = input<string | undefined>(undefined);\n\n\t/**\n\t * Value this panel contributes when the container is used as a form control\n\t * (see {@link HubPanelsComponent} `ControlValueAccessor`). Defaults to `id`.\n\t */\n\treadonly value = input<unknown>(undefined);\n\n\t/** Whether the panel is currently active (expanded, in the accordion view). */\n\treadonly active = model(false);\n\n\t/** Emitted when the panel becomes active. */\n\treadonly selectPanel = output<HubPanelComponent>();\n\n\t/** Emitted when the panel stops being active. */\n\treadonly deselectPanel = output<HubPanelComponent>();\n\n\t/** Emitted when the panel is removed through the ✕ button or the Delete key. */\n\treadonly removed = output<HubPanelComponent>();\n\n\t/** Custom header template registered by `HubPanelHeadingDirective`. */\n\treadonly headingRef = signal<TemplateRef<unknown> | undefined>(undefined);\n\n\t/**\n\t * Header actions template registered by `HubPanelHeadingActionsDirective`.\n\t * Rendered beside the accordion disclosure button — never inside it — so\n\t * real `<button>`s stay valid and reachable while the row is collapsed.\n\t */\n\treadonly headingActionsRef = signal<TemplateRef<unknown> | undefined>(undefined);\n\n\t/** Whether the owning container renders the accordion visualization. */\n\tprotected readonly accordionView = computed(() => !this.standalone && (this.tabset?.isAccordionView() ?? false));\n\n\t/**\n\t * Whether this panel's disclosure chevron leads the header row.\n\t *\n\t * Resolved on the PANEL, not on the container: a nested accordion is a DOM descendant of\n\t * the outer one, so a descendant selector on the container would leak the outer chevron\n\t * placement into every accordion inside its panels.\n\t */\n\tprotected readonly toggleAtStart = computed(() => this.accordionView() && this.tabset?.togglePosition() === 'start');\n\n\t/**\n\t * Whether this panel renders as a card: either inside a `<hub-panels\n\t * type=\"card\">` container or standalone (no owning container at all).\n\t */\n\tprotected readonly cardView = computed(() => this.standalone || !this.tabset || this.tabset.isCardView());\n\n\t/**\n\t * Whether this panel renders as a semantic alert: `appearance=\"alert\"` while\n\t * in a card-capable context (standalone or inside a `card` container). In the\n\t * strip / accordion views the alert appearance is ignored.\n\t */\n\tprotected readonly alertView = computed(() => this.appearance() === 'alert' && this.cardView());\n\n\t/**\n\t * Only a `danger` or `warning` alert interrupts a screen reader (`role=\"alert\"`, assertive).\n\t * Any other variant, or none, is advisory and waits its turn (`role=\"status\"`, polite):\n\t * announcing an info note as urgent cuts off whatever the person was listening to.\n\t */\n\tprotected readonly alertRole = computed(() =>\n\t\tthis.variant() === 'danger' || this.variant() === 'warning' ? 'alert' : 'status'\n\t);\n\n\t/**\n\t * Inline accent fed to the alert styles, resolved from the `variant` input so\n\t * ANY colour works. A bareword (a semantic name, a registered accent or a CSS\n\t * named colour) resolves to `var(--hub-sys-color-<variant>, <variant>)` — the\n\t * design-system token with the word itself as the raw fallback; a literal\n\t * (`#hex` / `rgb()` / `oklch()` / `var()`) is passed through unchanged. Returns\n\t * `null` for a neutral alert / non-alert view. The built-in semantic variants\n\t * additionally pick up their exact ds tints through the SCSS `@each`.\n\t */\n\tprotected readonly alertAccent = computed(() => {\n\t\tif (!this.alertView()) {\n\t\t\treturn null;\n\t\t}\n\t\treturn resolveHubAccent(this.variant());\n\t});\n\n\t/**\n\t * Inline accent fed to the card variant tint, resolved from the `variant` input\n\t * exactly like {@link alertAccent}: a bareword becomes\n\t * `var(--hub-sys-color-<variant>, <variant>)` and a literal colour is passed\n\t * through unchanged. Returns `null` for an alert or non-card view, keeping the\n\t * card variant set open with no colour values living in this library.\n\t */\n\tprotected readonly cardAccent = computed(() => {\n\t\tif (!this.cardView() || this.alertView()) {\n\t\t\treturn null;\n\t\t}\n\t\treturn resolveHubAccent(this.variant());\n\t});\n\n\t/** Form value resolved for this panel: the explicit `value` or the panel id. */\n\treadonly formValue = computed(() => (this.value() !== undefined ? this.value() : this.id()));\n\n\t/** `routerLink` normalised to a segments array, or `null` when not routed. */\n\treadonly routerUrl = computed<string[] | null>(() => {\n\t\tconst link = this.routerLink();\n\t\tif (!link) {\n\t\t\treturn null;\n\t\t}\n\t\treturn Array.isArray(link) ? link : [link];\n\t});\n\n\t/** Last activation state seen by the effect — avoids emitting on init. */\n\t#wasActive = false;\n\n\tconstructor() {\n\t\t// A standalone panel (no container, or explicitly `standalone` inside one)\n\t\t// renders as a card and skips registration so it never becomes a hidden tab.\n\t\tif (!this.standalone) {\n\t\t\tthis.tabset?.registerPanel(this);\n\t\t}\n\n\t\t// Mirror `customClass` onto the pane host element.\n\t\teffect((onCleanup) => {\n\t\t\tconst classes = (this.customClass() ?? '')\n\t\t\t\t.split(' ')\n\t\t\t\t.map((cssClass) => cssClass.trim())\n\t\t\t\t.filter((cssClass) => cssClass.length > 0);\n\t\t\tfor (const cssClass of classes) {\n\t\t\t\tthis.#renderer.addClass(this.elementRef.nativeElement, cssClass);\n\t\t\t}\n\t\t\tonCleanup(() => {\n\t\t\t\tfor (const cssClass of classes) {\n\t\t\t\t\tthis.#renderer.removeClass(this.elementRef.nativeElement, cssClass);\n\t\t\t\t}\n\t\t\t});\n\t\t});\n\n\t\t// Activation side effects: emit outputs and enforce single-active-panel\n\t\t// (unless the container allows multiple expanded panels — accordion mode).\n\t\teffect(() => {\n\t\t\tconst isActive = this.active();\n\t\t\tif (isActive && this.disabled()) {\n\t\t\t\tthis.active.set(false);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tif (isActive === this.#wasActive) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tthis.#wasActive = isActive;\n\t\t\tif (isActive) {\n\t\t\t\tthis.selectPanel.emit(this);\n\t\t\t\tif (this.tabset && !this.tabset.allowsMultipleActive()) {\n\t\t\t\t\tfor (const panel of this.tabset.panels()) {\n\t\t\t\t\t\tif (panel !== this) {\n\t\t\t\t\t\t\tpanel.active.set(false);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthis.deselectPanel.emit(this);\n\t\t\t}\n\t\t});\n\t}\n\n\tngOnDestroy(): void {\n\t\tif (!this.standalone) {\n\t\t\tthis.tabset?.removePanel(this, { reselect: false, emit: false, track: false });\n\t\t}\n\t}\n\n\t/** Route path plus query string, or `null` when the panel is not routed. */\n\tgetFullRoute(): string | null {\n\t\tconst route = this.getRoute();\n\t\tif (!route) {\n\t\t\treturn null;\n\t\t}\n\t\tconst queryString = this.getQueryParamsString();\n\t\treturn queryString ? `${route}?${queryString}` : route;\n\t}\n\n\t/** Normalised absolute route path, or `null` when the panel is not routed. */\n\tgetRoute(): string | null {\n\t\tconst routerUrl = this.routerUrl();\n\t\tif (!routerUrl) {\n\t\t\treturn null;\n\t\t}\n\t\tlet route = routerUrl.join('/').replace(/\\/\\/+/g, '/');\n\t\tif (route.charAt(0) === '.') {\n\t\t\troute = route.substring(1);\n\t\t}\n\t\tif (route.charAt(0) !== '/') {\n\t\t\troute = `/${route}`;\n\t\t}\n\t\treturn route;\n\t}\n\n\t/** `queryParams` serialised as `key=value&…`, or `null` when empty. */\n\tgetQueryParamsString(): string | null {\n\t\tconst params = this.queryParams();\n\t\tif (!params || !Object.keys(params).length) {\n\t\t\treturn null;\n\t\t}\n\t\treturn Object.entries(params)\n\t\t\t.map(([key, value]) => `${key}=${value}`)\n\t\t\t.join('&');\n\t}\n\n\t/** Navigates to the panel's route. No-op for non-routed panels. */\n\tnavigate(): void {\n\t\tconst routerUrl = this.routerUrl();\n\t\tif (routerUrl) {\n\t\t\tthis.#router.navigate(routerUrl, { queryParams: this.queryParams() ?? {} });\n\t\t}\n\t}\n\n\t/** Accordion header click — toggles this panel through the container. */\n\tprotected onAccordionHeaderClick(): void {\n\t\tthis.tabset?.togglePanel(this);\n\t}\n\n\t/** Accordion header keyboard navigation, delegated to the container. */\n\tprotected onAccordionHeaderKeydown(event: KeyboardEvent): void {\n\t\tthis.tabset?.onAccordionKeydown(event, this);\n\t}\n\n\t/**\n\t * Removes this panel through the accordion header's ✕ button, handing\n\t * keyboard focus to the closest remaining header afterwards.\n\t */\n\tprotected removeSelf(): void {\n\t\tthis.tabset?.removePanelAndRefocus(this);\n\t}\n}\n","@if (accordionView()) {\n\t<h2 class=\"hub-panels__accordion-header\" [class.hub-panels__accordion-header--expanded]=\"active()\">\n\t\t<button\n\t\t\ttype=\"button\"\n\t\t\tclass=\"hub-panels__accordion-btn\"\n\t\t\t[class.hub-panels__accordion-btn--collapsed]=\"!active()\"\n\t\t\t[id]=\"id() + '-link'\"\n\t\t\t[disabled]=\"disabled() || tabset?.formDisabled()\"\n\t\t\t[attr.aria-expanded]=\"active()\"\n\t\t\t[attr.aria-controls]=\"id()\"\n\t\t\t(click)=\"onAccordionHeaderClick()\"\n\t\t\t(keydown)=\"onAccordionHeaderKeydown($event)\"\n\t\t>\n\t\t\t@if (headingRef(); as headingTemplate) {\n\t\t\t\t<ng-container [ngTemplateOutlet]=\"headingTemplate\" />\n\t\t\t} @else {\n\t\t\t\t{{ heading() }}\n\t\t\t}\n\t\t</button>\n\n\t\t<!-- Row affordances live OUTSIDE the disclosure button: a control nested\n\t\t\t in another control is invalid and unreachable by keyboard. They stay\n\t\t\t visible while the row is collapsed, unlike `hubPanelHeader`. The ✕\n\t\t\t remove control is a real button here for the same reason — focusable,\n\t\t\t keyboard operable and labelled for assistive technologies. -->\n\t\t@if (removable() || headingActionsRef()) {\n\t\t\t<span class=\"hub-panels__accordion-actions\">\n\t\t\t\t@if (headingActionsRef(); as actionsTemplate) {\n\t\t\t\t\t<ng-container [ngTemplateOutlet]=\"actionsTemplate\" />\n\t\t\t\t}\n\t\t\t\t@if (removable()) {\n\t\t\t\t\t<button\n\t\t\t\t\t\ttype=\"button\"\n\t\t\t\t\t\tclass=\"hub-panels__remove-btn\"\n\t\t\t\t\t\t[disabled]=\"disabled() || tabset?.formDisabled()\"\n\t\t\t\t\t\t[attr.aria-label]=\"removeLabel()\"\n\t\t\t\t\t\t(click)=\"removeSelf()\"\n\t\t\t\t\t>\n\t\t\t\t\t\t&times;\n\t\t\t\t\t</button>\n\t\t\t\t}\n\t\t\t</span>\n\t\t}\n\t</h2>\n}\n\n<!-- Projection slots for every view. In the strip views the wrappers are plain\n\t pass-throughs; in the accordion view they become the animated collapse\n\t region. The header/footer `select` slots and the default `<ng-content>` are\n\t all UNCONDITIONAL — never wrapped in `@if` — to avoid the lost-projection\n\t bug that conditional slots cause. Header/footer render in every view; the\n\t `card` view styles them as the card's header and footer bands. -->\n<div\n\tclass=\"hub-panels__panel-collapse\"\n\t[class.hub-panels__accordion-collapse]=\"accordionView()\"\n\t[class.hub-panels__accordion-collapse--collapsed]=\"accordionView() && !active()\"\n\t[attr.role]=\"accordionView() ? 'region' : null\"\n\t[attr.id]=\"accordionView() ? id() : null\"\n\t[attr.aria-labelledby]=\"accordionView() ? id() + '-link' : null\"\n\t[attr.aria-hidden]=\"accordionView() ? !active() : null\"\n\t[attr.inert]=\"accordionView() && !active() ? '' : null\"\n>\n\t<div class=\"hub-panels__panel-region\" [class.hub-panels__accordion-body]=\"accordionView()\">\n\t\t<ng-content select=\"[hubPanelHeader]\" />\n\t\t<div class=\"hub-panels__panel-body\">\n\t\t\t<ng-content />\n\t\t</div>\n\t\t<ng-content select=\"[hubPanelFooter]\" />\n\t</div>\n</div>\n","import { Directive, inject, TemplateRef } from '@angular/core';\n\nimport { HubPanelComponent } from '../components/panel/panel.component';\n\n/**\n * Marks an `<ng-template>` inside a `hub-panel` as that panel's custom header\n * (strip link in `tabs`/`pills` view, disclosure button in `accordion` view),\n * replacing the plain-text `heading` input.\n *\n * @example\n * ```html\n * <hub-panel>\n * <ng-template hubPanelHeading><em>Rich</em> heading</ng-template>\n * Panel content\n * </hub-panel>\n * ```\n */\n@Directive({ selector: '[hubPanelHeading]' })\nexport class HubPanelHeadingDirective {\n\tconstructor() {\n\t\tinject(HubPanelComponent).headingRef.set(inject(TemplateRef));\n\t}\n}\n","import { Directive, inject, TemplateRef } from '@angular/core';\n\nimport { HubPanelComponent } from '../components/panel/panel.component';\n\n/**\n * Marks an `<ng-template>` inside a `hub-panel` as that panel's header\n * **actions** slot, rendered in the `accordion` view as a sibling of the\n * disclosure button — inside the header row, outside the button.\n *\n * This is the slot for row affordances that must stay reachable while the\n * panel is collapsed (edit, delete, a menu). They cannot live in\n * `hubPanelHeading`, which projects *inside* the disclosure `<button>`: a\n * `<button>` nested in another button is invalid HTML and is not reachable\n * with the keyboard. Nor can they live in `hubPanelHeader`, which projects\n * inside the collapse region and therefore disappears when the row closes.\n *\n * Clicks on the actions never toggle the panel — the slot sits outside the\n * button, so no `stopPropagation` is needed. In the `tabs` / `pills` / `card`\n * views the slot renders nothing (those views have no header row of their own).\n *\n * @example\n * ```html\n * <hub-panels type=\"accordion\" multiple>\n * <hub-panel>\n * <ng-template hubPanelHeading>Shipping address</ng-template>\n * <ng-template hubPanelHeadingActions>\n * <button type=\"button\" (click)=\"edit()\">Edit</button>\n * <button type=\"button\" (click)=\"remove()\">Delete</button>\n * </ng-template>\n * Panel content\n * </hub-panel>\n * </hub-panels>\n * ```\n */\n@Directive({ selector: '[hubPanelHeadingActions]' })\nexport class HubPanelHeadingActionsDirective {\n\tconstructor() {\n\t\tinject(HubPanelComponent).headingActionsRef.set(inject(TemplateRef));\n\t}\n}\n","import { Directive } from '@angular/core';\n\n/**\n * Marks an element inside a `hub-panel` as the panel's content **header** band,\n * projected at the top of the panel body (above `<ng-content>`).\n *\n * Unlike `hubPanelHeading` — which renders the navigational label in the\n * `tabs`/`pills` strip or the `accordion` disclosure button — this header lives\n * inside the panel body and renders in **every** view (`tabs`, `pills`,\n * `accordion`, `card`). It is the natural title slot for the `card` format.\n *\n * @example\n * ```html\n * <hub-panel>\n * <div hubPanelHeader>Card title</div>\n * Card content\n * <div hubPanelFooter>Actions</div>\n * </hub-panel>\n * ```\n */\n@Directive({\n\tselector: '[hubPanelHeader]',\n\thost: { class: 'hub-panels__panel-header' }\n})\nexport class HubPanelHeaderDirective {}\n","import { Directive } from '@angular/core';\n\n/**\n * Marks an element inside a `hub-panel` as the panel's content **footer** band,\n * projected at the bottom of the panel body (below `<ng-content>`).\n *\n * Renders in **every** view (`tabs`, `pills`, `accordion`, `card`); it is the\n * natural actions/footer slot for the `card` format.\n *\n * @example\n * ```html\n * <hub-panel>\n * <div hubPanelHeader>Card title</div>\n * Card content\n * <div hubPanelFooter>Actions</div>\n * </hub-panel>\n * ```\n */\n@Directive({\n\tselector: '[hubPanelFooter]',\n\thost: { class: 'hub-panels__panel-footer' }\n})\nexport class HubPanelFooterDirective {}\n","import {\n\tbooleanAttribute,\n\tChangeDetectionStrategy,\n\tComponent,\n\tcomputed,\n\tElementRef,\n\tinject,\n\tinput,\n\tmodel,\n\tViewEncapsulation\n} from '@angular/core';\n\nimport type { HubTabNavAppearance, HubTabNavItem } from './tab-nav.types';\n\n/**\n * Lightweight, value-bound tab strip — the hub `tab-nav` primitive.\n *\n * Where `<hub-panels type=\"tabs\">` couples the strip to projected\n * `<hub-panel>` content (lazy render, accordion / card modes, routing, forms),\n * `<hub-tab-nav>` is a **content-less** controlled strip: it renders an\n * accessible `role=\"tablist\"` of `role=\"tab\"` buttons from a plain `items`\n * array and emits the selected `value` through the two-way `active` model. The\n * consumer owns the view and renders it themselves based on `active()` /\n * `(activeChange)` — a segmented control, a filter switch or a manual\n * tabs-with-external-content layout.\n *\n * It reuses the `<hub-panels>` strip look through the same\n * `--hub-panels-*` theming tokens (picked up automatically when nested in a\n * themed panels subtree, literal fallbacks otherwise) and exposes two\n * strip-local tokens: `--hub-tabs-indicator-color` (the active underline / pill\n * fill) and `--hub-tabs-gap` (the inter-tab gap).\n *\n * Keyboard: arrow keys move focus and activate the neighbour (roving\n * `tabindex`), `Home` / `End` jump to the first / last enabled tab. Disabled\n * tabs are skipped by pointer and keyboard.\n *\n * @example\n * ```html\n * <hub-tab-nav\n * \t[items]=\"[{ value: 'all', label: 'All' }, { value: 'open', label: 'Open' }]\"\n * \t[(active)]=\"filter\"\n * \tappearance=\"pills\"\n * />\n * <!-- consumer renders its own view based on `filter` -->\n * ```\n */\n@Component({\n\tselector: 'hub-tab-nav',\n\texportAs: 'hubTabNav',\n\ttemplateUrl: './tab-nav.component.html',\n\tstyleUrl: './tab-nav.component.scss',\n\t// Library-style global stylesheet: rules stay namespaced under\n\t// `.hub-tab-nav*` and reach the projected `<button>` headers.\n\tencapsulation: ViewEncapsulation.None,\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\thost: {\n\t\tclass: 'hub-tab-nav',\n\t\t'[class.hub-tab-nav--vertical]': 'vertical()'\n\t}\n})\nexport class HubTabNavComponent {\n\treadonly #host = inject<ElementRef<HTMLElement>>(ElementRef);\n\n\t/** The selectable tabs, in render order. */\n\treadonly items = input<HubTabNavItem[]>([]);\n\n\t/** Two-way selected value; `activeChange` fires whenever it changes. */\n\treadonly active = model<unknown>();\n\n\t/** Visual appearance — underlined `'tabs'` (default) or rounded `'pills'`. */\n\treadonly appearance = input<HubTabNavAppearance>('tabs');\n\n\t/** Whether the tabs stretch to share the available width equally. */\n\treadonly justified = input(false, { transform: booleanAttribute });\n\n\t/** Whether the strip stacks vertically instead of in a row. */\n\treadonly vertical = input(false, { transform: booleanAttribute });\n\n\t/** Index of the item whose value matches `active`, or `-1` when none does. */\n\treadonly activeIndex = computed(() => {\n\t\tconst active = this.active();\n\t\treturn this.items().findIndex((item) => item.value === active);\n\t});\n\n\t/** Whether the given item is the active one. */\n\tprotected isActive(item: HubTabNavItem): boolean {\n\t\treturn item.value === this.active();\n\t}\n\n\t/** ARIA id of a tab button — the item's own `id` or a deterministic fallback. */\n\tprotected itemId(item: HubTabNavItem, index: number): string {\n\t\treturn item.id ?? `hub-tab-nav-${index}`;\n\t}\n\n\t/**\n\t * Roving `tabindex` for the tab at `index`: `0` for the active tab (or the\n\t * first enabled tab when none is active), `-1` for the rest — so the strip\n\t * is a single tab stop and arrow keys move within it.\n\t */\n\tprotected tabIndexFor(index: number): number {\n\t\tconst activeIndex = this.activeIndex();\n\t\tif (activeIndex >= 0) {\n\t\t\treturn index === activeIndex ? 0 : -1;\n\t\t}\n\t\treturn index === this.items().findIndex((item) => !item.disabled) ? 0 : -1;\n\t}\n\n\t/**\n\t * Activates a tab on behalf of the user: sets `active` to its value (which\n\t * emits `activeChange`). Disabled tabs and re-selecting the active tab\n\t * no-op.\n\t */\n\tselect(item: HubTabNavItem): void {\n\t\tif (item.disabled || this.isActive(item)) {\n\t\t\treturn;\n\t\t}\n\t\tthis.active.set(item.value);\n\t}\n\n\t/** Keyboard navigation for the strip (arrows / Home / End). */\n\tprotected onKeydown(event: KeyboardEvent, index: number): void {\n\t\tlet target: number;\n\t\tswitch (event.key) {\n\t\t\tcase 'ArrowRight':\n\t\t\tcase 'ArrowDown':\n\t\t\t\ttarget = this.#stepEnabledIndex(index, 1);\n\t\t\t\tbreak;\n\t\t\tcase 'ArrowLeft':\n\t\t\tcase 'ArrowUp':\n\t\t\t\ttarget = this.#stepEnabledIndex(index, -1);\n\t\t\t\tbreak;\n\t\t\tcase 'Home':\n\t\t\t\ttarget = this.items().findIndex((item) => !item.disabled);\n\t\t\t\tbreak;\n\t\t\tcase 'End': {\n\t\t\t\tconst items = this.items();\n\t\t\t\ttarget = items.length - 1 - [...items].reverse().findIndex((item) => !item.disabled);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tdefault:\n\t\t\t\treturn;\n\t\t}\n\t\tif (target < 0) {\n\t\t\treturn;\n\t\t}\n\t\tevent.preventDefault();\n\t\tconst item = this.items()[target];\n\t\tif (item && !item.disabled) {\n\t\t\tthis.active.set(item.value);\n\t\t\tthis.#focusAt(target);\n\t\t}\n\t}\n\n\t/** Next enabled tab index from `index` in `direction`, wrapping around. */\n\t#stepEnabledIndex(index: number, direction: 1 | -1): number {\n\t\tconst items = this.items();\n\t\tconst count = items.length;\n\t\tif (!count) {\n\t\t\treturn -1;\n\t\t}\n\t\tfor (let step = 1; step <= count; step += 1) {\n\t\t\tconst candidate = (((index + direction * step) % count) + count) % count;\n\t\t\tif (!items[candidate].disabled) {\n\t\t\t\treturn candidate;\n\t\t\t}\n\t\t}\n\t\treturn index;\n\t}\n\n\t/** Moves DOM focus to the tab button at `index`. */\n\t#focusAt(index: number): void {\n\t\tconst buttons = this.#host.nativeElement.querySelectorAll<HTMLElement>('.hub-tab-nav__nav-link');\n\t\tbuttons[index]?.focus();\n\t}\n}\n","<ul\n\tclass=\"hub-tab-nav__nav\"\n\trole=\"tablist\"\n\t[attr.aria-orientation]=\"vertical() ? 'vertical' : 'horizontal'\"\n\t[class.hub-tab-nav__nav--tabs]=\"appearance() === 'tabs'\"\n\t[class.hub-tab-nav__nav--pills]=\"appearance() === 'pills'\"\n\t[class.hub-tab-nav__nav--vertical]=\"vertical()\"\n\t[class.hub-tab-nav__nav--justified]=\"justified()\"\n>\n\t@for (item of items(); track item.value; let i = $index) {\n\t\t<li\n\t\t\tclass=\"hub-tab-nav__nav-item\"\n\t\t\t[class.hub-tab-nav__nav-item--active]=\"isActive(item)\"\n\t\t\t[class.hub-tab-nav__nav-item--disabled]=\"!!item.disabled\"\n\t\t>\n\t\t\t<button\n\t\t\t\ttype=\"button\"\n\t\t\t\tclass=\"hub-tab-nav__nav-link\"\n\t\t\t\trole=\"tab\"\n\t\t\t\t[id]=\"itemId(item, i)\"\n\t\t\t\t[class.hub-tab-nav__nav-link--active]=\"isActive(item)\"\n\t\t\t\t[class.hub-tab-nav__nav-link--disabled]=\"!!item.disabled\"\n\t\t\t\t[disabled]=\"!!item.disabled\"\n\t\t\t\t[attr.aria-selected]=\"isActive(item)\"\n\t\t\t\t[attr.tabindex]=\"tabIndexFor(i)\"\n\t\t\t\t(click)=\"select(item)\"\n\t\t\t\t(keydown)=\"onKeydown($event, i)\"\n\t\t\t>\n\t\t\t\t{{ item.label }}\n\t\t\t</button>\n\t\t</li>\n\t}\n</ul>\n","import { afterNextRender, ChangeDetectionStrategy, Component, DestroyRef, ElementRef, inject, signal } from '@angular/core';\n\n/**\n * Layout parent of one or more `<hub-side-panel>` elements.\n *\n * A docked (`side`) panel can only narrow the content if something lays the two out together, so\n * the container is a flex row that holds the page content in its own scrolling area and the\n * panels as direct children. It also measures its own inline size, which is what a panel compares\n * with its `breakpoint` to decide whether it still has room to dock or has to float over the\n * content instead. Measuring the container rather than the viewport keeps that decision right when\n * the container is not full width (a shell with a navigation rail, an embedded demo).\n *\n * A panel declared with a static `position=\"start\"` attribute is projected before the content and\n * every other panel after it, so the DOM order (and therefore the tab order) follows the visual\n * order in the common case. A panel whose `position` is bound is projected after the content and\n * placed visually by CSS `order`.\n *\n * Give the container a block size (`height: 100dvh` in an app shell, a fixed height in a card):\n * the content area scrolls inside it, and an `over` panel spans the container's full height.\n *\n * @example\n * ```html\n * <hub-side-panel-container class=\"app-shell\">\n * \t<main>…the page…</main>\n * \t<hub-side-panel [(open)]=\"assistantOpen\" ariaLabel=\"Assistant\">…</hub-side-panel>\n * </hub-side-panel-container>\n * ```\n */\n@Component({\n\tselector: 'hub-side-panel-container',\n\texportAs: 'hubSidePanelContainer',\n\ttemplateUrl: './side-panel-container.component.html',\n\tstyleUrl: './side-panel-container.component.scss',\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\thost: {\n\t\tclass: 'hub-side-panel-container'\n\t}\n})\nexport class HubSidePanelContainerComponent {\n\treadonly #inlineSize = signal<number | null>(null);\n\n\t/**\n\t * Measured inline size of the container in CSS pixels, or `null` before the first measurement\n\t * and wherever `ResizeObserver` does not exist (server rendering). Panels read it to apply their\n\t * `breakpoint`; `null` means \"assume there is room\", so the server renders the requested mode.\n\t */\n\treadonly inlineSize = this.#inlineSize.asReadonly();\n\n\tconstructor() {\n\t\tconst host = inject<ElementRef<HTMLElement>>(ElementRef).nativeElement;\n\t\tconst destroyRef = inject(DestroyRef);\n\n\t\tafterNextRender(() => {\n\t\t\tif (typeof ResizeObserver === 'undefined') {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t// `borderBoxSize` is logical, so the value stays the inline size in vertical writing\n\t\t\t// modes too; `contentRect.width` is only the fallback for engines that lack it.\n\t\t\tconst observer = new ResizeObserver(([entry]) => {\n\t\t\t\tthis.#inlineSize.set(entry.borderBoxSize?.[0]?.inlineSize ?? entry.contentRect.width);\n\t\t\t});\n\t\t\tobserver.observe(host);\n\t\t\tdestroyRef.onDestroy(() => observer.disconnect());\n\t\t});\n\t}\n}\n","<ng-content select=\"hub-side-panel[position=start]\" />\n<div class=\"hub-side-panel-container__content\"><ng-content /></div>\n<ng-content select=\"hub-side-panel\" />\n","import {\n\tafterNextRender,\n\tbooleanAttribute,\n\tChangeDetectionStrategy,\n\tComponent,\n\tcomputed,\n\tDOCUMENT,\n\teffect,\n\tElementRef,\n\tinject,\n\tInjector,\n\tinput,\n\tmodel,\n\tnumberAttribute,\n\tuntracked\n} from '@angular/core';\n\nimport { HubSidePanelContainerComponent } from './side-panel-container.component';\nimport type { HubSidePanelMode, HubSidePanelPosition, HubSidePanelRole } from './side-panel.types';\n\n/** Elements that can take keyboard focus, in the order a first-focus search should try them. */\nconst TABBABLE =\n\t'a[href], button:not([disabled]), input:not([disabled]):not([type=\"hidden\"]), select:not([disabled]), ' +\n\t'textarea:not([disabled]), [contenteditable=\"true\"], [tabindex]:not([tabindex=\"-1\"])';\n\n/**\n * Non-modal panel docked to one inline edge of a `<hub-side-panel-container>`.\n *\n * `ng-hub-ui-modal` in offcanvas mode is a real dialog: it covers the viewport, locks the body\n * scroll and traps focus, which is right for a task that must be finished before the page is\n * used again and wrong for a companion that lives beside the page (an assistant, an inspector, a\n * detail pane). This panel is that companion: no backdrop, no scroll lock, no focus trap and no\n * `aria-modal`, so the page stays usable while it is open.\n *\n * - `mode=\"side\"` takes its width from the container row, and the content narrows to make room.\n * Below `breakpoint` (measured on the container) it falls back to `over`, because a docked panel\n * on a phone would leave the content a sliver.\n * - `mode=\"over\"` floats over the content edge. Only the strip the panel covers is unusable.\n *\n * Both modes animate the same property: a closed panel keeps its width and sits just beyond the\n * container edge through a negative logical margin, and opening animates that margin to zero. In\n * the docked row that one transition slides the panel in and narrows the content in the same\n * frames; for the floating panel it is a slide. Logical margins keep it right under `dir=\"rtl\"`\n * without a physical transform. `prefers-reduced-motion` turns the transition off.\n *\n * **Content is never destroyed by closing.** Projected content belongs to the consumer's view and\n * lives as long as the `<hub-side-panel>` element does; closing hides it (`visibility: hidden`\n * once the slide ends, and `inert` straight away, so nothing inside can be focused or read while\n * it is shut) and opening shows the same instances again. A chat keeps its thread and its draft.\n * A consumer who wants the content torn down on close wraps it in `@if (panel.open())`.\n *\n * Focus: nothing moves on open unless `autoFocus` is set, in which case the first `[autofocus]`\n * element, else the first tabbable element, else the panel itself takes it. On close, if focus was\n * inside the panel, it goes back to the element that had it when the panel opened, so closing\n * from inside (Escape, a close button) never drops the reader on `<body>`.\n *\n * @example\n * ```html\n * <hub-side-panel-container style=\"height: 100dvh\">\n * \t<main>…the page…</main>\n *\n * \t<hub-side-panel #assistant [(open)]=\"assistantOpen\" ariaLabel=\"Assistant\" autoFocus>\n * \t\t<header hubSidePanelHeader>\n * \t\t\tAssistant <button type=\"button\" (click)=\"assistant.close()\">Close</button>\n * \t\t</header>\n * \t\t<app-chat-thread />\n * \t\t<footer hubSidePanelFooter><textarea autofocus></textarea></footer>\n * \t</hub-side-panel>\n * </hub-side-panel-container>\n * ```\n */\n@Component({\n\tselector: 'hub-side-panel',\n\texportAs: 'hubSidePanel',\n\ttemplateUrl: './side-panel.component.html',\n\tstyleUrl: './side-panel.component.scss',\n\tchangeDetection: ChangeDetectionStrategy.OnPush,\n\thost: {\n\t\tclass: 'hub-side-panel',\n\t\ttabindex: '-1',\n\t\t'[attr.role]': 'role()',\n\t\t'[attr.aria-label]': 'ariaLabel() || null',\n\t\t'[attr.aria-labelledby]': 'ariaLabelledBy() || null',\n\t\t'[attr.inert]': \"open() ? null : ''\",\n\t\t'[class.hub-side-panel--open]': 'open()',\n\t\t'[class.hub-side-panel--side]': \"effectiveMode() === 'side'\",\n\t\t'[class.hub-side-panel--over]': \"effectiveMode() === 'over'\",\n\t\t'[class.hub-side-panel--start]': \"position() === 'start'\",\n\t\t'[class.hub-side-panel--end]': \"position() === 'end'\",\n\t\t'(keydown.escape)': 'onEscape($event)'\n\t}\n})\nexport class HubSidePanelComponent {\n\treadonly #host = inject<ElementRef<HTMLElement>>(ElementRef);\n\treadonly #document = inject(DOCUMENT);\n\treadonly #injector = inject(Injector);\n\treadonly #container = inject(HubSidePanelContainerComponent, { optional: true });\n\n\t/** Element that held focus when the panel last opened, where focus returns on close. */\n\t#returnFocusTo: HTMLElement | null = null;\n\n\t/** Docked beside the content (`'side'`) or floating over its edge (`'over'`). */\n\treadonly mode = input<HubSidePanelMode>('side');\n\n\t/** Inline edge of the container the panel sits on; logical, so `'end'` is the left edge in RTL. */\n\treadonly position = input<HubSidePanelPosition>('end');\n\n\t/** Two-way open state; `openChange` fires whenever it changes, whoever changed it. */\n\treadonly open = model(false);\n\n\t/** Whether Escape pressed inside the panel closes it. Escape pressed elsewhere is never taken. */\n\treadonly closeOnEscape = input(true, { transform: booleanAttribute });\n\n\t/**\n\t * Container inline size in CSS pixels below which a `side` panel renders as `over`. The default\n\t * matches `--hub-sys-breakpoint-md`. `0` keeps the panel docked at any width.\n\t */\n\treadonly breakpoint = input(768, { transform: numberAttribute });\n\n\t/** Whether opening moves focus into the panel. Off by default: a companion should not steal focus. */\n\treadonly autoFocus = input(false, { transform: booleanAttribute });\n\n\t/** Landmark role; use `'region'` when the panel sits inside the page's `<main>`. */\n\treadonly role = input<HubSidePanelRole>('complementary');\n\n\t/** Accessible name of the landmark. Give it this or `ariaLabelledBy`: an unnamed landmark is noise. */\n\treadonly ariaLabel = input<string>();\n\n\t/** Id of the element that names the landmark, typically the heading in the header slot. */\n\treadonly ariaLabelledBy = input<string>();\n\n\t/**\n\t * The mode actually rendered: `mode`, except that a `side` panel whose container is narrower\n\t * than `breakpoint` floats instead. Outside a container, or before the container has measured\n\t * itself, the requested mode is used.\n\t */\n\treadonly effectiveMode = computed<HubSidePanelMode>(() => {\n\t\tif (this.mode() === 'over') {\n\t\t\treturn 'over';\n\t\t}\n\t\tconst inlineSize = this.#container?.inlineSize();\n\t\tconst breakpoint = this.breakpoint();\n\t\treturn inlineSize != null && breakpoint > 0 && inlineSize < breakpoint ? 'over' : 'side';\n\t});\n\n\tconstructor() {\n\t\t// Focus handling reacts to transitions of `open`, not to its value: the first run only\n\t\t// records the initial state, so a panel rendered open never grabs focus on page load.\n\t\tlet previous: boolean | undefined;\n\t\teffect(() => {\n\t\t\tconst open = this.open();\n\t\t\tuntracked(() => {\n\t\t\t\tif (previous !== undefined && previous !== open) {\n\t\t\t\t\tif (open) {\n\t\t\t\t\t\tthis.#onOpened();\n\t\t\t\t\t} else {\n\t\t\t\t\t\tthis.#onClosed();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tprevious = open;\n\t\t\t});\n\t\t});\n\t}\n\n\t/**\n\t * Opens or closes the panel.\n\t *\n\t * @param force - `true` to open, `false` to close; omitted, the state flips.\n\t */\n\ttoggle(force?: boolean): void {\n\t\tthis.open.set(force ?? !this.open());\n\t}\n\n\t/** Closes the panel. Focus, if it was inside, returns to where it was before the panel opened. */\n\tclose(): void {\n\t\tthis.open.set(false);\n\t}\n\n\t/**\n\t * Closes on Escape. A handler inside the panel that already consumed the key (a select closing\n\t * its list calls `preventDefault()`) keeps the panel open; the key is marked consumed here in\n\t * turn, so an ancestor listening for Escape does not close as well.\n\t */\n\tprotected onEscape(event: Event): void {\n\t\tif (!this.open() || !this.closeOnEscape() || event.defaultPrevented) {\n\t\t\treturn;\n\t\t}\n\t\tevent.preventDefault();\n\t\tthis.close();\n\t}\n\n\t/** Remembers where focus was, and moves it inside once the open state has rendered. */\n\t#onOpened(): void {\n\t\tconst active = this.#document.activeElement as HTMLElement | null;\n\t\tthis.#returnFocusTo =\n\t\t\tactive && active !== this.#document.body && !this.#host.nativeElement.contains(active) ? active : null;\n\n\t\tif (this.autoFocus()) {\n\t\t\t// After render, not now: the host is still `inert` until the open state reaches the DOM.\n\t\t\tafterNextRender(() => this.#focusInitial(), { injector: this.#injector });\n\t\t}\n\t}\n\n\t/**\n\t * Hands focus back when it was inside the panel. Checked now, while the element that has focus\n\t * is still inside: once `inert` lands the browser blurs it to `<body>`.\n\t */\n\t#onClosed(): void {\n\t\tconst target = this.#returnFocusTo;\n\t\tthis.#returnFocusTo = null;\n\n\t\tconst active = this.#document.activeElement;\n\t\tif (active && this.#host.nativeElement.contains(active) && target?.isConnected) {\n\t\t\ttarget.focus();\n\t\t}\n\t}\n\n\t/**\n\t * Focuses the first `[autofocus]` element, else the first tabbable one, else the panel. The\n\t * scroll is prevented because the container clips a panel that is still sliding in, and a\n\t * focus-driven scroll would shift the whole row sideways.\n\t */\n\t#focusInitial(): void {\n\t\tif (!this.open()) {\n\t\t\treturn;\n\t\t}\n\t\tconst host = this.#host.nativeElement;\n\t\tconst target = host.querySelector<HTMLElement>('[autofocus]') ?? host.querySelector<HTMLElement>(TABBABLE) ?? host;\n\t\ttarget.focus({ preventScroll: true });\n\t}\n}\n","<div class=\"hub-side-panel__header\"><ng-content select=\"[hubSidePanelHeader]\" /></div>\n<div class=\"hub-side-panel__body\"><ng-content /></div>\n<div class=\"hub-side-panel__footer\"><ng-content select=\"[hubSidePanelFooter]\" /></div>\n","/*\n * Public API Surface of ng-hub-ui-panels\n */\n\nexport { HubPanelHeadingDirective } from './lib/directives/panel-heading.directive';\nexport { HubPanelHeadingActionsDirective } from './lib/directives/panel-heading-actions.directive';\nexport { HubPanelHeaderDirective } from './lib/directives/panel-header.directive';\nexport { HubPanelFooterDirective } from './lib/directives/panel-footer.directive';\nexport { HubPanelComponent } from './lib/components/panel/panel.component';\nexport { HubPanelsComponent } from './lib/components/panels/panels.component';\nexport { HubTabNavComponent } from './lib/components/tab-nav/tab-nav.component';\nexport { HubSidePanelContainerComponent } from './lib/components/side-panel/side-panel-container.component';\nexport { HubSidePanelComponent } from './lib/components/side-panel/side-panel.component';\nexport { HubPanelsConfig } from './lib/services/panels-config.service';\nexport type {\n\tHubPanelAppearance,\n\tHubPanelsTogglePosition,\n\tHubPanelVariant,\n\tPanelChangeEvent,\n\tPanelsType\n} from './lib/models/panels.types';\nexport type { HubTabNavAppearance, HubTabNavItem } from './lib/components/tab-nav/tab-nav.types';\nexport type { HubSidePanelMode, HubSidePanelPosition, HubSidePanelRole } from './lib/components/side-panel/side-panel.types';\n\n// ─── Deprecated aliases ───────────────────────────────────────────────────────\n// Every class in the family carries the `Hub` prefix, so a consumer importing several\n// packages into one file cannot end up with two `PanelComponent`s. The classes behind\n// these aliases are unchanged; only the exported names move.\n\n/** @deprecated Renamed to `HubPanelHeadingDirective`, and removed under this name in **23.0.0**. */\nexport { HubPanelHeadingDirective as PanelHeadingDirective } from './lib/directives/panel-heading.directive';\n/** @deprecated Renamed to `HubPanelHeadingActionsDirective`, and removed under this name in **23.0.0**. */\nexport { HubPanelHeadingActionsDirective as PanelHeadingActionsDirective } from './lib/directives/panel-heading-actions.directive';\n/** @deprecated Renamed to `HubPanelHeaderDirective`, and removed under this name in **23.0.0**. */\nexport { HubPanelHeaderDirective as PanelHeaderDirective } from './lib/directives/panel-header.directive';\n/** @deprecated Renamed to `HubPanelFooterDirective`, and removed under this name in **23.0.0**. */\nexport { HubPanelFooterDirective as PanelFooterDirective } from './lib/directives/panel-footer.directive';\n/** @deprecated Renamed to `HubPanelComponent`, and removed under this name in **23.0.0**. */\nexport { HubPanelComponent as PanelComponent } from './lib/components/panel/panel.component';\n/** @deprecated Renamed to `HubPanelsComponent`, and removed under this name in **23.0.0**. */\nexport { HubPanelsComponent as PanelsComponent } from './lib/components/panels/panels.component';\n/** @deprecated Renamed to `HubPanelsConfig`, and removed under this name in **23.0.0**. */\nexport { HubPanelsConfig as PanelsConfig } from './lib/services/panels-config.service';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "ng-hub-ui-panels",
3
- "version": "22.17.0",
3
+ "version": "22.18.0",
4
4
  "license": "MIT",
5
5
  "description": "A versatile, accessible content-panels container for Angular with four visualizations (tabs, pills, accordion, card), standalone cards, content header/footer slots, routing, reactive forms and keyboard navigation. Part of the ng-hub-ui family.",
6
6
  "author": "Carlos Morcillo Fernández <carlos.morcillo@me.com> (https://www.carlosmorcillo.com)",
@@ -495,6 +495,12 @@ declare class HubPanelComponent implements OnDestroy {
495
495
  * strip / accordion views the alert appearance is ignored.
496
496
  */
497
497
  protected readonly alertView: _angular_core.Signal<boolean>;
498
+ /**
499
+ * Only a `danger` or `warning` alert interrupts a screen reader (`role="alert"`, assertive).
500
+ * Any other variant, or none, is advisory and waits its turn (`role="status"`, polite):
501
+ * announcing an info note as urgent cuts off whatever the person was listening to.
502
+ */
503
+ protected readonly alertRole: _angular_core.Signal<"alert" | "status">;
498
504
  /**
499
505
  * Inline accent fed to the alert styles, resolved from the `variant` input so
500
506
  * ANY colour works. A bareword (a semantic name, a registered accent or a CSS