@ixfx/components 0.11.7 → 0.11.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (104) hide show
  1. package/bundle/index.d.ts +165 -2
  2. package/bundle/index.d.ts.map +1 -1
  3. package/bundle/index.js +1160 -164
  4. package/bundle/index.js.map +1 -1
  5. package/dist/ac-text.d.ts +1 -1
  6. package/dist/{ac-token--_vCHXWw.d.ts → ac-token-TCLAZeVg.d.ts} +2 -2
  7. package/dist/{ac-token--_vCHXWw.d.ts.map → ac-token-TCLAZeVg.d.ts.map} +1 -1
  8. package/dist/ac-token.d.ts +1 -1
  9. package/dist/colour-picker.d.ts +1 -1
  10. package/dist/crumbs.d.ts +1 -1
  11. package/dist/crumbs.js +1 -1
  12. package/dist/{data-grid-C6EjCe5O.d.ts → data-grid-Oiyt5qbA.d.ts} +4 -4
  13. package/dist/{data-grid-C6EjCe5O.d.ts.map → data-grid-Oiyt5qbA.d.ts.map} +1 -1
  14. package/dist/data-grid.d.ts +1 -1
  15. package/dist/data-grid.js +1 -1
  16. package/dist/{detail-list-CgkOHYOa.d.ts → detail-list-B0waVNeS.d.ts} +37 -6
  17. package/dist/detail-list-B0waVNeS.d.ts.map +1 -0
  18. package/dist/detail-list.d.ts +4 -3
  19. package/dist/detail-list.js +271 -6
  20. package/dist/detail-list.js.map +1 -1
  21. package/dist/{grid-list-3fGhdaFA.js → grid-list-Bwaf61is.js} +659 -158
  22. package/dist/grid-list-Bwaf61is.js.map +1 -0
  23. package/dist/{grid-list-D6AfWfwn.d.ts → grid-list-bzKuNTtu.d.ts} +43 -2
  24. package/dist/grid-list-bzKuNTtu.d.ts.map +1 -0
  25. package/dist/grid-list.d.ts +3 -2
  26. package/dist/grid-list.js +2 -1
  27. package/dist/{grouped-item-lister-DETte0Dh.d.ts → grouped-item-lister-Bhyo-dkH.d.ts} +2 -2
  28. package/dist/{grouped-item-lister-DETte0Dh.d.ts.map → grouped-item-lister-Bhyo-dkH.d.ts.map} +1 -1
  29. package/dist/grouped-item-lister.d.ts +1 -1
  30. package/dist/grouping-CUKgmkMm.d.ts +63 -0
  31. package/dist/grouping-CUKgmkMm.d.ts.map +1 -0
  32. package/dist/grouping-RYPnHkrS.js +53 -0
  33. package/dist/grouping-RYPnHkrS.js.map +1 -0
  34. package/dist/{icon-CDGprSdE.d.ts → icon-DR_3rSyZ.d.ts} +2 -2
  35. package/dist/icon-DR_3rSyZ.d.ts.map +1 -0
  36. package/dist/icons.d.ts +2 -2
  37. package/dist/incr-search.d.ts +1 -1
  38. package/dist/{index-tq6f8007.d.ts → index-BOUaDIW-.d.ts} +2 -2
  39. package/dist/{index-tq6f8007.d.ts.map → index-BOUaDIW-.d.ts.map} +1 -1
  40. package/dist/{index-CoqtMSd9.d.ts → index-BUB5SICW.d.ts} +2 -2
  41. package/dist/{index-CoqtMSd9.d.ts.map → index-BUB5SICW.d.ts.map} +1 -1
  42. package/dist/{index-CMsmZ6Or.d.ts → index-BvxHQUME.d.ts} +2 -2
  43. package/dist/{index-CMsmZ6Or.d.ts.map → index-BvxHQUME.d.ts.map} +1 -1
  44. package/dist/{index-UvnoZUAo.d.ts → index-CJ5fshD3.d.ts} +2 -2
  45. package/dist/{index-UvnoZUAo.d.ts.map → index-CJ5fshD3.d.ts.map} +1 -1
  46. package/dist/{index-DyTSt9OK.d.ts → index-CW2QL33o.d.ts} +3 -3
  47. package/dist/{index-DyTSt9OK.d.ts.map → index-CW2QL33o.d.ts.map} +1 -1
  48. package/dist/{index-CYndvTWH.d.ts → index-garxxqgV.d.ts} +2 -2
  49. package/dist/{index-CYndvTWH.d.ts.map → index-garxxqgV.d.ts.map} +1 -1
  50. package/dist/index.d.ts +20 -18
  51. package/dist/index.d.ts.map +1 -1
  52. package/dist/index.js +7 -5
  53. package/dist/index.js.map +1 -1
  54. package/dist/{labelled-input-base-DiTme1JO.d.ts → labelled-input-base-Dp_9KP0G.d.ts} +2 -2
  55. package/dist/{labelled-input-base-DiTme1JO.d.ts.map → labelled-input-base-Dp_9KP0G.d.ts.map} +1 -1
  56. package/dist/labelled-radial-input.d.ts +2 -2
  57. package/dist/labelled-radial-input.d.ts.map +1 -1
  58. package/dist/labelled-range-input.d.ts +1 -1
  59. package/dist/labelled-slider-input.d.ts +1 -1
  60. package/dist/list-group-header.d.ts +26 -0
  61. package/dist/list-group-header.d.ts.map +1 -0
  62. package/dist/list-group-header.js +122 -0
  63. package/dist/list-group-header.js.map +1 -0
  64. package/dist/{list-selection-controller-SA4piSBi.js → list-selection-controller-BeE70lbB.js} +42 -4
  65. package/dist/list-selection-controller-BeE70lbB.js.map +1 -0
  66. package/dist/{menu-CsBUyUuS.js → menu-DaAlsyhf.js} +2 -2
  67. package/dist/{menu-CsBUyUuS.js.map → menu-DaAlsyhf.js.map} +1 -1
  68. package/dist/{menu-item-BbgdcwBX.d.ts → menu-item-B0zqw2xp.d.ts} +14 -2
  69. package/dist/menu-item-B0zqw2xp.d.ts.map +1 -0
  70. package/dist/{menu-item-CfndBGO8.js → menu-item-CDPFgaSF.js} +32 -1
  71. package/dist/menu-item-CDPFgaSF.js.map +1 -0
  72. package/dist/menu.d.ts +2 -2
  73. package/dist/menu.js +2 -2
  74. package/dist/miller.d.ts +1 -1
  75. package/dist/panel.d.ts +1 -1
  76. package/dist/{split-layout-JK3xWVX2.d.ts → split-layout-C5SYbDrq.d.ts} +2 -2
  77. package/dist/{split-layout-JK3xWVX2.d.ts.map → split-layout-C5SYbDrq.d.ts.map} +1 -1
  78. package/dist/split-layout.d.ts +1 -1
  79. package/dist/{tab-list-pqfKaVAE.d.ts → tab-list-v8mKX7Fu.d.ts} +2 -2
  80. package/dist/{tab-list-pqfKaVAE.d.ts.map → tab-list-v8mKX7Fu.d.ts.map} +1 -1
  81. package/dist/tabs.d.ts +1 -1
  82. package/dist/{titlebar-Tqu-VvMU.d.ts → titlebar-B5zSTZnF.d.ts} +2 -2
  83. package/dist/{titlebar-Tqu-VvMU.d.ts.map → titlebar-B5zSTZnF.d.ts.map} +1 -1
  84. package/dist/titlebar.d.ts +1 -1
  85. package/dist/tree.d.ts +1 -1
  86. package/dist/{vertical-list-DTp-UIUE.d.ts → vertical-list-DheZSEmB.d.ts} +2 -2
  87. package/dist/{vertical-list-DTp-UIUE.d.ts.map → vertical-list-DheZSEmB.d.ts.map} +1 -1
  88. package/dist/vertical-list.d.ts +1 -1
  89. package/dist/vertical-list.js +1 -1
  90. package/docs-user/README.md +1 -0
  91. package/docs-user/detail-list.md +28 -0
  92. package/docs-user/grid-list.md +35 -3
  93. package/docs-user/index.json +7 -2
  94. package/docs-user/list-group-header.md +14 -0
  95. package/docs-user/llms.txt +1 -0
  96. package/llms.txt +1 -0
  97. package/package.json +5 -1
  98. package/dist/detail-list-CgkOHYOa.d.ts.map +0 -1
  99. package/dist/grid-list-3fGhdaFA.js.map +0 -1
  100. package/dist/grid-list-D6AfWfwn.d.ts.map +0 -1
  101. package/dist/icon-CDGprSdE.d.ts.map +0 -1
  102. package/dist/list-selection-controller-SA4piSBi.js.map +0 -1
  103. package/dist/menu-item-BbgdcwBX.d.ts.map +0 -1
  104. package/dist/menu-item-CfndBGO8.js.map +0 -1
