@nvidia-elements/core 0.0.10 → 0.0.11

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 (191) hide show
  1. package/CHANGELOG.md +12 -0
  2. package/dist/accordion/accordion.examples.json +11 -11
  3. package/dist/accordion/accordion2.js +4 -4
  4. package/dist/alert/alert-group2.js +1 -1
  5. package/dist/alert/alert.examples.json +12 -12
  6. package/dist/alert/alert2.js +1 -1
  7. package/dist/avatar/avatar-group2.js +1 -1
  8. package/dist/avatar/avatar.examples.json +6 -6
  9. package/dist/avatar/avatar2.js +1 -1
  10. package/dist/badge/badge.examples.json +12 -12
  11. package/dist/badge/badge2.js +1 -1
  12. package/dist/breadcrumb/breadcrumb.examples.json +3 -3
  13. package/dist/breadcrumb/breadcrumb2.js +1 -1
  14. package/dist/bundles/index.js +3 -3
  15. package/dist/button/button.examples.json +24 -24
  16. package/dist/button/button2.js +1 -1
  17. package/dist/button-group/button-group.examples.json +11 -11
  18. package/dist/button-group/button-group2.js +1 -1
  19. package/dist/card/card.examples.json +10 -10
  20. package/dist/card/card2.js +4 -4
  21. package/dist/chat-message/chat-message.examples.json +7 -7
  22. package/dist/chat-message/chat-message2.js +1 -1
  23. package/dist/checkbox/checkbox-group2.js +1 -1
  24. package/dist/checkbox/checkbox.examples.json +7 -7
  25. package/dist/checkbox/checkbox2.js +1 -1
  26. package/dist/color/color.examples.json +4 -4
  27. package/dist/color/color2.js +1 -1
  28. package/dist/combobox/combobox.examples.json +24 -24
  29. package/dist/combobox/combobox2.js +1 -1
  30. package/dist/copy-button/copy-button.examples.json +9 -9
  31. package/dist/copy-button/copy-button2.js +1 -1
  32. package/dist/custom-elements.json +13 -71
  33. package/dist/date/date.examples.json +7 -7
  34. package/dist/date/date2.js +1 -1
  35. package/dist/datetime/datetime.examples.json +4 -4
  36. package/dist/datetime/datetime2.js +1 -1
  37. package/dist/dialog/dialog-footer2.js +1 -1
  38. package/dist/dialog/dialog-header2.js +1 -1
  39. package/dist/dialog/dialog.examples.json +21 -21
  40. package/dist/dialog/dialog2.js +1 -1
  41. package/dist/divider/divider.examples.json +5 -5
  42. package/dist/divider/divider2.js +1 -1
  43. package/dist/dot/dot.examples.json +5 -5
  44. package/dist/dot/dot2.js +1 -1
  45. package/dist/drawer/drawer-content2.js +1 -1
  46. package/dist/drawer/drawer-footer2.js +1 -1
  47. package/dist/drawer/drawer-header2.js +1 -1
  48. package/dist/drawer/drawer.examples.json +13 -13
  49. package/dist/drawer/drawer2.js +1 -1
  50. package/dist/dropdown/dropdown-footer2.js +1 -1
  51. package/dist/dropdown/dropdown-header2.js +1 -1
  52. package/dist/dropdown/dropdown.examples.json +14 -14
  53. package/dist/dropdown/dropdown2.js +1 -1
  54. package/dist/dropdown-group/dropdown-group.examples.json +4 -4
  55. package/dist/dropdown-group/dropdown-group.js +1 -1
  56. package/dist/dropzone/dropzone.examples.json +3 -3
  57. package/dist/dropzone/dropzone2.js +1 -1
  58. package/dist/file/file.examples.json +3 -3
  59. package/dist/file/file2.js +1 -1
  60. package/dist/format-datetime/format-datetime.examples.json +9 -9
  61. package/dist/format-datetime/format-datetime2.js +1 -1
  62. package/dist/format-relative-time/format-relative-time.examples.json +7 -7
  63. package/dist/format-relative-time/format-relative-time2.js +1 -1
  64. package/dist/forms/actions.examples.json +3 -3
  65. package/dist/forms/control/control.examples.json +11 -11
  66. package/dist/forms/control/control2.js +1 -1
  67. package/dist/forms/control-group/control-group2.js +1 -1
  68. package/dist/forms/control-message/control-message2.js +1 -1
  69. package/dist/forms/forms.examples.json +8 -8
  70. package/dist/forms/validation.examples.json +5 -5
  71. package/dist/grid/cell/cell2.js +1 -1
  72. package/dist/grid/column/column2.js +1 -1
  73. package/dist/grid/footer/footer2.js +1 -1
  74. package/dist/grid/grid.examples.json +43 -43
  75. package/dist/grid/grid2.js +1 -1
  76. package/dist/grid/header/header2.js +2 -2
  77. package/dist/grid/header/header2.js.map +1 -1
  78. package/dist/grid/placeholder/placeholder2.js +1 -1
  79. package/dist/grid/row/row2.js +1 -1
  80. package/dist/icon/icon.examples.json +8 -8
  81. package/dist/icon/icon2.js +2 -2
  82. package/dist/icon-button/icon-button.examples.json +13 -13
  83. package/dist/icon-button/icon-button2.js +1 -1
  84. package/dist/index.js +1 -1
  85. package/dist/input/input-group.examples.json +2 -2
  86. package/dist/input/input-group2.js +1 -1
  87. package/dist/input/input.examples.json +8 -8
  88. package/dist/input/input2.js +1 -1
  89. package/dist/internal/controllers/i18n.controller.examples.json +1 -1
  90. package/dist/internal/controllers/keynav-grid.controller.examples.json +2 -2
  91. package/dist/internal/controllers/keynav-grid.controller.js +15 -7
  92. package/dist/internal/controllers/keynav-grid.controller.js.map +1 -1
  93. package/dist/internal/controllers/keynav-list.controller.examples.json +4 -4
  94. package/dist/internal/controllers/keynav-list.controller.js +11 -5
  95. package/dist/internal/controllers/keynav-list.controller.js.map +1 -1
  96. package/dist/internal/controllers/popover.examples.json +8 -8
  97. package/dist/internal/controllers/type-button.controller.examples.json +1 -1
  98. package/dist/internal/controllers/type-popover.controller.examples.json +2 -2
  99. package/dist/internal/controllers/type-touch.controller.examples.json +1 -1
  100. package/dist/internal/services/global.service.js +1 -1
  101. package/dist/logo/logo.examples.json +6 -6
  102. package/dist/logo/logo2.js +1 -1
  103. package/dist/menu/menu-item2.js +1 -1
  104. package/dist/menu/menu.examples.json +15 -15
  105. package/dist/menu/menu2.js +1 -1
  106. package/dist/month/month.examples.json +4 -4
  107. package/dist/month/month2.js +1 -1
  108. package/dist/notification/notification-group2.js +1 -1
  109. package/dist/notification/notification.examples.json +15 -15
  110. package/dist/notification/notification2.js +1 -1
  111. package/dist/page/page-panel/page-panel-content2.js +1 -1
  112. package/dist/page/page-panel/page-panel-footer2.js +1 -1
  113. package/dist/page/page-panel/page-panel-header2.js +1 -1
  114. package/dist/page/page-panel/page-panel2.js +1 -1
  115. package/dist/page/page.examples.js.map +1 -1
  116. package/dist/page/page.examples.json +36 -34
  117. package/dist/page/page2.js +1 -1
  118. package/dist/page-header/page-header.examples.json +9 -9
  119. package/dist/page-header/page-header2.js +1 -1
  120. package/dist/page-loader/page-loader.examples.json +2 -2
  121. package/dist/page-loader/page-loader2.js +1 -1
  122. package/dist/pagination/pagination.examples.json +16 -16
  123. package/dist/pagination/pagination2.js +1 -1
  124. package/dist/panel/panel.examples.json +7 -7
  125. package/dist/panel/panel2.js +4 -4
  126. package/dist/password/password.examples.json +3 -3
  127. package/dist/password/password2.js +1 -1
  128. package/dist/preferences-input/preferences-input.examples.json +3 -3
  129. package/dist/preferences-input/preferences-input2.js +1 -1
  130. package/dist/progress-bar/progress-bar.examples.json +8 -8
  131. package/dist/progress-bar/progress-bar2.js +1 -1
  132. package/dist/progress-ring/progress-ring.examples.json +8 -8
  133. package/dist/progress-ring/progress-ring2.js +1 -1
  134. package/dist/progressive-filter-chip/progressive-filter-chip.examples.json +7 -7
  135. package/dist/progressive-filter-chip/progressive-filter-chip2.js +1 -1
  136. package/dist/pulse/pulse.examples.json +4 -4
  137. package/dist/pulse/pulse2.js +1 -1
  138. package/dist/radio/radio-group2.js +1 -1
  139. package/dist/radio/radio.examples.json +5 -5
  140. package/dist/radio/radio2.js +1 -1
  141. package/dist/range/range.examples.json +9 -9
  142. package/dist/range/range2.js +1 -1
  143. package/dist/resize-handle/resize-handle.examples.json +7 -7
  144. package/dist/resize-handle/resize-handle2.js +1 -1
  145. package/dist/search/search.examples.json +5 -5
  146. package/dist/search/search2.js +1 -1
  147. package/dist/select/select.examples.json +18 -18
  148. package/dist/select/select2.js +1 -1
  149. package/dist/skeleton/skeleton.examples.json +4 -4
  150. package/dist/skeleton/skeleton2.js +1 -1
  151. package/dist/sort-button/sort-button.examples.json +3 -3
  152. package/dist/sort-button/sort-button2.js +1 -1
  153. package/dist/sparkline/sparkline.examples.json +13 -13
  154. package/dist/sparkline/sparkline.utils.d.ts +26 -5
  155. package/dist/sparkline/sparkline.utils.js +30 -30
  156. package/dist/sparkline/sparkline.utils.js.map +1 -1
  157. package/dist/sparkline/sparkline2.js +21 -6
  158. package/dist/sparkline/sparkline2.js.map +1 -1
  159. package/dist/star-rating/star-rating.examples.json +4 -4
  160. package/dist/star-rating/star-rating2.js +1 -1
  161. package/dist/steps/steps.examples.json +5 -5
  162. package/dist/steps/steps2.js +2 -2
  163. package/dist/switch/switch-group2.js +1 -1
  164. package/dist/switch/switch.examples.json +7 -7
  165. package/dist/switch/switch2.js +1 -1
  166. package/dist/tabs/tabs-group2.js +9 -6
  167. package/dist/tabs/tabs-group2.js.map +1 -1
  168. package/dist/tabs/tabs.examples.json +14 -14
  169. package/dist/tabs/tabs2.js +2 -2
  170. package/dist/tag/tag.examples.json +8 -8
  171. package/dist/tag/tag2.js +1 -1
  172. package/dist/textarea/textarea.examples.json +5 -5
  173. package/dist/textarea/textarea2.js +1 -1
  174. package/dist/time/time.examples.json +4 -4
  175. package/dist/time/time2.js +1 -1
  176. package/dist/toast/toast.examples.json +11 -11
  177. package/dist/toast/toast2.js +1 -1
  178. package/dist/toggletip/toggletip-footer2.js +1 -1
  179. package/dist/toggletip/toggletip-header2.js +1 -1
  180. package/dist/toggletip/toggletip.examples.json +12 -12
  181. package/dist/toggletip/toggletip2.js +1 -1
  182. package/dist/toolbar/toolbar.examples.json +8 -8
  183. package/dist/toolbar/toolbar2.js +1 -1
  184. package/dist/tooltip/tooltip.examples.json +22 -22
  185. package/dist/tooltip/tooltip2.js +1 -1
  186. package/dist/tree/tree-node2.js +1 -1
  187. package/dist/tree/tree.examples.json +13 -13
  188. package/dist/tree/tree2.js +1 -1
  189. package/dist/week/week.examples.json +5 -5
  190. package/dist/week/week2.js +1 -1
  191. package/package.json +3 -3
