@aceshooting/lyra-ui 9.1.1 → 10.0.1

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 (578) hide show
  1. package/CHANGELOG.md +597 -0
  2. package/custom-elements.json +1 -1
  3. package/dist/cli/migrate-wa.mjs +52 -0
  4. package/dist/cli/migration-contract.json +1 -1
  5. package/dist/components/agent-tools/activity-feed/activity-feed.class.js +1 -1
  6. package/dist/components/agent-tools/activity-feed/activity-feed.styles.js +0 -16
  7. package/dist/components/agent-tools/agent-eval-dashboard/agent-eval-dashboard.class.js +1 -1
  8. package/dist/components/agent-tools/agent-eval-dashboard/agent-eval-dashboard.styles.js +7 -5
  9. package/dist/components/agent-tools/agent-run/agent-run.class.js +2 -2
  10. package/dist/components/agent-tools/agent-run/agent-run.styles.js +0 -13
  11. package/dist/components/agent-tools/agent-trace/agent-trace.styles.js +7 -4
  12. package/dist/components/agent-tools/approval-queue/approval-queue.styles.js +7 -5
  13. package/dist/components/agent-tools/artifact-panel/artifact-panel.styles.js +0 -3
  14. package/dist/components/agent-tools/browser-frame/browser-frame.styles.js +3 -5
  15. package/dist/components/agent-tools/commit-card/commit-card.styles.js +0 -10
  16. package/dist/components/agent-tools/compare-panel/compare-panel.styles.js +11 -6
  17. package/dist/components/agent-tools/confirm-bar/confirm-bar.styles.js +0 -46
  18. package/dist/components/agent-tools/eval-dataset/eval-dataset.styles.js +0 -7
  19. package/dist/components/agent-tools/evaluation-run/evaluation-run.class.js +2 -2
  20. package/dist/components/agent-tools/prompt-studio/prompt-studio.styles.js +0 -15
  21. package/dist/components/agent-tools/result-card/result-card.styles.js +0 -7
  22. package/dist/components/agent-tools/result-card/result-field.styles.js +0 -5
  23. package/dist/components/agent-tools/schema-viewer/schema-viewer.styles.js +0 -3
  24. package/dist/components/agent-tools/span-waterfall/span-waterfall.styles.js +0 -15
  25. package/dist/components/agent-tools/stack-trace/stack-trace.styles.js +0 -20
  26. package/dist/components/agent-tools/subagent-panel/subagent-panel.class.js +2 -2
  27. package/dist/components/agent-tools/subagent-panel/subagent-panel.styles.js +0 -3
  28. package/dist/components/agent-tools/task-list/task-list.styles.js +0 -15
  29. package/dist/components/agent-tools/terminal/terminal.class.d.ts +11 -6
  30. package/dist/components/agent-tools/terminal/terminal.class.js +4 -4
  31. package/dist/components/agent-tools/terminal/terminal.styles.js +0 -46
  32. package/dist/components/agent-tools/test-results/test-results.class.js +2 -2
  33. package/dist/components/agent-tools/test-results/test-results.styles.js +0 -5
  34. package/dist/components/agent-tools/thinking-panel/thinking-panel.styles.js +0 -41
  35. package/dist/components/agent-tools/tool-approval-dialog/tool-approval-dialog.styles.js +0 -41
  36. package/dist/components/agent-tools/tool-call-chip/tool-call-chip.styles.js +0 -30
  37. package/dist/components/agent-tools/tool-param-form/tool-param-form.class.js +6 -6
  38. package/dist/components/agent-tools/tool-param-form/tool-param-form.styles.js +0 -5
  39. package/dist/components/agent-tools/tool-result-dialog/tool-result-dialog.styles.js +0 -20
  40. package/dist/components/agent-tools/tool-result-view/tool-result-view.styles.js +0 -4
  41. package/dist/components/agent-tools/tool-select-dialog/tool-select-dialog.styles.js +0 -21
  42. package/dist/components/agent-tools/trace-tree/trace-tree.styles.js +7 -31
  43. package/dist/components/charts/chart/box-plot.styles.js +0 -20
  44. package/dist/components/charts/chart/chart-colors.d.ts +1 -1
  45. package/dist/components/charts/chart/chart-colors.js +1 -1
  46. package/dist/components/charts/chart/chart-core-loader.d.ts +1 -0
  47. package/dist/components/charts/chart/chart-core-loader.js +1 -1
  48. package/dist/components/charts/chart/chart-feature-loader.d.ts +35 -0
  49. package/dist/components/charts/chart/chart-feature-loader.js +1 -1
  50. package/dist/components/charts/chart/chart.class.d.ts +93 -0
  51. package/dist/components/charts/chart/chart.class.js +3 -3
  52. package/dist/components/charts/chart/chart.styles.js +0 -27
  53. package/dist/components/charts/chart/lite-chart.class.d.ts +20 -1
  54. package/dist/components/charts/chart/lite-chart.class.js +4 -4
  55. package/dist/components/charts/chart/lite-chart.styles.js +0 -27
  56. package/dist/components/conversation/agent-workspace/agent-workspace.class.d.ts +20 -0
  57. package/dist/components/conversation/agent-workspace/agent-workspace.class.js +3 -1
  58. package/dist/components/conversation/agent-workspace/agent-workspace.styles.js +3 -0
  59. package/dist/components/conversation/audio-visualizer/audio-visualizer.styles.js +0 -7
  60. package/dist/components/conversation/branch-picker/branch-picker.styles.js +0 -3
  61. package/dist/components/conversation/chat-composer/chat-composer.styles.js +0 -51
  62. package/dist/components/conversation/chat-message/chat-message.styles.js +7 -35
  63. package/dist/components/conversation/chat-viewport/chat-viewport.class.js +1 -1
  64. package/dist/components/conversation/chat-viewport/chat-viewport.styles.js +0 -33
  65. package/dist/components/conversation/checkpoint/checkpoint.class.js +1 -1
  66. package/dist/components/conversation/checkpoint/checkpoint.styles.js +0 -3
  67. package/dist/components/conversation/code-block/code-block-shared.d.ts +5 -2
  68. package/dist/components/conversation/code-block/code-block.class.js +1 -1
  69. package/dist/components/conversation/code-block/code-block.styles.js +4 -95
  70. package/dist/components/conversation/code-block/code-loader.d.ts +11 -0
  71. package/dist/components/conversation/code-block/code-loader.js +1 -1
  72. package/dist/components/conversation/code-block/shiki-types.d.ts +12 -0
  73. package/dist/components/conversation/code-block/shiki-types.js +1 -1
  74. package/dist/components/conversation/conversation-item/conversation-item.styles.js +8 -54
  75. package/dist/components/conversation/generation-metrics/generation-metrics.class.js +2 -2
  76. package/dist/components/conversation/generation-metrics/generation-metrics.styles.js +0 -17
  77. package/dist/components/conversation/markdown/markdown-base.class.js +1 -1
  78. package/dist/components/conversation/markdown/markdown.styles.js +0 -41
  79. package/dist/components/conversation/message-actions/message-actions.styles.js +0 -3
  80. package/dist/components/conversation/message-feedback/message-feedback.styles.js +0 -35
  81. package/dist/components/conversation/message-parts/message-parts.class.d.ts +1 -1
  82. package/dist/components/conversation/message-parts/message-parts.styles.js +0 -5
  83. package/dist/components/conversation/model-select/model-select.class.js +3 -3
  84. package/dist/components/conversation/model-select/model-select.styles.js +12 -47
  85. package/dist/components/conversation/model-settings-panel/model-settings-panel.styles.js +0 -6
  86. package/dist/components/conversation/prompt-input/prompt-input.class.d.ts +3 -0
  87. package/dist/components/conversation/prompt-input/prompt-input.styles.js +0 -10
  88. package/dist/components/conversation/push-to-talk/push-to-talk.styles.js +0 -8
  89. package/dist/components/conversation/selection-toolbar/selection-toolbar.styles.js +1 -11
  90. package/dist/components/conversation/stream-status/stream-status.styles.js +0 -16
  91. package/dist/components/conversation/streaming-text/streaming-text.styles.js +0 -15
  92. package/dist/components/conversation/suggestion-chips/suggestion-chips.styles.js +0 -5
  93. package/dist/components/conversation/thread-list/thread-list.styles.js +0 -23
  94. package/dist/components/conversation/transcript-feed/transcript-feed.class.d.ts +16 -4
  95. package/dist/components/conversation/transcript-feed/transcript-feed.class.js +1 -1
  96. package/dist/components/conversation/transcript-feed/transcript-feed.styles.js +0 -1
  97. package/dist/components/conversation/typing-indicator/typing-indicator.styles.js +0 -23
  98. package/dist/components/conversation/usage-badge/usage-badge.styles.js +0 -3
  99. package/dist/components/conversation/voice-picker/voice-picker.class.js +3 -3
  100. package/dist/components/conversation/voice-picker/voice-picker.styles.js +9 -29
  101. package/dist/components/conversation/widget-renderer/resolve.d.ts +2 -0
  102. package/dist/components/conversation/widget-renderer/resolve.js +1 -1
  103. package/dist/components/data/calendar/calendar.class.d.ts +15 -2
  104. package/dist/components/data/calendar/calendar.class.js +2 -2
  105. package/dist/components/data/calendar/calendar.styles.js +2 -28
  106. package/dist/components/data/condition-builder/condition-builder.class.d.ts +10 -6
  107. package/dist/components/data/condition-builder/condition-builder.class.js +2 -2
  108. package/dist/components/data/condition-builder/condition-builder.styles.js +0 -6
  109. package/dist/components/data/context-meter/context-meter.styles.js +0 -24
  110. package/dist/components/data/data-grid/data-grid.class.js +3 -3
  111. package/dist/components/data/data-grid/data-grid.styles.js +0 -22
  112. package/dist/components/data/document-library/document-library.class.js +2 -2
  113. package/dist/components/data/document-library/document-library.styles.js +0 -4
  114. package/dist/components/data/env-list/env-list.class.js +1 -1
  115. package/dist/components/data/env-list/env-list.styles.js +7 -4
  116. package/dist/components/data/file-tree/file-tree.class.d.ts +12 -0
  117. package/dist/components/data/flow-canvas/flow-canvas.styles.js +12 -19
  118. package/dist/components/data/flow-controls/flow-controls.class.js +2 -2
  119. package/dist/components/data/flow-controls/flow-controls.styles.js +3 -36
  120. package/dist/components/data/flow-minimap/flow-minimap.class.js +1 -1
  121. package/dist/components/data/flow-minimap/flow-minimap.styles.js +0 -9
  122. package/dist/components/data/flow-node/flow-node.styles.js +0 -23
  123. package/dist/components/data/flow-run-status/flow-run-status.class.js +1 -1
  124. package/dist/components/data/flow-run-status/flow-run-status.styles.js +0 -7
  125. package/dist/components/data/graph-query-builder/graph-query-builder.class.d.ts +0 -7
  126. package/dist/components/data/graph-query-builder/graph-query-builder.class.js +1 -1
  127. package/dist/components/data/graph-query-builder/graph-query-builder.styles.js +0 -10
  128. package/dist/components/data/heatmap/heatmap-scale.d.ts +20 -0
  129. package/dist/components/data/heatmap/heatmap-scale.js +1 -1
  130. package/dist/components/data/heatmap/heatmap.class.d.ts +84 -1
  131. package/dist/components/data/heatmap/heatmap.class.js +2 -2
  132. package/dist/components/data/heatmap/heatmap.styles.js +0 -54
  133. package/dist/components/data/pagination/pagination.styles.js +23 -46
  134. package/dist/components/data/sequence-strip/sequence-strip.class.d.ts +34 -1
  135. package/dist/components/data/sequence-strip/sequence-strip.class.js +5 -2
  136. package/dist/components/data/sequence-strip/sequence-strip.styles.js +14 -20
  137. package/dist/components/data/sparkline/sparkline.class.js +1 -1
  138. package/dist/components/data/stat/stat.styles.js +0 -67
  139. package/dist/components/data/table/table.class.d.ts +42 -3
  140. package/dist/components/data/table/table.class.js +4 -4
  141. package/dist/components/data/table/table.styles.js +20 -91
  142. package/dist/components/data/timeline/timeline-item.styles.js +0 -30
  143. package/dist/components/data/timeline/timeline.class.d.ts +89 -1
  144. package/dist/components/data/timeline/timeline.class.js +2 -2
  145. package/dist/components/data/timeline/timeline.styles.js +111 -31
  146. package/dist/components/data/tree/tree-item.styles.js +1 -28
  147. package/dist/components/data/tree/tree.class.js +2 -2
  148. package/dist/components/data/tree/tree.styles.js +0 -6
  149. package/dist/components/data/word-cloud/word-cloud.styles.js +0 -5
  150. package/dist/components/forms/button/button.class.js +1 -1
  151. package/dist/components/forms/button/button.styles.js +0 -105
  152. package/dist/components/forms/checkbox/checkbox.class.d.ts +3 -0
  153. package/dist/components/forms/checkbox/checkbox.class.js +1 -1
  154. package/dist/components/forms/checkbox/checkbox.styles.js +0 -39
  155. package/dist/components/forms/checkbox-group/checkbox-group.class.d.ts +21 -2
  156. package/dist/components/forms/checkbox-group/checkbox-group.class.js +1 -1
  157. package/dist/components/forms/checkbox-group/checkbox-group.styles.js +0 -18
  158. package/dist/components/forms/code-editor/code-editor.styles.js +0 -30
  159. package/dist/components/forms/color-picker/color-picker.class.js +2 -2
  160. package/dist/components/forms/color-picker/color-picker.styles.js +0 -69
  161. package/dist/components/forms/combobox/combobox.class.js +2 -2
  162. package/dist/components/forms/combobox/combobox.styles.js +22 -111
  163. package/dist/components/forms/combobox/option.styles.js +7 -1
  164. package/dist/components/forms/date-picker/date-input.class.js +1 -1
  165. package/dist/components/forms/date-picker/date-input.styles.js +12 -67
  166. package/dist/components/forms/date-picker/date-picker.class.d.ts +1 -0
  167. package/dist/components/forms/date-picker/date-picker.class.js +22 -20
  168. package/dist/components/forms/date-picker/date-picker.styles.js +36 -29
  169. package/dist/components/forms/emoji-picker/emoji-data-loader.d.ts +6 -3
  170. package/dist/components/forms/emoji-picker/emoji-data-loader.js +1 -1
  171. package/dist/components/forms/emoji-picker/emoji-picker.class.d.ts +8 -1
  172. package/dist/components/forms/emoji-picker/emoji-picker.class.js +1 -1
  173. package/dist/components/forms/emoji-picker/emoji-picker.styles.js +3 -41
  174. package/dist/components/forms/icon-button/icon-button.class.js +1 -1
  175. package/dist/components/forms/icon-button/icon-button.styles.js +0 -16
  176. package/dist/components/forms/input/input.styles.js +0 -54
  177. package/dist/components/forms/input/number-input.styles.d.ts +4 -5
  178. package/dist/components/forms/input/number-input.styles.js +0 -11
  179. package/dist/components/forms/input/time-input-shared.d.ts +11 -0
  180. package/dist/components/forms/input/time-input-shared.js +1 -1
  181. package/dist/components/forms/input/time-input.class.d.ts +11 -2
  182. package/dist/components/forms/input/time-input.class.js +1 -1
  183. package/dist/components/forms/input/time-input.styles.js +0 -6
  184. package/dist/components/forms/locale-picker/locale-picker.class.js +2 -2
  185. package/dist/components/forms/locale-picker/locale-picker.styles.js +1 -26
  186. package/dist/components/forms/otp-input/otp-input.class.js +3 -3
  187. package/dist/components/forms/otp-input/otp-input.styles.js +0 -16
  188. package/dist/components/forms/phone-input/phone-input.class.d.ts +9 -1
  189. package/dist/components/forms/phone-input/phone-input.class.js +2 -2
  190. package/dist/components/forms/phone-input/phone-input.styles.js +0 -37
  191. package/dist/components/forms/radio/radio-button.styles.js +1 -30
  192. package/dist/components/forms/radio/radio-group.styles.js +0 -4
  193. package/dist/components/forms/radio/radio.styles.js +0 -44
  194. package/dist/components/forms/rubric-form/rubric-form.styles.js +0 -5
  195. package/dist/components/forms/select/select.class.js +1 -1
  196. package/dist/components/forms/select/select.styles.js +14 -114
  197. package/dist/components/forms/slider/slider.styles.js +0 -55
  198. package/dist/components/forms/swatch-picker/swatch-picker.class.d.ts +0 -11
  199. package/dist/components/forms/swatch-picker/swatch-picker.class.js +2 -2
  200. package/dist/components/forms/swatch-picker/swatch-picker.styles.js +0 -77
  201. package/dist/components/forms/switch/switch.class.d.ts +3 -0
  202. package/dist/components/forms/switch/switch.class.js +1 -1
  203. package/dist/components/forms/switch/switch.styles.js +0 -37
  204. package/dist/components/forms/textarea/textarea.styles.js +0 -28
  205. package/dist/components/forms/time-range/time-range.styles.js +12 -84
  206. package/dist/components/forms/token-input/token-input.class.d.ts +23 -9
  207. package/dist/components/forms/token-input/token-input.class.js +1 -1
  208. package/dist/components/forms/token-input/token-input.styles.js +1 -54
  209. package/dist/components/layout/app-rail/app-rail-item.class.js +2 -2
  210. package/dist/components/layout/app-rail/app-rail-item.styles.js +0 -13
  211. package/dist/components/layout/app-rail/app-rail.class.d.ts +5 -0
  212. package/dist/components/layout/app-rail/app-rail.class.js +1 -1
  213. package/dist/components/layout/app-rail/app-rail.styles.js +0 -46
  214. package/dist/components/layout/button-group/button-group.styles.js +0 -6
  215. package/dist/components/layout/card/card.class.d.ts +12 -0
  216. package/dist/components/layout/card/card.styles.js +3 -11
  217. package/dist/components/layout/carousel/carousel.styles.js +0 -1
  218. package/dist/components/layout/command-palette/command-palette.class.d.ts +8 -0
  219. package/dist/components/layout/command-palette/command-palette.class.js +3 -1
  220. package/dist/components/layout/command-palette/command-palette.styles.js +1 -13
  221. package/dist/components/layout/control-group/control-group.styles.js +0 -7
  222. package/dist/components/layout/dashboard-grid/dashboard-grid.styles.js +6 -25
  223. package/dist/components/layout/details/accordion.class.d.ts +13 -0
  224. package/dist/components/layout/details/accordion.class.js +1 -1
  225. package/dist/components/layout/details/details.class.js +1 -1
  226. package/dist/components/layout/details/details.styles.js +0 -12
  227. package/dist/components/layout/dock-panel/dock-panel.styles.js +0 -45
  228. package/dist/components/layout/drilldown-panel/drilldown-panel.class.d.ts +2 -0
  229. package/dist/components/layout/drilldown-panel/drilldown-panel.class.js +2 -2
  230. package/dist/components/layout/drilldown-panel/drilldown-panel.styles.js +0 -4
  231. package/dist/components/layout/filter-bar/filter-bar.class.js +1 -1
  232. package/dist/components/layout/filter-bar/filter-bar.styles.js +0 -9
  233. package/dist/components/layout/menu/menu-item.class.d.ts +5 -0
  234. package/dist/components/layout/menu/menu-item.class.js +1 -1
  235. package/dist/components/layout/menu/menu-item.styles.js +0 -49
  236. package/dist/components/layout/menu/menu-label.styles.js +0 -2
  237. package/dist/components/layout/menu/menu.styles.js +0 -18
  238. package/dist/components/layout/multi-split/multi-split.styles.js +0 -63
  239. package/dist/components/layout/page/page.class.d.ts +4 -0
  240. package/dist/components/layout/page/page.class.js +1 -1
  241. package/dist/components/layout/reorder-list/reorder-item.styles.js +0 -4
  242. package/dist/components/layout/responsive-panel/responsive-panel.styles.js +0 -27
  243. package/dist/components/layout/scroller/scroller.styles.js +0 -20
  244. package/dist/components/layout/segmented/segmented.class.d.ts +7 -1
  245. package/dist/components/layout/segmented/segmented.class.js +1 -1
  246. package/dist/components/layout/segmented/segmented.styles.js +69 -37
  247. package/dist/components/layout/split-panel/split-panel.styles.js +1 -7
  248. package/dist/components/layout/stepper/stepper.class.d.ts +8 -1
  249. package/dist/components/layout/stepper/stepper.class.js +1 -1
  250. package/dist/components/layout/stepper/stepper.styles.js +140 -41
  251. package/dist/components/layout/tab-group/tab-group.class.d.ts +4 -1
  252. package/dist/components/layout/tab-group/tab-group.styles.js +9 -75
  253. package/dist/components/layout/tab-group/tab.styles.js +0 -2
  254. package/dist/components/layout/virtual-list/virtual-list.class.d.ts +4 -4
  255. package/dist/components/layout/virtual-list/virtual-list.class.js +1 -1
  256. package/dist/components/layout/virtual-list/virtual-list.styles.js +0 -68
  257. package/dist/components/layout/widget/widget.class.d.ts +5 -1
  258. package/dist/components/layout/widget/widget.class.js +1 -1
  259. package/dist/components/layout/widget/widget.styles.js +97 -40
  260. package/dist/components/media/animated-image/animated-image.class.d.ts +3 -0
  261. package/dist/components/media/animated-image/animated-image.class.js +1 -1
  262. package/dist/components/media/animated-image/animated-image.styles.js +0 -28
  263. package/dist/components/media/attachment-chip/attachment-chip.class.d.ts +1 -1
  264. package/dist/components/media/attachment-chip/attachment-chip.class.js +1 -1
  265. package/dist/components/media/attachment-chip/attachment-chip.styles.js +0 -31
  266. package/dist/components/media/attachment-trigger/attachment-trigger.class.js +3 -3
  267. package/dist/components/media/attachment-trigger/attachment-trigger.styles.js +0 -40
  268. package/dist/components/media/av-player/av-player.class.d.ts +5 -6
  269. package/dist/components/media/av-player/av-player.class.js +1 -1
  270. package/dist/components/media/av-player/av-player.styles.js +0 -45
  271. package/dist/components/media/avatar/avatar.styles.js +3 -16
  272. package/dist/components/media/file-icon/file-icon.class.d.ts +1 -2
  273. package/dist/components/media/file-icon/file-icon.class.js +1 -1
  274. package/dist/components/media/file-input/file-input.class.d.ts +12 -0
  275. package/dist/components/media/file-input/file-input.styles.js +3 -24
  276. package/dist/components/media/flag/flag.class.d.ts +20 -0
  277. package/dist/components/media/flag/flag.class.js +4 -2
  278. package/dist/components/media/flag/flag.styles.js +7 -1
  279. package/dist/components/media/flag/language-map.d.ts +10 -0
  280. package/dist/components/media/flag/language-map.js +1 -1
  281. package/dist/components/media/image-comparer/image-comparer.styles.js +4 -33
  282. package/dist/components/media/image-viewer/image-viewer.class.js +0 -2
  283. package/dist/components/media/image-viewer/image-viewer.styles.js +7 -27
  284. package/dist/components/media/lightbox/lightbox.class.js +0 -2
  285. package/dist/components/media/lightbox/lightbox.styles.js +0 -21
  286. package/dist/components/media/map/map-loader.d.ts +19 -1
  287. package/dist/components/media/map/map-loader.js +1 -1
  288. package/dist/components/media/map/map.class.d.ts +141 -1
  289. package/dist/components/media/map/map.class.js +15 -3
  290. package/dist/components/media/map/map.styles.js +20 -17
  291. package/dist/components/media/media-card/media-card.class.d.ts +14 -3
  292. package/dist/components/media/media-card/media-card.class.js +1 -1
  293. package/dist/components/media/media-card/media-card.styles.js +2 -28
  294. package/dist/components/media/pan-zoom/pan-zoom.styles.js +0 -3
  295. package/dist/components/media/qr-code/qr-code.class.d.ts +3 -2
  296. package/dist/components/media/qr-code/qr-code.class.js +2 -2
  297. package/dist/components/media/qr-code/qr-code.styles.js +0 -3
  298. package/dist/components/media/sequence-playback/sequence-playback.class.d.ts +2 -0
  299. package/dist/components/media/sequence-playback/sequence-playback.class.js +2 -1
  300. package/dist/components/media/sequence-playback/sequence-playback.styles.js +0 -19
  301. package/dist/components/media/video/video.class.d.ts +23 -2
  302. package/dist/components/media/video/video.class.js +3 -3
  303. package/dist/components/media/video/video.styles.js +4 -2
  304. package/dist/components/media/zoomable-frame/zoomable-frame.class.d.ts +3 -2
  305. package/dist/components/media/zoomable-frame/zoomable-frame.class.js +2 -2
  306. package/dist/components/media/zoomable-frame/zoomable-frame.styles.js +0 -5
  307. package/dist/components/overlays/alert/alert.styles.js +4 -2
  308. package/dist/components/overlays/badge/badge.styles.js +4 -48
  309. package/dist/components/overlays/badge/tag.styles.js +0 -14
  310. package/dist/components/overlays/callout/callout.styles.js +0 -11
  311. package/dist/components/overlays/chip/chip-group.styles.js +0 -18
  312. package/dist/components/overlays/chip/chip.styles.js +6 -69
  313. package/dist/components/overlays/dialog/confirm.d.ts +1 -4
  314. package/dist/components/overlays/dialog/confirm.js +1 -1
  315. package/dist/components/overlays/dialog/dialog.class.d.ts +12 -9
  316. package/dist/components/overlays/dialog/dialog.class.js +1 -1
  317. package/dist/components/overlays/dialog/dialog.styles.js +0 -43
  318. package/dist/components/overlays/drawer/drawer.class.d.ts +2 -2
  319. package/dist/components/overlays/drawer/drawer.styles.js +0 -9
  320. package/dist/components/overlays/empty/empty.styles.js +0 -12
  321. package/dist/components/overlays/kbd/kbd.styles.js +0 -8
  322. package/dist/components/overlays/overlay/dropdown.class.d.ts +1 -6
  323. package/dist/components/overlays/overlay/dropdown.class.js +2 -2
  324. package/dist/components/overlays/overlay/overlay.styles.js +0 -28
  325. package/dist/components/overlays/overlay/popover.class.d.ts +9 -1
  326. package/dist/components/overlays/overlay/popover.class.js +2 -2
  327. package/dist/components/overlays/overlay/tooltip.class.d.ts +10 -0
  328. package/dist/components/overlays/overlay/tooltip.class.js +1 -1
  329. package/dist/components/overlays/popup/popup.class.d.ts +1 -0
  330. package/dist/components/overlays/popup/popup.class.js +1 -1
  331. package/dist/components/overlays/popup/popup.styles.js +0 -15
  332. package/dist/components/overlays/progress/progress-ring.class.d.ts +9 -1
  333. package/dist/components/overlays/progress/progress-ring.class.js +3 -3
  334. package/dist/components/overlays/progress/progress.styles.js +0 -21
  335. package/dist/components/overlays/rating/rating.styles.js +0 -25
  336. package/dist/components/overlays/skeleton/skeleton.styles.js +0 -4
  337. package/dist/components/overlays/spinner/spinner.styles.js +0 -3
  338. package/dist/components/overlays/toast/toast-item.styles.js +3 -45
  339. package/dist/components/retrieval/chunk-inspector/chunk-inspector.styles.js +0 -35
  340. package/dist/components/retrieval/citation-badge/citation-badge.class.d.ts +2 -2
  341. package/dist/components/retrieval/citation-badge/citation-badge.class.js +3 -3
  342. package/dist/components/retrieval/citation-badge/citation-badge.styles.js +0 -20
  343. package/dist/components/retrieval/claim-evidence/claim-evidence.styles.js +0 -8
  344. package/dist/components/retrieval/community-card/community-card.class.d.ts +1 -0
  345. package/dist/components/retrieval/community-card/community-card.styles.js +0 -6
  346. package/dist/components/retrieval/embedding-explorer/embedding-explorer.styles.js +8 -12
  347. package/dist/components/retrieval/entity-card/entity-card.class.d.ts +4 -3
  348. package/dist/components/retrieval/entity-card/entity-card.class.js +1 -1
  349. package/dist/components/retrieval/entity-card/entity-card.styles.js +0 -12
  350. package/dist/components/retrieval/entity-chip/entity-chip.class.d.ts +10 -4
  351. package/dist/components/retrieval/entity-chip/entity-chip.class.js +3 -3
  352. package/dist/components/retrieval/entity-chip/entity-chip.styles.js +6 -9
  353. package/dist/components/retrieval/entity-dossier/entity-dossier.class.d.ts +19 -5
  354. package/dist/components/retrieval/graph/graph.class.d.ts +5 -0
  355. package/dist/components/retrieval/graph/graph.class.js +1 -1
  356. package/dist/components/retrieval/graph/graph.styles.js +0 -30
  357. package/dist/components/retrieval/graph-legend/graph-legend.styles.js +0 -3
  358. package/dist/components/retrieval/ingestion-queue/ingestion-queue.styles.js +0 -25
  359. package/dist/components/retrieval/knowledge-base-admin/knowledge-base-admin.class.d.ts +2 -0
  360. package/dist/components/retrieval/knowledge-base-admin/knowledge-base-admin.styles.js +0 -7
  361. package/dist/components/retrieval/knowledge-graph-explorer/knowledge-graph-explorer.class.d.ts +20 -6
  362. package/dist/components/retrieval/knowledge-graph-explorer/knowledge-graph-explorer.class.js +2 -2
  363. package/dist/components/retrieval/knowledge-graph-explorer/knowledge-graph-explorer.styles.js +0 -16
  364. package/dist/components/retrieval/mind-map/mind-map.class.d.ts +5 -3
  365. package/dist/components/retrieval/mind-map/mind-map.class.js +1 -1
  366. package/dist/components/retrieval/mind-map/mind-map.styles.js +0 -2
  367. package/dist/components/retrieval/neighbor-list/neighbor-list.class.d.ts +3 -2
  368. package/dist/components/retrieval/neighbor-list/neighbor-list.class.js +1 -1
  369. package/dist/components/retrieval/neighbor-list/neighbor-list.styles.js +0 -30
  370. package/dist/components/retrieval/node-palette/node-palette.styles.js +0 -11
  371. package/dist/components/retrieval/path-strip/path-strip.styles.js +0 -10
  372. package/dist/components/retrieval/provenance-panel/provenance-panel.class.d.ts +12 -3
  373. package/dist/components/retrieval/provenance-panel/provenance-panel.styles.js +0 -2
  374. package/dist/components/retrieval/rag-eval-dashboard/rag-eval-dashboard.class.d.ts +3 -2
  375. package/dist/components/retrieval/rag-eval-dashboard/rag-eval-dashboard.class.js +2 -2
  376. package/dist/components/retrieval/retrieval-results/retrieval-results.styles.js +0 -28
  377. package/dist/components/retrieval/retrieval-search/retrieval-search.styles.js +0 -4
  378. package/dist/components/retrieval/retrieval-trace/retrieval-trace.styles.js +0 -2
  379. package/dist/components/retrieval/source-card/source-card.styles.js +0 -13
  380. package/dist/components/retrieval/source-list/source-list.styles.js +0 -7
  381. package/dist/components/retrieval/source-picker/source-picker.styles.js +0 -7
  382. package/dist/components/utility/copy-button/copy-button.styles.js +0 -10
  383. package/dist/components/utility/diff-view/diff-view.styles.js +0 -14
  384. package/dist/components/utility/export-button/export-button.styles.js +0 -22
  385. package/dist/components/utility/icon/icon.styles.js +0 -6
  386. package/dist/components/utility/json-viewer/json-viewer.styles.js +2 -48
  387. package/dist/components/utility/known-date/known-date.class.d.ts +7 -3
  388. package/dist/components/utility/known-date/known-date.styles.js +10 -51
  389. package/dist/components/utility/live-region/live-region.styles.js +0 -4
  390. package/dist/components/utility/mention-popover/mention-popover.styles.js +0 -25
  391. package/dist/components/utility/poll-status/poll-status.styles.js +0 -4
  392. package/dist/components/utility/random-content/random-content.class.d.ts +22 -0
  393. package/dist/components/utility/random-content/random-content.class.js +3 -2
  394. package/dist/components/utility/random-content/random-content.styles.js +6 -13
  395. package/dist/components/utility/tour/tour.class.d.ts +4 -2
  396. package/dist/components/utility/tour/tour.class.js +3 -3
  397. package/dist/components/utility/tour/tour.styles.js +0 -13
  398. package/dist/components/utility/visually-hidden/visually-hidden.styles.js +0 -5
  399. package/dist/components/viewers/archive-viewer/archive-viewer.class.js +1 -1
  400. package/dist/components/viewers/archive-viewer/archive-viewer.styles.d.ts +2 -2
  401. package/dist/components/viewers/archive-viewer/archive-viewer.styles.js +0 -10
  402. package/dist/components/viewers/csv-viewer/csv-viewer.class.js +1 -1
  403. package/dist/components/viewers/csv-viewer/csv-viewer.styles.js +0 -19
  404. package/dist/components/viewers/dataset-viewer/dataset-viewer.class.js +1 -1
  405. package/dist/components/viewers/dataset-viewer/dataset-viewer.styles.js +0 -15
  406. package/dist/components/viewers/document-compare/document-compare.styles.js +0 -3
  407. package/dist/components/viewers/document-preview/document-preview.styles.js +0 -25
  408. package/dist/components/viewers/document-viewer/document-viewer.class.d.ts +2 -1
  409. package/dist/components/viewers/document-viewer/document-viewer.class.js +1 -1
  410. package/dist/components/viewers/document-viewer/document-viewer.styles.js +0 -5
  411. package/dist/components/viewers/docx-viewer/docx-viewer.styles.js +0 -17
  412. package/dist/components/viewers/ebook-viewer/ebook-viewer.styles.js +0 -4
  413. package/dist/components/viewers/email-viewer/email-viewer.styles.js +0 -7
  414. package/dist/components/viewers/geojson-view/geojson-view.styles.js +0 -5
  415. package/dist/components/viewers/highlight-layer/highlight-layer.styles.js +0 -3
  416. package/dist/components/viewers/notebook-viewer/notebook-viewer.class.js +1 -1
  417. package/dist/components/viewers/notebook-viewer/notebook-viewer.styles.js +0 -38
  418. package/dist/components/viewers/page-rail/page-rail.class.js +1 -1
  419. package/dist/components/viewers/page-rail/page-rail.styles.js +0 -13
  420. package/dist/components/viewers/pdf-viewer/pdf-loader.d.ts +13 -2
  421. package/dist/components/viewers/pdf-viewer/pdf-loader.js +1 -1
  422. package/dist/components/viewers/pdf-viewer/pdf-viewer.class.d.ts +32 -2
  423. package/dist/components/viewers/pdf-viewer/pdf-viewer.class.js +4 -4
  424. package/dist/components/viewers/pdf-viewer/pdf-viewer.styles.js +1 -27
  425. package/dist/components/viewers/pptx-viewer/pptx-viewer.styles.js +0 -3
  426. package/dist/components/viewers/spreadsheet-viewer/spreadsheet-viewer.class.js +1 -1
  427. package/dist/components/viewers/spreadsheet-viewer/spreadsheet-viewer.styles.js +0 -14
  428. package/dist/components/viewers/svg-viewer/svg-viewer.styles.js +0 -7
  429. package/dist/components/viewers/xml-viewer/xml-viewer.styles.js +2 -24
  430. package/dist/custom-elements-jsx.d.ts +56 -37
  431. package/dist/events.d.ts +43 -33
  432. package/dist/internal/agent-status-variants.d.ts +18 -0
  433. package/dist/internal/agent-status-variants.js +1 -0
  434. package/dist/internal/announcer.d.ts +8 -3
  435. package/dist/internal/announcer.js +1 -1
  436. package/dist/internal/autoloader-manifest.js +1 -1
  437. package/dist/internal/canvas-color.d.ts +16 -0
  438. package/dist/internal/canvas-color.js +1 -1
  439. package/dist/internal/catalog-picker.d.ts +0 -1
  440. package/dist/internal/catalog-picker.js +1 -1
  441. package/dist/internal/default-strings.generated.d.ts +1 -0
  442. package/dist/internal/default-strings.generated.js +1 -1
  443. package/dist/internal/dev-mode-attribute-warning.d.ts +27 -4
  444. package/dist/internal/dev-mode-attribute-warning.js +1 -1
  445. package/dist/internal/localization-runtime.js +1 -1
  446. package/dist/internal/localization-types.d.ts +1 -1
  447. package/dist/internal/localization.js +1 -1
  448. package/dist/internal/lyra-element.d.ts +13 -0
  449. package/dist/internal/lyra-element.js +1 -1
  450. package/dist/internal/media-controller.js +1 -1
  451. package/dist/internal/package-metadata.d.ts +1 -1
  452. package/dist/internal/package-metadata.js +1 -1
  453. package/dist/internal/scroll-overflow.d.ts +35 -13
  454. package/dist/internal/scroll-overflow.js +1 -1
  455. package/dist/internal/sizes.styles.js +0 -2
  456. package/dist/internal/specialist-tokens.styles.js +6 -11
  457. package/dist/internal/text-highlights.d.ts +4 -1
  458. package/dist/internal/text-highlights.js +1 -1
  459. package/dist/internal/tokens/palette.styles.js +0 -15
  460. package/dist/internal/tokens.styles.js +19 -113
  461. package/dist/lyra.d.ts +8 -5
  462. package/dist/styles/reservations.css +82 -0
  463. package/dist/svelte.d.ts +56 -37
  464. package/dist/translations/ar.js +1 -1
  465. package/dist/translations/de.js +1 -1
  466. package/dist/translations/es.js +1 -1
  467. package/dist/translations/fa.js +1 -1
  468. package/dist/translations/fr.js +1 -1
  469. package/dist/translations/he.js +1 -1
  470. package/dist/translations/ja.js +1 -1
  471. package/dist/translations/pt-BR.js +1 -1
  472. package/dist/translations/ru.js +1 -1
  473. package/dist/translations/zh-CN.js +1 -1
  474. package/dist/vue.d.ts +56 -37
  475. package/llms/components/lr-accordion-item.md +12 -3
  476. package/llms/components/lr-accordion.md +11 -2
  477. package/llms/components/lr-agent-eval-dashboard.md +1 -1
  478. package/llms/components/lr-agent-trace.md +3 -1
  479. package/llms/components/lr-agent-workspace.md +20 -0
  480. package/llms/components/lr-artifact-panel.md +10 -4
  481. package/llms/components/lr-attachment-chip.md +7 -4
  482. package/llms/components/lr-attachment-trigger.md +7 -4
  483. package/llms/components/lr-av-player.md +3 -1
  484. package/llms/components/lr-avatar.md +6 -6
  485. package/llms/components/lr-bar-chart.md +4 -3
  486. package/llms/components/lr-box-plot.md +1 -1
  487. package/llms/components/lr-browser-frame.md +7 -3
  488. package/llms/components/lr-bubble-chart.md +4 -3
  489. package/llms/components/lr-calendar.md +9 -2
  490. package/llms/components/lr-card.md +24 -0
  491. package/llms/components/lr-chart.md +32 -8
  492. package/llms/components/lr-chat-viewport.md +7 -2
  493. package/llms/components/lr-checkbox-group.md +13 -5
  494. package/llms/components/lr-checkbox.md +5 -2
  495. package/llms/components/lr-checkpoint.md +6 -2
  496. package/llms/components/lr-combobox.md +5 -2
  497. package/llms/components/lr-command-palette.md +4 -1
  498. package/llms/components/lr-confirm-bar.md +7 -3
  499. package/llms/components/lr-context-meter.md +12 -11
  500. package/llms/components/lr-conversation-item.md +7 -4
  501. package/llms/components/lr-details.md +11 -2
  502. package/llms/components/lr-dialog.md +15 -10
  503. package/llms/components/lr-dock-panel.md +7 -10
  504. package/llms/components/lr-document-preview.md +6 -1
  505. package/llms/components/lr-document-viewer.md +3 -2
  506. package/llms/components/lr-doughnut-chart.md +4 -3
  507. package/llms/components/lr-drawer.md +3 -3
  508. package/llms/components/lr-entity-card.md +3 -3
  509. package/llms/components/lr-entity-chip.md +1 -1
  510. package/llms/components/lr-entity-dossier.md +4 -1
  511. package/llms/components/lr-file-input.md +2 -2
  512. package/llms/components/lr-flag.md +20 -5
  513. package/llms/components/lr-heatmap.md +28 -0
  514. package/llms/components/lr-histogram.md +3 -1
  515. package/llms/components/lr-icon.md +1 -1
  516. package/llms/components/lr-json-schema-viewer.md +2 -1
  517. package/llms/components/lr-knowledge-graph-explorer.md +8 -3
  518. package/llms/components/lr-known-date.md +4 -2
  519. package/llms/components/lr-line-chart.md +4 -3
  520. package/llms/components/lr-lite-chart.md +16 -6
  521. package/llms/components/lr-map.md +72 -8
  522. package/llms/components/lr-markdown-core.md +3 -2
  523. package/llms/components/lr-media-card.md +28 -12
  524. package/llms/components/lr-message-parts.md +2 -1
  525. package/llms/components/lr-model-select.md +9 -10
  526. package/llms/components/lr-model-settings-panel.md +9 -9
  527. package/llms/components/lr-neighbor-list.md +1 -1
  528. package/llms/components/lr-notebook-viewer.md +6 -3
  529. package/llms/components/lr-option.md +5 -2
  530. package/llms/components/lr-pdf-viewer.md +62 -2
  531. package/llms/components/lr-pie-chart.md +4 -3
  532. package/llms/components/lr-polar-area-chart.md +4 -3
  533. package/llms/components/lr-popover.md +5 -0
  534. package/llms/components/lr-progress-ring.md +8 -1
  535. package/llms/components/lr-prompt-studio.md +1 -1
  536. package/llms/components/lr-provenance-panel.md +4 -2
  537. package/llms/components/lr-qr-code.md +1 -1
  538. package/llms/components/lr-radar-chart.md +4 -3
  539. package/llms/components/lr-rag-eval-dashboard.md +2 -2
  540. package/llms/components/lr-random-content.md +13 -0
  541. package/llms/components/lr-reorder-item.md +6 -1
  542. package/llms/components/lr-reorder-list.md +6 -1
  543. package/llms/components/lr-responsive-panel.md +11 -7
  544. package/llms/components/lr-scatter-chart.md +4 -3
  545. package/llms/components/lr-sequence-strip.md +16 -2
  546. package/llms/components/lr-slider.md +12 -5
  547. package/llms/components/lr-sparkline.md +1 -1
  548. package/llms/components/lr-suggestion-chips.md +7 -2
  549. package/llms/components/lr-swatch-picker.md +5 -5
  550. package/llms/components/lr-switch.md +5 -2
  551. package/llms/components/lr-table.md +30 -4
  552. package/llms/components/lr-terminal.md +3 -1
  553. package/llms/components/lr-thread-list.md +8 -8
  554. package/llms/components/lr-time-input.md +6 -1
  555. package/llms/components/lr-timeline-item.md +24 -0
  556. package/llms/components/lr-timeline.md +25 -1
  557. package/llms/components/lr-token-input.md +7 -2
  558. package/llms/components/lr-tool-approval-dialog.md +7 -8
  559. package/llms/components/lr-tool-call-chip.md +5 -1
  560. package/llms/components/lr-tool-param-form.md +14 -12
  561. package/llms/components/lr-tool-result-dialog.md +11 -9
  562. package/llms/components/lr-tool-result-view.md +7 -6
  563. package/llms/components/lr-tool-select-dialog.md +18 -16
  564. package/llms/components/lr-trace-tree.md +3 -1
  565. package/llms/components/lr-usage-badge.md +4 -1
  566. package/llms/components/lr-video-playlist.md +1 -1
  567. package/llms/components/lr-virtual-list.md +22 -14
  568. package/llms/components/lr-voice-picker.md +8 -5
  569. package/llms/components/lr-widget-renderer.md +3 -3
  570. package/llms/components/lr-widget.md +1 -1
  571. package/llms/components/lr-word-cloud.md +6 -2
  572. package/llms/peers.md +12 -2
  573. package/llms/shared.md +70 -2
  574. package/llms-full.txt +1143 -285
  575. package/package.json +17 -5
  576. package/vscode-css-data.json +37 -2
  577. package/vscode-html-data.json +401 -44
  578. package/web-types.json +299 -55
