stimeo-ui 0.17.0 → 0.18.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 (299) hide show
  1. package/CHANGELOG.md +136 -2
  2. package/README.md +19 -10
  3. package/dist/cable/index.d.ts +11 -9
  4. package/dist/cable/index.js +22 -14
  5. package/dist/cable/index.js.map +1 -1
  6. package/dist/coerce-JtZVNG5h.d.ts +20 -0
  7. package/dist/controllers/accordion_controller.js +14 -6
  8. package/dist/controllers/accordion_controller.js.map +1 -1
  9. package/dist/controllers/alert_dialog_controller.js +145 -118
  10. package/dist/controllers/alert_dialog_controller.js.map +1 -1
  11. package/dist/controllers/announcer_controller.d.ts +5 -3
  12. package/dist/controllers/announcer_controller.js +113 -17
  13. package/dist/controllers/announcer_controller.js.map +1 -1
  14. package/dist/controllers/auto_submit_controller.js +185 -60
  15. package/dist/controllers/auto_submit_controller.js.map +1 -1
  16. package/dist/controllers/avatar_controller.js +55 -43
  17. package/dist/controllers/avatar_controller.js.map +1 -1
  18. package/dist/controllers/breadcrumb_controller.js.map +1 -1
  19. package/dist/controllers/bulk_select_controller.d.ts +3 -3
  20. package/dist/controllers/bulk_select_controller.js +64 -50
  21. package/dist/controllers/bulk_select_controller.js.map +1 -1
  22. package/dist/controllers/calendar_controller.d.ts +15 -12
  23. package/dist/controllers/calendar_controller.js +55 -53
  24. package/dist/controllers/calendar_controller.js.map +1 -1
  25. package/dist/controllers/carousel_controller.d.ts +9 -5
  26. package/dist/controllers/carousel_controller.js +124 -86
  27. package/dist/controllers/carousel_controller.js.map +1 -1
  28. package/dist/controllers/character_counter_controller.d.ts +27 -6
  29. package/dist/controllers/character_counter_controller.js +291 -95
  30. package/dist/controllers/character_counter_controller.js.map +1 -1
  31. package/dist/controllers/checkbox_controller.js +6 -0
  32. package/dist/controllers/checkbox_controller.js.map +1 -1
  33. package/dist/controllers/clipboard_controller.js +118 -27
  34. package/dist/controllers/clipboard_controller.js.map +1 -1
  35. package/dist/controllers/collapsible_controller.d.ts +1 -1
  36. package/dist/controllers/collapsible_controller.js +52 -49
  37. package/dist/controllers/collapsible_controller.js.map +1 -1
  38. package/dist/controllers/color_picker_controller.js +29 -7
  39. package/dist/controllers/color_picker_controller.js.map +1 -1
  40. package/dist/controllers/combobox_controller.d.ts +1 -1
  41. package/dist/controllers/combobox_controller.js +210 -71
  42. package/dist/controllers/combobox_controller.js.map +1 -1
  43. package/dist/controllers/command_palette_controller.d.ts +9 -9
  44. package/dist/controllers/command_palette_controller.js +290 -140
  45. package/dist/controllers/command_palette_controller.js.map +1 -1
  46. package/dist/controllers/conditional_fields_controller.js +145 -58
  47. package/dist/controllers/conditional_fields_controller.js.map +1 -1
  48. package/dist/controllers/confirm_controller.js +145 -118
  49. package/dist/controllers/confirm_controller.js.map +1 -1
  50. package/dist/controllers/context_menu_controller.d.ts +49 -14
  51. package/dist/controllers/context_menu_controller.js +138 -73
  52. package/dist/controllers/context_menu_controller.js.map +1 -1
  53. package/dist/controllers/count_up_controller.js.map +1 -1
  54. package/dist/controllers/countdown_controller.d.ts +2 -2
  55. package/dist/controllers/countdown_controller.js +109 -21
  56. package/dist/controllers/countdown_controller.js.map +1 -1
  57. package/dist/controllers/currency_input_controller.d.ts +75 -11
  58. package/dist/controllers/currency_input_controller.js +446 -72
  59. package/dist/controllers/currency_input_controller.js.map +1 -1
  60. package/dist/controllers/data_grid_controller.d.ts +10 -8
  61. package/dist/controllers/data_grid_controller.js +134 -28
  62. package/dist/controllers/data_grid_controller.js.map +1 -1
  63. package/dist/controllers/date_range_picker_controller.d.ts +12 -9
  64. package/dist/controllers/date_range_picker_controller.js +93 -72
  65. package/dist/controllers/date_range_picker_controller.js.map +1 -1
  66. package/dist/controllers/dialog_controller.d.ts +4 -5
  67. package/dist/controllers/dialog_controller.js +145 -118
  68. package/dist/controllers/dialog_controller.js.map +1 -1
  69. package/dist/controllers/direct_upload_controller.d.ts +1 -1
  70. package/dist/controllers/direct_upload_controller.js +24 -14
  71. package/dist/controllers/direct_upload_controller.js.map +1 -1
  72. package/dist/controllers/dirty_form_controller.d.ts +6 -1
  73. package/dist/controllers/dirty_form_controller.js +68 -31
  74. package/dist/controllers/dirty_form_controller.js.map +1 -1
  75. package/dist/controllers/dismissible_controller.js +66 -46
  76. package/dist/controllers/dismissible_controller.js.map +1 -1
  77. package/dist/controllers/drawer_controller.js +145 -118
  78. package/dist/controllers/drawer_controller.js.map +1 -1
  79. package/dist/controllers/dropdown_controller.js +76 -63
  80. package/dist/controllers/dropdown_controller.js.map +1 -1
  81. package/dist/controllers/editable_controller.js +200 -62
  82. package/dist/controllers/editable_controller.js.map +1 -1
  83. package/dist/controllers/empty_state_controller.js +13 -6
  84. package/dist/controllers/empty_state_controller.js.map +1 -1
  85. package/dist/controllers/file_dropzone_controller.d.ts +3 -0
  86. package/dist/controllers/file_dropzone_controller.js +55 -48
  87. package/dist/controllers/file_dropzone_controller.js.map +1 -1
  88. package/dist/controllers/filter_controller.js +9 -2
  89. package/dist/controllers/filter_controller.js.map +1 -1
  90. package/dist/controllers/flash_controller.d.ts +4 -4
  91. package/dist/controllers/flash_controller.js +66 -33
  92. package/dist/controllers/flash_controller.js.map +1 -1
  93. package/dist/controllers/focus_controller.d.ts +3 -3
  94. package/dist/controllers/focus_controller.js +39 -14
  95. package/dist/controllers/focus_controller.js.map +1 -1
  96. package/dist/controllers/form_field_controller.d.ts +2 -1
  97. package/dist/controllers/form_field_controller.js +52 -43
  98. package/dist/controllers/form_field_controller.js.map +1 -1
  99. package/dist/controllers/form_validation_controller.d.ts +3 -3
  100. package/dist/controllers/form_validation_controller.js +18 -11
  101. package/dist/controllers/form_validation_controller.js.map +1 -1
  102. package/dist/controllers/frame_loading_controller.d.ts +13 -12
  103. package/dist/controllers/frame_loading_controller.js +55 -48
  104. package/dist/controllers/frame_loading_controller.js.map +1 -1
  105. package/dist/controllers/highlight_controller.d.ts +5 -4
  106. package/dist/controllers/highlight_controller.js.map +1 -1
  107. package/dist/controllers/hover_card_controller.d.ts +4 -1
  108. package/dist/controllers/hover_card_controller.js +67 -61
  109. package/dist/controllers/hover_card_controller.js.map +1 -1
  110. package/dist/controllers/idle_controller.d.ts +6 -5
  111. package/dist/controllers/idle_controller.js +10 -6
  112. package/dist/controllers/idle_controller.js.map +1 -1
  113. package/dist/controllers/input_mask_controller.d.ts +31 -13
  114. package/dist/controllers/input_mask_controller.js +434 -24
  115. package/dist/controllers/input_mask_controller.js.map +1 -1
  116. package/dist/controllers/intersection_controller.js +3 -0
  117. package/dist/controllers/intersection_controller.js.map +1 -1
  118. package/dist/controllers/lazy_frame_controller.d.ts +3 -2
  119. package/dist/controllers/lazy_frame_controller.js +15 -3
  120. package/dist/controllers/lazy_frame_controller.js.map +1 -1
  121. package/dist/controllers/listbox_controller.d.ts +10 -7
  122. package/dist/controllers/listbox_controller.js +260 -79
  123. package/dist/controllers/listbox_controller.js.map +1 -1
  124. package/dist/controllers/local_time_controller.d.ts +8 -6
  125. package/dist/controllers/local_time_controller.js +48 -13
  126. package/dist/controllers/local_time_controller.js.map +1 -1
  127. package/dist/controllers/masonry_controller.js +11 -4
  128. package/dist/controllers/masonry_controller.js.map +1 -1
  129. package/dist/controllers/menu_controller.d.ts +24 -5
  130. package/dist/controllers/menu_controller.js +138 -82
  131. package/dist/controllers/menu_controller.js.map +1 -1
  132. package/dist/controllers/menubar_controller.d.ts +49 -7
  133. package/dist/controllers/menubar_controller.js +65 -19
  134. package/dist/controllers/menubar_controller.js.map +1 -1
  135. package/dist/controllers/meter_controller.d.ts +13 -20
  136. package/dist/controllers/meter_controller.js +270 -24
  137. package/dist/controllers/meter_controller.js.map +1 -1
  138. package/dist/controllers/multi_select_controller.d.ts +19 -16
  139. package/dist/controllers/multi_select_controller.js +272 -95
  140. package/dist/controllers/multi_select_controller.js.map +1 -1
  141. package/dist/controllers/navigation_menu_controller.d.ts +19 -5
  142. package/dist/controllers/navigation_menu_controller.js +67 -19
  143. package/dist/controllers/navigation_menu_controller.js.map +1 -1
  144. package/dist/controllers/nested_form_controller.js +98 -64
  145. package/dist/controllers/nested_form_controller.js.map +1 -1
  146. package/dist/controllers/network_status_controller.js +70 -52
  147. package/dist/controllers/network_status_controller.js.map +1 -1
  148. package/dist/controllers/number_input_controller.d.ts +24 -6
  149. package/dist/controllers/number_input_controller.js +344 -94
  150. package/dist/controllers/number_input_controller.js.map +1 -1
  151. package/dist/controllers/optimistic_controller.d.ts +8 -5
  152. package/dist/controllers/optimistic_controller.js +29 -11
  153. package/dist/controllers/optimistic_controller.js.map +1 -1
  154. package/dist/controllers/otp_controller.d.ts +35 -4
  155. package/dist/controllers/otp_controller.js +502 -104
  156. package/dist/controllers/otp_controller.js.map +1 -1
  157. package/dist/controllers/overflow_indicator_controller.js +6 -0
  158. package/dist/controllers/overflow_indicator_controller.js.map +1 -1
  159. package/dist/controllers/overflow_menu_controller.d.ts +10 -9
  160. package/dist/controllers/overflow_menu_controller.js +136 -21
  161. package/dist/controllers/overflow_menu_controller.js.map +1 -1
  162. package/dist/controllers/pagination_controller.d.ts +3 -2
  163. package/dist/controllers/pagination_controller.js +47 -14
  164. package/dist/controllers/pagination_controller.js.map +1 -1
  165. package/dist/controllers/password_reveal_controller.d.ts +5 -4
  166. package/dist/controllers/password_reveal_controller.js +52 -49
  167. package/dist/controllers/password_reveal_controller.js.map +1 -1
  168. package/dist/controllers/password_strength_controller.d.ts +1 -1
  169. package/dist/controllers/password_strength_controller.js +13 -6
  170. package/dist/controllers/password_strength_controller.js.map +1 -1
  171. package/dist/controllers/persist_controller.js +48 -128
  172. package/dist/controllers/persist_controller.js.map +1 -1
  173. package/dist/controllers/pointer_drag_controller.d.ts +20 -8
  174. package/dist/controllers/pointer_drag_controller.js +255 -24
  175. package/dist/controllers/pointer_drag_controller.js.map +1 -1
  176. package/dist/controllers/popover_controller.d.ts +9 -5
  177. package/dist/controllers/popover_controller.js +91 -65
  178. package/dist/controllers/popover_controller.js.map +1 -1
  179. package/dist/controllers/portal_controller.js +6 -0
  180. package/dist/controllers/portal_controller.js.map +1 -1
  181. package/dist/controllers/preview_guard_controller.js +14 -3
  182. package/dist/controllers/preview_guard_controller.js.map +1 -1
  183. package/dist/controllers/progress_controller.d.ts +9 -19
  184. package/dist/controllers/progress_controller.js +271 -27
  185. package/dist/controllers/progress_controller.js.map +1 -1
  186. package/dist/controllers/radio_group_controller.d.ts +11 -8
  187. package/dist/controllers/radio_group_controller.js +167 -80
  188. package/dist/controllers/radio_group_controller.js.map +1 -1
  189. package/dist/controllers/range_slider_controller.d.ts +4 -3
  190. package/dist/controllers/range_slider_controller.js +27 -7
  191. package/dist/controllers/range_slider_controller.js.map +1 -1
  192. package/dist/controllers/rating_controller.js +93 -57
  193. package/dist/controllers/rating_controller.js.map +1 -1
  194. package/dist/controllers/read_more_controller.js +10 -6
  195. package/dist/controllers/read_more_controller.js.map +1 -1
  196. package/dist/controllers/reading_progress_controller.js +22 -5
  197. package/dist/controllers/reading_progress_controller.js.map +1 -1
  198. package/dist/controllers/relative_time_controller.d.ts +4 -4
  199. package/dist/controllers/relative_time_controller.js +75 -11
  200. package/dist/controllers/relative_time_controller.js.map +1 -1
  201. package/dist/controllers/reset_on_restore_controller.d.ts +3 -3
  202. package/dist/controllers/reset_on_restore_controller.js +6 -0
  203. package/dist/controllers/reset_on_restore_controller.js.map +1 -1
  204. package/dist/controllers/resizable_controller.d.ts +3 -0
  205. package/dist/controllers/resizable_controller.js +55 -22
  206. package/dist/controllers/resizable_controller.js.map +1 -1
  207. package/dist/controllers/roving_controller.d.ts +3 -3
  208. package/dist/controllers/roving_controller.js +10 -4
  209. package/dist/controllers/roving_controller.js.map +1 -1
  210. package/dist/controllers/scroll_area_controller.js +129 -88
  211. package/dist/controllers/scroll_area_controller.js.map +1 -1
  212. package/dist/controllers/scroll_restore_controller.d.ts +3 -3
  213. package/dist/controllers/scroll_restore_controller.js +14 -2
  214. package/dist/controllers/scroll_restore_controller.js.map +1 -1
  215. package/dist/controllers/scroll_visibility_controller.js +93 -60
  216. package/dist/controllers/scroll_visibility_controller.js.map +1 -1
  217. package/dist/controllers/scrollspy_controller.js +11 -5
  218. package/dist/controllers/scrollspy_controller.js.map +1 -1
  219. package/dist/controllers/separator_controller.d.ts +1 -1
  220. package/dist/controllers/separator_controller.js +59 -43
  221. package/dist/controllers/separator_controller.js.map +1 -1
  222. package/dist/controllers/sidebar_controller.d.ts +1 -1
  223. package/dist/controllers/sidebar_controller.js +150 -122
  224. package/dist/controllers/sidebar_controller.js.map +1 -1
  225. package/dist/controllers/skeleton_controller.js +55 -48
  226. package/dist/controllers/skeleton_controller.js.map +1 -1
  227. package/dist/controllers/slider_controller.d.ts +2 -1
  228. package/dist/controllers/slider_controller.js +27 -6
  229. package/dist/controllers/slider_controller.js.map +1 -1
  230. package/dist/controllers/smart_sticky_header_controller.d.ts +1 -1
  231. package/dist/controllers/smart_sticky_header_controller.js +13 -5
  232. package/dist/controllers/smart_sticky_header_controller.js.map +1 -1
  233. package/dist/controllers/sortable_controller.d.ts +4 -4
  234. package/dist/controllers/sortable_controller.js +27 -14
  235. package/dist/controllers/sortable_controller.js.map +1 -1
  236. package/dist/controllers/spinner_controller.js +55 -48
  237. package/dist/controllers/spinner_controller.js.map +1 -1
  238. package/dist/controllers/step_indicator_controller.d.ts +4 -4
  239. package/dist/controllers/step_indicator_controller.js +6 -0
  240. package/dist/controllers/step_indicator_controller.js.map +1 -1
  241. package/dist/controllers/stepper_controller.d.ts +2 -3
  242. package/dist/controllers/stepper_controller.js +6 -0
  243. package/dist/controllers/stepper_controller.js.map +1 -1
  244. package/dist/controllers/stick_to_bottom_controller.d.ts +3 -1
  245. package/dist/controllers/stick_to_bottom_controller.js +19 -8
  246. package/dist/controllers/stick_to_bottom_controller.js.map +1 -1
  247. package/dist/controllers/sticky_observer_controller.js +49 -43
  248. package/dist/controllers/sticky_observer_controller.js.map +1 -1
  249. package/dist/controllers/submit_once_controller.d.ts +2 -1
  250. package/dist/controllers/submit_once_controller.js +145 -85
  251. package/dist/controllers/submit_once_controller.js.map +1 -1
  252. package/dist/controllers/switch_controller.d.ts +7 -4
  253. package/dist/controllers/switch_controller.js +172 -28
  254. package/dist/controllers/switch_controller.js.map +1 -1
  255. package/dist/controllers/tabs_controller.d.ts +7 -4
  256. package/dist/controllers/tabs_controller.js +6 -1
  257. package/dist/controllers/tabs_controller.js.map +1 -1
  258. package/dist/controllers/tags_input_controller.d.ts +4 -3
  259. package/dist/controllers/tags_input_controller.js +157 -28
  260. package/dist/controllers/tags_input_controller.js.map +1 -1
  261. package/dist/controllers/textarea_autosize_controller.d.ts +1 -1
  262. package/dist/controllers/textarea_autosize_controller.js +40 -19
  263. package/dist/controllers/textarea_autosize_controller.js.map +1 -1
  264. package/dist/controllers/theme_controller.d.ts +3 -2
  265. package/dist/controllers/theme_controller.js +10 -4
  266. package/dist/controllers/theme_controller.js.map +1 -1
  267. package/dist/controllers/time_picker_controller.d.ts +38 -5
  268. package/dist/controllers/time_picker_controller.js +192 -54
  269. package/dist/controllers/time_picker_controller.js.map +1 -1
  270. package/dist/controllers/toast_controller.d.ts +4 -5
  271. package/dist/controllers/toast_controller.js +58 -27
  272. package/dist/controllers/toast_controller.js.map +1 -1
  273. package/dist/controllers/toggle_group_controller.d.ts +2 -3
  274. package/dist/controllers/toggle_group_controller.js +158 -56
  275. package/dist/controllers/toggle_group_controller.js.map +1 -1
  276. package/dist/controllers/toolbar_controller.d.ts +8 -6
  277. package/dist/controllers/toolbar_controller.js +150 -21
  278. package/dist/controllers/toolbar_controller.js.map +1 -1
  279. package/dist/controllers/tooltip_controller.d.ts +4 -1
  280. package/dist/controllers/tooltip_controller.js.map +1 -1
  281. package/dist/controllers/transition_controller.js.map +1 -1
  282. package/dist/controllers/tree_view_controller.d.ts +1 -1
  283. package/dist/controllers/tree_view_controller.js +134 -25
  284. package/dist/controllers/tree_view_controller.js.map +1 -1
  285. package/dist/index.d.ts +4 -1
  286. package/dist/index.js +2515 -1315
  287. package/dist/index.js.map +1 -1
  288. package/dist/inspector/cli.d.ts +25 -12
  289. package/dist/inspector/cli.js +21 -3
  290. package/dist/inspector/cli.js.map +1 -1
  291. package/dist/inspector/cli_bin.d.ts +1 -1
  292. package/dist/inspector/cli_bin.js +62 -8
  293. package/dist/inspector/cli_bin.js.map +1 -1
  294. package/dist/inspector/examples.json +13 -13
  295. package/dist/inspector/manifest.json +19 -5
  296. package/dist/positioning/index.d.ts +9 -8
  297. package/dist/positioning/index.js +6 -0
  298. package/dist/positioning/index.js.map +1 -1
  299. package/package.json +11 -10
