@adia-ai/web-components 0.4.6 → 0.4.8

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 (399) hide show
  1. package/README.md +39 -0
  2. package/USAGE.md +29 -9
  3. package/components/accordion/accordion.a2ui.json +3 -0
  4. package/components/accordion/accordion.d.ts +27 -0
  5. package/components/accordion/accordion.js +10 -117
  6. package/components/accordion/accordion.yaml +4 -0
  7. package/components/accordion/class.js +132 -0
  8. package/components/action-list/action-list.a2ui.json +3 -0
  9. package/components/action-list/action-list.d.ts +25 -0
  10. package/components/action-list/action-list.js +9 -140
  11. package/components/action-list/action-list.yaml +4 -0
  12. package/components/action-list/class.js +156 -0
  13. package/components/agent-artifact/agent-artifact.a2ui.json +4 -0
  14. package/components/agent-artifact/agent-artifact.d.ts +35 -0
  15. package/components/agent-artifact/agent-artifact.js +8 -181
  16. package/components/agent-artifact/agent-artifact.yaml +5 -0
  17. package/components/agent-artifact/class.js +200 -0
  18. package/components/agent-feedback-bar/agent-feedback-bar.a2ui.json +3 -0
  19. package/components/agent-feedback-bar/agent-feedback-bar.d.ts +33 -0
  20. package/components/agent-feedback-bar/agent-feedback-bar.js +8 -143
  21. package/components/agent-feedback-bar/agent-feedback-bar.yaml +4 -0
  22. package/components/agent-feedback-bar/class.js +162 -0
  23. package/components/agent-questions/agent-questions.a2ui.json +3 -0
  24. package/components/agent-questions/agent-questions.d.ts +33 -0
  25. package/components/agent-questions/agent-questions.js +8 -180
  26. package/components/agent-questions/agent-questions.yaml +4 -0
  27. package/components/agent-questions/class.js +199 -0
  28. package/components/agent-reasoning/agent-reasoning.a2ui.json +4 -0
  29. package/components/agent-reasoning/agent-reasoning.d.ts +37 -0
  30. package/components/agent-reasoning/agent-reasoning.js +8 -494
  31. package/components/agent-reasoning/agent-reasoning.yaml +5 -0
  32. package/components/agent-reasoning/class.js +513 -0
  33. package/components/agent-suggestions/agent-suggestions.a2ui.json +3 -0
  34. package/components/agent-suggestions/agent-suggestions.d.ts +31 -0
  35. package/components/agent-suggestions/agent-suggestions.js +8 -78
  36. package/components/agent-suggestions/agent-suggestions.yaml +4 -0
  37. package/components/agent-suggestions/class.js +97 -0
  38. package/components/agent-trace/agent-trace.a2ui.json +1 -0
  39. package/components/agent-trace/agent-trace.d.ts +29 -0
  40. package/components/alert/alert.a2ui.json +1 -0
  41. package/components/alert/alert.d.ts +39 -0
  42. package/components/alert/alert.js +8 -175
  43. package/components/alert/class.js +194 -0
  44. package/components/aside/aside.a2ui.json +1 -0
  45. package/components/avatar/avatar.a2ui.json +3 -0
  46. package/components/avatar/avatar.d.ts +28 -0
  47. package/components/avatar/avatar.js +9 -159
  48. package/components/avatar/avatar.yaml +4 -0
  49. package/components/avatar/class.js +173 -0
  50. package/components/badge/badge.a2ui.json +3 -0
  51. package/components/badge/badge.d.ts +28 -0
  52. package/components/badge/badge.js +9 -75
  53. package/components/badge/badge.yaml +4 -0
  54. package/components/badge/class.js +93 -0
  55. package/components/block/block.a2ui.json +1 -0
  56. package/components/block/block.d.ts +20 -0
  57. package/components/block/block.js +9 -15
  58. package/components/block/class.js +33 -0
  59. package/components/breadcrumb/breadcrumb.a2ui.json +5 -0
  60. package/components/breadcrumb/breadcrumb.d.ts +24 -0
  61. package/components/breadcrumb/breadcrumb.js +8 -113
  62. package/components/breadcrumb/breadcrumb.yaml +6 -0
  63. package/components/breadcrumb/class.js +132 -0
  64. package/components/button/button.a2ui.json +3 -0
  65. package/components/button/button.d.ts +44 -0
  66. package/components/button/button.js +15 -66
  67. package/components/button/button.yaml +5 -0
  68. package/components/button/class.js +80 -0
  69. package/components/calendar-picker/calendar-picker.a2ui.json +7 -1
  70. package/components/calendar-picker/calendar-picker.js +8 -332
  71. package/components/calendar-picker/calendar-picker.yaml +51 -177
  72. package/components/calendar-picker/class.js +351 -0
  73. package/components/canvas/canvas.a2ui.json +7 -1
  74. package/components/canvas/canvas.d.ts +33 -0
  75. package/components/canvas/canvas.yaml +29 -36
  76. package/components/card/card.a2ui.json +4 -0
  77. package/components/card/card.d.ts +37 -0
  78. package/components/card/card.js +9 -50
  79. package/components/card/card.yaml +171 -433
  80. package/components/card/class.js +68 -0
  81. package/components/chart/chart.a2ui.json +1 -0
  82. package/components/chart/chart.d.ts +55 -0
  83. package/components/chart/chart.js +8 -2131
  84. package/components/chart/class.js +2150 -0
  85. package/components/chart-legend/chart-legend.a2ui.json +4 -0
  86. package/components/chart-legend/chart-legend.d.ts +37 -0
  87. package/components/chart-legend/chart-legend.js +8 -197
  88. package/components/chart-legend/chart-legend.yaml +5 -0
  89. package/components/chart-legend/class.js +215 -0
  90. package/components/chat-thread/chat-thread.a2ui.json +1 -0
  91. package/components/chat-thread/chat-thread.d.ts +27 -0
  92. package/components/chat-thread/chat-thread.js +8 -157
  93. package/components/chat-thread/class.js +176 -0
  94. package/components/check/check.a2ui.json +1 -0
  95. package/components/check/check.js +11 -52
  96. package/components/check/class.js +68 -0
  97. package/components/code/class.js +501 -0
  98. package/components/code/code.a2ui.json +1 -0
  99. package/components/code/code.js +8 -482
  100. package/components/col/class.js +30 -0
  101. package/components/col/col.a2ui.json +1 -0
  102. package/components/col/col.d.ts +24 -0
  103. package/components/col/col.js +10 -13
  104. package/components/color-picker/class.js +550 -0
  105. package/components/color-picker/color-picker.a2ui.json +3 -0
  106. package/components/color-picker/color-picker.js +8 -531
  107. package/components/color-picker/color-picker.yaml +4 -0
  108. package/components/command/class.js +364 -0
  109. package/components/command/command.a2ui.json +4 -0
  110. package/components/command/command.d.ts +31 -0
  111. package/components/command/command.js +8 -345
  112. package/components/command/command.yaml +105 -124
  113. package/components/demo-toggle/class.js +153 -0
  114. package/components/demo-toggle/demo-toggle.a2ui.json +1 -0
  115. package/components/demo-toggle/demo-toggle.d.ts +33 -0
  116. package/components/demo-toggle/demo-toggle.js +8 -135
  117. package/components/description-list/class.js +86 -0
  118. package/components/description-list/description-list.a2ui.json +1 -0
  119. package/components/description-list/description-list.d.ts +22 -0
  120. package/components/description-list/description-list.js +8 -67
  121. package/components/divider/class.js +57 -0
  122. package/components/divider/divider.a2ui.json +1 -0
  123. package/components/divider/divider.d.ts +20 -0
  124. package/components/divider/divider.js +10 -40
  125. package/components/drawer/class.js +306 -0
  126. package/components/drawer/drawer.a2ui.json +1 -0
  127. package/components/drawer/drawer.d.ts +35 -0
  128. package/components/drawer/drawer.js +8 -287
  129. package/components/embed/class.js +73 -0
  130. package/components/embed/embed.a2ui.json +1 -0
  131. package/components/embed/embed.d.ts +24 -0
  132. package/components/embed/embed.js +9 -55
  133. package/components/empty-state/class.js +108 -0
  134. package/components/empty-state/empty-state.a2ui.json +3 -0
  135. package/components/empty-state/empty-state.d.ts +22 -0
  136. package/components/empty-state/empty-state.js +9 -90
  137. package/components/empty-state/empty-state.yaml +4 -0
  138. package/components/feed/class.js +381 -0
  139. package/components/feed/feed.a2ui.json +9 -1
  140. package/components/feed/feed.d.ts +29 -0
  141. package/components/feed/feed.js +9 -367
  142. package/components/feed/feed.yaml +8 -1
  143. package/components/field/class.js +266 -0
  144. package/components/field/field.a2ui.json +1 -0
  145. package/components/field/field.d.ts +24 -0
  146. package/components/field/field.js +8 -247
  147. package/components/fields/class.js +106 -0
  148. package/components/fields/fields.a2ui.json +1 -0
  149. package/components/fields/fields.d.ts +20 -0
  150. package/components/fields/fields.js +8 -87
  151. package/components/footer/footer.a2ui.json +1 -0
  152. package/components/grid/class.js +31 -0
  153. package/components/grid/grid.a2ui.json +1 -0
  154. package/components/grid/grid.d.ts +24 -0
  155. package/components/grid/grid.js +10 -14
  156. package/components/header/header.a2ui.json +1 -0
  157. package/components/heatmap/class.js +305 -0
  158. package/components/heatmap/heatmap.a2ui.json +1 -0
  159. package/components/heatmap/heatmap.d.ts +43 -0
  160. package/components/heatmap/heatmap.js +8 -286
  161. package/components/icon/class.js +54 -0
  162. package/components/icon/icon.a2ui.json +1 -0
  163. package/components/icon/icon.d.ts +24 -0
  164. package/components/icon/icon.js +13 -40
  165. package/components/image/class.js +112 -0
  166. package/components/image/image.a2ui.json +3 -0
  167. package/components/image/image.d.ts +34 -0
  168. package/components/image/image.js +9 -94
  169. package/components/image/image.yaml +4 -0
  170. package/components/index.js +8 -0
  171. package/components/input/class.js +773 -0
  172. package/components/input/input.a2ui.json +7 -0
  173. package/components/input/input.js +8 -755
  174. package/components/input/input.yaml +177 -442
  175. package/components/inspector/class.js +142 -0
  176. package/components/inspector/inspector.a2ui.json +13 -1
  177. package/components/inspector/inspector.d.ts +18 -0
  178. package/components/inspector/inspector.js +8 -124
  179. package/components/inspector/inspector.yaml +21 -30
  180. package/components/kbd/class.js +34 -0
  181. package/components/kbd/kbd.a2ui.json +4 -0
  182. package/components/kbd/kbd.d.ts +18 -0
  183. package/components/kbd/kbd.js +10 -17
  184. package/components/kbd/kbd.yaml +54 -185
  185. package/components/link/class.js +187 -0
  186. package/components/link/link.a2ui.json +1 -0
  187. package/components/link/link.d.ts +65 -0
  188. package/components/link/link.js +8 -168
  189. package/components/list/class.js +249 -0
  190. package/components/list/list.a2ui.json +3 -0
  191. package/components/list/list.d.ts +33 -0
  192. package/components/list/list.js +9 -231
  193. package/components/list/list.yaml +4 -0
  194. package/components/menu/class.js +332 -0
  195. package/components/menu/menu.a2ui.json +3 -0
  196. package/components/menu/menu.d.ts +31 -0
  197. package/components/menu/menu.js +11 -316
  198. package/components/menu/menu.yaml +4 -0
  199. package/components/modal/class.js +231 -0
  200. package/components/modal/modal.a2ui.json +6 -1
  201. package/components/modal/modal.d.ts +33 -0
  202. package/components/modal/modal.js +8 -212
  203. package/components/modal/modal.yaml +19 -39
  204. package/components/nav/class.js +150 -0
  205. package/components/nav/nav.a2ui.json +1 -0
  206. package/components/nav/nav.d.ts +41 -0
  207. package/components/nav/nav.js +8 -131
  208. package/components/nav-group/class.js +152 -0
  209. package/components/nav-group/nav-group.a2ui.json +1 -0
  210. package/components/nav-group/nav-group.d.ts +45 -0
  211. package/components/nav-group/nav-group.js +9 -134
  212. package/components/nav-item/class.js +86 -0
  213. package/components/nav-item/nav-item.a2ui.json +1 -0
  214. package/components/nav-item/nav-item.d.ts +47 -0
  215. package/components/nav-item/nav-item.js +10 -69
  216. package/components/noodles/class.js +510 -0
  217. package/components/noodles/noodles.a2ui.json +1 -0
  218. package/components/noodles/noodles.d.ts +47 -0
  219. package/components/noodles/noodles.js +9 -493
  220. package/components/option-card/class.js +167 -0
  221. package/components/option-card/option-card.a2ui.json +3 -0
  222. package/components/option-card/option-card.js +8 -149
  223. package/components/option-card/option-card.yaml +4 -0
  224. package/components/otp-input/class.js +180 -0
  225. package/components/otp-input/otp-input.a2ui.json +6 -1
  226. package/components/otp-input/otp-input.js +9 -162
  227. package/components/otp-input/otp-input.yaml +45 -174
  228. package/components/page/class.js +97 -0
  229. package/components/page/page.a2ui.json +1 -0
  230. package/components/page/page.d.ts +47 -0
  231. package/components/page/page.js +8 -79
  232. package/components/pagination/class.js +195 -0
  233. package/components/pagination/pagination.a2ui.json +1 -0
  234. package/components/pagination/pagination.d.ts +33 -0
  235. package/components/pagination/pagination.js +9 -177
  236. package/components/pane/class.js +186 -0
  237. package/components/pane/pane.a2ui.json +20 -2
  238. package/components/pane/pane.d.ts +41 -0
  239. package/components/pane/pane.js +8 -167
  240. package/components/pane/pane.yaml +64 -158
  241. package/components/pipeline-status/class.js +189 -0
  242. package/components/pipeline-status/pipeline-status.a2ui.json +8 -1
  243. package/components/pipeline-status/pipeline-status.d.ts +22 -0
  244. package/components/pipeline-status/pipeline-status.js +9 -172
  245. package/components/pipeline-status/pipeline-status.yaml +34 -72
  246. package/components/popover/class.js +194 -0
  247. package/components/popover/popover.a2ui.json +1 -0
  248. package/components/popover/popover.d.ts +24 -0
  249. package/components/popover/popover.js +9 -176
  250. package/components/progress/class.js +74 -0
  251. package/components/progress/progress.a2ui.json +4 -0
  252. package/components/progress/progress.d.ts +20 -0
  253. package/components/progress/progress.js +10 -57
  254. package/components/progress/progress.yaml +124 -287
  255. package/components/progress-row/class.js +110 -0
  256. package/components/progress-row/progress-row.a2ui.json +3 -0
  257. package/components/progress-row/progress-row.d.ts +24 -0
  258. package/components/progress-row/progress-row.js +8 -92
  259. package/components/progress-row/progress-row.yaml +4 -0
  260. package/components/radio/class.js +83 -0
  261. package/components/radio/radio.a2ui.json +1 -0
  262. package/components/radio/radio.js +11 -67
  263. package/components/range/class.js +194 -0
  264. package/components/range/range.a2ui.json +1 -0
  265. package/components/range/range.js +9 -176
  266. package/components/rating/class.js +148 -0
  267. package/components/rating/rating.a2ui.json +1 -0
  268. package/components/rating/rating.js +9 -130
  269. package/components/richtext/class.js +87 -0
  270. package/components/richtext/richtext.a2ui.json +8 -1
  271. package/components/richtext/richtext.d.ts +20 -0
  272. package/components/richtext/richtext.js +8 -68
  273. package/components/richtext/richtext.yaml +30 -65
  274. package/components/row/class.js +50 -0
  275. package/components/row/row.a2ui.json +1 -0
  276. package/components/row/row.d.ts +37 -0
  277. package/components/row/row.js +10 -33
  278. package/components/search/class.js +134 -0
  279. package/components/search/search.a2ui.json +1 -0
  280. package/components/search/search.js +10 -117
  281. package/components/section/section.a2ui.json +1 -0
  282. package/components/segment/class.js +62 -0
  283. package/components/segment/segment.a2ui.json +3 -0
  284. package/components/segment/segment.d.ts +26 -0
  285. package/components/segment/segment.js +10 -45
  286. package/components/segment/segment.yaml +4 -0
  287. package/components/segmented/class.js +165 -0
  288. package/components/segmented/segmented.a2ui.json +5 -0
  289. package/components/segmented/segmented.js +10 -148
  290. package/components/segmented/segmented.yaml +41 -59
  291. package/components/select/class.js +408 -0
  292. package/components/select/select.a2ui.json +3 -0
  293. package/components/select/select.js +15 -396
  294. package/components/select/select.yaml +4 -0
  295. package/components/skeleton/class.js +52 -0
  296. package/components/skeleton/skeleton.a2ui.json +1 -0
  297. package/components/skeleton/skeleton.d.ts +24 -0
  298. package/components/skeleton/skeleton.js +8 -34
  299. package/components/slider/class.js +184 -0
  300. package/components/slider/slider.a2ui.json +1 -0
  301. package/components/slider/slider.js +9 -166
  302. package/components/stack/class.js +28 -0
  303. package/components/stack/stack.a2ui.json +1 -0
  304. package/components/stack/stack.d.ts +18 -0
  305. package/components/stack/stack.js +10 -11
  306. package/components/stat/stat.a2ui.json +1 -0
  307. package/components/step-progress/class.js +98 -0
  308. package/components/step-progress/step-progress.a2ui.json +1 -0
  309. package/components/step-progress/step-progress.d.ts +28 -0
  310. package/components/step-progress/step-progress.js +8 -79
  311. package/components/stepper/class.js +126 -0
  312. package/components/stepper/stepper.a2ui.json +3 -0
  313. package/components/stepper/stepper.d.ts +20 -0
  314. package/components/stepper/stepper.js +9 -112
  315. package/components/stepper/stepper.yaml +4 -0
  316. package/components/stream/class.js +109 -0
  317. package/components/stream/stream.a2ui.json +1 -0
  318. package/components/stream/stream.d.ts +33 -0
  319. package/components/stream/stream.js +8 -90
  320. package/components/swatch/class.js +131 -0
  321. package/components/swatch/swatch.a2ui.json +1 -0
  322. package/components/swatch/swatch.d.ts +29 -0
  323. package/components/swatch/swatch.js +8 -112
  324. package/components/swiper/class.js +373 -0
  325. package/components/swiper/swiper.a2ui.json +7 -0
  326. package/components/swiper/swiper.d.ts +45 -0
  327. package/components/swiper/swiper.js +8 -354
  328. package/components/swiper/swiper.yaml +72 -212
  329. package/components/switch/class.js +63 -0
  330. package/components/switch/switch.a2ui.json +7 -1
  331. package/components/switch/switch.js +11 -47
  332. package/components/switch/switch.yaml +70 -265
  333. package/components/table/class.js +1453 -0
  334. package/components/table/table.a2ui.json +7 -0
  335. package/components/table/table.d.ts +55 -0
  336. package/components/table/table.js +8 -1435
  337. package/components/table/table.yaml +8 -0
  338. package/components/table-toolbar/class.js +680 -0
  339. package/components/table-toolbar/table-toolbar.a2ui.json +12 -0
  340. package/components/table-toolbar/table-toolbar.d.ts +49 -0
  341. package/components/table-toolbar/table-toolbar.js +8 -689
  342. package/components/table-toolbar/table-toolbar.yaml +13 -0
  343. package/components/tabs/class.js +242 -0
  344. package/components/tabs/tabs.a2ui.json +3 -0
  345. package/components/tabs/tabs.d.ts +31 -0
  346. package/components/tabs/tabs.js +8 -223
  347. package/components/tabs/tabs.yaml +4 -0
  348. package/components/tag/class.js +99 -0
  349. package/components/tag/tag.a2ui.json +1 -0
  350. package/components/tag/tag.d.ts +37 -0
  351. package/components/tag/tag.js +8 -80
  352. package/components/text/class.js +46 -0
  353. package/components/text/text.a2ui.json +1 -0
  354. package/components/text/text.d.ts +26 -0
  355. package/components/text/text.js +9 -28
  356. package/components/textarea/class.js +134 -0
  357. package/components/textarea/textarea.a2ui.json +1 -0
  358. package/components/textarea/textarea.js +11 -118
  359. package/components/timeline/class.js +176 -0
  360. package/components/timeline/timeline.a2ui.json +18 -1
  361. package/components/timeline/timeline.d.ts +36 -0
  362. package/components/timeline/timeline.js +9 -162
  363. package/components/timeline/timeline.yaml +14 -1
  364. package/components/toast/class.js +92 -0
  365. package/components/toast/toast.a2ui.json +1 -0
  366. package/components/toast/toast.d.ts +33 -0
  367. package/components/toast/toast.js +9 -76
  368. package/components/toggle-group/class.js +154 -0
  369. package/components/toggle-group/toggle-group.a2ui.json +1 -0
  370. package/components/toggle-group/toggle-group.d.ts +29 -0
  371. package/components/toggle-group/toggle-group.js +11 -140
  372. package/components/toggle-scheme/class.js +286 -0
  373. package/components/toggle-scheme/toggle-scheme.a2ui.json +3 -0
  374. package/components/toggle-scheme/toggle-scheme.d.ts +51 -0
  375. package/components/toggle-scheme/toggle-scheme.js +8 -268
  376. package/components/toggle-scheme/toggle-scheme.yaml +4 -0
  377. package/components/toolbar/class.js +388 -0
  378. package/components/toolbar/toolbar.a2ui.json +3 -0
  379. package/components/toolbar/toolbar.d.ts +24 -0
  380. package/components/toolbar/toolbar.js +10 -376
  381. package/components/toolbar/toolbar.yaml +4 -0
  382. package/components/tooltip/class.js +299 -0
  383. package/components/tooltip/tooltip.a2ui.json +1 -0
  384. package/components/tooltip/tooltip.d.ts +28 -0
  385. package/components/tooltip/tooltip.js +8 -280
  386. package/components/tree/class.js +245 -0
  387. package/components/tree/tree.a2ui.json +3 -0
  388. package/components/tree/tree.d.ts +25 -0
  389. package/components/tree/tree.js +9 -244
  390. package/components/tree/tree.yaml +4 -0
  391. package/components/upload/class.js +199 -0
  392. package/components/upload/upload.a2ui.json +1 -0
  393. package/components/upload/upload.js +11 -183
  394. package/core/icons-phosphor.js +93 -0
  395. package/core/icons.js +92 -90
  396. package/core/index.js +5 -0
  397. package/index.d.ts +160 -5
  398. package/index.js +7 -0
  399. package/package.json +7 -2