@@ -6,9 +6,6 @@ import{css}from"lit";const styles=css`
6
6
  [part='base'] {
7
7
  max-inline-size: 100%;
8
8
  }
9
- /* Line packing is consumer-tunable because it is unreachable otherwise: centering the chips under
10
- centered empty-state text needs the wrapped final line centered too, and ::part(base) can only
11
- center the row while it still fits on one line. */
12
9
  .row {
13
10
  display: flex;
14
11
  justify-content: var(--lr-suggestion-chips-justify, flex-start);
@@ -49,8 +46,6 @@ import{css}from"lit";const styles=css`
49
46
  background: var(--lr-suggestion-chips-hover-bg, var(--lr-color-brand-quiet));
50
47
  border-color: var(--lr-suggestion-chips-hover-border, var(--lr-color-brand));
51
48
  }
52
- /* Mixes the SAME --lr-suggestion-chips-hover-bg the rule above uses, so a consumer retinting the
53
- hover fill gets a matching pressed step without a second custom property to keep in sync. */
54
49
  [part~='chip']:active {
55
50
  background: color-mix(
56
51
  in oklab,
@@ -30,10 +30,6 @@ import{css}from"lit";const styles=css`
30
30
  outline: var(--lr-focus-ring-width) solid var(--lr-focus-ring-color);
31
31
  outline-offset: var(--lr-focus-ring-offset);
32
32
  }
33
- /* no-pressed-state: [part='search-input'] is a text field. A press on it is answered by the field
34
- taking focus and raising its focus ring, which is both stronger than any momentary pressed tint
35
- and outlasts the mouse button; a second, competing flash on mousedown would only add noise to
36
- the one interaction that already has unambiguous feedback. */
37
33
  [part='search-input']:hover {
38
34
  border-color: var(--lr-color-brand);
39
35
  }
@@ -52,14 +48,6 @@ import{css}from"lit";const styles=css`
52
48
  display: flex;
53
49
  flex-direction: column;
54
50
  }
55
- /* The internal list has to fill whatever height this component was given, instead of scrolling
56
- inside lr-virtual-list's own 24rem --lr-virtual-list-height default. Deliberately *not*
57
- --lr-virtual-list-height: 100%: that percentage resolves against this host, which is a flex
58
- item, so in an auto-height container it chains to auto and the viewport either collapses to
59
- zero (no rows) or grows to the full un-virtualized content height (rows). Making the list host
60
- a column flex container instead turns the shipped block-size: 24rem on [part='base'] into its
61
- *flex-basis*: it grows to fill a bounded pane, shrinks below 24rem in a short one, and in an
62
- auto-height container falls back to exactly the 24rem it renders at today. */
63
51
  lr-virtual-list {
64
52
  flex: 1 1 auto;
65
53
  min-block-size: 0;
@@ -84,11 +72,6 @@ import{css}from"lit";const styles=css`
84
72
  background: var(--lr-color-surface);
85
73
  color: var(--lr-color-text-quiet);
86
74
  }
87
- /* sticky-groups: the pinned copy of the current group header. lr-virtual-list ships that layer
88
- pointer-transparent, because it is a copy of a row that already exists; this component's header
89
- owns a real collapse toggle, so it opts back in. Everything else about the copy -- padding,
90
- background, the toggle and icon -- comes from the group-header/group-toggle/group-icon rules
91
- around this one, which the copy shares by rendering the same parts. */
92
75
  lr-virtual-list::part(sticky-group) {
93
76
  pointer-events: auto;
94
77
  }
@@ -138,10 +121,6 @@ import{css}from"lit";const styles=css`
138
121
  lr-virtual-list::part(row-actions) {
139
122
  min-inline-size: 0;
140
123
  }
141
- /* row-start/row-actions (see thread-list.class.ts) are plain <span>s, so they default to
142
- display: inline -- an ordinary text baseline box with descender strut height. Their
143
- content is adornments (icon/avatar, action buttons), not text, so center them on a flex
144
- line instead; row-content/row-meta hold real text and keep their own inline/block flow. */
145
124
  lr-virtual-list::part(row-start),
146
125
  lr-virtual-list::part(row-actions) {
147
126
  display: inline-flex;
@@ -151,8 +130,6 @@ import{css}from"lit";const styles=css`
151
130
  display: inline-flex;
152
131
  align-items: center;
153
132
  justify-content: center;
154
- /* Keep the glyph compact while giving the interactive box the shared
155
- minimum target size. */
156
133
  inline-size: var(--lr-size-1-5rem);
157
134
  block-size: var(--lr-size-1-5rem);
158
135
  min-inline-size: var(--lr-icon-button-size);
@@ -42,9 +42,9 @@ export interface LyraTranscriptFeedEventMap {
42
42
  *
43
43
  * @customElement lr-transcript-feed
44
44
  * @slot empty - Custom empty state. Default: the localized "No transcript yet".
45
- * @event lr-follow-change - `detail: { following: boolean }` — fires on every `follow` transition,
46
- * whether user-driven (scroll away/jump button) or a direct host assignment. Never fires for the
47
- * value already in effect on the very first render.
45
+ * @event lr-follow-change - `detail: { following: boolean }` — a user scroll or jump-button click
46
+ * changed stick-to-bottom. Direct `follow` assignments and calling `scrollToBottom()` directly
47
+ * are controlled input and do not echo an event, matching `lr-terminal`'s identical contract.
48
48
  * @csspart base - The scroll container.
49
49
  * @csspart log - The `role="log"` region wrapping final entries only.
50
50
  * @csspart interim-area - The wrapper around the interim (not-yet-final) entries, rendered as a sibling of `log`. Only rendered while at least one interim entry exists.
@@ -114,9 +114,21 @@ export declare class LyraTranscriptFeed extends LyraElement<LyraTranscriptFeedEv
114
114
  /** Re-engages `follow` and scrolls the feed to its current bottom, instantly -- matching the
115
115
  * shared stick-to-bottom contract. New entries can arrive in rapid succession while streaming;
116
116
  * an animated scroll on every single one would fight itself rather than settle cleanly, so this
117
- * is a plain jump rather than a CSS-smoothed transition. */
117
+ * is a plain jump rather than a CSS-smoothed transition. Imperative navigation, like a direct
118
+ * `follow` assignment: does not itself emit `lr-follow-change` (see `onJumpClick`, the
119
+ * user-driven wrapper that does, mirroring `lr-terminal`'s `scrollToBottom()`/`jumpToLatest()`
120
+ * split). */
118
121
  scrollToBottom(): void;
122
+ /** The sole source of a user-driven `follow` transition from scrolling: this handler runs only
123
+ * in response to a real `scroll` event on `[part="base"]`, so setting `follow` here -- unlike a
124
+ * generic `updated()` diff of the property, which cannot tell a user scroll from a host
125
+ * assignment or this component's own `scrollToBottom()` -- is unambiguously the user's own
126
+ * action, and is the only path that emits `lr-follow-change`. */
119
127
  private onScroll;
128
+ /** The jump-button's click handler: the other user-driven source of an `lr-follow-change`
129
+ * transition. Delegates the actual re-engage/scroll to `scrollToBottom()` (which does not
130
+ * itself emit) and emits only when clicking it actually changed `follow` -- identical shape to
131
+ * `lr-terminal`'s `jumpToLatest()`. */
120
132
  private onJumpClick;
121
133
  private showSpeakerFor;
122
134
  private formatTs;
@@ -1,4 +1,4 @@
1
- var __decorate=function(decorators,target,key,desc){var c=arguments.length,r=c<3?target:desc===null?desc=Object.getOwnPropertyDescriptor(target,key):desc,d;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")r=Reflect.decorate(decorators,target,key,desc);else for(var i=decorators.length-1;i>=0;i--)(d=decorators[i])&&(r=(c<3?d(r):c>3?d(target,key,r):d(target,key))||r);return c>3&&r&&Object.defineProperty(target,key,r),r};import{html,nothing}from"lit";import{property}from"lit/decorators.js";import{repeat}from"lit/directives/repeat.js";import{LyraElement}from"../../../internal/lyra-element.js";import{acquireAnnouncementSink}from"../../../internal/announcer.js";import{getDateTimeFormat}from"../../../internal/intl-cache.js";import{finiteCount}from"../../../internal/numbers.js";import{styles}from"./transcript-feed.styles.js";import{presenceTrueDefaultBooleanConverter as trueDefaultBooleanConverter}from"../../../internal/converters.js";import{normalizeLyraTimestamp}from"../timestamp.js";import{LYRA_DEFAULT_jumpToLatest,LYRA_DEFAULT_transcriptFeedEmpty,LYRA_DEFAULT_transcriptFeedInterim,LYRA_DEFAULT_transcriptFeedLabel}from"../../../internal/default-strings.generated.js";const NEAR_BOTTOM_PX=48;class LyraTranscriptFeed extends LyraElement{constructor(){super(...arguments),this.entries=[],this.follow=!0,this.showTimestamps=!1,this.maxRenderedEntries=500,this.sessionId="",this.accessibleLabel=null,this._isFirstUpdate=!0,this.announcedFinalIds=new Set,this.sessionChanged=!1,this.onScroll=e=>{const base=e.currentTarget,atBottom=base.scrollHeight-base.scrollTop-base.clientHeight<=NEAR_BOTTOM_PX;atBottom!==this.follow&&(this.follow=atBottom)},this.onJumpClick=()=>{this.scrollToBottom()}}static{this.defaultStrings={...super.defaultStrings,jumpToLatest:LYRA_DEFAULT_jumpToLatest,transcriptFeedEmpty:LYRA_DEFAULT_transcriptFeedEmpty,transcriptFeedInterim:LYRA_DEFAULT_transcriptFeedInterim,transcriptFeedLabel:LYRA_DEFAULT_transcriptFeedLabel}}static{this.ownedCollectionProperties=Object.freeze(["entries"])}static{this.styles=[LyraElement.styles,styles]}get effectiveMaxRenderedEntries(){return finiteCount(this.maxRenderedEntries,500)}get normalizedEntries(){const seen=new Set;return this.entries.filter(entry=>entry===null||typeof entry!="object"||typeof entry.id!="string"||entry.id.trim().length===0||seen.has(entry.id)?!1:(seen.add(entry.id),!0))}get renderedEntries(){const entries=this.normalizedEntries,maxRenderedEntries=this.effectiveMaxRenderedEntries;return maxRenderedEntries>0&&entries.length>maxRenderedEntries?entries.slice(-maxRenderedEntries):entries}connectedCallback(){super.connectedCallback(),this.syncAnnouncementSink()}disconnectedCallback(){super.disconnectedCallback(),this.releaseAnnouncementSink()}adoptedCallback(){super.adoptedCallback(),this.syncAnnouncementSink()}releaseAnnouncementSink(){this.announcementSink?.release(),this.announcementSink=void 0}syncAnnouncementSink(){if(!this.isConnected){this.releaseAnnouncementSink();return}this.announcementSink?.element.ownerDocument!==this.ownerDocument&&(this.releaseAnnouncementSink(),this.announcementSink=acquireAnnouncementSink("polite",{document:this.ownerDocument,source:this}))}willUpdate(changed){super.willUpdate(changed),this._isFirstUpdate=!this.hasUpdated,this.sessionChanged=changed.has("sessionId")&&this.hasUpdated,this.sessionChanged&&this.announcedFinalIds.clear()}updated(changed){super.updated(changed),changed.has("entries")&&(this.follow&&this.scrollToBottom(),this.announceFinalizedEntries()),changed.has("follow")&&(this.follow&&this.scrollToBottom(),this._isFirstUpdate||this.emit("lr-follow-change",{following:this.follow}))}announceFinalizedEntries(){const alreadyAnnounced=this.announcedFinalIds,fresh=[];for(const entry of this.normalizedEntries)entry.interim||alreadyAnnounced.has(entry.id)||(alreadyAnnounced.add(entry.id),fresh.push(entry.text));if(this._isFirstUpdate||this.sessionChanged)return;const sink=this.announcementSink;if(sink)for(const text of fresh){const message=text.replace(/\s+/g," ").trim();message&&sink.announce(message)}}scrollToBottom(){this.follow=!0;const base=this.renderRoot.querySelector('[part="base"]');base&&(base.scrollTop=base.scrollHeight)}showSpeakerFor(list,index){const prev=list[index-1],current=list[index];return!prev||prev.speaker!==current.speaker}formatTs(value){const date=normalizeLyraTimestamp(value);return date?this.formatTimestamp?this.formatTimestamp(date):getDateTimeFormat(this.effectiveLocale,{hour:"numeric",minute:"2-digit"}).format(date):null}renderEntry(entry,showSpeaker,interim){const parts=["entry"];interim&&parts.push("interim");const timestamp=entry.timestamp==null?null:this.formatTs(entry.timestamp);return html`
1
+ var __decorate=function(decorators,target,key,desc){var c=arguments.length,r=c<3?target:desc===null?desc=Object.getOwnPropertyDescriptor(target,key):desc,d;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")r=Reflect.decorate(decorators,target,key,desc);else for(var i=decorators.length-1;i>=0;i--)(d=decorators[i])&&(r=(c<3?d(r):c>3?d(target,key,r):d(target,key))||r);return c>3&&r&&Object.defineProperty(target,key,r),r};import{html,nothing}from"lit";import{property}from"lit/decorators.js";import{repeat}from"lit/directives/repeat.js";import{LyraElement}from"../../../internal/lyra-element.js";import{acquireAnnouncementSink}from"../../../internal/announcer.js";import{getDateTimeFormat}from"../../../internal/intl-cache.js";import{finiteCount}from"../../../internal/numbers.js";import{styles}from"./transcript-feed.styles.js";import{presenceTrueDefaultBooleanConverter as trueDefaultBooleanConverter}from"../../../internal/converters.js";import{normalizeLyraTimestamp}from"../timestamp.js";import{LYRA_DEFAULT_jumpToLatest,LYRA_DEFAULT_transcriptFeedEmpty,LYRA_DEFAULT_transcriptFeedInterim,LYRA_DEFAULT_transcriptFeedLabel}from"../../../internal/default-strings.generated.js";const NEAR_BOTTOM_PX=48;class LyraTranscriptFeed extends LyraElement{constructor(){super(...arguments),this.entries=[],this.follow=!0,this.showTimestamps=!1,this.maxRenderedEntries=500,this.sessionId="",this.accessibleLabel=null,this._isFirstUpdate=!0,this.announcedFinalIds=new Set,this.sessionChanged=!1,this.onScroll=e=>{const base=e.currentTarget,atBottom=base.scrollHeight-base.scrollTop-base.clientHeight<=NEAR_BOTTOM_PX;atBottom!==this.follow&&(this.follow=atBottom,this.emit("lr-follow-change",{following:atBottom}))},this.onJumpClick=()=>{const changed=!this.follow;this.scrollToBottom(),changed&&this.emit("lr-follow-change",{following:!0})}}static{this.defaultStrings={...super.defaultStrings,jumpToLatest:LYRA_DEFAULT_jumpToLatest,transcriptFeedEmpty:LYRA_DEFAULT_transcriptFeedEmpty,transcriptFeedInterim:LYRA_DEFAULT_transcriptFeedInterim,transcriptFeedLabel:LYRA_DEFAULT_transcriptFeedLabel}}static{this.ownedCollectionProperties=Object.freeze(["entries"])}static{this.styles=[LyraElement.styles,styles]}get effectiveMaxRenderedEntries(){return finiteCount(this.maxRenderedEntries,500)}get normalizedEntries(){const seen=new Set;return this.entries.filter(entry=>entry===null||typeof entry!="object"||typeof entry.id!="string"||entry.id.trim().length===0||seen.has(entry.id)?!1:(seen.add(entry.id),!0))}get renderedEntries(){const entries=this.normalizedEntries,maxRenderedEntries=this.effectiveMaxRenderedEntries;return maxRenderedEntries>0&&entries.length>maxRenderedEntries?entries.slice(-maxRenderedEntries):entries}connectedCallback(){super.connectedCallback(),this.syncAnnouncementSink()}disconnectedCallback(){super.disconnectedCallback(),this.releaseAnnouncementSink()}adoptedCallback(){super.adoptedCallback(),this.syncAnnouncementSink()}releaseAnnouncementSink(){this.announcementSink?.release(),this.announcementSink=void 0}syncAnnouncementSink(){if(!this.isConnected){this.releaseAnnouncementSink();return}this.announcementSink?.element.ownerDocument!==this.ownerDocument&&(this.releaseAnnouncementSink(),this.announcementSink=acquireAnnouncementSink("polite",{document:this.ownerDocument,source:this}))}willUpdate(changed){super.willUpdate(changed),this._isFirstUpdate=!this.hasUpdated,this.sessionChanged=changed.has("sessionId")&&this.hasUpdated,this.sessionChanged&&this.announcedFinalIds.clear()}updated(changed){super.updated(changed),changed.has("entries")&&(this.follow&&this.scrollToBottom(),this.announceFinalizedEntries())}announceFinalizedEntries(){const alreadyAnnounced=this.announcedFinalIds,fresh=[];for(const entry of this.normalizedEntries)entry.interim||alreadyAnnounced.has(entry.id)||(alreadyAnnounced.add(entry.id),fresh.push(entry.text));if(this._isFirstUpdate||this.sessionChanged)return;const sink=this.announcementSink;if(sink)for(const text of fresh){const message=text.replace(/\s+/g," ").trim();message&&sink.announce(message)}}scrollToBottom(){this.follow=!0;const base=this.renderRoot.querySelector('[part="base"]');base&&(base.scrollTop=base.scrollHeight)}showSpeakerFor(list,index){const prev=list[index-1],current=list[index];return!prev||prev.speaker!==current.speaker}formatTs(value){const date=normalizeLyraTimestamp(value);return date?this.formatTimestamp?this.formatTimestamp(date):getDateTimeFormat(this.effectiveLocale,{hour:"numeric",minute:"2-digit"}).format(date):null}renderEntry(entry,showSpeaker,interim){const parts=["entry"];interim&&parts.push("interim");const timestamp=entry.timestamp==null?null:this.formatTs(entry.timestamp);return html`
2
2
  <div part=${parts.join(" ")} ?data-interim=${interim}>
3
3
  ${showSpeaker&&entry.speaker?html`<span part="speaker">${entry.speaker}</span>`:nothing}
4
4
  <span part="text" dir="auto">${entry.text}</span>
@@ -95,7 +95,6 @@ import{css}from"lit";import{srOnly}from"../../../internal/a11y.js";const styles=
95
95
  background: var(--lr-color-surface);
96
96
  color: var(--lr-color-text);
97
97
  cursor: pointer;
98
- /* Overlay step, matching lr-chat-viewport's jump pill: it floats over the feed, not in it. */
99
98
  box-shadow: var(--lr-shadow-m);
100
99
  }
101
100
  [part='jump-button']:focus-visible {
@@ -9,19 +9,9 @@ import{css}from"lit";const styles=css`
9
9
  --_lr-inline-cursor-width-default: var(--lr-size-0-125rem);
10
10
  --_lr-inline-cursor-height-default: var(--lr-size-1em);
11
11
  --_lr-typing-duration-default: var(--lr-transition-ambient);
12
- /* Themeable, not auto-derived from --lr-typing-duration: like the compound
13
- --lr-transition-ambient it aliases (duration + timing-function, e.g. "1.8s ease-in-out")
14
- baked into the animation: shorthand above, it can't be decomposed via calc() into a
15
- fraction of just its duration. A consumer retiming --lr-typing-duration keeps the
16
- stagger proportional by also setting these two explicitly. */
17
12
  --_lr-typing-dot-stagger-1-default: 600ms;
18
13
  --_lr-typing-dot-stagger-2-default: 1200ms;
19
14
  }
20
- /* The shared six-step size ladder renders here as three tiers: a presence cue is a few pixels of
21
- decoration, and six distinguishable dot diameters inside a 1em line box do not exist. Every
22
- step of the ladder still matches a rule -- a value the type accepts and no selector matches
23
- would quietly render at the default tier, which nothing in this repo can detect. Both
24
- spellings of each tier are listed, so migrating markup never loses its sizing. */
25
15
  :host([size='2xs']),
26
16
  :host([size='xs']),
27
17
  :host([size='s']),
@@ -44,7 +34,6 @@ import{css}from"lit";const styles=css`
44
34
  gap: var(--lr-typing-gap, var(--_lr-typing-gap-default));
45
35
  }
46
36
 
47
- /* -- dots -------------------------------------------------------------- */
48
37
  [part='dot'] {
49
38
  inline-size: var(--lr-typing-dot-size, var(--_lr-typing-dot-size-default));
50
39
  block-size: var(--lr-typing-dot-size, var(--_lr-typing-dot-size-default));
@@ -72,8 +61,6 @@ import{css}from"lit";const styles=css`
72
61
  }
73
62
  }
74
63
 
75
- /* -- pulse --------------------------------------------------------------
76
- A single breathing dot, meant for tighter spaces than three dots allow. */
77
64
  [part='pulse'] {
78
65
  inline-size: var(--lr-typing-dot-size, var(--_lr-typing-dot-size-default));
79
66
  block-size: var(--lr-typing-dot-size, var(--_lr-typing-dot-size-default));
@@ -95,12 +82,6 @@ import{css}from"lit";const styles=css`
95
82
  }
96
83
  }
97
84
 
98
- /* -- cursor -------------------------------------------------------------
99
- A blinking vertical bar for inline placement at the tail of streamed
100
- text. The two adjacent keyframe stops (49% / 50%) hold identical values
101
- either side of an instant flip, so the blink still reads as a sharp
102
- on/off even though the token's ease-out timing-function is in effect
103
- across the whole animation. */
104
85
  [part='cursor'] {
105
86
  inline-size: var(--lr-inline-cursor-width, var(--_lr-inline-cursor-width-default));
106
87
  block-size: var(--lr-inline-cursor-height, var(--_lr-inline-cursor-height-default));
@@ -120,10 +101,6 @@ import{css}from"lit";const styles=css`
120
101
  }
121
102
  }
122
103
 
123
- /* Every variant collapses to its plain, fully-visible resting state
124
- under reduced motion -- never a static mid-animation frame (e.g. a
125
- permanently-invisible cursor, had the blink's "off" half been frozen
126
- instead). */
127
104
  @media (prefers-reduced-motion: reduce) {
128
105
  [part='dot'],
129
106
  [part='pulse'],
@@ -8,9 +8,6 @@ import{css}from"lit";const styles=css`
8
8
  [part='base']:where([tabindex]) {
9
9
  cursor: help;
10
10
  }
11
- /* no-pressed-state: with a tabindex, [part='base'] is a focusable role="group" that reveals a
12
- tooltip (cursor: help) -- it is not activatable, has no click handler and nothing happens on
13
- mousedown, so a pressed tint would promise an action the badge does not perform. */
14
11
  :where([part='base'][tabindex]):hover {
15
12
  background: var(--lr-color-surface-raised);
16
13
  }
@@ -1,4 +1,4 @@
1
- var __decorate=function(decorators,target,key,desc){var c=arguments.length,r=c<3?target:desc===null?desc=Object.getOwnPropertyDescriptor(target,key):desc,d;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")r=Reflect.decorate(decorators,target,key,desc);else for(var i=decorators.length-1;i>=0;i--)(d=decorators[i])&&(r=(c<3?d(r):c>3?d(target,key,r):d(target,key))||r);return c>3&&r&&Object.defineProperty(target,key,r),r};import{html,nothing}from"lit";import{property,state}from"lit/decorators.js";import{LyraElement}from"../../../internal/lyra-element.js";import{sizes}from"../../../internal/sizes.styles.js";import{nextId}from"../../../internal/a11y.js";import{chevronIcon,playIcon,pauseIcon}from"../../../internal/icons.js";import{AnchoredValidityController,VALIDITY_ANCHOR}from"../../../internal/anchored-validity.js";import{attachInternalsSafely,getFormOwner,installCustomErrorProperty,isBarredFromValidation,setFormOwner}from"../../../internal/form-associated.js";import{installInvalidEventAlias}from"../../../internal/invalid-event-alias.js";import{syncValidityStates}from"../../../internal/custom-states.js";import{safeMediaSrc}from"../../../internal/safe-url.js";import{styles}from"./voice-picker.styles.js";import{trueDefaultBooleanConverter,trueDefaultSpellcheckConverter as spellcheckConverter}from"../../../internal/converters.js";import{CatalogPickerController}from"../../../internal/catalog-picker.js";import{activeElementIn}from"../../../internal/active-element.js";import{SlotPresenceController}from"../../../internal/slot-presence-controller.js";import{LYRA_DEFAULT_fieldRequired,LYRA_DEFAULT_noMatches,LYRA_DEFAULT_notInCatalog,LYRA_DEFAULT_voice,LYRA_DEFAULT_voicePickerNoVoices,LYRA_DEFAULT_voicePickerPreview,LYRA_DEFAULT_voicePickerRequired,LYRA_DEFAULT_voicePickerStopPreview}from"../../../internal/default-strings.generated.js";const MAX_VOICE_CATALOG_ENTRIES=1e4;function ownString(value,key){try{const descriptor=Object.getOwnPropertyDescriptor(value,key);return descriptor&&"value"in descriptor&&typeof descriptor.value=="string"?descriptor.value:void 0}catch{return}}function snapshotVoiceCatalog(value){if(!Array.isArray(value))return;const stringSnapshot=[],entrySnapshot=[];let objectCatalog=!1,length=0;try{length=Math.min(value.length,MAX_VOICE_CATALOG_ENTRIES)}catch{return Object.freeze(stringSnapshot)}for(let index=0;index<length;index+=1){let descriptor;try{descriptor=Object.getOwnPropertyDescriptor(value,String(index))}catch{continue}if(!descriptor||!("value"in descriptor))continue;const candidate=descriptor.value;if(typeof candidate=="string"){objectCatalog?entrySnapshot.push(Object.freeze({id:candidate,label:candidate})):stringSnapshot.push(candidate);continue}if(candidate===null||typeof candidate!="object")continue;const id=ownString(candidate,"id"),label=ownString(candidate,"label");if(id===void 0||label===void 0)continue;objectCatalog||(entrySnapshot.push(...stringSnapshot.map(entry=>Object.freeze({id:entry,label:entry}))),objectCatalog=!0);const language=ownString(candidate,"language"),description=ownString(candidate,"description"),previewUrl=ownString(candidate,"previewUrl");entrySnapshot.push(Object.freeze({id,label,...language===void 0?{}:{language},...description===void 0?{}:{description},...previewUrl===void 0?{}:{previewUrl}}))}return Object.freeze(objectCatalog?entrySnapshot:stringSnapshot)}class LyraVoicePicker extends LyraElement{static{this.defaultStrings={...super.defaultStrings,fieldRequired:LYRA_DEFAULT_fieldRequired,noMatches:LYRA_DEFAULT_noMatches,notInCatalog:LYRA_DEFAULT_notInCatalog,voice:LYRA_DEFAULT_voice,voicePickerNoVoices:LYRA_DEFAULT_voicePickerNoVoices,voicePickerPreview:LYRA_DEFAULT_voicePickerPreview,voicePickerRequired:LYRA_DEFAULT_voicePickerRequired,voicePickerStopPreview:LYRA_DEFAULT_voicePickerStopPreview}}static{this.formAssociated=!0}static{this.styles=[LyraElement.styles,sizes,styles]}static{this.properties={customError:{attribute:"custom-error",reflect:!0,noAccessor:!0},disabled:{type:Boolean,reflect:!0,noAccessor:!0},required:{type:Boolean,reflect:!0,noAccessor:!0},value:{attribute:!1,noAccessor:!0},defaultValue:{attribute:"value",reflect:!1,useDefault:!0,noAccessor:!0},name:{reflect:!0,noAccessor:!0}}}get catalog(){return this._catalog}set catalog(next){const old=this._catalog;next!==old&&(this.internalPreviewTargetId!==null&&this.stopInternalPreview(),this._catalog=snapshotVoiceCatalog(next),this.requestUpdate("catalog",old))}get open(){return this.catalogPicker.open}set open(next){this.catalogPicker.setOpen(next)}get activeIndex(){return this.catalogPicker.activeIndex}get query(){return this.catalogPicker.query}constructor(){super(),this.provider="",this.allowCustom=!1,this.preview=!0,this.label="",this.hint="",this.errorText="",this.placeholder="",this.spellcheck=!0,this.autocapitalize="",this.autoCorrect="",this.autocomplete="off",this.inputMode="",this.enterKeyHint="",this.size="m",this.touched=!1,this.slotPresence=new SlotPresenceController(this),this.previewingId=null,this.listId=nextId("voice-picker-list"),this.controlId=nextId("voice-picker-control"),this.pendingPreviewId=null,this.previewGeneration=0,this._fieldsetDisabled=!1,this._name="",this._disabled=!1,this._required=!1,this.transferControlFocus=!1,this.catalogPicker=new CatalogPickerController(this,{catalog:()=>this.catalog,allowCustom:()=>this.allowCustom,locale:()=>this.effectiveLocale,searchableFields:entry=>[entry.id,entry.label,entry.language??"",entry.description??""],emitChange:detail=>this.emit("lr-change",detail),emitFocusAlias:()=>{},beforeValueChange:value=>{const previewTarget=this.internalPreviewTargetId;previewTarget!==null&&previewTarget!==value&&this.stopInternalPreview()},beforeActiveIndexChange:next=>this.reconcilePreviewForActiveIndex(next),afterQueryChange:()=>this.reconcilePreviewVisibility(this.open,this.catalogPicker.filteredEntries),onValueChange:(value,oldValue)=>{this.internals.setFormValue(value),this.updateValidity(),this.requestUpdate("value",oldValue)},onDefaultValueChange:(_value,oldValue)=>this.requestUpdate("defaultValue",oldValue),onStateChange:(state2,oldValue)=>{state2==="open"?(this.catalogPicker.open||this.reconcilePreviewVisibility(!1,[]),this.requestUpdate("open",oldValue)):this.requestUpdate()},onControlBlur:()=>{this.effectiveDisabled||(this.touched=!0)}}),this.onAudioEnded=event=>{event.currentTarget===this.audioEl&&this.stopInternalPreview()},this.onAudioLoadFailure=eventOrAudio=>{const direct=eventOrAudio,isDomErrorEvent=direct.localName!=="audio",audioLike=direct.localName==="audio"?eventOrAudio:eventOrAudio.currentTarget,failedAudio=audioLike?.localName==="audio"&&typeof audioLike.pause=="function"&&typeof audioLike.removeEventListener=="function"?audioLike:void 0;if(!failedAudio||(failedAudio.removeEventListener("ended",this.onAudioEnded),failedAudio.removeEventListener("error",this.onAudioLoadFailure),failedAudio.pause(),failedAudio!==this.audioEl))return;const pendingVoiceId=this.pendingPreviewId;this.previewGeneration++,this.audioEl=void 0,this.pendingPreviewId=null,isDomErrorEvent&&this.previewingId===null&&pendingVoiceId!==null&&(this.previewingId=pendingVoiceId,this.emit("lr-preview-change",{voiceId:pendingVoiceId})),this.previewingId!==null&&(this.previewingId=null,this.emit("lr-preview-change",{voiceId:null}))},this.onPreviewButtonClick=()=>{const candidate=this.previewCandidateId;candidate&&(this.internalPreviewTargetId===candidate?this.stopInternalPreview():this.requestPreview(candidate))},this.onOptionPreviewClick=(e,entry)=>{e.stopPropagation(),this.internalPreviewTargetId===entry.id?this.stopInternalPreview():this.requestPreview(entry.id)},this.onTriggerClick=()=>{this.effectiveDisabled||(this.open?this.hide():this.show())},this.onControlBlur=event=>{this.catalogPicker.handleControlBlur(event)},this.onControlFocus=event=>{this.catalogPicker.handleControlFocus(event)},this.onTriggerKeyDown=e=>{this.catalogPicker.handleTriggerKeyDown(e)},this.onComboMouseDown=e=>{this.catalogPicker.handleComboMouseDown(e)},this.onInputFocus=event=>{this.catalogPicker.handleInputFocus(event)},this.onInput=e=>{this.catalogPicker.handleInput(e)},this.onInputKeyDown=e=>{this.catalogPicker.handleInputKeyDown(e)},this.onListboxMouseDown=e=>{this.catalogPicker.handleListboxMouseDown(e)},this.onListboxClick=e=>{this.catalogPicker.handleListboxClick(e)},this.internals=attachInternalsSafely(this),this.validityController=new AnchoredValidityController(this,this.internals,()=>this[VALIDITY_ANCHOR]()),installCustomErrorProperty(this,()=>this.validityController.customValidityMessage),installInvalidEventAlias(this,init=>this.emit("lr-invalid",null,init)),this.internals.setFormValue("")}get form(){return getFormOwner(this.internals)}set form(owner){setFormOwner(this,owner)}getForm(){return getFormOwner(this.internals)}get labels(){return this.internals.labels}get validity(){return this.internals.validity}get validationMessage(){return this.internals.validationMessage}get willValidate(){return this.internals.willValidate}[VALIDITY_ANCHOR](){return this.renderRoot?.querySelector('[part="trigger"], [part="combobox-input"]')??null}click(){this.catalogPicker.click()}focus(options){this.catalogPicker.focus(options)}blur(){this.catalogPicker.blur()}get input(){return this.catalogPicker.input}get selectionStart(){return this.input?.selectionStart??null}set selectionStart(value){this.input&&(this.input.selectionStart=value)}get selectionEnd(){return this.input?.selectionEnd??null}set selectionEnd(value){this.input&&(this.input.selectionEnd=value)}get selectionDirection(){return this.input?.selectionDirection??null}set selectionDirection(value){this.input&&(this.input.selectionDirection=value)}select(){this.catalogPicker.select()}setSelectionRange(start,end,direction){this.catalogPicker.setSelectionRange(start,end,direction)}setRangeText(replacement,start,end,selectMode){this.catalogPicker.setRangeText(replacement,start,end,selectMode)}connectedCallback(){super.connectedCallback(),this.updateValidity(),this.catalogPicker.connected(this.hasUpdated)}willUpdate(changed){if(super.willUpdate(changed),this.hasUpdated){const switchingMode=this.renderRoot.querySelector('[part="trigger"]')!==null!==this.closedMode,focused=activeElementIn(this.shadowRoot??this.ownerDocument);this.catalogPicker.suppressControlEvents=switchingMode,this.transferControlFocus=switchingMode&&focused?.nodeType===1&&focused.matches('[part="trigger"], [part="combobox-input"]')}if(this.hasUpdated&&(changed.has("catalog")||changed.has("allowCustom")||changed.has("value"))){const activeValue=this.renderRoot.querySelector('[part="option"][data-active]')?.dataset.value,rows=this.closedMode?this.effectiveEntries:this.filteredEntries;this.catalogPicker.reconcileRows(activeValue,!1),this.reconcilePreviewVisibility(this.open,rows)}changed.has("preview")&&!this.preview&&this.stopInternalPreview()}disconnectedCallback(){super.disconnectedCallback(),this.stopInternalPreview(),this.catalogPicker.disconnected()}adoptedCallback(){super.adoptedCallback(),this.stopInternalPreview(),this.catalogPicker.adopted()}get value(){return this.catalogPicker.value}set value(next){this.catalogPicker.value=next}get defaultValue(){return this.catalogPicker.defaultValue}set defaultValue(next){this.catalogPicker.defaultValue=next}get name(){return this._name}set name(next){const old=this._name;this._name=next??"",this._name?this.setAttribute("name",this._name):this.removeAttribute("name"),this.requestUpdate("name",old)}get disabled(){return this._disabled}set disabled(next){const old=this._disabled;this._disabled=!!next,this.toggleAttribute("disabled",this._disabled),this._disabled&&(this.hide(),this.stopInternalPreview()),this.updateValidity(),this.requestUpdate("disabled",old)}get required(){return this._required}set required(next){const old=this._required;this._required=!!next,this.toggleAttribute("required",this._required),this.updateValidity(),this.requestUpdate("required",old)}get effectiveDisabled(){return this.disabled||this._fieldsetDisabled}get barredFromValidation(){return isBarredFromValidation(this,this.internals)}updateValidity(){this.barredFromValidation?this.validityController.setValidity({}):this.required&&!this.value?this.validityController.setValidity({valueMissing:!0},this.localize("voicePickerRequired")):this.validityController.setValidity({}),this.publishValidityStates()}publishValidityStates(){syncValidityStates(this.internals,{required:this.required,hasInteracted:this.touched,barred:this.barredFromValidation})}formResetCallback(){this.touched=!1,this.catalogPicker.resetValue()}formStateRestoreCallback(state2,_mode){this.catalogPicker.restoreState(state2)}formDisabledCallback(disabled){this._fieldsetDisabled=disabled,disabled&&(this.hide(),this.stopInternalPreview()),this.updateValidity(),this.requestUpdate()}checkValidity(){return this.internals.checkValidity()}reportValidity(){return this.touched=!0,this.publishValidityStates(),this.internals.reportValidity()}setCustomValidity(message){this.validityController.setCustomValidity(message??""),this.publishValidityStates()}get closedMode(){return this.catalogPicker.closedMode}get effectiveEntries(){return this.catalogPicker.effectiveEntries}get filteredEntries(){return this.catalogPicker.filteredEntries}get malformedCatalogEntries(){const raw=this.catalog;if(!raw||raw.length===0)return[];const out=[];for(const item of raw){const record=typeof item=="string"?{id:item,label:item}:item;typeof record?.id=="string"&&record.id.trim()!==""||out.push({...record,id:"",synthetic:!1})}return out}labelFor(id){return this.catalogPicker.labelFor(id)}show(){this.catalogPicker.show()}hide(){this.catalogPicker.hide()}updated(changed){super.updated(changed);const reposition=changed.has("open")||this.open&&(changed.has("catalog")||changed.has("allowCustom"));this.catalogPicker.updated(reposition),(changed.has("required")||changed.has("touched")||changed.has("value"))&&this.toggleAttribute("data-invalid",this.touched&&!this.internals.validity.valid),this.publishValidityStates(),this.transferControlFocus&&(this.transferControlFocus=!1,this.renderRoot.querySelector('[part="trigger"], [part="combobox-input"]')?.focus()),this.catalogPicker.suppressControlEvents=!1}get internalPreviewTargetId(){return this.pendingPreviewId??this.previewingId}reconcilePreviewVisibility(open,rows){const target=this.internalPreviewTargetId;if(target===null)return;const standaloneCandidate=open&&this.activeIndex>=0?rows[this.activeIndex]?.id??this.value:this.value,hasVisibleRow=open&&rows.some(entry=>entry.id===target&&!!entry.previewUrl);target!==standaloneCandidate&&!hasVisibleRow&&this.stopInternalPreview()}reconcilePreviewForActiveIndex(next){const target=this.internalPreviewTargetId;if(target!==null){const rows=this.closedMode?this.effectiveEntries:this.filteredEntries,nextCandidate=this.open&&next>=0?rows[next]?.id??this.value:this.value;target!==nextCandidate&&this.stopInternalPreview()}}get previewCandidateId(){return this.open&&this.activeIndex>=0?(this.closedMode?this.effectiveEntries:this.filteredEntries)[this.activeIndex]?.id??this.value:this.value}requestPreview(voiceId){if(!voiceId)return;const currentTarget=this.internalPreviewTargetId;currentTarget!==null&&currentTarget!==voiceId&&this.stopInternalPreview();const previewUrl=this.effectiveEntries.find(e=>e.id===voiceId)?.previewUrl;!this.emit("lr-preview-request",{voiceId,previewUrl},{cancelable:!0}).defaultPrevented&&previewUrl&&this.playInternal(voiceId,previewUrl)}playInternal(voiceId,url){const safe=safeMediaSrc(url);if(!safe)return;this.stopInternalPreview();const audio=this.ownerDocument.createElement("audio");audio.src=safe,audio.addEventListener("ended",this.onAudioEnded),audio.addEventListener("error",this.onAudioLoadFailure);const generation=++this.previewGeneration;this.audioEl=audio,this.pendingPreviewId=voiceId;let playResult;try{playResult=audio.play()}catch{this.onAudioLoadFailure(audio);return}Promise.resolve(playResult).then(()=>{generation!==this.previewGeneration||audio!==this.audioEl||this.pendingPreviewId!==voiceId||(this.pendingPreviewId=null,this.previewingId=voiceId,this.emit("lr-preview-change",{voiceId}))},()=>this.onAudioLoadFailure(audio))}stopInternalPreview(){const hadTarget=this.internalPreviewTargetId!==null||this.audioEl!==void 0;this.audioEl&&(this.audioEl.removeEventListener("ended",this.onAudioEnded),this.audioEl.removeEventListener("error",this.onAudioLoadFailure),this.audioEl.pause(),this.audioEl=void 0),hadTarget&&this.previewGeneration++,this.pendingPreviewId=null,this.previewingId!==null&&(this.previewingId=null,this.emit("lr-preview-change",{voiceId:null}))}get previewButtonLabel(){const candidate=this.previewCandidateId,playing=this.previewingId!==null&&this.previewingId===candidate,name=this.labelFor(candidate)||candidate;return playing?this.localize("voicePickerStopPreview"):this.localize("voicePickerPreview",void 0,{name})}renderRows(rows,activeId){return rows.map((entry,i)=>{const id=`${this.listId}-opt-${i}`,selected=entry.id!==""&&entry.id===this.value,meta=[entry.language,entry.description].filter(Boolean).join(" \xB7 ");return html`<div
1
+ var __decorate=function(decorators,target,key,desc){var c=arguments.length,r=c<3?target:desc===null?desc=Object.getOwnPropertyDescriptor(target,key):desc,d;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")r=Reflect.decorate(decorators,target,key,desc);else for(var i=decorators.length-1;i>=0;i--)(d=decorators[i])&&(r=(c<3?d(r):c>3?d(target,key,r):d(target,key))||r);return c>3&&r&&Object.defineProperty(target,key,r),r};import{html,nothing}from"lit";import{property,state}from"lit/decorators.js";import{LyraElement}from"../../../internal/lyra-element.js";import{sizes}from"../../../internal/sizes.styles.js";import{hostAriaLabel,nextId}from"../../../internal/a11y.js";import{chevronIcon,playIcon,pauseIcon}from"../../../internal/icons.js";import{AnchoredValidityController,VALIDITY_ANCHOR}from"../../../internal/anchored-validity.js";import{attachInternalsSafely,getFormOwner,installCustomErrorProperty,isBarredFromValidation,setFormOwner}from"../../../internal/form-associated.js";import{installInvalidEventAlias}from"../../../internal/invalid-event-alias.js";import{syncValidityStates}from"../../../internal/custom-states.js";import{safeMediaSrc}from"../../../internal/safe-url.js";import{styles}from"./voice-picker.styles.js";import{trueDefaultBooleanConverter,trueDefaultSpellcheckConverter as spellcheckConverter}from"../../../internal/converters.js";import{CatalogPickerController}from"../../../internal/catalog-picker.js";import{activeElementIn}from"../../../internal/active-element.js";import{SlotPresenceController}from"../../../internal/slot-presence-controller.js";import{LYRA_DEFAULT_fieldRequired,LYRA_DEFAULT_noMatches,LYRA_DEFAULT_notInCatalog,LYRA_DEFAULT_voice,LYRA_DEFAULT_voicePickerNoVoices,LYRA_DEFAULT_voicePickerPreview,LYRA_DEFAULT_voicePickerRequired,LYRA_DEFAULT_voicePickerStopPreview}from"../../../internal/default-strings.generated.js";const MAX_VOICE_CATALOG_ENTRIES=1e4;function ownString(value,key){try{const descriptor=Object.getOwnPropertyDescriptor(value,key);return descriptor&&"value"in descriptor&&typeof descriptor.value=="string"?descriptor.value:void 0}catch{return}}function snapshotVoiceCatalog(value){if(!Array.isArray(value))return;const stringSnapshot=[],entrySnapshot=[];let objectCatalog=!1,length=0;try{length=Math.min(value.length,MAX_VOICE_CATALOG_ENTRIES)}catch{return Object.freeze(stringSnapshot)}for(let index=0;index<length;index+=1){let descriptor;try{descriptor=Object.getOwnPropertyDescriptor(value,String(index))}catch{continue}if(!descriptor||!("value"in descriptor))continue;const candidate=descriptor.value;if(typeof candidate=="string"){objectCatalog?entrySnapshot.push(Object.freeze({id:candidate,label:candidate})):stringSnapshot.push(candidate);continue}if(candidate===null||typeof candidate!="object")continue;const id=ownString(candidate,"id"),label=ownString(candidate,"label");if(id===void 0||label===void 0)continue;objectCatalog||(entrySnapshot.push(...stringSnapshot.map(entry=>Object.freeze({id:entry,label:entry}))),objectCatalog=!0);const language=ownString(candidate,"language"),description=ownString(candidate,"description"),previewUrl=ownString(candidate,"previewUrl");entrySnapshot.push(Object.freeze({id,label,...language===void 0?{}:{language},...description===void 0?{}:{description},...previewUrl===void 0?{}:{previewUrl}}))}return Object.freeze(objectCatalog?entrySnapshot:stringSnapshot)}class LyraVoicePicker extends LyraElement{static{this.defaultStrings={...super.defaultStrings,fieldRequired:LYRA_DEFAULT_fieldRequired,noMatches:LYRA_DEFAULT_noMatches,notInCatalog:LYRA_DEFAULT_notInCatalog,voice:LYRA_DEFAULT_voice,voicePickerNoVoices:LYRA_DEFAULT_voicePickerNoVoices,voicePickerPreview:LYRA_DEFAULT_voicePickerPreview,voicePickerRequired:LYRA_DEFAULT_voicePickerRequired,voicePickerStopPreview:LYRA_DEFAULT_voicePickerStopPreview}}static{this.formAssociated=!0}static{this.styles=[LyraElement.styles,sizes,styles]}static{this.properties={customError:{attribute:"custom-error",reflect:!0,noAccessor:!0},disabled:{type:Boolean,reflect:!0,noAccessor:!0},required:{type:Boolean,reflect:!0,noAccessor:!0},value:{attribute:!1,noAccessor:!0},defaultValue:{attribute:"value",reflect:!1,useDefault:!0,noAccessor:!0},name:{reflect:!0,noAccessor:!0}}}get catalog(){return this._catalog}set catalog(next){const old=this._catalog;next!==old&&(this.internalPreviewTargetId!==null&&this.stopInternalPreview(),this._catalog=snapshotVoiceCatalog(next),this.requestUpdate("catalog",old))}get open(){return this.catalogPicker.open}set open(next){this.catalogPicker.setOpen(next)}get activeIndex(){return this.catalogPicker.activeIndex}get query(){return this.catalogPicker.query}constructor(){super(),this.provider="",this.allowCustom=!1,this.preview=!0,this.label="",this.hint="",this.errorText="",this.placeholder="",this.spellcheck=!0,this.autocapitalize="",this.autoCorrect="",this.autocomplete="off",this.inputMode="",this.enterKeyHint="",this.size="m",this.touched=!1,this.slotPresence=new SlotPresenceController(this),this.previewingId=null,this.listId=nextId("voice-picker-list"),this.controlId=nextId("voice-picker-control"),this.pendingPreviewId=null,this.previewGeneration=0,this._fieldsetDisabled=!1,this._name="",this._disabled=!1,this._required=!1,this.transferControlFocus=!1,this.catalogPicker=new CatalogPickerController(this,{catalog:()=>this.catalog,allowCustom:()=>this.allowCustom,locale:()=>this.effectiveLocale,searchableFields:entry=>[entry.id,entry.label,entry.language??"",entry.description??""],emitChange:detail=>this.emit("lr-change",detail),beforeValueChange:value=>{const previewTarget=this.internalPreviewTargetId;previewTarget!==null&&previewTarget!==value&&this.stopInternalPreview()},beforeActiveIndexChange:next=>this.reconcilePreviewForActiveIndex(next),afterQueryChange:()=>this.reconcilePreviewVisibility(this.open,this.catalogPicker.filteredEntries),onValueChange:(value,oldValue)=>{this.internals.setFormValue(value),this.updateValidity(),this.requestUpdate("value",oldValue)},onDefaultValueChange:(_value,oldValue)=>this.requestUpdate("defaultValue",oldValue),onStateChange:(state2,oldValue)=>{state2==="open"?(this.catalogPicker.open||this.reconcilePreviewVisibility(!1,[]),this.requestUpdate("open",oldValue)):this.requestUpdate()},onControlBlur:()=>{this.effectiveDisabled||(this.touched=!0)}}),this.onAudioEnded=event=>{event.currentTarget===this.audioEl&&this.stopInternalPreview()},this.onAudioLoadFailure=eventOrAudio=>{const direct=eventOrAudio,isDomErrorEvent=direct.localName!=="audio",audioLike=direct.localName==="audio"?eventOrAudio:eventOrAudio.currentTarget,failedAudio=audioLike?.localName==="audio"&&typeof audioLike.pause=="function"&&typeof audioLike.removeEventListener=="function"?audioLike:void 0;if(!failedAudio||(failedAudio.removeEventListener("ended",this.onAudioEnded),failedAudio.removeEventListener("error",this.onAudioLoadFailure),failedAudio.pause(),failedAudio!==this.audioEl))return;const pendingVoiceId=this.pendingPreviewId;this.previewGeneration++,this.audioEl=void 0,this.pendingPreviewId=null,isDomErrorEvent&&this.previewingId===null&&pendingVoiceId!==null&&(this.previewingId=pendingVoiceId,this.emit("lr-preview-change",{voiceId:pendingVoiceId})),this.previewingId!==null&&(this.previewingId=null,this.emit("lr-preview-change",{voiceId:null}))},this.onPreviewButtonClick=()=>{const candidate=this.previewCandidateId;candidate&&(this.internalPreviewTargetId===candidate?this.stopInternalPreview():this.requestPreview(candidate))},this.onOptionPreviewClick=(e,entry)=>{e.stopPropagation(),this.internalPreviewTargetId===entry.id?this.stopInternalPreview():this.requestPreview(entry.id)},this.onTriggerClick=()=>{this.effectiveDisabled||(this.open?this.hide():this.show())},this.onControlBlur=event=>{this.catalogPicker.handleControlBlur(event)},this.onControlFocus=event=>{this.catalogPicker.handleControlFocus(event)},this.onTriggerKeyDown=e=>{this.catalogPicker.handleTriggerKeyDown(e)},this.onComboMouseDown=e=>{this.catalogPicker.handleComboMouseDown(e)},this.onInputFocus=event=>{this.catalogPicker.handleInputFocus(event)},this.onInput=e=>{this.catalogPicker.handleInput(e)},this.onInputKeyDown=e=>{this.catalogPicker.handleInputKeyDown(e)},this.onListboxMouseDown=e=>{this.catalogPicker.handleListboxMouseDown(e)},this.onListboxClick=e=>{this.catalogPicker.handleListboxClick(e)},this.internals=attachInternalsSafely(this),this.validityController=new AnchoredValidityController(this,this.internals,()=>this[VALIDITY_ANCHOR]()),installCustomErrorProperty(this,()=>this.validityController.customValidityMessage),installInvalidEventAlias(this,init=>this.emit("lr-invalid",null,init)),this.internals.setFormValue("")}get form(){return getFormOwner(this.internals)}set form(owner){setFormOwner(this,owner)}getForm(){return getFormOwner(this.internals)}get labels(){return this.internals.labels}get validity(){return this.internals.validity}get validationMessage(){return this.internals.validationMessage}get willValidate(){return this.internals.willValidate}[VALIDITY_ANCHOR](){return this.renderRoot?.querySelector('[part="trigger"], [part="combobox-input"]')??null}click(){this.catalogPicker.click()}focus(options){this.catalogPicker.focus(options)}blur(){this.catalogPicker.blur()}get input(){return this.catalogPicker.input}get selectionStart(){return this.input?.selectionStart??null}set selectionStart(value){this.input&&(this.input.selectionStart=value)}get selectionEnd(){return this.input?.selectionEnd??null}set selectionEnd(value){this.input&&(this.input.selectionEnd=value)}get selectionDirection(){return this.input?.selectionDirection??null}set selectionDirection(value){this.input&&(this.input.selectionDirection=value)}select(){this.catalogPicker.select()}setSelectionRange(start,end,direction){this.catalogPicker.setSelectionRange(start,end,direction)}setRangeText(replacement,start,end,selectMode){this.catalogPicker.setRangeText(replacement,start,end,selectMode)}connectedCallback(){super.connectedCallback(),this.updateValidity(),this.catalogPicker.connected(this.hasUpdated)}willUpdate(changed){if(super.willUpdate(changed),this.hasUpdated){const switchingMode=this.renderRoot.querySelector('[part="trigger"]')!==null!==this.closedMode,focused=activeElementIn(this.shadowRoot??this.ownerDocument);this.catalogPicker.suppressControlEvents=switchingMode,this.transferControlFocus=switchingMode&&focused?.nodeType===1&&focused.matches('[part="trigger"], [part="combobox-input"]')}if(this.hasUpdated&&(changed.has("catalog")||changed.has("allowCustom")||changed.has("value"))){const activeValue=this.renderRoot.querySelector('[part="option"][data-active]')?.dataset.value,rows=this.closedMode?this.effectiveEntries:this.filteredEntries;this.catalogPicker.reconcileRows(activeValue,!1),this.reconcilePreviewVisibility(this.open,rows)}changed.has("preview")&&!this.preview&&this.stopInternalPreview()}disconnectedCallback(){super.disconnectedCallback(),this.stopInternalPreview(),this.catalogPicker.disconnected()}adoptedCallback(){super.adoptedCallback(),this.stopInternalPreview(),this.catalogPicker.adopted()}get value(){return this.catalogPicker.value}set value(next){this.catalogPicker.value=next}get defaultValue(){return this.catalogPicker.defaultValue}set defaultValue(next){this.catalogPicker.defaultValue=next}get name(){return this._name}set name(next){const old=this._name;this._name=next??"",this._name?this.setAttribute("name",this._name):this.removeAttribute("name"),this.requestUpdate("name",old)}get disabled(){return this._disabled}set disabled(next){const old=this._disabled;this._disabled=!!next,this.toggleAttribute("disabled",this._disabled),this._disabled&&(this.hide(),this.stopInternalPreview()),this.updateValidity(),this.requestUpdate("disabled",old)}get required(){return this._required}set required(next){const old=this._required;this._required=!!next,this.toggleAttribute("required",this._required),this.updateValidity(),this.requestUpdate("required",old)}get effectiveDisabled(){return this.disabled||this._fieldsetDisabled}get barredFromValidation(){return isBarredFromValidation(this,this.internals)}updateValidity(){this.barredFromValidation?this.validityController.setValidity({}):this.required&&!this.value?this.validityController.setValidity({valueMissing:!0},this.localize("voicePickerRequired")):this.validityController.setValidity({}),this.publishValidityStates()}publishValidityStates(){syncValidityStates(this.internals,{required:this.required,hasInteracted:this.touched,barred:this.barredFromValidation})}formResetCallback(){this.touched=!1,this.catalogPicker.resetValue()}formStateRestoreCallback(state2,_mode){this.catalogPicker.restoreState(state2)}formDisabledCallback(disabled){this._fieldsetDisabled=disabled,disabled&&(this.hide(),this.stopInternalPreview()),this.updateValidity(),this.requestUpdate()}checkValidity(){return this.internals.checkValidity()}reportValidity(){return this.touched=!0,this.publishValidityStates(),this.internals.reportValidity()}setCustomValidity(message){this.validityController.setCustomValidity(message??""),this.publishValidityStates()}get closedMode(){return this.catalogPicker.closedMode}get effectiveEntries(){return this.catalogPicker.effectiveEntries}get filteredEntries(){return this.catalogPicker.filteredEntries}get malformedCatalogEntries(){const raw=this.catalog;if(!raw||raw.length===0)return[];const out=[];for(const item of raw){const record=typeof item=="string"?{id:item,label:item}:item;typeof record?.id=="string"&&record.id.trim()!==""||out.push({...record,id:"",synthetic:!1})}return out}labelFor(id){return this.catalogPicker.labelFor(id)}show(){this.catalogPicker.show()}hide(){this.catalogPicker.hide()}updated(changed){super.updated(changed);const reposition=changed.has("open")||this.open&&(changed.has("catalog")||changed.has("allowCustom"));this.catalogPicker.updated(reposition),(changed.has("required")||changed.has("touched")||changed.has("value"))&&this.toggleAttribute("data-invalid",this.touched&&!this.internals.validity.valid),this.publishValidityStates(),this.transferControlFocus&&(this.transferControlFocus=!1,this.renderRoot.querySelector('[part="trigger"], [part="combobox-input"]')?.focus()),this.catalogPicker.suppressControlEvents=!1}get internalPreviewTargetId(){return this.pendingPreviewId??this.previewingId}reconcilePreviewVisibility(open,rows){const target=this.internalPreviewTargetId;if(target===null)return;const standaloneCandidate=open&&this.activeIndex>=0?rows[this.activeIndex]?.id??this.value:this.value,hasVisibleRow=open&&rows.some(entry=>entry.id===target&&!!entry.previewUrl);target!==standaloneCandidate&&!hasVisibleRow&&this.stopInternalPreview()}reconcilePreviewForActiveIndex(next){const target=this.internalPreviewTargetId;if(target!==null){const rows=this.closedMode?this.effectiveEntries:this.filteredEntries,nextCandidate=this.open&&next>=0?rows[next]?.id??this.value:this.value;target!==nextCandidate&&this.stopInternalPreview()}}get previewCandidateId(){return this.open&&this.activeIndex>=0?(this.closedMode?this.effectiveEntries:this.filteredEntries)[this.activeIndex]?.id??this.value:this.value}requestPreview(voiceId){if(!voiceId)return;const currentTarget=this.internalPreviewTargetId;currentTarget!==null&&currentTarget!==voiceId&&this.stopInternalPreview();const previewUrl=this.effectiveEntries.find(e=>e.id===voiceId)?.previewUrl;!this.emit("lr-preview-request",{voiceId,previewUrl},{cancelable:!0}).defaultPrevented&&previewUrl&&this.playInternal(voiceId,previewUrl)}playInternal(voiceId,url){const safe=safeMediaSrc(url);if(!safe)return;this.stopInternalPreview();const audio=this.ownerDocument.createElement("audio");audio.src=safe,audio.addEventListener("ended",this.onAudioEnded),audio.addEventListener("error",this.onAudioLoadFailure);const generation=++this.previewGeneration;this.audioEl=audio,this.pendingPreviewId=voiceId;let playResult;try{playResult=audio.play()}catch{this.onAudioLoadFailure(audio);return}Promise.resolve(playResult).then(()=>{generation!==this.previewGeneration||audio!==this.audioEl||this.pendingPreviewId!==voiceId||(this.pendingPreviewId=null,this.previewingId=voiceId,this.emit("lr-preview-change",{voiceId}))},()=>this.onAudioLoadFailure(audio))}stopInternalPreview(){const hadTarget=this.internalPreviewTargetId!==null||this.audioEl!==void 0;this.audioEl&&(this.audioEl.removeEventListener("ended",this.onAudioEnded),this.audioEl.removeEventListener("error",this.onAudioLoadFailure),this.audioEl.pause(),this.audioEl=void 0),hadTarget&&this.previewGeneration++,this.pendingPreviewId=null,this.previewingId!==null&&(this.previewingId=null,this.emit("lr-preview-change",{voiceId:null}))}get previewButtonLabel(){const candidate=this.previewCandidateId,playing=this.previewingId!==null&&this.previewingId===candidate,name=this.labelFor(candidate)||candidate;return playing?this.localize("voicePickerStopPreview"):this.localize("voicePickerPreview",void 0,{name})}renderRows(rows,activeId){return rows.map((entry,i)=>{const id=`${this.listId}-opt-${i}`,selected=entry.id!==""&&entry.id===this.value,meta=[entry.language,entry.description].filter(Boolean).join(" \xB7 ");return html`<div
2
2
  part="option"
3
3
  id=${id}
4
4
  role="option"
@@ -63,7 +63,7 @@ var __decorate=function(decorators,target,key,desc){var c=arguments.length,r=c<3
63
63
  aria-expanded=${this.open?"true":"false"}
64
64
  aria-controls=${this.listId}
65
65
  aria-activedescendant=${activeId}
66
- aria-label=${this.getAttribute("aria-label")||(hasLabel?nothing:this.placeholder||this.localize("voice"))}
66
+ aria-label=${hostAriaLabel(this)??(hasLabel?nothing:this.placeholder||this.localize("voice"))}
67
67
  aria-describedby=${describedBy||nothing}
68
68
  aria-required=${this.required?"true":"false"}
69
69
  aria-invalid=${this.touched&&!this.internals.validity.valid?"true":"false"}
@@ -92,7 +92,7 @@ var __decorate=function(decorators,target,key,desc){var c=arguments.length,r=c<3
92
92
  id=${this.controlId}
93
93
  part="combobox-input"
94
94
  role="combobox"
95
- aria-label=${this.getAttribute("aria-label")||(hasLabel?nothing:this.placeholder||this.localize("voice"))}
95
+ aria-label=${hostAriaLabel(this)??(hasLabel?nothing:this.placeholder||this.localize("voice"))}
96
96
  aria-expanded=${this.open?"true":"false"}
97
97
  aria-controls=${this.listId}
98
98
  aria-activedescendant=${activeId}
@@ -22,9 +22,6 @@ import{css}from"lit";import{formControlRequiredMarker}from"../../../internal/for
22
22
  [part='form-control-label'][hidden] {
23
23
  display: none;
24
24
  }
25
- /* This control accepts required and renders a visible label like every other field in the
26
- library, so it marks it the same way -- the [hidden] rule above is what keeps the marker from
27
- orphaning a stray glyph when no label is set. */
28
25
  ${formControlRequiredMarker}
29
26
 
30
27
  .control-row {
@@ -60,8 +57,6 @@ import{css}from"lit";import{formControlRequiredMarker}from"../../../internal/for
60
57
  [part='trigger']:hover:not(:disabled) {
61
58
  border-color: var(--lr-color-brand);
62
59
  }
63
- /* Hover recolors the border only; the press additionally fills the trigger, mixing its resting
64
- surface toward the text color so the pressed state escalates hover instead of restating it. */
65
60
  [part='trigger']:active:not(:disabled) {
66
61
  border-color: var(--lr-color-brand);
67
62
  background: color-mix(in oklab, var(--lr-color-surface), var(--lr-color-mix-partner) var(--lr-color-mix-active));
@@ -143,8 +138,6 @@ import{css}from"lit";import{formControlRequiredMarker}from"../../../internal/for
143
138
  justify-content: center;
144
139
  inline-size: max(var(--lr-icon-button-size), var(--lr-form-control-height));
145
140
  block-size: max(var(--lr-icon-button-size), var(--lr-form-control-height));
146
- /* Compact picker chrome may be smaller than the WCAG interaction floor; the independent
147
- preview action never is. Large tiers grow the action with the field. */
148
141
  min-inline-size: var(--lr-icon-button-size);
149
142
  min-block-size: var(--lr-icon-button-size);
150
143
  border: var(--lr-border-width-thin) solid var(--lr-color-border);
@@ -176,16 +169,8 @@ import{css}from"lit";import{formControlRequiredMarker}from"../../../internal/for
176
169
  position: fixed;
177
170
  z-index: var(--lr-layer-dropdown);
178
171
  box-sizing: border-box;
179
- /* Clamped against internal/positioner.js's place()-published available-space custom
180
- properties (see menu.styles.ts's/combobox.styles.ts's identical [part='listbox']
181
- treatment) so this popup can't overflow off-screen on a short/keyboard-shrunk viewport. */
182
172
  max-block-size: min(var(--lr-size-18rem), var(--lr-positioner-available-block-size, var(--lr-size-18rem)));
183
173
  overflow-y: auto;
184
- /* Pinned explicitly alongside overflow-y -- per the CSS overflow spec, once one axis is
185
- forced non-'visible', the other axis's used value also computes to 'auto' (never stays
186
- 'visible'), risking a phantom empty horizontal scrollbar from sub-pixel rounding (the same
187
- bug lr-tab-group' tablist was fixed for). inline-size is max-content below, so this axis never
188
- actually needs to scroll. */
189
174
  overflow-x: hidden;
190
175
  inline-size: max-content;
191
176
  min-inline-size: min(var(--lr-size-12rem), var(--lr-positioner-available-inline-size, var(--lr-size-12rem)));
@@ -194,7 +179,6 @@ import{css}from"lit";import{formControlRequiredMarker}from"../../../internal/for
194
179
  background: var(--lr-color-surface);
195
180
  border: var(--lr-border-width-thin) solid var(--lr-color-border);
196
181
  border-radius: var(--lr-voice-picker-radius, var(--_lr-voice-picker-radius-default));
197
- /* Anchored overlay: a positioner-placed listbox floating over page content, not a modal layer. */
198
182
  box-shadow: var(--lr-shadow-m);
199
183
  visibility: hidden;
200
184
  opacity: 0;
@@ -230,12 +214,19 @@ import{css}from"lit";import{formControlRequiredMarker}from"../../../internal/for
230
214
  text-align: start;
231
215
  cursor: pointer;
232
216
  }
217
+ [part='option'][aria-selected='true'] {
218
+ border-color: var(--lr-voice-picker-option-selected-border, var(--lr-color-brand));
219
+ color: var(--lr-voice-picker-option-selected-color, var(--lr-color-brand));
220
+ background: var(--lr-voice-picker-option-selected-bg, transparent);
221
+ font-weight: var(
222
+ --lr-voice-picker-option-selected-font-weight,
223
+ var(--lr-font-weight-semibold)
224
+ );
225
+ }
233
226
  [part='option']:hover,
234
227
  [part='option'][data-active] {
235
228
  background: var(--lr-voice-picker-option-active-bg, var(--lr-color-brand-quiet));
236
229
  }
237
- /* Mixes the SAME --lr-voice-picker-option-active-bg the hover/active-descendant rule above uses,
238
- so a consumer retinting the highlight gets a matching pressed step for free. */
239
230
  [part='option']:active {
240
231
  background: color-mix(
241
232
  in oklab,
@@ -243,15 +234,6 @@ import{css}from"lit";import{formControlRequiredMarker}from"../../../internal/for
243
234
  var(--lr-color-mix-partner) var(--lr-color-mix-active)
244
235
  );
245
236
  }
246
- [part='option'][aria-selected='true'] {
247
- border-color: var(--lr-voice-picker-option-selected-border, var(--lr-color-brand));
248
- color: var(--lr-voice-picker-option-selected-color, var(--lr-color-brand));
249
- background: var(--lr-voice-picker-option-selected-bg, transparent);
250
- font-weight: var(
251
- --lr-voice-picker-option-selected-font-weight,
252
- var(--lr-font-weight-semibold)
253
- );
254
- }
255
237
  [part='option-label'] {
256
238
  flex: 1 1 auto;
257
239
  min-inline-size: 0;
@@ -301,8 +283,6 @@ import{css}from"lit";import{formControlRequiredMarker}from"../../../internal/for
301
283
  background: var(--lr-voice-picker-preview-hover-bg, var(--lr-color-brand-quiet));
302
284
  color: var(--lr-voice-picker-preview-hover-color, var(--lr-color-brand));
303
285
  }
304
- /* Mixes the SAME --lr-voice-picker-preview-hover-bg the rule above uses, so a consumer retinting
305
- the hover fill gets a matching pressed step without a second custom property to keep in sync. */
306
286
  [part='option-preview']:active {
307
287
  background: color-mix(
308
288
  in oklab,
@@ -25,6 +25,8 @@ export interface LyraWidgetDocument {
25
25
  /**
26
26
  * Creates an immediate, bounded, frozen version-two document snapshot. Widget-owned structure and
27
27
  * prop records are copied; opaque prop values and action payloads intentionally retain identity.
28
+ * String children and string prop values are truncated to `WIDGET_MAX_STRING_LENGTH`, the same
29
+ * silent admission ceiling the depth/node/prop budgets apply here.
28
30
  * Malformed, cyclic, duplicate-id, or hostile input throws `TypeError` before a document escapes.
29
31
  */
30
32
  export declare function createWidgetDocument(root: LyraWidgetNode): LyraWidgetDocument;
@@ -1 +1 @@
1
- import{isWidgetTypeRegistry}from"./registry.js";import{readWidgetPointer,WIDGET_MAX_DEPTH,WIDGET_MAX_NODES,WIDGET_MAX_PROPS_PER_NODE,WIDGET_MAX_WARNINGS}from"../../../internal/widget-resolver.js";const DOCUMENT_INVALID=Symbol("invalid-widget-document"),DOCUMENT_MISSING=Symbol("missing-widget-document-field");function readDocumentField(input,key){try{return Object.hasOwn(input,key)?Reflect.get(input,key):DOCUMENT_MISSING}catch{return DOCUMENT_INVALID}}function snapshotDocumentProps(input){const output={};let admitted=0;try{for(const key in input){if(!Object.hasOwn(input,key))continue;if(admitted>=WIDGET_MAX_PROPS_PER_NODE)break;const value=Reflect.get(input,key);admitted+=1,output[key]=value}}catch{return DOCUMENT_INVALID}return Object.freeze(output)}function snapshotDocumentNode(input,depth,context){if(depth>WIDGET_MAX_DEPTH||context.remaining<=0)return null;if(context.remaining-=1,input===null||typeof input!="object"||Array.isArray(input)||context.ancestors.has(input))return DOCUMENT_INVALID;const type=readDocumentField(input,"type");if(typeof type!="string")return DOCUMENT_INVALID;const id=readDocumentField(input,"id"),slot=readDocumentField(input,"slot"),actionId=readDocumentField(input,"actionId"),propsInput=readDocumentField(input,"props"),childrenInput=readDocumentField(input,"children");if([id,slot,actionId,propsInput,childrenInput].includes(DOCUMENT_INVALID)||id!==DOCUMENT_MISSING&&(typeof id!="string"||id.length===0||id!==id.trim()))return DOCUMENT_INVALID;if(typeof id=="string"){if(context.ids.has(id))return DOCUMENT_INVALID;context.ids.add(id)}if(slot!==DOCUMENT_MISSING&&(typeof slot!="string"||slot.length===0||slot!==slot.trim())||actionId!==DOCUMENT_MISSING&&(typeof actionId!="string"||actionId.length===0||actionId!==actionId.trim())||propsInput!==DOCUMENT_MISSING&&(propsInput===null||typeof propsInput!="object"||Array.isArray(propsInput))||childrenInput!==DOCUMENT_MISSING&&!Array.isArray(childrenInput))return DOCUMENT_INVALID;const props=propsInput===DOCUMENT_MISSING?void 0:snapshotDocumentProps(propsInput);if(props===DOCUMENT_INVALID)return DOCUMENT_INVALID;let payload=DOCUMENT_MISSING;if(actionId!==DOCUMENT_MISSING&&(payload=readDocumentField(input,"payload"),payload===DOCUMENT_INVALID))return DOCUMENT_INVALID;const children=[];if(childrenInput!==DOCUMENT_MISSING&&depth<WIDGET_MAX_DEPTH){const length=readDocumentField(childrenInput,"length");if(typeof length!="number"||!Number.isSafeInteger(length)||length<0)return DOCUMENT_INVALID;context.ancestors.add(input);try{for(let index=0;index<length&&context.remaining>0;index++){const child=readDocumentField(childrenInput,index);if(child===DOCUMENT_INVALID||child===DOCUMENT_MISSING)return DOCUMENT_INVALID;if(typeof child=="string"){context.remaining-=1,children.push(child);continue}const snapshot=snapshotDocumentNode(child,depth+1,context);if(snapshot===DOCUMENT_INVALID)return DOCUMENT_INVALID;snapshot&&children.push(snapshot)}}finally{context.ancestors.delete(input)}}return Object.freeze({type,...typeof id=="string"?{id}:{},...typeof slot=="string"?{slot}:{},...typeof actionId=="string"?{actionId,payload:payload===DOCUMENT_MISSING?void 0:payload}:{},...props===void 0?{}:{props},...children.length===0?{}:{children:Object.freeze(children)}})}function createWidgetDocument(root){const snapshot=snapshotDocumentNode(root,0,{ancestors:new Set,ids:new Set,remaining:WIDGET_MAX_NODES});if(snapshot===DOCUMENT_INVALID||snapshot===null)throw new TypeError("A widget document root must be a valid bounded widget node.");return Object.freeze({version:"2",root:snapshot})}const WARNING_SUPPRESSION_KEY="__warning-cap__",INVALID=Symbol("invalid-widget-input"),ROW_COL_PROP_ENUMS={gap:["s","m","l"],align:["start","center","end","stretch"],justify:["start","center","end","between"]};function warnOnce(ctx,key,message){if(!ctx.warned.has(key)){if(ctx.warned.size>=WIDGET_MAX_WARNINGS){if(ctx.warned.has(WARNING_SUPPRESSION_KEY))return;ctx.warned.add(WARNING_SUPPRESSION_KEY),(ctx.warn??console.warn)(`[lr-widget-renderer] suppressed further diagnostics after ${WIDGET_MAX_WARNINGS} unique warnings`);return}ctx.warned.add(key),(ctx.warn??console.warn)(`[lr-widget-renderer] ${message}`)}}function isBinding(value){return!!(value&&typeof value=="object"&&!Array.isArray(value)&&typeof value.$bind=="string")}function resolveValue(value,ctx){if(!isBinding(value))return{value};const resolved=readWidgetPointer(ctx.bindingState,value.$bind);return{value:resolved===void 0?value.fallback:resolved,path:value.$bind}}function consumeNodeBudget(snapshot){return snapshot.remaining<=0?(warnOnce(snapshot.resolve,"__node-cap__",`stopped resolving after the ${WIDGET_MAX_NODES}-node cap was reached`),!1):(snapshot.remaining--,!0)}function snapshotProps(input,type,ctx){const out={};let visited=0;for(const key in input){if(visited>=WIDGET_MAX_PROPS_PER_NODE){warnOnce(ctx,`__prop-cap__:${type}`,`stopped reading props on type "${type}" after the ${WIDGET_MAX_PROPS_PER_NODE}-prop cap was reached`);break}visited++,Object.hasOwn(input,key)&&(out[key]=input[key])}return out}function definitionFor(type,registry){return registry.get(type)}function snapshotNode(input,depth,snapshot){if(depth>WIDGET_MAX_DEPTH)return warnOnce(snapshot.resolve,"__depth-cap__",`stopped resolving after the ${WIDGET_MAX_DEPTH}-level depth cap was reached`),null;if(!consumeNodeBudget(snapshot))return null;if(input===null||typeof input!="object"||Array.isArray(input)||snapshot.ancestors.has(input))return INVALID;const candidate=input,type=candidate.type;if(typeof type!="string")return INVALID;if(!(type==="row"||type==="col"||type==="text")&&!definitionFor(type,snapshot.resolve.registry))return{type};const id=candidate.id;if(id!==void 0&&(typeof id!="string"||id.length===0||id!==id.trim()))return INVALID;const slot=candidate.slot;if(slot!==void 0&&(typeof slot!="string"||slot.length===0||slot!==slot.trim()))return INVALID;const actionId=candidate.actionId;if(actionId!==void 0&&(typeof actionId!="string"||actionId.length===0||actionId!==actionId.trim()))return INVALID;const propsInput=candidate.props;if(propsInput!==void 0&&(propsInput===null||typeof propsInput!="object"||Array.isArray(propsInput)))return INVALID;const childrenInput=candidate.children;if(childrenInput!==void 0&&!Array.isArray(childrenInput))return INVALID;const node={type,...id!==void 0?{id}:{},...slot!==void 0?{slot}:{},...actionId!==void 0?{actionId,payload:candidate.payload}:{},...propsInput!==void 0?{props:snapshotProps(propsInput,type,snapshot.resolve)}:{}};if(childrenInput===void 0||depth===WIDGET_MAX_DEPTH)return childrenInput&&childrenInput.length>0&&warnOnce(snapshot.resolve,"__depth-cap__",`stopped resolving after the ${WIDGET_MAX_DEPTH}-level depth cap was reached`),node;const children=[];snapshot.ancestors.add(input);try{const childCount=childrenInput.length;for(let index=0;index<childCount;index++){if(snapshot.remaining<=0){consumeNodeBudget(snapshot);break}const child=childrenInput[index];if(typeof child=="string"){if(!consumeNodeBudget(snapshot))break;children.push(child);continue}const accepted=snapshotNode(child,depth+1,snapshot);if(accepted===INVALID)return INVALID;accepted&&children.push(accepted)}}finally{snapshot.ancestors.delete(input)}return children.length>0?{...node,children}:node}function filterRowColProps(props){const out={};if(!props)return out;for(const[key,allowed]of Object.entries(ROW_COL_PROP_ENUMS)){const value=props[key];typeof value=="string"&&allowed.includes(value)&&(out[key]=value)}return out}function filterMappedProps(props,def,ctx,type){const out={},bindings=[],allowlist=def.props??{};if(props)for(const[key,rawValue]of Object.entries(props)){const expectedType=allowlist[key],{value,path}=resolveValue(rawValue,ctx);if(expectedType===void 0||typeof value!==expectedType){warnOnce(ctx,`${type}:${key}`,`skipped disallowed or mistyped prop "${key}" on type "${type}"`);continue}out[key]=value,path&&bindings.push({prop:key,path,event:def.bindings?.[key]?.event})}return{props:{...out,...def.forcedProps??{}},bindings}}function containsInteractive(node){return node.kind==="text"?!1:node.interactive||node.children.some(containsInteractive)}function resolveChild(value,ctx,path){return typeof value=="string"?{nodeKey:`path:${path}`,nodePath:path,kind:"text",text:value}:resolveNode(value,ctx,path)}function resolveNode(node,ctx,path){const authoredId=node.id,nodeKey=authoredId?`id:${authoredId}`:`path:${path}`;let kind,tag,interactive=!1,props,actionEvent,bindings=[],slots=[];if(node.type==="row"||node.type==="col")kind=node.type==="row"?"builtin-row":"builtin-col",props=filterRowColProps(node.props);else if(node.type==="text"){kind="builtin-text";const resolved=resolveValue(node.props?.value,ctx);if(props=typeof resolved.value=="string"||typeof resolved.value=="number"?{value:String(resolved.value)}:{},resolved.path){if(!authoredId)throw warnOnce(ctx,`__required-id__:${path}`,"rejected bound text without a stable id"),new TypeError("A bound widget node requires a stable id.");bindings=[{prop:"value",path:resolved.path}]}}else{const def=definitionFor(node.type,ctx.registry);if(!def)return warnOnce(ctx,node.type,`skipped unknown widget type "${node.type}" (and its subtree)`),null;kind="mapped",tag=def.tag,interactive=def.interaction==="control";const filtered=filterMappedProps(node.props,def,ctx,node.type);if(props=filtered.props,bindings=filtered.bindings,slots=def.slots??[],node.actionId!==void 0&&def.action&&(actionEvent=def.action.event),(actionEvent||bindings.length>0)&&!authoredId)throw warnOnce(ctx,`__required-id__:${path}`,`rejected stateful or actionable type "${node.type}" without a stable id`),new TypeError("A stateful or actionable widget node requires a stable id.")}const children=[];for(let index=0;index<(node.children?.length??0);index++){const resolvedChild=resolveChild(node.children[index],ctx,`${path}.${index}`);if(resolvedChild){if(interactive&&containsInteractive(resolvedChild)){warnOnce(ctx,`__nested-interactive__:${node.type}`,`skipped a control descendant inside control type "${node.type}"`);continue}resolvedChild.slot!==void 0&&!slots.includes(resolvedChild.slot)&&(resolvedChild.slot=void 0),children.push(resolvedChild)}}return{nodeId:authoredId,nodeKey,nodePath:path,kind,tag,interactive,props,actionEvent,actionId:actionEvent?node.actionId:void 0,payload:actionEvent?node.payload:void 0,bindings,children,slot:node.slot}}function hasDuplicateAuthoredIds(root,ctx){const counts=new Map,pending=[root];for(;pending.length>0;){const node=pending.pop();node.id&&counts.set(node.id,(counts.get(node.id)??0)+1);for(const child of node.children??[])typeof child!="string"&&pending.push(child)}let duplicate=!1;for(const[id,count]of counts)count<2||(duplicate=!0,warnOnce(ctx,`__duplicate-id__:${id}`,`rejected duplicate widget id "${id}"`));return duplicate}function resolveTree(root,ctx){if(root==null)return null;if(!isWidgetTypeRegistry(ctx.registry))throw new TypeError("A widget renderer registry must be created with createWidgetTypeRegistry().");const snapshot=snapshotNode(root,0,{resolve:ctx,ancestors:new Set,remaining:WIDGET_MAX_NODES});return snapshot===INVALID||snapshot===null||hasDuplicateAuthoredIds(snapshot,ctx)?null:resolveNode(snapshot,ctx,"0")}export{createWidgetDocument,resolveTree};
1
+ import{isWidgetTypeRegistry}from"./registry.js";import{readWidgetPointer,WIDGET_MAX_DEPTH,WIDGET_MAX_NODES,WIDGET_MAX_PROPS_PER_NODE,WIDGET_MAX_WARNINGS}from"../../../internal/widget-resolver.js";const WIDGET_MAX_STRING_LENGTH=16384;function truncateWidgetString(value){if(value.length<=WIDGET_MAX_STRING_LENGTH)return value;const capped=value.slice(0,WIDGET_MAX_STRING_LENGTH),last=capped.charCodeAt(capped.length-1);return last>=55296&&last<=56319?capped.slice(0,-1):capped}const DOCUMENT_INVALID=Symbol("invalid-widget-document"),DOCUMENT_MISSING=Symbol("missing-widget-document-field");function readDocumentField(input,key){try{return Object.hasOwn(input,key)?Reflect.get(input,key):DOCUMENT_MISSING}catch{return DOCUMENT_INVALID}}function snapshotDocumentProps(input){const output={};let admitted=0;try{for(const key in input){if(!Object.hasOwn(input,key))continue;if(admitted>=WIDGET_MAX_PROPS_PER_NODE)break;const value=Reflect.get(input,key);admitted+=1,output[key]=typeof value=="string"?truncateWidgetString(value):value}}catch{return DOCUMENT_INVALID}return Object.freeze(output)}function snapshotDocumentNode(input,depth,context){if(depth>WIDGET_MAX_DEPTH||context.remaining<=0)return null;if(context.remaining-=1,input===null||typeof input!="object"||Array.isArray(input)||context.ancestors.has(input))return DOCUMENT_INVALID;const type=readDocumentField(input,"type");if(typeof type!="string")return DOCUMENT_INVALID;const id=readDocumentField(input,"id"),slot=readDocumentField(input,"slot"),actionId=readDocumentField(input,"actionId"),propsInput=readDocumentField(input,"props"),childrenInput=readDocumentField(input,"children");if([id,slot,actionId,propsInput,childrenInput].includes(DOCUMENT_INVALID)||id!==DOCUMENT_MISSING&&(typeof id!="string"||id.length===0||id!==id.trim()))return DOCUMENT_INVALID;if(typeof id=="string"){if(context.ids.has(id))return DOCUMENT_INVALID;context.ids.add(id)}if(slot!==DOCUMENT_MISSING&&(typeof slot!="string"||slot.length===0||slot!==slot.trim())||actionId!==DOCUMENT_MISSING&&(typeof actionId!="string"||actionId.length===0||actionId!==actionId.trim())||propsInput!==DOCUMENT_MISSING&&(propsInput===null||typeof propsInput!="object"||Array.isArray(propsInput))||childrenInput!==DOCUMENT_MISSING&&!Array.isArray(childrenInput))return DOCUMENT_INVALID;const props=propsInput===DOCUMENT_MISSING?void 0:snapshotDocumentProps(propsInput);if(props===DOCUMENT_INVALID)return DOCUMENT_INVALID;let payload=DOCUMENT_MISSING;if(actionId!==DOCUMENT_MISSING&&(payload=readDocumentField(input,"payload"),payload===DOCUMENT_INVALID))return DOCUMENT_INVALID;const children=[];if(childrenInput!==DOCUMENT_MISSING&&depth<WIDGET_MAX_DEPTH){const length=readDocumentField(childrenInput,"length");if(typeof length!="number"||!Number.isSafeInteger(length)||length<0)return DOCUMENT_INVALID;context.ancestors.add(input);try{for(let index=0;index<length&&context.remaining>0;index++){const child=readDocumentField(childrenInput,index);if(child===DOCUMENT_INVALID||child===DOCUMENT_MISSING)return DOCUMENT_INVALID;if(typeof child=="string"){context.remaining-=1,children.push(truncateWidgetString(child));continue}const snapshot=snapshotDocumentNode(child,depth+1,context);if(snapshot===DOCUMENT_INVALID)return DOCUMENT_INVALID;snapshot&&children.push(snapshot)}}finally{context.ancestors.delete(input)}}return Object.freeze({type,...typeof id=="string"?{id}:{},...typeof slot=="string"?{slot}:{},...typeof actionId=="string"?{actionId,payload:payload===DOCUMENT_MISSING?void 0:payload}:{},...props===void 0?{}:{props},...children.length===0?{}:{children:Object.freeze(children)}})}function createWidgetDocument(root){const snapshot=snapshotDocumentNode(root,0,{ancestors:new Set,ids:new Set,remaining:WIDGET_MAX_NODES});if(snapshot===DOCUMENT_INVALID||snapshot===null)throw new TypeError("A widget document root must be a valid bounded widget node.");return Object.freeze({version:"2",root:snapshot})}const WARNING_SUPPRESSION_KEY="__warning-cap__",INVALID=Symbol("invalid-widget-input"),ROW_COL_PROP_ENUMS={gap:["s","m","l"],align:["start","center","end","stretch"],justify:["start","center","end","between"]};function warnOnce(ctx,key,message){if(!ctx.warned.has(key)){if(ctx.warned.size>=WIDGET_MAX_WARNINGS){if(ctx.warned.has(WARNING_SUPPRESSION_KEY))return;ctx.warned.add(WARNING_SUPPRESSION_KEY),(ctx.warn??console.warn)(`[lr-widget-renderer] suppressed further diagnostics after ${WIDGET_MAX_WARNINGS} unique warnings`);return}ctx.warned.add(key),(ctx.warn??console.warn)(`[lr-widget-renderer] ${message}`)}}function capResolvedString(value,ctx,key,subject){const capped=truncateWidgetString(value);return capped.length!==value.length&&warnOnce(ctx,`__string-cap__:${key}`,`truncated ${subject} after the ${WIDGET_MAX_STRING_LENGTH}-character string cap was reached`),capped}function isBinding(value){return!!(value&&typeof value=="object"&&!Array.isArray(value)&&typeof value.$bind=="string")}function resolveValue(value,ctx){if(!isBinding(value))return{value};const resolved=readWidgetPointer(ctx.bindingState,value.$bind);return{value:resolved===void 0?value.fallback:resolved,path:value.$bind}}function consumeNodeBudget(snapshot){return snapshot.remaining<=0?(warnOnce(snapshot.resolve,"__node-cap__",`stopped resolving after the ${WIDGET_MAX_NODES}-node cap was reached`),!1):(snapshot.remaining--,!0)}function snapshotProps(input,type,ctx){const out={};let visited=0;for(const key in input){if(visited>=WIDGET_MAX_PROPS_PER_NODE){warnOnce(ctx,`__prop-cap__:${type}`,`stopped reading props on type "${type}" after the ${WIDGET_MAX_PROPS_PER_NODE}-prop cap was reached`);break}visited++,Object.hasOwn(input,key)&&(out[key]=input[key])}return out}function definitionFor(type,registry){return registry.get(type)}function snapshotNode(input,depth,snapshot){if(depth>WIDGET_MAX_DEPTH)return warnOnce(snapshot.resolve,"__depth-cap__",`stopped resolving after the ${WIDGET_MAX_DEPTH}-level depth cap was reached`),null;if(!consumeNodeBudget(snapshot))return null;if(input===null||typeof input!="object"||Array.isArray(input)||snapshot.ancestors.has(input))return INVALID;const candidate=input,type=candidate.type;if(typeof type!="string")return INVALID;if(!(type==="row"||type==="col"||type==="text")&&!definitionFor(type,snapshot.resolve.registry))return{type};const id=candidate.id;if(id!==void 0&&(typeof id!="string"||id.length===0||id!==id.trim()))return INVALID;const slot=candidate.slot;if(slot!==void 0&&(typeof slot!="string"||slot.length===0||slot!==slot.trim()))return INVALID;const actionId=candidate.actionId;if(actionId!==void 0&&(typeof actionId!="string"||actionId.length===0||actionId!==actionId.trim()))return INVALID;const propsInput=candidate.props;if(propsInput!==void 0&&(propsInput===null||typeof propsInput!="object"||Array.isArray(propsInput)))return INVALID;const childrenInput=candidate.children;if(childrenInput!==void 0&&!Array.isArray(childrenInput))return INVALID;const node={type,...id!==void 0?{id}:{},...slot!==void 0?{slot}:{},...actionId!==void 0?{actionId,payload:candidate.payload}:{},...propsInput!==void 0?{props:snapshotProps(propsInput,type,snapshot.resolve)}:{}};if(childrenInput===void 0||depth===WIDGET_MAX_DEPTH)return childrenInput&&childrenInput.length>0&&warnOnce(snapshot.resolve,"__depth-cap__",`stopped resolving after the ${WIDGET_MAX_DEPTH}-level depth cap was reached`),node;const children=[];snapshot.ancestors.add(input);try{const childCount=childrenInput.length;for(let index=0;index<childCount;index++){if(snapshot.remaining<=0){consumeNodeBudget(snapshot);break}const child=childrenInput[index];if(typeof child=="string"){if(!consumeNodeBudget(snapshot))break;children.push(child);continue}const accepted=snapshotNode(child,depth+1,snapshot);if(accepted===INVALID)return INVALID;accepted&&children.push(accepted)}}finally{snapshot.ancestors.delete(input)}return children.length>0?{...node,children}:node}function filterRowColProps(props){const out={};if(!props)return out;for(const[key,allowed]of Object.entries(ROW_COL_PROP_ENUMS)){const value=props[key];typeof value=="string"&&allowed.includes(value)&&(out[key]=value)}return out}function filterMappedProps(props,def,ctx,type){const out={},bindings=[],allowlist=def.props??{};if(props)for(const[key,rawValue]of Object.entries(props)){const expectedType=allowlist[key],{value,path}=resolveValue(rawValue,ctx);if(expectedType===void 0||typeof value!==expectedType){warnOnce(ctx,`${type}:${key}`,`skipped disallowed or mistyped prop "${key}" on type "${type}"`);continue}out[key]=typeof value=="string"?capResolvedString(value,ctx,`${type}:${key}`,`string prop "${key}" on type "${type}"`):value,path&&bindings.push({prop:key,path,event:def.bindings?.[key]?.event})}return{props:{...out,...def.forcedProps??{}},bindings}}function containsInteractive(node){return node.kind==="text"?!1:node.interactive||node.children.some(containsInteractive)}function resolveChild(value,ctx,path){return typeof value=="string"?{nodeKey:`path:${path}`,nodePath:path,kind:"text",text:capResolvedString(value,ctx,"__text__","a text child")}:resolveNode(value,ctx,path)}function resolveNode(node,ctx,path){const authoredId=node.id,nodeKey=authoredId?`id:${authoredId}`:`path:${path}`;let kind,tag,interactive=!1,props,actionEvent,bindings=[],slots=[];if(node.type==="row"||node.type==="col")kind=node.type==="row"?"builtin-row":"builtin-col",props=filterRowColProps(node.props);else if(node.type==="text"){kind="builtin-text";const resolved=resolveValue(node.props?.value,ctx);if(props=typeof resolved.value=="string"||typeof resolved.value=="number"?{value:capResolvedString(String(resolved.value),ctx,"__text-value__",'the "value" of a built-in text node')}:{},resolved.path){if(!authoredId)throw warnOnce(ctx,`__required-id__:${path}`,"rejected bound text without a stable id"),new TypeError("A bound widget node requires a stable id.");bindings=[{prop:"value",path:resolved.path}]}}else{const def=definitionFor(node.type,ctx.registry);if(!def)return warnOnce(ctx,node.type,`skipped unknown widget type "${node.type}" (and its subtree)`),null;kind="mapped",tag=def.tag,interactive=def.interaction==="control";const filtered=filterMappedProps(node.props,def,ctx,node.type);if(props=filtered.props,bindings=filtered.bindings,slots=def.slots??[],node.actionId!==void 0&&def.action&&(actionEvent=def.action.event),(actionEvent||bindings.length>0)&&!authoredId)throw warnOnce(ctx,`__required-id__:${path}`,`rejected stateful or actionable type "${node.type}" without a stable id`),new TypeError("A stateful or actionable widget node requires a stable id.")}const children=[];for(let index=0;index<(node.children?.length??0);index++){const resolvedChild=resolveChild(node.children[index],ctx,`${path}.${index}`);if(resolvedChild){if(interactive&&containsInteractive(resolvedChild)){warnOnce(ctx,`__nested-interactive__:${node.type}`,`skipped a control descendant inside control type "${node.type}"`);continue}resolvedChild.slot!==void 0&&!slots.includes(resolvedChild.slot)&&(resolvedChild.slot=void 0),children.push(resolvedChild)}}return{nodeId:authoredId,nodeKey,nodePath:path,kind,tag,interactive,props,actionEvent,actionId:actionEvent?node.actionId:void 0,payload:actionEvent?node.payload:void 0,bindings,children,slot:node.slot}}function hasDuplicateAuthoredIds(root,ctx){const counts=new Map,pending=[root];for(;pending.length>0;){const node=pending.pop();node.id&&counts.set(node.id,(counts.get(node.id)??0)+1);for(const child of node.children??[])typeof child!="string"&&pending.push(child)}let duplicate=!1;for(const[id,count]of counts)count<2||(duplicate=!0,warnOnce(ctx,`__duplicate-id__:${id}`,`rejected duplicate widget id "${id}"`));return duplicate}function resolveTree(root,ctx){if(root==null)return null;if(!isWidgetTypeRegistry(ctx.registry))throw new TypeError("A widget renderer registry must be created with createWidgetTypeRegistry().");const snapshot=snapshotNode(root,0,{resolve:ctx,ancestors:new Set,remaining:WIDGET_MAX_NODES});return snapshot===INVALID||snapshot===null||hasDuplicateAuthoredIds(snapshot,ctx)?null:resolveNode(snapshot,ctx,"0")}export{WIDGET_MAX_STRING_LENGTH,createWidgetDocument,resolveTree};
@@ -1,5 +1,6 @@
1
1
  import { type TemplateResult } from 'lit';
2
2
  import { LyraElement } from '../../../internal/lyra-element.js';
3
+ import type { LyraDatePickerFirstDayOfWeek } from '../../forms/date-picker/date-picker.class.js';
3
4
  export interface CalendarEvent {
4
5
  readonly id?: string;
5
6
  readonly date: string;
@@ -20,6 +21,10 @@ export interface LyraCalendarEventMap {
20
21
  }
21
22
  /** The two display modes `view` accepts. */
22
23
  export type CalendarView = 'month' | 'agenda';
24
+ /** The shared closed weekday vocabulary `lr-date-picker`/`lr-date-input` already accept
25
+ * (`'auto'`, then `'sun'` through `'sat'`) -- reusing {@link LyraDatePickerFirstDayOfWeek}
26
+ * instead of a parallel string union. */
27
+ export type LyraCalendarFirstDayOfWeek = LyraDatePickerFirstDayOfWeek;
23
28
  /** `<lr-calendar>` — responsive month calendar with event markers and agenda mode.
24
29
  *
25
30
  * Month-view event markers are real buttons inside each focusable gridcell, so
@@ -29,6 +34,11 @@ export type CalendarView = 'month' | 'agenda';
29
34
  * Public collection properties take bounded, clone-owned readonly snapshots. Create a new
30
35
  * collection and reassign it after changes; mutating the assigned array does not update the view.
31
36
  *
37
+ * `firstDayOfWeek` defaults to `'auto'`, deriving the week start from `effectiveLocale` (via the
38
+ * shared `resolveFirstDayOfWeek()` contract also used by `lr-date-picker`/`lr-date-input`), and
39
+ * also accepts one of the shared weekday-name tokens (`'sun'` through `'sat'`) for an explicit,
40
+ * locale-independent week start.
41
+ *
32
42
  * @customElement lr-calendar
33
43
  * @event lr-date-select - A calendar date was selected.
34
44
  * @event lr-event-select - An event was selected.
@@ -72,11 +82,14 @@ export declare class LyraCalendar extends LyraElement<LyraCalendarEventMap> {
72
82
  private _view;
73
83
  get view(): CalendarView;
74
84
  set view(value: CalendarView);
75
- firstDayOfWeek: number;
85
+ firstDayOfWeek: LyraCalendarFirstDayOfWeek;
76
86
  accessibleLabel: string;
77
87
  private focusedDate;
78
88
  private get viewStart();
79
- /** `firstDayOfWeek` clamped into the 0–6 range `monthMatrix`/`weekdayLabels` expect, tolerating a malformed or out-of-range attribute value instead of letting it silently drop leading days of the month or produce `Invalid Date`. `finiteInteger` sanitizes a NaN/non-finite/fractional raw value to a safe integer (falling back to `1` to match this property's own default) before the modulo wraps any still-out-of-range integer (including negatives) into `[0, 6]`. */
89
+ /** `firstDayOfWeek` resolved into the 0–6 range `monthMatrix`/`weekdayLabels` expect --
90
+ * `'auto'`, a weekday-name token, or any other malformed token all go through the shared
91
+ * `resolveFirstDayOfWeek()` contract, which derives `'auto'` from `effectiveLocale` and falls
92
+ * back to Sunday (0) for anything else. */
80
93
  private get normalizedFirstDayOfWeek();
81
94
  private changeMonth;
82
95
  private selectDate;
@@ -1,2 +1,2 @@
1
- var __decorate=function(decorators,target,key,desc){var c=arguments.length,r=c<3?target:desc===null?desc=Object.getOwnPropertyDescriptor(target,key):desc,d;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")r=Reflect.decorate(decorators,target,key,desc);else for(var i=decorators.length-1;i>=0;i--)(d=decorators[i])&&(r=(c<3?d(r):c>3?d(target,key,r):d(target,key))||r);return c>3&&r&&Object.defineProperty(target,key,r),r};import{html}from"lit";import{property,state}from"lit/decorators.js";import{styleMap}from"lit/directives/style-map.js";import{LyraElement}from"../../../internal/lyra-element.js";import{formatISO,monthMatrix,parseISO,weekdayLabels}from"../../forms/date-picker/calendar-core.js";import{sanitizeCssColor}from"../../../internal/safe-css.js";import{finiteInteger}from"../../../internal/numbers.js";import{styles}from"./calendar.styles.js";import{getDateTimeFormat,getNumberFormat}from"../../../internal/intl-cache.js";import{LYRA_DEFAULT_calendarEmpty,LYRA_DEFAULT_calendarLabel,LYRA_DEFAULT_calendarNextMonth,LYRA_DEFAULT_calendarPreviousMonth}from"../../../internal/default-strings.generated.js";const monthStart=date=>new Date(date.getFullYear(),date.getMonth(),1);class LyraCalendar extends LyraElement{constructor(){super(...arguments),this.events=[],this.value="",this.viewDate=formatISO(new Date).slice(0,7)+"-01",this._view="month",this.firstDayOfWeek=1,this.accessibleLabel="",this.focusedDate=""}static{this.defaultStrings={...super.defaultStrings,calendarEmpty:LYRA_DEFAULT_calendarEmpty,calendarLabel:LYRA_DEFAULT_calendarLabel,calendarNextMonth:LYRA_DEFAULT_calendarNextMonth,calendarPreviousMonth:LYRA_DEFAULT_calendarPreviousMonth}}static{this.ownedCollectionProperties=Object.freeze(["events"])}static{this.identityCollectionProperties=Object.freeze(["events"])}static{this.styles=[LyraElement.styles,styles]}get view(){return this._view}set view(value){const normalized=value==="agenda"?"agenda":"month",previous=this._view;if(previous===normalized){value!==normalized&&this.requestUpdate("view",previous);return}this._view=normalized,this.requestUpdate("view",previous)}get viewStart(){const parsed=new Date(`${this.viewDate}T00:00:00`);return Number.isNaN(parsed.valueOf())?monthStart(new Date):monthStart(parsed)}get normalizedFirstDayOfWeek(){return(finiteInteger(this.firstDayOfWeek,1)%7+7)%7}changeMonth(delta){const next=new Date(this.viewStart.getFullYear(),this.viewStart.getMonth()+delta,1);this.viewDate=formatISO(next),this.emit("lr-view-change",{viewDate:this.viewDate})}selectDate(date){this.value=date,this.focusedDate=date,this.emit("lr-date-select",{date})}bucketEventsByDate(){const buckets=new Map;for(const event of this.events){const bucket=buckets.get(event.date);bucket?bucket.push(event):buckets.set(event.date,[event])}return buckets}weeks(){const start=this.viewStart;return monthMatrix(start.getFullYear(),start.getMonth(),this.normalizedFirstDayOfWeek)}gridBounds(weeks){return[weeks[0][0],weeks[weeks.length-1][6]]}onDayKeyDown(event,date){let delta=0;if(event.key==="ArrowLeft")delta=this.effectiveDirection==="rtl"?1:-1;else if(event.key==="ArrowRight")delta=this.effectiveDirection==="rtl"?-1:1;else if(event.key==="ArrowUp")delta=-7;else if(event.key==="ArrowDown")delta=7;else if(event.key==="Enter"||event.key===" "){event.preventDefault(),this.selectDate(formatISO(date));return}else return;event.preventDefault();const next=new Date(date);next.setDate(next.getDate()+delta);const[gridFirst,gridLast]=this.gridBounds(this.weeks());(next<gridFirst||next>gridLast)&&(this.viewDate=formatISO(monthStart(next)),this.emit("lr-view-change",{viewDate:this.viewDate})),this.focusedDate=formatISO(next),queueMicrotask(()=>this.renderRoot.querySelector(`[data-date="${this.focusedDate}"]`)?.focus())}weekdays(){return weekdayLabels(this.normalizedFirstDayOfWeek,"short",this.effectiveLocale)}updated(changed){super.updated(changed),this.getAttribute("view")!==this._view&&this.setAttribute("view",this._view)}render(){const start=this.viewStart,weeks=this.weeks(),monthTitle=getDateTimeFormat(this.effectiveLocale,{month:"long",year:"numeric"}).format(start),today=formatISO(new Date),label=this.accessibleLabel||this.localize("calendarLabel"),dayLabelFmt=getDateTimeFormat(this.effectiveLocale,{dateStyle:"full"}),agendaDateFmt=getDateTimeFormat(this.effectiveLocale,{dateStyle:"medium"}),dayNumberFmt=getNumberFormat(this.effectiveLocale),agenda=this.events.filter(event=>event.date.startsWith(formatISO(start).slice(0,7))).sort((a,b)=>a.date<b.date?-1:a.date>b.date?1:0),eventsByDate=this.view==="month"?this.bucketEventsByDate():void 0,[gridFirst,gridLast]=this.gridBounds(weeks),rawAnchor=this.focusedDate||this.value||today,rawAnchorDate=parseISO(rawAnchor),anchor=rawAnchorDate&&rawAnchorDate>=gridFirst&&rawAnchorDate<=gridLast?rawAnchor:formatISO(start);return html`<section aria-label=${label}><header part="header navigation"><button part="nav previous-button" type="button" aria-label=${this.localize("calendarPreviousMonth")} @click=${()=>this.changeMonth(-1)}><span part="nav-glyph" aria-hidden="true">‹</span></button><span part="title">${monthTitle}</span><button part="nav next-button" type="button" aria-label=${this.localize("calendarNextMonth")} @click=${()=>this.changeMonth(1)}><span part="nav-glyph" aria-hidden="true">›</span></button></header>
2
- ${this.view==="agenda"?html`<div part="agenda">${agenda.length?agenda.map(event=>{const date=parseISO(event.date);return html`<button part="agenda-event" type="button" @click=${()=>this.emit("lr-event-select",{event})}><strong>${date?agendaDateFmt.format(date):event.date}</strong> ${event.title}</button>`}):html`<p>${this.localize("calendarEmpty")}</p>`}</div>`:html`<div part="weekdays">${this.weekdays().map(day=>html`<span part="weekday">${day}</span>`)}</div><div part="grid" role="grid" aria-label=${monthTitle}>${weeks.map(week=>html`<div part="week" role="row">${week.map(date=>{const dateIso=formatISO(date),dayEvents=eventsByDate?.get(dateIso)??[];return html`<div part="day" role="gridcell" data-date=${dateIso} data-outside=${date.getMonth()!==start.getMonth()?"true":"false"} data-today=${dateIso===today?"true":"false"} data-selected=${dateIso===this.value?"true":"false"} aria-selected=${dateIso===this.value?"true":"false"} aria-label=${dayLabelFmt.format(date)} tabindex=${dateIso===anchor?"0":"-1"} @click=${event=>{(event.target===event.currentTarget||event.target.getAttribute("part")==="date")&&this.selectDate(dateIso)}} @keydown=${event=>{event.target===event.currentTarget&&this.onDayKeyDown(event,date)}}><span part="date">${dayNumberFmt.format(date.getDate())}</span>${dayEvents.map(item=>{const bg=item.color?sanitizeCssColor(item.color):void 0;return html`<button part="event" type="button" style=${styleMap(bg?{backgroundColor:bg}:{})} @click=${event=>{event.stopPropagation(),this.emit("lr-event-select",{event:item})}}>${item.title}</button>`})}</div>`})}</div>`)}</div>`}</section>`}}__decorate([property({attribute:!1})],LyraCalendar.prototype,"events",void 0),__decorate([property()],LyraCalendar.prototype,"value",void 0),__decorate([property({attribute:"view-date"})],LyraCalendar.prototype,"viewDate",void 0),__decorate([property({reflect:!0})],LyraCalendar.prototype,"view",null),__decorate([property({type:Number,attribute:"first-day-of-week"})],LyraCalendar.prototype,"firstDayOfWeek",void 0),__decorate([property({attribute:"aria-label"})],LyraCalendar.prototype,"accessibleLabel",void 0),__decorate([state()],LyraCalendar.prototype,"focusedDate",void 0);export{LyraCalendar};
1
+ var __decorate=function(decorators,target,key,desc){var c=arguments.length,r=c<3?target:desc===null?desc=Object.getOwnPropertyDescriptor(target,key):desc,d;if(typeof Reflect=="object"&&typeof Reflect.decorate=="function")r=Reflect.decorate(decorators,target,key,desc);else for(var i=decorators.length-1;i>=0;i--)(d=decorators[i])&&(r=(c<3?d(r):c>3?d(target,key,r):d(target,key))||r);return c>3&&r&&Object.defineProperty(target,key,r),r};import{html}from"lit";import{property,state}from"lit/decorators.js";import{styleMap}from"lit/directives/style-map.js";import{LyraElement}from"../../../internal/lyra-element.js";import{formatISO,monthMatrix,parseISO,resolveFirstDayOfWeek,weekdayLabels}from"../../forms/date-picker/calendar-core.js";import{sanitizeCssColor}from"../../../internal/safe-css.js";import{styles}from"./calendar.styles.js";import{getDateTimeFormat,getNumberFormat}from"../../../internal/intl-cache.js";import{LYRA_DEFAULT_calendarEmpty,LYRA_DEFAULT_calendarLabel,LYRA_DEFAULT_calendarNextMonth,LYRA_DEFAULT_calendarPreviousMonth}from"../../../internal/default-strings.generated.js";const monthStart=date=>new Date(date.getFullYear(),date.getMonth(),1);class LyraCalendar extends LyraElement{constructor(){super(...arguments),this.events=[],this.value="",this.viewDate=formatISO(new Date).slice(0,7)+"-01",this._view="month",this.firstDayOfWeek="auto",this.accessibleLabel="",this.focusedDate=""}static{this.defaultStrings={...super.defaultStrings,calendarEmpty:LYRA_DEFAULT_calendarEmpty,calendarLabel:LYRA_DEFAULT_calendarLabel,calendarNextMonth:LYRA_DEFAULT_calendarNextMonth,calendarPreviousMonth:LYRA_DEFAULT_calendarPreviousMonth}}static{this.ownedCollectionProperties=Object.freeze(["events"])}static{this.identityCollectionProperties=Object.freeze(["events"])}static{this.styles=[LyraElement.styles,styles]}get view(){return this._view}set view(value){const normalized=value==="agenda"?"agenda":"month",previous=this._view;if(previous===normalized){value!==normalized&&this.requestUpdate("view",previous);return}this._view=normalized,this.requestUpdate("view",previous)}get viewStart(){const parsed=new Date(`${this.viewDate}T00:00:00`);return Number.isNaN(parsed.valueOf())?monthStart(new Date):monthStart(parsed)}get normalizedFirstDayOfWeek(){return resolveFirstDayOfWeek(this.firstDayOfWeek,this.effectiveLocale)}changeMonth(delta){const next=new Date(this.viewStart.getFullYear(),this.viewStart.getMonth()+delta,1);this.viewDate=formatISO(next),this.emit("lr-view-change",{viewDate:this.viewDate})}selectDate(date){this.value=date,this.focusedDate=date,this.emit("lr-date-select",{date})}bucketEventsByDate(){const buckets=new Map;for(const event of this.events){const bucket=buckets.get(event.date);bucket?bucket.push(event):buckets.set(event.date,[event])}return buckets}weeks(){const start=this.viewStart;return monthMatrix(start.getFullYear(),start.getMonth(),this.normalizedFirstDayOfWeek)}gridBounds(weeks){return[weeks[0][0],weeks[weeks.length-1][6]]}onDayKeyDown(event,date){let delta=0;if(event.key==="ArrowLeft")delta=this.effectiveDirection==="rtl"?1:-1;else if(event.key==="ArrowRight")delta=this.effectiveDirection==="rtl"?-1:1;else if(event.key==="ArrowUp")delta=-7;else if(event.key==="ArrowDown")delta=7;else if(event.key==="Enter"||event.key===" "){event.preventDefault(),this.selectDate(formatISO(date));return}else return;event.preventDefault();const next=new Date(date);next.setDate(next.getDate()+delta);const[gridFirst,gridLast]=this.gridBounds(this.weeks());(next<gridFirst||next>gridLast)&&(this.viewDate=formatISO(monthStart(next)),this.emit("lr-view-change",{viewDate:this.viewDate})),this.focusedDate=formatISO(next),queueMicrotask(()=>this.renderRoot.querySelector(`[data-date="${this.focusedDate}"]`)?.focus())}weekdays(){return weekdayLabels(this.normalizedFirstDayOfWeek,"short",this.effectiveLocale)}updated(changed){super.updated(changed),this.getAttribute("view")!==this._view&&this.setAttribute("view",this._view)}render(){const start=this.viewStart,weeks=this.weeks(),monthTitle=getDateTimeFormat(this.effectiveLocale,{month:"long",year:"numeric"}).format(start),today=formatISO(new Date),label=this.accessibleLabel||this.localize("calendarLabel"),dayLabelFmt=getDateTimeFormat(this.effectiveLocale,{dateStyle:"full"}),agendaDateFmt=getDateTimeFormat(this.effectiveLocale,{dateStyle:"medium"}),dayNumberFmt=getNumberFormat(this.effectiveLocale),agenda=this.events.filter(event=>event.date.startsWith(formatISO(start).slice(0,7))).sort((a,b)=>a.date<b.date?-1:a.date>b.date?1:0),eventsByDate=this.view==="month"?this.bucketEventsByDate():void 0,[gridFirst,gridLast]=this.gridBounds(weeks),rawAnchor=this.focusedDate||this.value||today,rawAnchorDate=parseISO(rawAnchor),anchor=rawAnchorDate&&rawAnchorDate>=gridFirst&&rawAnchorDate<=gridLast?rawAnchor:formatISO(start);return html`<section aria-label=${label}><header part="header navigation"><button part="nav previous-button" type="button" aria-label=${this.localize("calendarPreviousMonth")} @click=${()=>this.changeMonth(-1)}><span part="nav-glyph" aria-hidden="true">‹</span></button><span part="title">${monthTitle}</span><button part="nav next-button" type="button" aria-label=${this.localize("calendarNextMonth")} @click=${()=>this.changeMonth(1)}><span part="nav-glyph" aria-hidden="true">›</span></button></header>
2
+ ${this.view==="agenda"?html`<div part="agenda">${agenda.length?agenda.map(event=>{const date=parseISO(event.date);return html`<button part="agenda-event" type="button" @click=${()=>this.emit("lr-event-select",{event})}><strong>${date?agendaDateFmt.format(date):event.date}</strong> ${event.title}</button>`}):html`<p>${this.localize("calendarEmpty")}</p>`}</div>`:html`<div part="weekdays">${this.weekdays().map(day=>html`<span part="weekday">${day}</span>`)}</div><div part="grid" role="grid" aria-label=${monthTitle}>${weeks.map(week=>html`<div part="week" role="row">${week.map(date=>{const dateIso=formatISO(date),dayEvents=eventsByDate?.get(dateIso)??[];return html`<div part="day" role="gridcell" data-date=${dateIso} data-outside=${date.getMonth()!==start.getMonth()?"true":"false"} data-today=${dateIso===today?"true":"false"} data-selected=${dateIso===this.value?"true":"false"} aria-selected=${dateIso===this.value?"true":"false"} aria-label=${dayLabelFmt.format(date)} tabindex=${dateIso===anchor?"0":"-1"} @click=${event=>{(event.target===event.currentTarget||event.target.getAttribute("part")==="date")&&this.selectDate(dateIso)}} @keydown=${event=>{event.target===event.currentTarget&&this.onDayKeyDown(event,date)}}><span part="date">${dayNumberFmt.format(date.getDate())}</span>${dayEvents.map(item=>{const bg=item.color?sanitizeCssColor(item.color):void 0;return html`<button part="event" type="button" style=${styleMap(bg?{backgroundColor:bg}:{})} @click=${event=>{event.stopPropagation(),this.emit("lr-event-select",{event:item})}}>${item.title}</button>`})}</div>`})}</div>`)}</div>`}</section>`}}__decorate([property({attribute:!1})],LyraCalendar.prototype,"events",void 0),__decorate([property()],LyraCalendar.prototype,"value",void 0),__decorate([property({attribute:"view-date"})],LyraCalendar.prototype,"viewDate",void 0),__decorate([property({reflect:!0})],LyraCalendar.prototype,"view",null),__decorate([property({attribute:"first-day-of-week"})],LyraCalendar.prototype,"firstDayOfWeek",void 0),__decorate([property({attribute:"aria-label"})],LyraCalendar.prototype,"accessibleLabel",void 0),__decorate([state()],LyraCalendar.prototype,"focusedDate",void 0);export{LyraCalendar};