@ixfx/components 0.13.2 → 0.13.4

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 (306) hide show
  1. package/bundle/index.d.ts +1649 -128
  2. package/bundle/index.js +1595 -44437
  3. package/bundle/rolldown-runtime-CEoa-xHZ.js +1 -0
  4. package/dist/ac-text.d.ts +2 -3
  5. package/dist/ac-text.js +0 -2
  6. package/dist/{ac-token-TCLAZeVg.d.ts → ac-token--_vCHXWw.d.ts} +2 -3
  7. package/dist/ac-token.d.ts +1 -1
  8. package/dist/ac-token.js +1 -3
  9. package/dist/button-B7mgqtxR.js +0 -2
  10. package/dist/{button-CTL45aBl.d.ts → button-BYuf72aR.d.ts} +2 -3
  11. package/dist/button.d.ts +1 -1
  12. package/dist/checkbox.d.ts +1 -2
  13. package/dist/checkbox.js +0 -2
  14. package/dist/checked-select-CglRukbP.d.ts +1 -2
  15. package/dist/checked-select-lDgAQQ7v.js +0 -2
  16. package/dist/colour-picker-BCMU7W7R.js +0 -2
  17. package/dist/colour-picker.d.ts +1 -1
  18. package/dist/crumbs.d.ts +2 -3
  19. package/dist/crumbs.js +1 -3
  20. package/dist/data-controller-DOlmqNKb.js +0 -2
  21. package/dist/data-display.d.ts +1 -2
  22. package/dist/data-display.js +0 -2
  23. package/dist/{data-grid-Ck1Qx2H1.d.ts → data-grid-BtBZt8M1.d.ts} +10 -9
  24. package/dist/data-grid-FHr7wZ_k.js +2108 -0
  25. package/dist/data-grid.d.ts +1 -1
  26. package/dist/data-grid.js +1 -1923
  27. package/dist/data-provider-35TyWclX.js +0 -2
  28. package/dist/data-provider-BAn_-oR1.d.ts +1 -2
  29. package/dist/decorate-VRK8rslU.js +0 -2
  30. package/dist/defaults-B4ePs4LB.js +0 -2
  31. package/dist/detail-list-BfYHNh6B.js +1999 -0
  32. package/dist/{detail-list-C1xzr1z7.d.ts → detail-list-u2rWnAXQ.d.ts} +13 -5
  33. package/dist/detail-list.d.ts +2 -2
  34. package/dist/detail-list.js +1 -1680
  35. package/dist/drag-ghost-DtSDvjri.js +0 -2
  36. package/dist/editable-label-rzXkjf1H.d.ts +1 -2
  37. package/dist/editable-label.js +0 -2
  38. package/dist/fallbacks-DQ_5OsmR.js +0 -2
  39. package/dist/{flat-list-Ohxqsy0g.d.ts → flat-list-DNnTQ65v.d.ts} +3 -4
  40. package/dist/flat-list.d.ts +1 -1
  41. package/dist/flat-list.js +5 -3
  42. package/dist/form-CsXJX15p.js +0 -2
  43. package/dist/form.d.ts +1 -2
  44. package/dist/{grid-list-pefLORIr.d.ts → grid-list-BLnV9oZE.d.ts} +9 -3
  45. package/dist/{grid-list-DjIl910A.js → grid-list-CkU8gHCh.js} +189 -42
  46. package/dist/grid-list.d.ts +1 -1
  47. package/dist/grid-list.js +1 -1
  48. package/dist/{grouped-item-lister-Bhyo-dkH.d.ts → grouped-item-lister-DETte0Dh.d.ts} +2 -3
  49. package/dist/grouped-item-lister.d.ts +1 -1
  50. package/dist/grouped-item-lister.js +0 -2
  51. package/dist/grouping-CUKgmkMm.d.ts +1 -2
  52. package/dist/grouping-RYPnHkrS.js +0 -2
  53. package/dist/handle-DAXs7kbJ.js +0 -2
  54. package/dist/hex-editor-Caq8vNQk.d.ts +1 -2
  55. package/dist/hex-editor-DiYpgIKs.js +0 -2
  56. package/dist/highlight-B-eQrhhb.js +0 -2
  57. package/dist/icon-1gpwtPx8.js +0 -2
  58. package/dist/{icon-DR_3rSyZ.d.ts → icon-CDGprSdE.d.ts} +2 -3
  59. package/dist/icons.d.ts +2 -2
  60. package/dist/icons.js +0 -2
  61. package/dist/{incr-search-D91M4Ozq.js → incr-search-JIhwB49y.js} +26 -6
  62. package/dist/incr-search.d.ts +1 -1
  63. package/dist/incr-search.js +1 -1
  64. package/dist/{index-Dq30pOnn.d.ts → index-B-hzcIP0.d.ts} +3 -4
  65. package/dist/{index-CxZ61DO1.d.ts → index-BYIRgv49.d.ts} +9 -3
  66. package/dist/index-CCC0G1nO.d.ts +324 -0
  67. package/dist/{index-garxxqgV.d.ts → index-CYndvTWH.d.ts} +2 -3
  68. package/dist/{index-BUB5SICW.d.ts → index-CoqtMSd9.d.ts} +2 -3
  69. package/dist/index-DV3iaUBW.d.ts +1 -2
  70. package/dist/{index-CJ5fshD3.d.ts → index-UvnoZUAo.d.ts} +2 -3
  71. package/dist/index-o-CWDt11.d.ts +1 -2
  72. package/dist/{index-BOUaDIW-.d.ts → index-tq6f8007.d.ts} +2 -3
  73. package/dist/index.d.ts +21 -22
  74. package/dist/index.js +48 -29
  75. package/dist/item-appearance-BjcMyauw.js +0 -2
  76. package/dist/keyboard-B5xD7Fz-.js +0 -2
  77. package/dist/labelled-input-base-BFa4xlYV.js +0 -2
  78. package/dist/{labelled-input-base-Dp_9KP0G.d.ts → labelled-input-base-DiTme1JO.d.ts} +2 -3
  79. package/dist/labelled-radial-input.d.ts +3 -4
  80. package/dist/labelled-radial-input.js +0 -2
  81. package/dist/labelled-range-input.d.ts +1 -1
  82. package/dist/labelled-range-input.js +0 -2
  83. package/dist/labelled-slider-input-FdCRi6st.js +0 -2
  84. package/dist/labelled-slider-input.d.ts +1 -1
  85. package/dist/led.d.ts +1 -2
  86. package/dist/led.js +0 -2
  87. package/dist/list-group-header.d.ts +2 -3
  88. package/dist/list-group-header.js +0 -2
  89. package/dist/list-item-animation-BUoEKi5s.js +0 -2
  90. package/dist/list-native-drag-controller-B9xO0XWn.js +0 -2
  91. package/dist/list-native-drag-controller-ChIi3eK5.d.ts +1 -2
  92. package/dist/list-selection-controller-BeE70lbB.js +0 -2
  93. package/dist/list-selection-types-PjKdhF-a.d.ts +1 -2
  94. package/dist/list-viewport-types-BRZsLcvp.d.ts +1 -2
  95. package/dist/menu-CwcXXeLM.js +0 -2
  96. package/dist/menu-item-BDEekBVy.js +0 -2
  97. package/dist/{menu-item-B0zqw2xp.d.ts → menu-item-bF6narIz.d.ts} +2 -3
  98. package/dist/menu.d.ts +2 -2
  99. package/dist/miller.d.ts +2 -3
  100. package/dist/miller.js +146 -102
  101. package/dist/narrowed-text.js +1 -3
  102. package/dist/notification-pill-DyZydXoZ.d.ts +1 -2
  103. package/dist/notifier.js +0 -2
  104. package/dist/pan-text-CoYmt2qd.d.ts +1 -2
  105. package/dist/pan-text-CqtvjPyK.js +0 -2
  106. package/dist/panel.d.ts +2 -3
  107. package/dist/panel.js +0 -2
  108. package/dist/polar-pad.d.ts +1 -2
  109. package/dist/polar-pad.js +0 -2
  110. package/dist/popup-D80sj2QC.js +0 -2
  111. package/dist/prominence-DlFShic3.js +0 -2
  112. package/dist/radial-input-DU6t2hYO.d.ts +1 -2
  113. package/dist/radial-input-KMVltQfe.js +0 -2
  114. package/dist/range-input.d.ts +1 -2
  115. package/dist/range-input.js +0 -2
  116. package/dist/range.d.ts +1 -2
  117. package/dist/range.js +0 -2
  118. package/dist/registry-BEtb8_wB.js +0 -2
  119. package/dist/{scroll-fade-BrNUIYnm.js → scroll-fade-Xx28D7mH.js} +11 -7
  120. package/dist/select-horiz.d.ts +1 -2
  121. package/dist/select-horiz.js +1 -3
  122. package/dist/slider-input-BxURAAmD.d.ts +1 -2
  123. package/dist/slider-input-ByHdotzp.js +0 -2
  124. package/dist/snackbar.d.ts +1 -2
  125. package/dist/snackbar.js +0 -2
  126. package/dist/snap-container.d.ts +1 -2
  127. package/dist/snap-container.js +0 -2
  128. package/dist/{split-layout-CXotkdbx.js → split-layout-Deoxy47d.js} +5 -2
  129. package/dist/{split-layout-C5SYbDrq.d.ts → split-layout-JK3xWVX2.d.ts} +2 -3
  130. package/dist/split-layout.d.ts +1 -1
  131. package/dist/split-layout.js +1 -1
  132. package/dist/swipe.d.ts +1 -2
  133. package/dist/swipe.js +0 -2
  134. package/dist/{tab-list-v8mKX7Fu.d.ts → tab-list-CexFFg6O.d.ts} +3 -5
  135. package/dist/tabs.d.ts +1 -1
  136. package/dist/tabs.js +23 -3
  137. package/dist/tickled-controller-D-HZymaZ.js +0 -2
  138. package/dist/tickled-controller-DodxD3eQ.d.ts +1 -2
  139. package/dist/tickled-styles-BrAHEj1q.js +0 -2
  140. package/dist/timeline-BP1Ux2EV.js +0 -2
  141. package/dist/{titlebar-B5zSTZnF.d.ts → titlebar-Tqu-VvMU.d.ts} +2 -3
  142. package/dist/titlebar.d.ts +1 -1
  143. package/dist/titlebar.js +0 -2
  144. package/dist/tooltip-BlvBUQxx.d.ts +1 -2
  145. package/dist/tooltip-CJt3WLmN.js +0 -2
  146. package/dist/transitory-label.d.ts +1 -2
  147. package/dist/transitory-label.js +0 -2
  148. package/dist/{tree-DGveys4K.js → tree-DD8OaqsK.js} +1009 -231
  149. package/dist/tree-component-Cj8V3uar.d.ts +1 -2
  150. package/dist/tree.d.ts +4 -267
  151. package/dist/tree.js +1 -1
  152. package/dist/types-DQ7KOUIj.d.ts +1 -2
  153. package/dist/{vertical-list-CqBc-t8w.d.ts → vertical-list-m7GJtXwv.d.ts} +3 -3
  154. package/dist/vertical-list.d.ts +1 -1
  155. package/dist/vertical-list.js +114 -27
  156. package/dist/wheel-nudge-By5s_ioH.d.ts +1 -2
  157. package/dist/wheel-nudge-D5rmht3v.js +0 -2
  158. package/dist/xy-axis-CyMd_Bn1.js +0 -2
  159. package/dist/xy-axis-DQqd2yXJ.d.ts +1 -2
  160. package/dist/xy-pad.d.ts +1 -2
  161. package/dist/xy-pad.js +0 -2
  162. package/docs-user/data-grid.md +74 -4
  163. package/docs-user/detail-list.md +65 -0
  164. package/docs-user/grid-list.md +81 -4
  165. package/docs-user/index.json +2 -2
  166. package/docs-user/miller.md +59 -3
  167. package/docs-user/tree.md +63 -2
  168. package/docs-user/vertical-list.md +9 -1
  169. package/package.json +6 -1
  170. package/bundle/index.d.ts.map +0 -1
  171. package/bundle/index.js.map +0 -1
  172. package/bundle/rolldown-runtime-D7D4PA-g.js +0 -13
  173. package/dist/ac-text.d.ts.map +0 -1
  174. package/dist/ac-text.js.map +0 -1
  175. package/dist/ac-token-TCLAZeVg.d.ts.map +0 -1
  176. package/dist/ac-token.js.map +0 -1
  177. package/dist/button-B7mgqtxR.js.map +0 -1
  178. package/dist/button-CTL45aBl.d.ts.map +0 -1
  179. package/dist/checkbox.d.ts.map +0 -1
  180. package/dist/checkbox.js.map +0 -1
  181. package/dist/checked-select-CglRukbP.d.ts.map +0 -1
  182. package/dist/checked-select-lDgAQQ7v.js.map +0 -1
  183. package/dist/colour-picker-BCMU7W7R.js.map +0 -1
  184. package/dist/crumbs.d.ts.map +0 -1
  185. package/dist/crumbs.js.map +0 -1
  186. package/dist/data-controller-DOlmqNKb.js.map +0 -1
  187. package/dist/data-display.d.ts.map +0 -1
  188. package/dist/data-display.js.map +0 -1
  189. package/dist/data-grid-Ck1Qx2H1.d.ts.map +0 -1
  190. package/dist/data-grid.js.map +0 -1
  191. package/dist/data-provider-35TyWclX.js.map +0 -1
  192. package/dist/data-provider-BAn_-oR1.d.ts.map +0 -1
  193. package/dist/decorate-VRK8rslU.js.map +0 -1
  194. package/dist/defaults-B4ePs4LB.js.map +0 -1
  195. package/dist/detail-list-C1xzr1z7.d.ts.map +0 -1
  196. package/dist/detail-list.js.map +0 -1
  197. package/dist/drag-ghost-DtSDvjri.js.map +0 -1
  198. package/dist/editable-label-rzXkjf1H.d.ts.map +0 -1
  199. package/dist/editable-label.js.map +0 -1
  200. package/dist/fallbacks-DQ_5OsmR.js.map +0 -1
  201. package/dist/flat-list-Ohxqsy0g.d.ts.map +0 -1
  202. package/dist/flat-list.js.map +0 -1
  203. package/dist/form-CsXJX15p.js.map +0 -1
  204. package/dist/form.d.ts.map +0 -1
  205. package/dist/grid-list-DjIl910A.js.map +0 -1
  206. package/dist/grid-list-pefLORIr.d.ts.map +0 -1
  207. package/dist/grouped-item-lister-Bhyo-dkH.d.ts.map +0 -1
  208. package/dist/grouped-item-lister.js.map +0 -1
  209. package/dist/grouping-CUKgmkMm.d.ts.map +0 -1
  210. package/dist/grouping-RYPnHkrS.js.map +0 -1
  211. package/dist/handle-DAXs7kbJ.js.map +0 -1
  212. package/dist/hex-editor-Caq8vNQk.d.ts.map +0 -1
  213. package/dist/hex-editor-DiYpgIKs.js.map +0 -1
  214. package/dist/highlight-B-eQrhhb.js.map +0 -1
  215. package/dist/icon-1gpwtPx8.js.map +0 -1
  216. package/dist/icon-DR_3rSyZ.d.ts.map +0 -1
  217. package/dist/icons.js.map +0 -1
  218. package/dist/incr-search-D91M4Ozq.js.map +0 -1
  219. package/dist/index-BOUaDIW-.d.ts.map +0 -1
  220. package/dist/index-BUB5SICW.d.ts.map +0 -1
  221. package/dist/index-CJ5fshD3.d.ts.map +0 -1
  222. package/dist/index-CxZ61DO1.d.ts.map +0 -1
  223. package/dist/index-DV3iaUBW.d.ts.map +0 -1
  224. package/dist/index-Dq30pOnn.d.ts.map +0 -1
  225. package/dist/index-garxxqgV.d.ts.map +0 -1
  226. package/dist/index-o-CWDt11.d.ts.map +0 -1
  227. package/dist/index.d.ts.map +0 -1
  228. package/dist/index.js.map +0 -1
  229. package/dist/item-appearance-BjcMyauw.js.map +0 -1
  230. package/dist/keyboard-B5xD7Fz-.js.map +0 -1
  231. package/dist/labelled-input-base-BFa4xlYV.js.map +0 -1
  232. package/dist/labelled-input-base-Dp_9KP0G.d.ts.map +0 -1
  233. package/dist/labelled-radial-input.d.ts.map +0 -1
  234. package/dist/labelled-radial-input.js.map +0 -1
  235. package/dist/labelled-range-input.js.map +0 -1
  236. package/dist/labelled-slider-input-FdCRi6st.js.map +0 -1
  237. package/dist/led.d.ts.map +0 -1
  238. package/dist/led.js.map +0 -1
  239. package/dist/list-group-header.d.ts.map +0 -1
  240. package/dist/list-group-header.js.map +0 -1
  241. package/dist/list-item-animation-BUoEKi5s.js.map +0 -1
  242. package/dist/list-native-drag-controller-B9xO0XWn.js.map +0 -1
  243. package/dist/list-native-drag-controller-ChIi3eK5.d.ts.map +0 -1
  244. package/dist/list-selection-controller-BeE70lbB.js.map +0 -1
  245. package/dist/list-selection-types-PjKdhF-a.d.ts.map +0 -1
  246. package/dist/list-viewport-types-BRZsLcvp.d.ts.map +0 -1
  247. package/dist/menu-CwcXXeLM.js.map +0 -1
  248. package/dist/menu-item-B0zqw2xp.d.ts.map +0 -1
  249. package/dist/menu-item-BDEekBVy.js.map +0 -1
  250. package/dist/miller.d.ts.map +0 -1
  251. package/dist/miller.js.map +0 -1
  252. package/dist/narrowed-text.js.map +0 -1
  253. package/dist/notification-pill-DyZydXoZ.d.ts.map +0 -1
  254. package/dist/notifier.js.map +0 -1
  255. package/dist/pan-text-CoYmt2qd.d.ts.map +0 -1
  256. package/dist/pan-text-CqtvjPyK.js.map +0 -1
  257. package/dist/panel.d.ts.map +0 -1
  258. package/dist/panel.js.map +0 -1
  259. package/dist/polar-pad.d.ts.map +0 -1
  260. package/dist/polar-pad.js.map +0 -1
  261. package/dist/popup-D80sj2QC.js.map +0 -1
  262. package/dist/prominence-DlFShic3.js.map +0 -1
  263. package/dist/radial-input-DU6t2hYO.d.ts.map +0 -1
  264. package/dist/radial-input-KMVltQfe.js.map +0 -1
  265. package/dist/range-input.d.ts.map +0 -1
  266. package/dist/range-input.js.map +0 -1
  267. package/dist/range.d.ts.map +0 -1
  268. package/dist/range.js.map +0 -1
  269. package/dist/registry-BEtb8_wB.js.map +0 -1
  270. package/dist/scroll-fade-BrNUIYnm.js.map +0 -1
  271. package/dist/select-horiz.d.ts.map +0 -1
  272. package/dist/select-horiz.js.map +0 -1
  273. package/dist/slider-input-BxURAAmD.d.ts.map +0 -1
  274. package/dist/slider-input-ByHdotzp.js.map +0 -1
  275. package/dist/snackbar.d.ts.map +0 -1
  276. package/dist/snackbar.js.map +0 -1
  277. package/dist/snap-container.d.ts.map +0 -1
  278. package/dist/snap-container.js.map +0 -1
  279. package/dist/split-layout-C5SYbDrq.d.ts.map +0 -1
  280. package/dist/split-layout-CXotkdbx.js.map +0 -1
  281. package/dist/swipe.d.ts.map +0 -1
  282. package/dist/swipe.js.map +0 -1
  283. package/dist/tab-list-v8mKX7Fu.d.ts.map +0 -1
  284. package/dist/tabs.js.map +0 -1
  285. package/dist/tickled-controller-D-HZymaZ.js.map +0 -1
  286. package/dist/tickled-controller-DodxD3eQ.d.ts.map +0 -1
  287. package/dist/tickled-styles-BrAHEj1q.js.map +0 -1
  288. package/dist/timeline-BP1Ux2EV.js.map +0 -1
  289. package/dist/titlebar-B5zSTZnF.d.ts.map +0 -1
  290. package/dist/titlebar.js.map +0 -1
  291. package/dist/tooltip-BlvBUQxx.d.ts.map +0 -1
  292. package/dist/tooltip-CJt3WLmN.js.map +0 -1
  293. package/dist/transitory-label.d.ts.map +0 -1
  294. package/dist/transitory-label.js.map +0 -1
  295. package/dist/tree-DGveys4K.js.map +0 -1
  296. package/dist/tree-component-Cj8V3uar.d.ts.map +0 -1
  297. package/dist/tree.d.ts.map +0 -1
  298. package/dist/types-DQ7KOUIj.d.ts.map +0 -1
  299. package/dist/vertical-list-CqBc-t8w.d.ts.map +0 -1
  300. package/dist/vertical-list.js.map +0 -1
  301. package/dist/wheel-nudge-By5s_ioH.d.ts.map +0 -1
  302. package/dist/wheel-nudge-D5rmht3v.js.map +0 -1
  303. package/dist/xy-axis-CyMd_Bn1.js.map +0 -1
  304. package/dist/xy-axis-DQqd2yXJ.d.ts.map +0 -1
  305. package/dist/xy-pad.d.ts.map +0 -1
  306. package/dist/xy-pad.js.map +0 -1
