@fusion.dev/helix-headless 0.147.0 → 0.149.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (296) hide show
  1. package/custom-elements.json +11222 -2332
  2. package/dist/accordion/item/accordion-item.d.ts +5 -2
  3. package/dist/accordion/item/accordion-item.js +11 -7
  4. package/dist/accordion/root/accordion-root.js +4 -6
  5. package/dist/announcement/root/announcement-root.d.ts +61 -5
  6. package/dist/announcement/root/announcement-root.js +126 -20
  7. package/dist/area-chart/root/area-chart-root.d.ts +11 -0
  8. package/dist/area-chart/root/area-chart-root.js +21 -9
  9. package/dist/avatar/group/avatar-group.d.ts +10 -2
  10. package/dist/avatar/group/avatar-group.js +10 -5
  11. package/dist/badge/count.d.ts +19 -0
  12. package/dist/badge/count.js +20 -0
  13. package/dist/badge/root/badge-root.d.ts +6 -2
  14. package/dist/badge/root/badge-root.js +8 -22
  15. package/dist/bar-chart/root/bar-chart-root.d.ts +13 -1
  16. package/dist/bar-chart/root/bar-chart-root.js +17 -4
  17. package/dist/blockquote/root/blockquote-root.d.ts +66 -8
  18. package/dist/blockquote/root/blockquote-root.js +85 -8
  19. package/dist/breadcrumbs/breadcrumb/breadcrumb.js +2 -2
  20. package/dist/breadcrumbs/root/breadcrumbs-root.d.ts +8 -1
  21. package/dist/breadcrumbs/root/breadcrumbs-root.js +5 -2
  22. package/dist/button/root/button-root.d.ts +10 -1
  23. package/dist/button/root/button-root.js +3 -2
  24. package/dist/button-group/arrows.d.ts +14 -0
  25. package/dist/button-group/arrows.js +10 -0
  26. package/dist/button-group/root/button-group-root.d.ts +144 -3
  27. package/dist/button-group/root/button-group-root.js +142 -2
  28. package/dist/callout/root/callout-root.d.ts +16 -2
  29. package/dist/callout/root/callout-root.js +16 -4
  30. package/dist/canvas/describe.d.ts +10 -0
  31. package/dist/canvas/describe.js +9 -0
  32. package/dist/canvas/edge-pan.d.ts +61 -0
  33. package/dist/canvas/edge-pan.js +63 -0
  34. package/dist/canvas/neighbor.d.ts +17 -0
  35. package/dist/canvas/neighbor.js +1 -0
  36. package/dist/canvas/node/canvas-node.d.ts +12 -2
  37. package/dist/canvas/node/canvas-node.js +8 -3
  38. package/dist/canvas/root/canvas-document.d.ts +10 -0
  39. package/dist/canvas/root/canvas-document.js +1 -0
  40. package/dist/canvas/root/canvas-root.d.ts +168 -9
  41. package/dist/canvas/root/canvas-root.js +239 -69
  42. package/dist/canvas/snap.d.ts +42 -0
  43. package/dist/canvas/snap.js +32 -0
  44. package/dist/carousel/root/carousel-root.d.ts +9 -3
  45. package/dist/carousel/root/carousel-root.js +17 -10
  46. package/dist/chat/composer/chat-composer.d.ts +5 -0
  47. package/dist/chat/composer/chat-composer.js +4 -1
  48. package/dist/chat/message/chat-message.d.ts +9 -5
  49. package/dist/chat/message/chat-message.js +8 -4
  50. package/dist/chat/naming.js +2 -2
  51. package/dist/chat/root/chat-root.d.ts +40 -4
  52. package/dist/chat/root/chat-root.js +38 -14
  53. package/dist/checkbox/root/checkbox-root.d.ts +11 -0
  54. package/dist/checkbox/root/checkbox-root.js +8 -2
  55. package/dist/checkbox-group/root/checkbox-group-root.d.ts +24 -0
  56. package/dist/checkbox-group/root/checkbox-group-root.js +28 -12
  57. package/dist/checkbox-group/select-all.d.ts +11 -0
  58. package/dist/checkbox-group/select-all.js +5 -0
  59. package/dist/code-block/root/code-block-root.d.ts +20 -8
  60. package/dist/code-block/root/code-block-root.js +16 -5
  61. package/dist/color-input/root/color-input-root.d.ts +13 -0
  62. package/dist/color-input/root/color-input-root.js +18 -5
  63. package/dist/color-picker/root/color-picker-root.d.ts +19 -3
  64. package/dist/color-picker/root/color-picker-root.js +52 -24
  65. package/dist/color-picker/wheel.d.ts +11 -0
  66. package/dist/color-picker/wheel.js +9 -0
  67. package/dist/combobox/root/combobox-root.d.ts +106 -18
  68. package/dist/combobox/root/combobox-root.js +101 -26
  69. package/dist/command/root/command-root.d.ts +19 -9
  70. package/dist/command/root/command-root.js +9 -4
  71. package/dist/copy-button/root/copy-button-root.d.ts +5 -0
  72. package/dist/copy-button/root/copy-button-root.js +7 -2
  73. package/dist/data-table/root/data-table-root.d.ts +171 -29
  74. package/dist/data-table/root/data-table-root.js +284 -161
  75. package/dist/date-input/root/date-input-root.d.ts +32 -9
  76. package/dist/date-input/root/date-input-root.js +66 -44
  77. package/dist/date-picker/root/date-picker-root.d.ts +38 -15
  78. package/dist/date-picker/root/date-picker-root.js +52 -33
  79. package/dist/description-list/item/description-list-item.d.ts +4 -0
  80. package/dist/description-list/item/description-list-item.js +7 -1
  81. package/dist/dialog/root/dialog-root.d.ts +12 -1
  82. package/dist/dialog/root/dialog-root.js +11 -4
  83. package/dist/divider/root/divider-root.d.ts +45 -16
  84. package/dist/divider/root/divider-root.js +28 -4
  85. package/dist/donut-chart/root/donut-chart-root.d.ts +5 -0
  86. package/dist/donut-chart/root/donut-chart-root.js +8 -5
  87. package/dist/drawer/root/drawer-root.d.ts +12 -1
  88. package/dist/drawer/root/drawer-root.js +9 -2
  89. package/dist/drilldown/item/drilldown-item.js +3 -4
  90. package/dist/drilldown/root/drilldown-root.d.ts +5 -0
  91. package/dist/drilldown/root/drilldown-root.js +4 -1
  92. package/dist/element-events.generated.js +26 -3
  93. package/dist/empty/root/empty-root.d.ts +17 -3
  94. package/dist/empty/root/empty-root.js +29 -5
  95. package/dist/file-input/root/file-input-root.d.ts +18 -3
  96. package/dist/file-input/root/file-input-root.js +34 -18
  97. package/dist/file-input/status.js +2 -1
  98. package/dist/filter-input/chip/filter-chip.d.ts +13 -0
  99. package/dist/filter-input/chip/filter-chip.js +7 -3
  100. package/dist/filter-input/menu/filter-menu.d.ts +5 -0
  101. package/dist/filter-input/menu/filter-menu.js +3 -1
  102. package/dist/filter-input/root/filter-input-root.d.ts +20 -3
  103. package/dist/filter-input/root/filter-input-root.js +8 -4
  104. package/dist/format-date/fields.d.ts +20 -0
  105. package/dist/format-date/fields.js +14 -0
  106. package/dist/format-date/options.d.ts +2 -1
  107. package/dist/format-date/options.js +9 -38
  108. package/dist/format-date/root/format-date-root.d.ts +55 -5
  109. package/dist/format-date/root/format-date-root.js +29 -34
  110. package/dist/graph/root/graph-model.d.ts +11 -0
  111. package/dist/graph/root/graph-model.js +4 -0
  112. package/dist/graph/root/graph-root.d.ts +101 -14
  113. package/dist/graph/root/graph-root.js +140 -46
  114. package/dist/heatmap/root/heatmap-root.d.ts +37 -4
  115. package/dist/heatmap/root/heatmap-root.js +51 -16
  116. package/dist/icon-button/root/icon-button-root.d.ts +5 -0
  117. package/dist/icon-button/root/icon-button-root.js +1 -0
  118. package/dist/image/root/image-root.d.ts +11 -0
  119. package/dist/input/root/input-root.d.ts +5 -0
  120. package/dist/input/root/input-root.js +4 -1
  121. package/dist/kbd/root/kbd-root.js +1 -2
  122. package/dist/legend/root/legend-root.js +4 -17
  123. package/dist/lightbox/root/lightbox-root.d.ts +14 -4
  124. package/dist/lightbox/root/lightbox-root.js +25 -7
  125. package/dist/line-chart/root/line-chart-root.d.ts +5 -0
  126. package/dist/line-chart/root/line-chart-root.js +4 -2
  127. package/dist/list/item/list-item.d.ts +32 -0
  128. package/dist/list/item/list-item.js +34 -7
  129. package/dist/list/root/list-root.d.ts +87 -0
  130. package/dist/list/root/list-root.js +119 -23
  131. package/dist/listbox/reorder/index.d.ts +1 -0
  132. package/dist/listbox/reorder/index.js +4 -0
  133. package/dist/listbox/reorder/listbox-reorder.d.ts +83 -0
  134. package/dist/listbox/reorder/listbox-reorder.js +151 -0
  135. package/dist/listbox/root/listbox-root.d.ts +185 -33
  136. package/dist/listbox/root/listbox-root.js +166 -136
  137. package/dist/loader/root/loader-root.d.ts +5 -0
  138. package/dist/loader/root/loader-root.js +3 -1
  139. package/dist/map/area/map-area.d.ts +5 -0
  140. package/dist/map/area/map-area.js +3 -1
  141. package/dist/map/buildings/map-buildings.d.ts +5 -0
  142. package/dist/map/buildings/map-buildings.js +3 -1
  143. package/dist/map/contours/map-contours.d.ts +5 -0
  144. package/dist/map/contours/map-contours.js +3 -1
  145. package/dist/map/landcover/map-landcover.d.ts +5 -0
  146. package/dist/map/landcover/map-landcover.js +3 -1
  147. package/dist/map/marker/map-marker.d.ts +18 -2
  148. package/dist/map/marker/map-marker.js +13 -5
  149. package/dist/map/points/map-points.d.ts +5 -0
  150. package/dist/map/points/map-points.js +6 -4
  151. package/dist/map/position/map-position.d.ts +5 -0
  152. package/dist/map/position/map-position.js +3 -1
  153. package/dist/map/raster/map-raster.d.ts +5 -0
  154. package/dist/map/raster/map-raster.js +3 -1
  155. package/dist/map/root/map-root.d.ts +73 -16
  156. package/dist/map/root/map-root.js +122 -44
  157. package/dist/map/route/map-route.d.ts +5 -0
  158. package/dist/map/route/map-route.js +3 -1
  159. package/dist/map/terrain/map-terrain.d.ts +5 -0
  160. package/dist/map/terrain/map-terrain.js +3 -1
  161. package/dist/megamenu/root/megamenu-root.js +4 -11
  162. package/dist/menu/root/menu-root.d.ts +7 -2
  163. package/dist/menu/root/menu-root.js +3 -1
  164. package/dist/meter/root/meter-root.d.ts +16 -3
  165. package/dist/meter/root/meter-root.js +12 -5
  166. package/dist/navigation/root/navigation-root.d.ts +5 -0
  167. package/dist/navigation/root/navigation-root.js +7 -8
  168. package/dist/notifications/group/notification-group.d.ts +8 -1
  169. package/dist/notifications/group/notification-group.js +12 -6
  170. package/dist/notifications/notification/notification.d.ts +17 -1
  171. package/dist/notifications/notification/notification.js +6 -2
  172. package/dist/notifications/root/notifications-root.d.ts +49 -5
  173. package/dist/notifications/root/notifications-root.js +36 -8
  174. package/dist/number-input/root/number-input-root.d.ts +21 -8
  175. package/dist/number-input/root/number-input-root.js +26 -11
  176. package/dist/object-inspector/root/object-inspector-root.d.ts +56 -13
  177. package/dist/object-inspector/root/object-inspector-root.js +41 -30
  178. package/dist/outline/root/outline-root.d.ts +5 -0
  179. package/dist/outline/root/outline-root.js +3 -1
  180. package/dist/pagination/root/pagination-root.d.ts +7 -1
  181. package/dist/pagination/root/pagination-root.js +16 -7
  182. package/dist/pagination/size/pagination-size.d.ts +8 -3
  183. package/dist/pagination/size/pagination-size.js +5 -3
  184. package/dist/pagination/summary/pagination-summary.d.ts +8 -6
  185. package/dist/pagination/summary/pagination-summary.js +4 -9
  186. package/dist/pin-input/code.d.ts +23 -0
  187. package/dist/pin-input/code.js +21 -0
  188. package/dist/pin-input/root/pin-input-root.d.ts +9 -3
  189. package/dist/pin-input/root/pin-input-root.js +13 -23
  190. package/dist/popover/root/popover-root.d.ts +12 -2
  191. package/dist/popover/root/popover-root.js +10 -4
  192. package/dist/progress/root/progress-root.d.ts +7 -2
  193. package/dist/progress/root/progress-root.js +5 -2
  194. package/dist/qr-code/name.d.ts +3 -2
  195. package/dist/qr-code/name.js +2 -2
  196. package/dist/qr-code/root/qr-code-root.d.ts +26 -5
  197. package/dist/qr-code/root/qr-code-root.js +27 -6
  198. package/dist/radio/group/radio-group.d.ts +11 -0
  199. package/dist/radio/group/radio-group.js +8 -2
  200. package/dist/rating/root/rating-root.d.ts +12 -1
  201. package/dist/rating/root/rating-root.js +10 -3
  202. package/dist/scatter-chart/measures.d.ts +22 -0
  203. package/dist/scatter-chart/measures.js +11 -0
  204. package/dist/scatter-chart/root/scatter-chart-root.d.ts +22 -8
  205. package/dist/scatter-chart/root/scatter-chart-root.js +25 -23
  206. package/dist/select/root/select-root.d.ts +67 -8
  207. package/dist/select/root/select-root.js +45 -11
  208. package/dist/skip-link/root/skip-link-root.d.ts +5 -0
  209. package/dist/skip-link/root/skip-link-root.js +3 -1
  210. package/dist/slider/root/slider-root.d.ts +7 -2
  211. package/dist/slider/root/slider-root.js +11 -5
  212. package/dist/sparkline/readings.d.ts +15 -5
  213. package/dist/sparkline/readings.js +3 -3
  214. package/dist/sparkline/root/sparkline-root.d.ts +9 -4
  215. package/dist/sparkline/root/sparkline-root.js +9 -3
  216. package/dist/speed-dial/group/speed-dial-group.d.ts +48 -0
  217. package/dist/speed-dial/group/speed-dial-group.js +43 -0
  218. package/dist/speed-dial/index.d.ts +1 -0
  219. package/dist/speed-dial/index.js +1 -0
  220. package/dist/speed-dial/item/speed-dial-item.d.ts +26 -1
  221. package/dist/speed-dial/item/speed-dial-item.js +41 -3
  222. package/dist/speed-dial/long-press.d.ts +50 -0
  223. package/dist/speed-dial/long-press.js +48 -0
  224. package/dist/speed-dial/root/speed-dial-root.d.ts +85 -1
  225. package/dist/speed-dial/root/speed-dial-root.js +117 -5
  226. package/dist/splitter/root/splitter-root.d.ts +12 -3
  227. package/dist/splitter/root/splitter-root.js +22 -4
  228. package/dist/steps/root/steps-root.d.ts +9 -2
  229. package/dist/steps/root/steps-root.js +6 -3
  230. package/dist/steps/step/step.d.ts +12 -0
  231. package/dist/steps/step/step.js +11 -2
  232. package/dist/switch/root/switch-root.d.ts +11 -0
  233. package/dist/switch/root/switch-root.js +8 -2
  234. package/dist/table/cell/table-cell.d.ts +8 -1
  235. package/dist/table/cell/table-cell.js +6 -2
  236. package/dist/table/column/table-column.d.ts +11 -4
  237. package/dist/table/column/table-column.js +15 -10
  238. package/dist/table/grid-controller.d.ts +122 -0
  239. package/dist/table/grid-controller.js +299 -0
  240. package/dist/table/root/table-root.d.ts +154 -8
  241. package/dist/table/root/table-root.js +197 -38
  242. package/dist/table/row/table-row.d.ts +55 -1
  243. package/dist/table/row/table-row.js +60 -7
  244. package/dist/tabs/root/tabs-root.d.ts +5 -0
  245. package/dist/tabs/root/tabs-root.js +3 -1
  246. package/dist/tag/group/tag-group.d.ts +5 -0
  247. package/dist/tag/group/tag-group.js +8 -15
  248. package/dist/tag/root/tag-root.d.ts +14 -1
  249. package/dist/tag/root/tag-root.js +11 -8
  250. package/dist/textarea/root/textarea-root.d.ts +5 -0
  251. package/dist/textarea/root/textarea-root.js +3 -1
  252. package/dist/time-input/root/time-input-root.d.ts +14 -7
  253. package/dist/time-input/root/time-input-root.js +43 -32
  254. package/dist/time-picker/root/time-picker-root.d.ts +16 -7
  255. package/dist/time-picker/root/time-picker-root.js +28 -12
  256. package/dist/toast/item/toast-item.d.ts +13 -3
  257. package/dist/toast/item/toast-item.js +2 -0
  258. package/dist/toast/root/toast-root.d.ts +22 -2
  259. package/dist/toast/root/toast-root.js +24 -17
  260. package/dist/toggle/group/toggle-group.js +3 -5
  261. package/dist/toolbar/root/toolbar-root.d.ts +36 -0
  262. package/dist/toolbar/root/toolbar-root.js +43 -9
  263. package/dist/tooltip/root/tooltip-root.d.ts +27 -17
  264. package/dist/tooltip/root/tooltip-root.js +1 -2
  265. package/dist/tour/root/tour-root.d.ts +8 -2
  266. package/dist/tour/root/tour-root.js +4 -2
  267. package/dist/tour/stop/tour-stop.d.ts +5 -0
  268. package/dist/tour/stop/tour-stop.js +6 -1
  269. package/dist/tree/grip.d.ts +5 -0
  270. package/dist/tree/grip.js +1 -0
  271. package/dist/tree/item/tree-item.d.ts +24 -0
  272. package/dist/tree/item/tree-item.js +27 -5
  273. package/dist/tree/root/tree-root.d.ts +66 -1
  274. package/dist/tree/root/tree-root.js +77 -5
  275. package/dist/trend/root/trend-root.d.ts +20 -4
  276. package/dist/trend/root/trend-root.js +20 -5
  277. package/dist/video/root/video-root.d.ts +23 -3
  278. package/dist/video/root/video-root.js +56 -15
  279. package/dist/video-playlist/menu/video-playlist-menu.d.ts +5 -0
  280. package/dist/video-playlist/menu/video-playlist-menu.js +3 -1
  281. package/dist/video-playlist/root/video-playlist-root.d.ts +5 -0
  282. package/dist/video-playlist/root/video-playlist-root.js +3 -1
  283. package/dist/virtual-list/root/virtual-list-root.d.ts +19 -3
  284. package/dist/virtual-list/root/virtual-list-root.js +10 -19
  285. package/lint.json +1 -1
  286. package/package.json +7 -6
  287. package/types/jsx.d.ts +6005 -2114
  288. package/types/svelte.d.ts +1 -0
  289. package/types/vue.d.ts +1594 -676
  290. package/types/words.d.ts +3280 -0
  291. package/dist/kbd/keys.d.ts +0 -29
  292. package/dist/kbd/keys.js +0 -52
  293. package/dist/toast/hotkey.d.ts +0 -22
  294. package/dist/toast/hotkey.js +0 -23
  295. package/dist/tooltip/focus-target.d.ts +0 -6
  296. package/dist/tooltip/focus-target.js +0 -9