@@ -0,0 +1,199 @@
1
+ /**
2
+ * Non-side-effect class export for `<upload-ui>`.
3
+ *
4
+ * Importing this file gives you the class(es) without auto-registering the tag.
5
+ * Useful for test isolation, subclassing with tag-name override, or selective
6
+ * composition.
7
+ *
8
+ * The auto-register path stays at `@adia-ai/web-components/components/upload`
9
+ * (which imports this file + calls `defineIfFree()`).
10
+ *
11
+ * @see ../../USAGE.md#registration--auto-vs-explicit
12
+ */
13
+
14
+ /**
15
+ * <upload-ui> — File upload with drag-and-drop.
16
+ * Uses showOpenFilePicker (modern) with <input type="file"> fallback.
17
+ * Form-associated via UIFormElement + ElementInternals.
18
+ */
19
+
20
+ import { UIFormElement } from '../../core/form.js';
21
+
22
+ export class UIUpload extends UIFormElement {
23
+ static properties = {
24
+ ...UIFormElement.properties,
25
+ label: { type: String, default: '', reflect: true },
26
+ accept: { type: String, default: '', reflect: true },
27
+ multiple: { type: Boolean, default: false, reflect: true },
28
+ };
29
+
30
+ static template = () => null;
31
+
32
+ #files = [];
33
+ #dropzoneEl = null;
34
+
35
+ connected() {
36
+ super.connected();
37
+
38
+ if (!this.querySelector('[data-dropzone]')) {
39
+ this.innerHTML = `
40
+ <div data-dropzone tabindex="0" role="button">Drop files here or click to browse</div>
41
+ <span hint="${this.hint || ''}"></span>
42
+ <div data-filelist></div>
43
+ `;
44
+ }
45
+
46
+ this.#dropzoneEl = this.querySelector('[data-dropzone]');
47
+ if (this.#dropzoneEl) {
48
+ this.#dropzoneEl.addEventListener('click', this.#onClickZone);
49
+ this.#dropzoneEl.addEventListener('keydown', this.#onKeyZone);
50
+ this.#dropzoneEl.addEventListener('dragover', this.#onDragOver);
51
+ this.#dropzoneEl.addEventListener('dragleave', this.#onDragLeave);
52
+ this.#dropzoneEl.addEventListener('drop', this.#onDrop);
53
+ }
54
+ }
55
+
56
+ render() {
57
+ const filelist = this.querySelector('[data-filelist]');
58
+ if (!this.#dropzoneEl || !filelist) return;
59
+
60
+ // Update hint attribute
61
+ const hintEl = this.querySelector('span[hint]');
62
+ if (hintEl && this.hint) hintEl.setAttribute('hint', this.hint);
63
+
64
+ // Render file list
65
+ filelist.innerHTML = '';
66
+ for (const f of this.#files) {
67
+ const span = document.createElement('span');
68
+ span.textContent = f.name;
69
+ filelist.appendChild(span);
70
+ }
71
+ }
72
+
73
+ get files() {
74
+ return this.#files;
75
+ }
76
+
77
+ // ── File picking ──
78
+
79
+ #onClickZone = () => {
80
+ if (this.disabled) return;
81
+ this.#pickFiles();
82
+ };
83
+
84
+ #onKeyZone = (e) => {
85
+ if (this.disabled) return;
86
+ if (e.key === 'Enter' || e.key === ' ') {
87
+ e.preventDefault();
88
+ this.#pickFiles();
89
+ }
90
+ };
91
+
92
+ async #pickFiles() {
93
+ try {
94
+ if (window.showOpenFilePicker) {
95
+ const types = this.#parseAcceptTypes();
96
+ const opts = { multiple: this.multiple };
97
+ if (types.length) opts.types = types;
98
+ const handles = await window.showOpenFilePicker(opts);
99
+ if (!this.isConnected) return;
100
+ const files = await Promise.all(handles.map(h => h.getFile()));
101
+ if (!this.isConnected) return;
102
+ this.#setFiles(files);
103
+ } else {
104
+ this.#pickFallback();
105
+ }
106
+ } catch (err) {
107
+ // User cancelled — AbortError is expected
108
+ if (err.name !== 'AbortError') throw err;
109
+ }
110
+ }
111
+
112
+ #pickFallback() {
113
+ const input = document.createElement('input');
114
+ input.type = 'file';
115
+ if (this.accept) input.accept = this.accept;
116
+ if (this.multiple) input.multiple = true;
117
+ input.style.display = 'none';
118
+ document.body.appendChild(input);
119
+ input.addEventListener('change', () => {
120
+ if (input.files?.length) {
121
+ this.#setFiles([...input.files]);
122
+ }
123
+ input.remove();
124
+ }, { once: true });
125
+ // Handle cancel (input removed on blur after a delay)
126
+ input.addEventListener('cancel', () => input.remove(), { once: true });
127
+ input.click();
128
+ }
129
+
130
+ /**
131
+ * Parse the accept attribute into showOpenFilePicker types array.
132
+ * e.g. "image/*,.pdf" → [{ accept: { "image/*": [], "application/pdf": [".pdf"] } }]
133
+ */
134
+ #parseAcceptTypes() {
135
+ if (!this.accept) return [];
136
+ const accept = {};
137
+ for (const part of this.accept.split(',')) {
138
+ const token = part.trim();
139
+ if (!token) continue;
140
+ if (token.startsWith('.')) {
141
+ // Extension — map to wildcard
142
+ accept['application/octet-stream'] = accept['application/octet-stream'] || [];
143
+ accept['application/octet-stream'].push(token);
144
+ } else {
145
+ accept[token] = accept[token] || [];
146
+ }
147
+ }
148
+ return Object.keys(accept).length ? [{ accept }] : [];
149
+ }
150
+
151
+ // ── Drag-and-drop ──
152
+
153
+ #onDragOver = (e) => {
154
+ e.preventDefault();
155
+ this.querySelector('[data-dropzone]')?.setAttribute('data-dragover', '');
156
+ };
157
+
158
+ #onDragLeave = () => {
159
+ this.querySelector('[data-dropzone]')?.removeAttribute('data-dragover');
160
+ };
161
+
162
+ #onDrop = (e) => {
163
+ e.preventDefault();
164
+ this.querySelector('[data-dropzone]')?.removeAttribute('data-dragover');
165
+ if (this.disabled) return;
166
+ const dt = e.dataTransfer;
167
+ if (dt?.files?.length) {
168
+ this.#setFiles([...dt.files]);
169
+ }
170
+ };
171
+
172
+ // ── Internal state ──
173
+
174
+ #setFiles(fileArray) {
175
+ this.#files = fileArray;
176
+
177
+ // Set form value as FormData
178
+ const fd = new FormData();
179
+ for (const f of this.#files) {
180
+ fd.append(this.name || 'file', f);
181
+ }
182
+ this.internals.setFormValue(fd);
183
+
184
+ this.dispatchEvent(new CustomEvent('change', { bubbles: true, detail: { value: this.value, files: this.files } }));
185
+ this.render();
186
+ }
187
+
188
+ disconnected() {
189
+ super.disconnected();
190
+ if (this.#dropzoneEl) {
191
+ this.#dropzoneEl.removeEventListener('click', this.#onClickZone);
192
+ this.#dropzoneEl.removeEventListener('keydown', this.#onKeyZone);
193
+ this.#dropzoneEl.removeEventListener('dragover', this.#onDragOver);
194
+ this.#dropzoneEl.removeEventListener('dragleave', this.#onDragLeave);
195
+ this.#dropzoneEl.removeEventListener('drop', this.#onDrop);
196
+ }
197
+ this.#dropzoneEl = null;
198
+ }
199
+ }
@@ -64,6 +64,7 @@
64
64
  "x-adiaui": {
65
65
  "anti_patterns": [],
66
66
  "category": "input",
67
+ "composes": [],
67
68
  "events": {
68
69
  "change": {
69
70
  "description": "Fired when files are selected via click or drag-and-drop"
@@ -1,189 +1,17 @@
1
1
  /**
2
- * <upload-ui>File upload with drag-and-drop.
3
- * Uses showOpenFilePicker (modern) with <input type="file"> fallback.
4
- * Form-associated via UIFormElement + ElementInternals.
2
+ * `<upload-ui>`auto-registers the tag on import.
3
+ *
4
+ * For non-side-effect class import (test isolation, tag override), use
5
+ * the `class` subpath:
6
+ *
7
+ * import { UIUpload } from '@adia-ai/web-components/components/upload/class';
8
+ *
9
+ * @see ../../USAGE.md#registration--auto-vs-explicit
5
10
  */
6
11
 
7
- import { UIFormElement } from '../../core/form.js';
12
+ import { defineIfFree } from '../../core/register.js';
13
+ import { UIUpload } from './class.js';
8
14
 
9
- class UIUpload extends UIFormElement {
10
- static properties = {
11
- ...UIFormElement.properties,
12
- label: { type: String, default: '', reflect: true },
13
- accept: { type: String, default: '', reflect: true },
14
- multiple: { type: Boolean, default: false, reflect: true },
15
- };
16
-
17
- static template = () => null;
18
-
19
- #files = [];
20
- #dropzoneEl = null;
21
-
22
- connected() {
23
- super.connected();
24
-
25
- if (!this.querySelector('[data-dropzone]')) {
26
- this.innerHTML = `
27
- <div data-dropzone tabindex="0" role="button">Drop files here or click to browse</div>
28
- <span hint="${this.hint || ''}"></span>
29
- <div data-filelist></div>
30
- `;
31
- }
32
-
33
- this.#dropzoneEl = this.querySelector('[data-dropzone]');
34
- if (this.#dropzoneEl) {
35
- this.#dropzoneEl.addEventListener('click', this.#onClickZone);
36
- this.#dropzoneEl.addEventListener('keydown', this.#onKeyZone);
37
- this.#dropzoneEl.addEventListener('dragover', this.#onDragOver);
38
- this.#dropzoneEl.addEventListener('dragleave', this.#onDragLeave);
39
- this.#dropzoneEl.addEventListener('drop', this.#onDrop);
40
- }
41
- }
42
-
43
- render() {
44
- const filelist = this.querySelector('[data-filelist]');
45
- if (!this.#dropzoneEl || !filelist) return;
46
-
47
- // Update hint attribute
48
- const hintEl = this.querySelector('span[hint]');
49
- if (hintEl && this.hint) hintEl.setAttribute('hint', this.hint);
50
-
51
- // Render file list
52
- filelist.innerHTML = '';
53
- for (const f of this.#files) {
54
- const span = document.createElement('span');
55
- span.textContent = f.name;
56
- filelist.appendChild(span);
57
- }
58
- }
59
-
60
- get files() {
61
- return this.#files;
62
- }
63
-
64
- // ── File picking ──
65
-
66
- #onClickZone = () => {
67
- if (this.disabled) return;
68
- this.#pickFiles();
69
- };
70
-
71
- #onKeyZone = (e) => {
72
- if (this.disabled) return;
73
- if (e.key === 'Enter' || e.key === ' ') {
74
- e.preventDefault();
75
- this.#pickFiles();
76
- }
77
- };
78
-
79
- async #pickFiles() {
80
- try {
81
- if (window.showOpenFilePicker) {
82
- const types = this.#parseAcceptTypes();
83
- const opts = { multiple: this.multiple };
84
- if (types.length) opts.types = types;
85
- const handles = await window.showOpenFilePicker(opts);
86
- if (!this.isConnected) return;
87
- const files = await Promise.all(handles.map(h => h.getFile()));
88
- if (!this.isConnected) return;
89
- this.#setFiles(files);
90
- } else {
91
- this.#pickFallback();
92
- }
93
- } catch (err) {
94
- // User cancelled — AbortError is expected
95
- if (err.name !== 'AbortError') throw err;
96
- }
97
- }
98
-
99
- #pickFallback() {
100
- const input = document.createElement('input');
101
- input.type = 'file';
102
- if (this.accept) input.accept = this.accept;
103
- if (this.multiple) input.multiple = true;
104
- input.style.display = 'none';
105
- document.body.appendChild(input);
106
- input.addEventListener('change', () => {
107
- if (input.files?.length) {
108
- this.#setFiles([...input.files]);
109
- }
110
- input.remove();
111
- }, { once: true });
112
- // Handle cancel (input removed on blur after a delay)
113
- input.addEventListener('cancel', () => input.remove(), { once: true });
114
- input.click();
115
- }
116
-
117
- /**
118
- * Parse the accept attribute into showOpenFilePicker types array.
119
- * e.g. "image/*,.pdf" → [{ accept: { "image/*": [], "application/pdf": [".pdf"] } }]
120
- */
121
- #parseAcceptTypes() {
122
- if (!this.accept) return [];
123
- const accept = {};
124
- for (const part of this.accept.split(',')) {
125
- const token = part.trim();
126
- if (!token) continue;
127
- if (token.startsWith('.')) {
128
- // Extension — map to wildcard
129
- accept['application/octet-stream'] = accept['application/octet-stream'] || [];
130
- accept['application/octet-stream'].push(token);
131
- } else {
132
- accept[token] = accept[token] || [];
133
- }
134
- }
135
- return Object.keys(accept).length ? [{ accept }] : [];
136
- }
137
-
138
- // ── Drag-and-drop ──
139
-
140
- #onDragOver = (e) => {
141
- e.preventDefault();
142
- this.querySelector('[data-dropzone]')?.setAttribute('data-dragover', '');
143
- };
144
-
145
- #onDragLeave = () => {
146
- this.querySelector('[data-dropzone]')?.removeAttribute('data-dragover');
147
- };
148
-
149
- #onDrop = (e) => {
150
- e.preventDefault();
151
- this.querySelector('[data-dropzone]')?.removeAttribute('data-dragover');
152
- if (this.disabled) return;
153
- const dt = e.dataTransfer;
154
- if (dt?.files?.length) {
155
- this.#setFiles([...dt.files]);
156
- }
157
- };
158
-
159
- // ── Internal state ──
160
-
161
- #setFiles(fileArray) {
162
- this.#files = fileArray;
163
-
164
- // Set form value as FormData
165
- const fd = new FormData();
166
- for (const f of this.#files) {
167
- fd.append(this.name || 'file', f);
168
- }
169
- this.internals.setFormValue(fd);
170
-
171
- this.dispatchEvent(new CustomEvent('change', { bubbles: true, detail: { value: this.value, files: this.files } }));
172
- this.render();
173
- }
174
-
175
- disconnected() {
176
- super.disconnected();
177
- if (this.#dropzoneEl) {
178
- this.#dropzoneEl.removeEventListener('click', this.#onClickZone);
179
- this.#dropzoneEl.removeEventListener('keydown', this.#onKeyZone);
180
- this.#dropzoneEl.removeEventListener('dragover', this.#onDragOver);
181
- this.#dropzoneEl.removeEventListener('dragleave', this.#onDragLeave);
182
- this.#dropzoneEl.removeEventListener('drop', this.#onDrop);
183
- }
184
- this.#dropzoneEl = null;
185
- }
186
- }
187
- customElements.define('upload-ui', UIUpload);
15
+ defineIfFree('upload-ui', UIUpload);
188
16
 