@@ -1,19 +1,6 @@
1
1
  import { Controller } from '@hotwired/stimulus';
2
+ import { N as NumericValueEvent } from '../coerce-JtZVNG5h.js';
2
3
 
3
- /**
4
- * Event shape `setValue` accepts: an action param `amount` or a `detail.value`.
5
- * Both are typed `number | string` because, while Stimulus coerces numeric action
6
- * params to numbers, a `progress:set` CustomEvent (or a non-numeric-looking param)
7
- * may carry a string; {@link ProgressController.setValue} normalizes either form.
8
- */
9
- type SetValueEvent = Event & {
10
- params?: {
11
- amount?: number | string;
12
- };
13
- detail?: {
14
- value?: number | string;
15
- };
16
- };
17
4
  /**
18
5
  * Headless progress-bar behavior backed by the WAI-ARIA `progressbar` role.
19
6
  *
@@ -26,7 +13,7 @@ type SetValueEvent = Event & {
26
13
  * </div>
27
14
  *
28
15
  * This is the *progress over time* role (a task advancing toward completion),
29
- * deliberately distinct from {@link MeterController}'s point-in-time `meter`. The
16
+ * deliberately distinct from `stimeo--meter`'s point-in-time `meter`. The
30
17
  * controller owns value normalization and ARIA value-attribute synchronization;
31
18
  * the bar's width/animation is the consumer's, driven off the
32
19
  * `--stimeo--progress-ratio` (0–1) custom property and `data-state`.
@@ -36,8 +23,8 @@ type SetValueEvent = Event & {
36
23
  *
37
24
  * @remarks
38
25
  * Behavior only — no styling is emitted. An indeterminate bar drops
39
- * `aria-valuenow` (per ARIA) so assistive tech announces "busy" rather than a
40
- * stale value; the consumer animates the indeterminate look off
26
+ * `aria-valuenow` (per ARIA) so assistive tech treats the bar as indeterminate
27
+ * rather than reading a stale value; the consumer animates the indeterminate look off
41
28
  * `data-state="indeterminate"`.
42
29
  */