@@ -33,9 +33,9 @@ declare abstract class LabelledInputBase extends LitElement {
33
33
  value: number;
34
34
  }>) => void;
35
35
  protected _syncValue(v: number): void;
36
- protected _renderEditableNumber(): typeof nothing | import("lit").TemplateResult<1>;
36
+ protected _renderEditableNumber(): import("lit").TemplateResult<1> | typeof nothing;
37
37
  updated(changedProperties: Map<string, unknown>): void;
38
38
  }
39
39
  //#endregion
40
40
  export { LabelledInputBase as t };
41
- //# sourceMappingURL=labelled-input-base-DiTme1JO.d.ts.map
41
+ //# sourceMappingURL=labelled-input-base-Dp_9KP0G.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"labelled-input-base-DiTme1JO.d.ts","names":[],"sources":["../src/mixins/labelled-input-base.ts"],"mappings":";;uBAIsB,0BAA0B;EAClC;EAEgB;EACA;EACA;EACA;EACA;EAC+B;EAEI;EACC;EAEjB;YAE5B;YACA;YACA,cAAc;UAEzB;UACA;oBAEU;MAEd,cAAc;MAId,UAAU,SAAS;gBAIT;EAIL;EAMA;YAMC,cAAc,SAAS;YAcvB,sBAAuB,GAAG;IAAc;;YAYxC,qBAAsB,GAAG;IAAc;;YAcvC,qBAAsB,GAAG;IAAc;;YAavC,WAAW;YAYX,gCAAqB,wBAAA;EAuBtB,QAAQ,mBAAmB"}
1
+ {"version":3,"file":"labelled-input-base-Dp_9KP0G.d.ts","names":[],"sources":["../src/mixins/labelled-input-base.ts"],"mappings":";;uBAIsB,0BAA0B;EAClC;EAEgB;EACA;EACA;EACA;EACA;EAC+B;EAEI;EACC;EAEjB;YAE5B;YACA;YACA,cAAc;UAEzB;UACA;oBAEU;MAEd,cAAc;MAId,UAAU,SAAS;gBAIT;EAIL;EAMA;YAMC,cAAc,SAAS;YAcvB,sBAAuB,GAAG;IAAc;;YAYxC,qBAAsB,GAAG;IAAc;;YAcvC,qBAAsB,GAAG;IAAc;;YAavC,WAAW;YAYX,uCAAqB,2BAAA;EAuBtB,QAAQ,mBAAmB"}
@@ -1,4 +1,4 @@
1
- import { t as LabelledInputBase } from "./labelled-input-base-DiTme1JO.js";
1
+ import { t as LabelledInputBase } from "./labelled-input-base-Dp_9KP0G.js";
2
2
  import { i as MarkerStyle, l as ValueMode } from "./radial-input-DU6t2hYO.js";
3
3
  import { CSSResultGroup, nothing } from "lit";
4
4
  //#region src/labelled-radial-input/labelled-radial-input.d.ts