@@ -1 +0,0 @@
1
- {"version":3,"file":"crumbs.js","names":["#getTickledItems","#onTickled","#getHostContainer","#onMenuKeyNav","#currentOpenTrigger","#menuOpenedByKeyboard","#canFocusSuggestions","#shiftFocusToNarrowedText","#handleOpenCaretMenu","#activateTickled","#shiftFocusToPath","#isWheelScrolling","#wheelScrollTimeout","#findPath","#scrollTickledIntoView","#pendingNode","#hasChildOptions","#propagateInputModeToMenu","#setSelected","#modelUnsubscribe","#runLayoutUpdate","#onHostClick","#onWheel","#previousSelectionKey","#scrollToValue","#pendingController","#updateTrailingWidth","#scrollSegmentIntoView","#abortPending","#invokeLoadChildren","#onChildClick","#currentLeadingSiblings","#findNodePath","#getSiblingMenuItems","#onLabelClick","#onSegmentMenuCommand","#onUpClick","#onFocus","#onBlur","#onKeyDown","#onMenuTriggerClose","#renderChildOptions","#getChildOptionsWidth","#onNarrowedTextChange","#onNarrowedTextBlur","#onNarrowedTextShiftTab","customElement"],"sources":["../src/crumbs/crumb-navigation.ts"],"sourcesContent":["/* eslint-disable ts/no-unsafe-declaration-merging */\nimport type { PropertyValues } from 'lit';\nimport type {\n TreeActivateEvent,\n TreeComponent,\n TreeComponentEventMap,\n TreeExpandEvent,\n TreeItemClickEvent,\n TreeSelectDetail,\n TreeSelectEvent,\n TreeTickleDetail,\n TreeTickleEvent,\n} from '../common/tree-component.js';\nimport type { TreeDataModel } from '../common/tree-data-model.js';\nimport type {\n TreeExclusivity,\n TreeFilterPredicate,\n TreeSelectionFilter,\n} from '../common/types.js';\nimport type { MenuTrigger } from '../menu/menu-trigger.js';\nimport type { LoadChildrenCallback, TreeNode } from '../tree/types.js';\nimport { css, html, LitElement, nothing } from 'lit';\nimport { property, state } from 'lit/decorators.js';\nimport { collectDataResult } from '../common/data-provider.js';\n\nimport { TickledController, tickledItemStyles, tickledStyles } from '../interaction/index.js';\nimport { themeFallbacks } from '../styles/fallbacks.js';\nimport { scrollFadeStyles } from '../styles/scroll-fade.js';\nimport { safeCustomElement as customElement } from '../util/custom-elements.js';\nimport '../menu/menu-trigger.js';\nimport '../menu/menu-container.js';\nimport '../menu/menu-item.js';\n\nimport '../narrowed-text/index.js';\n\n/** @deprecated Use TreeSelectDetail from src/common/tree-component.ts */\nexport type CrumbNavigationChangeDetail = {\n readonly selected: TreeNode;\n readonly previous: TreeNode | undefined;\n};\n\nexport type CrumbNavigationChangeEvent = CustomEvent<CrumbNavigationChangeDetail>;\n\nexport type CrumbNavigationItemClickDetail = { node: TreeNode; depth: number };\nexport type CrumbNavigationItemClickEvent = CustomEvent<CrumbNavigationItemClickDetail>;\n\nexport type CrumbNavigationExpandDetail = { node: TreeNode; depth: number };\nexport type CrumbNavigationExpandEvent = CustomEvent<CrumbNavigationExpandDetail>;\n\n/** Menu / suggestion order: by label, without mutating the tree's own order. */\nfunction sortNodesByLabel(nodes: readonly TreeNode[]): TreeNode[] {\n return [...nodes].sort((a, b) => (a.item.label ?? ``).localeCompare(b.item.label ?? ``));\n}\n\n/**\n * Breadcrumb navigation with lazy-loading support.\n *\n * Uses the same `TreeNode` / `TreeItem` data model as `ixfx-tree-list`,\n * so the two components can be swapped with minimal code changes.\n *\n * Events\n * - `navigate`: fired when user clicks a breadcrumb label. detail: `{ node: TreeNode }`\n * - `change`: fired when selected node changes. detail: `{ selected: TreeNode, previous: TreeNode | undefined }`\n * - `expand`: fired when user clicks a caret whose node has no children yet.\n * detail: `{ node: TreeNode, depth: number, signal: AbortSignal }`\n * Populate `node.children` then call `requestUpdate()` on the element.\n *\n * CSS variables\n * --crumb-item-bg: var(--item-bg, transparent); // item background\n * --crumb-item-bg-tickled: var(--item-bg-tickled); // item background on hover\n * --crumb-item-text-tickled: var(--item-text-tickled); // text color on hover\n * --crumb-item-border: var(--item-border); // item border\n * --crumb-item-border-tickled: var(--item-border-tickled); // border color on hover\n * --crumb-item-padding: var(--item-padding, var(--space-xs)); // item padding\n * --crumb-item-border-radius: var(--item-border-radius); // item border radius\n * --crumb-item-gap: var(--item-gap, var(--space-xs)); // gap between items\n * --crumb-separator: var(--surface-muted-text); // separator/caret color\n * --crumb-truncate-min-width: 5ch; // minimum width for truncatable segments\n */\n@customElement(`ixfx-crumb-navigation`)\nexport class CrumbNavigationElement extends LitElement implements TreeComponent {\n @property({ type: Object })\n root: TreeNode | undefined;\n\n @property({ attribute: false })\n model: TreeDataModel | undefined;\n\n @property({ type: Object })\n selectedNode: TreeNode | undefined;\n\n @state()\n private _selectedNodes = new Set<TreeNode>();\n\n get selectedNodes(): ReadonlySet<TreeNode> {\n return this._selectedNodes;\n }\n\n /** Callback to lazily load children for a node. When set, replaces event-based lazy loading. */\n @property({ attribute: false })\n loadChildren: LoadChildrenCallback | undefined;\n\n @property({ attribute: false })\n filterPredicate: TreeFilterPredicate | undefined;\n\n @property({ reflect: true, attribute: `exclusivity` })\n exclusivity: TreeExclusivity = `none`;\n\n @property({ reflect: true, attribute: `selection-filter` })\n selectionFilter: TreeSelectionFilter = `leaf`;\n\n @state()\n private _openIdx = -1;\n\n @state()\n private _isFocused = false;\n\n @state()\n private _menuOpen = false;\n\n @state()\n private _focusOnNarrowedText = false;\n\n @property({ reflect: true, attribute: `input-mode` })\n inputMode: string = ``;\n\n @property({ type: Boolean, reflect: true, attribute: `no-truncate` })\n noTruncate = false;\n\n @property({ type: Boolean, reflect: true, attribute: `show-suggestions` })\n showSuggestions = false;\n\n @property({ type: Boolean, reflect: true, attribute: `leading-caret` })\n leadingCaret = false;\n\n @property({ type: Boolean, reflect: true, attribute: `caret-embedded` })\n caretEmbedded = true;\n\n @property({ type: Boolean, reflect: true, attribute: `hide-root` })\n hideRoot = false;\n\n @property({ type: Boolean, reflect: true, attribute: `pad-ending` })\n padEnding = false;\n\n @property({ type: Boolean, reflect: true, attribute: `with-up` })\n withUp = false;\n\n #pendingNode: TreeNode | undefined;\n #pendingController: AbortController | undefined;\n #modelUnsubscribe: (() => void) | undefined;\n\n #previousSelectionKey = ``;\n #menuOpenedByKeyboard = false;\n #currentOpenTrigger: MenuTrigger | null = null;\n\n private tickled = new TickledController<number>(this, {\n getItems: () => this.#getTickledItems(),\n onTickle: (index) => {\n if (index !== undefined) {\n this.#onTickled(index);\n }\n },\n });\n\n #getTickledItems() {\n const r = this.root;\n const sel = this.selectedNode;\n if (!r || !sel)\n return [];\n\n const pathNodes = this.#findPath(r, sel) ?? [r];\n const items: Array<{ id: number; enabled: boolean }> = [];\n\n if (this.caretEmbedded) {\n pathNodes.forEach((_node, i) => {\n items.push({ id: i, enabled: true });\n });\n if (this.#canFocusSuggestions()) {\n items.push({ id: pathNodes.length, enabled: true });\n }\n } else {\n let segmentId = 0;\n pathNodes.forEach((node, i) => {\n const isLast = i === pathNodes.length - 1;\n const hasChildren = node.item.isLeaf !== true && (node.children === undefined || node.children.length > 0);\n const showLeadingCaret = this.leadingCaret && (i > 0 || this.hideRoot) && hasChildren;\n const showTrailingCaret = (!this.leadingCaret && hasChildren) || (this.leadingCaret && isLast && hasChildren);\n\n if (showLeadingCaret) {\n items.push({ id: segmentId++, enabled: true });\n }\n items.push({ id: segmentId++, enabled: true });\n if (showTrailingCaret) {\n items.push({ id: segmentId++, enabled: true });\n }\n });\n }\n\n return items;\n }\n\n #onTickled(index: number) {\n if (this.tickled.inputMode === `keyboard`) {\n this.#scrollTickledIntoView(index);\n }\n }\n\n #scrollTickledIntoView(index: number): void {\n const r = this.root;\n const sel = this.selectedNode;\n if (!r || !sel)\n return;\n\n const pathNodes = this.#findPath(r, sel) ?? [r];\n let el: HTMLElement | null = null;\n\n if (this.caretEmbedded && this.#canFocusSuggestions() && index === pathNodes.length) {\n el = this.shadowRoot?.querySelector<HTMLElement>(`ixfx-narrowed-text`) ?? null;\n } else {\n el = this.shadowRoot?.querySelectorAll<HTMLElement>(`.crumb-segment`)[index] ?? null;\n }\n\n el?.scrollIntoView({ inline: `nearest`, block: `nearest`, behavior: `smooth` });\n }\n\n #hasChildOptions(): boolean {\n const s = this.selectedNode;\n if (s === undefined)\n return false;\n\n const isPending = this.#pendingNode === s;\n const children = s.children ?? [];\n\n return children.length > 0 || isPending;\n }\n\n /** True when the suggestions (narrowed-text) sub-part is renderable and focusable. */\n #canFocusSuggestions(): boolean {\n return this.showSuggestions && this.#hasChildOptions();\n }\n\n #onFocus = (): void => {\n this._isFocused = true;\n };\n\n #onBlur = (): void => {\n this._isFocused = false;\n };\n\n #getHostContainer(): HTMLElement | null {\n return this.shadowRoot?.querySelector<HTMLElement>(`.host-container`) ?? null;\n }\n\n #onHostClick = (): void => {\n this.#getHostContainer()?.focus();\n };\n\n #handleOpenCaretMenu() {\n const currentTickled = this.tickled.tickledId;\n if (currentTickled === undefined)\n return;\n\n const r = this.root;\n const sel = this.selectedNode;\n if (!r || !sel)\n return;\n\n const pathNodes = this.#findPath(r, sel) ?? [r];\n\n // Virtual \"beyond last\" item (embedded mode only, when suggestions are available)\n if (this.caretEmbedded && this.#canFocusSuggestions() && currentTickled === pathNodes.length) {\n this.#shiftFocusToNarrowedText();\n return;\n }\n\n const segments = this.shadowRoot?.querySelectorAll<HTMLElement>(`.crumb-segment`);\n const trigger = segments?.[currentTickled]?.querySelector<MenuTrigger>(`.caret ixfx-menu-trigger`);\n if (trigger) {\n this.#menuOpenedByKeyboard = true;\n this.#currentOpenTrigger = trigger;\n document.addEventListener(`keydown`, this.#onMenuKeyNav, { capture: true });\n trigger.openMenu();\n this.#propagateInputModeToMenu();\n }\n }\n\n #propagateInputModeToMenu(): void {\n const inputMode = this.tickled.inputMode;\n requestAnimationFrame(() => {\n const container = this.#currentOpenTrigger?.querySelector(`ixfx-menu-container`);\n if (container) {\n container.setAttribute(`data-input-mode`, inputMode);\n }\n });\n }\n\n #onMenuTriggerClose = (): void => {\n document.removeEventListener(`keydown`, this.#onMenuKeyNav, { capture: true });\n this.#currentOpenTrigger = null;\n this.#menuOpenedByKeyboard = false;\n requestAnimationFrame(() => {\n this.#getHostContainer()?.focus();\n });\n };\n\n #onMenuKeyNav = (e: KeyboardEvent): void => {\n // Only handle ArrowLeft/ArrowRight - close menu and navigate to previous/next breadcrumb segment\n // ArrowDown/ArrowUp should pass through to let the menu handle them\n const container = this.#currentOpenTrigger?.querySelector(`ixfx-menu-container`);\n if (!container || !this.#currentOpenTrigger?.isOpen)\n return;\n\n switch (e.key) {\n case `ArrowLeft`:\n case `ArrowRight`: {\n e.preventDefault();\n e.stopPropagation();\n this.#currentOpenTrigger.closeMenu();\n const r = this.root;\n const sel = this.selectedNode;\n if (!r || !sel)\n break;\n const totalItems = this.#getTickledItems().length;\n const currentTickled = this.tickled.tickledId ?? -1;\n if (e.key === `ArrowLeft`) {\n if (currentTickled > 0) {\n this.tickled.handleKeyboardNavigation(`previous`);\n }\n } else {\n if (currentTickled < totalItems - 1) {\n this.tickled.handleKeyboardNavigation(`next`);\n }\n }\n break;\n }\n }\n };\n\n #onKeyDown = (e: KeyboardEvent): void => {\n const r = this.root;\n const sel = this.selectedNode;\n if (!r || !sel)\n return;\n\n const totalItems = this.#getTickledItems().length;\n const currentTickled = this.tickled.tickledId ?? -1;\n\n switch (e.key) {\n case `ArrowRight`: {\n e.preventDefault();\n if (currentTickled < totalItems - 1) {\n this.tickled.handleKeyboardNavigation(`next`);\n } else if (currentTickled === totalItems - 1 && this.#canFocusSuggestions()) {\n this.#shiftFocusToNarrowedText();\n }\n break;\n }\n case `ArrowLeft`: {\n e.preventDefault();\n if (currentTickled > 0) {\n this.tickled.handleKeyboardNavigation(`previous`);\n }\n break;\n }\n case `ArrowDown`:\n case `ArrowUp`: {\n if (this.tickled.tickledId !== undefined) {\n e.preventDefault();\n if (this.#currentOpenTrigger?.isOpen) {\n // Menu is already open - dispatch ArrowDown to the popover element for it to handle\n const container = this.#currentOpenTrigger.querySelector(`ixfx-menu-container`);\n const popover = container?.shadowRoot?.querySelector(`.popover`);\n if (popover) {\n popover.dispatchEvent(new KeyboardEvent(`keydown`, { key: e.key, bubbles: true }));\n }\n } else {\n this.#handleOpenCaretMenu();\n }\n }\n break;\n }\n case `Enter`:\n case ` `: {\n e.preventDefault();\n this.#activateTickled();\n break;\n }\n case `Escape`: {\n e.preventDefault();\n this._menuOpen = false;\n this.tickled.clearTickled();\n this.blur();\n break;\n }\n case `Tab`: {\n if (e.shiftKey) {\n // Let default Shift+Tab move focus backward, out of the component.\n break;\n }\n if (currentTickled === totalItems - 1 && this.#canFocusSuggestions()) {\n e.preventDefault();\n this.#shiftFocusToNarrowedText();\n }\n break;\n }\n }\n };\n\n /** Activates the currently tickled item, as if it had been clicked. */\n #activateTickled() {\n const currentTickled = this.tickled.tickledId;\n if (currentTickled === undefined)\n return;\n\n const r = this.root;\n const sel = this.selectedNode;\n if (!r || !sel)\n return;\n\n const pathNodes = this.#findPath(r, sel) ?? [r];\n\n // Virtual \"beyond last\" item (embedded mode only, when suggestions are available)\n if (this.caretEmbedded && this.#canFocusSuggestions() && currentTickled === pathNodes.length) {\n this.#shiftFocusToNarrowedText();\n return;\n }\n\n const segment = this.shadowRoot?.querySelector<HTMLElement>(`.crumb-segment[data-segment-id=\"${currentTickled}\"]`);\n segment?.click();\n }\n\n #shiftFocusToNarrowedText() {\n const narrowedText = this.shadowRoot?.querySelector(`ixfx-narrowed-text`);\n if (narrowedText) {\n this._menuOpen = false;\n this._focusOnNarrowedText = true;\n narrowedText.focus();\n }\n }\n\n #shiftFocusToPath() {\n this._focusOnNarrowedText = false;\n const hostContainer = this.#getHostContainer();\n if (hostContainer) {\n hostContainer.focus();\n }\n }\n\n #onNarrowedTextBlur = (): void => {\n this._focusOnNarrowedText = false;\n this.#shiftFocusToPath();\n };\n\n #onNarrowedTextShiftTab = (): void => {\n this._focusOnNarrowedText = false;\n this.#shiftFocusToPath();\n };\n\n // --- TreeComponent methods ---\n\n select(node: TreeNode): void {\n this.#setSelected(node);\n }\n\n deselect(_node: TreeNode): void {\n // Crumb navigation is single-selection; deselect navigates to parent or root\n }\n\n clearSelection(): void {\n if (this.root)\n this.#setSelected(this.root);\n }\n\n /** Not implemented on crumb-navigation. */\n selectAll(): void {\n // no-op\n }\n\n /** Not implemented on crumb-navigation. */\n deselectAll(): void {\n // no-op\n }\n\n getNodes(): ReadonlyArray<{ node: TreeNode; depth: number }> {\n if (!this.root)\n return [];\n const result: Array<{ node: TreeNode; depth: number }> = [];\n const visit = (node: TreeNode, depth: number) => {\n result.push({ node, depth });\n if (node.children) {\n for (const child of node.children) visit(child, depth + 1);\n }\n };\n for (const child of this.root.children ?? []) visit(child, 0);\n return result;\n }\n\n // --- Lifecycle ---\n\n override updated(changedProps: PropertyValues): void {\n if (changedProps.has(`model`)) {\n this.#modelUnsubscribe?.();\n this.#modelUnsubscribe = undefined;\n const model = this.model;\n if (model) {\n this.root = model.root;\n this.#modelUnsubscribe = model._subscribe((event) => {\n if (event.type === `root`) {\n this.root = event.root;\n this.requestUpdate();\n }\n });\n }\n }\n this.#runLayoutUpdate(changedProps);\n }\n\n override connectedCallback() {\n super.connectedCallback();\n this.addEventListener(`click`, this.#onHostClick);\n this.addEventListener(`wheel`, this.#onWheel, { passive: false });\n }\n\n override disconnectedCallback() {\n super.disconnectedCallback();\n this.removeEventListener(`click`, this.#onHostClick);\n this.removeEventListener(`wheel`, this.#onWheel);\n this.#modelUnsubscribe?.();\n this.#modelUnsubscribe = undefined;\n document.removeEventListener(`keydown`, this.#onMenuKeyNav, { capture: true });\n this.#currentOpenTrigger = null;\n }\n\n override firstUpdated() {\n const hostContainer = this.#getHostContainer();\n if (hostContainer) {\n hostContainer.scrollLeft = hostContainer.scrollWidth - hostContainer.clientWidth;\n }\n }\n\n #isWheelScrolling = false;\n\n #onWheel = (e: Event) => {\n const wheelEvent = e as WheelEvent;\n if (wheelEvent.deltaX !== 0 || wheelEvent.deltaY !== 0) {\n e.preventDefault();\n if (!this.#isWheelScrolling) {\n this.#isWheelScrolling = true;\n this.tickled.clearTickled();\n }\n const hostContainer = this.#getHostContainer();\n if (hostContainer) {\n hostContainer.scrollLeft += wheelEvent.deltaX + wheelEvent.deltaY;\n }\n clearTimeout(this.#wheelScrollTimeout);\n this.#wheelScrollTimeout = setTimeout(() => {\n this.#isWheelScrolling = false;\n }, 150);\n }\n };\n\n #wheelScrollTimeout: ReturnType<typeof setTimeout> | undefined;\n\n #runLayoutUpdate(_changedProperties: PropertyValues): void {\n if (!this.shadowRoot)\n return;\n\n const hsiElement: HTMLElement | null = this.shadowRoot.querySelector(`.horiz-select-items`);\n if (!hsiElement)\n return;\n\n const ulElement: HTMLElement | null = hsiElement.querySelector(`ul`);\n if (!ulElement)\n return;\n\n const menuTrigger: HTMLElement | null = this.shadowRoot.querySelector(`ixfx-menu-trigger`);\n if (!menuTrigger)\n return;\n\n if (ulElement.getBoundingClientRect().width > hsiElement.getBoundingClientRect().width) {\n menuTrigger.style.display = `inline-flex`;\n } else {\n menuTrigger.style.display = `none`;\n }\n\n for (const li of ulElement.querySelectorAll(`li`)) {\n const key = li.getAttribute(`data-key`) ?? ``;\n if (key === this.#previousSelectionKey) {\n this.#scrollToValue(li);\n break;\n }\n }\n }\n\n #scrollToValue(li: HTMLLIElement) {\n let l = li.offsetLeft;\n\n const ul = li.parentElement;\n if (!ul)\n return;\n l -= ul.offsetLeft;\n\n const horizSelectItems = ul.parentElement;\n if (!horizSelectItems)\n return;\n horizSelectItems.scroll({ left: l, top: 0, behavior: `smooth` });\n\n const horizSelect = horizSelectItems.parentElement;\n if (!horizSelect)\n return;\n horizSelect.style.minWidth = `${li.getBoundingClientRect().width}px`;\n }\n\n #abortPending() {\n if (this.#pendingController) {\n this.#pendingController.abort();\n this.#pendingController = undefined;\n this.#pendingNode = undefined;\n }\n }\n\n #findPath(node: TreeNode, target: TreeNode, acc: TreeNode[] = []): TreeNode[] | undefined {\n const path = [...acc, node];\n if (node === target)\n return path;\n if (!node.children)\n return undefined;\n for (const child of node.children) {\n const result = this.#findPath(child, target, path);\n if (result)\n return result;\n }\n return undefined;\n }\n\n #scrollSegmentIntoView(depth: number) {\n if (!this.shadowRoot)\n return;\n const segments = this.shadowRoot.querySelectorAll(`.crumb-segment`);\n const segment = segments[depth];\n segment?.scrollIntoView({ block: `nearest`, inline: `start` });\n }\n\n #updateTrailingWidth(): void {\n if (!this.padEnding || !this.shadowRoot)\n return;\n const hostContainer = this.shadowRoot.querySelector<HTMLElement>(`.host-container`);\n const trailing = this.shadowRoot.querySelector<HTMLElement>(`.trailing`);\n if (!hostContainer || !trailing)\n return;\n const segments = this.shadowRoot.querySelectorAll(`.crumb-segment`);\n const lastSegment = segments[segments.length - 1];\n if (!lastSegment)\n return;\n const containerWidth = hostContainer.getBoundingClientRect().width;\n const itemWidth = lastSegment.getBoundingClientRect().width;\n if (itemWidth < containerWidth) {\n trailing.style.width = `${containerWidth - itemWidth - 5}px`;\n requestAnimationFrame(() => {\n if (hostContainer.scrollWidth <= hostContainer.clientWidth) {\n hostContainer.style.setProperty(`--scroll-fade-x-start`, `0px`, `important`);\n } else {\n hostContainer.style.removeProperty(`--scroll-fade-x-start`);\n }\n });\n } else {\n trailing.style.width = ``;\n }\n }\n\n #setSelected(node: TreeNode) {\n const previous = this.selectedNode;\n if (previous) {\n this.#previousSelectionKey = previous.item?.key ?? ``;\n } else {\n this.#previousSelectionKey = ``;\n }\n const previousSet: ReadonlySet<TreeNode> = previous ? new Set([previous]) : new Set();\n this.selectedNode = node;\n this._selectedNodes = new Set([node]);\n\n if (this.root) {\n const path = this.#findPath(this.root, node);\n if (path) {\n const depth = this.hideRoot && path.length > 1 ? path.length - 2 : path.length - 1;\n requestAnimationFrame(() => {\n this.#updateTrailingWidth();\n const hostContainer = this.#getHostContainer();\n if (hostContainer) {\n hostContainer.scrollLeft = 0;\n }\n this.#scrollSegmentIntoView(depth);\n });\n }\n }\n\n this.dispatchEvent(new CustomEvent<TreeSelectDetail>(`select`, {\n detail: { selected: new Set([node]), previous: previousSet },\n bubbles: true,\n composed: true,\n }));\n }\n\n #onLabelClick(node: TreeNode, depth: number) {\n this._openIdx = -1;\n this.#setSelected(node);\n this.#scrollSegmentIntoView(depth);\n this.dispatchEvent(new CustomEvent<CrumbNavigationItemClickDetail>(`item-click`, {\n detail: { node, depth },\n bubbles: true,\n composed: true,\n }));\n }\n\n #onCaretClick(node: TreeNode, depth: number, e: MouseEvent) {\n e.preventDefault();\n e.stopPropagation();\n\n if (this._openIdx === depth) {\n this._openIdx = -1;\n return;\n }\n this._openIdx = depth;\n\n if (node.children === undefined && this.#pendingNode !== node) {\n this.#abortPending();\n this.#pendingNode = node;\n const controller = new AbortController();\n this.#pendingController = controller;\n\n if (this.loadChildren) {\n this.#invokeLoadChildren(node, depth, controller).catch(() => {});\n }\n }\n\n this.requestUpdate();\n }\n\n async #invokeLoadChildren(node: TreeNode, depth: number, controller: AbortController): Promise<void> {\n try {\n const children = [...await collectDataResult(\n this.loadChildren!({ node, depth }, controller.signal),\n controller.signal,\n )];\n if (controller.signal.aborted)\n return;\n node.children = children;\n this.#pendingNode = undefined;\n this.#pendingController = undefined;\n this.dispatchEvent(new CustomEvent<CrumbNavigationExpandDetail>(`expand`, {\n detail: { node, depth },\n bubbles: true,\n composed: true,\n }));\n this.requestUpdate();\n } catch {\n if (controller.signal.aborted)\n return;\n node.children = [];\n this.#pendingNode = undefined;\n this.#pendingController = undefined;\n this.requestUpdate();\n }\n }\n\n #onSegmentMenuCommand(e: CustomEvent, node: TreeNode, depth: number) {\n const key = e.detail.command;\n if (this.leadingCaret) {\n const child = node.children?.find(c => c.item.key === key);\n if (child) {\n this.#onChildClick(child, depth + 1);\n return;\n }\n if (this.#currentLeadingSiblings) {\n const sibling = this.#currentLeadingSiblings.find(c => c.item.key === key);\n if (sibling) {\n this.#onChildClick(sibling, depth);\n }\n this.#currentLeadingSiblings = undefined;\n return;\n }\n }\n const child = node.children?.find(c => c.item.key === key);\n if (child) {\n this.#onChildClick(child, depth + 1);\n }\n }\n\n #currentLeadingSiblings: TreeNode[] | undefined = undefined;\n\n #getSiblingMenuItems(pathNodes: TreeNode[], index: number): unknown {\n if (index === 0) {\n if (!this.hideRoot || !this.root)\n return [];\n const siblings = sortNodesByLabel(this.root.children ?? []);\n this.#currentLeadingSiblings = siblings;\n return siblings.map(sibling => html`\n <ixfx-menu-item\n label=\"${sibling.item.label}\"\n command=\"${sibling.item.key}\"\n icon-name=\"${sibling.item.icon ?? nothing}\"\n @click=${() => {\n this.#onChildClick(sibling, index);\n }}\n ></ixfx-menu-item>\n `);\n }\n const parent = pathNodes[index - 1];\n const siblings = sortNodesByLabel(parent.children ?? []);\n this.#currentLeadingSiblings = siblings;\n return siblings.map(sibling => html`\n <ixfx-menu-item\n label=\"${sibling.item.label}\"\n command=\"${sibling.item.key}\"\n icon-name=\"${sibling.item.icon ?? nothing}\"\n @click=${() => {\n this.#onChildClick(sibling, index);\n }}\n ></ixfx-menu-item>\n `);\n }\n\n #onChildClick(node: TreeNode, depth: number) {\n this._openIdx = -1;\n this.#setSelected(node);\n this.dispatchEvent(new CustomEvent<CrumbNavigationItemClickDetail>(`item-click`, {\n detail: { node, depth },\n bubbles: true,\n composed: true,\n }));\n }\n\n #onUpClick(): void {\n const r = this.root;\n const sel = this.selectedNode;\n if (!r || !sel)\n return;\n\n const path = this.#findPath(r, sel);\n if (!path || path.length <= 1)\n return;\n\n const parent = path[path.length - 2];\n this.#setSelected(parent);\n }\n\n /** Navigate to a node by key path. Returns false if any key is not found in already-loaded children. */\n navigateTo(keys: readonly string[]): boolean {\n if (!this.root?.children)\n return false;\n let current: TreeNode | undefined = this.root;\n for (const key of keys) {\n const found: TreeNode | undefined = current?.children?.find(n => n.item.key === key);\n if (!found)\n return false;\n current = found;\n }\n if (current && current !== this.root) {\n this.#setSelected(current);\n }\n return true;\n }\n\n /** Navigate to the first node matching the predicate. Returns false if not found. */\n navigateToNode(predicate: (node: TreeNode) => boolean): boolean {\n if (!this.root)\n return false;\n const keyPath = this.#findNodePath(this.root.children ?? [], predicate);\n if (!keyPath)\n return false;\n return this.navigateTo(keyPath);\n }\n\n /** `TreeComponent` parity — a crumb path always follows the selection, so this just navigates to `key`. */\n revealKey(key: string): boolean {\n return this.navigateToNode(n => n.item.key === key);\n }\n\n /** `TreeComponent` parity — a crumb path is a single selection, so only the last node is kept. */\n selectMany(nodes: Iterable<TreeNode>): void {\n const last = [...nodes].at(-1);\n if (last)\n this.select(last);\n else\n this.clearSelection();\n }\n\n #findNodePath(\n nodes: TreeNode[],\n predicate: (node: TreeNode) => boolean,\n prefix: string[] = [],\n ): string[] | undefined {\n for (const node of nodes) {\n const path = [...prefix, node.item.key];\n if (predicate(node))\n return path;\n if (node.children?.length) {\n const result = this.#findNodePath(node.children, predicate, path);\n if (result)\n return result;\n }\n }\n return undefined;\n }\n\n #onMenuCommand(e: CustomEvent) {\n const node = this.selectedNode;\n if (!node?.children)\n return;\n\n const key = e.detail.command;\n const child = node.children.find(c => c.item.key === key);\n if (child) {\n const depth = this.root ? (this.#findPath(this.root, node)?.length ?? 1) : 1;\n this.#onChildClick(child, depth);\n }\n }\n\n render() {\n const r = this.root;\n const sel = this.selectedNode;\n\n if (!r || !sel) {\n return html``;\n }\n\n this.inputMode = this.tickled.inputMode;\n\n let pathNodes = this.#findPath(r, sel) ?? [r];\n if (this.hideRoot && pathNodes.length > 1) {\n pathNodes = pathNodes.slice(1);\n }\n const _hasChildOptions = this.#hasChildOptions();\n\n const isAtRoot = (() => {\n const fullPath = this.#findPath(r, sel) ?? [r];\n return fullPath.length <= 1;\n })();\n\n const parts: Array<ReturnType<typeof html>> = [];\n let segmentId = 0;\n\n pathNodes.forEach((node, i) => {\n const isLast = i === pathNodes.length - 1;\n const isPending = this.#pendingNode === node;\n const isOpen = this._openIdx === i;\n const hasChildren = node.item.isLeaf !== true && (node.children === undefined || node.children.length > 0);\n const isTickled = this.tickled.isTickled(i);\n\n const showLeadingCaret = this.leadingCaret && (i > 0 || this.hideRoot) && hasChildren;\n const showTrailingCaret = (!this.leadingCaret && hasChildren) || (this.leadingCaret && isLast && hasChildren);\n\n const siblingMenuItems = showLeadingCaret ? this.#getSiblingMenuItems(pathNodes, i) : [];\n const childMenuItems = sortNodesByLabel(node.children ?? []).map(c => html`\n <ixfx-menu-item\n label=\"${c.item.label}\"\n command=\"${c.item.key}\"\n icon-name=\"${c.item.icon ?? nothing}\"\n ></ixfx-menu-item>\n `);\n\n if (this.caretEmbedded) {\n const canTruncate = !this.noTruncate && !isLast && !isTickled;\n\n parts.push(html`\n <div class=\"item crumb-segment ${isTickled ? `tickled` : ``} ${canTruncate ? `truncatable` : ``} ${this.leadingCaret ? `leading-caret` : ``} ${isLast ? `last-label` : ``}\" data-segment-id=\"${i}\" data-path-index=\"${i}\"\n @click=${(e: MouseEvent) => {\n if ((e.target as HTMLElement).closest(`.caret`))\n return; this.#onLabelClick(node, i);\n }}\n >\n ${showLeadingCaret\n ? html`\n <span class=\"caret ${isOpen ? `open` : ``} ${isPending ? `pending` : ``}\">\n ${isPending\n ? html`<span class=\"loading-spinner\"></span>`\n : html`\n <ixfx-menu-trigger mode=\"trigger\" label=\"›\" .tabStop=${false} @menu-command=${(e: CustomEvent) => this.#onSegmentMenuCommand(e, node, i)}>\n <ixfx-menu-container slot=\"menu\">\n ${siblingMenuItems}\n </ixfx-menu-container>\n </ixfx-menu-trigger>\n `\n }\n </span>\n `\n : nothing\n }\n <span class=\"label\">${node.item.label}</span>\n ${showTrailingCaret\n ? html`\n <span class=\"caret ${isOpen ? `open` : ``} ${isPending ? `pending` : ``}\">\n ${isPending\n ? html`<span class=\"loading-spinner\"></span>`\n : html`\n <ixfx-menu-trigger mode=\"trigger\" label=\"›\" .tabStop=${false} placement=\"right-start\" @menu-command=${(e: CustomEvent) => this.#onSegmentMenuCommand(e, node, i)}>\n <ixfx-menu-container slot=\"menu\">\n ${childMenuItems}\n </ixfx-menu-container>\n </ixfx-menu-trigger>\n `\n }\n </span>\n `\n : nothing\n }\n </div>\n `);\n } else {\n const leadingCaretTickled = showLeadingCaret ? this.tickled.isTickled(segmentId) : false;\n if (showLeadingCaret) {\n parts.push(html`\n <div class=\"item crumb-segment ${leadingCaretTickled ? `tickled` : ``}\" data-segment-id=\"${segmentId}\" data-path-index=\"${i}\"\n @click=${(e: MouseEvent) => {\n const trigger = (e.target as HTMLElement).closest(`.crumb-segment`)?.querySelector(`ixfx-menu-trigger`);\n if (trigger)\n trigger.openMenu();\n }}\n >\n <span class=\"caret ${isOpen ? `open` : ``} ${isPending ? `pending` : ``}\">\n ${isPending\n ? html`<span class=\"loading-spinner\"></span>`\n : html`\n <ixfx-menu-trigger mode=\"trigger\" label=\"›\" .tabStop=${false} placement=\"right-start\" @menu-command=${(e: CustomEvent) => this.#onSegmentMenuCommand(e, node, i)}>\n <ixfx-menu-container slot=\"menu\">\n ${siblingMenuItems}\n </ixfx-menu-container>\n </ixfx-menu-trigger>\n `\n }\n </span>\n </div>\n `);\n segmentId++;\n }\n const labelTickled = this.tickled.isTickled(segmentId);\n const canTruncate = !this.noTruncate && !isLast && !labelTickled;\n parts.push(html`\n <div class=\"item crumb-segment ${labelTickled ? `tickled` : ``} ${canTruncate ? `truncatable` : ``} ${isLast ? `last-label` : ``}\" data-segment-id=\"${segmentId}\" data-path-index=\"${i}\"\n @click=${(e: MouseEvent) => {\n if ((e.target as HTMLElement).closest(`.caret`))\n return; this.#onLabelClick(node, i);\n }}\n >\n <span class=\"label\">${node.item.label}</span>\n </div>\n `);\n segmentId++;\n if (showTrailingCaret) {\n const trailingCaretTickled = this.tickled.isTickled(segmentId);\n parts.push(html`\n <div class=\"item crumb-segment ${trailingCaretTickled ? `tickled` : ``}\" data-segment-id=\"${segmentId}\" data-path-index=\"${i}\"\n @click=${(e: MouseEvent) => {\n const trigger = (e.target as HTMLElement).closest(`.crumb-segment`)?.querySelector(`ixfx-menu-trigger`);\n if (trigger)\n trigger.openMenu();\n }}\n >\n <span class=\"caret ${isOpen ? `open` : ``} ${isPending ? `pending` : ``}\">\n ${isPending\n ? html`<span class=\"loading-spinner\"></span>`\n : html`\n <ixfx-menu-trigger mode=\"trigger\" label=\"›\" .tabStop=${false} @menu-command=${(e: CustomEvent) => this.#onSegmentMenuCommand(e, node, i)}>\n <ixfx-menu-container slot=\"menu\">\n ${childMenuItems}\n </ixfx-menu-container>\n </ixfx-menu-trigger>\n `\n }\n </span>\n </div>\n `);\n segmentId++;\n }\n }\n });\n\n return html`\n <div class=\"crumb-wrapper\">\n ${this.withUp\n ? html`\n <button\n class=\"up-button\"\n ?disabled=${isAtRoot}\n aria-label=\"Go up one level\"\n @click=${this.#onUpClick}\n >\n <span class=\"label\"><ixfx-icon name=\"folder-up\"></ixfx-icon></span>\n </button>\n `\n : nothing}\n <div\n class=\"host-container scroll-fade-x\"\n tabindex=\"0\"\n @focus=${this.#onFocus}\n @blur=${this.#onBlur}\n @keydown=${this.#onKeyDown}\n @click=${this.#onHostClick}\n @menu-trigger-close=${this.#onMenuTriggerClose}\n @mouseout=${(e: MouseEvent) => this.tickled.handlePointerLeave(e as PointerEvent)}\n >\n <div class=\"parts\"\n @mouseover=${(e: MouseEvent) => {\n if (this.#isWheelScrolling)\n return;\n const target = e.target;\n if (!(target instanceof HTMLElement))\n return;\n const segment = target.closest(`.crumb-segment`) as HTMLElement | null;\n if (!segment)\n return;\n const segmentId = parseInt(segment.dataset.segmentId ?? ``, 10);\n if (Number.isNaN(segmentId))\n return;\n const pathIndex = parseInt(segment.dataset.pathIndex ?? ``, 10);\n const node = pathNodes[pathIndex];\n if (!node)\n return;\n this.tickled.handlePointerEnter(segmentId);\n this.dispatchEvent(new CustomEvent<TreeTickleDetail>(`tickle`, { detail: { node, depth: pathIndex }, bubbles: true, composed: true }));\n }}\n >${parts}${this.padEnding ? html`<div class=\"trailing\"></div>` : nothing}</div>\n ${this.showSuggestions ? this.#renderChildOptions() : nothing}\n </div>\n </div>\n `;\n }\n\n #renderChildOptions() {\n const s = this.selectedNode;\n if (s === undefined) {\n return nothing;\n }\n\n const isPending = this.#pendingNode === s;\n const children = s.children ?? [];\n\n if (children.length === 0 && !isPending) {\n return nothing;\n }\n\n if (isPending) {\n return html`\n <div class=\"horiz-select\">\n <div class=\"horiz-select-items\">\n <span class=\"loading-spinner\"></span>\n </div>\n </div>\n `;\n }\n\n return html`\n <ixfx-narrowed-text\n class=\"horiz-select\"\n selection-mode=\"single\"\n orientation=\"horizontal\"\n nowrap\n width=${this.#getChildOptionsWidth()}\n @change=${this.#onNarrowedTextChange}\n @narrowed-text-blur=${this.#onNarrowedTextBlur}\n @narrowed-text-shift-tab=${this.#onNarrowedTextShiftTab}\n >\n ${sortNodesByLabel(children).map(c => html`\n <span data-value=\"${c.item.key}\" data-label=\"${c.item.label}\"></span>\n `)}\n </ixfx-narrowed-text>\n `;\n }\n\n #onNarrowedTextChange(e: CustomEvent) {\n e.stopPropagation();\n const detail = e.detail as { item: { value: string } };\n const node = this.selectedNode;\n if (!node?.children)\n return;\n\n const child = node.children.find(c => c.item.key === detail.item.value);\n if (child) {\n const depth = this.root ? (this.#findPath(this.root, node)?.length ?? 1) : 1;\n this.#onChildClick(child, depth);\n }\n }\n\n #getChildOptionsWidth(): string {\n return `var(--child-options-width, 50ch)`;\n }\n\n static styles = [themeFallbacks, tickledStyles, tickledItemStyles, scrollFadeStyles(`x`), css`\n :host {\n --crumb-item-bg: var(--item-bg, transparent);\n --crumb-item-bg-tickled: var(--item-bg-tickled);\n --crumb-item-text-tickled: var(--item-text-tickled);\n --crumb-item-border: var(--item-border);\n --crumb-item-border-tickled: var(--item-border-tickled);\n --crumb-item-padding: var(--space-s, 2px);\n --crumb-item-border-radius: var(--item-border-radius);\n --crumb-item-gap: var(--item-gap, var(--space-xs));\n --crumb-separator: var(--surface-muted-text);\n --crumb-truncate-min-width: 10ch;\n display: flex;\n width: 100%;\n }\n\n /* Outline goes on :host, not .host-container: .host-container carries the\n * scroll-fade mask-image, and CSS masks clip everything painted outside\n * the masked box - including an outline, which paints outside the border edge. */\n :host(:focus-within) {\n outline: 2px solid var(--accent);\n outline-offset: 2px;\n }\n\n .crumb-wrapper {\n display: flex;\n align-items: center;\n gap: var(--crumb-item-gap);\n width: 100%;\n }\n\n .up-button {\n box-sizing: border-box;\n display: inline-flex;\n align-items: center;\n justify-content: center;\n flex-shrink: 0;\n background: var(--crumb-item-bg);\n border: var(--crumb-item-border);\n border-radius: var(--crumb-item-border-radius);\n padding: 0;\n margin: 0;\n cursor: pointer;\n color: inherit;\n font: inherit;\n line-height: normal;\n }\n\n .up-button:disabled {\n opacity: 0.5;\n cursor: not-allowed;\n }\n\n .up-button:hover:not(:disabled) {\n background: var(--crumb-item-bg-tickled);\n border-color: var(--crumb-item-border-tickled);\n }\n\n .up-button .label {\n display: flex;\n align-items: center;\n padding: var(--crumb-item-padding);\n }\n\n .up-button .label ixfx-icon {\n display: block;\n width: 1em;\n height: 1em;\n pointer-events: none;\n }\n\n /* Edge fade (shows/hides based on scroll position) comes from the\n * shared .scroll-fade-x class - see ../styles/scroll-fade.ts */\n .host-container {\n display: flex;\n flex: 1;\n min-width: 0;\n outline: none;\n overflow: scroll;\n scroll-snap-type: x mandatory;\n scrollbar-width: none;\n overscroll-behavior: none;\n }\n\n .host-container::-webkit-scrollbar {\n display: none;\n }\n\n .parts {\n display: flex;\n gap: var(--space-s);\n }\n\n .trailing {\n flex-shrink: 0;\n }\n\n .crumb-segment {\n display: flex;\n align-items: center;\n flex-shrink: 0;\n background: var(--crumb-item-bg);\n border: var(--crumb-item-border);\n border-radius: var(--crumb-item-border-radius);\n padding:0;\n }\n\n .crumb-segment.leading-caret {\n flex-direction: row;\n }\n\n .crumb-segment.tickled {\n background: var(--crumb-item-bg-tickled);\n border-color: var(--crumb-item-border-tickled);\n color: var(--crumb-item-text-tickled);\n flex-shrink: 0;\n min-width: auto;\n }\n\n .crumb-segment.truncatable {\n flex-shrink: 1;\n min-width: min(var(--crumb-truncate-min-width), auto);\n overflow: hidden;\n }\n\n .crumb-segment.truncatable .label {\n overflow: hidden;\n text-overflow: ellipsis;\n white-space: nowrap;\n min-width: 0;\n }\n\n .label {\n padding: var(--crumb-item-padding);\n cursor: pointer;\n white-space: nowrap;\n color: inherit;\n }\n\n .crumb-segment.last-label .label {\n color: var(--crumb-last-label-color, inherit);\n font-style: var(--crumb-last-label-font-style, inherit);\n font-weight: var(--crumb-last-label-font-weight, inherit);\n text-decoration: var(--crumb-last-label-text-decoration, inherit);\n text-underline-offset: var(--crumb-last-label-text-underline-offset, auto);\n }\n\n .crumb-segment.tickled .label {\n color: var(--crumb-item-text-tickled);\n overflow: visible;\n text-overflow: clip;\n }\n\n .crumb-segment ixfx-menu-trigger {\n --ixfx-button-padding: var(--space-s, 2px);\n }\n\n .caret {\n position: relative;\n cursor: pointer;\n color: var(--crumb-separator);\n display: inline-flex;\n align-items: center;\n justify-content: center;\n transition: all 0.2s ease-in-out;\n }\n\n .caret.open {\n background: color-mix(in srgb, var(--surface-5) 40%, transparent);\n }\n\n .caret.pending {\n display: inline-flex;\n }\n\n .caret > ixfx-menu-trigger {\n display: inline-flex;\n margin: 0;\n --_trigger-hover-bg: transparent;\n --_trigger-hover-opacity: 0.6;\n }\n\n .caret > ixfx-menu-trigger::part(base) {\n background: none;\n border: none;\n color: inherit;\n cursor: pointer;\n font-size: inherit;\n line-height: 1;\n }\n\n .caret > ixfx-menu-trigger::part(base):hover {\n background: none;\n opacity: 0.6;\n }\n\n .separator {\n margin-left: var(--crumb-item-gap);\n margin-right: var(--crumb-item-gap);\n color: var(--crumb-separator);\n }\n\n .separator-trigger {\n display: inline-flex;\n margin-left: var(--crumb-item-gap);\n margin-right: var(--crumb-item-gap);\n --_trigger-hover-bg: transparent;\n --_trigger-hover-opacity: 0.6;\n }\n\n .separator-trigger::part(base) {\n background: none;\n border: none;\n color: var(--crumb-separator);\n padding: 0;\n cursor: pointer;\n font-size: inherit;\n line-height: 1;\n }\n\n .separator-trigger::part(base):hover {\n background: none;\n opacity: 0.6;\n }\n\n .separator-trigger.tickled::part(base) {\n }\n\n ixfx-menu-trigger {\n display: none;\n }\n\n .horiz-select > ixfx-menu-trigger {\n display: inline-flex;\n }\n\n .horiz-select {\n display: flex;\n min-width: 5ch;\n }\n\n .loading-spinner {\n display: inline-block;\n width: 12px;\n height: 12px;\n border: 2px solid var(--surface-5);\n border-top-color: var(--accent);\n border-radius: 50%;\n animation: crumb-spin 0.7s linear infinite;\n }\n\n @keyframes crumb-spin {\n to { transform: rotate(360deg); }\n }\n\n ::slotted(*), option {\n user-select: none;\n scroll-snap-align: start;\n }\n `];\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n \"ixfx-crumb-navigation\": CrumbNavigationElement;\n }\n}\n\nexport interface CrumbNavigationElementEventMap extends TreeComponentEventMap {\n 'item-click': TreeItemClickEvent;\n 'expand': TreeExpandEvent;\n 'select': TreeSelectEvent;\n 'tickle': TreeTickleEvent;\n 'activate': TreeActivateEvent;\n}\n\nexport interface CrumbNavigationElement {\n addEventListener: (<K extends keyof CrumbNavigationElementEventMap>(\n type: K,\n listener: (this: CrumbNavigationElement, event: CrumbNavigationElementEventMap[K]) => void,\n options?: boolean | AddEventListenerOptions,\n ) => void) & ((\n type: string,\n listener: EventListenerOrEventListenerObject,\n options?: boolean | AddEventListenerOptions,\n ) => void);\n}\n"],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"data-controller-DOlmqNKb.js","names":["#host","#opts","#provider","#items","#loading","#loaded","#total","#error","#abort","#consume","#applyBatch","#consumeStream","#handleError"],"sources":["../src/common/data-controller.ts"],"sourcesContent":["import type { ReactiveController, ReactiveControllerHost } from 'lit';\nimport type { DataBatch, DataProviderResult, IDataProvider } from './data-provider.js';\n\nexport type DataControllerOptions = {\n /**\n * Clear accumulated items immediately when request() is called.\n * When false, stale items remain visible while the new request is in-flight\n * (useful for re-query-on-keystroke patterns — avoids a blank flash).\n * Default: true.\n */\n clearOnRequest?: boolean;\n /**\n * Called when the provider throws or rejects. Useful for logging without\n * coupling the error to render logic.\n */\n onError?: (err: unknown) => void;\n};\n\nfunction isAsyncIterable<T>(v: unknown): v is AsyncIterable<T> {\n return typeof v === `object` && v !== null && Symbol.asyncIterator in v;\n}\n\n/**\n * Lit ReactiveController that manages one active data provider request at a time.\n *\n * Handles all three provider return modes (sync, async one-shot, streaming),\n * tracks progress, and cancels in-flight requests when a new one starts.\n * Calls host.requestUpdate() on every state change so the component re-renders\n * automatically.\n *\n * @typeParam TQuery - The query/scope type passed to the provider.\n * @typeParam TItem - The item type produced by the provider.\n *\n * @example\n * ```ts\n * class MyList extends LitElement {\n * #data = new DataController<string, MyItem>(this, myProvider);\n *\n * protected override render() {\n * return html`\n * ${this.#data.loading ? html`<span>Loading…</span>` : nothing}\n * ${this.#data.items.map(item => html`<div>${item.label}</div>`)}\n * `;\n * }\n * }\n * ```\n */\nexport class DataController<TQuery, TItem> implements ReactiveController {\n readonly #host: ReactiveControllerHost;\n readonly #opts: Required<Omit<DataControllerOptions, `onError`>> & Pick<DataControllerOptions, `onError`>;\n\n #provider: IDataProvider<TQuery, TItem> | undefined;\n #abort: AbortController | undefined;\n\n #items: readonly TItem[] = [];\n #loading = false;\n #loaded = 0;\n #total: number | undefined;\n #error: unknown;\n\n constructor(\n host: ReactiveControllerHost,\n provider?: IDataProvider<TQuery, TItem>,\n options?: DataControllerOptions,\n ) {\n this.#host = host;\n this.#provider = provider;\n this.#opts = {\n clearOnRequest: options?.clearOnRequest ?? true,\n onError: options?.onError,\n };\n host.addController(this);\n }\n\n // ---- ReactiveController lifecycle ----\n\n hostConnected(): void {}\n\n hostDisconnected(): void {\n this.cancel();\n }\n\n // ---- Configuration ----\n\n get provider(): IDataProvider<TQuery, TItem> | undefined {\n return this.#provider;\n }\n\n set provider(value: IDataProvider<TQuery, TItem> | undefined) {\n this.#provider = value;\n }\n\n // ---- Reactive state (read-only) ----\n\n /** The currently accumulated items. */\n get items(): readonly TItem[] {\n return this.#items;\n }\n\n /** True while a provider call is pending or a stream is still open. */\n get loading(): boolean {\n return this.#loading;\n }\n\n /** Number of items accumulated so far in the current request. */\n get loaded(): number {\n return this.#loaded;\n }\n\n /**\n * Provider's latest estimate of the total number of items expected.\n * Undefined when the provider has not reported a total.\n */\n get total(): number | undefined {\n return this.#total;\n }\n\n /**\n * Progress as a 0–1 value, or undefined when total is unknown.\n * Derived from loaded / total.\n */\n get progress(): number | undefined {\n if (this.#total === undefined || this.#total === 0)\n return undefined;\n return Math.min(this.#loaded / this.#total, 1);\n }\n\n /** The last error thrown by the provider, or undefined if the last request succeeded. */\n get error(): unknown {\n return this.#error;\n }\n\n // ---- Control ----\n\n /**\n * Cancel any in-flight request and start a new one.\n * Clears items immediately unless clearOnRequest was set to false.\n */\n request(query: TQuery): void {\n this.cancel();\n\n if (!this.#provider)\n return;\n\n if (this.#opts.clearOnRequest) {\n this.#items = [];\n this.#loaded = 0;\n }\n this.#total = undefined;\n this.#error = undefined;\n this.#loading = true;\n this.#host.requestUpdate();\n\n this.#abort = new AbortController();\n const { signal } = this.#abort;\n\n this.#consume(this.#provider(query, signal), signal);\n }\n\n /** Abort any in-flight request without issuing a new one. */\n cancel(): void {\n this.#abort?.abort();\n this.#abort = undefined;\n if (this.#loading) {\n this.#loading = false;\n this.#host.requestUpdate();\n }\n }\n\n // ---- Internal ----\n\n #consume(result: DataProviderResult<TItem>, signal: AbortSignal): void {\n if (Array.isArray(result)) {\n this.#applyBatch({ items: result }, signal);\n this.#loading = false;\n this.#host.requestUpdate();\n } else if (isAsyncIterable<DataBatch<TItem>>(result)) {\n this.#consumeStream(result, signal);\n } else {\n // Promise (async one-shot)\n (result as Promise<readonly TItem[]>).then(\n (items) => {\n if (signal.aborted)\n return;\n this.#applyBatch({ items }, signal);\n this.#loading = false;\n this.#host.requestUpdate();\n },\n (err: unknown) => {\n if (signal.aborted)\n return;\n this.#handleError(err);\n },\n );\n }\n }\n\n async #consumeStream(stream: AsyncIterable<DataBatch<TItem>>, signal: AbortSignal): Promise<void> {\n try {\n for await (const batch of stream) {\n if (signal.aborted)\n return;\n this.#applyBatch(batch, signal);\n this.#host.requestUpdate();\n }\n } catch (err) {\n if (signal.aborted)\n return;\n this.#handleError(err);\n return;\n }\n if (!signal.aborted) {\n this.#loading = false;\n this.#host.requestUpdate();\n }\n }\n\n #applyBatch(batch: { items: readonly TItem[]; replace?: boolean; total?: number }, _signal: AbortSignal): void {\n if (batch.replace) {\n this.#items = [...batch.items];\n this.#loaded = batch.items.length;\n } else {\n this.#items = [...this.#items, ...batch.items];\n this.#loaded = this.#items.length;\n }\n if (batch.total !== undefined) {\n this.#total = batch.total;\n }\n }\n\n #handleError(err: unknown): void {\n this.#error = err;\n this.#loading = false;\n this.#opts.onError?.(err);\n this.#host.requestUpdate();\n }\n}\n"],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"data-display.d.ts","names":[],"sources":["../src/data-display/data-display.ts"],"mappings":";;KAOY;KASA,wBACV,cACA,OAAO,eACP,UAAU;KAGA;WACD;WACA;;cAWE,6BAA6B;;SACxB,sBAAM;EAqCtB;EAEA,eAAe;EACf,YAAY;;EAYH;EAKT,UAAU,QAAQ;EAalB,YAAY,YAAY,UAAS;EAqBjC,YAAY,GAAG;EAQf,WAAW,OAAO;EAMlB,YAAY,cAAc,QAAQ,QAAQ,uBAAuB;;QA6V3D;YACI;IACR,qBAAqB"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"data-display.js","names":["#config","#previousValues","#rangeStreams","#currentData","#renderAll","#walk","#cleanupPaths","#ensureRow","#updateRenderer","#hasDescendantConfig","#renderNestedDisplay","#determineAutoStyle","#renderText","#rendererTag","#getOrCreateRendererElement","#applyValue","#applyLed","#applyPlotOptions","#applyPlotXy","#formatTimeElapsed","customElement"],"sources":["../src/data-display/data-display.ts"],"sourcesContent":["import { rangeStream, round } from \"@ixfx/numbers\";\n\nimport { css, LitElement } from 'lit';\nimport { property } from 'lit/decorators.js';\nimport { themeFallbacks } from '../styles/fallbacks.js';\nimport { safeCustomElement as customElement } from '../util/custom-elements.js';\n\nexport type RendererStyle\n = | `led`\n | `plot`\n | `plot-xy`\n | `plot-heat`\n | `plot-histogram`\n | `time-elapsed`\n | `hide`;\n\nexport type ConfigEntry = readonly [\n path: string,\n style: RendererStyle,\n options?: Record<string, unknown>,\n];\n\nexport type FormattingOptions = {\n readonly precision?: number;\n readonly roundNumbers?: number;\n};\n\ntype ConfigRecord = {\n readonly style: RendererStyle;\n readonly options?: Record<string, unknown>;\n};\n\ntype RangeStream = ReturnType<typeof rangeStream>;\n\n@customElement(`ixfx-data-display`)\nexport class DataDisplayComponent extends LitElement {\n static override styles = [themeFallbacks, css`\n :host {\n display: block;\n width: fit-content;\n }\n section {\n background: var(--surface-3);\n color: var(--surface-2-text);\n border: var(--border);\n padding: var(--space-m);\n font-family: var(--font-mono);\n display: grid;\n grid-template-columns: auto auto;\n column-gap: var(--space-s);\n }\n .row {\n display: contents;\n }\n .row > label {\n font-weight: bold;\n text-align: end;\n justify-self: end;\n padding: 2px 0;\n }\n .row > :not(label) {\n padding: 2px 0;\n }\n .row > ixfx-led {\n align-self: center;\n }\n .value {\n font-variant-numeric: tabular-nums;\n white-space: pre;\n }\n `];\n\n @property({ type: Boolean })\n automap = false;\n\n previousValue: Record<string, unknown> | undefined;\n _container: HTMLElement;\n\n #config = new Map<string, ConfigRecord>();\n #previousValues = new Map<string, unknown>();\n #rangeStreams = new Map<string, RangeStream>();\n #currentData: Record<string, unknown> | undefined;\n\n constructor() {\n super();\n this._container = document.createElement(`section`);\n }\n\n override connectedCallback() {\n super.connectedCallback();\n this.renderRoot.append(this._container);\n }\n\n configure(config: ConfigEntry[]) {\n this.#config.clear();\n for (const [path, style, options] of config) {\n this.#config.set(path, { style, options });\n }\n this._container.innerHTML = ``;\n this.#previousValues.clear();\n this.#rangeStreams.clear();\n if (this.#currentData !== undefined) {\n this.#renderAll(this.#currentData);\n }\n }\n\n formatValue(v: unknown, options: FormattingOptions = {}): string {\n if (v === null)\n return `(null)`;\n if (v === undefined)\n return `(undefined)`;\n if (typeof v === `boolean`)\n return v ? `true` : `false`;\n if (typeof v === `string`)\n return `\"${v}\"`;\n if (typeof v === `number`) {\n let vAsNumber = v;\n if (options.roundNumbers !== undefined)\n vAsNumber = round(options.roundNumbers, v);\n if (options.precision !== undefined)\n return vAsNumber.toFixed(options.precision);\n const formatted = vAsNumber.toFixed(2);\n return vAsNumber >= 0 ? ` ${formatted}` : formatted;\n }\n return JSON.stringify(v);\n }\n\n displayData(o: Record<string, unknown> | unknown[]) {\n if (o === null) {\n this.innerHTML = ``;\n return;\n }\n this.#renderAll(o as Record<string, unknown>);\n }\n\n updateData(value: Record<string, unknown>) {\n this.#currentData = value;\n this.#renderAll(value);\n this.previousValue = value;\n }\n\n getOrCreate(path: string, init?: (parent: HTMLElement) => void): HTMLElement {\n const element = this.renderRoot.querySelector(`#${path}`) as HTMLElement | null;\n if (element !== null)\n return element;\n\n const elementCreated = document.createElement(`div`);\n elementCreated.id = path;\n if (init)\n init(elementCreated);\n this._container.append(elementCreated);\n return elementCreated;\n }\n\n #renderAll(data: Record<string, unknown>) {\n const activePaths = new Set<string>();\n this.#walk(data, ``, activePaths);\n this.#cleanupPaths(activePaths);\n }\n\n #walk(\n data: Record<string, unknown>,\n basePath: string,\n activePaths: Set<string>,\n ) {\n for (const [key, value] of Object.entries(data)) {\n const fullPath = basePath ? `${basePath}.${key}` : key;\n activePaths.add(fullPath);\n\n const config = this.#config.get(fullPath);\n\n if (config !== undefined) {\n if (config.style !== `hide`) {\n const row = this.#ensureRow(fullPath, key);\n this.#updateRenderer(row, fullPath, config.style, value, config.options);\n }\n continue;\n }\n\n if (typeof value === `object` && value !== null && !Array.isArray(value)) {\n if (this.#hasDescendantConfig(fullPath)) {\n this.#walk(value as Record<string, unknown>, fullPath, activePaths);\n } else if (this.automap) {\n const row = this.#ensureRow(fullPath, key);\n this.#renderNestedDisplay(row, value as Record<string, unknown>, true);\n } else {\n const row = this.#ensureRow(fullPath, key);\n this.#renderNestedDisplay(row, value as Record<string, unknown>);\n }\n } else {\n const autoStyle = this.#determineAutoStyle(value);\n if (autoStyle !== undefined) {\n const row = this.#ensureRow(fullPath, key);\n this.#updateRenderer(row, fullPath, autoStyle, value, undefined);\n } else {\n const row = this.#ensureRow(fullPath, key);\n this.#renderText(row, this.formatValue(value));\n }\n }\n }\n }\n\n #hasDescendantConfig(path: string): boolean {\n const prefix = path ? `${path}.` : ``;\n for (const configPath of this.#config.keys()) {\n if (configPath.startsWith(prefix))\n return true;\n }\n return false;\n }\n\n #determineAutoStyle(value: unknown): RendererStyle | undefined {\n if (!this.automap)\n return undefined;\n if (typeof value === `boolean`)\n return `led`;\n if (typeof value === `number`)\n return `plot`;\n return undefined;\n }\n\n #ensureRow(path: string, label: string): HTMLElement {\n const id = `path-${path}`;\n let row = this.renderRoot.querySelector(`#${CSS.escape(id)}`) as HTMLElement | null;\n if (row !== null)\n return row;\n\n row = document.createElement(`div`);\n row.id = id;\n row.classList.add(`row`);\n\n const labelEl = document.createElement(`label`);\n labelEl.textContent = label;\n row.append(labelEl);\n\n this._container.append(row);\n return row;\n }\n\n #updateRenderer(\n row: HTMLElement,\n path: string,\n style: RendererStyle,\n value: unknown,\n options?: Record<string, unknown>,\n ) {\n const tag = this.#rendererTag(style, value);\n if (tag === null)\n return;\n\n const el = this.#getOrCreateRendererElement(row, tag);\n if (el === null)\n return;\n\n this.#applyValue(el, tag, style, path, value, options);\n }\n\n #rendererTag(style: RendererStyle, value: unknown): string | null {\n switch (style) {\n case `hide`:\n return null;\n case `led`:\n return `ixfx-led`;\n case `plot`:\n if (typeof value === `number`)\n return `ixfx-plot-single-axis`;\n if (typeof value === `object` && value !== null)\n return `ixfx-plot-multi-axis`;\n return `span`;\n case `plot-xy`:\n return `ixfx-plot-xy-axis`;\n case `plot-heat`:\n case `plot-histogram`:\n return `ixfx-plot-histogram`;\n case `time-elapsed`:\n return `span`;\n }\n }\n\n #getOrCreateRendererElement(row: HTMLElement, tag: string): HTMLElement | null {\n const existing = row.querySelector(`:scope > [data-renderer]`) as HTMLElement | null;\n if (existing !== null) {\n if (existing.tagName.toLowerCase() === tag)\n return existing;\n existing.remove();\n }\n const el = document.createElement(tag);\n el.dataset.renderer = ``;\n if (tag.startsWith(`ixfx-plot`)) {\n (el as HTMLElement).style.height = `1.4em`;\n if (tag === `ixfx-plot-xy-axis`) {\n (el as HTMLElement).style.width = `1.4em`;\n } else {\n (el as HTMLElement).style.width = `5em`;\n }\n }\n row.append(el);\n return el;\n }\n\n #applyValue(\n el: HTMLElement,\n _tag: string,\n style: RendererStyle,\n path: string,\n value: unknown,\n options?: Record<string, unknown>,\n ) {\n const prev = this.#previousValues.get(path);\n const changed = prev !== value;\n\n switch (style) {\n case `led`:\n this.#applyLed(el, path, value, options);\n break;\n\n case `plot`:\n if (typeof value === `number`) {\n if (changed) {\n (el as any).add(value);\n }\n } else if (typeof value === `object` && value !== null && changed) {\n if (Array.isArray(value)) {\n const record: Record<string, number> = {};\n value.forEach((v: unknown, i: number) => {\n if (typeof v === `number`)\n record[String(i)] = v;\n });\n if (Object.keys(record).length > 0) {\n (el as any).addData(record);\n }\n } else {\n (el as any).addData(value as Record<string, number>);\n }\n }\n this.#applyPlotOptions(el, style, options);\n break;\n\n case `plot-xy`:\n if (changed) {\n this.#applyPlotXy(el, value);\n }\n this.#applyPlotOptions(el, style, options);\n break;\n // @ts-expect-error fallthrough allowed\n case `plot-heat`:\n el.style.setProperty(`--plot-histogram-bar-length`, `1`);\n // falls through\n case `plot-histogram`:\n if (typeof value === `number` && changed) {\n (el as any).add(value);\n }\n this.#applyPlotOptions(el, style, options);\n break;\n\n case `time-elapsed`:\n el.textContent = this.#formatTimeElapsed(value);\n break;\n }\n\n this.#previousValues.set(path, value);\n }\n\n #applyLed(el: HTMLElement, path: string, value: unknown, options?: Record<string, unknown>) {\n const led = el as any;\n\n if (typeof value === `boolean`) {\n led.lit = value;\n led.value = value ? 1 : 0;\n } else if (typeof value === `number`) {\n let rs = this.#rangeStreams.get(path);\n if (rs === undefined) {\n rs = rangeStream();\n this.#rangeStreams.set(path, rs);\n }\n const range = rs.seen(value);\n const normalized = range.max !== range.min\n ? (value - range.min) / (range.max - range.min)\n : 0.5;\n led.value = normalized;\n led.lit = normalized > 0.3;\n }\n\n if (options?.color !== undefined)\n led.color = options.color;\n }\n\n #applyPlotXy(el: HTMLElement, value: unknown) {\n const xy = el as any;\n\n if (Array.isArray(value) && value.length >= 2) {\n xy.add(value[0], value[1]);\n } else if (typeof value === `object` && value !== null) {\n const obj = value as Record<string, number>;\n if (`x` in obj && `y` in obj) {\n xy.add(obj.x, obj.y);\n } else {\n const entries = Object.entries(obj).filter(([_, v]) => typeof v === `number`);\n if (entries.length >= 2) {\n xy.add(entries[0][1], entries[1][1]);\n }\n }\n }\n }\n\n #applyPlotOptions(el: HTMLElement, _style: RendererStyle, options?: Record<string, unknown>) {\n if (options === undefined)\n return;\n\n const target = el as any;\n\n if (typeof options.capacity === `number`)\n target.capacity = options.capacity;\n if (typeof options.resolution === `number`)\n target.resolution = options.resolution;\n if (typeof options.drawStyle === `string`)\n target.drawStyle = options.drawStyle;\n if (typeof options.orientation === `string`)\n target.orientation = options.orientation;\n if (typeof options.layout === `string`)\n target.layout = options.layout;\n }\n\n #formatTimeElapsed(value: unknown): string {\n let timestamp: number;\n\n if (value instanceof Date) {\n timestamp = value.getTime();\n } else if (typeof value === `number`) {\n if (value > 1e12) {\n timestamp = value;\n } else {\n timestamp = Date.now();\n }\n } else if (typeof value === `string`) {\n timestamp = new Date(value).getTime();\n } else {\n return String(value);\n }\n\n if (Number.isNaN(timestamp))\n return String(value);\n\n const elapsed = Date.now() - timestamp;\n const abs = Math.abs(elapsed);\n\n if (abs < 1000)\n return `${abs}ms`;\n if (abs < 60000)\n return `${(abs / 1000).toFixed(1)}s`;\n if (abs < 3600000)\n return `${(abs / 60000).toFixed(1)}mins`;\n if (abs < 86400000)\n return `${(abs / 3600000).toFixed(1)}h`;\n return `${(abs / 86400000).toFixed(1)}d`;\n }\n\n #renderText(row: HTMLElement, text: string) {\n let valueEl = row.querySelector(`:scope > .value`) as HTMLElement | null;\n if (valueEl === null) {\n valueEl = document.createElement(`span`);\n valueEl.classList.add(`value`);\n row.append(valueEl);\n }\n valueEl.textContent = text;\n }\n\n #renderNestedDisplay(row: HTMLElement, data: Record<string, unknown>, automapChild = false) {\n let child = row.querySelector(`:scope > ixfx-data-display`) as DataDisplayComponent | null;\n if (child === null) {\n child = document.createElement(`ixfx-data-display`) as DataDisplayComponent;\n row.append(child);\n }\n child.automap = automapChild;\n child.updateData(data);\n }\n\n #cleanupPaths(activePaths: Set<string>) {\n const rows = this._container.querySelectorAll<HTMLElement>(`[id^=\"path-\"]`);\n for (const row of rows) {\n const path = row.id.slice(5);\n if (!activePaths.has(path)) {\n row.remove();\n this.#rangeStreams.delete(path);\n this.#previousValues.delete(path);\n }\n }\n }\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'ixfx-data-display': DataDisplayComponent;\n }\n}\n"],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"data-grid-Ck1Qx2H1.d.ts","names":[],"sources":["../src/data-grid/types.ts","../src/data-grid/data-grid.ts"],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"data-grid.js","names":["#nativeDrag","#prepareNativeDrag","#nativeDragging","#dragOriginKey","#startPostDragSuppressTimer","#createSearchAdapter","#viewportChangeRaf","#emitViewportChangeIfChanged","#postDragSuppressTimer","#searchRegistry","#searchKeyByRow","#rowSearchText","#effectiveSearchModes","#unregisterSearchCommands","#syncSearchCommands","#rowReflowTimer","#viewportResizeObserver","#measureViewport","#scheduleViewportChangeEmit","#appendInProgress","#noteFlatMutation","#prevFlatKeys","#dataGridRenderedOnce","#enteringRowKeys","#pointerEventSuppressess","#appendToFlat","#resortRaf","#visibleKeys","#lastViewportRenderedKeys","#lastViewportVisibleKeys","customElement"],"sources":["../src/data-grid/data-grid.ts"],"sourcesContent":["/* eslint-disable ts/no-unsafe-declaration-merging */\nimport type { CommandId, CommandRegistry } from '@clinth/ui-commands';\nimport type { ListSearchAdapter, ListSearchMode } from '../incr-search/index.js';\nimport type {\n ListDragEntry,\n ListDragPreviewRenderer,\n ListDragPreviewSourceResolver,\n ListNativeDragStartDetail,\n ListNativeDragStartEvent,\n} from '../interaction/list-drag-types.js';\nimport type { ListViewportChangeDetail, ListViewportChangeEvent } from '../interaction/list-viewport-types.js';\nimport type { DragGhost } from '../util/drag-ghost.js';\nimport type { BuiltInFormatterName, BuiltInFormatterOptions, DataGridCellOverflow, DataGridColumn, DataGridColumnMenu, DataGridEditability, DataGridEditorFactory, DataGridGetRowKey, DataGridGroupBy, DataGridGroupLabel, DataGridInteractionMode, DataGridSelectionMode, DataGridSortState, GlobalFormatter } from './types.js';\nimport { createCommandRegistry } from '@clinth/ui-commands';\nimport { css, html, LitElement, nothing } from 'lit';\nimport { property, query, state } from 'lit/decorators.js';\nimport { repeat } from 'lit/directives/repeat.js';\nimport { appearanceAbsent, appearanceColor } from '../common/item-appearance.js';\nimport {\n LIST_SEARCH_MODES,\n ListSearchController,\n listSearchStyles,\n registerListSearchCommands,\n} from '../incr-search/index.js';\nimport { listItemFadeKeyframes, TickledController, tickledItemStyles, tickledStyles } from '../interaction/index.js';\nimport { ListNativeDragController } from '../interaction/list-native-drag-controller.js';\nimport { themeFallbacks } from '../styles/fallbacks.js';\nimport { handleStyles } from '../styles/handle.js';\nimport { scrollFadeStyles } from '../styles/scroll-fade.js';\nimport { safeCustomElement as customElement } from '../util/custom-elements.js';\nimport { createDragGhost } from '../util/drag-ghost.js';\nimport '../icons/icon.js';\nimport '../menu/index.js';\nimport '../pan-text/pan-text.js';\n\n// Events\nexport type DataGridSortDetail = { readonly sort: DataGridSortState; readonly previous: DataGridSortState };\nexport type DataGridSortEvent = CustomEvent<DataGridSortDetail>;\nexport type DataGridSelectDetail = { readonly selectedKeys: ReadonlySet<string>; readonly previous: ReadonlySet<string> };\nexport type DataGridSelectEvent = CustomEvent<DataGridSelectDetail>;\nexport type DataGridColumnReorderDetail = { readonly from: number; readonly to: number; readonly columns: readonly DataGridColumn[] };\nexport type DataGridColumnReorderEvent = CustomEvent<DataGridColumnReorderDetail>;\nexport type DataGridColumnResizeDetail = { readonly key: string; readonly width: number };\nexport type DataGridColumnResizeEvent = CustomEvent<DataGridColumnResizeDetail>;\nexport type DataGridColumnVisibilityDetail = { readonly key: string; readonly visible: boolean };\nexport type DataGridColumnVisibilityEvent = CustomEvent<DataGridColumnVisibilityDetail>;\nexport type DataGridCellClickDetail = { readonly rowKey: string; readonly colKey: string; readonly rowIndex: number; readonly colIndex: number };\nexport type DataGridCellClickEvent = CustomEvent<DataGridCellClickDetail>;\nexport type DataGridCellEditDetail = { readonly rowKey: string; readonly colKey: string; readonly oldValue: unknown; readonly newValue: unknown };\nexport type DataGridCellEditEvent = CustomEvent<DataGridCellEditDetail>;\n\nexport type DataGridGroupChangeDetail = { readonly groupBy: DataGridGroupBy<unknown> | null };\nexport type DataGridGroupChangeEvent = CustomEvent<DataGridGroupChangeDetail>;\nexport type DataGridRowActivateDetail = { readonly rowKey: string; readonly row: unknown; readonly rowIndex: number };\nexport type DataGridRowActivateEvent = CustomEvent<DataGridRowActivateDetail>;\n\n/** Same shape as the list components' shared `ListViewportChangeDetail`. */\nexport type DataGridViewportChangeDetail = ListViewportChangeDetail;\nexport type DataGridViewportChangeEvent = ListViewportChangeEvent;\n\n/** Resolved per-cell appearance — see `DataGridRowLook` and `_cellLook`. */\ntype DataGridCellLook = {\n readonly textColor: string | undefined;\n readonly icon: unknown;\n readonly iconColor: string | undefined;\n readonly badge: unknown;\n};\n\nconst EMPTY_CELL_LOOK: DataGridCellLook = {\n textColor: undefined,\n icon: undefined,\n iconColor: undefined,\n badge: undefined,\n};\n\nexport interface DataGridElementEventMap {\n 'datagrid-sort': DataGridSortEvent;\n 'datagrid-select': DataGridSelectEvent;\n 'datagrid-column-reorder': DataGridColumnReorderEvent;\n 'datagrid-column-resize': DataGridColumnResizeEvent;\n 'datagrid-column-visibility': DataGridColumnVisibilityEvent;\n 'datagrid-cell-click': DataGridCellClickEvent;\n 'datagrid-cell-edit': DataGridCellEditEvent;\n 'datagrid-group-change': DataGridGroupChangeEvent;\n 'datagrid-row-activate': DataGridRowActivateEvent;\n 'datagrid-viewport-change': DataGridViewportChangeEvent;\n 'list-native-drag-start': ListNativeDragStartEvent<unknown>;\n}\n\nexport type {\n ListDragEntry,\n ListDragPreview,\n ListDragPreviewContext,\n ListDragPreviewRenderer,\n ListDragSource,\n ListNativeDragStartDetail,\n ListNativeDragStartEvent,\n} from '../interaction/list-drag-types.js';\n\nexport type {\n BuiltInFormatterName,\n BuiltInFormatterOptions,\n DataGridColumn,\n DataGridColumnMenu,\n DataGridDataType,\n DataGridEditability,\n DataGridEditorContext,\n DataGridEditorFactory,\n DataGridEditorType,\n DataGridGetRowKey,\n DataGridGroupBy,\n DataGridGroupLabel,\n DataGridInteractionMode,\n DataGridRowLook,\n DataGridSelectionMode,\n DataGridSortDirection,\n DataGridSortState,\n GlobalFormatter,\n} from './types.js';\n\n/** Shallow key-array equality, treating `undefined` (never dispatched) as different. */\nfunction sameKeys(a: readonly string[] | undefined, b: readonly string[]): boolean {\n if (a === undefined || a.length !== b.length)\n return false;\n for (let i = 0; i < a.length; i++) {\n if (a[i] !== b[i])\n return false;\n }\n return true;\n}\n\n@customElement(`ixfx-data-grid`)\nexport class DataGridElement extends LitElement {\n static override styles = [themeFallbacks, handleStyles, tickledStyles, tickledItemStyles, listItemFadeKeyframes, listSearchStyles, scrollFadeStyles(`x`), scrollFadeStyles(`y`), css`\n :host {\n --data-grid-row-height: 28px;\n --data-grid-header-height: 32px;\n --data-grid-bg: var(--surface-3);\n --data-grid-header-bg: var(--surface-2);\n --data-grid-border: var(--border);\n --data-grid-header-text: var(--surface-3-text);\n --data-grid-reorder-handle-width: 4px;\n /* How strongly the alternate (\"zebra\") row stands out from the base row\n background when [zebra-stripes] is set - a color-mix() percentage. */\n --data-grid-zebra-intensity: 6%;\n /* Duration of the width transition when a column is auto-sized via\n autoSizeColumn(). Read back in JS (_columnResizeAnimationMs) to know\n when the animation has finished, so keep it a plain time value. */\n --data-grid-column-resize-duration: 180ms;\n /* Dense 28px rows read badly under the global 30px full-strength fade,\n so default to a shorter, shallower edge hint. Consumers can override\n --scroll-fade-width / --scroll-fade-strength per instance. */\n --scroll-fade-width: 20px;\n --scroll-fade-strength: 0.8;\n position: relative;\n display: block;\n overflow: hidden;\n border: var(--data-grid-border);\n border-radius: var(--radius-m);\n background: var(--data-grid-bg);\n color: var(--surface-3-text);\n font-family: var(--font-family);\n font-size: var(--text-m);\n }\n :host(:focus-visible) { outline: 2px solid var(--accent); outline-offset: 2px; }\n .grid { display: flex; flex-direction: column; height: 100%; min-height: 200px; position: relative; }\n .header-bar {\n display: flex; align-items: stretch; height: var(--data-grid-header-height);\n background: var(--data-grid-header-bg); border-bottom: var(--data-grid-border);\n overflow: visible; flex-shrink: 0; position: relative;\n }\n .header-scroll {\n display: flex; flex: 1; overflow: hidden;\n /* Horizontal edge fade comes from the shared .scroll-fade-x class\n (see ../styles/scroll-fade.ts). Its scrollLeft is synced from the\n viewport in _onScroll, which drives its own scroll-timeline. */\n }\n .header-cell {\n display: flex; align-items: center; gap: var(--space-xs);\n padding: 0 var(--space-s); border-right: var(--border-subtle);\n flex-shrink: 0; user-select: none; cursor: pointer; position: relative;\n background: var(--data-grid-header-bg);\n box-sizing: border-box;\n }\n .header-cell[data-tickled] { background: var(--surface-5); }\n /* Applied to a header-cell / cell while its column is animating towards\n an autoSizeColumn() target width. */\n .header-cell.width-animating, .cell.width-animating {\n transition: width var(--data-grid-column-resize-duration, 180ms) ease-out;\n }\n @media (prefers-reduced-motion: reduce) {\n .header-cell.width-animating, .cell.width-animating { transition: none; }\n }\n .header-label { flex: 1; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }\n .sort-icon { display: inline-flex; align-items: center; opacity: 0.7; }\n .resize-handle {\n position: absolute; right: -4px; top: 0; bottom: 0; width: 8px; cursor: col-resize; z-index: 1;\n display: flex; align-items: stretch; justify-content: center;\n }\n .resize-handle::before {\n content: ''; width: 2px; margin: 2px 0; border-radius: 1px; background: var(--split-gutter-color, transparent);\n transition: background-color var(--transition, 0.15s ease-out);\n }\n .resize-handle:hover::before { background: var(--split-gutter-hover-color, var(--surface-6)); }\n .resize-handle[data-active]::before { background: var(--split-gutter-active-color, var(--accent)); }\n .reorder-handle { cursor: grab; opacity: 0; display: inline-flex; align-items: center; transition: opacity var(--transition, 0.15s ease-out); }\n .header-cell:hover .reorder-handle, .header-cell:focus-within .reorder-handle, .header-cell[drag-source] .reorder-handle { opacity: var(--ixfx-handle-opacity, 0.5); }\n .col-button { opacity: 0; pointer-events: none; display: inline-flex; align-items: center; justify-content: center; width: 20px; height: 20px; border-radius: var(--radius-s); cursor: pointer; flex-shrink: 0; margin-left: var(--space-xs); transition: opacity var(--transition, 0.15s ease-out), background var(--transition, 0.15s ease-out); }\n .col-button ixfx-icon { width: 14px; height: 14px; }\n .header-cell:hover .col-button, .header-cell:focus-within .col-button { opacity: 1; pointer-events: auto; }\n .col-button:hover { background: var(--surface-4); }\n .reorder-handle .ixfx-handle { --ixfx-handle-length: 14px; --ixfx-handle-thickness: var(--data-grid-reorder-handle-width, 10px); --ixfx-handle-dot-size: 3px; }\n .flyout-trigger { flex-shrink: 0; width: 36px; display: flex; align-items: center; justify-content: center; cursor: pointer; border-left: var(--border-subtle); background: var(--data-grid-header-bg); }\n .viewport { flex: 1; overflow: auto; position: relative; }\n /* Vertical edge fade from the shared .scroll-fade-y class\n (see ../styles/scroll-fade.ts). The mask lives on the viewport —\n below the header bar — so the top fade never covers the column\n headers. Reach/strength tune via --scroll-fade-width /\n --scroll-fade-strength (defaults set on :host above). */\n .spacer { position: relative; }\n .row.item {\n position: absolute; left: 0; right: 0; display: flex; align-items: stretch;\n gap: 0;\n height: var(--data-grid-row-height);\n /* Border width is always 1px, even when not visually shown (transparent),\n so hover/selection never changes the box size and shifts content. */\n border: 1px solid transparent;\n background: var(--item-bg);\n border-radius: var(--item-border-radius);\n padding: 0;\n box-sizing: border-box;\n /* Only background transitions - hover (\"tickled\") no longer changes\n border, so there is nothing else to animate. */\n transition: background var(--transition, 0.1s ease-out);\n }\n /* Zebra striping: alternate rows tint towards the text colour, which\n lightens in dark themes and darkens in light themes - so it reads as\n \"more contrast\" either way. The zebra-odd class is only applied when\n zebraStripes is set (see render()). Declared before .tickled /\n .selected so those states (same specificity) still win when a striped\n row is also hovered or selected. */\n .row.item.zebra-odd {\n background: color-mix(in oklch, transparent calc(100% - var(--data-grid-zebra-intensity, 6%)), var(--surface-3-text) var(--data-grid-zebra-intensity, 6%));\n }\n /* Hover: background only, no border change (avoids layout shift + colour flash). */\n .row.item.tickled { background: var(--item-bg-tickled); color: var(--item-text-tickled); }\n .row.item.selected { background: var(--item-bg-selected); border: var(--item-border-selected); color: var(--item-text-selected); }\n .row.item.selected.tickled { background: var(--item-bg-selected-tickled); }\n .row.item.dragging-origin { opacity: 0.6; }\n\n /* Insertion / removal animation. Only while [reflowing] — the ~0.3s after\n the row set changes — do rows slide (their top transitions) to make or\n close a gap; a freshly inserted row also fades in. Kept scoped so it\n never fires while scrolling the virtualised list. */\n :host([reflowing]) .row.item,\n :host([reflowing]) .group-row {\n transition: top var(--data-grid-row-move-duration, 200ms) cubic-bezier(0.2, 0, 0, 1);\n }\n .row.item.entering {\n animation: ixfx-list-item-in var(--data-grid-row-move-duration, 200ms) ease both;\n }\n @media (prefers-reduced-motion: reduce) {\n :host([reflowing]) .row.item, :host([reflowing]) .group-row { transition: none; }\n .row.item.entering { animation: none; }\n }\n .cell {\n flex-shrink: 0; display: flex; align-items: center; padding: 0 var(--space-s);\n overflow: hidden; text-overflow: ellipsis; white-space: nowrap; border-right: var(--border-subtle);\n box-sizing: border-box;\n font-variant-numeric: tabular-nums;\n }\n .cell.editable-text { cursor: text; }\n .cell input, .cell select { width: 100%; font: inherit; }\n /* Per-row icon / badge, enabled by nominating iconColumn / badgeColumn.\n The badge self-justifies to the cell's trailing edge; the value text\n keeps its own flex sizing so the cell still ellipsises. */\n .cell-icon {\n flex: none;\n display: inline-flex;\n align-items: center;\n justify-content: center;\n margin-inline-end: var(--data-grid-cell-icon-gap, 6px);\n width: var(--data-grid-cell-icon-size, 1em);\n height: var(--data-grid-cell-icon-size, 1em);\n }\n .cell-badge {\n flex: none;\n display: inline-flex;\n align-items: center;\n margin-inline-start: auto;\n padding-inline-start: var(--data-grid-badge-gap, 6px);\n }\n .checkbox-col { width: 28px; display: flex; align-items: center; justify-content: center; flex-shrink: 0; }\n ixfx-menu-trigger { flex-shrink: 0; border-left: var(--border-subtle); background: var(--data-grid-header-bg); display: flex; align-items: center; --ixfx-button-padding: var(--space-s) var(--space-m); min-width: 44px; min-height: var(--data-grid-header-height); justify-content: center; }\n .header-cell[drag-source] { opacity: 0.4; }\n .drop-caret {\n position: absolute; top: 0; bottom: 0; width: 2px;\n background: var(--accent); border-radius: 1px; pointer-events: none; z-index: 2;\n }\n .group-row {\n position: absolute; left: 0; right: 0; display: flex; align-items: center; gap: var(--space-s);\n height: var(--data-grid-row-height); background: transparent; color: var(--surface-3-text);\n border-bottom: 1px solid var(--border); font-weight: 600; padding: 0 var(--space-s);\n cursor: pointer; user-select: none;\n }\n .group-row .caret { transition: transform 0.15s; display: inline-flex; }\n .group-row.collapsed .caret { transform: rotate(-90deg); }\n .group-row .divider { flex: 1; height: 1px; background: var(--border); margin-left: var(--space-s); }\n .group-row .count { opacity: 0.6; font-weight: 400; font-size: 0.9em; }\n\n `];\n\n @property({ type: Array }) columns: DataGridColumn[] = [];\n @property({ type: Array }) rows: unknown[] = [];\n @property({ type: String, attribute: `selection-mode` }) selectionMode: DataGridSelectionMode = `single`;\n @property({ type: String, attribute: `interaction-mode` }) interactionMode: DataGridInteractionMode = `standard`;\n @property({ attribute: false }) sortState: DataGridSortState = null;\n @property({ type: Number, attribute: `row-height` }) rowHeight = 28;\n @property({ attribute: false }) getRowKey: DataGridGetRowKey<unknown> = (r: unknown, i: number) => (r as Record<string, unknown>).key as string ?? (r as Record<string, unknown>).id as string ?? String(i);\n @property({ attribute: false }) checkboxRenderer?: (checked: boolean) => unknown;\n @property({ attribute: false }) editable: boolean | ((row: unknown, col: DataGridColumn) => boolean) = false;\n @property({ type: String, reflect: true }) editability: DataGridEditability = `user`;\n @property({ type: String, attribute: `cell-overflow` }) cellOverflow: DataGridCellOverflow = `ellipsis`;\n @property({ type: Boolean, attribute: `zebra-stripes`, reflect: true }) zebraStripes = false;\n\n @property({ attribute: false }) groupBy: DataGridGroupBy<unknown> | null = null;\n @property({ type: Boolean, attribute: `allow-grouping` }) allowGrouping = false;\n @property({ attribute: false }) groupLabel: DataGridGroupLabel | undefined;\n /** Columns keys that can be grouped by; undefined = all groupable columns */\n @property({ attribute: false }) groupableColumns: string[] | undefined;\n @property({ type: Boolean, attribute: `cross-group-selection`, reflect: true }) crossGroupSelection = false;\n /**\n * `auto` (default): render the built-in header column/group menu.\n * `none`: don't render it — for hosts that supply their own column UI via\n * `column.visible` + `datagrid-column-visibility`.\n */\n @property({ type: String, attribute: `column-menu` }) columnMenu: DataGridColumnMenu = `auto`;\n @property({ attribute: false }) globalFormatter?: GlobalFormatter;\n\n // --- Per-row appearance \"nomination\" columns ---\n //\n // A grid has no per-item schema of its own, so the consumer nominates the\n // column that carries each appearance feature. The value itself is read off\n // the row, not off the cell's own column value — see `DataGridRowLook`.\n\n /**\n * Key of the column whose cell text takes the row's `textColor` — e.g. a\n * status column that renders a red \"Failed\" only on some rows.\n */\n @property({ type: String, attribute: `text-color-column` }) textColorColumn = ``;\n\n /**\n * Key of the column that renders the row's `icon` (tinted by `iconColor`).\n */\n @property({ type: String, attribute: `icon-column` }) iconColumn = ``;\n\n /**\n * Key of the column that renders the row's `badge`, right-justified in the\n * cell after the cell's own value.\n */\n @property({ type: String, attribute: `badge-column` }) badgeColumn = ``;\n\n /**\n * Predicate used by incremental filter-search (and callable directly). Rows\n * for which it returns `false` are dropped from the flat list — hidden from\n * view and navigation.\n */\n @property({ attribute: false }) filterPredicate?: (row: unknown) => boolean;\n\n /** Text a row is matched against by incremental search. Default: its visible cells joined by a space. */\n @property({ attribute: false }) rowSearchText?: (row: unknown) => string;\n\n /**\n * Space-separated subset of `navigate select filter` — limits which\n * incremental-search modes are offered. Unset ⇒ all three; empty ⇒ search\n * disabled. See `docs/infra-incremental.md`.\n */\n @property({ type: String, attribute: `search-modes`, reflect: true }) searchModes: string | undefined;\n\n /**\n * Enable native browser drag-and-drop for selectable rows. When true,\n * selectable rows become draggable and the grid emits\n * `list-native-drag-start` when a drag begins.\n */\n @property({ type: Boolean, attribute: `items-draggable`, reflect: true }) itemsDraggable = false;\n\n /**\n * Custom drag preview renderer (synchronous). Defaults to the shared\n * built-in HTML+canvas preview.\n */\n @property({ attribute: false }) dragPreviewRenderer: ListDragPreviewRenderer<unknown> | undefined;\n\n @property({ attribute: false }) dragPreviewSource: ListDragPreviewSourceResolver<unknown> | undefined;\n\n /**\n * Default icon name for column header buttons. Defaults to `ellipsis`.\n * Individual columns can override with `button: { icon: '...' }`.\n */\n @property({ type: String, attribute: `column-button-icon` }) columnButtonIcon = `ellipsis`;\n\n private _columnFormatters = new Map<string, (value: unknown) => unknown>();\n\n @state() private _resizingColKey: string | undefined = undefined;\n @state() private _animatingColKeys = new Set<string>();\n @state() private _selectedKeys = new Set<string>();\n @state() private _scrollTop = 0;\n @state() private _scrollLeft = 0;\n @state() private _viewportH = 300;\n @state() private _viewportW = 600;\n @state() private _collapsedGroups = new Set<string>();\n @state() private _editing: { rowKey: string; colKey: string } | null = null;\n @state() private _editingRow: string | null = null;\n @state() private _lastClick: { key: string; col: string; time: number } | null = null;\n @state() private _lastClickedCell: { rowKey: string; colKey: string } | null = null;\n @state() private _editValue: unknown = ``;\n\n @query(`.viewport`) private _viewportEl!: HTMLElement;\n @query(`.header-scroll`) private _headerScrollEl!: HTMLElement;\n #viewportResizeObserver?: ResizeObserver;\n\n private _tickled = new TickledController<string>(this, {\n getItems: () => this._flatKeys.map(k => ({ id: k, enabled: true })),\n onStateChange: () => this.requestUpdate(),\n hoverDisabled: () => this.#nativeDrag.isDragging,\n });\n\n #nativeDragging = false;\n #dragOriginKey: string | undefined;\n #postDragSuppressTimer = 0;\n #pointerEventSuppressess = new WeakMap<PointerEvent, boolean>();\n\n readonly #nativeDrag = new ListNativeDragController<unknown>(this, {\n source: `data-grid`,\n isEnabled: () => this.itemsDraggable && this.selectionMode !== `none` && this._flat.some(f => f.type === `row`),\n resolveEventToKey: (target) => {\n if (!(target instanceof Element))\n return undefined;\n // Column-header reorder uses pointer drag on `.header-cell` — never a row drag.\n if (target.closest?.(`.header-cell`))\n return undefined;\n const row = target.closest?.(`.row`) as HTMLElement | null;\n return row?.dataset.key;\n },\n prepareSelection: originKey => this.#prepareNativeDrag(originKey),\n getMetrics: () => ({ rowHeight: this.rowHeight }),\n getRenderer: () => this.dragPreviewRenderer,\n getDragPreviewSourceResolver: () => this.dragPreviewSource,\n dispatch: detail => this.dispatchEvent(new CustomEvent<ListNativeDragStartDetail<unknown>>(`list-native-drag-start`, {\n detail,\n bubbles: true,\n composed: true,\n cancelable: true,\n })),\n onActiveChange: (active, originKey) => {\n this.#nativeDragging = active;\n this.#dragOriginKey = active ? originKey : undefined;\n this.toggleAttribute(`data-native-dragging`, active);\n if (active) {\n const count = this._selectedKeys.size;\n this.setAttribute(`aria-label`, count <= 1 ? `Dragging 1 item` : `Dragging ${count} items`);\n } else {\n this.removeAttribute(`aria-label`);\n }\n this.requestUpdate();\n },\n onEnd: () => {\n this.#nativeDragging = false;\n this.#dragOriginKey = undefined;\n this.toggleAttribute(`data-native-dragging`, false);\n this.removeAttribute(`aria-label`);\n this.#startPostDragSuppressTimer();\n },\n });\n\n #prepareNativeDrag(originKey: string): { origin: ListDragEntry<unknown>; selected: Array<ListDragEntry<unknown>> } | undefined {\n const rows = this._flat.filter(f => f.type === `row`);\n if (!rows.some(f => f.key === originKey))\n return undefined;\n if (!this._selectedKeys.has(originKey))\n this._replaceSelection(originKey);\n const selected: Array<ListDragEntry<unknown>> = [];\n let displayIndex = 0;\n for (const entry of rows) {\n if (!this._selectedKeys.has(entry.key)) {\n displayIndex++;\n continue;\n }\n const rowEl = this.renderRoot.querySelector(`.row[data-key=\"${CSS.escape(entry.key)}\"]`) ?? undefined;\n selected.push({\n key: entry.key,\n index: displayIndex,\n item: entry.row,\n ...(rowEl ? { element: rowEl as Element } : {}),\n });\n displayIndex++;\n }\n const origin = selected.find(entry => entry.key === originKey);\n if (!origin)\n return undefined;\n return { origin, selected };\n }\n\n #startPostDragSuppressTimer(): void {\n if (this.#postDragSuppressTimer)\n clearTimeout(this.#postDragSuppressTimer);\n this.#postDragSuppressTimer = window.setTimeout(() => {\n this.#postDragSuppressTimer = 0;\n }, 0);\n }\n\n private _sortedRows: unknown[] = [];\n private _flat: Array<{ type: `group`; key: string; label: string; count: number } | { type: `row`; key: string; row: unknown; idx: number }> = [];\n private _flatKeys: string[] = [];\n\n #searchRegistry: CommandRegistry<unknown> | undefined;\n #unregisterSearchCommands: (() => void) | undefined;\n #searchKeyByRow = new Map<unknown, string>();\n\n /** Incremental search (navigate / select / filter). See `docs/infra-incremental.md`. */\n readonly search = new ListSearchController<unknown>(this, {\n adapter: this.#createSearchAdapter(),\n });\n\n /** Command registry carrying this grid's `list.search.*` commands. */\n get registry(): CommandRegistry<unknown> | undefined {\n return this.#searchRegistry;\n }\n\n #rowSearchText(row: unknown): string {\n if (this.rowSearchText)\n return this.rowSearchText(row);\n const rec = row as Record<string, unknown>;\n return this._visibleColumns.map(c => String(rec[c.key] ?? ``)).join(` `);\n }\n\n #createSearchAdapter(): ListSearchAdapter<unknown> {\n return {\n getItems: () => {\n this.#searchKeyByRow.clear();\n this._sortedRows.forEach((r, i) => this.#searchKeyByRow.set(r, this.getRowKey(r, i)));\n return this._sortedRows;\n },\n getLabel: row => this.#rowSearchText(row),\n getKey: row => this.#searchKeyByRow.get(row) ?? String(this._sortedRows.indexOf(row)),\n focusItem: (row) => {\n if (row === undefined)\n return;\n const key = this.#searchKeyByRow.get(row);\n if (key !== undefined)\n this.tickleRow(key);\n },\n selectItems: (rows) => {\n this.selectKeys(rows.map(r => this.#searchKeyByRow.get(r)).filter((k): k is string => k !== undefined));\n },\n applyFilter: (matched) => {\n this.filterPredicate = matched === undefined\n ? undefined\n : (row) => {\n const k = this.#searchKeyByRow.get(row);\n return k === undefined || matched.has(k);\n };\n },\n // No character highlights: match positions index into the whole-row search\n // text, which spans multiple cells, so they can't be mapped to one cell.\n };\n }\n\n #effectiveSearchModes(): ListSearchMode[] {\n const raw = this.searchModes?.trim();\n if (raw === undefined)\n return [...LIST_SEARCH_MODES];\n const requested = new Set(raw.split(/\\s+/));\n return LIST_SEARCH_MODES.filter(m => requested.has(m));\n }\n\n #syncSearchCommands(): void {\n if (!this.#searchRegistry)\n return;\n this.search.setModes(this.#effectiveSearchModes());\n this.#unregisterSearchCommands?.();\n this.#unregisterSearchCommands = registerListSearchCommands(this.#searchRegistry, this.search);\n }\n\n /** Row-key snapshot from the previous update, for the insertion / removal animation. */\n #prevFlatKeys: string[] = [];\n #enteringRowKeys = new Set<string>();\n #rowReflowTimer = 0;\n #dataGridRenderedOnce = false;\n private _visibleColumns: DataGridColumn[] = [];\n private _colOffsets: number[] = [];\n private _colWidthSum = 0;\n private _raf = 0;\n #viewportChangeRaf = 0;\n /** Key sets as of the last `datagrid-viewport-change` dispatch, for dedupe. */\n #lastViewportRenderedKeys: readonly string[] | undefined;\n #lastViewportVisibleKeys: readonly string[] | undefined;\n #appendInProgress = false;\n #resortRaf = 0;\n private _drag: { pointerId: number; from: number; startX: number; startY: number; active: boolean; ghost: DragGhost | null; gap: number | undefined; sourceCol: DataGridColumn } | null = null;\n\n override connectedCallback(): void {\n super.connectedCallback();\n if (!this.hasAttribute(`tabindex`))\n this.tabIndex = 0;\n this.addEventListener(`keydown`, this._onKeyDown as EventListener);\n this.addEventListener(`focusout`, this._onFocusOut as EventListener);\n this.#searchRegistry ??= createCommandRegistry();\n this.#syncSearchCommands();\n }\n\n override disconnectedCallback(): void {\n super.disconnectedCallback();\n this.removeEventListener(`keydown`, this._onKeyDown as EventListener);\n this.removeEventListener(`focusout`, this._onFocusOut as EventListener);\n cancelAnimationFrame(this._raf);\n cancelAnimationFrame(this.#viewportChangeRaf);\n this.#viewportChangeRaf = 0;\n this.#unregisterSearchCommands?.();\n this.#unregisterSearchCommands = undefined;\n this.#searchRegistry = undefined;\n if (this.#rowReflowTimer) {\n clearTimeout(this.#rowReflowTimer);\n this.#rowReflowTimer = 0;\n }\n if (this.#postDragSuppressTimer) {\n clearTimeout(this.#postDragSuppressTimer);\n this.#postDragSuppressTimer = 0;\n }\n this.#viewportResizeObserver?.disconnect();\n this.#viewportResizeObserver = undefined;\n }\n\n /**\n * Dispatch a command to this grid — routes through the command registry so\n * `list.search.*` (and any other registered commands) work.\n */\n dispatch(commandId: CommandId, args?: Record<string, unknown>): void {\n this.#searchRegistry?.invoke(commandId, args);\n }\n\n private _onFocusOut = (e: FocusEvent): void => {\n if (this._suppressBlurCommit)\n return;\n if (this.editability === `immediate`)\n return;\n if (!this._editing && !this._editingRow)\n return;\n const next = e.relatedTarget as Node | null;\n if (next && this.contains(next))\n return;\n // focus moved outside component → revert editors\n this._editing = null;\n this._editingRow = null;\n this.requestUpdate();\n };\n\n protected override firstUpdated(): void {\n this.#viewportResizeObserver = new ResizeObserver(() => this.#measureViewport());\n this.#viewportResizeObserver.observe(this._viewportEl);\n this.#measureViewport();\n }\n\n /**\n * Re-read the viewport's size and update `_viewportH`/`_viewportW` if it\n * changed. A zero-sized read (e.g. while hosted in a hidden/inactive dock\n * tab) is ignored so it never clobbers the last known-good geometry — the\n * observer fires again with the real size once the host becomes visible.\n */\n #measureViewport(): void {\n if (!this._viewportEl)\n return;\n const w = this._viewportEl.clientWidth;\n const h = this._viewportEl.clientHeight;\n if (w <= 0 || h <= 0)\n return;\n if (w === this._viewportW && h === this._viewportH)\n return;\n this._viewportW = w;\n this._viewportH = h;\n this.#scheduleViewportChangeEmit();\n }\n\n /**\n * Force a fresh re-measure of the viewport and re-render. Normally\n * unnecessary — a `ResizeObserver` tracks the viewport automatically — but\n * gives a consumer an escape hatch to recover if an ancestor's\n * layout/visibility changes without the observer noticing (matches\n * `ixfx-grid-list`'s `refreshLayout()`).\n */\n refreshLayout(): void {\n this.#measureViewport();\n this.requestUpdate();\n }\n\n protected override updated(changed: Map<string, unknown>): void {\n super.updated(changed);\n if (changed.has(`rows`) || changed.has(`sortState`) || changed.has(`columns`) || changed.has(`groupBy`) || changed.has(`groupLabel`) || changed.has(`filterPredicate`) || changed.has(`rowHeight`)) {\n // Row set / layout shift can move the window without a scroll event.\n this.#scheduleViewportChangeEmit();\n }\n if (changed.has(`_editing`) || changed.has(`_editingRow`)) {\n requestAnimationFrame(() => {\n let sel: string | null = null;\n if (this._editing)\n sel = `.row[data-key=\"${this._editing.rowKey}\"] .cell[data-col=\"${this._editing.colKey}\"] input, .row[data-key=\"${this._editing.rowKey}\"] .cell[data-col=\"${this._editing.colKey}\"] select`;\n else if (this._editingRow)\n sel = `.row[data-key=\"${this._editingRow}\"] .cell input, .row[data-key=\"${this._editingRow}\"] .cell select`;\n if (!sel)\n return;\n const el = this.renderRoot.querySelector(sel) as HTMLElement | null;\n el?.focus();\n if (el instanceof HTMLInputElement && el.type === `text`)\n el.select();\n });\n }\n }\n\n protected override willUpdate(changed: Map<string, unknown>): void {\n super.willUpdate(changed);\n this.setAttribute(`data-input-mode`, this._tickled.inputMode);\n if (changed.has(`searchModes`)) {\n this.#syncSearchCommands();\n }\n // `appendRows()` maintains the derived arrays itself and coalesces any\n // re-sort — skip the full rebuild that a plain `rows` reassignment triggers.\n if (!this.#appendInProgress) {\n if (changed.has(`rows`) || changed.has(`sortState`) || changed.has(`columns`) || changed.has(`groupBy`) || changed.has(`groupLabel`)) {\n this._sortedRows = this._applySort([...this.rows]);\n }\n this._rebuildFlat();\n }\n this._visibleColumns = this.columns.filter(c => c.visible !== false);\n let off = 0;\n this._colOffsets = this._visibleColumns.map((c) => {\n const o = off;\n off += c.width ?? 150;\n return o;\n });\n this._colWidthSum = off;\n if (this.interactionMode === `checked`)\n this._colWidthSum += 28;\n this.#noteFlatMutation();\n }\n\n /**\n * Diff the row-key list against the previous update. Rows that appeared get an\n * enter fade; any add/remove opens a short `[reflowing]` window so the rows\n * that shift slide (their `top` transitions) instead of snapping. Bounded in\n * time so it never bleeds into scroll virtualisation.\n */\n #noteFlatMutation(): void {\n const now = this._flatKeys;\n const prev = this.#prevFlatKeys;\n this.#prevFlatKeys = now.slice();\n if (!this.#dataGridRenderedOnce) {\n this.#dataGridRenderedOnce = true;\n return;\n }\n if (prev.length === 0 || now.length === 0) {\n this.#enteringRowKeys.clear();\n return;\n }\n const before = new Set(prev);\n const after = new Set(now);\n const added = now.filter(k => !before.has(k));\n const removed = prev.filter(k => !after.has(k));\n if (added.length === now.length || (added.length === 0 && removed.length === 0))\n return;\n this.#enteringRowKeys = new Set(added);\n this.toggleAttribute(`reflowing`, true);\n if (this.#rowReflowTimer)\n clearTimeout(this.#rowReflowTimer);\n this.#rowReflowTimer = window.setTimeout(() => {\n this.#rowReflowTimer = 0;\n this.#enteringRowKeys.clear();\n this.toggleAttribute(`reflowing`, false);\n this.requestUpdate();\n }, 320);\n }\n\n private _getGroupKey(row: unknown): string | null {\n if (!this.groupBy)\n return null;\n if (typeof this.groupBy === `string`)\n return String((row as Record<string, unknown>)[this.groupBy] ?? ``);\n return String((this.groupBy as (r: unknown) => string)(row));\n }\n\n private _rebuildFlat(): void {\n const filtered = this.filterPredicate !== undefined;\n const source = filtered\n ? this._sortedRows.filter(r => this.filterPredicate!(r))\n : this._sortedRows;\n if (!this.groupBy) {\n this._flat = source.map((r, i) => {\n const idx = filtered ? this._sortedRows.indexOf(r) : i;\n return { type: `row` as const, key: this.getRowKey(r, idx), row: r, idx };\n });\n this._flatKeys = this._flat.map(f => f.key);\n return;\n }\n const groups = new Map<string, unknown[]>();\n for (const r of source) {\n const k = this._getGroupKey(r) ?? ``;\n const arr = groups.get(k);\n if (arr)\n arr.push(r); else groups.set(k, [r]);\n }\n const flat: typeof this._flat = [];\n const keys: string[] = [];\n for (const [gKey, rows] of groups) {\n const label = this.groupLabel ? this.groupLabel(gKey, rows) : gKey;\n const gId = `__group__${gKey}`;\n flat.push({ type: `group`, key: gId, label, count: rows.length });\n keys.push(gId);\n if (this._collapsedGroups.has(gKey))\n continue;\n for (const r of rows) {\n const idx = this._sortedRows.indexOf(r);\n const rk = this.getRowKey(r, idx);\n flat.push({ type: `row`, key: rk, row: r, idx });\n keys.push(rk);\n }\n }\n this._flat = flat;\n this._flatKeys = keys;\n }\n\n private _toggleGroup(gKey: string): void {\n const next = new Set(this._collapsedGroups);\n if (next.has(gKey))\n next.delete(gKey); else next.add(gKey);\n this._collapsedGroups = next;\n }\n\n private _applySort(rows: unknown[]): unknown[] {\n if (!this.sortState)\n return rows;\n const col = this.columns.find(c => c.key === this.sortState!.key);\n if (!col)\n return rows;\n const dir = this.sortState.direction === `asc` ? 1 : -1;\n if (col.sortFn)\n return rows.sort((a, b) => dir * col.sortFn!(a as never, b as never));\n const dataType = col.dataType ?? `text`;\n return rows.sort((a, b) => {\n const av = (a as Record<string, unknown>)[col.key];\n const bv = (b as Record<string, unknown>)[col.key];\n if (av === bv)\n return 0;\n if (dataType === `number`)\n return dir * ((av as number) - (bv as number));\n if (dataType === `boolean`)\n return dir * ((Boolean(av) === Boolean(bv)) ? 0 : (av ? 1 : -1));\n return dir * String(av).localeCompare(String(bv));\n });\n }\n\n private _onScroll = (e: Event): void => {\n const el = e.target as HTMLElement;\n cancelAnimationFrame(this._raf);\n this._raf = requestAnimationFrame(() => {\n this._scrollTop = el.scrollTop;\n this._scrollLeft = el.scrollLeft;\n if (this._headerScrollEl)\n this._headerScrollEl.scrollLeft = el.scrollLeft;\n this.requestUpdate();\n // A content/layout check may already be queued for this frame. Fold it\n // into this scroll result so there can be only one dispatch per frame.\n cancelAnimationFrame(this.#viewportChangeRaf);\n this.#viewportChangeRaf = 0;\n this.#emitViewportChangeIfChanged();\n });\n };\n\n private _onHeaderClick(col: DataGridColumn, e?: MouseEvent): void {\n if (col.sortable === false)\n return;\n if (e) {\n const pointerEvent = e.composedPath()[0] as unknown as PointerEvent | undefined;\n if (pointerEvent && this.#pointerEventSuppressess.get(pointerEvent)) {\n this.#pointerEventSuppressess.delete(pointerEvent);\n return;\n }\n }\n const prev = this.sortState;\n let next: DataGridSortState = null;\n if (!prev || prev.key !== col.key)\n next = { key: col.key, direction: `asc` };\n else if (prev.direction === `asc`)\n next = { key: col.key, direction: `desc` };\n else next = null;\n this.sortState = next;\n this.dispatchEvent(new CustomEvent<DataGridSortDetail>(`datagrid-sort`, { detail: { sort: next, previous: prev }, bubbles: true, composed: true }));\n }\n\n private _onHeaderPointerUp(col: DataGridColumn, e: PointerEvent): void {\n let stopped = false;\n const customEvent = new CustomEvent(`datagrid-header-pointerup`, {\n detail: { key: col.key, column: col },\n bubbles: true,\n composed: true,\n cancelable: true,\n });\n this.dispatchEvent(customEvent);\n if (customEvent.defaultPrevented)\n stopped = true;\n if (stopped)\n this.#pointerEventSuppressess.set(e, true);\n }\n\n private _onColButtonClick(col: DataGridColumn, e: PointerEvent): void {\n e.stopPropagation();\n const icon = col.button === false\n ? this.columnButtonIcon\n : (typeof col.button === `object` && col.button.icon) ? col.button.icon : this.columnButtonIcon;\n const target = e.currentTarget as HTMLElement;\n const customEvent = new CustomEvent(`datagrid-header-button-click`, {\n detail: { key: col.key, column: col, icon, clientX: e.clientX, clientY: e.clientY, anchorElement: target },\n bubbles: true,\n composed: true,\n cancelable: true,\n });\n this.dispatchEvent(customEvent);\n if (customEvent.defaultPrevented)\n this.#pointerEventSuppressess.set(e, true);\n }\n\n private _onRowClick(rowKey: string, col: DataGridColumn | null, e: MouseEvent): void {\n if (this.#nativeDrag.isDragging || this.#postDragSuppressTimer !== 0)\n return;\n if (col && col.selectable === false)\n return;\n if (this.selectionMode === `none` && this.interactionMode !== `checked` && this.interactionMode !== `sticky`)\n return;\n if (this.interactionMode === `manual`)\n return;\n if (this.interactionMode === `implicit`) {\n this._replaceSelection(rowKey); return;\n }\n if (this.interactionMode === `checked`)\n return;\n if (this.interactionMode === `sticky`) {\n this._toggleSelection(rowKey); return;\n }\n // standard / vscode\n if (e.ctrlKey || e.metaKey) {\n if (this.selectionMode === `multiple` || this.interactionMode === `vscode`)\n this._toggleSelection(rowKey);\n } else if (e.shiftKey && (this.selectionMode === `multiple` || this.interactionMode === `vscode`)) {\n this._rangeSelectTo(rowKey);\n } else {\n this._replaceSelection(rowKey);\n }\n }\n\n private _onCheckboxClick(rowKey: string, e: MouseEvent): void {\n e.stopPropagation();\n this._onRowClick(rowKey, null, e);\n }\n\n private _onVisibilityToggle(col: DataGridColumn, checked: boolean): void {\n col.visible = checked;\n this.columns = [...this.columns];\n this.dispatchEvent(new CustomEvent<DataGridColumnVisibilityDetail>(`datagrid-column-visibility`, { detail: { key: col.key, visible: checked }, bubbles: true, composed: true }));\n }\n\n private _beginHeaderDrag(e: PointerEvent, col: DataGridColumn, idx: number): void {\n e.stopPropagation();\n const anchor = (e.currentTarget as HTMLElement).closest(`.header-cell`) as HTMLElement ?? e.currentTarget as HTMLElement;\n this._drag = { pointerId: e.pointerId, from: idx, startX: e.clientX, startY: e.clientY, active: false, ghost: null, gap: undefined, sourceCol: col };\n const onMove = (ev: PointerEvent): void => {\n if (!this._drag || ev.pointerId !== this._drag.pointerId)\n return;\n const dx = ev.clientX - this._drag.startX;\n const dy = ev.clientY - this._drag.startY;\n if (!this._drag.active) {\n if (Math.hypot(dx, dy) < 5)\n return;\n this._drag.active = true;\n const content = document.createElement(`span`);\n content.textContent = col.label;\n try {\n this._drag.ghost = createDragGhost({ anchor, content });\n this._drag.ghost.move(ev.clientX, ev.clientY);\n } catch { /* ignore */ }\n try {\n this._headerScrollEl?.setPointerCapture(ev.pointerId);\n } catch { /* ignore */ }\n }\n this._drag.ghost?.move(ev.clientX, ev.clientY);\n const x = ev.clientX - (this._headerScrollEl?.getBoundingClientRect().left ?? 0) + (this._headerScrollEl?.scrollLeft ?? 0);\n let gap = this._drag.from;\n let bestDist = Infinity;\n for (let i = 0; i < this._visibleColumns.length; i++) {\n if (i === this._drag.from)\n continue;\n const rectLeft = this._colOffsets[i];\n const rectRight = rectLeft + (this._visibleColumns[i].width ?? 150);\n const mid = (rectLeft + rectRight) / 2;\n // gap before i\n const gapPos = x < mid ? rectLeft : rectRight;\n const gapIdx = x < mid ? i : i + 1;\n const d = Math.abs(x - gapPos);\n if (d < bestDist) {\n bestDist = d; gap = gapIdx > this._drag.from ? gapIdx - 1 : gapIdx;\n }\n }\n // handle gap after last\n if (this._visibleColumns.length > 0) {\n const lastOff = this._colOffsets[this._colOffsets.length - 1] + (this._visibleColumns[this._visibleColumns.length - 1].width ?? 150);\n const d = Math.abs(x - lastOff);\n if (d < bestDist) {\n bestDist = d; gap = this._visibleColumns.length - 1; if (this._drag.from === this._visibleColumns.length - 1)\n gap = this._drag.from; else if (gap >= this._drag.from)\n gap = this._visibleColumns.length - 1;\n }\n }\n // normalized gap for reorder (visible index without source)\n const siblings = this._visibleColumns.length - 1;\n let normalizedGap = gap;\n if (normalizedGap < 0)\n normalizedGap = 0;\n if (normalizedGap > siblings)\n normalizedGap = siblings;\n this._drag.gap = normalizedGap;\n this.requestUpdate();\n };\n const onUp = (ev: PointerEvent): void => {\n if (!this._drag || ev.pointerId !== this._drag.pointerId)\n return;\n const active = this._drag.active;\n const from = this._drag.from;\n const gap = this._drag.gap;\n this._drag.ghost?.destroy();\n try {\n this._headerScrollEl?.releasePointerCapture(ev.pointerId);\n } catch { /* ignore */ }\n window.removeEventListener(`pointermove`, onMove);\n window.removeEventListener(`pointerup`, onUp);\n window.removeEventListener(`pointercancel`, onUp);\n this._drag = null;\n this.requestUpdate();\n if (active && gap !== undefined && gap !== from) {\n // convert visible gap to actual reorder (filter hidden)\n this._onReorderDrag(from, gap);\n }\n };\n window.addEventListener(`pointermove`, onMove);\n window.addEventListener(`pointerup`, onUp);\n window.addEventListener(`pointercancel`, onUp as EventListener);\n }\n\n private _onReorderDrag(fromIdx: number, toIdx: number): void {\n if (fromIdx === toIdx)\n return;\n const cols = [...this.columns];\n const vis = cols.filter(c => c.visible !== false);\n const hidden = cols.filter(c => c.visible === false);\n const [moved] = vis.splice(fromIdx, 1);\n vis.splice(toIdx, 0, moved);\n this.columns = [...vis, ...hidden];\n this.dispatchEvent(new CustomEvent<DataGridColumnReorderDetail>(`datagrid-column-reorder`, { detail: { from: fromIdx, to: toIdx, columns: [...this.columns] }, bubbles: true, composed: true }));\n }\n\n private _anchorKey: string | undefined;\n\n private _scrollRowIntoView(key: string): void {\n const idx = this._flat.findIndex(f => f.key === key);\n if (idx < 0 || !this._viewportEl)\n return;\n const top = idx * this.rowHeight;\n const bottom = top + this.rowHeight;\n const vt = this._viewportEl.scrollTop;\n const vb = vt + this._viewportEl.clientHeight;\n if (top < vt)\n this._viewportEl.scrollTop = top;\n else if (bottom > vb)\n this._viewportEl.scrollTop = bottom - this._viewportEl.clientHeight;\n }\n\n private _getRowForKey(key: string): unknown | undefined {\n const entry = this._flat.find(f => f.key === key) as { row?: unknown } | undefined;\n return (entry as { row?: unknown })?.row;\n }\n\n // --- Public keyed API ---\n\n /** The selected row keys (read-only). */\n get selectedKeys(): ReadonlySet<string> {\n return this._selectedKeys;\n }\n\n /** Replace the selection with these row keys (clamped to known rows). */\n set selectedKeys(keys: Iterable<string>) {\n this.selectKeys(keys);\n }\n\n /**\n * Replace the selection with the given row keys. Unknown keys are dropped;\n * in a single-select mode only the last surviving key is kept;\n * `selectionMode=\"none\"` clears. Fires `datagrid-select` with the previous\n * set when the selection actually changes.\n */\n selectKeys(keys: Iterable<string>): void {\n const known = new Set(this._flat.filter(f => f.type === `row`).map(f => f.key));\n let next = new Set([...keys].filter(k => known.has(k)));\n const multi = this.selectionMode === `multiple`\n || this.interactionMode === `checked`\n || this.interactionMode === `sticky`\n || this.interactionMode === `vscode`;\n if (this.selectionMode === `none`) {\n next = new Set();\n } else if (!multi && next.size > 1) {\n const last = [...next].at(-1);\n next = last === undefined ? new Set() : new Set([last]);\n }\n const prev = new Set(this._selectedKeys);\n if (prev.size === next.size && [...next].every(k => prev.has(k)))\n return;\n this._selectedKeys = next;\n this._anchorKey = [...next].at(-1);\n this.dispatchEvent(new CustomEvent<DataGridSelectDetail>(`datagrid-select`, {\n detail: { selectedKeys: new Set(next), previous: prev },\n bubbles: true,\n composed: true,\n }));\n }\n\n /** The row key under the cursor, or `undefined`. */\n get tickledKey(): string | undefined {\n return this._tickled.tickledId;\n }\n\n /** Move the cursor to this row key and scroll it into view. */\n tickleRow(key: string): void {\n if (!this._flatKeys.includes(key))\n return;\n this._tickled.focus(key);\n this._scrollRowIntoView(key);\n }\n\n /**\n * Append rows without the full O(n log n) rebuild that reassigning `rows`\n * incurs. `rows` still gets a new array reference (reactivity is preserved),\n * but the derived arrays are extended over the appended slice only. When a\n * sort is active the new rows show unsorted for one frame, then a single\n * coalesced re-sort runs. Scroll position, selection and cursor are kept.\n */\n appendRows(rows: readonly unknown[]): void {\n if (rows.length === 0)\n return;\n const startIdx = this.rows.length;\n this.#appendInProgress = true;\n this.rows = [...this.rows, ...rows];\n const appended = this.rows.slice(startIdx);\n\n if (this._sortedRows.length === startIdx) {\n this._sortedRows = [...this._sortedRows, ...appended];\n } else {\n // derived arrays out of sync — fall back to a full rebuild\n this._sortedRows = this._applySort([...this.rows]);\n this._rebuildFlat();\n this.#appendInProgress = false;\n this.requestUpdate();\n return;\n }\n this.#appendToFlat(appended, startIdx);\n this.#appendInProgress = false;\n this.requestUpdate();\n\n if (this.sortState != null) {\n cancelAnimationFrame(this.#resortRaf);\n this.#resortRaf = requestAnimationFrame(() => {\n this._sortedRows = this._applySort([...this.rows]);\n this._rebuildFlat();\n this.requestUpdate();\n });\n }\n }\n\n #appendToFlat(appended: readonly unknown[], startIdx: number): void {\n if (this.groupBy) {\n // grouped flat layout can't be extended in place — rebuild it\n this._rebuildFlat();\n return;\n }\n for (let j = 0; j < appended.length; j++) {\n const idx = startIdx + j;\n const key = this.getRowKey(appended[j], idx);\n this._flat.push({ type: `row`, key, row: appended[j], idx });\n this._flatKeys.push(key);\n }\n }\n\n private _replaceSelection(key: string): void {\n if (this.selectionMode === `none`)\n return;\n const prev = new Set(this._selectedKeys);\n if (this.groupBy && !this.crossGroupSelection) {\n const g = this._getGroupKey(this._getRowForKey(key) ?? { key });\n const keep = [...prev].filter(k => this._getGroupKey(this._getRowForKey(k) ?? { key: k }) === g);\n // cross-group off → keep only same-group, then replace\n this._selectedKeys = new Set([key]);\n void keep;\n } else {\n this._selectedKeys = new Set([key]);\n }\n this._anchorKey = key;\n this.dispatchEvent(new CustomEvent<DataGridSelectDetail>(`datagrid-select`, { detail: { selectedKeys: new Set(this._selectedKeys), previous: prev }, bubbles: true, composed: true }));\n }\n\n private _toggleSelection(key: string): void {\n const prev = new Set(this._selectedKeys);\n const next = new Set(this._selectedKeys);\n if (next.has(key)) {\n next.delete(key);\n } else {\n if (this.groupBy && !this.crossGroupSelection) {\n const g = this._getGroupKey(this._getRowForKey(key) ?? { key });\n for (const k of [...next]) {\n if (this._getGroupKey(this._getRowForKey(k) ?? { key: k }) !== g)\n next.delete(k);\n }\n }\n if (this.selectionMode !== `multiple` && this.interactionMode !== `checked` && this.interactionMode !== `sticky`)\n next.clear();\n next.add(key);\n }\n this._selectedKeys = next;\n this._anchorKey = key;\n this.dispatchEvent(new CustomEvent<DataGridSelectDetail>(`datagrid-select`, { detail: { selectedKeys: new Set(this._selectedKeys), previous: prev }, bubbles: true, composed: true }));\n }\n\n private _rangeSelectTo(key: string): void {\n if (!this._anchorKey) {\n this._replaceSelection(key); return;\n }\n const keys = this._flat.filter(f => f.type === `row`).map(f => f.key);\n const a = keys.indexOf(this._anchorKey);\n const b = keys.indexOf(key);\n if (a < 0 || b < 0) {\n this._replaceSelection(key); return;\n }\n if (this.groupBy && !this.crossGroupSelection) {\n const anchorGroup = this._getGroupKey(this._getRowForKey(this._anchorKey) ?? { key: this._anchorKey });\n const targetGroup = this._getGroupKey(this._getRowForKey(key) ?? { key });\n if (anchorGroup !== targetGroup) {\n this._replaceSelection(key); return;\n }\n // restrict range to rows of that group\n const groupKeys = keys.filter(k => this._getGroupKey(this._getRowForKey(k) ?? { key: k }) === anchorGroup);\n const ga = groupKeys.indexOf(this._anchorKey);\n const gb = groupKeys.indexOf(key);\n if (ga < 0 || gb < 0) {\n this._replaceSelection(key); return;\n }\n const lo = Math.min(ga, gb); const hi = Math.max(ga, gb);\n const prev = new Set(this._selectedKeys);\n this._selectedKeys = new Set(groupKeys.slice(lo, hi + 1));\n this.dispatchEvent(new CustomEvent<DataGridSelectDetail>(`datagrid-select`, { detail: { selectedKeys: new Set(this._selectedKeys), previous: prev }, bubbles: true, composed: true }));\n return;\n }\n const lo = Math.min(a, b); const hi = Math.max(a, b);\n const prev = new Set(this._selectedKeys);\n this._selectedKeys = new Set(keys.slice(lo, hi + 1));\n this.dispatchEvent(new CustomEvent<DataGridSelectDetail>(`datagrid-select`, { detail: { selectedKeys: new Set(this._selectedKeys), previous: prev }, bubbles: true, composed: true }));\n }\n\n private _onKeyDown = (e: KeyboardEvent): void => {\n if ((e.ctrlKey || e.metaKey) && e.key.toLowerCase() === `a`) {\n if (this.selectionMode === `multiple` || this.interactionMode === `checked` || this.interactionMode === `sticky` || this.interactionMode === `vscode` || this.interactionMode === `standard`) {\n e.preventDefault();\n const prev = new Set(this._selectedKeys);\n if (this.groupBy && !this.crossGroupSelection && this._anchorKey) {\n const g = this._getGroupKey(this._getRowForKey(this._anchorKey) ?? { key: this._anchorKey });\n this._selectedKeys = new Set(this._flat.filter(f => f.type === `row` && this._getGroupKey((f as { row: unknown }).row) === g).map(f => f.key));\n } else {\n this._selectedKeys = new Set(this._flat.filter(f => f.type === `row`).map(f => f.key));\n }\n this.dispatchEvent(new CustomEvent<DataGridSelectDetail>(`datagrid-select`, { detail: { selectedKeys: new Set(this._selectedKeys), previous: prev }, bubbles: true, composed: true }));\n }\n return;\n }\n // If editing, Up/Down commits and moves to same column in adjacent row\n if (this._editing && (e.key === `ArrowDown` || e.key === `ArrowUp`)) {\n const active = this.shadowRoot?.activeElement as HTMLElement | null;\n if (active?.tagName === `SELECT`)\n return; // let native select handle\n e.preventDefault();\n const cur = this._editing;\n const dir = e.key === `ArrowDown` ? 1 : -1;\n const colKey = cur.colKey;\n this._suppressBlurCommit = true;\n this._commitEdit();\n const rowKeys = this._flat.filter(f => f.type === `row`).map(f => f.key);\n const idx = rowKeys.indexOf(cur.rowKey);\n let nextIdx = idx + dir;\n while (nextIdx >= 0 && nextIdx < rowKeys.length) {\n const nk = rowKeys[nextIdx];\n const row = this._sortedRows.find((r, i) => this.getRowKey(r, i) === nk);\n const col = this._visibleColumns.find(c => c.key === colKey);\n if (row && col && this._isEditable(row, col)) {\n this._startEdit(nk, colKey);\n this._tickled.handleKeyboardNavigation(nextIdx > idx ? `next` : `previous`);\n this._scrollRowIntoView(nk);\n break;\n }\n nextIdx += dir;\n }\n if (nextIdx < 0 || nextIdx >= rowKeys.length) {\n // no editable target, stay on current row tickled\n this._tickled.handleKeyboardNavigation(dir > 0 ? `next` : `previous`);\n if (this._tickled.tickledId)\n this._scrollRowIntoView(this._tickled.tickledId);\n }\n requestAnimationFrame(() => {\n this._suppressBlurCommit = false;\n });\n return;\n }\n if (e.key === `ArrowDown` || e.key === `ArrowUp` || e.key === `Home` || e.key === `End`) {\n e.preventDefault();\n this._tickled.setInputMode(`keyboard`);\n }\n switch (e.key) {\n case `ArrowDown`: {\n this._tickled.handleKeyboardNavigation(`next`);\n if (this._tickled.tickledId)\n this._scrollRowIntoView(this._tickled.tickledId);\n if (this.interactionMode === `implicit` && this._tickled.tickledId)\n this._replaceSelection(this._tickled.tickledId);\n if (e.shiftKey && (this.interactionMode === `standard` || this.interactionMode === `vscode`) && this._tickled.tickledId)\n this._rangeSelectTo(this._tickled.tickledId);\n break;\n }\n case `ArrowUp`: {\n this._tickled.handleKeyboardNavigation(`previous`);\n if (this._tickled.tickledId)\n this._scrollRowIntoView(this._tickled.tickledId);\n if (this.interactionMode === `implicit` && this._tickled.tickledId)\n this._replaceSelection(this._tickled.tickledId);\n if (e.shiftKey && (this.interactionMode === `standard` || this.interactionMode === `vscode`) && this._tickled.tickledId)\n this._rangeSelectTo(this._tickled.tickledId);\n break;\n }\n case `Home`: {\n this._tickled.handleKeyboardNavigation(`first`);\n if (this._tickled.tickledId)\n this._scrollRowIntoView(this._tickled.tickledId);\n break;\n }\n case `End`: {\n this._tickled.handleKeyboardNavigation(`last`);\n if (this._tickled.tickledId)\n this._scrollRowIntoView(this._tickled.tickledId);\n break;\n }\n case `Enter`: {\n const key = this._tickled.tickledId;\n if (!key)\n break;\n e.preventDefault();\n if (!this._editing && this.editability === `user`) {\n const idx = this._sortedRows.findIndex((r, i) => this.getRowKey(r, i) === key);\n if (idx >= 0) {\n const row = this._sortedRows[idx];\n // prefer lastClickedCell if it is in this row and editable\n if (this._lastClickedCell?.rowKey === key) {\n const col = this._visibleColumns.find(c => c.key === this._lastClickedCell!.colKey);\n if (col && this._isEditable(row, col)) {\n this._startEdit(key, col.key); break;\n }\n }\n const firstEditable = this._visibleColumns.find(c => this._isEditable(row, c));\n if (firstEditable) {\n this._startEdit(key, firstEditable.key); break;\n }\n }\n }\n if (!this._editing) {\n const idx = this._sortedRows.findIndex((r, i) => this.getRowKey(r, i) === key);\n if (this._selectedKeys.has(key)) {\n this._activateRow(key, idx >= 0 ? this._sortedRows[idx] : undefined, idx);\n break;\n }\n if (this.interactionMode !== `manual` && this.interactionMode !== `checked`)\n this._replaceSelection(key);\n this.dispatchEvent(new CustomEvent<DataGridCellClickDetail>(`datagrid-cell-click`, { detail: { rowKey: key, colKey: ``, rowIndex: idx, colIndex: -1 }, bubbles: true, composed: true }));\n }\n break;\n }\n case ` `: {\n if (this._editing) {\n const col = this.columns.find(c => c.key === this._editing!.colKey);\n const effectiveDataType = col?.dataType ?? `text`;\n if (effectiveDataType === `boolean`) {\n e.preventDefault();\n const isImmediate = this.editability === `immediate`;\n const rowKey = this._editing.rowKey;\n const colKey = this._editing.colKey;\n // Toggle: use checkbox checked if focused, else flip _editValue / row value\n const active = this.shadowRoot?.activeElement as HTMLInputElement | null;\n let next: boolean;\n if (active?.type === `checkbox`) {\n next = !active.checked;\n active.checked = next;\n } else {\n const row = this._sortedRows.find((r, i) => this.getRowKey(r, i) === rowKey) as Record<string, unknown> | undefined;\n const cur = this._editValue !== `` ? Boolean(this._editValue) : Boolean(row?.[colKey]);\n next = !cur;\n }\n if (isImmediate) {\n this._commitImmediate(rowKey, colKey, next);\n } else {\n this._editValue = next; this._commitEdit();\n }\n }\n break;\n }\n const key = this._tickled.tickledId;\n if (!key)\n break;\n e.preventDefault();\n if (this.interactionMode === `checked` || this.interactionMode === `sticky` || this.interactionMode === `standard` || this.interactionMode === `vscode` || this.interactionMode === `manual`)\n this._toggleSelection(key);\n else this._replaceSelection(key);\n break;\n }\n case `Escape`: {\n if (this._editing || this._editingRow) {\n e.preventDefault(); this._editing = null; this._editingRow = null; this.requestUpdate();\n } else if (this._selectedKeys.size) {\n e.preventDefault(); const prev = new Set(this._selectedKeys); this._selectedKeys = new Set(); this.dispatchEvent(new CustomEvent<DataGridSelectDetail>(`datagrid-select`, { detail: { selectedKeys: new Set(), previous: prev }, bubbles: true, composed: true }));\n }\n break;\n }\n }\n };\n\n private _isEditable(row: unknown, col: DataGridColumn): boolean {\n if (this.editability === `disabled`)\n return false;\n if (typeof this.editable === `function`)\n return (this.editable as (r: unknown, c: DataGridColumn) => boolean)(row, col);\n if (this.editable === true)\n return col.editable !== false;\n return !!col.editable;\n }\n\n private _isTextEditor(col: DataGridColumn): boolean {\n const e = col.editor;\n return !e || e === `auto`;\n }\n\n private _isCellEditing(rowKey: string, colKey: string): boolean {\n if (this.editability === `immediate` && this._isEditable(this._sortedRows.find((r, i) => this.getRowKey(r, i) === rowKey) ?? {}, this.columns.find(c => c.key === colKey)!))\n return true;\n if (this._editingRow === rowKey)\n return this._isEditable(this._sortedRows.find((r, i) => this.getRowKey(r, i) === rowKey) ?? {}, this.columns.find(c => c.key === colKey)!);\n return this._editing?.rowKey === rowKey && this._editing?.colKey === colKey;\n }\n\n private _activateRow(rowKey: string, row: unknown, rowIndex: number): void {\n this.dispatchEvent(new CustomEvent<DataGridRowActivateDetail>(`datagrid-row-activate`, { detail: { rowKey, row, rowIndex }, bubbles: true, composed: true }));\n }\n\n private _startEdit(rowKey: string, colKey: string): void {\n if (this.editability === `disabled`)\n return;\n const row = this._sortedRows.find((r, i) => this.getRowKey(r, i) === rowKey);\n if (!row)\n return;\n const col = this.columns.find(c => c.key === colKey);\n if (!col || !this._isEditable(row, col))\n return;\n this._editing = { rowKey, colKey };\n this._editingRow = null;\n this._editValue = (row as Record<string, unknown>)[colKey];\n }\n\n /** Programmatic: put a single cell in edit mode. Works in manual/user/immediate (no-op if disabled or not editable). */\n startEdit(rowKey: string, colKey: string): void {\n this._startEdit(rowKey, colKey);\n }\n\n /** Programmatic: put all editable cells of a row in edit mode. */\n startRowEdit(rowKey: string): void {\n if (this.editability === `disabled`)\n return;\n const row = this._sortedRows.find((r, i) => this.getRowKey(r, i) === rowKey);\n if (!row)\n return;\n this._editing = null;\n this._editingRow = rowKey;\n this.requestUpdate();\n }\n\n stopEdit(): void {\n this._editing = null; this._editingRow = null;\n }\n\n setColumnFormatter(columnKey: string, formatter: ((value: unknown) => unknown) | BuiltInFormatterName | null, options?: BuiltInFormatterOptions): void {\n if (!formatter) {\n this._columnFormatters.delete(columnKey); this.requestUpdate(); return;\n }\n if (typeof formatter === `string`) {\n const digits = options?.digits ?? (formatter === `integer` ? 0 : 2);\n if (formatter === `fixed`)\n this._columnFormatters.set(columnKey, v => typeof v === `number` && Number.isFinite(v) ? v.toFixed(digits) : String(v ?? ``));\n else if (formatter === `percentage`)\n this._columnFormatters.set(columnKey, v => typeof v === `number` && Number.isFinite(v) ? `${v.toFixed(digits)}%` : String(v ?? ``));\n else if (formatter === `integer`)\n this._columnFormatters.set(columnKey, v => typeof v === `number` && Number.isFinite(v) ? Math.round(v).toString() : String(v ?? ``));\n } else {\n this._columnFormatters.set(columnKey, formatter as (value: unknown) => unknown);\n }\n this.requestUpdate();\n }\n\n private _formatValue(value: unknown, col: DataGridColumn, row: unknown): unknown {\n const perCol = this._columnFormatters.get(col.key);\n if (perCol)\n return perCol(value);\n if (col.formatter)\n return col.formatter(value, row, col);\n if (this.globalFormatter)\n return this.globalFormatter(value, col.key, row);\n return value;\n }\n\n /**\n * Resolve the per-row appearance for the cell at `colKey`, honouring the\n * nominated columns. Additive — `col.renderer` / `col.formatter` still own\n * the cell's value; this only decorates it. Returns all-`undefined` for\n * every cell when nothing is nominated (the common case).\n */\n private _cellLook(row: unknown, colKey: string): DataGridCellLook {\n if (this.textColorColumn === `` && this.iconColumn === `` && this.badgeColumn === ``)\n return EMPTY_CELL_LOOK;\n const rec = (typeof row === `object` && row !== null ? row : {}) as Record<string, unknown>;\n const textColor = colKey === this.textColorColumn ? appearanceColor(rec.textColor) : undefined;\n const icon = colKey === this.iconColumn && !appearanceAbsent(rec.icon) ? rec.icon : undefined;\n const iconColor = icon === undefined ? undefined : appearanceColor(rec.iconColor);\n const badge = colKey === this.badgeColumn && !appearanceAbsent(rec.badge) ? rec.badge : undefined;\n if (textColor === undefined && icon === undefined && badge === undefined)\n return EMPTY_CELL_LOOK;\n return { textColor, icon, iconColor, badge };\n }\n\n private _handleCellSecondClick(rowKey: string, col: DataGridColumn): void {\n if (this.editability !== `user`)\n return;\n const now = Date.now();\n if (this._lastClick && this._lastClick.key === rowKey && this._lastClick.col === col.key && now - this._lastClick.time < 700 && now - this._lastClick.time > 150) {\n this._startEdit(rowKey, col.key);\n this._lastClick = null;\n } else {\n this._lastClick = { key: rowKey, col: col.key, time: now };\n }\n }\n\n private _commitEdit(fromImmediate = false): void {\n // immediate/row-edit: commit uses current _editValue or val; keep simple single-cell path\n if (!this._editing && !fromImmediate)\n return;\n const target = this._editing;\n if (!target)\n return;\n const { rowKey, colKey } = target;\n const row = this._sortedRows.find((r, i) => this.getRowKey(r, i) === rowKey) as Record<string, unknown> | undefined;\n if (!row) {\n this._editing = null; return;\n }\n const oldValue = row[colKey];\n const newValue = this._editValue;\n const col = this.columns.find(c => c.key === colKey);\n if (col?.editor && typeof col.editor === `function`) {\n // custom factory handles commit itself\n } else {\n row[colKey] = newValue as never;\n this.rows = [...this.rows];\n }\n this._editing = null;\n this.dispatchEvent(new CustomEvent<DataGridCellEditDetail>(`datagrid-cell-edit`, { detail: { rowKey, colKey, oldValue, newValue }, bubbles: true, composed: true }));\n }\n\n private _suppressBlurCommit = false;\n private _tabToNext(rowKey: string, curColKey: string, dir: number): void {\n const row = this._sortedRows.find((r, i) => this.getRowKey(r, i) === rowKey);\n if (!row)\n return;\n const cols = this._visibleColumns;\n const curIdx = cols.findIndex(c => c.key === curColKey);\n let next = curIdx + dir;\n while (next >= 0 && next < cols.length) {\n if (this._isEditable(row, cols[next])) {\n // commit current before moving (use _editValue if pending)\n if (this._editing)\n this._commitEdit();\n this._suppressBlurCommit = true;\n this._startEdit(rowKey, cols[next].key);\n requestAnimationFrame(() => {\n this._suppressBlurCommit = false;\n });\n return;\n }\n next += dir;\n }\n if (this._editing)\n this._commitEdit();\n this._editing = null;\n this.requestUpdate();\n }\n\n private _commitImmediate(rowKey: string, colKey: string, value: unknown): void {\n const row = this._sortedRows.find((r, i) => this.getRowKey(r, i) === rowKey) as Record<string, unknown> | undefined;\n if (!row)\n return;\n const oldValue = row[colKey];\n if (oldValue === value)\n return;\n row[colKey] = value as never;\n this.rows = [...this.rows];\n this.dispatchEvent(new CustomEvent<DataGridCellEditDetail>(`datagrid-cell-edit`, { detail: { rowKey, colKey, oldValue, newValue: value }, bubbles: true, composed: true }));\n }\n\n /**\n * Measure the width a column would need to show its header label and every\n * row's (formatted) value without truncation, clamped to `minWidth`/`maxWidth`.\n * Values are measured from their formatted string via canvas `measureText` -\n * accurate for plain text, an estimate for anything else.\n */\n private _measureAutoWidth(col: DataGridColumn): number {\n const cs = getComputedStyle(this);\n const font = `${cs.fontSize} ${cs.fontFamily}`;\n const canvas = document.createElement(`canvas`);\n const ctx = canvas.getContext(`2d`);\n const cellPad = 24; // ~space-s + space-xs + handle-width for left-aligned items\n const headerExtra = 40; // sort icon + reorder handle + resize handle\n const measure = (text: string): number => {\n if (!ctx)\n return text.length * 8;\n ctx.font = font;\n return Math.ceil(ctx.measureText(text).width);\n };\n let maxW = measure(col.label) + headerExtra;\n for (const r of this.rows) {\n const v = (r as Record<string, unknown>)[col.key];\n if (v === null || v === undefined || v === ``)\n continue;\n const text = String(this._formatValue(v, col, r));\n const w = measure(text) + cellPad;\n if (w > maxW)\n maxW = w;\n }\n const min = col.minWidth ?? 40;\n const max = col.maxWidth ?? 600;\n return Math.max(min, Math.min(max, maxW));\n }\n\n private _autoSizeColumn(col: DataGridColumn): void {\n const w = this._measureAutoWidth(col);\n col.width = w;\n this.requestUpdate();\n this.dispatchEvent(new CustomEvent<DataGridColumnResizeDetail>(`datagrid-column-resize`, { detail: { key: col.key, width: w }, bubbles: true, composed: true }));\n }\n\n /**\n * Resize a single column, by key, to fit its contents (header label + every\n * row's formatted value), animating the width change smoothly. Only works\n * for plain columns - one with a custom `renderer` can't be measured\n * reliably from its raw value, so it's left untouched. Returns `false` (and\n * does nothing) if the column doesn't exist, isn't resizable, or has a\n * `renderer`.\n */\n autoSizeColumn(key: string): boolean {\n const col = this.columns.find(c => c.key === key);\n if (!col || col.resizable === false || col.renderer)\n return false;\n const target = this._measureAutoWidth(col);\n if ((col.width ?? 150) === target)\n return true;\n this._animatingColKeys = new Set(this._animatingColKeys).add(key);\n // Let the \"width transitions\" class above take effect on the current\n // width for one frame before changing it, so the browser animates the\n // change instead of snapping straight to it.\n requestAnimationFrame(() => {\n col.width = target;\n this.requestUpdate();\n this.dispatchEvent(new CustomEvent<DataGridColumnResizeDetail>(`datagrid-column-resize`, { detail: { key, width: target }, bubbles: true, composed: true }));\n window.setTimeout(() => {\n const next = new Set(this._animatingColKeys);\n next.delete(key);\n this._animatingColKeys = next;\n }, this._columnResizeAnimationMs());\n });\n return true;\n }\n\n private _columnResizeAnimationMs(): number {\n const raw = getComputedStyle(this).getPropertyValue(`--data-grid-column-resize-duration`).trim();\n const ms = raw.endsWith(`ms`) ? Number.parseFloat(raw) : raw.endsWith(`s`) ? Number.parseFloat(raw) * 1000 : Number.parseFloat(raw);\n return (Number.isFinite(ms) && ms > 0 ? ms : 180) + 30; // small margin over the CSS transition duration\n }\n\n private _onResizePointerDown(e: PointerEvent, col: DataGridColumn): void {\n e.preventDefault(); e.stopPropagation();\n const startX = e.clientX;\n const startW = col.width ?? 150;\n this._resizingColKey = col.key;\n const onMove = (ev: PointerEvent): void => {\n const w = Math.max(col.minWidth ?? 40, Math.min(col.maxWidth ?? 600, startW + ev.clientX - startX));\n col.width = w;\n this.requestUpdate();\n };\n const onUp = (ev: PointerEvent): void => {\n window.removeEventListener(`pointermove`, onMove);\n window.removeEventListener(`pointerup`, onUp);\n this._resizingColKey = undefined;\n const w = Math.max(col.minWidth ?? 40, Math.min(col.maxWidth ?? 600, startW + ev.clientX - startX));\n this.dispatchEvent(new CustomEvent<DataGridColumnResizeDetail>(`datagrid-column-resize`, { detail: { key: col.key, width: w }, bubbles: true, composed: true }));\n };\n window.addEventListener(`pointermove`, onMove);\n window.addEventListener(`pointerup`, onUp);\n }\n\n // Public API for stress demo\n getVisibleRange(): { startRow: number; endRow: number; startCol: number; endCol: number } {\n const rh = this.rowHeight;\n const startRow = Math.max(0, Math.floor(this._scrollTop / rh) - 2);\n const endRow = Math.min(this._flat.length, Math.ceil((this._scrollTop + this._viewportH) / rh) + 2);\n const startCol = this._findFirstVisibleCol(this._scrollLeft);\n const endCol = this._findLastVisibleCol(this._scrollLeft + this._viewportW);\n return { startRow, endRow, startCol, endCol };\n }\n\n /** Row keys currently within the windowed/visible range, in display order. */\n renderedKeys(): string[] {\n const { startRow, endRow } = this.getVisibleRange();\n return this._flat.slice(startRow, endRow).filter(f => f.type === `row`).map(f => f.key);\n }\n\n /**\n * Row keys strictly intersecting the viewport (no overscan), mirroring\n * `ixfx-grid-list.visibleKeys()` for the `datagrid-viewport-change` detail.\n */\n #visibleKeys(): string[] {\n const rh = this.rowHeight;\n const startRow = Math.max(0, Math.floor(this._scrollTop / rh));\n const endRow = Math.min(this._flat.length, Math.ceil((this._scrollTop + this._viewportH) / rh));\n return this._flat.slice(startRow, endRow).filter(f => f.type === `row`).map(f => f.key);\n }\n\n /** Coalesce viewport-change dispatches to at most one per animation frame. */\n #scheduleViewportChangeEmit(): void {\n if (this.#viewportChangeRaf !== 0)\n return;\n this.#viewportChangeRaf = requestAnimationFrame(() => {\n this.#viewportChangeRaf = 0;\n this.#emitViewportChangeIfChanged();\n });\n }\n\n /**\n * Dispatch `datagrid-viewport-change` with the current key sets — unless\n * neither set changed since the last dispatch, so coalesced frames and\n * no-op scrolls stay silent.\n */\n #emitViewportChangeIfChanged(): void {\n const renderedKeys = this.renderedKeys();\n const visibleKeys = this.#visibleKeys();\n if (sameKeys(this.#lastViewportRenderedKeys, renderedKeys) && sameKeys(this.#lastViewportVisibleKeys, visibleKeys))\n return;\n this.#lastViewportRenderedKeys = renderedKeys;\n this.#lastViewportVisibleKeys = visibleKeys;\n this.dispatchEvent(new CustomEvent<DataGridViewportChangeDetail>(`datagrid-viewport-change`, {\n detail: { renderedKeys, visibleKeys },\n bubbles: true,\n composed: true,\n }));\n }\n\n private _findFirstVisibleCol(scrollLeft: number): number {\n let lo = 0; let hi = this._colOffsets.length - 1; let ans = 0;\n while (lo <= hi) {\n const mid = (lo + hi) >> 1;\n if (this._colOffsets[mid] <= scrollLeft) {\n ans = mid; lo = mid + 1;\n } else {\n hi = mid - 1;\n }\n }\n return ans;\n }\n\n private _findLastVisibleCol(right: number): number {\n for (let i = 0; i < this._colOffsets.length; i++) {\n if (this._colOffsets[i] > right)\n return i;\n }\n return this._colOffsets.length;\n }\n\n protected override render() {\n const rh = this.rowHeight;\n const startRow = Math.max(0, Math.floor(this._scrollTop / rh) - 2);\n const endRow = Math.min(this._flat.length, Math.ceil((this._scrollTop + this._viewportH) / rh) + 2);\n const visibleFlat = this._flat.slice(startRow, endRow);\n const showCheckbox = this.interactionMode === `checked`;\n\n return html`\n <div class=\"grid\">\n <div class=\"header-bar\">\n <div class=\"header-scroll scroll-fade-x\">\n ${showCheckbox ? html`<div class=\"header-cell checkbox-col\"></div>` : nothing}\n ${repeat(this._visibleColumns, c => c.key, (col, idx) => html`\n <div class=\"header-cell ${this._animatingColKeys.has(col.key) ? `width-animating` : ``}\" style=\"width:${col.width ?? 150}px\" ?drag-source=${this._drag?.active && this._drag.sourceCol.key === col.key}\n @click=${(e: MouseEvent) => this._onHeaderClick(col, e)}\n @pointerenter=${() => this._tickled.handlePointerEnter(col.key)}>\n ${col.reorderable !== false\n ? html`<span class=\"reorder-handle\" draggable=\"false\"\n @pointerdown=${(e: PointerEvent) => this._beginHeaderDrag(e, col, idx)}\n ><span class=\"ixfx-handle\" data-handle=\"dotted\" data-shape=\"vertical\" part=\"reorder-handle\"></span></span>`\n : nothing}\n <span class=\"header-label\" @pointerup=${(e: PointerEvent) => this._onHeaderPointerUp(col, e)}>${col.label}</span>\n ${this.sortState?.key === col.key ? html`<span class=\"sort-icon\"><ixfx-icon name=${this.sortState.direction === `asc` ? `chevron-up` : `chevron-down`} size=\"12\"></ixfx-icon></span>` : nothing}\n ${col.button !== false ? html`<span class=\"col-button\" @click=${(e: PointerEvent) => this._onColButtonClick(col, e)}><ixfx-icon name=${col.button && typeof col.button === `object` && col.button.icon ? col.button.icon : this.columnButtonIcon} size=\"14\"></ixfx-icon></span>` : nothing}\n ${col.resizable !== false\n ? html`<span class=\"resize-handle\" ?data-active=${this._resizingColKey === col.key} @pointerdown=${(e: PointerEvent) => this._onResizePointerDown(e, col)} @click=${(e: MouseEvent) => e.stopPropagation()} @dblclick=${(e: MouseEvent) => {\n e.preventDefault(); e.stopPropagation(); this._autoSizeColumn(col);\n }}></span>`\n : nothing}\n </div>\n `)}\n ${this._drag?.active && this._drag.gap !== undefined\n ? html`<div class=\"drop-caret\" style=\"left:${(() => {\n const gap = this._drag!.gap!;\n if (gap < this._colOffsets.length)\n return this._colOffsets[gap];\n const last = this._colOffsets.length - 1;\n return last >= 0 ? this._colOffsets[last] + (this._visibleColumns[last].width ?? 150) : 0;\n })()}px\"></div>`\n : nothing}\n </div>\n ${this.columnMenu === `none`\n ? nothing\n : html`\n <ixfx-menu-trigger label=\"⚙\" placement=\"bottom-end\" @menu-command=${(e: CustomEvent) => {\n const cmd = (e.detail as { command?: string; checked?: boolean; value?: string }).command;\n const checked = (e.detail as { checked?: boolean }).checked;\n const value = (e.detail as { value?: string }).value;\n if (cmd?.startsWith(`col:`)) {\n const key = cmd.slice(4);\n const col = this.columns.find(c => c.key === key);\n if (col)\n this._onVisibilityToggle(col, !!checked);\n e.stopPropagation();\n return;\n }\n if (cmd === `groupBy`) {\n const v = value ?? ``;\n this.groupBy = v || null;\n this._collapsedGroups = new Set();\n this.dispatchEvent(new CustomEvent<DataGridGroupChangeDetail>(`datagrid-group-change`, { detail: { groupBy: this.groupBy as DataGridGroupBy<unknown> | null }, bubbles: true, composed: true }));\n e.stopPropagation();\n }\n }}>\n <ixfx-menu-container slot=\"menu\">\n <ixfx-menu-header label=\"Columns\"></ixfx-menu-header>\n ${repeat(this.columns, c => c.key, col => html`\n <ixfx-menu-check-item command=\"col:${col.key}\" label=${col.label} ?checked=${col.visible !== false}></ixfx-menu-check-item>\n `)}\n ${this.allowGrouping\n ? html`\n <ixfx-menu-separator></ixfx-menu-separator>\n <ixfx-menu-header label=\"Group by\"></ixfx-menu-header>\n <ixfx-menu-radio-group name=\"groupBy\" value=${typeof this.groupBy === `string` ? this.groupBy : ``}>\n <ixfx-menu-radio-item value=\"\" label=\"None\"></ixfx-menu-radio-item>\n ${this.columns.filter(c => c.groupable !== false && (!this.groupableColumns || this.groupableColumns.includes(c.key))).map(col => html`\n <ixfx-menu-radio-item value=${col.key} label=${col.label}></ixfx-menu-radio-item>\n `)}\n </ixfx-menu-radio-group>\n `\n : nothing}\n </ixfx-menu-container>\n </ixfx-menu-trigger>`}\n </div>\n <div class=\"viewport scroll-fade-y\" @scroll=${this._onScroll}>\n <div class=\"spacer\" style=\"height:${this._flat.length * rh}px; width:${this._colWidthSum}px\">\n ${repeat(visibleFlat, f => f.key, (entry, i) => {\n const absIdx = startRow + i;\n if (entry.type === `group`) {\n const gKey = entry.key.replace(/^__group__/, ``);\n const collapsed = this._collapsedGroups.has(gKey);\n return html`<div class=\"group-row ${collapsed ? `collapsed` : ``}\" style=\"top:${absIdx * rh}px; height:${rh}px\" @click=${() => this._toggleGroup(gKey)}><span class=\"caret\"><ixfx-icon name=\"chevron-down\" size=\"12\"></ixfx-icon></span><span>${entry.label}</span><span class=\"count\">(${entry.count})</span><span class=\"divider\"></span></div>`;\n }\n const row = entry.row;\n const absIdx2 = entry.idx;\n const rowKey = entry.key;\n const selected = this._selectedKeys.has(rowKey);\n const tickled = this._tickled.isTickled(rowKey);\n return html`\n <div class=\"row item ${selected ? `selected` : ``} ${tickled ? `tickled` : ``} ${this.zebraStripes && absIdx2 % 2 === 1 ? `zebra-odd` : ``} ${this.#enteringRowKeys.has(rowKey) ? `entering` : ``} ${this.#nativeDragging && rowKey === this.#dragOriginKey ? `dragging-origin` : ``}\" style=\"top:${absIdx * rh}px; height:${rh}px\"\n data-key=${rowKey}\n draggable=${this.#nativeDrag.draggableAttr}\n @click=${(e: MouseEvent) => {\n this._onRowClick(rowKey, null, e); this.dispatchEvent(new CustomEvent<DataGridCellClickDetail>(`datagrid-cell-click`, { detail: { rowKey, colKey: ``, rowIndex: absIdx2, colIndex: -1 }, bubbles: true, composed: true }));\n }}\n @pointerenter=${() => this._tickled.handlePointerEnter(rowKey)}\n @pointerleave=${() => this._tickled.clearTickled()}\n @dblclick=${() => {\n if (this._visibleColumns[0] && this._isEditable(row, this._visibleColumns[0]))\n this._startEdit(rowKey, this._visibleColumns[0].key);\n else\n this._activateRow(rowKey, row, absIdx2);\n }}>\n ${showCheckbox ? html`<div class=\"checkbox-col\"><input type=\"checkbox\" .checked=${selected} @click=${(e: MouseEvent) => this._onCheckboxClick(rowKey, e)} /></div>` : nothing}\n ${repeat(this._visibleColumns, c => c.key, (col) => {\n const val = (row as Record<string, unknown>)[col.key];\n const isEditing = this._isCellEditing(rowKey, col.key);\n if (isEditing) {\n const immediate = this.editability === `immediate` || this._editingRow === rowKey;\n const curVal = immediate ? val : (this._editValue ?? val);\n const effectiveDataType = col.dataType ?? `text`;\n if (effectiveDataType === `boolean` && (col.editor === `auto` || col.editor === `select` || !col.editor)) {\n return html`<div class=\"cell\" data-col=${col.key} style=\"width:${col.width ?? 150}px;justify-content:center;align-items:center\"><input type=\"checkbox\" .checked=${Boolean(curVal)} @change=${(e: Event) => {\n const v = (e.target as HTMLInputElement).checked;\n if (immediate) {\n this._commitImmediate(rowKey, col.key, v);\n } else {\n this._editValue = v; this._commitEdit();\n }\n }} /></div>`;\n }\n if (col.editor === `select`) {\n const opts = (col.editorOptions ?? []) as ReadonlyArray<string | { value: string; label: string }>;\n return html`<div class=\"cell\" data-col=${col.key} style=\"width:${col.width ?? 150}px\"><select @change=${(e: Event) => {\n const v = (e.target as HTMLSelectElement).value;\n if (immediate) {\n this._commitImmediate(rowKey, col.key, v);\n } else {\n this._editValue = v; this._commitEdit();\n }\n }} @keydown=${(e: KeyboardEvent) => {\n if (e.key === `Tab`) {\n e.preventDefault(); e.stopPropagation(); this._tabToNext(rowKey, col.key, e.shiftKey ? -1 : 1);\n } if (e.key === `Escape`) {\n this._editing = null; this._editingRow = null;\n }\n }} @blur=${() => {\n if (this._suppressBlurCommit)\n return; if (!immediate)\n this._commitEdit();\n }}><option value=\"\"></option>${opts.map((o) => {\n const v = typeof o === `string` ? o : o.value;\n const l = typeof o === `string` ? o : o.label;\n return html`<option value=${v} ?selected=${String(curVal) === v}>${l}</option>`;\n })}</select></div>`;\n }\n if (typeof col.editor === `function`) {\n const factory = col.editor as DataGridEditorFactory;\n const ctx = { row, column: col, rowIndex: absIdx2, colIndex: 0, value: curVal, commit: (v: unknown) => {\n if (immediate) {\n this._commitImmediate(rowKey, col.key, v);\n } else {\n this._editValue = v; this._commitEdit();\n }\n }, cancel: () => {\n this._editing = null; this._editingRow = null;\n } };\n return html`<div class=\"cell\" data-col=${col.key} style=\"width:${col.width ?? 150}px\">${factory(ctx)}</div>`;\n }\n const inputType = effectiveDataType === `number` ? `number` : `text`;\n const inputValue = effectiveDataType === `number` ? String(curVal ?? ``) : String(curVal ?? ``);\n return html`<div class=\"cell\" data-col=${col.key} style=\"width:${col.width ?? 150}px\"><input type=${inputType} .value=${inputValue} @input=${(e: Event) => this._editValue = (e.target as HTMLInputElement).value} @keydown=${(e: KeyboardEvent) => {\n if (e.key === `Enter`)\n this._commitEdit(); if (e.key === `Escape`) {\n this._editing = null; this._editingRow = null;\n } if (e.key === `Tab`) {\n e.preventDefault(); e.stopPropagation(); this._tabToNext(rowKey, col.key, e.shiftKey ? -1 : 1);\n }\n }} @blur=${() => {\n if (this._suppressBlurCommit)\n return; if (!immediate)\n this._commitEdit();\n }} autofocus /></div>`;\n }\n const displayVal = this._formatValue(val, col, row);\n const rendered = col.renderer ? col.renderer(row as never, col as never, absIdx2) : displayVal;\n // renderer may return TemplateResult or primitive; if renderer not used, display formatted\n const cellContent = col.renderer ? rendered : displayVal;\n const editable = this._isEditable(row, col);\n const textEditable = editable && this._isTextEditor(col);\n const leftAligned = col.align !== `right` && col.align !== `center`;\n const indent = leftAligned && col.reorderable !== false\n ? `padding-left:calc(var(--space-s) + var(--data-grid-reorder-handle-width, 10px) + var(--space-xs));`\n : ``;\n // Plain (non-renderer) text can pan instead of being CSS-ellipsised,\n // while its row is selected or under the tickle cursor.\n const canPan = this.cellOverflow === `pan-text` && !col.renderer && (selected || tickled);\n const look = this._cellLook(row, col.key);\n const cellStyle = look.textColor === undefined\n ? ``\n : `color:${look.textColor};`;\n return html`<div class=\"cell ${textEditable ? `editable-text` : ``} ${this._animatingColKeys.has(col.key) ? `width-animating` : ``}\" data-col=${col.key} style=\"width:${col.width ?? 150}px; justify-content:${col.align === `right` ? `flex-end` : col.align === `center` ? `center` : `flex-start`}; ${indent} ${cellStyle}\"\n @click=${(e: MouseEvent) => {\n this._lastClickedCell = { rowKey, colKey: col.key }; if (col.selectable !== false) {\n e.stopPropagation(); this._onRowClick(rowKey, col, e); this._handleCellSecondClick(rowKey, col);\n } this.dispatchEvent(new CustomEvent<DataGridCellClickDetail>(`datagrid-cell-click`, { detail: { rowKey, colKey: col.key, rowIndex: absIdx2, colIndex: this.columns.indexOf(col) }, bubbles: true, composed: true }));\n }}\n >${look.icon === undefined ? nothing : html`<span class=\"cell-icon\" part=\"icon\" style=${look.iconColor === undefined ? nothing : `color:${look.iconColor}`}>${look.icon}</span>`}${canPan ? html`<ixfx-pan-text mode=\"loop\">${cellContent as unknown as string}</ixfx-pan-text>` : cellContent as unknown as string}${look.badge === undefined ? nothing : html`<span class=\"cell-badge\" part=\"badge\">${look.badge}</span>`}</div>`;\n })}\n </div>\n `;\n })}\n </div>\n </div>\n ${this.search.renderField()}\n </div>\n `;\n }\n}\n\ndeclare global {\n interface HTMLElementTagNameMap { 'ixfx-data-grid': DataGridElement }\n}\nexport interface DataGridElement {\n addEventListener: (<K extends keyof DataGridElementEventMap>(type: K, listener: (this: DataGridElement, event: DataGridElementEventMap[K]) => void, options?: boolean | AddEventListenerOptions) => void) & ((type: string, listener: EventListenerOrEventListenerObject, options?: boolean | AddEventListenerOptions) => void);\n removeEventListener: (<K extends keyof DataGridElementEventMap>(type: K, listener: (this: DataGridElement, event: DataGridElementEventMap[K]) => void, options?: boolean | EventListenerOptions) => void) & ((type: string, listener: EventListenerOrEventListenerObject, options?: boolean | EventListenerOptions) => void);\n}\n"],"mappings":"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"}