43
30
  declare class ProgressController extends Controller<HTMLElement> {
@@ -91,14 +78,17 @@ declare class ProgressController extends Controller<HTMLElement> {
91
78
  valueTextValue: string;
92
79
  announceTextValue: string;
93
80
  connect(): void;
94
- /** Closes the window in which a queued repaint may still run. */
81
+ /**
82
+ * Closes the window in which a queued repaint may still run, and returns
83
+ * `aria-valuetext` to the authored value unless the page wrote its own meanwhile.
84
+ */
95
85
  disconnect(): void;
96
86
  /**
97
87
  * Updates the progress value from an action param (`amount`) or a
98
88
  * `detail.value` CustomEvent, normalizes it into range, syncs ARIA, and
99
89
  * dispatches `change` (always) plus `complete` when `max` is reached.
100
90
  */
101
- setValue(event: SetValueEvent): void;
91
+ setValue(event: NumericValueEvent): void;
102
92
  /** Repaints when application code (or a Turbo morph) changes `indeterminate` at runtime. */
103
93
  indeterminateValueChanged(): void;
104
94
  /** Repaints when application code (or a Turbo morph) changes `value` at runtime. */
@@ -1,5 +1,12 @@
1
1
  import { Controller } from '@hotwired/stimulus';
2
2
 
3
+ function fillTemplate(template, values) {
4
+ return template.replace(/\{([a-zA-Z][a-zA-Z0-9]*)\}/g, (match, name) => {
5
+ const replacement = Object.hasOwn(values, name) ? values[name] : void 0;
6
+ return replacement === void 0 ? match : String(replacement);
7
+ });
8
+ }
9
+
3
10
  function announce(message, options = {}) {
4
11
  const text = message.trim();
5
12
  if (text.length === 0) return;
@@ -9,12 +16,6 @@ function announce(message, options = {}) {
9
16
  })
10
17
  );
11
18
  }