189
17
  export { UIUpload };
@@ -0,0 +1,93 @@
1
+ /**
2
+ * Phosphor icon glob — side-effect module that wires the full
3
+ * @phosphor-icons/core asset tree (~9000 SVGs × 6 weights) into the
4
+ * registry exposed by `./icons.js`.
5
+ *
6
+ * ## When to import this
7
+ *
8
+ * import '@adia-ai/web-components/core/icons-phosphor';
9
+ *
10
+ * Use this only when you want any Phosphor name to resolve without
11
+ * pre-registering it. The main barrel (`import '@adia-ai/web-components'`)
12
+ * and the core barrel (`import '@adia-ai/web-components/core'`) already
13
+ * side-effect-import this file for zero-config users.
14
+ *
15
+ * ## What this costs
16
+ *
17
+ * `import.meta.glob` with the default lazy mode tells Vite to emit one
18
+ * code-split chunk per matched file. The full Phosphor set is ~9000 SVGs
19
+ * (~1500 names × 6 weights), so `vite build` emits ~9000 chunks even if
20
+ * your app only renders 2 icons. The chunks are HTTP-cacheable, but:
21
+ *
22
+ * - `vite build` graph cost scales with the Phosphor set, not your usage
23
+ * - `.vite/deps` cache grows >100 MB during dev
24
+ * - Static deploys without incremental upload push tens of thousands of
25
+ * tiny files on every deploy
26
+ * - Rollup warns "(!) Some chunks are larger than 500 KB"
27
+ *
28
+ * For production bundles with size SLOs, skip this side-effect import and
29
+ * register only the icons you use:
30
+ *
31
+ * import { installIconLoaders } from '@adia-ai/web-components/core/icons';
32
+ * installIconLoaders({
33
+ * regular: import.meta.glob(
34
+ * '/node_modules/@phosphor-icons/core/assets/regular/{caret-right,moon,sun,x}.svg',
35
+ * { query: '?raw', import: 'default', eager: true }
36
+ * ),
37
+ * });
38
+ *
39
+ * Brace-list globs are statically analyzed; only the named files are
40
+ * emitted as chunks (or inlined when `eager: true`).
41
+ *
42
+ * ## Vite glob detection
43
+ *
44
+ * `import.meta.glob` is a build-time macro — Vite's AST transform replaces
45
+ * each call with a literal `{ path: loader }` object before the module
46
+ * reaches the browser. At runtime `import.meta.glob` is undefined, so a
47
+ * direct call throws. We wrap the assignment in try/catch to handle both:
48
+ *
49
+ * - Vite dev/build → rewritten to literals → try block succeeds
50
+ * - Static serving → actual runtime call throws → catch falls through
51
+ * to the manifest fetch below
52
+ */
53
+
54
+ import { installIconLoaders } from './icons.js';
55
+
56
+ let weightModules;
57
+ let hasViteGlob = false;
58
+ try {
59
+ weightModules = {
60
+ regular: import.meta.glob('/node_modules/@phosphor-icons/core/assets/regular/*.svg', { query: '?raw', import: 'default' }),
61
+ thin: import.meta.glob('/node_modules/@phosphor-icons/core/assets/thin/*.svg', { query: '?raw', import: 'default' }),
62
+ light: import.meta.glob('/node_modules/@phosphor-icons/core/assets/light/*.svg', { query: '?raw', import: 'default' }),
63
+ bold: import.meta.glob('/node_modules/@phosphor-icons/core/assets/bold/*.svg', { query: '?raw', import: 'default' }),
64
+ fill: import.meta.glob('/node_modules/@phosphor-icons/core/assets/fill/*.svg', { query: '?raw', import: 'default' }),
65
+ duotone: import.meta.glob('/node_modules/@phosphor-icons/core/assets/duotone/*.svg', { query: '?raw', import: 'default' }),
66
+ };
67
+ hasViteGlob = true;
68
+ } catch {
69
+ /* non-Vite static serving — manifest fetch below handles it */
70
+ }
71
+
72
+ if (hasViteGlob) {
73
+ installIconLoaders(weightModules);
74
+ } else {
75
+ // Non-Vite static serving: fetch the build-time manifest in the
76
+ // background. No top-level await — module finishes loading immediately;
77
+ // icons appear once the one-shot manifest fetch resolves.
78
+ // The specifier is hidden behind a variable so Vite's static analysis
79
+ // never tries to pre-resolve it in dev (where the file doesn't exist).
80
+ const manifestSpec = './icons-manifest.js';
81
+ import(/* @vite-ignore */ manifestSpec).then(({ default: manifest }) => {
82
+ const modules = Object.fromEntries(Object.entries(manifest).map(([weight, names]) => {
83
+ const prefix = `/node_modules/@phosphor-icons/core/assets/${weight}/`;
84
+ const entries = names.map(name => {
85
+ const path = prefix + name;
86
+ const loader = () => fetch(path).then(r => r.ok ? r.text() : Promise.reject(new Error(`icon fetch failed: ${path}`)));
87
+ return [path, loader];
88
+ });
89
+ return [weight, Object.fromEntries(entries)];
90
+ }));
91
+ installIconLoaders(modules);
92
+ }).catch(() => { /* manifest missing — registry stays empty; consumers can registerIcon() themselves */ });
93
+ }