@@ -4,7 +4,7 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
4
4
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
5
  return c > 3 && r && Object.defineProperty(target, key, r), r;
6
6
  };
7
- import { customElement, HelixElement, rgbOf } from '@fusion.dev/helix-core';
7
+ import { customElement, formatWords, HelixElement, reportRuntime, rgbOf, slotFilled, words, } from '@fusion.dev/helix-core';
8
8
  import { html, nothing, svg, } from 'lit';
9
9
  import { property } from 'lit/decorators.js';
10
10
  import { encode } from 'uqr';
@@ -77,12 +77,15 @@ const pathFor = (matrix, style, only = 'all') => {
77
77
  let HelixHeadlessQrCode = class HelixHeadlessQrCode extends HelixElement {
78
78
  constructor() {
79
79
  super(...arguments);
80
+ this.addressLabel = '{code}, {address}';
80
81
  this.codeLabel = 'QR code';
81
82
  this.label = '';
82
83
  this.value = '';
83
84
  this.logo = false;
85
+ this.toldLogo = false;
84
86
  this.overflowed = '';
85
87
  }
88
+ static { this.words = 'helix-qr-code'; }
86
89
  willUpdate(changed) {
87
90
  super.willUpdate(changed);
88
91
  if (this.childrenKnown) {
@@ -96,6 +99,17 @@ let HelixHeadlessQrCode = class HelixHeadlessQrCode extends HelixElement {
96
99
  get level() {
97
100
  return this.correction ?? (this.logo ? 'H' : 'M');
98
101
  }
102
+ auditLogo() {
103
+ if (this.toldLogo || !this.logo || (this.correction ?? 'H') === 'H') {
104
+ return;
105
+ }
106
+ this.toldLogo = true;
107
+ reportRuntime({
108
+ kind: 'unscannable-logo',
109
+ message: `<${this.localName}> holds a logo at correction "${this.correction}", which may keep it from scanning. Set \`correction\` to "H", or leave it unset.`,
110
+ tag: this.localName,
111
+ });
112
+ }
99
113
  encoded() {
100
114
  try {
101
115
  return encode(this.value, { border: 0, ecc: this.level });
@@ -109,6 +123,7 @@ let HelixHeadlessQrCode = class HelixHeadlessQrCode extends HelixElement {
109
123
  }
110
124
  updated(changed) {
111
125
  super.updated(changed);
126
+ this.auditLogo();
112
127
  const key = `${this.level}:${this.value}`;
113
128
  const overflow = this.value !== '' && this.encoded() === undefined;
114
129
  this.toggleState('overflow', overflow);
@@ -186,11 +201,12 @@ let HelixHeadlessQrCode = class HelixHeadlessQrCode extends HelixElement {
186
201
  return new Promise((resolve) => canvas.toBlob(resolve, 'image/png'));
187
202
  }
188
203
  async download(filename = 'qr-code.png', size = 512) {
189
- const png = await this.toPng(size);
190
- if (!png) {
204
+ const svg = /\.svg$/i.test(filename) ? this.toSvg(size) : '';
205
+ const file = svg ? new Blob([svg], { type: 'image/svg+xml' }) : await this.toPng(size);
206
+ if (!file) {
191
207
  return;
192
208
  }
193
- const url = URL.createObjectURL(png);
209
+ const url = URL.createObjectURL(file);
194
210
  const link = document.createElement('a');
195
211
  link.href = url;
196
212
  link.download = filename;
@@ -210,7 +226,7 @@ let HelixHeadlessQrCode = class HelixHeadlessQrCode extends HelixElement {
210
226
  viewBox="0 0 ${box} ${box}"
211
227
  xmlns="http://www.w3.org/2000/svg"
212
228
  role="img"
213
- aria-label=${qrName(this.label, this.value, this.codeLabel)}
229
+ aria-label=${qrName(this.label, this.value, this.codeLabel, (address) => formatWords(this, 'addressLabel', { address, code: this.codeLabel }))}
214
230
  shape-rendering="crispEdges"
215
231
  >
216
232
  <path
@@ -235,7 +251,7 @@ let HelixHeadlessQrCode = class HelixHeadlessQrCode extends HelixElement {
235
251
  <slot
236
252
  name="logo"
237
253
  @slotchange=${(event) => {
238
- const next = event.target.assignedNodes().length > 0;
254
+ const next = slotFilled(event.target);
239
255
  if (next !== this.logo) {
240
256
  this.logo = next;
241
257
  this.requestUpdate();
@@ -246,6 +262,11 @@ let HelixHeadlessQrCode = class HelixHeadlessQrCode extends HelixElement {
246
262
  }
247
263
  };
248
264
  __decorate([
265
+ words,
266
+ property({ attribute: 'address-label' })
267
+ ], HelixHeadlessQrCode.prototype, "addressLabel", void 0);
268
+ __decorate([
269
+ words,
249
270
  property({ attribute: 'code-label' })
250
271
  ], HelixHeadlessQrCode.prototype, "codeLabel", void 0);
251
272
  __decorate([
@@ -68,6 +68,11 @@ declare const HelixHeadlessRadioGroup_base: (new (...args: any[]) => import("@fu
68
68
  * @cssstate invalid - The group has an error to show, from the browser's validation or from your `feedback`.
69
69
  */
70
70
  export declare class HelixHeadlessRadioGroup extends HelixHeadlessRadioGroup_base {
71
+ /**
72
+ * The key this family's words are registered under, its styled tag:
73
+ * `registerWords('de', { 'helix-radio-group': { valueMissingMessage: '...' } })`.
74
+ */
75
+ static words: string;
71
76
  /**
72
77
  * Whether the group holds a tab stop of its own.
73
78
  *
@@ -101,6 +106,12 @@ export declare class HelixHeadlessRadioGroup extends HelixHeadlessRadioGroup_bas
101
106
  * `aria-readonly`. A script can still set `value`.
102
107
  */
103
108
  readOnly: boolean;
109
+ /**
110
+ * The message reported when the field is required and no option is chosen.
111
+ * Absent, or empty, is this sentence, or the words registered for the page's
112
+ * locale.
113
+ */
114
+ valueMissingMessage: string;
104
115
  protected readonly keys: KeyboardNavigationController;
105
116
  protected readonly cascade: DisabledCascadeController;
106
117
  /** The radios, in light-DOM order. Client only: the server has no tree. */
@@ -4,7 +4,7 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
4
4
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
5
  return c > 3 && r && Object.defineProperty(target, key, r), r;
6
6
  };
7
- import { customElement, DisabledCascadeController, HelixFormElement, hostAria, KeyboardNavigationController, MixinControllerValue, MixinField, } from '@fusion.dev/helix-core';
7
+ import { customElement, DisabledCascadeController, HelixFormElement, hostAria, KeyboardNavigationController, MixinControllerValue, MixinField, words, } from '@fusion.dev/helix-core';
8
8
  import { html } from 'lit';
9
9
  import { property } from 'lit/decorators.js';
10
10
  import { HelixHeadlessRadio } from '../root/radio-root.js';
@@ -13,6 +13,7 @@ let HelixHeadlessRadioGroup = class HelixHeadlessRadioGroup extends MixinControl
13
13
  super(...arguments);
14
14
  this.focusable = true;
15
15
  this.readOnly = false;
16
+ this.valueMissingMessage = 'Choose one to continue.';
16
17
  this.keys = new KeyboardNavigationController(this, {
17
18
  items: () => this.items,
18
19
  origin: () => (this.readOnly ? 'focus' : 'selection'),
@@ -39,6 +40,7 @@ let HelixHeadlessRadioGroup = class HelixHeadlessRadioGroup extends MixinControl
39
40
  });
40
41
  };
41
42
  }
43
+ static { this.words = 'helix-radio-group'; }
42
44
  get items() {
43
45
  return [...(this.children ?? [])].filter((child) => child instanceof HelixHeadlessRadio);
44
46
  }
@@ -84,7 +86,7 @@ let HelixHeadlessRadioGroup = class HelixHeadlessRadioGroup extends MixinControl
84
86
  sync() {
85
87
  const answered = this.answered;
86
88
  this.internals.setFormValue(answered ? this.value : null);
87
- this.reportRequired(!answered, 'Choose one to continue.', 'items');
89
+ this.reportRequired(!answered, this.valueMissingMessage, 'items');
88
90
  }
89
91
  connectedCallback() {
90
92
  super.connectedCallback();
@@ -124,6 +126,10 @@ __decorate([
124
126
  __decorate([
125
127
  property({ attribute: 'readonly', reflect: true, type: Boolean })
126
128
  ], HelixHeadlessRadioGroup.prototype, "readOnly", void 0);
129
+ __decorate([
130
+ words,
131
+ property({ attribute: 'value-missing-message' })
132
+ ], HelixHeadlessRadioGroup.prototype, "valueMissingMessage", void 0);
127
133
  HelixHeadlessRadioGroup = __decorate([
128
134
  customElement('helix-headless-radio-group')
129
135
  ], HelixHeadlessRadioGroup);
@@ -69,6 +69,11 @@ declare const HelixHeadlessRating_base: (new (...args: any[]) => import("@fusion
69
69
  * @cssstate invalid - The control has an error to show, from the browser's validation or from your `feedback`.
70
70
  */
71
71
  export declare class HelixHeadlessRating extends HelixHeadlessRating_base {
72
+ /**
73
+ * The key this family's words are registered under, its styled tag:
74
+ * `registerWords('de', { 'helix-rating': { optionLabel: '{score} von {max}' } })`.
75
+ */
76
+ static words: string;
72
77
  protected readonly announcesInput = false;
73
78
  /**
74
79
  * Whether a reader can take the rating back to unrated: by pressing the
@@ -125,7 +130,7 @@ export declare class HelixHeadlessRating extends HelixHeadlessRating_base {
125
130
  min: number;
126
131
  /**
127
132
  * The name of each mark a reader can choose, with `{score}` and `{max}`
128
- * filled in. Set it to translate "3 out of 5".
133
+ * filled in, written in the locale. Set it to translate "3 out of 5".
129
134
  *
130
135
  * Also what a read-only rating says for its score where `value-text` is
131
136
  * empty.
@@ -158,6 +163,12 @@ export declare class HelixHeadlessRating extends HelixHeadlessRating_base {
158
163
  * than an index: with halves, five marks are ten answers.
159
164
  */
160
165
  step: number;
166
+ /**
167
+ * The message reported when the field is required and no rating is chosen.
168
+ * Absent, or empty, is this sentence, or the words registered for the page's
169
+ * locale.
170
+ */
171
+ valueMissingMessage: string;
161
172
  /**
162
173
  * The text screen readers read for the score, in place of "3.5 out of 5".
163
174
  *
@@ -4,7 +4,7 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
4
4
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
5
  return c > 3 && r && Object.defineProperty(target, key, r), r;
6
6
  };
7
- import { AriaForwardController, valueAsNumber as asNumber, customElement, fillTemplate, numberAsValue as fromNumber, HelixClearEvent, HelixFormElement, HelixPreviewEvent, KeyboardNavigationController, MixinControllerValue, MixinField, nearest, reportRuntime, SlottedGlyph, } from '@fusion.dev/helix-core';
7
+ import { AriaForwardController, valueAsNumber as asNumber, customElement, formatWords, numberAsValue as fromNumber, HelixClearEvent, HelixFormElement, HelixPreviewEvent, KeyboardNavigationController, MixinControllerValue, MixinField, nearest, reportRuntime, SlottedGlyph, words, } from '@fusion.dev/helix-core';
8
8
  import { html, nothing } from 'lit';
9
9
  import { property, state } from 'lit/decorators.js';
10
10
  let HelixHeadlessRating = class HelixHeadlessRating extends MixinControllerValue(MixinField(HelixFormElement)) {
@@ -18,6 +18,7 @@ let HelixHeadlessRating = class HelixHeadlessRating extends MixinControllerValue
18
18
  this.readOnly = false;
19
19
  this.showValue = false;
20
20
  this.step = 1;
21
+ this.valueMissingMessage = 'Choose a rating to continue.';
21
22
  this.valueText = '';
22
23
  this.aria = new AriaForwardController(this, {
23
24
  target: () => this.partNamed('marks'),
@@ -123,6 +124,7 @@ let HelixHeadlessRating = class HelixHeadlessRating extends MixinControllerValue
123
124
  };
124
125
  this.warned = false;
125
126
  }
127
+ static { this.words = 'helix-rating'; }
126
128
  get namedControl() {
127
129
  return this.partNamed('marks');
128
130
  }
@@ -183,7 +185,7 @@ let HelixHeadlessRating = class HelixHeadlessRating extends MixinControllerValue
183
185
  }
184
186
  sync() {
185
187
  this.internals.setFormValue(this.value === '' ? null : this.value);
186
- this.reportRequired(this.value === '', 'Choose a rating to continue.', 'marks');
188
+ this.reportRequired(this.value === '', this.valueMissingMessage, 'marks');
187
189
  }
188
190
  clear() {
189
191
  if (this.value !== '' && !this.readOnly && !this.isDisabled && this.requestValue('')) {
@@ -231,7 +233,7 @@ let HelixHeadlessRating = class HelixHeadlessRating extends MixinControllerValue
231
233
  this.sync();
232
234
  }
233
235
  nameFor(score) {
234
- return fillTemplate(this.optionLabel, { max: this.max, score });
236
+ return formatWords(this, 'optionLabel', { max: this.max, score });
235
237
  }
236
238
  stopAt(answered, first) {
237
239
  if (!answered) {
@@ -335,6 +337,7 @@ __decorate([
335
337
  property({ type: Number })
336
338
  ], HelixHeadlessRating.prototype, "min", void 0);
337
339
  __decorate([
340
+ words,
338
341
  property({ attribute: 'option-label' })
339
342
  ], HelixHeadlessRating.prototype, "optionLabel", void 0);
340
343
  __decorate([
@@ -346,6 +349,10 @@ __decorate([
346
349
  __decorate([
347
350
  property({ type: Number })
348
351
  ], HelixHeadlessRating.prototype, "step", void 0);
352
+ __decorate([
353
+ words,
354
+ property({ attribute: 'value-missing-message' })
355
+ ], HelixHeadlessRating.prototype, "valueMissingMessage", void 0);
349
356
  __decorate([
350
357
  property({ attribute: 'value-text' })
351
358
  ], HelixHeadlessRating.prototype, "valueText", void 0);
@@ -0,0 +1,22 @@
1
+ /** The numeric columns by what they measure. */
2
+ export interface Measures {
3
+ /** The column across, the first one that is not the size. */
4
+ across: number | undefined;
5
+ /** The column `size-by` names, which sizes the points. */
6
+ size: number | undefined;
7
+ /** Every other column, each a series up. */
8
+ ups: number[];
9
+ }
10
+ /**
11
+ * The numeric columns by what they measure: the column whose heading
12
+ * `sizeBy` names as the size, by its series key, then the first of the rest
13
+ * across and every other one up.
14
+ */
15
+ export declare const measuresOf: (columns: readonly number[], name: (column: number) => string, sizeBy: string) => Measures;
16
+ /**
17
+ * Each row's point size from its reading in the size column, by area, so a
18
+ * point twice the measure is twice the ink: the square root of its share of
19
+ * the largest. A size below zero is none, and a row with no size, or a column
20
+ * whose largest is not above zero, has no weight.
21
+ */
22
+ export declare const bubbleWeights: (sizes: readonly (number | undefined)[]) => (number | undefined)[];
@@ -0,0 +1,11 @@
1
+ import { seriesKey } from '@fusion.dev/helix-core';
2
+ export const measuresOf = (columns, name, sizeBy) => {
3
+ const key = seriesKey(sizeBy);
4
+ const size = key === '' ? undefined : columns.find((column) => seriesKey(name(column)) === key);
5
+ const [across, ...ups] = columns.filter((column) => column !== size);
6
+ return { across, size, ups };
7
+ };
8
+ export const bubbleWeights = (sizes) => {
9
+ const largest = Math.max(0, ...sizes.map((one) => one ?? 0));
10
+ return sizes.map((one) => one === undefined || largest <= 0 ? undefined : Math.sqrt(Math.max(0, one) / largest));
11
+ };
@@ -1,6 +1,7 @@
1
1
  import { HelixElement } from '@fusion.dev/helix-core';
2
2
  import { nothing, type TemplateResult } from 'lit';
3
3
  import '../../tooltip/index.js';
4
+ import { type Measures } from '../measures.js';
4
5
  /** One row drawn as a point: which row, which series, and where, in percent of the plot. */
5
6
  export interface ScatterPoint {
6
7
  depth: number;
@@ -111,7 +112,13 @@ declare const HelixHeadlessScatterChart_base: typeof HelixElement & (new (...arg
111
112
  */
112
113
  export declare class HelixHeadlessScatterChart extends HelixHeadlessScatterChart_base {
113
114
  /**
114
- * The word the summary uses for the strength of the relation.
115
+ * The key this family's words are registered under, its styled tag:
116
+ * `registerWords('de', { 'helix-scatter-chart': { seriesLabel: '…' } })`.
117
+ */
118
+ static words: string;
119
+ /**
120
+ * The word for the strength of the relation, `{correlationLabel}` in
121
+ * `series-label`.
115
122
  */
116
123
  correlationLabel: string;
117
124
  /**
@@ -124,9 +131,21 @@ export declare class HelixHeadlessScatterChart extends HelixHeadlessScatterChart
124
131
  */
125
132
  gridlines?: 'both' | 'x' | 'y';
126
133
  /**
127
- * The word the summary uses for a row when it counts them.
134
+ * The word for the rows a series rests on, `{pointsLabel}` in
135
+ * `series-label`. `{count}` is how many, so the word takes its plural
136
+ * forms: `{count, plural, one {punkt} few {punkty} other {punktów}}`.
128
137
  */
129
138
  pointsLabel: string;
139
+ /**
140
+ * What the summary says of each series. `{y}` is what the series measures up,
141
+ * `{x}` what the chart measures across, `{count}` how many rows it rests on,
142
+ * written in the locale, `{pointsLabel}` the word for them, and
143
+ * `{correlation}` its correlation, or `none` where there are fewer than
144
+ * three points or no spread to measure, so each case is a whole sentence:
145
+ * `{correlation, select, none {...} other {...}}`. `{correlationLabel}` is
146
+ * `correlation-label`.
147
+ */
148
+ seriesLabel: string;
130
149
  /**
131
150
  * The heading of a column whose numbers size the points, such as
132
151
  * `Population`, which makes the chart a bubble chart.
@@ -172,12 +191,7 @@ export declare class HelixHeadlessScatterChart extends HelixHeadlessScatterChart
172
191
  * The numeric columns by what they measure: the first across, the column
173
192
  * `size-by` names as the size, and every other one up, as a series.
174
193
  */
175
- protected get measures(): {
176
- across: number | undefined;
177
- size: number | undefined;
178
- ups: number[];
179
- };
180
- showsColumn(cell: number): boolean;
194
+ protected get measures(): Measures;
181
195
  /** Whether the levels across are ruled. */
182
196
  protected get rulesX(): boolean;
183
197
  /** Whether the levels up are ruled. */
@@ -4,11 +4,12 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
4
4
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
5
  return c > 3 && r && Object.defineProperty(target, key, r), r;
6
6
  };
7
- import { CHART_PLOT, customElement, drawTooltip, extent, formatNumbers, HelixElement, isRtl, linear, MixinChartSource, PLOT_HEIGHT, PLOT_WIDTH, seriesIndex, seriesKey, ticks, } from '@fusion.dev/helix-core';
7
+ import { CHART_PLOT, customElement, drawTooltip, extent, formatNumbers, formatWords, HelixElement, isRtl, linear, MixinChartSource, PLOT_HEIGHT, PLOT_WIDTH, seriesIndex, ticks, words, wordsLocale, } from '@fusion.dev/helix-core';
8
8
  import { html, nothing, svg } from 'lit';
9
9
  import { property } from 'lit/decorators.js';
10
10
  import '../../tooltip/index.js';
11
11
  import { correlation, leastSquares } from '../fit.js';
12
+ import { bubbleWeights, measuresOf } from '../measures.js';
12
13
  const REACH = 24;
13
14
  const COEFFICIENTS = new Map();
14
15
  const coefficientIn = (locale) => {
@@ -36,7 +37,8 @@ let HelixHeadlessScatterChart = class HelixHeadlessScatterChart extends MixinCha
36
37
  constructor() {
37
38
  super(...arguments);
38
39
  this.correlationLabel = 'correlation';
39
- this.pointsLabel = 'points';
40
+ this.pointsLabel = '{count, plural, one {point} other {points}}';
41
+ this.seriesLabel = '{correlation, select, none {{y} / {x}: {count} {pointsLabel}} other {{y} / {x}: {count} {pointsLabel}, {correlationLabel} {correlation}}}';
40
42
  this.sizeBy = '';
41
43
  this.trend = false;
42
44
  this.drawn = [];
@@ -71,6 +73,7 @@ let HelixHeadlessScatterChart = class HelixHeadlessScatterChart extends MixinCha
71
73
  this.nearest = undefined;
72
74
  };
73
75
  }
76
+ static { this.words = 'helix-scatter-chart'; }
74
77
  connectedCallback() {
75
78
  super.connectedCallback();
76
79
  this.pointer.axis = 'none';
@@ -87,16 +90,7 @@ let HelixHeadlessScatterChart = class HelixHeadlessScatterChart extends MixinCha
87
90
  return depth < 0 ? undefined : seriesIndex(depth);
88
91
  }
89
92
  get measures() {
90
- const rows = this.sourceRows;
91
- const key = seriesKey(this.sizeBy);
92
- const size = key === ''
93
- ? undefined
94
- : this.plottedColumns.find((column) => seriesKey(rows.find((row) => row.cells[column])?.cells[column]?.name ?? '') === key);
95
- const [across, ...ups] = this.plottedColumns.filter((column) => column !== size);
96
- return { across, size, ups };
97
- }
98
- showsColumn(cell) {
99
- return cell !== this.measures.size && super.showsColumn(cell);
93
+ return measuresOf(this.plottedColumns, (column) => this.columnName(column), this.sizeBy);
100
94
  }
101
95
  get rulesX() {
102
96
  return this.gridlines !== undefined && this.gridlines !== 'y';
@@ -107,7 +101,7 @@ let HelixHeadlessScatterChart = class HelixHeadlessScatterChart extends MixinCha
107
101
  get field() {
108
102
  const rows = this.sourceRows;
109
103
  const { across, size, ups } = this.measures;
110
- const name = (column) => column === undefined ? '' : (rows.find((row) => row.cells[column])?.cells[column]?.name ?? '');
104
+ const name = (column) => column === undefined ? '' : this.columnName(column);
111
105
  const pairs = ups.map((column) => rows.flatMap((row, index) => {
112
106
  const x = across === undefined ? undefined : row.cells[across]?.value;
113
107
  const y = row.cells[column]?.value;
@@ -119,19 +113,14 @@ let HelixHeadlessScatterChart = class HelixHeadlessScatterChart extends MixinCha
119
113
  const y = nice(extent(all.length > 0 ? all.map(([, one]) => one) : [0]));
120
114
  const along = linear(x, [0, PLOT_WIDTH]);
121
115
  const up = linear(y, [PLOT_HEIGHT, 0]);
122
- const sizes = rows.map((row) => (size === undefined ? undefined : row.cells[size]?.value));
123
- const largest = Math.max(0, ...sizes.map((one) => one ?? 0));
124
- const weight = (row) => {
125
- const one = sizes[row];
126
- return one === undefined || largest <= 0 ? undefined : Math.sqrt(Math.max(0, one) / largest);
127
- };
116
+ const weights = bubbleWeights(rows.map((row) => (size === undefined ? undefined : row.cells[size]?.value)));
128
117
  return {
129
118
  pairs: pairs.map((series) => series.map(([one, two]) => [one, two])),
130
119
  points: pairs.flatMap((series, depth) => shown[depth]
131
120
  ? series.map(([one, two, row]) => ({
132
121
  depth,
133
122
  row,
134
- weight: weight(row),
123
+ weight: weights[row],
135
124
  x: along(one),
136
125
  y: up(two),
137
126
  }))
@@ -150,7 +139,7 @@ let HelixHeadlessScatterChart = class HelixHeadlessScatterChart extends MixinCha
150
139
  <div id=${CHART_PLOT} part="plot"></div>
151
140
  </div>`;
152
141
  }
153
- const format = formatNumbers(this.locale);
142
+ const format = formatNumbers(wordsLocale(this));
154
143
  const along = linear(field.x, [0, PLOT_WIDTH]);
155
144
  const up = linear(field.y, [PLOT_HEIGHT, 0]);
156
145
  return html `<div dir="ltr" part="plane">
@@ -229,11 +218,18 @@ let HelixHeadlessScatterChart = class HelixHeadlessScatterChart extends MixinCha
229
218
  });
230
219
  }
231
220
  renderSummary(field) {
221
+ const coefficient = coefficientIn(wordsLocale(this));
232
222
  const clauses = field.yNames.map((name, depth) => {
233
223
  const pairs = field.pairs[depth] ?? [];
234
224
  const r = correlation(pairs);
235
- const strength = r === undefined ? '' : `, ${this.correlationLabel} ${coefficientIn(this.locale).format(r)}`;
236
- return `${name} / ${field.xName}: ${pairs.length} ${this.pointsLabel}${strength}`;
225
+ return formatWords(this, 'seriesLabel', {
226
+ correlation: r === undefined ? 'none' : coefficient.format(r),
227
+ correlationLabel: this.correlationLabel,
228
+ count: pairs.length,
229
+ pointsLabel: formatWords(this, 'pointsLabel', { count: pairs.length }),
230
+ x: field.xName,
231
+ y: name,
232
+ });
237
233
  });
238
234
  const named = this.named ? `${this.named}. ` : '';
239
235
  return html `<p id="helix-chart-summary" part="summary">${named}${clauses.join('; ')}.</p>`;
@@ -259,14 +255,20 @@ let HelixHeadlessScatterChart = class HelixHeadlessScatterChart extends MixinCha
259
255
  }
260
256
  };
261
257
  __decorate([
258
+ words,
262
259
  property({ attribute: 'correlation-label' })
263
260
  ], HelixHeadlessScatterChart.prototype, "correlationLabel", void 0);
264
261
  __decorate([
265
262
  property()
266
263
  ], HelixHeadlessScatterChart.prototype, "gridlines", void 0);
267
264
  __decorate([
265
+ words,
268
266
  property({ attribute: 'points-label' })
269
267
  ], HelixHeadlessScatterChart.prototype, "pointsLabel", void 0);
268
+ __decorate([
269
+ words,
270
+ property({ attribute: 'series-label' })
271
+ ], HelixHeadlessScatterChart.prototype, "seriesLabel", void 0);
270
272
  __decorate([
271
273
  property({ attribute: 'size-by' })
272
274
  ], HelixHeadlessScatterChart.prototype, "sizeBy", void 0);
@@ -21,13 +21,36 @@ declare const HelixHeadlessSelect_base: (new (...args: any[]) => import("@fusion
21
21
  * Set `valueContent` to draw the trigger's content from the chosen options,
22
22
  * and several chosen options are written as a list in the reader's language.
23
23
  *
24
- * In the open list the arrow keys, Home, End, PageUp, PageDown and typed
25
- * letters move the highlight, and Enter, Space or a click chooses it and
26
- * closes the list. Tab closes the list and moves on. On the closed trigger,
27
- * ArrowDown, Enter and Space open the list on the chosen option, ArrowUp opens
28
- * it on the chosen or last option, Home and End open it on the first or last,
29
- * and typed letters choose the option whose words start with them, as a native
30
- * `<select>` does.
24
+ * **Keyboard.** On the closed trigger:
25
+ *
26
+ * | Key | What it does |
27
+ * |---|---|
28
+ * | Down, Enter, Space | Opens the list on the chosen option, or the first. |
29
+ * | Up | Opens the list on the chosen option, or the last. |
30
+ * | Home, End | Opens the list on the first or the last option. |
31
+ * | Left, Right | Chooses the option before or after the chosen one without opening, as React Aria's Select does, in either direction of text. |
32
+ * | A letter or a word | Chooses the option whose words start with what you typed, as a native `<select>` does. With `multiple`, opens the list on it. |
33
+ *
34
+ * In the open list, which is a `Listbox`:
35
+ *
36
+ * | Key | What it does |
37
+ * |---|---|
38
+ * | Down, Up, Home, End, Page Down, Page Up | Moves the highlight. |
39
+ * | A letter or a word | Moves the highlight to the next option whose words start with what you typed. |
40
+ * | Enter, Space | Chooses the highlighted option and closes the list. With `multiple`, toggles it and leaves the list open. |
41
+ * | Escape | Closes the list and puts focus back on the trigger. |
42
+ * | Tab | Closes the list and moves on. |
43
+ *
44
+ * A choice made on the closed trigger is said aloud on Apple devices, where
45
+ * VoiceOver does not read the trigger's new name.
46
+ *
47
+ * **ARIA.** The trigger is a `button` with `aria-haspopup="listbox"` and
48
+ * `aria-expanded`, named by the label and then the chosen words, as a native
49
+ * `<select>` is. The list is the listbox `Listbox` describes, named by the
50
+ * label, or by `list-label` where there is none.
51
+ *
52
+ * Set `autocomplete` to let a browser's autofill choose, as a native `<select>`
53
+ * with the same attribute would.
31
54
  *
32
55
  * @since 0.1.0
33
56
  * @status stable
@@ -69,6 +92,7 @@ declare const HelixHeadlessSelect_base: (new (...args: any[]) => import("@fusion
69
92
  * @csspart listbox-loading - The text shown while the options load.
70
93
  * @csspart listbox-search - The region that holds the filter field.
71
94
  * @csspart listbox-search-field - The filter field.
95
+ * @csspart live - The region a screen reader announces a choice made on the closed trigger from, drawn once there is one to say. Visually hidden in the styled tier.
72
96
  * @csspart surface - The floating panel.
73
97
  * @csspart trigger - The closed control, which shows the chosen value.
74
98
  * @csspart value - The chosen option's text inside the trigger.
@@ -80,7 +104,24 @@ declare const HelixHeadlessSelect_base: (new (...args: any[]) => import("@fusion
80
104
  * @cssstate open - While the list is open.
81
105
  */
82
106
  export declare class HelixHeadlessSelect extends HelixHeadlessSelect_base {
107
+ /**
108
+ * The key this family's words are registered under, its styled tag:
109
+ * `registerWords('de', { 'helix-select': { placeholder: 'Auswählen' } })`.
110
+ */
111
+ static words: string;
83
112
  protected readonly aria: AriaForwardController;
113
+ /** The region a choice made on the closed trigger is said from. */
114
+ private readonly status;
115
+ /**
116
+ * What a browser's autofill may fill in, as a platform token such as
117
+ * `country` or `cc-exp-month`, as on a native `<select>`.
118
+ *
119
+ * Set, the select keeps a hidden native `<select>` with the same options for
120
+ * the browser to fill, as React Aria's `HiddenSelect` does, and takes the
121
+ * option the browser picks, by its value or its words, as the value. Empty
122
+ * draws no hidden select, and a browser fills nothing.
123
+ */
124
+ autocomplete: string;
84
125
  /**
85
126
  * The text shown when no options match the filter.
86
127
  */
@@ -158,6 +199,12 @@ export declare class HelixHeadlessSelect extends HelixHeadlessSelect_base {
158
199
  * write a function in markup.
159
200
  */
160
201
  valueContent?: ((chosen: readonly HelixHeadlessOption[]) => unknown) | undefined;
202
+ /**
203
+ * The message reported when the field is required and nothing is chosen.
204
+ * Absent, or empty, is this sentence, or the words registered for the page's
205
+ * locale.
206
+ */
207
+ valueMissingMessage: string;
161
208
  /**
162
209
  * Which option is chosen, as an index, or `-1` where none is.
163
210
  *
@@ -283,9 +330,21 @@ export declare class HelixHeadlessSelect extends HelixHeadlessSelect_base {
283
330
  * Aria's Select do, so a reader who knows the answer types it. A Space in the
284
331
  * middle of those letters is one of them. With `multiple`, a letter opens the
285
332
  * list on the match instead, because adding to a set is a choice the reader
286
- * makes in the list.
333
+ * makes in the list. ArrowLeft and ArrowRight choose the option before and
334
+ * after the chosen one.
287
335
  */
288
336
  private readonly handleTriggerKeydown;
337
+ /**
338
+ * Chooses from the closed trigger, and says the choice on Apple devices.
339
+ *
340
+ * The trigger is named by the label and the chosen words, so a choice made
341
+ * on it renames the control in focus. VoiceOver does not read a name that
342
+ * changes under focus, so a reader there heard nothing as a letter or an
343
+ * arrow changed the answer. The words are said in a live region, as React
344
+ * Aria says a combobox's choice for VoiceOver alone, since other screen
345
+ * readers read the new name.
346
+ */
347
+ private choose;
289
348
  /**
290
349
  * Tab closes the list and lets focus move on, as a native `<select>` does.
291
350
  *