12
- function fillTemplate(template, values) {
13
- return template.replace(/\{([a-zA-Z][a-zA-Z0-9]*)\}/g, (match, name) => {
14
- const replacement = values[name];
15
- return replacement === void 0 ? match : String(replacement);
16
- });
17
- }
18
19
 
19
20
  var NUMBER_BOUNDS = {
20
21
  finite: { finite: true }};
@@ -32,6 +33,9 @@ function matchesNumberBounds(value, bounds) {
32
33
  return true;
33
34
  }
34
35
 
36
+ function eventNumber(event) {
37
+ return toFiniteNumber(event.params?.amount ?? event.detail?.value);
38
+ }
35
39
  function toFiniteNumber(raw) {
36
40
  if (typeof raw !== "number" && typeof raw !== "string") return null;
37
41
  if (typeof raw === "string" && raw.trim().length === 0) return null;
@@ -69,6 +73,9 @@ var MicrotaskCoalescer = class {
69
73
  this.#queued = false;
70
74
  this.#generation += 1;
71
75
  }
76
+ get pending() {
77
+ return this.#queued;
78
+ }
72
79
  schedule() {
73
80
  if (!this.#active || this.#queued) return;
74
81
  this.#queued = true;
@@ -99,6 +106,9 @@ var MorphRenderWatcher = class {
99
106
  schedule() {
100
107
  this.#pass.schedule();
101
108
  }
109
+ get pending() {
110
+ return this.#pass.pending;
111
+ }
102
112
  disconnect() {
103
113
  this.#listeners.dispose();
104
114
  this.#pass.cancel();
@@ -133,7 +143,7 @@ var NumberValueReader = class {
133
143
  function rangeFraction(value, min, max) {
134
144
  const span = max - min;
135
145
  if (!(span > 0)) return 0;
136
- const clamped = Math.min(max, Math.max(min, value));
146
+ const clamped = clampRange(value, min, max);
137
147
  let fraction;
138
148
  if (Number.isFinite(span)) {
139
149
  fraction = (clamped - min) / span;
@@ -144,13 +154,254 @@ function rangeFraction(value, min, max) {
144
154
  if (!Number.isFinite(fraction)) return 0;
145
155
  return Math.min(1, Math.max(0, fraction));
146
156
  }
157
+ function clampRange(value, min, max) {
158
+ return Math.min(max, Math.max(min, value));
159
+ }
160
+
161
+ function setAttributeIfChanged(element, name, value, beforeWrite) {
162
+ if (element.getAttribute(name) === value) return false;
163
+ if (value === null) element.removeAttribute(name);
164
+ else element.setAttribute(name, value);
165
+ return true;
166
+ }
167
+
168
+ function sharedRegistry(key, create) {
169
+ const symbol = Symbol.for(key);
170
+ const scope = globalThis;
171
+ const existing = scope[symbol];
172
+ if (existing !== void 0) return existing;
173
+ const registry2 = create();
174
+ Object.defineProperty(globalThis, symbol, { value: registry2 });
175
+ return registry2;
176
+ }
177
+
178
+ var registry = sharedRegistry(
179
+ "stimeo-ui.attribute-lease.registry.v1",
180
+ () => ({ stacks: /* @__PURE__ */ new WeakMap(), names: /* @__PURE__ */ new Map() })
181
+ );
182
+ function isAttributeValue(value) {
183
+ return value === null || typeof value === "string";
184
+ }
185
+ function readLeaseRecord(element, record) {
186
+ try {
187
+ const parsed = JSON.parse(element.getAttribute(record) ?? "null");
188
+ if (!Array.isArray(parsed)) return void 0;
189
+ const [original, written, ...rest] = parsed;
190
+ const linked = rest[0] !== false;
191
+ const beneath = linked ? rest : rest.slice(1);
192
+ if (!beneath.every((under) => typeof under === "string")) return void 0;
193
+ return isAttributeValue(original) && isAttributeValue(written) ? { original, written, linked, beneath } : void 0;
194
+ } catch {
195
+ return void 0;
196
+ }
197
+ }
198
+ function attributeStack(element, attribute) {
199
+ const byAttribute = registry.stacks.get(element) ?? /* @__PURE__ */ new Map();
200
+ registry.stacks.set(element, byAttribute);
201
+ const known = byAttribute.get(attribute);
202
+ if (known) return known;
203
+ const found = [];
204
+ for (const record of registry.names.get(attribute) ?? []) {
205
+ const read = readLeaseRecord(element, record);
206
+ if (read) found.push({ ...read, record });
207
+ }
208
+ const depth = ({ beneath }) => beneath.filter((name) => found.some((other) => other.record === name)).length;
209
+ const stack = found.sort((one, other) => depth(one) - depth(other)).map(({ record, written, original, linked }, index) => ({
210
+ lease: null,
211
+ record,
212
+ written,
213
+ original,
214
+ linked: linked && index > 0
215
+ }));
216
+ byAttribute.set(attribute, stack);
217
+ return stack;
218
+ }
219
+ function findHold(stack, lease, record) {
220
+ return stack.find((held) => held.lease === lease) ?? stack.find((held) => held.lease === null && held.record === record);
221
+ }
222
+ function readAttributeLease(element, attribute, owner, lease, expected) {
223
+ const stack = attributeStack(element, attribute);
224
+ const hold = findHold(stack, lease, `data-${owner}-${attribute}-lease`);
225
+ const current = element.getAttribute(attribute);
226
+ const covering = [...stack].reverse().find((other) => other.written === current);
227
+ const original = (hold ?? covering)?.original;
228
+ const authored = original === void 0 ? current : original;
229
+ return {
230
+ original: authored,
231
+ allowed: hold ? current === hold.written || stack.slice(stack.indexOf(hold) + 1).some((above) => above.written === current) : authored === expected
232
+ };
233
+ }
234
+ var AttributeLease = class {
235
+ #attribute;
236
+ #record;
237
+ #base;
238
+ #preserveAuthor;
239
+ #held = /* @__PURE__ */ new Set();
240
+ constructor(attribute, owner, options = {}) {
241
+ this.#attribute = attribute;
242
+ this.#record = `data-${owner}-${attribute}-lease`;
243
+ this.#base = options.base === true;
244
+ this.#preserveAuthor = options.preserveAuthor === true;
245
+ const names = registry.names;
246
+ names.set(attribute, (names.get(attribute) ?? /* @__PURE__ */ new Set()).add(this.#record));
247
+ }
248
+ write(element, value) {
249
+ const stack = attributeStack(element, this.#attribute);
250
+ const hold = this.#take(stack) ?? this.#acquire(element, stack);
251
+ this.#held.add(element);
252
+ const shows = !this.#covered(element, stack, hold);
253
+ hold.written = value;
254
+ this.#mark(element, stack);
255
+ if (shows) this.#reflect(element, value);
256
+ }
257
+ return(element) {
258
+ const held = this.#held.delete(element);
259
+ const known = registry.stacks.get(element)?.has(this.#attribute);
260
+ const stack = held || known || element.hasAttribute(this.#record) ? attributeStack(element, this.#attribute) : [];
261
+ const hold = this.#take(stack);
262
+ if (!hold) return false;
263
+ const carries = element.getAttribute(this.#attribute) === hold.written;
264
+ const owns = carries && !this.#covered(element, stack, hold);
265
+ const index = stack.indexOf(hold);
266
+ stack.splice(index, 1);
267
+ const above = stack[index];
268
+ if (above) above.linked &&= hold.linked;
269
+ this.#mark(element, stack);
270
+ if (!owns) return true;
271
+ const below = hold.linked ? stack[index - 1] : void 0;
272
+ this.#reflect(element, below ? below.written : hold.original);
273
+ return true;
274
+ }
275
+ returnAll() {
276
+ for (const element of Array.from(this.#held)) this.return(element);
277
+ }
278
+ #take(stack) {
279
+ const hold = findHold(stack, this, this.#record);
280
+ if (hold) hold.lease = this;
281
+ return hold;
282
+ }
283
+ #acquire(element, stack) {
284
+ const current = element.getAttribute(this.#attribute);
285
+ const top = stack.at(-1);
286
+ const bottom = stack[0];
287
+ const over = top?.written === current ? top : void 0;
288
+ const from = this.#base ? this.#preserveAuthor && !stack.some((held) => held.written === current) ? void 0 : bottom : over;
289
+ const hold = {
290
+ lease: this,
291
+ record: this.#record,
292
+ written: current,
293
+ original: from ? from.original : current,
294
+ linked: !this.#base && over !== void 0
295
+ };
296
+ if (this.#base && bottom) {
297
+ bottom.linked = true;
298
+ stack.unshift(hold);
299
+ } else stack.push(hold);
300
+ return hold;
301
+ }
302
+ #covered(element, stack, hold) {
303
+ const current = element.getAttribute(this.#attribute);
304
+ return stack.slice(stack.indexOf(hold) + 1).some((above) => above.written === current);
305
+ }
306
+ #mark(element, stack) {
307
+ const records = /* @__PURE__ */ new Map([[this.#record, null]]);
308
+ stack.forEach((hold, index) => {
309
+ const names = stack.slice(0, index).map((under) => under.record);
310
+ const beneath = [...new Set(names.reverse())].filter((name) => name !== hold.record);
311
+ const marker = hold.linked || beneath.length === 0 ? [] : [false];
312
+ records.set(
313
+ hold.record,
314
+ hold.written === hold.original && beneath.length === 0 && index === stack.length - 1 ? null : JSON.stringify([hold.original, hold.written, ...marker, ...beneath])
315
+ );
316
+ });
317
+ for (const [name, recorded] of records) {
318
+ setAttributeIfChanged(element, name, recorded);
319
+ }
320
+ }
321
+ #reflect(element, value) {
322
+ setAttributeIfChanged(element, this.#attribute, value);
323
+ }
324
+ };
325
+
326
+ var TemplateAttributeLease = class {
327
+ #lease;
328
+ #record;
329
+ #attribute;
330
+ #owner;
331
+ #states = /* @__PURE__ */ new WeakMap();
332
+ constructor(attribute, owner) {
333
+ this.#attribute = attribute;
334
+ this.#owner = owner;
335
+ this.#lease = new AttributeLease(attribute, owner, { base: true, preserveAuthor: true });
336
+ this.#record = `data-${owner}-${attribute}-template`;
337
+ }
338
+ render(element, source, value) {
339
+ let state = this.#read(element);
340
+ if (!state && source.length === 0) {
341
+ this.#lease.return(element);
342
+ return;
343
+ }
344
+ if (!state || state.source !== source) {
345
+ this.#lease.return(element);
346
+ state = { source, expected: this.#view(element, null).original, yielded: false };
347
+ }
348
+ if (source.length === 0 || value === null) {
349
+ this.#states.set(element, state);
350
+ this.release(element);
351
+ return;
352
+ }
353
+ if (!state.yielded && this.#continues(element, state)) {
354
+ this.#lease.write(element, value);
355
+ state.expected = value;
356
+ } else {
357
+ state.yielded = true;
358
+ this.#lease.return(element);
359
+ }
360
+ this.#mark(element, state);
361
+ }
362
+ release(element) {
363
+ const state = this.#read(element);
364
+ if (state && !state.yielded) {
365
+ state.yielded = !this.#continues(element, state);
366
+ if (!state.yielded) state.expected = this.#view(element, null).original;
367
+ }
368
+ this.#lease.return(element);
369
+ if (state) this.#mark(element, state);
370
+ }
371
+ #continues(element, state) {
372
+ const view = this.#view(element, state.expected);
373
+ return view.allowed || !element.hasAttribute(this.#record) && element.getAttribute(this.#attribute) === view.original;
374
+ }
375
+ #view(element, expected) {
376
+ return readAttributeLease(element, this.#attribute, this.#owner, this.#lease, expected);
377
+ }
378
+ #read(element) {
379
+ const live = this.#states.get(element);
380
+ if (live) return live;
381
+ try {
382
+ const parsed = JSON.parse(element.getAttribute(this.#record) ?? "null");
383
+ if (!Array.isArray(parsed) || parsed.length !== 3) return void 0;
384
+ const [source, expected, yielded] = parsed;
385
+ if (typeof source !== "string" || expected !== null && typeof expected !== "string" || typeof yielded !== "boolean")
386
+ return void 0;
387
+ return { source, expected, yielded };
388
+ } catch {
389
+ return void 0;
390
+ }
391
+ }
392
+ #mark(element, state) {
393
+ this.#states.set(element, state);
394
+ setAttributeIfChanged(
395
+ element,
396
+ this.#record,
397
+ JSON.stringify([state.source, state.expected, state.yielded])
398
+ );
399
+ }
400
+ };
147
401
 
148
- var OWNED_VALUE_TEXT = "owns-valuetext";
149
402
  var ProgressController = class _ProgressController extends Controller {
150
403
  #numbers = new NumberValueReader();
151
- get #ownedValueText() {
152
- return `data-${this.identifier}-${OWNED_VALUE_TEXT}`;
153
- }
404
+ #valueText = new TemplateAttributeLease("aria-valuetext", this.identifier);
154
405
  static targets = ["bar"];
155
406
  static values = {
156
407
  value: { type: Number, default: 0 },
@@ -176,9 +427,10 @@ var ProgressController = class _ProgressController extends Controller {
176
427
  }
177
428
  disconnect() {
178
429
  this.#repaint.disconnect();
430
+ this.#valueText.release(this.element);
179
431
  }
180
432
  setValue(event) {
181
- const next = toFiniteNumber(event.params?.amount ?? event.detail?.value);
433
+ const next = eventNumber(event);
182
434
  if (next === null) return;
183
435
  const value = this.#clamp(next);
184
436
  this.valueValue = value;
@@ -208,7 +460,7 @@ var ProgressController = class _ProgressController extends Controller {
208
460
  this.#repaint.schedule();
209
461
  }
210
462
  #clamp(raw) {
211
- return Math.min(this.#safeMax, Math.max(this.#safeMin, raw));
463
+ return clampRange(raw, this.#safeMin, this.#safeMax);
212
464
  }
213
465
  get #ratio() {
214
466
  return rangeFraction(this.#safeValue, this.#safeMin, this.#safeMax);
@@ -218,7 +470,7 @@ var ProgressController = class _ProgressController extends Controller {
218
470
  this.element.setAttribute("aria-valuemax", String(this.#safeMax));
219
471
  if (this.indeterminateValue) {
220
472
  this.element.removeAttribute("aria-valuenow");
221
- this.#clearOwnValueText();
473
+ this.#valueText.render(this.element, this.valueTextValue, null);
222
474
  this.element.style.removeProperty("--stimeo--progress-ratio");
223
475
  this.element.setAttribute("data-state", "indeterminate");
224
476
  return;
@@ -230,19 +482,11 @@ var ProgressController = class _ProgressController extends Controller {
230
482
  this.#applyValueText(value);
231
483
  }
232
484
  #applyValueText(value) {
233
- if (this.valueTextValue.length === 0) {
234
- this.#clearOwnValueText();
235
- return;
236
- }
237
- const percent = Math.round(this.#ratio * 100);
238
- const text = this.valueTextValue.replaceAll("{value}", String(value)).replaceAll("{percent}", String(percent));
239
- this.element.setAttribute("aria-valuetext", text);
240
- this.element.setAttribute(this.#ownedValueText, "");
241
- }
242
- #clearOwnValueText() {
243
- if (!this.element.hasAttribute(this.#ownedValueText)) return;
244
- this.element.removeAttribute("aria-valuetext");
245
- this.element.removeAttribute(this.#ownedValueText);
485
+ this.#valueText.render(
486
+ this.element,
487
+ this.valueTextValue,
488
+ fillTemplate(this.valueTextValue, { value, percent: Math.round(this.#ratio * 100) })
489
+ );
246
490
  }
247
491
  get #safeValue() {
248
492
  return this.#numbers.read(