@@ -19,7 +19,7 @@ declare class LabelledRadialInput extends LabelledInputBase {
19
19
  private _isWide;
20
20
  private _getEffectivePrecision;
21
21
  protected _handleResize(entries: ResizeObserverEntry[]): void;
22
- protected _renderEditableNumber(): typeof nothing | import("lit").TemplateResult<1>;
22
+ protected _renderEditableNumber(): import("lit").TemplateResult<1> | typeof nothing;
23
23
  render(): import("lit").TemplateResult<1>;
24
24
  private _getTooltipValue;
25
25
  static styles: CSSResultGroup;
@@ -1 +1 @@
1
- {"version":3,"file":"labelled-radial-input.d.ts","names":[],"sources":["../src/labelled-radial-input/labelled-radial-input.ts"],"mappings":";;;;cA0Da,4BAA4B;WAC9B;EAGA;EACA;EAEmB;EACA;EAC2B,aAAa;EACvC;EACwB,WAAW;EACnC;EACA;EAEoC;;EAGpC;UAEZ;UAIT;YAeW,cAAc,SAAS;YAMvB,gCAAqB,wBAAA;EA0B/B,wBAAM;UA6BP;SAYD,QAAQ;;QA0ET;YACI;IACR,8BAA8B"}
1
+ {"version":3,"file":"labelled-radial-input.d.ts","names":[],"sources":["../src/labelled-radial-input/labelled-radial-input.ts"],"mappings":";;;;cA0Da,4BAA4B;WAC9B;EAGA;EACA;EAEmB;EACA;EAC2B,aAAa;EACvC;EACwB,WAAW;EACnC;EACA;EAEoC;;EAGpC;UAEZ;UAIT;YAeW,cAAc,SAAS;YAMvB,uCAAqB,2BAAA;EA0B/B,wBAAM;UA6BP;SAYD,QAAQ;;QA0ET;YACI;IACR,8BAA8B"}
@@ -1,2 +1,2 @@
1
- import { t as LabelledRangeInput } from "./index-CoqtMSd9.js";
1
+ import { t as LabelledRangeInput } from "./index-BUB5SICW.js";
2
2
  export { LabelledRangeInput };
@@ -1,2 +1,2 @@
1
- import { t as LabelledSliderInput } from "./index-UvnoZUAo.js";
1
+ import { t as LabelledSliderInput } from "./index-CJ5fshD3.js";
2
2
  export { LabelledSliderInput };
@@ -0,0 +1,26 @@
1
+ import "./icon-DR_3rSyZ.js";
2
+ import { LitElement } from "lit";
3
+ //#region src/list-group-header/list-group-header.d.ts
4
+ /**
5
+ * Collapsible group header used by `ixfx-grid-list` and `ixfx-detail-list`.
6
+ * Look matches the group rows of `ixfx-data-grid`: caret, bold label, muted
7
+ * count, and a hairline divider. The host list owns the click handling.
8
+ */
9
+ declare class ListGroupHeaderElement extends LitElement {
10
+ static styles: import("lit").CSSResult;
11
+ label: string;
12
+ count: number;
13
+ collapsed: boolean;
14
+ orientation: `horizontal` | `vertical`;
15
+ connectedCallback(): void;
16
+ protected willUpdate(): void;
17
+ protected render(): import("lit").TemplateResult<1>;
18
+ }
19
+ declare global {
20
+ interface HTMLElementTagNameMap {
21
+ 'ixfx-list-group-header': ListGroupHeaderElement;
22
+ }
23
+ }
24
+ //#endregion
25
+ export { ListGroupHeaderElement };
26
+ //# sourceMappingURL=list-group-header.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list-group-header.d.ts","names":[],"sources":["../src/list-group-header/list-group-header.ts"],"mappings":";;;;;;;;cAWa,+BAA+B;SAC1B,sBAAM;EAuEtB;EAGA;EAGA;EAGA;EAES;YAKU;YAKA,wBAAM;;QAUnB;YACI;IACR,0BAA0B"}
@@ -0,0 +1,122 @@
1
+ import { n as safeCustomElement, t as __decorate } from "./decorate-VRK8rslU.js";
2
+ import "./icon-1gpwtPx8.js";
3
+ import { LitElement, css, html } from "lit";
4
+ import { property } from "lit/decorators.js";
5
+ //#region src/list-group-header/list-group-header.ts
6
+ let ListGroupHeaderElement = class ListGroupHeaderElement extends LitElement {
7
+ constructor(..._args) {
8
+ super(..._args);
9
+ this.label = ``;
10
+ this.count = 0;
11
+ this.collapsed = false;
12
+ this.orientation = `horizontal`;
13
+ }
14
+ static {
15
+ this.styles = css`
16
+ :host {
17
+ --_height: var(--list-group-header-height, 28px);
18
+ --_border: var(--list-group-header-border, var(--border));
19
+
20
+ display: flex;
21
+ align-items: center;
22
+ gap: var(--space-s);
23
+ box-sizing: border-box;
24
+ min-height: var(--_height);
25
+ padding: 0 var(--space-s);
26
+ background: transparent;
27
+ color: var(--list-group-header-text, var(--surface-3-text));
28
+ border-bottom: 1px solid var(--_border);
29
+ font-weight: 600;
30
+ cursor: pointer;
31
+ user-select: none;
32
+ }
33
+
34
+ .caret {
35
+ display: inline-flex;
36
+ transition: transform 0.15s;
37
+ }
38
+
39
+ :host([collapsed]) .caret {
40
+ transform: rotate(-90deg);
41
+ }
42
+
43
+ .count {
44
+ opacity: 0.6;
45
+ font-weight: 400;
46
+ font-size: 0.9em;
47
+ }
48
+
49
+ .label {
50
+ overflow: hidden;
51
+ text-overflow: ellipsis;
52
+ white-space: nowrap;
53
+ min-width: 0;
54
+ }
55
+
56
+ .divider {
57
+ flex: 1;
58
+ height: 1px;
59
+ background: var(--_border);
60
+ margin-left: var(--space-s);
61
+ }
62
+
63
+ /* Single-row (grid-list \`row\` orientation) layout: a narrow column cell. */
64
+ :host([orientation="vertical"]) {
65
+ flex-direction: column;
66
+ justify-content: flex-start;
67
+ padding: var(--space-s) 0;
68
+ border-bottom: 0;
69
+ border-right: 1px solid var(--_border);
70
+ min-height: 0;
71
+ }
72
+
73
+ :host([orientation="vertical"]) .divider {
74
+ width: 1px;
75
+ height: auto;
76
+ margin-left: 0;
77
+ margin-top: var(--space-s);
78
+ }
79
+
80
+ @media (prefers-reduced-motion: reduce) {
81
+ .caret { transition: none; }
82
+ }
83
+ `;
84
+ }
85
+ connectedCallback() {
86
+ super.connectedCallback();
87
+ this.setAttribute(`role`, `button`);
88
+ }
89
+ willUpdate() {
90
+ this.setAttribute(`aria-expanded`, this.collapsed ? `false` : `true`);
91
+ this.setAttribute(`aria-label`, `${this.label}, ${this.count} ${this.count === 1 ? `item` : `items`}`);
92
+ }
93
+ render() {
94
+ return html`
95
+ <span class="caret"><ixfx-icon name="chevron-down" size="12"></ixfx-icon></span>
96
+ <span class="label" part="label">${this.label}</span>
97
+ <span class="count" part="count">(${this.count})</span>
98
+ <span class="divider" part="divider"></span>
99
+ `;
100
+ }
101
+ };
102
+ __decorate([property({
103
+ type: String,
104
+ reflect: true
105
+ })], ListGroupHeaderElement.prototype, "label", void 0);
106
+ __decorate([property({
107
+ type: Number,
108
+ reflect: true
109
+ })], ListGroupHeaderElement.prototype, "count", void 0);
110
+ __decorate([property({
111
+ type: Boolean,
112
+ reflect: true
113
+ })], ListGroupHeaderElement.prototype, "collapsed", void 0);
114
+ __decorate([property({
115
+ type: String,
116
+ reflect: true
117
+ })], ListGroupHeaderElement.prototype, "orientation", void 0);
118
+ ListGroupHeaderElement = __decorate([safeCustomElement(`ixfx-list-group-header`)], ListGroupHeaderElement);
119
+ //#endregion
120
+ export { ListGroupHeaderElement };
121
+
122
+ //# sourceMappingURL=list-group-header.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list-group-header.js","names":["customElement"],"sources":["../src/list-group-header/list-group-header.ts"],"sourcesContent":["import { css, html, LitElement } from 'lit';\nimport { property } from 'lit/decorators.js';\nimport { safeCustomElement as customElement } from '../util/custom-elements.js';\nimport '../icons/icon.js';\n\n/**\n * Collapsible group header used by `ixfx-grid-list` and `ixfx-detail-list`.\n * Look matches the group rows of `ixfx-data-grid`: caret, bold label, muted\n * count, and a hairline divider. The host list owns the click handling.\n */\n@customElement(`ixfx-list-group-header`)\nexport class ListGroupHeaderElement extends LitElement {\n static override styles = css`\n :host {\n --_height: var(--list-group-header-height, 28px);\n --_border: var(--list-group-header-border, var(--border));\n\n display: flex;\n align-items: center;\n gap: var(--space-s);\n box-sizing: border-box;\n min-height: var(--_height);\n padding: 0 var(--space-s);\n background: transparent;\n color: var(--list-group-header-text, var(--surface-3-text));\n border-bottom: 1px solid var(--_border);\n font-weight: 600;\n cursor: pointer;\n user-select: none;\n }\n\n .caret {\n display: inline-flex;\n transition: transform 0.15s;\n }\n\n :host([collapsed]) .caret {\n transform: rotate(-90deg);\n }\n\n .count {\n opacity: 0.6;\n font-weight: 400;\n font-size: 0.9em;\n }\n\n .label {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n min-width: 0;\n }\n\n .divider {\n flex: 1;\n height: 1px;\n background: var(--_border);\n margin-left: var(--space-s);\n }\n\n /* Single-row (grid-list \\`row\\` orientation) layout: a narrow column cell. */\n :host([orientation=\"vertical\"]) {\n flex-direction: column;\n justify-content: flex-start;\n padding: var(--space-s) 0;\n border-bottom: 0;\n border-right: 1px solid var(--_border);\n min-height: 0;\n }\n\n :host([orientation=\"vertical\"]) .divider {\n width: 1px;\n height: auto;\n margin-left: 0;\n margin-top: var(--space-s);\n }\n\n @media (prefers-reduced-motion: reduce) {\n .caret { transition: none; }\n }\n `;\n\n @property({ type: String, reflect: true })\n label = ``;\n\n @property({ type: Number, reflect: true })\n count = 0;\n\n @property({ type: Boolean, reflect: true })\n collapsed = false;\n\n @property({ type: String, reflect: true })\n orientation: `horizontal` | `vertical` = `horizontal`;\n\n override connectedCallback(): void {\n super.connectedCallback();\n this.setAttribute(`role`, `button`);\n }\n\n protected override willUpdate(): void {\n this.setAttribute(`aria-expanded`, this.collapsed ? `false` : `true`);\n this.setAttribute(`aria-label`, `${this.label}, ${this.count} ${this.count === 1 ? `item` : `items`}`);\n }\n\n protected override render() {\n return html`\n <span class=\"caret\"><ixfx-icon name=\"chevron-down\" size=\"12\"></ixfx-icon></span>\n <span class=\"label\" part=\"label\">${this.label}</span>\n <span class=\"count\" part=\"count\">(${this.count})</span>\n <span class=\"divider\" part=\"divider\"></span>\n `;\n }\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'ixfx-list-group-header': ListGroupHeaderElement;\n }\n}\n"],"mappings":";;;;;AAWO,IAAM,yBAAN,MAAM,+BAA+B,WAAW;;;EAwE7C,KAAA,QAAA;EAGA,KAAA,QAAA;EAGI,KAAA,YAAA;EAG6B,KAAA,cAAA;;;EAhFhB,KAAA,SAAA,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAkF5B,oBAAmC;EACjC,MAAM,kBAAkB;EACxB,KAAK,aAAa,QAAQ,QAAQ;CACpC;CAEA,aAAsC;EACpC,KAAK,aAAa,iBAAiB,KAAK,YAAY,UAAU,MAAM;EACpE,KAAK,aAAa,cAAc,GAAG,KAAK,MAAM,IAAI,KAAK,MAAM,GAAG,KAAK,UAAU,IAAI,SAAS,SAAS;CACvG;CAEA,SAA4B;EAC1B,OAAO,IAAI;;yCAE0B,KAAK,MAAM;0CACV,KAAK,MAAM;;;CAGnD;AACF;AA9BG,WAAA,CAAA,SAAS;CAAE,MAAM;CAAQ,SAAS;AAAK,CAAC,CAAA,GAAA,uBAAA,WAAA,SAAA,KAAA,CAAA;AAGxC,WAAA,CAAA,SAAS;CAAE,MAAM;CAAQ,SAAS;AAAK,CAAC,CAAA,GAAA,uBAAA,WAAA,SAAA,KAAA,CAAA;AAGxC,WAAA,CAAA,SAAS;CAAE,MAAM;CAAS,SAAS;AAAK,CAAC,CAAA,GAAA,uBAAA,WAAA,aAAA,KAAA,CAAA;AAGzC,WAAA,CAAA,SAAS;CAAE,MAAM;CAAQ,SAAS;AAAK,CAAC,CAAA,GAAA,uBAAA,WAAA,eAAA,KAAA,CAAA;AAjF1CA,yBAAAA,WAAAA,CAAAA,kBAAc,wBAAwB,CAAA,GAAA,sBAAA"}
@@ -381,6 +381,10 @@ var ListSelectionController = class {
381
381
  if (next.has(item)) next.delete(item);
382
382
  else {
383
383
  if (!this.canSelectMultiple()) next.clear();
384
+ if (this.#clamped()) {
385
+ const g = this.#groupOf(item);
386
+ for (const other of [...next]) if (this.#groupOf(other) !== g) next.delete(other);
387
+ }
384
388
  next.add(item);
385
389
  }
386
390
  this.#apply(next);
@@ -399,6 +403,22 @@ var ListSelectionController = class {
399
403
  this.replace(item);
400
404
  return;
401
405
  }
406
+ if (this.#clamped()) {
407
+ const group = this.#groupOf(this.#anchor);
408
+ if (group !== this.#groupOf(item)) {
409
+ this.replace(item);
410
+ return;
411
+ }
412
+ const inGroup = ordered.filter((t) => this.#groupOf(t) === group);
413
+ const a = inGroup.indexOf(this.#anchor);
414
+ const b = inGroup.indexOf(item);
415
+ if (a === -1 || b === -1) {
416
+ this.replace(item);
417
+ return;
418
+ }
419
+ this.#apply(new Set(inGroup.slice(Math.min(a, b), Math.max(a, b) + 1).filter((t) => this.#config.isSelectable(t))));
420
+ return;
421
+ }
402
422
  const start = Math.min(anchorIdx, targetIdx);
403
423
  const end = Math.max(anchorIdx, targetIdx);
404
424
  this.#apply(new Set(ordered.slice(start, end + 1).filter((t) => this.#config.isSelectable(t))));
@@ -410,8 +430,12 @@ var ListSelectionController = class {
410
430
  }
411
431
  /** Select every ordered item that passes `isSelectable`. */
412
432
  selectAll() {
413
- const ordered = this.#config.getOrderedItems();
433
+ let ordered = this.#config.getOrderedItems();
414
434
  if (ordered.length === 0) return;
435
+ if (this.#clamped()) {
436
+ const group = (this.#anchor === void 0 ? null : this.#groupOf(this.#anchor)) ?? this.#config.getFallbackGroupKey?.() ?? null;
437
+ if (group !== null) ordered = ordered.filter((t) => this.#groupOf(t) === group);
438
+ }
415
439
  const next = new Set(ordered.filter((t) => this.#config.isSelectable(t)));
416
440
  if (next.size === 0) return;
417
441
  this.#apply(next);
@@ -423,7 +447,7 @@ var ListSelectionController = class {
423
447
  selectMany(items) {
424
448
  const { selectionMode } = this.#config.getModes();
425
449
  if (selectionMode !== `multiple`) throw new Error(`selectMany requires selectionMode="multiple" (current: "${selectionMode}")`);
426
- const next = new Set([...items].filter((t) => this.#config.isSelectable(t)));
450
+ const next = this.#clampToFirstGroup(new Set([...items].filter((t) => this.#config.isSelectable(t))));
427
451
  if (next.size === 0) return;
428
452
  this.#anchor = [...next].at(-1);
429
453
  this.#apply(next);
@@ -448,7 +472,7 @@ var ListSelectionController = class {
448
472
  */
449
473
  applyDragSelection(items) {
450
474
  if (!this.canDragSelect()) return;
451
- const next = new Set([...items].filter((t) => this.#config.isSelectable(t)));
475
+ const next = this.#clampToFirstGroup(new Set([...items].filter((t) => this.#config.isSelectable(t))));
452
476
  if (next.size === 0 && this.#selected.size === 0) return;
453
477
  this.#anchor = [...next].at(-1);
454
478
  this.#apply(next);
@@ -577,6 +601,20 @@ var ListSelectionController = class {
577
601
  this.#selected = new Set(items);
578
602
  this.#anchor = anchor;
579
603
  }
604
+ /** Whether gestures must stay inside one group. */
605
+ #clamped() {
606
+ return this.#config.getGroupKey !== void 0 && !(this.#config.crossGroupSelection?.() ?? false);
607
+ }
608
+ #groupOf(item) {
609
+ return this.#config.getGroupKey?.(item) ?? null;
610
+ }
611
+ /** Keep only items in the group of the first item (in display order) when clamped. */
612
+ #clampToFirstGroup(items) {
613
+ if (!this.#clamped() || items.size === 0) return new Set(items);
614
+ const first = this.#config.getOrderedItems().find((t) => items.has(t)) ?? [...items][0];
615
+ const group = this.#groupOf(first);
616
+ return new Set([...items].filter((t) => this.#groupOf(t) === group));
617
+ }
580
618
  #apply(next) {
581
619
  const previous = this.#selected;
582
620
  this.#selected = next;
@@ -586,4 +624,4 @@ var ListSelectionController = class {
586
624
  //#endregion
587
625
  export { isMultiMode as n, ListDragSelectController as r, ListSelectionController as t };
588
626
 
589
- //# sourceMappingURL=list-selection-controller-SA4piSBi.js.map
627
+ //# sourceMappingURL=list-selection-controller-BeE70lbB.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list-selection-controller-BeE70lbB.js","names":["#host","#config","#dragging","#suppressClick","#bindSurface","#onPointerMove","#onPointerUp","#onPointerCancel","#unbindSurface","#stopAutoScroll","#reset","#safeSurface","#boundSurface","#onPointerDown","#enabledTypes","#pointerId","#startClientX","#startClientY","#currentClientX","#currentClientY","#startX","#startY","#base","#lastMode","#lastModifiers","#threshold","#updatePreview","#kickAutoScroll","#surfaceBox","#currentRect","#modeFor","#preview","#raf","#autoScrollTick","#config","#selected","#anchor","#apply","#clamped","#groupOf","#clampToFirstGroup","#effectiveMulti"],"sources":["../src/interaction/list-drag-select-controller.ts","../src/interaction/list-selection-controller.ts"],"sourcesContent":["import type { ReactiveController, ReactiveControllerHost } from 'lit';\n\n/** Surface-relative rectangle: origin at the scroll container's top-left. */\nexport type DragSelectRect = {\n readonly x: number;\n readonly y: number;\n readonly width: number;\n readonly height: number;\n};\n\nexport type ListDragSelectControllerConfig<T> = {\n /** Element the marquee is drawn in and pointer geometry is measured against. */\n getSurface: () => HTMLElement | undefined;\n /** Is drag-select currently allowed? (multi-capable, has items, not disabled) */\n isEnabled: () => boolean;\n /** Pointer types that may start a drag. Default ['mouse', 'pen'] — touch still scrolls. */\n pointerTypes?: readonly string[];\n /** Movement in px before a press becomes a drag. Default 4. */\n threshold?: number;\n /** Map a surface-relative rect to covered items. */\n hitTest: (rect: DragSelectRect) => Iterable<T>;\n /**\n * Selection snapshotted when the drag starts, combined with the hit set\n * while modifiers are held: Shift adds (`base + hit`), Cmd / Ctrl inverts\n * (covered items toggle, the rest is untouched).\n */\n getBaseSelection: () => ReadonlySet<T>;\n /** Continuous visual feedback: the preview set + current rect (undefined when idle). */\n onPreview: (preview: ReadonlySet<T>, rect: DragSelectRect | undefined) => void;\n /**\n * Fired once on release with the final set. Host applies it to its\n * selection. `additive` is `true` when the drag ran with Shift (add) or\n * Cmd / Ctrl (invert) held.\n */\n onCommit: (finalSet: ReadonlySet<T>, info: { additive: boolean }) => void;\n /** Optional: scroll the surface when the pointer nears an edge during a drag. */\n autoScroll?: (dx: number, dy: number) => void;\n /**\n * Optional predicate called on pointerdown before the controller records its\n * pointer id or later calls setPointerCapture/preventDefault. Return false\n * to yield to another gesture (e.g. native item drag).\n */\n shouldStart?: (event: PointerEvent) => boolean;\n};\n\ntype DragHost = ReactiveControllerHost & HTMLElement;\n\nconst DEFAULT_POINTER_TYPES = [`mouse`, `pen`] as const;\nconst DEFAULT_THRESHOLD = 4;\n/** Pointer distance (px) from an edge that triggers auto-scroll. */\nconst EDGE_ZONE = 28;\n/** Max auto-scroll speed in px per frame. */\nconst MAX_SCROLL_SPEED = 16;\n\n/**\n * Shared pointer-drag (marquee / rubber-band) selection for list components.\n *\n * Owns all pointer plumbing and rectangle state; knows nothing about DOM\n * geometry or the selection model — those are host callbacks. Mirrors the\n * `TickledController` attach pattern (`new ListDragSelectController(this, …)`).\n *\n * Behaviour: `pointerdown` on the surface records a start point; once the\n * pointer moves past `threshold`, the surface captures the pointer and every\n * move recomputes the rect, hit-tests, and calls `onPreview`. On release the\n * final set is delivered once via `onCommit`. A press that never crosses the\n * threshold does nothing (the normal `@click` path runs).\n */\nexport class ListDragSelectController<T> implements ReactiveController {\n readonly #host: DragHost;\n readonly #config: ListDragSelectControllerConfig<T>;\n\n #boundSurface: EventTarget | undefined;\n\n #pointerId: number | undefined;\n #startClientX = 0;\n #startClientY = 0;\n #startX = 0;\n #startY = 0;\n #currentClientX = 0;\n #currentClientY = 0;\n #lastModifiers = { shiftKey: false, ctrlKey: false, metaKey: false };\n #dragging = false;\n #suppressClick = false;\n /** Selection as it was when the drag started — the combine baseline. */\n #base: ReadonlySet<T> = new Set();\n /** Combine mode of the most recent preview (drives the commit flag). */\n #lastMode: `replace` | `add` | `invert` = `replace`;\n #preview: ReadonlySet<T> = new Set();\n #raf = 0;\n\n constructor(host: DragHost, config: ListDragSelectControllerConfig<T>) {\n this.#host = host;\n this.#config = config;\n host.addController(this);\n }\n\n /** `true` while a drag is in progress or its trailing click is still pending. */\n get isDragging(): boolean {\n return this.#dragging || this.#suppressClick;\n }\n\n /** `true` once the press has crossed the threshold and a rect is live. */\n get isActive(): boolean {\n return this.#dragging;\n }\n\n hostConnected(): void {\n this.#bindSurface();\n window.addEventListener(`pointermove`, this.#onPointerMove);\n window.addEventListener(`pointerup`, this.#onPointerUp);\n window.addEventListener(`pointercancel`, this.#onPointerCancel);\n }\n\n hostDisconnected(): void {\n this.#unbindSurface();\n window.removeEventListener(`pointermove`, this.#onPointerMove);\n window.removeEventListener(`pointerup`, this.#onPointerUp);\n window.removeEventListener(`pointercancel`, this.#onPointerCancel);\n this.#stopAutoScroll();\n this.#reset();\n }\n\n /** Re-bind when the surface element appears/changes (e.g. first render). */\n hostUpdated(): void {\n const next = this.#safeSurface() ?? this.#host;\n if (next !== this.#boundSurface) {\n this.#bindSurface();\n }\n }\n\n #safeSurface(): HTMLElement | undefined {\n try {\n return this.#config.getSurface();\n } catch {\n return undefined;\n }\n }\n\n #bindSurface(): void {\n const next = this.#safeSurface() ?? this.#host;\n if (next === this.#boundSurface)\n return;\n this.#unbindSurface();\n this.#boundSurface = next;\n next.addEventListener(`pointerdown`, this.#onPointerDown as EventListener);\n }\n\n #unbindSurface(): void {\n this.#boundSurface?.removeEventListener(`pointerdown`, this.#onPointerDown as EventListener);\n this.#boundSurface = undefined;\n }\n\n #enabledTypes(): readonly string[] {\n return this.#config.pointerTypes ?? DEFAULT_POINTER_TYPES;\n }\n\n #threshold(): number {\n return this.#config.threshold ?? DEFAULT_THRESHOLD;\n }\n\n #onPointerDown = (event: PointerEvent): void => {\n if (event.button !== 0)\n return;\n if (!this.#enabledTypes().includes(event.pointerType))\n return;\n let enabled = false;\n try {\n enabled = this.#config.isEnabled();\n } catch {\n return;\n }\n if (!enabled)\n return;\n const target = event.target as Element | null;\n if (target instanceof Element && typeof target.closest === `function`) {\n if (target.closest(`input,button,a,select,textarea,[contenteditable]`))\n return;\n }\n if (this.#config.shouldStart) {\n try {\n if (!this.#config.shouldStart(event))\n return;\n } catch {\n return;\n }\n }\n const surface = this.#safeSurface() ?? this.#host;\n const box = surface.getBoundingClientRect();\n this.#pointerId = event.pointerId;\n this.#startClientX = event.clientX;\n this.#startClientY = event.clientY;\n this.#currentClientX = event.clientX;\n this.#currentClientY = event.clientY;\n this.#startX = Math.min(Math.max(event.clientX - box.left, 0), Math.max(0, box.width));\n this.#startY = Math.min(Math.max(event.clientY - box.top, 0), Math.max(0, box.height));\n this.#dragging = false;\n this.#suppressClick = false;\n this.#base = new Set();\n this.#lastMode = `replace`;\n this.#lastModifiers = { shiftKey: event.shiftKey, ctrlKey: event.ctrlKey, metaKey: event.metaKey };\n // Do not capture yet — a sub-threshold press is a plain click.\n };\n\n /** Combine mode for the current modifiers: Shift adds, Cmd/Ctrl inverts. */\n #modeFor(modifiers: { shiftKey: boolean; ctrlKey: boolean; metaKey: boolean }): `replace` | `add` | `invert` {\n if (modifiers.metaKey || modifiers.ctrlKey)\n return `invert`;\n if (modifiers.shiftKey)\n return `add`;\n return `replace`;\n }\n\n #onPointerMove = (event: PointerEvent): void => {\n if (this.#pointerId === undefined || event.pointerId !== this.#pointerId)\n return;\n this.#currentClientX = event.clientX;\n this.#currentClientY = event.clientY;\n this.#lastModifiers = { shiftKey: event.shiftKey, ctrlKey: event.ctrlKey, metaKey: event.metaKey };\n const moved = Math.hypot(event.clientX - this.#startClientX, event.clientY - this.#startClientY);\n if (!this.#dragging) {\n if (moved < this.#threshold())\n return;\n this.#dragging = true;\n try {\n this.#base = new Set(this.#config.getBaseSelection());\n } catch {\n this.#base = new Set();\n }\n const surface = this.#safeSurface() ?? this.#host;\n try {\n if (typeof surface.setPointerCapture === `function`)\n surface.setPointerCapture(event.pointerId);\n } catch {\n // happy-dom and some environments lack setPointerCapture — non-fatal.\n }\n }\n try {\n event.preventDefault?.();\n } catch {\n // Ignore — prevents native image drag where supported.\n }\n this.#updatePreview();\n this.#kickAutoScroll();\n };\n\n #surfaceBox(): DOMRect | undefined {\n const surface = this.#safeSurface() ?? this.#host;\n try {\n return surface.getBoundingClientRect();\n } catch {\n return undefined;\n }\n }\n\n #currentRect(): DragSelectRect | undefined {\n const box = this.#surfaceBox();\n if (!box)\n return undefined;\n const cx = Math.min(Math.max(this.#currentClientX - box.left, 0), Math.max(0, box.width));\n const cy = Math.min(Math.max(this.#currentClientY - box.top, 0), Math.max(0, box.height));\n return {\n x: Math.min(this.#startX, cx),\n y: Math.min(this.#startY, cy),\n width: Math.abs(cx - this.#startX),\n height: Math.abs(cy - this.#startY),\n };\n }\n\n #updatePreview(): void {\n const rect = this.#currentRect();\n if (!rect)\n return;\n let hit: Iterable<T> = [];\n try {\n hit = this.#config.hitTest(rect);\n } catch {\n hit = [];\n }\n const mode = this.#modeFor(this.#lastModifiers);\n this.#lastMode = mode;\n const hitSet = new Set(hit);\n let preview: ReadonlySet<T>;\n if (mode === `add`) {\n preview = new Set([...this.#base, ...hitSet]);\n } else if (mode === `invert`) {\n const toggled = new Set(this.#base);\n for (const item of hitSet) {\n if (toggled.has(item))\n toggled.delete(item);\n else\n toggled.add(item);\n }\n preview = toggled;\n } else {\n preview = hitSet;\n }\n this.#preview = preview;\n try {\n this.#config.onPreview(preview, rect);\n } catch {\n // Host preview must never break the gesture.\n }\n }\n\n #onPointerUp = (event: PointerEvent): void => {\n if (this.#pointerId === undefined || event.pointerId !== this.#pointerId)\n return;\n this.#lastModifiers = { shiftKey: event.shiftKey, ctrlKey: event.ctrlKey, metaKey: event.metaKey };\n const wasDragging = this.#dragging;\n const surface = this.#safeSurface() ?? this.#host;\n try {\n if (typeof surface.hasPointerCapture === `function`\n && typeof surface.releasePointerCapture === `function`\n && surface.hasPointerCapture(event.pointerId)) {\n surface.releasePointerCapture(event.pointerId);\n }\n } catch {\n // Non-fatal (see pointermove).\n }\n this.#stopAutoScroll();\n this.#pointerId = undefined;\n if (!wasDragging) {\n this.#reset();\n return;\n }\n this.#dragging = false;\n const final = this.#preview;\n try {\n this.#config.onCommit(final, { additive: this.#lastMode !== `replace` });\n } catch {\n // Host commit must never break state reset.\n }\n try {\n this.#config.onPreview(new Set(), undefined);\n } catch {\n // Ignore.\n }\n this.#preview = new Set();\n // Keep `isDragging` true until the trailing synthetic `click` has been\n // dispatched so hosts can swallow it; clicks dispatch before timers fire.\n this.#suppressClick = true;\n window.setTimeout(() => {\n this.#suppressClick = false;\n }, 0);\n };\n\n #onPointerCancel = (event: PointerEvent): void => {\n if (this.#pointerId === undefined || event.pointerId !== this.#pointerId)\n return;\n this.#stopAutoScroll();\n this.#pointerId = undefined;\n this.#dragging = false;\n this.#preview = new Set();\n try {\n this.#config.onPreview(new Set(), undefined);\n } catch {\n // Ignore.\n }\n this.#suppressClick = false;\n };\n\n #kickAutoScroll(): void {\n if (!this.#config.autoScroll || this.#raf !== 0)\n return;\n this.#raf = requestAnimationFrame(this.#autoScrollTick);\n }\n\n #autoScrollTick = (): void => {\n this.#raf = 0;\n if (!this.#dragging || this.#pointerId === undefined)\n return;\n const box = this.#surfaceBox();\n if (!box)\n return;\n const px = this.#currentClientX - box.left;\n const py = this.#currentClientY - box.top;\n let dx = 0;\n let dy = 0;\n if (px < EDGE_ZONE)\n dx = -Math.ceil(MAX_SCROLL_SPEED * (1 - Math.max(0, px) / EDGE_ZONE));\n else if (px > box.width - EDGE_ZONE)\n dx = Math.ceil(MAX_SCROLL_SPEED * (1 - Math.max(0, box.width - px) / EDGE_ZONE));\n if (py < EDGE_ZONE)\n dy = -Math.ceil(MAX_SCROLL_SPEED * (1 - Math.max(0, py) / EDGE_ZONE));\n else if (py > box.height - EDGE_ZONE)\n dy = Math.ceil(MAX_SCROLL_SPEED * (1 - Math.max(0, box.height - py) / EDGE_ZONE));\n if (dx === 0 && dy === 0)\n return;\n const autoScroll = this.#config.autoScroll;\n if (!autoScroll)\n return;\n try {\n autoScroll(dx, dy);\n } catch {\n // Ignore.\n }\n // Scrolling changes which items a fixed surface-relative rect covers\n // (hosts add the scroll offset in hitTest), so re-run the preview.\n this.#updatePreview();\n this.#raf = requestAnimationFrame(this.#autoScrollTick);\n };\n\n #stopAutoScroll(): void {\n if (this.#raf !== 0) {\n cancelAnimationFrame(this.#raf);\n this.#raf = 0;\n }\n }\n\n #reset(): void {\n this.#dragging = false;\n this.#suppressClick = false;\n this.#base = new Set();\n this.#lastMode = `replace`;\n this.#preview = new Set();\n }\n}\n","import type { ListInteractionMode, ListSelectionMode } from './list-selection-types.js';\n\n/** Modifier state needed to route a click gesture per interaction mode. */\nexport type ListSelectionGesture = {\n readonly ctrlKey: boolean;\n readonly metaKey: boolean;\n readonly shiftKey: boolean;\n};\n\nexport type ListSelectionModes = {\n readonly selectionMode: ListSelectionMode;\n readonly interactionMode: ListInteractionMode;\n};\n\n/**\n * Configuration supplied by the host component.\n *\n * The controller owns selection *state* only — everything DOM- or\n * component-specific is expressed through these callbacks.\n */\nexport type ListSelectionControllerConfig<T> = {\n /** Visible items in navigation order — used for range selection and select-all. */\n readonly getOrderedItems: () => readonly T[];\n /** Whether an item may join the selection (e.g. reject `not-checked` rows). */\n readonly isSelectable: (item: T) => boolean;\n /** Current modes; read on every gesture so property changes apply immediately. */\n readonly getModes: () => ListSelectionModes;\n /**\n * Fired after every selection change. The host syncs DOM state\n * (`data-selected` / `data-checked`), dispatches `list-select`, and\n * requests an update.\n */\n readonly onChange: (selected: ReadonlySet<T>, previous: ReadonlySet<T>) => void;\n /**\n * Optional: derive a stable string key for an item. Enables `selectedKeys`\n * and `selectKeys()`. When omitted, `selectedKeys` is always empty.\n */\n readonly getKey?: (item: T) => string | undefined;\n /**\n * Optional: the group an item belongs to (`null` when ungrouped or the item\n * cannot be resolved). With this set and `crossGroupSelection` off, gestures\n * are confined to a single group — same rules as `ixfx-data-grid` and\n * `ixfx-grouped-item-lister`. Programmatic key APIs are never clamped.\n */\n readonly getGroupKey?: (item: T) => string | null;\n /** Whether selection may span groups. Read on every gesture; defaults to `false`. */\n readonly crossGroupSelection?: () => boolean;\n /** Group used by `selectAll` when there is no anchor (e.g. the cursor's group). */\n readonly getFallbackGroupKey?: () => string | null;\n};\n\n/** Whether the interaction mode allows building a multi-item selection. */\nexport function isMultiMode(mode: ListInteractionMode): boolean {\n return mode === `checked` || mode === `sticky` || mode === `vscode` || mode === `standard`;\n}\n\n/**\n * Generic selection state machine shared by list components.\n *\n * Owns the selected set plus the range-selection anchor, the selection\n * primitives (`replace` / `toggle` / `rangeTo` / `clear` / `selectAll` /\n * `selectMany` / `deselect`) and the per-interactionMode gesture routers\n * (`handleClick` / `handleSpace`).\n *\n * Identity is generic: both `ixfx-vertical-list` and `ixfx-detail-list` use\n * `ListSelectionController<Element>`.\n *\n * @example\n * ```ts\n * const selection = new ListSelectionController<Element>({\n * getOrderedItems: () => this.getVisibleItems(),\n * isSelectable: el => !el.hasAttribute(`not-checked`),\n * getModes: () => ({ selectionMode: this.selectionMode, interactionMode: this.interactionMode }),\n * onChange: (selected, previous) => {\n * this.syncItemStates();\n * this.dispatchEvent(new CustomEvent(`list-select`, { detail: { selected, previous } }));\n * },\n * });\n * ```\n */\nexport class ListSelectionController<T> {\n readonly #config: ListSelectionControllerConfig<T>;\n #selected: ReadonlySet<T> = new Set();\n #anchor: T | undefined;\n\n constructor(config: ListSelectionControllerConfig<T>) {\n this.#config = config;\n }\n\n /** The current selection set (read-only). */\n get selected(): ReadonlySet<T> {\n return this.#selected;\n }\n\n /**\n * The current selection as stable string keys (read-only). Empty unless a\n * `getKey` was supplied in config. Items whose `getKey` returns `undefined`\n * are omitted.\n */\n get selectedKeys(): ReadonlySet<string> {\n const getKey = this.#config.getKey;\n const out = new Set<string>();\n if (getKey) {\n for (const item of this.#selected) {\n const key = getKey(item);\n if (key !== undefined) {\n out.add(key);\n }\n }\n }\n return out;\n }\n\n /** Anchor for range (shift) selection — the last plainly-selected item. */\n get anchor(): T | undefined {\n return this.#anchor;\n }\n\n /** Whether \"select all\" (Cmd/Ctrl+A) is currently permitted. */\n canSelectAll(): boolean {\n return this.canSelectMultiple() && this.#config.getModes().selectionMode !== `none`;\n }\n\n /** Whether a multi-item selection can be built in the current modes. */\n canSelectMultiple(): boolean {\n const { selectionMode, interactionMode } = this.#config.getModes();\n return selectionMode === `multiple` || isMultiMode(interactionMode);\n }\n\n // --- Selection primitives ---\n\n /** Replace the entire selection with a single item; updates the anchor. */\n replace(item: T): void {\n if (this.#config.getModes().selectionMode === `none`)\n return;\n if (!this.#config.isSelectable(item))\n return;\n this.#anchor = item;\n this.#apply(new Set([item]));\n }\n\n /** Toggle a single item in/out of the selection without replacing it. Anchor unchanged. */\n toggle(item: T): void {\n const { selectionMode, interactionMode } = this.#config.getModes();\n if (!this.#config.isSelectable(item))\n return;\n // checked/vscode/sticky modes imply multiple selection capacity\n if (selectionMode === `none` && interactionMode !== `checked` && interactionMode !== `sticky`)\n return;\n\n const next = new Set(this.#selected);\n if (next.has(item)) {\n next.delete(item);\n } else {\n if (!this.canSelectMultiple())\n next.clear();\n if (this.#clamped()) {\n const g = this.#groupOf(item);\n for (const other of [...next]) {\n if (this.#groupOf(other) !== g)\n next.delete(other);\n }\n }\n next.add(item);\n }\n this.#apply(next);\n }\n\n /** Select the contiguous ordered range from the anchor to `item`. Anchor unchanged. */\n rangeTo(item: T): void {\n if (this.#config.getModes().selectionMode === `none`)\n return;\n if (this.#anchor === undefined) {\n this.replace(item);\n return;\n }\n const ordered = this.#config.getOrderedItems();\n const anchorIdx = ordered.indexOf(this.#anchor);\n const targetIdx = ordered.indexOf(item);\n if (anchorIdx === -1 || targetIdx === -1) {\n this.replace(item);\n return;\n }\n if (this.#clamped()) {\n const group = this.#groupOf(this.#anchor);\n if (group !== this.#groupOf(item)) {\n this.replace(item);\n return;\n }\n const inGroup = ordered.filter(t => this.#groupOf(t) === group);\n const a = inGroup.indexOf(this.#anchor);\n const b = inGroup.indexOf(item);\n if (a === -1 || b === -1) {\n this.replace(item);\n return;\n }\n this.#apply(new Set(inGroup.slice(Math.min(a, b), Math.max(a, b) + 1).filter(t => this.#config.isSelectable(t))));\n return;\n }\n const start = Math.min(anchorIdx, targetIdx);\n const end = Math.max(anchorIdx, targetIdx);\n this.#apply(new Set(ordered.slice(start, end + 1).filter(t => this.#config.isSelectable(t))));\n }\n\n /** Clear the selection. No change event when the selection is already empty. */\n clear(): void {\n if (this.#selected.size === 0)\n return;\n this.#apply(new Set());\n }\n\n /** Select every ordered item that passes `isSelectable`. */\n selectAll(): void {\n let ordered = this.#config.getOrderedItems();\n if (ordered.length === 0)\n return;\n if (this.#clamped()) {\n const group = (this.#anchor === undefined ? null : this.#groupOf(this.#anchor))\n ?? this.#config.getFallbackGroupKey?.()\n ?? null;\n if (group !== null)\n ordered = ordered.filter(t => this.#groupOf(t) === group);\n }\n const next = new Set(ordered.filter(t => this.#config.isSelectable(t)));\n if (next.size === 0)\n return;\n this.#apply(next);\n }\n\n /**\n * Replace the selection with many items at once. Requires\n * `selectionMode=\"multiple\"`, throws otherwise. Updates the anchor.\n */\n selectMany(items: Iterable<T>): void {\n const { selectionMode } = this.#config.getModes();\n if (selectionMode !== `multiple`) {\n throw new Error(`selectMany requires selectionMode=\"multiple\" (current: \"${selectionMode}\")`);\n }\n const next = this.#clampToFirstGroup(new Set([...items].filter(t => this.#config.isSelectable(t))));\n if (next.size === 0)\n return;\n this.#anchor = [...next].at(-1);\n this.#apply(next);\n }\n\n /**\n * Whether a drag / marquee gesture may build a selection in the current\n * modes: `selectionMode=\"multiple\"`, or a multi interaction mode\n * (`checked` / `sticky` / `vscode`) outside `selectionMode=\"none\"`.\n * Stricter than `canSelectMultiple()` — `single` + `standard` does not\n * qualify (a drag there would be a surprising multi-select).\n */\n canDragSelect(): boolean {\n return this.#config.getModes().selectionMode !== `none` && this.#effectiveMulti();\n }\n\n /**\n * Replace the selection with `items` from a drag / marquee gesture. Like\n * `selectMany` but gated on `canDragSelect()` instead of throwing, and a\n * no-op in single/none modes. Non-selectable items are dropped; the anchor\n * moves to the last item. Fires `onChange` once. An empty result clears a\n * non-empty selection (e.g. a Cmd-drag that toggles everything off) but is\n * a no-op when nothing is selected.\n */\n applyDragSelection(items: Iterable<T>): void {\n if (!this.canDragSelect())\n return;\n const next = this.#clampToFirstGroup(new Set([...items].filter(t => this.#config.isSelectable(t))));\n if (next.size === 0 && this.#selected.size === 0)\n return;\n this.#anchor = [...next].at(-1);\n this.#apply(next);\n }\n\n /** Remove a single item from the selection. */\n deselect(item: T): void {\n if (!this.#selected.has(item))\n return;\n const next = new Set(this.#selected);\n next.delete(item);\n this.#apply(next);\n }\n\n // --- Key-based selection ---\n\n /**\n * Whether the current modes permit a selection of more than one item.\n * Stricter than `canSelectMultiple()`: `standard` / `implicit` only count\n * as multi when `selectionMode=\"multiple\"`.\n */\n #effectiveMulti(): boolean {\n const { selectionMode, interactionMode } = this.#config.getModes();\n return selectionMode === `multiple`\n || interactionMode === `checked`\n || interactionMode === `sticky`\n || interactionMode === `vscode`;\n }\n\n /**\n * Replace the selection with the items resolved from `keys`. Keys that\n * `resolve` cannot map, or that resolve to a non-selectable item, are\n * ignored. `selectionMode=\"none\"` is a no-op. When multi-select is not\n * available, only the last resolvable key is kept. `onChange` fires once.\n */\n selectKeys(keys: Iterable<string>, resolve: (key: string) => T | undefined): void {\n if (this.#config.getModes().selectionMode === `none`)\n return;\n let next = new Set<T>();\n for (const key of new Set(keys)) {\n const item = resolve(key);\n if (item !== undefined && this.#config.isSelectable(item)) {\n next.add(item);\n }\n }\n if (!this.#effectiveMulti() && next.size > 1) {\n const last = [...next].at(-1);\n next = last === undefined ? new Set() : new Set([last]);\n }\n this.#anchor = [...next].at(-1);\n this.#apply(next);\n }\n\n /**\n * Add the items resolved from `keys` to the selection (multi-select only;\n * a no-op otherwise). `onChange` fires once if anything changed.\n */\n addKeys(keys: Iterable<string>, resolve: (key: string) => T | undefined): void {\n if (!this.#effectiveMulti())\n return;\n const next = new Set(this.#selected);\n let changed = false;\n for (const key of new Set(keys)) {\n const item = resolve(key);\n if (item !== undefined && !next.has(item) && this.#config.isSelectable(item)) {\n next.add(item);\n changed = true;\n }\n }\n if (changed) {\n this.#apply(next);\n }\n }\n\n /**\n * Remove the items resolved from `keys` from the selection. `onChange`\n * fires once if anything changed.\n */\n removeKeys(keys: Iterable<string>, resolve: (key: string) => T | undefined): void {\n if (this.#selected.size === 0)\n return;\n const next = new Set(this.#selected);\n let changed = false;\n for (const key of new Set(keys)) {\n const item = resolve(key);\n if (item !== undefined && next.delete(item)) {\n changed = true;\n }\n }\n if (changed) {\n this.#apply(next);\n }\n }\n\n // --- Gesture routers ---\n\n /** Route a click on `item` according to the current interaction mode. */\n handleClick(item: T, gesture: ListSelectionGesture): void {\n const { selectionMode, interactionMode: mode } = this.#config.getModes();\n if (mode === `manual`)\n return;\n if (selectionMode === `none` && mode !== `checked` && mode !== `sticky`)\n return;\n\n switch (mode) {\n case `implicit`:\n // Single-select only; modifier keys have no effect\n this.replace(item);\n break;\n\n case `standard`:\n case `vscode`:\n if (gesture.ctrlKey || gesture.metaKey) {\n // Ctrl/Cmd+click: toggle item; requires effective multi-select\n if (selectionMode === `multiple` || mode === `vscode`) {\n this.toggle(item);\n }\n } else if (gesture.shiftKey && (selectionMode === `multiple` || mode === `vscode`)) {\n // Shift+click: range-select from anchor\n this.rangeTo(item);\n } else {\n // Plain click: replace selection, update anchor\n this.replace(item);\n }\n break;\n\n case `checked`:\n // Body clicks do nothing — only the checkbox column toggles.\n break;\n\n case `sticky`:\n // Every tap/click toggles — multi-select without modifier keys (touchscreens).\n this.toggle(item);\n break;\n }\n }\n\n /** Route a Space keypress on `item` according to the current interaction mode. */\n handleSpace(item: T): void {\n const mode = this.#config.getModes().interactionMode;\n if (mode === `manual`)\n return;\n if (mode === `implicit`) {\n // Space selects (same as click) in implicit mode\n this.replace(item);\n } else {\n // standard / vscode / checked / sticky: Space toggles\n this.toggle(item);\n }\n }\n\n // --- Maintenance ---\n\n /** Drop the range-selection anchor (e.g. when the interaction mode changes). */\n clearAnchor(): void {\n this.#anchor = undefined;\n }\n\n /**\n * Re-key the selection across an identity boundary — e.g. when items are\n * wrapped/unwrapped and the selected Element references change. Silent:\n * no `onChange` is fired.\n */\n remap(fn: (item: T) => T): void {\n if (this.#selected.size === 0)\n return;\n this.#selected = new Set([...this.#selected].map(fn));\n }\n\n /**\n * Hard reset: empty the selection and clear the anchor without firing\n * `onChange` (e.g. when all items are removed).\n */\n reset(): void {\n this.#selected = new Set();\n this.#anchor = undefined;\n }\n\n /**\n * Replace the selection and anchor silently (no `onChange`). Used to\n * re-key the selection when items are rebuilt from data — e.g. matching\n * new elements to previously selected keys.\n */\n seed(items: Iterable<T>, anchor?: T): void {\n this.#selected = new Set(items);\n this.#anchor = anchor;\n }\n\n // --- Grouping ---\n\n /** Whether gestures must stay inside one group. */\n #clamped(): boolean {\n return this.#config.getGroupKey !== undefined && !(this.#config.crossGroupSelection?.() ?? false);\n }\n\n #groupOf(item: T): string | null {\n return this.#config.getGroupKey?.(item) ?? null;\n }\n\n /** Keep only items in the group of the first item (in display order) when clamped. */\n #clampToFirstGroup(items: ReadonlySet<T>): Set<T> {\n if (!this.#clamped() || items.size === 0)\n return new Set(items);\n const first = this.#config.getOrderedItems().find(t => items.has(t)) ?? [...items][0];\n const group = this.#groupOf(first);\n return new Set([...items].filter(t => this.#groupOf(t) === group));\n }\n\n #apply(next: ReadonlySet<T>): void {\n const previous = this.#selected;\n this.#selected = next;\n this.#config.onChange(next, previous);\n }\n}\n"],"mappings":"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"}
@@ -4,7 +4,7 @@ import { t as themeFallbacks } from "./fallbacks-DQ_5OsmR.js";
4
4
  import { n as safeCustomElement, t as __decorate } from "./decorate-VRK8rslU.js";
5
5
  import "./icon-1gpwtPx8.js";
6
6
  import "./interaction-BskmlA9t.js";
7
- import { n as MenuTrigger, r as MenuContainer, t as MenuItem } from "./menu-item-CfndBGO8.js";
7
+ import { n as MenuTrigger, r as MenuContainer, t as MenuItem } from "./menu-item-CDPFgaSF.js";
8
8
  import { LitElement, css, html, nothing } from "lit";
9
9
  import { property, query, state } from "lit/decorators.js";
10
10
  //#region src/menu/menu-bar.ts
@@ -823,4 +823,4 @@ var menu_exports = /* @__PURE__ */ __exportAll({
823
823
  //#endregion
824
824
  export { menuFromTreeToElements as a, MenuSubTrigger as c, MenuBar as d, menuFromTree as i, MenuCommandController as l, MenuRadioGroup as n, MenuHeader as o, MenuRadioItem as r, MenuSeparator as s, menu_exports as t, MenuCheckItem as u };
825
825
 
826
- //# sourceMappingURL=menu-CsBUyUuS.js.map
826
+ //# sourceMappingURL=menu-DaAlsyhf.js.map