@@ -22,7 +22,7 @@ var v = class extends h {
22
22
  static {
23
23
  this.metadata = {
24
24
  tag: "nve-grid",
25
- version: "0.0.10",
25
+ version: "0.0.11",
26
26
  children: [
27
27
  u.metadata.tag,
28
28
  d.metadata.tag,
@@ -19,7 +19,7 @@ var m = class extends d {
19
19
  static {
20
20
  this.metadata = {
21
21
  tag: "nve-grid-header",
22
- version: "0.0.10",
22
+ version: "0.0.11",
23
23
  children: [c.metadata.tag]
24
24
  };
25
25
  }
@@ -43,7 +43,7 @@ var m = class extends d {
43
43
  super.firstUpdated(e), await this.updateComplete, this.#i();
44
44
  }
45
45
  async #r() {
46
- await this.updateComplete, this.columns.forEach((e, t) => e.ariaColIndex = `${t + 1}`), this.#e.style.setProperty("--grid-auto-flow", "initial"), this.#e.style.setProperty("--grid-template-column", this.columns.map((e, t) => `var(--c${t})`).join(" ")), this.columns.forEach((e, t) => this.#e.style.setProperty(`--c${t}`, e.width ? e.width : "1fr")), await this.updateComplete, this.columns.forEach((e, t) => this.#e.style.setProperty(`--c${t}`, e.width ? e.width : `minmax(auto, ${e.getBoundingClientRect().width}px)`));
46
+ await this.updateComplete, this.columns.forEach((e, t) => e.ariaColIndex = `${t + 1}`), this.#e.style.setProperty("--grid-auto-flow", "initial"), this.#e.style.setProperty("--grid-template-column", this.columns.map((e, t) => `var(--c${t})`).join(" ")), this.columns.forEach((e, t) => this.#e.style.setProperty(`--c${t}`, e.width ? e.width : "1fr")), await this.updateComplete, this.columns.map((e) => e.width ? e.width : `minmax(auto, ${e.getBoundingClientRect().width}px)`).forEach((e, t) => this.#e.style.setProperty(`--c${t}`, e));
47
47
  }
48
48
  #i() {
49
49
  if (e.state.env !== "production") {
@@ -1 +1 @@
1
- {"version":3,"file":"header2.js","names":["#grid","#computeColumnWidths","#onColumnResize","#resizeObserver","#validateColumns"],"sources":["../../../src/grid/header/header.ts"],"sourcesContent":["// SPDX-FileCopyrightText: Copyright (c) 2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved.\n// SPDX-License-Identifier: Apache-2.0\n\nimport type { PropertyValues } from 'lit';\nimport { html, LitElement } from 'lit';\nimport { queryAssignedElements } from 'lit/decorators/query-assigned-elements.js';\nimport {\n useStyles,\n attachInternals,\n debounce,\n LogService,\n audit,\n GlobalStateService\n} from '@nvidia-elements/core/internal';\nimport styles from './header.css?inline';\nimport { GridColumn } from '../column/column.js';\nimport type { Grid } from '../grid.js';\nimport { GridRow } from '../row/row.js';\nimport { GridCell } from '../cell/cell.js';\n\n/**\n * @element nve-grid-header\n * @description Contains the column headers of a grid, managing column widths and providing structural context for the data rows below.\n * @since 0.11.0\n * @entrypoint \\@nvidia-elements/core/grid\n * @slot - default slot for `nve-grid-column`\n * @cssprop --background\n * @cssprop --border-bottom\n * @cssprop --padding\n * @aria https://www.w3.org/WAI/ARIA/apg/patterns/grid/\n */\n@audit()\nexport class GridHeader extends LitElement {\n static styles = useStyles([styles]);\n\n static readonly metadata = {\n tag: 'nve-grid-header',\n version: '0.0.0',\n children: [GridColumn.metadata.tag]\n };\n\n /** @private */\n declare _internals: ElementInternals;\n\n /** @private */\n @queryAssignedElements({\n selector: GridColumn.metadata.tag,\n flatten: true\n })\n columns!: GridColumn[];\n\n get #grid() {\n return this.parentElement as Grid;\n }\n\n render() {\n return html`\n <div internal-host>\n <slot @slotchange=${() => this.#computeColumnWidths()}></slot>\n </div>\n `;\n }\n\n connectedCallback() {\n super.connectedCallback();\n attachInternals(this);\n this._internals.role = 'row';\n this.addEventListener('nve-grid-column-resize', this.#onColumnResize);\n this.#resizeObserver ??= new ResizeObserver(debounce(() => this.#computeColumnWidths(), 100));\n this.#resizeObserver.observe(this);\n }\n\n disconnectedCallback() {\n super.disconnectedCallback();\n this.removeEventListener('nve-grid-column-resize', this.#onColumnResize);\n this.#resizeObserver?.disconnect();\n }\n\n #onColumnResize = () => {\n void this.#computeColumnWidths();\n };\n\n #resizeObserver?: ResizeObserver;\n\n async firstUpdated(props: PropertyValues<this>) {\n super.firstUpdated(props);\n await this.updateComplete;\n this.#validateColumns();\n }\n\n async #computeColumnWidths() {\n await this.updateComplete;\n this.columns.forEach((c, i) => (c.ariaColIndex = `${i + 1}`));\n this.#grid.style.setProperty('--grid-auto-flow', 'initial');\n this.#grid.style.setProperty('--grid-template-column', this.columns.map((_, i) => `var(--c${i})`).join(' '));\n\n // compute initial column width\n this.columns.forEach((c, i) => this.#grid.style.setProperty(`--c${i}`, c.width ? c.width : `1fr`));\n\n // compute column width based on content\n await this.updateComplete;\n this.columns.forEach((c, i) =>\n this.#grid.style.setProperty(`--c${i}`, c.width ? c.width : `minmax(auto, ${c.getBoundingClientRect().width}px)`)\n );\n }\n\n #validateColumns() {\n if (GlobalStateService.state.env !== 'production') {\n const cells = this.#grid.querySelector(GridRow.metadata.tag)?.querySelectorAll(GridCell.metadata.tag);\n if (this.columns && cells && this.columns.length !== cells.length) {\n LogService.error(`grid-column (${this.columns.length}) and grid-cell (${cells.length}) count mismatch`);\n }\n }\n }\n}\n"],"mappings":";;;;;;;;;;;;;;AAgCO,IAAA,IAAA,cAAyB,EAAW;;gBACzB,EAAU,CAAC,EAAO,CAAC;;;kBAER;GACzB,KAAK;GACL,SAAS;GACT,UAAU,CAAC,EAAW,SAAS,IAAA;GAChC;;CAYD,KAAA,IAAY;AACV,SAAO,KAAK;;CAGd,SAAS;AACP,SAAO,CAAI,+CAEmB,MAAA,GAA2B,CAAC;;CAK5D,oBAAoB;AAMlB,EALA,MAAM,mBAAmB,EACzB,EAAgB,KAAK,EACrB,KAAK,WAAW,OAAO,OACvB,KAAK,iBAAiB,0BAA0B,MAAA,EAAqB,EACrE,MAAA,MAAyB,IAAI,eAAe,QAAe,MAAA,GAA2B,EAAE,IAAI,CAAC,EAC7F,MAAA,EAAqB,QAAQ,KAAK;;CAGpC,uBAAuB;AAGrB,EAFA,MAAM,sBAAsB,EAC5B,KAAK,oBAAoB,0BAA0B,MAAA,EAAqB,EACxE,MAAA,GAAsB,YAAY;;CAGpC,WAAwB;AACjB,QAAA,GAA2B;;CAGlC;CAEA,MAAM,aAAa,GAA6B;AAG9C,EAFA,MAAM,aAAa,EAAM,EACzB,MAAM,KAAK,gBACX,MAAA,GAAuB;;CAGzB,OAAA,IAA6B;AAW3B,EAVA,MAAM,KAAK,gBACX,KAAK,QAAQ,SAAS,GAAG,MAAO,EAAE,eAAe,GAAG,IAAI,IAAK,EAC7D,MAAA,EAAW,MAAM,YAAY,oBAAoB,UAAU,EAC3D,MAAA,EAAW,MAAM,YAAY,0BAA0B,KAAK,QAAQ,KAAK,GAAG,MAAM,UAAU,EAAE,GAAG,CAAC,KAAK,IAAI,CAAC,EAG5G,KAAK,QAAQ,SAAS,GAAG,MAAM,MAAA,EAAW,MAAM,YAAY,MAAM,KAAK,EAAE,QAAQ,EAAE,QAAQ,MAAM,CAAC,EAGlG,MAAM,KAAK,gBACX,KAAK,QAAQ,SAAS,GAAG,MACvB,MAAA,EAAW,MAAM,YAAY,MAAM,KAAK,EAAE,QAAQ,EAAE,QAAQ,gBAAgB,EAAE,uBAAuB,CAAC,MAAM,KAAK,CAClH;;CAGH,KAAmB;AACjB,MAAI,EAAmB,MAAM,QAAQ,cAAc;GACjD,IAAM,IAAQ,MAAA,EAAW,cAAc,EAAQ,SAAS,IAAI,EAAE,iBAAiB,EAAS,SAAS,IAAI;AACrG,GAAI,KAAK,WAAW,KAAS,KAAK,QAAQ,WAAW,EAAM,UACzD,EAAW,MAAM,gBAAgB,KAAK,QAAQ,OAAO,mBAAmB,EAAM,OAAO,kBAAkB;;;;GAjE5G,EAAsB;CACrB,UAAU,EAAW,SAAS;CAC9B,SAAS;CACV,CAAC,CAAA,EAAA,EAAA,WAAA,WAAA,KAAA,EAAA,SAjBH,GAAO,CAAA,EAAA,EAAA"}
1
+ {"version":3,"file":"header2.js","names":["#grid","#computeColumnWidths","#onColumnResize","#resizeObserver","#validateColumns"],"sources":["../../../src/grid/header/header.ts"],"sourcesContent":["// SPDX-FileCopyrightText: Copyright (c) 2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved.\n// SPDX-License-Identifier: Apache-2.0\n\nimport type { PropertyValues } from 'lit';\nimport { html, LitElement } from 'lit';\nimport { queryAssignedElements } from 'lit/decorators/query-assigned-elements.js';\nimport {\n useStyles,\n attachInternals,\n debounce,\n LogService,\n audit,\n GlobalStateService\n} from '@nvidia-elements/core/internal';\nimport styles from './header.css?inline';\nimport { GridColumn } from '../column/column.js';\nimport type { Grid } from '../grid.js';\nimport { GridRow } from '../row/row.js';\nimport { GridCell } from '../cell/cell.js';\n\n/**\n * @element nve-grid-header\n * @description Contains the column headers of a grid, managing column widths and providing structural context for the data rows below.\n * @since 0.11.0\n * @entrypoint \\@nvidia-elements/core/grid\n * @slot - default slot for `nve-grid-column`\n * @cssprop --background\n * @cssprop --border-bottom\n * @cssprop --padding\n * @aria https://www.w3.org/WAI/ARIA/apg/patterns/grid/\n */\n@audit()\nexport class GridHeader extends LitElement {\n static styles = useStyles([styles]);\n\n static readonly metadata = {\n tag: 'nve-grid-header',\n version: '0.0.0',\n children: [GridColumn.metadata.tag]\n };\n\n /** @private */\n declare _internals: ElementInternals;\n\n /** @private */\n @queryAssignedElements({\n selector: GridColumn.metadata.tag,\n flatten: true\n })\n columns!: GridColumn[];\n\n get #grid() {\n return this.parentElement as Grid;\n }\n\n render() {\n return html`\n <div internal-host>\n <slot @slotchange=${() => this.#computeColumnWidths()}></slot>\n </div>\n `;\n }\n\n connectedCallback() {\n super.connectedCallback();\n attachInternals(this);\n this._internals.role = 'row';\n this.addEventListener('nve-grid-column-resize', this.#onColumnResize);\n this.#resizeObserver ??= new ResizeObserver(debounce(() => this.#computeColumnWidths(), 100));\n this.#resizeObserver.observe(this);\n }\n\n disconnectedCallback() {\n super.disconnectedCallback();\n this.removeEventListener('nve-grid-column-resize', this.#onColumnResize);\n this.#resizeObserver?.disconnect();\n }\n\n #onColumnResize = () => {\n void this.#computeColumnWidths();\n };\n\n #resizeObserver?: ResizeObserver;\n\n async firstUpdated(props: PropertyValues<this>) {\n super.firstUpdated(props);\n await this.updateComplete;\n this.#validateColumns();\n }\n\n async #computeColumnWidths() {\n await this.updateComplete;\n this.columns.forEach((c, i) => (c.ariaColIndex = `${i + 1}`));\n this.#grid.style.setProperty('--grid-auto-flow', 'initial');\n this.#grid.style.setProperty('--grid-template-column', this.columns.map((_, i) => `var(--c${i})`).join(' '));\n\n // compute initial column width\n this.columns.forEach((c, i) => this.#grid.style.setProperty(`--c${i}`, c.width ? c.width : `1fr`));\n\n // compute column width based on content\n await this.updateComplete;\n const widths = this.columns.map(c => (c.width ? c.width : `minmax(auto, ${c.getBoundingClientRect().width}px)`));\n widths.forEach((w, i) => this.#grid.style.setProperty(`--c${i}`, w));\n }\n\n #validateColumns() {\n if (GlobalStateService.state.env !== 'production') {\n const cells = this.#grid.querySelector(GridRow.metadata.tag)?.querySelectorAll(GridCell.metadata.tag);\n if (this.columns && cells && this.columns.length !== cells.length) {\n LogService.error(`grid-column (${this.columns.length}) and grid-cell (${cells.length}) count mismatch`);\n }\n }\n }\n}\n"],"mappings":";;;;;;;;;;;;;;AAgCO,IAAA,IAAA,cAAyB,EAAW;;gBACzB,EAAU,CAAC,EAAO,CAAC;;;kBAER;GACzB,KAAK;GACL,SAAS;GACT,UAAU,CAAC,EAAW,SAAS,IAAA;GAChC;;CAYD,KAAA,IAAY;AACV,SAAO,KAAK;;CAGd,SAAS;AACP,SAAO,CAAI,+CAEmB,MAAA,GAA2B,CAAC;;CAK5D,oBAAoB;AAMlB,EALA,MAAM,mBAAmB,EACzB,EAAgB,KAAK,EACrB,KAAK,WAAW,OAAO,OACvB,KAAK,iBAAiB,0BAA0B,MAAA,EAAqB,EACrE,MAAA,MAAyB,IAAI,eAAe,QAAe,MAAA,GAA2B,EAAE,IAAI,CAAC,EAC7F,MAAA,EAAqB,QAAQ,KAAK;;CAGpC,uBAAuB;AAGrB,EAFA,MAAM,sBAAsB,EAC5B,KAAK,oBAAoB,0BAA0B,MAAA,EAAqB,EACxE,MAAA,GAAsB,YAAY;;CAGpC,WAAwB;AACjB,QAAA,GAA2B;;CAGlC;CAEA,MAAM,aAAa,GAA6B;AAG9C,EAFA,MAAM,aAAa,EAAM,EACzB,MAAM,KAAK,gBACX,MAAA,GAAuB;;CAGzB,OAAA,IAA6B;AAWZ,EAVf,MAAM,KAAK,gBACX,KAAK,QAAQ,SAAS,GAAG,MAAO,EAAE,eAAe,GAAG,IAAI,IAAK,EAC7D,MAAA,EAAW,MAAM,YAAY,oBAAoB,UAAU,EAC3D,MAAA,EAAW,MAAM,YAAY,0BAA0B,KAAK,QAAQ,KAAK,GAAG,MAAM,UAAU,EAAE,GAAG,CAAC,KAAK,IAAI,CAAC,EAG5G,KAAK,QAAQ,SAAS,GAAG,MAAM,MAAA,EAAW,MAAM,YAAY,MAAM,KAAK,EAAE,QAAQ,EAAE,QAAQ,MAAM,CAAC,EAGlG,MAAM,KAAK,gBACI,KAAK,QAAQ,KAAI,MAAM,EAAE,QAAQ,EAAE,QAAQ,gBAAgB,EAAE,uBAAuB,CAAC,MAAM,KAAM,CACzG,SAAS,GAAG,MAAM,MAAA,EAAW,MAAM,YAAY,MAAM,KAAK,EAAE,CAAC;;CAGtE,KAAmB;AACjB,MAAI,EAAmB,MAAM,QAAQ,cAAc;GACjD,IAAM,IAAQ,MAAA,EAAW,cAAc,EAAQ,SAAS,IAAI,EAAE,iBAAiB,EAAS,SAAS,IAAI;AACrG,GAAI,KAAK,WAAW,KAAS,KAAK,QAAQ,WAAW,EAAM,UACzD,EAAW,MAAM,gBAAgB,KAAK,QAAQ,OAAO,mBAAmB,EAAM,OAAO,kBAAkB;;;;GAhE5G,EAAsB;CACrB,UAAU,EAAW,SAAS;CAC9B,SAAS;CACV,CAAC,CAAA,EAAA,EAAA,WAAA,WAAA,KAAA,EAAA,SAjBH,GAAO,CAAA,EAAA,EAAA"}
@@ -10,7 +10,7 @@ var a = class extends r {
10
10
  static {
11
11
  this.metadata = {
12
12
  tag: "nve-grid-placeholder",
13
- version: "0.0.10"
13
+ version: "0.0.11"
14
14
  };
15
15
  }
16
16
  render() {
@@ -15,7 +15,7 @@ var u = class extends s {
15
15
  static {
16
16
  this.metadata = {
17
17
  tag: "nve-grid-row",
18
- version: "0.0.10",
18
+ version: "0.0.11",
19
19
  children: [a.metadata.tag]
20
20
  };
21
21
  }
@@ -3,7 +3,7 @@
3
3
  "entrypoint": "@nvidia-elements/core/icon/icon.examples.json",
4
4
  "items": [
5
5
  {
6
- "id": "core-icon_default",
6
+ "id": "icon",
7
7
  "name": "Default",
8
8
  "template": "<nve-icon name=\"person\"></nve-icon>\n",
9
9
  "summary": "Basic icon component with standard appearance and usage for visual communication and interface navigation.",
@@ -12,7 +12,7 @@
12
12
  "tags": []
13
13
  },
14
14
  {
15
- "id": "core-icon_statuses",
15
+ "id": "icon-statuses",
16
16
  "name": "Statuses",
17
17
  "template": "<nve-icon name=\"person\"></nve-icon>\n<nve-icon name=\"person\" status=\"accent\"></nve-icon>\n<nve-icon name=\"person\" status=\"success\"></nve-icon>\n<nve-icon name=\"person\" status=\"warning\"></nve-icon>\n<nve-icon name=\"person\" status=\"danger\"></nve-icon>\n",
18
18
  "summary": "Semantic color variations to communicate different states, priorities, and contextual meanings in user interfaces.",
@@ -21,7 +21,7 @@
21
21
  "tags": []
22
22
  },
23
23
  {
24
- "id": "core-icon_size",
24
+ "id": "icon-size",
25
25
  "name": "Size",
26
26
  "template": "<nve-icon name=\"person\" size=\"sm\"></nve-icon>\n<nve-icon name=\"person\"></nve-icon>\n<nve-icon name=\"person\" size=\"lg\"></nve-icon>\n",
27
27
  "summary": "Icon size variants to accommodate layout densities, touch targets, and visual hierarchy requirements.",
@@ -30,7 +30,7 @@
30
30
  "tags": []
31
31
  },
32
32
  {
33
- "id": "core-icon_direction",
33
+ "id": "icon-direction",
34
34
  "name": "Direction",
35
35
  "template": "<nve-icon name=\"arrow-stop\" direction=\"left\"></nve-icon>\n<nve-icon name=\"arrow-stop\" direction=\"right\"></nve-icon>\n<nve-icon name=\"arrow\" direction=\"up\"></nve-icon>\n<nve-icon name=\"arrow\" direction=\"down\"></nve-icon>\n<nve-icon name=\"arrow\" direction=\"left\"></nve-icon>\n<nve-icon name=\"arrow\" direction=\"right\"></nve-icon>\n<nve-icon name=\"caret\" direction=\"up\"></nve-icon>\n<nve-icon name=\"caret\" direction=\"down\"></nve-icon>\n<nve-icon name=\"caret\" direction=\"left\"></nve-icon>\n<nve-icon name=\"caret\" direction=\"right\"></nve-icon>\n<nve-icon name=\"chevron\" direction=\"up\"></nve-icon>\n<nve-icon name=\"chevron\" direction=\"down\"></nve-icon>\n<nve-icon name=\"chevron\" direction=\"left\"></nve-icon>\n<nve-icon name=\"chevron\" direction=\"right\"></nve-icon>\n",
36
36
  "summary": "Directional icons for navigation, movement, and spatial relationships, providing clear visual cues for user actions.",
@@ -39,7 +39,7 @@
39
39
  "tags": []
40
40
  },
41
41
  {
42
- "id": "core-icon_themes",
42
+ "id": "icon-themes",
43
43
  "name": "Themes",
44
44
  "template": "<div nve-theme=\"root light\">\n <nve-icon name=\"person\"></nve-icon>\n <nve-icon name=\"person\" status=\"accent\"></nve-icon>\n <nve-icon name=\"person\" status=\"success\"></nve-icon>\n <nve-icon name=\"person\" status=\"warning\"></nve-icon>\n <nve-icon name=\"person\" status=\"danger\"></nve-icon>\n</div>\n<div nve-theme=\"root dark\">\n <nve-icon name=\"person\"></nve-icon>\n <nve-icon name=\"person\" status=\"accent\"></nve-icon>\n <nve-icon name=\"person\" status=\"success\"></nve-icon>\n <nve-icon name=\"person\" status=\"warning\"></nve-icon>\n <nve-icon name=\"person\" status=\"danger\"></nve-icon>\n</div>\n",
45
45
  "summary": "Icon appearance across light and dark themes, ensuring proper contrast and visibility in different visual environments.",
@@ -50,7 +50,7 @@
50
50
  ]
51
51
  },
52
52
  {
53
- "id": "core-icon_registration",
53
+ "id": "icon-registration",
54
54
  "name": "Registration",
55
55
  "template": "<nve-icon name=\"smile\" style=\"--width: 75px; --height: 75px\"></nve-icon>\n<script type=\"module\">\n customElements.get(\"nve-icon\").add({\n smile: {\n svg: () =>\n '<svg xmlns=\"http://www.w3.org/2000/svg\" fill=\"none\" viewBox=\"0 0 48 48\"><circle cx=\"24\" cy=\"24\" r=\"16\" stroke=\"currentColor\" stroke-width=\"3\"/><circle cx=\"18\" cy=\"20\" r=\"2\" fill=\"currentColor\"/><circle cx=\"30\" cy=\"20\" r=\"2\" fill=\"currentColor\"/><path d=\"M17 29c1.5 2.5 4.2 4 7 4s5.5-1.5 7-4\" stroke=\"currentColor\" stroke-width=\"3\" stroke-linecap=\"round\"/></svg>',\n },\n });\n</script>\n",
56
56
  "summary": "Register SVG paths and make them accessible to the `<nve-icon>` element. Define icons via a string or async function returning the resulting string.",
@@ -61,7 +61,7 @@
61
61
  ]
62
62
  },
63
63
  {
64
- "id": "core-icon_alias",
64
+ "id": "icon-alias",
65
65
  "name": "Alias",
66
66
  "template": "<script type=\"module\">\n await customElements.whenDefined(\"nve-icon\");\n customElements.get(\"nve-icon\").alias({\n attached: \"paper-clip\",\n });\n</script>\n<nve-icon name=\"paper-clip\"></nve-icon>\n<nve-icon name=\"attached\"></nve-icon>\n",
67
67
  "summary": "Alias icons to a different name. This supports context-specific names or migrations between icon sets.",
@@ -72,7 +72,7 @@
72
72
  ]
73
73
  },
74
74
  {
75
- "id": "core-icon_source",
75
+ "id": "icon-source",
76
76
  "name": "Source",
77
77
  "template": "<nve-icon name=\"/static/images/test-image-1.svg\" style=\"--width: 75px; --height: 75px\"></nve-icon>\n",
78
78
  "summary": "Provide direct SVG paths for rendering.",
@@ -16,7 +16,7 @@ var f = class e extends o {
16
16
  static {
17
17
  this.metadata = {
18
18
  tag: "nve-icon",
19
- version: "0.0.10"
19
+ version: "0.0.11"
20
20
  };
21
21
  }
22
22
  static {
@@ -86,7 +86,7 @@ n([l({
86
86
  })], f.prototype, "name", void 0), n([d()], f.prototype, "svg", void 0);
87
87
  function p(t) {
88
88
  if (typeof globalThis.customElements?.get == "function") {
89
- let n = e(t.metadata.version), r = e("0.0.10");
89
+ let n = e(t.metadata.version), r = e("0.0.11");
90
90
  n.minor <= r.minor && n.major <= r.major && (t._icons = {
91
91
  ...t._icons,
92
92
  ...i
@@ -3,7 +3,7 @@
3
3
  "entrypoint": "@nvidia-elements/core/icon-button/icon-button.examples.json",
4
4
  "items": [
5
5
  {
6
- "id": "core-icon-button_default",
6
+ "id": "icon-button",
7
7
  "name": "Default",
8
8
  "template": "<nve-icon-button icon-name=\"menu\"></nve-icon-button>\n",
9
9
  "summary": "Basic icon button for compact actions and toolbar controls with minimal visual footprint.",
@@ -12,7 +12,7 @@
12
12
  "tags": []
13
13
  },
14
14
  {
15
- "id": "core-icon-button_interactions",
15
+ "id": "icon-button-interactions",
16
16
  "name": "Interactions",
17
17
  "template": "<nve-icon-button icon-name=\"menu\"></nve-icon-button>\n<nve-icon-button interaction=\"emphasis\" icon-name=\"menu\"></nve-icon-button>\n<nve-icon-button interaction=\"destructive\" icon-name=\"menu\"></nve-icon-button>\n<nve-icon-button disabled icon-name=\"menu\"></nve-icon-button>\n",
18
18
  "summary": "Icon buttons with different interaction styles including default, emphasis, destructive, and disabled states.",
@@ -21,7 +21,7 @@
21
21
  "tags": []
22
22
  },
23
23
  {
24
- "id": "core-icon-button_size",
24
+ "id": "icon-button-size",
25
25
  "name": "Size",
26
26
  "template": "<nve-icon-button size=\"sm\" icon-name=\"menu\"></nve-icon-button>\n<nve-icon-button icon-name=\"menu\"></nve-icon-button>\n<nve-icon-button size=\"lg\" icon-name=\"menu\"></nve-icon-button>\n",
27
27
  "summary": "Icon buttons in different sizes (small, medium, large) for varying contexts and visual hierarchy.",
@@ -32,7 +32,7 @@
32
32
  ]
33
33
  },
34
34
  {
35
- "id": "core-icon-button_flat-interactions",
35
+ "id": "icon-button-flat-interactions",
36
36
  "name": "FlatInteractions",
37
37
  "template": "<nve-icon-button container=\"flat\" icon-name=\"menu\"></nve-icon-button>\n<nve-icon-button container=\"flat\" interaction=\"emphasis\" icon-name=\"menu\"></nve-icon-button>\n<nve-icon-button container=\"flat\" interaction=\"destructive\" icon-name=\"menu\"></nve-icon-button>\n<nve-icon-button container=\"flat\" icon-name=\"menu\" disabled></nve-icon-button>\n",
38
38
  "summary": "Flat container icon buttons with interaction styles for minimal visual weight in dense toolbars.",
@@ -43,7 +43,7 @@
43
43
  ]
44
44
  },
45
45
  {
46
- "id": "core-icon-button_pressed",
46
+ "id": "icon-button-pressed",
47
47
  "name": "Pressed",
48
48
  "template": "<nve-icon-button pressed icon-name=\"filter-stroke\"></nve-icon-button>\n<nve-icon-button icon-name=\"filter\"></nve-icon-button>\n",
49
49
  "summary": "Icon buttons with pressed state for toggle functionality like filters or visibility controls.",
@@ -52,7 +52,7 @@
52
52
  "tags": []
53
53
  },
54
54
  {
55
- "id": "core-icon-button_pressed-flat",
55
+ "id": "icon-button-pressed-flat",
56
56
  "name": "PressedFlat",
57
57
  "template": "<nve-icon-button pressed container=\"flat\" icon-name=\"eye-hidden\" aria-label=\"show\"></nve-icon-button>\n<nve-icon-button container=\"flat\" icon-name=\"eye\" aria-label=\"hide\"></nve-icon-button>\n",
58
58
  "summary": "Flat icon buttons with pressed state for low-emphasis toggles and compact toggle controls.",
@@ -63,7 +63,7 @@
63
63
  ]
64
64
  },
65
65
  {
66
- "id": "core-icon-button_pressed-inline",
66
+ "id": "icon-button-pressed-inline",
67
67
  "name": "PressedInline",
68
68
  "template": "<nve-icon-button pressed container=\"inline\" icon-name=\"eye-hidden\" aria-label=\"show\"></nve-icon-button>\n<nve-icon-button container=\"inline\" icon-name=\"eye\" aria-label=\"hide\"></nve-icon-button>\n",
69
69
  "summary": "Inline icon buttons with pressed state for minimal toggle controls within text or content flows.",
@@ -74,7 +74,7 @@
74
74
  ]
75
75
  },
76
76
  {
77
- "id": "core-icon-button_selected",
77
+ "id": "icon-button-selected",
78
78
  "name": "Selected",
79
79
  "template": "<nve-icon-button selected icon-name=\"split-vertical\" aria-label=\"split vertical\"></nve-icon-button>\n<nve-icon-button icon-name=\"split-horizontal\" aria-label=\"split horizontal\"></nve-icon-button>\n<nve-icon-button icon-name=\"split-none\" aria-label=\"preview\"></nve-icon-button>\n",
80
80
  "summary": "Icon buttons with selected state for mutually exclusive options like view modes or layout choices.",
@@ -83,7 +83,7 @@
83
83
  "tags": []
84
84
  },
85
85
  {
86
- "id": "core-icon-button_selected-flat",
86
+ "id": "icon-button-selected-flat",
87
87
  "name": "SelectedFlat",
88
88
  "template": "<nve-icon-button selected container=\"flat\" icon-name=\"split-vertical\" aria-label=\"split vertical\"></nve-icon-button>\n<nve-icon-button container=\"flat\" icon-name=\"split-horizontal\" aria-label=\"split horizontal\"></nve-icon-button>\n<nve-icon-button container=\"flat\" icon-name=\"split-none\" aria-label=\"preview\"></nve-icon-button>\n",
89
89
  "summary": "Flat icon buttons with selected state for low-emphasis mode selection in compact toolbars.",
@@ -94,7 +94,7 @@
94
94
  ]
95
95
  },
96
96
  {
97
- "id": "core-icon-button_selected-inline",
97
+ "id": "icon-button-selected-inline",
98
98
  "name": "SelectedInline",
99
99
  "template": "<nve-icon-button selected container=\"inline\" icon-name=\"split-vertical\" aria-label=\"split vertical\"></nve-icon-button>\n<nve-icon-button container=\"inline\" icon-name=\"split-horizontal\" aria-label=\"split horizontal\"></nve-icon-button>\n<nve-icon-button container=\"inline\" icon-name=\"split-none\" aria-label=\"preview\"></nve-icon-button>\n",
100
100
  "summary": "Inline icon buttons with selected state for minimal mode selection within content flows.",
@@ -105,7 +105,7 @@
105
105
  ]
106
106
  },
107
107
  {
108
- "id": "core-icon-button_custom-icon",
108
+ "id": "icon-button-custom-icon",
109
109
  "name": "CustomIcon",
110
110
  "template": "<nve-icon-button interaction=\"emphasis\">ML</nve-icon-button>\n<nve-icon-button>🎉</nve-icon-button>\n<nve-icon-button> 🔗 <a href=\"#\" aria-label=\"custom icon button\"></a> </nve-icon-button>\n",
111
111
  "summary": "Icon buttons with custom content like text initials, emojis, or symbols for personalized actions.",
@@ -116,7 +116,7 @@
116
116
  ]
117
117
  },
118
118
  {
119
- "id": "core-icon-button_link",
119
+ "id": "icon-button-link",
120
120
  "name": "Link",
121
121
  "template": "<nve-icon-button icon-name=\"menu\">\n <a href=\"#\" aria-label=\"link to page\"></a>\n</nve-icon-button>\n",
122
122
  "summary": "Proper implementation of icon buttons with links, showing correct and incorrect anchor placement patterns.",
@@ -125,7 +125,7 @@
125
125
  "tags": []
126
126
  },
127
127
  {
128
- "id": "core-icon-button_themes",
128
+ "id": "icon-button-themes",
129
129
  "name": "Themes",
130
130
  "template": "<div nve-theme=\"root light\">\n <nve-icon-button icon-name=\"menu\"></nve-icon-button>\n <nve-icon-button interaction=\"emphasis\" icon-name=\"menu\"></nve-icon-button>\n <nve-icon-button interaction=\"destructive\" icon-name=\"menu\"></nve-icon-button>\n <nve-icon-button container=\"flat\" icon-name=\"menu\"></nve-icon-button>\n <nve-icon-button disabled icon-name=\"menu\"></nve-icon-button>\n</div>\n<div nve-theme=\"root dark\">\n <nve-icon-button icon-name=\"menu\"></nve-icon-button>\n <nve-icon-button interaction=\"emphasis\" icon-name=\"menu\"></nve-icon-button>\n <nve-icon-button interaction=\"destructive\" icon-name=\"menu\"></nve-icon-button>\n <nve-icon-button container=\"flat\" icon-name=\"menu\"></nve-icon-button>\n <nve-icon-button disabled icon-name=\"menu\"></nve-icon-button>\n</div>\n",
131
131
  "summary": "Icon buttons styled for light and dark themes with all interaction states for theme consistency.",
@@ -15,7 +15,7 @@ var l = class extends a {
15
15
  static {
16
16
  this.metadata = {
17
17
  tag: "nve-icon-button",
18
- version: "0.0.10"
18
+ version: "0.0.11"
19
19
  };
20
20
  }
21
21
  static {
package/dist/index.js CHANGED
@@ -2,7 +2,7 @@ import { getThemeTokens as e } from "./internal/utils/dom.js";
2
2
  import { I18nService as t } from "./internal/services/i18n.service.js";
3
3
  import { statusIcons as n } from "./internal/types/index.js";
4
4
  //#region src/index.ts
5
- var r = "0.0.10", i = "@nvidia-elements";
5
+ var r = "0.0.11", i = "@nvidia-elements";
6
6
  //#endregion
7
7
  export { t as I18nService, i as SCOPE, r as VERSION, e as getThemeTokens, n as statusIcons };
8
8
 
@@ -3,7 +3,7 @@
3
3
  "entrypoint": "@nvidia-elements/core/input/input-group.examples.json",
4
4
  "items": [
5
5
  {
6
- "id": "core-input-input-group_default",
6
+ "id": "input-input-group",
7
7
  "name": "Default",
8
8
  "template": "<nve-input-group>\n <label>domain</label>\n <nve-select style=\"width: 130px\">\n <select aria-label=\"protocol\">\n <option>https://</option>\n <option>http://</option>\n </select>\n </nve-select>\n <nve-input>\n <input placeholder=\"example\" type=\"url\" aria-label=\"host\" />\n <nve-button container=\"flat\" readonly>.com</nve-button>\n </nve-input>\n <nve-control-message>host: 123456</nve-control-message>\n</nve-input-group>\n",
9
9
  "summary": "Input group combining select, input, and button for composite controls like domain URL entry.",
@@ -12,7 +12,7 @@
12
12
  "tags": []
13
13
  },
14
14
  {
15
- "id": "core-input-input-group_filter-group-range",
15
+ "id": "input-input-group-filter-group-range",
16
16
  "name": "FilterGroupRange",
17
17
  "template": "<div nve-layout=\"row align:vertical-center\">\n <nve-input-group>\n <nve-select style=\"width: 150px\">\n <select aria-label=\"date type\">\n <option value=\"1\">recording date</option>\n <option value=\"2\">process date</option>\n </select>\n </nve-select>\n <nve-date style=\"width: 220px\">\n <nve-button container=\"flat\" readonly>start</nve-button>\n <input type=\"date\" value=\"2022-05-11\" aria-label=\"start date\" />\n </nve-date>\n <nve-date style=\"width: 220px\">\n <nve-button container=\"flat\" readonly>end</nve-button>\n <input type=\"date\" value=\"2022-12-07\" aria-label=\"end date\" />\n </nve-date>\n <nve-icon-button aria-label=\"remove filter\" icon-name=\"cancel\"></nve-icon-button>\n </nve-input-group>\n</div>\n",
18
18
  "summary": "Input group with date range filters combining select and date inputs for filtering data by time periods.",
@@ -11,7 +11,7 @@ var a = class extends n {
11
11
  static {
12
12
  this.metadata = {
13
13
  tag: "nve-input-group",
14
- version: "0.0.10"
14
+ version: "0.0.11"
15
15
  };
16
16
  }
17
17
  async connectedCallback() {
@@ -3,7 +3,7 @@
3
3
  "entrypoint": "@nvidia-elements/core/input/input.examples.json",
4
4
  "items": [
5
5
  {
6
- "id": "core-input_default",
6
+ "id": "input",
7
7
  "name": "Default",
8
8
  "template": "<nve-input>\n <label>label</label>\n <input type=\"text\" />\n <nve-control-message>message</nve-control-message>\n</nve-input>\n",
9
9
  "summary": "Basic text input field with label and message for general text entry and form data collection.",
@@ -12,7 +12,7 @@
12
12
  "tags": []
13
13
  },
14
14
  {
15
- "id": "core-input_standard",
15
+ "id": "input-standard",
16
16
  "name": "Standard",
17
17
  "template": "<nve-input>\n <label>label</label>\n <input type=\"text\" />\n <nve-control-message>message</nve-control-message>\n</nve-input>\n",
18
18
  "summary": "Text input with the standard input structure, label, and control message.",
@@ -21,7 +21,7 @@
21
21
  "tags": []
22
22
  },
23
23
  {
24
- "id": "core-input_vertical",
24
+ "id": "input-vertical",
25
25
  "name": "Vertical",
26
26
  "template": "<div nve-layout=\"column gap:lg full\">\n <nve-input>\n <label>label</label>\n <input />\n <nve-control-message>message</nve-control-message>\n </nve-input>\n <nve-input>\n <label>disabled</label>\n <input disabled />\n <nve-control-message>message</nve-control-message>\n </nve-input>\n <nve-input>\n <label>success</label>\n <input />\n <nve-control-message status=\"success\">message</nve-control-message>\n </nve-input>\n <nve-input>\n <label>error</label>\n <input />\n <nve-control-message status=\"error\">message</nve-control-message>\n </nve-input>\n</div>\n",
27
27
  "summary": "Text inputs with vertical layout including validation states for disabled, success, and error.",
@@ -32,7 +32,7 @@
32
32
  ]
33
33
  },
34
34
  {
35
- "id": "core-input_horizontal",
35
+ "id": "input-horizontal",
36
36
  "name": "Horizontal",
37
37
  "template": "<div nve-layout=\"column gap:lg full\">\n <nve-input layout=\"horizontal\">\n <label>label</label>\n <input />\n <nve-control-message>message</nve-control-message>\n </nve-input>\n <nve-input layout=\"horizontal\">\n <label>disabled</label>\n <input disabled />\n <nve-control-message>message</nve-control-message>\n </nve-input>\n <nve-input layout=\"horizontal\">\n <label>success</label>\n <input />\n <nve-control-message status=\"success\">message</nve-control-message>\n </nve-input>\n <nve-input layout=\"horizontal\">\n <label>error</label>\n <input />\n <nve-control-message status=\"error\">message</nve-control-message>\n </nve-input>\n</div>\n",
38
38
  "summary": "Text inputs with horizontal layout showing validation states for inline forms and compact layouts.",
@@ -43,7 +43,7 @@
43
43
  ]
44
44
  },
45
45
  {
46
- "id": "core-input_rounded",
46
+ "id": "input-rounded",
47
47
  "name": "Rounded",
48
48
  "template": "<nve-input rounded>\n <label>label</label>\n <input />\n <nve-control-message>message</nve-control-message>\n</nve-input>\n",
49
49
  "summary": "Text input with rounded corners for a softer visual appearance and modern aesthetic.",
@@ -52,7 +52,7 @@
52
52
  "tags": []
53
53
  },
54
54
  {
55
- "id": "core-input_fit-text",
55
+ "id": "input-fit-text",
56
56
  "name": "FitText",
57
57
  "template": "<nve-input fit-text>\n <label>label</label>\n <input value=\"123456789012345678901234567890\" />\n <nve-control-message>message</nve-control-message>\n</nve-input>\n",
58
58
  "summary": "Text input with fit-text styling that adjusts width to match the input value for compact displays.",
@@ -63,7 +63,7 @@
63
63
  ]
64
64
  },
65
65
  {
66
- "id": "core-input_fit-content",
66
+ "id": "input-fit-content",
67
67
  "name": "FitContent",
68
68
  "template": "<nve-input fit-content>\n <label>label</label>\n <input />\n <nve-control-message>message</nve-control-message>\n</nve-input>\n",
69
69
  "summary": "Text input with fit-content sizing that automatically adjusts width based on available space.",
@@ -74,7 +74,7 @@
74
74
  ]
75
75
  },
76
76
  {
77
- "id": "core-input_flat",
77
+ "id": "input-flat",
78
78
  "name": "Flat",
79
79
  "template": "<nve-input container=\"flat\">\n <label>label</label>\n <input />\n <nve-control-message>message</nve-control-message>\n</nve-input>\n",
80
80
  "summary": "Text input with flat container styling for minimal visual appearance and borderless design.",
@@ -14,7 +14,7 @@ var a = r, o = class extends n {
14
14
  static {
15
15
  this.metadata = {
16
16
  tag: "nve-input",
17
- version: "0.0.10"
17
+ version: "0.0.11"
18
18
  };
19
19
  }
20
20
  };
@@ -2,7 +2,7 @@
2
2
  "entrypoint": "@nvidia-elements/core/internal/controllers/i18n.controller.examples.json",
3
3
  "items": [
4
4
  {
5
- "id": "core-internal-controllers-i18n.controller_i18n-controller-demo",
5
+ "id": "internal-controllers-i18n.controller-i18n-controller-demo",
6
6
  "name": "I18nControllerDemo",
7
7
  "template": "<i18n-demo></i18n-demo>\n",
8
8
  "summary": "Internationalization controller with dynamic language switching between English and French.",
@@ -2,7 +2,7 @@
2
2
  "entrypoint": "@nvidia-elements/core/internal/controllers/keynav-grid.controller.examples.json",
3
3
  "items": [
4
4
  {
5
- "id": "core-internal-controllers-keynav-grid.controller_styles",
5
+ "id": "internal-controllers-keynav-grid.controller-styles",
6
6
  "name": "styles",
7
7
  "template": "section { display: grid; gap: 4px; grid-template-columns: repeat(10, 50px); } .vertical { grid-template-rows: repeat(10,\n1fr); grid-template-columns: 50px; } .row { display: contents; } button { width: 100%; height: 30px; min-width: 30px;\ndisplay: block; } button[selected] { background: green; color: white; }\n",
8
8
  "summary": "",
@@ -11,7 +11,7 @@
11
11
  "tags": []
12
12
  },
13
13
  {
14
- "id": "core-internal-controllers-keynav-grid.controller_grid-demo",
14
+ "id": "internal-controllers-keynav-grid.controller-grid-demo",
15
15
  "name": "GridDemo",
16
16
  "template": "<demo-key-navigation-grid></demo-key-navigation-grid>\n",
17
17
  "summary": "Grid-based keyboard navigation controller with arrow key support across rows and columns.",
@@ -94,21 +94,29 @@ function _(e, t) {
94
94
  dy: 4
95
95
  } : null;
96
96
  }
97
- function v(e, t, n, r, i, a) {
97
+ function v(e, t, n) {
98
+ let { x: r, y: i } = t, { columnCount: a, rowCount: s, ctrlKey: c } = n;
98
99
  return e === o.End ? {
99
- x: r,
100
- y: a ? i : n
100
+ x: a,
101
+ y: c ? s : i
101
102
  } : e === o.Home ? {
102
103
  x: 0,
103
- y: a ? 0 : n
104
+ y: c ? 0 : i
104
105
  } : {
105
- x: t,
106
- y: n
106
+ x: r,
107
+ y: i
107
108
  };
108
109
  }
109
110
  function y(e, t, n) {
110
111
  let r = e.find((e) => e.tabIndex === 0), i = t.find((e) => s(e).find((e) => e === r)), a = Array.from(s(i)).filter((t) => !!e.find((e) => e === t)), o = t.length - 1, c = a.length - 1, l = a.indexOf(r), u = t.indexOf(i), d = _(n.code, n.dir);
111
- return d ? (l = Math.max(0, Math.min(c, l + d.dx)), u = Math.max(0, Math.min(o, u + d.dy))) : {x: l, y: u} = v(n.code, l, u, c, o, n.ctrlKey), {
112
+ return d ? (l = Math.max(0, Math.min(c, l + d.dx)), u = Math.max(0, Math.min(o, u + d.dy))) : {x: l, y: u} = v(n.code, {
113
+ x: l,
114
+ y: u
115
+ }, {
116
+ columnCount: c,
117
+ rowCount: o,
118
+ ctrlKey: n.ctrlKey
119
+ }), {
112
120
  x: l,
113
121
  y: u
114
122
  };
@@ -1 +1 @@
1
- {"version":3,"file":"keynav-grid.controller.js","names":["#config","#hostRows","#hostCells","#updateCellActivation","#keynavCell","#clickCell","#observers","#setActiveCell"],"sources":["../../../src/internal/controllers/keynav-grid.controller.ts"],"sourcesContent":["// SPDX-FileCopyrightText: Copyright (c) 2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved.\n// SPDX-License-Identifier: Apache-2.0\n\nimport type { ReactiveController, ReactiveElement } from 'lit';\nimport type { LegacyDecoratorTarget } from '../types/index.js';\nimport { onChildListMutation, throttle } from '../utils/events.js';\nimport { GlobalStateService } from '../services/global.service.js';\nimport { LogService } from '../services/log.service.js';\nimport {\n validKeyNavigationCode,\n isContextMenuClick,\n getFlattenedDOMTree,\n getFlattenedFocusableItems,\n KeynavCode,\n hasInvalidDOMGrid\n} from '../utils/dom.js';\nimport {\n focusElement,\n getActiveElement,\n initializeKeyListItems,\n setActiveKeyListItem,\n isSimpleFocusable\n} from '../utils/focus.js';\n\nexport interface KeynavGridConfig {\n grid?: HTMLElement;\n columnRow?: HTMLElement;\n columns?: NodeListOf<HTMLElement> | HTMLElement[];\n rows: NodeListOf<HTMLElement> | HTMLElement[];\n cells: NodeListOf<HTMLElement> | HTMLElement[];\n}\n\nexport interface KeynavGridElement {\n keynavGridConfig: KeynavGridConfig;\n}\n\n/**\n * https://w3c.github.io/aria-practices/#gridNav_focus\n */\nexport function keyNavigationGrid<T extends ReactiveElement & KeynavGridElement>(): ClassDecorator {\n return (target: LegacyDecoratorTarget) =>\n target.addInitializer!((instance: T) => new KeyNavigationGridController(instance));\n}\n\nexport class KeyNavigationGridController<T extends ReactiveElement & KeynavGridElement> implements ReactiveController {\n #observers: MutationObserver[] = [];\n\n get #config() {\n return {\n grid: this.host,\n ...this.host.keynavGridConfig\n };\n }\n\n get #hostRows() {\n const rows = Array.from(this.#config.rows);\n\n if (this.#config.columnRow) {\n rows.unshift(this.#config.columnRow);\n }\n\n return rows;\n }\n\n get #hostCells() {\n return [...Array.from(this.#config.columns ?? []), ...Array.from(this.#config.cells)];\n }\n\n constructor(private host: T) {\n this.host.addController(this);\n }\n\n async hostConnected() {\n await this.host.updateComplete;\n initializeKeyListItems(this.#hostCells);\n this.#config.grid.addEventListener('keyup', (e: KeyboardEvent) => this.#updateCellActivation(e));\n this.#config.grid.addEventListener('keydown', (e: KeyboardEvent) => this.#keynavCell(e));\n this.#config.grid.addEventListener('mouseup', (e: MouseEvent) => this.#clickCell(e));\n this.#observers.push(\n onChildListMutation(\n this.host,\n throttle(() => initializeKeyListItems(this.#hostCells), 500)\n )\n );\n }\n\n hostDisconnected() {\n this.#observers.forEach(o => o?.disconnect());\n }\n\n #clickCell(e: MouseEvent) {\n if (!isContextMenuClick(e)) {\n const focusedElement = e.composedPath()[0] as HTMLElement;\n const activeCell = this.#hostCells.find(i => i === focusedElement) ? focusedElement : null;\n if (activeCell) {\n this.#setActiveCell(e, activeCell as HTMLElement);\n }\n }\n }\n\n #keynavCell(e: KeyboardEvent) {\n const rows = Array.from(this.#hostRows);\n const cells = Array.from(this.#hostCells);\n\n if (GlobalStateService.state.env !== 'production' && hasInvalidDOMGrid(rows)) {\n LogService.warn('Invalid grid structure, all rows must have the same number of cells');\n return;\n }\n\n if (validKeyNavigationCode(e) && isSimpleFocusable(getActiveElement() as Element)) {\n const { x, y } = getNextKeyGridItem(cells, rows, {\n code: e.code,\n ctrlKey: e.ctrlKey,\n dir: this.host.dir\n });\n\n const nextCell = Array.from(getFlattenedDOMTree(rows[y]!)).filter(c => !!cells.find(i => i === c))[\n x\n ] as HTMLElement;\n this.#setActiveCell(e, nextCell);\n e.preventDefault();\n }\n }\n\n #setActiveCell(e: KeyboardEvent | MouseEvent, activeCell: HTMLElement) {\n setActiveKeyListItem(this.#hostCells, activeCell);\n\n const items = getFlattenedFocusableItems(activeCell);\n const simpleItems = items.filter(i => isSimpleFocusable(i));\n\n if (simpleItems.length === 1 && items.length === 1) {\n focusElement(simpleItems[0]!);\n } else {\n focusElement(activeCell);\n }\n\n const detail = { code: e instanceof KeyboardEvent ? e.code : null, shiftKey: e.shiftKey, activeItem: activeCell };\n activeCell.dispatchEvent(new CustomEvent('nve-key-change', { bubbles: true, composed: true, detail }));\n }\n\n #updateCellActivation(e: KeyboardEvent) {\n const activeCell = Array.from(this.#hostCells).find(i => i.tabIndex === 0) as HTMLElement;\n if (e.code === 'Escape') {\n activeCell?.focus();\n }\n\n if (e.code === 'Enter' && activeCell === e.composedPath()[0]) {\n getFlattenedFocusableItems(activeCell as HTMLElement)[0]?.focus();\n }\n }\n}\n\nfunction getGridDelta(code: KeynavCode | string, dir: string): { dx: number; dy: number } | null {\n const start = dir === 'rtl' ? KeynavCode.ArrowRight : KeynavCode.ArrowLeft;\n const end = dir === 'rtl' ? KeynavCode.ArrowLeft : KeynavCode.ArrowRight;\n\n if (code === KeynavCode.ArrowUp) return { dx: 0, dy: -1 };\n if (code === KeynavCode.ArrowDown) return { dx: 0, dy: 1 };\n if (code === start) return { dx: -1, dy: 0 };\n if (code === end) return { dx: 1, dy: 0 };\n if (code === KeynavCode.PageUp) return { dx: 0, dy: -4 };\n if (code === KeynavCode.PageDown) return { dx: 0, dy: 4 };\n return null;\n}\n\nfunction applyGridHomeEnd(\n code: KeynavCode | string,\n x: number,\n y: number,\n columnCount: number,\n rowCount: number,\n ctrlKey: boolean\n) {\n if (code === KeynavCode.End) {\n return { x: columnCount, y: ctrlKey ? rowCount : y };\n }\n\n if (code === KeynavCode.Home) {\n return { x: 0, y: ctrlKey ? 0 : y };\n }\n\n return { x, y };\n}\n\nexport function getNextKeyGridItem(\n cells: HTMLElement[],\n rows: HTMLElement[],\n config: { code: KeynavCode | string; ctrlKey: boolean; dir: string }\n) {\n const currentCell = cells.find(i => i.tabIndex === 0) as HTMLElement;\n const currentRow = rows.find(r => getFlattenedDOMTree(r).find(c => c === currentCell)) as HTMLElement;\n const currentRowCells = Array.from(getFlattenedDOMTree(currentRow)).filter(c => !!cells.find(i => i === c));\n const rowCount = rows.length - 1;\n const columnCount = currentRowCells.length - 1;\n\n let x = currentRowCells.indexOf(currentCell);\n let y = rows.indexOf(currentRow);\n\n const delta = getGridDelta(config.code, config.dir);\n if (delta) {\n x = Math.max(0, Math.min(columnCount, x + delta.dx));\n y = Math.max(0, Math.min(rowCount, y + delta.dy));\n } else {\n ({ x, y } = applyGridHomeEnd(config.code, x, y, columnCount, rowCount, config.ctrlKey));\n }\n\n return { x, y };\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"keynav-grid.controller.js","names":["#config","#hostRows","#hostCells","#updateCellActivation","#keynavCell","#clickCell","#observers","#setActiveCell"],"sources":["../../../src/internal/controllers/keynav-grid.controller.ts"],"sourcesContent":["// SPDX-FileCopyrightText: Copyright (c) 2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved.\n// SPDX-License-Identifier: Apache-2.0\n\nimport type { ReactiveController, ReactiveElement } from 'lit';\nimport type { LegacyDecoratorTarget } from '../types/index.js';\nimport { onChildListMutation, throttle } from '../utils/events.js';\nimport { GlobalStateService } from '../services/global.service.js';\nimport { LogService } from '../services/log.service.js';\nimport {\n validKeyNavigationCode,\n isContextMenuClick,\n getFlattenedDOMTree,\n getFlattenedFocusableItems,\n KeynavCode,\n hasInvalidDOMGrid\n} from '../utils/dom.js';\nimport {\n focusElement,\n getActiveElement,\n initializeKeyListItems,\n setActiveKeyListItem,\n isSimpleFocusable\n} from '../utils/focus.js';\n\nexport interface KeynavGridConfig {\n grid?: HTMLElement;\n columnRow?: HTMLElement;\n columns?: NodeListOf<HTMLElement> | HTMLElement[];\n rows: NodeListOf<HTMLElement> | HTMLElement[];\n cells: NodeListOf<HTMLElement> | HTMLElement[];\n}\n\nexport interface KeynavGridElement {\n keynavGridConfig: KeynavGridConfig;\n}\n\n/**\n * https://w3c.github.io/aria-practices/#gridNav_focus\n */\nexport function keyNavigationGrid<T extends ReactiveElement & KeynavGridElement>(): ClassDecorator {\n return (target: LegacyDecoratorTarget) =>\n target.addInitializer!((instance: T) => new KeyNavigationGridController(instance));\n}\n\nexport class KeyNavigationGridController<T extends ReactiveElement & KeynavGridElement> implements ReactiveController {\n #observers: MutationObserver[] = [];\n\n get #config() {\n return {\n grid: this.host,\n ...this.host.keynavGridConfig\n };\n }\n\n get #hostRows() {\n const rows = Array.from(this.#config.rows);\n\n if (this.#config.columnRow) {\n rows.unshift(this.#config.columnRow);\n }\n\n return rows;\n }\n\n get #hostCells() {\n return [...Array.from(this.#config.columns ?? []), ...Array.from(this.#config.cells)];\n }\n\n constructor(private host: T) {\n this.host.addController(this);\n }\n\n async hostConnected() {\n await this.host.updateComplete;\n initializeKeyListItems(this.#hostCells);\n this.#config.grid.addEventListener('keyup', (e: KeyboardEvent) => this.#updateCellActivation(e));\n this.#config.grid.addEventListener('keydown', (e: KeyboardEvent) => this.#keynavCell(e));\n this.#config.grid.addEventListener('mouseup', (e: MouseEvent) => this.#clickCell(e));\n this.#observers.push(\n onChildListMutation(\n this.host,\n throttle(() => initializeKeyListItems(this.#hostCells), 500)\n )\n );\n }\n\n hostDisconnected() {\n this.#observers.forEach(o => o?.disconnect());\n }\n\n #clickCell(e: MouseEvent) {\n if (!isContextMenuClick(e)) {\n const focusedElement = e.composedPath()[0] as HTMLElement;\n const activeCell = this.#hostCells.find(i => i === focusedElement) ? focusedElement : null;\n if (activeCell) {\n this.#setActiveCell(e, activeCell as HTMLElement);\n }\n }\n }\n\n #keynavCell(e: KeyboardEvent) {\n const rows = Array.from(this.#hostRows);\n const cells = Array.from(this.#hostCells);\n\n if (GlobalStateService.state.env !== 'production' && hasInvalidDOMGrid(rows)) {\n LogService.warn('Invalid grid structure, all rows must have the same number of cells');\n return;\n }\n\n if (validKeyNavigationCode(e) && isSimpleFocusable(getActiveElement() as Element)) {\n const { x, y } = getNextKeyGridItem(cells, rows, {\n code: e.code,\n ctrlKey: e.ctrlKey,\n dir: this.host.dir\n });\n\n const nextCell = Array.from(getFlattenedDOMTree(rows[y]!)).filter(c => !!cells.find(i => i === c))[\n x\n ] as HTMLElement;\n this.#setActiveCell(e, nextCell);\n e.preventDefault();\n }\n }\n\n #setActiveCell(e: KeyboardEvent | MouseEvent, activeCell: HTMLElement) {\n setActiveKeyListItem(this.#hostCells, activeCell);\n\n const items = getFlattenedFocusableItems(activeCell);\n const simpleItems = items.filter(i => isSimpleFocusable(i));\n\n if (simpleItems.length === 1 && items.length === 1) {\n focusElement(simpleItems[0]!);\n } else {\n focusElement(activeCell);\n }\n\n const detail = { code: e instanceof KeyboardEvent ? e.code : null, shiftKey: e.shiftKey, activeItem: activeCell };\n activeCell.dispatchEvent(new CustomEvent('nve-key-change', { bubbles: true, composed: true, detail }));\n }\n\n #updateCellActivation(e: KeyboardEvent) {\n const activeCell = Array.from(this.#hostCells).find(i => i.tabIndex === 0) as HTMLElement;\n if (e.code === 'Escape') {\n activeCell?.focus();\n }\n\n if (e.code === 'Enter' && activeCell === e.composedPath()[0]) {\n getFlattenedFocusableItems(activeCell as HTMLElement)[0]?.focus();\n }\n }\n}\n\nfunction getGridDelta(code: KeynavCode | string, dir: string): { dx: number; dy: number } | null {\n const start = dir === 'rtl' ? KeynavCode.ArrowRight : KeynavCode.ArrowLeft;\n const end = dir === 'rtl' ? KeynavCode.ArrowLeft : KeynavCode.ArrowRight;\n\n if (code === KeynavCode.ArrowUp) return { dx: 0, dy: -1 };\n if (code === KeynavCode.ArrowDown) return { dx: 0, dy: 1 };\n if (code === start) return { dx: -1, dy: 0 };\n if (code === end) return { dx: 1, dy: 0 };\n if (code === KeynavCode.PageUp) return { dx: 0, dy: -4 };\n if (code === KeynavCode.PageDown) return { dx: 0, dy: 4 };\n return null;\n}\n\nfunction applyGridHomeEnd(\n code: KeynavCode | string,\n position: { x: number; y: number },\n bounds: { columnCount: number; rowCount: number; ctrlKey: boolean }\n) {\n const { x, y } = position;\n const { columnCount, rowCount, ctrlKey } = bounds;\n if (code === KeynavCode.End) {\n return { x: columnCount, y: ctrlKey ? rowCount : y };\n }\n\n if (code === KeynavCode.Home) {\n return { x: 0, y: ctrlKey ? 0 : y };\n }\n\n return { x, y };\n}\n\nexport function getNextKeyGridItem(\n cells: HTMLElement[],\n rows: HTMLElement[],\n config: { code: KeynavCode | string; ctrlKey: boolean; dir: string }\n) {\n const currentCell = cells.find(i => i.tabIndex === 0) as HTMLElement;\n const currentRow = rows.find(r => getFlattenedDOMTree(r).find(c => c === currentCell)) as HTMLElement;\n const currentRowCells = Array.from(getFlattenedDOMTree(currentRow)).filter(c => !!cells.find(i => i === c));\n const rowCount = rows.length - 1;\n const columnCount = currentRowCells.length - 1;\n\n let x = currentRowCells.indexOf(currentCell);\n let y = rows.indexOf(currentRow);\n\n const delta = getGridDelta(config.code, config.dir);\n if (delta) {\n x = Math.max(0, Math.min(columnCount, x + delta.dx));\n y = Math.max(0, Math.min(rowCount, y + delta.dy));\n } else {\n ({ x, y } = applyGridHomeEnd(config.code, { x, y }, { columnCount, rowCount, ctrlKey: config.ctrlKey }));\n }\n\n return { x, y };\n}\n"],"mappings":"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"}
@@ -2,7 +2,7 @@
2
2
  "entrypoint": "@nvidia-elements/core/internal/controllers/keynav-list.controller.examples.json",
3
3
  "items": [
4
4
  {
5
- "id": "core-internal-controllers-keynav-list.controller_styles",
5
+ "id": "internal-controllers-keynav-list.controller-styles",
6
6
  "name": "styles",
7
7
  "template": "section { display: grid; gap: 4px; grid-template-columns: repeat(10, 50px); } .vertical { grid-template-rows: repeat(10,\n1fr); grid-template-columns: 50px; } .row { display: contents; } button { width: 100%; height: 30px; min-width: 30px;\ndisplay: block; } button[selected] { background: green; color: white; }\n",
8
8
  "summary": "",
@@ -11,7 +11,7 @@
11
11
  "tags": []
12
12
  },
13
13
  {
14
- "id": "core-internal-controllers-keynav-list.controller_list-demo",
14
+ "id": "internal-controllers-keynav-list.controller-list-demo",
15
15
  "name": "ListDemo",
16
16
  "template": "<demo-key-navigation-list></demo-key-navigation-list>\n",
17
17
  "summary": "Horizontal list keyboard navigation controller with arrow key support.",
@@ -22,7 +22,7 @@
22
22
  ]
23
23
  },
24
24
  {
25
- "id": "core-internal-controllers-keynav-list.controller_vertical-demo",
25
+ "id": "internal-controllers-keynav-list.controller-vertical-demo",
26
26
  "name": "VerticalDemo",
27
27
  "template": "<demo-key-navigation-list-vertical></demo-key-navigation-list-vertical>\n",
28
28
  "summary": "Vertical list keyboard navigation controller with up and down arrow key support.",
@@ -33,7 +33,7 @@
33
33
  ]
34
34
  },
35
35
  {
36
- "id": "core-internal-controllers-keynav-list.controller_loop-demo",
36
+ "id": "internal-controllers-keynav-list.controller-loop-demo",
37
37
  "name": "LoopDemo",
38
38
  "template": "<demo-key-navigation-list-loop></demo-key-navigation-list-loop>\n",
39
39
  "summary": "Vertical list keyboard navigation with looping enabled to wrap from last item to first.",
@@ -83,18 +83,24 @@ function s(e) {
83
83
  function c(e) {
84
84
  return e === r.End ? "end" : e === r.Home ? "home" : e === r.PageUp ? "pageup" : e === r.PageDown ? "pagedown" : null;
85
85
  }
86
- function l(e, t, n, r) {
87
- let i = e + n;
88
- return i >= 0 && i <= t ? i : r ? n < 0 ? t : 0 : e;
86
+ function l(e, t, n) {
87
+ let { limit: r, loop: i } = n, a = e + t;
88
+ return a >= 0 && a <= r ? a : i ? t < 0 ? r : 0 : e;
89
89
  }
90
90
  function u(e, t, n) {
91
91
  let r = t.indexOf(e), i = r, a = t.length - 1;
92
92
  switch (s(n) ?? c(n.code)) {
93
93
  case "backward":
94
- r = l(r, a, -1, n.loop);
94
+ r = l(r, -1, {
95
+ limit: a,
96
+ loop: n.loop
97
+ });
95
98
  break;
96
99
  case "forward":
97
- r = l(r, a, 1, n.loop);
100
+ r = l(r, 1, {
101
+ limit: a,
102
+ loop: n.loop
103
+ });
98
104
  break;
99
105
  case "end":
100
106
  r = a;