@expressivecss/expressive 0.14.1 → 0.16.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (603) hide show
  1. package/CHANGELOG.md +1589 -1
  2. package/README.md +9 -8
  3. package/dist/css/expressive.css +19304 -12021
  4. package/dist/css/expressive.css.map +1 -1
  5. package/dist/css/expressive.min.css +1 -1
  6. package/dist/css/expressive.min.css.map +1 -1
  7. package/dist/fonts/LICENSE-noto-sans-arabic +93 -0
  8. package/dist/fonts/LICENSE-noto-sans-hebrew +93 -0
  9. package/dist/fonts/LICENSE-noto-sans-thai +93 -0
  10. package/dist/fonts/material-symbols-outlined.woff2 +0 -0
  11. package/dist/fonts/material-symbols-rounded.woff2 +0 -0
  12. package/dist/fonts/material-symbols-sharp.woff2 +0 -0
  13. package/dist/fonts/noto-sans-arabic-arabic-400.woff2 +0 -0
  14. package/dist/fonts/noto-sans-arabic-arabic-500.woff2 +0 -0
  15. package/dist/fonts/noto-sans-arabic-arabic-700.woff2 +0 -0
  16. package/dist/fonts/noto-sans-cyrillic-400.woff2 +0 -0
  17. package/dist/fonts/noto-sans-cyrillic-500.woff2 +0 -0
  18. package/dist/fonts/noto-sans-cyrillic-700.woff2 +0 -0
  19. package/dist/fonts/noto-sans-cyrillic-ext-400.woff2 +0 -0
  20. package/dist/fonts/noto-sans-cyrillic-ext-500.woff2 +0 -0
  21. package/dist/fonts/noto-sans-cyrillic-ext-700.woff2 +0 -0
  22. package/dist/fonts/noto-sans-devanagari-400.woff2 +0 -0
  23. package/dist/fonts/noto-sans-devanagari-500.woff2 +0 -0
  24. package/dist/fonts/noto-sans-devanagari-700.woff2 +0 -0
  25. package/dist/fonts/noto-sans-greek-400.woff2 +0 -0
  26. package/dist/fonts/noto-sans-greek-500.woff2 +0 -0
  27. package/dist/fonts/noto-sans-greek-700.woff2 +0 -0
  28. package/dist/fonts/noto-sans-greek-ext-400.woff2 +0 -0
  29. package/dist/fonts/noto-sans-greek-ext-500.woff2 +0 -0
  30. package/dist/fonts/noto-sans-greek-ext-700.woff2 +0 -0
  31. package/dist/fonts/noto-sans-hebrew-hebrew-400.woff2 +0 -0
  32. package/dist/fonts/noto-sans-hebrew-hebrew-500.woff2 +0 -0
  33. package/dist/fonts/noto-sans-hebrew-hebrew-700.woff2 +0 -0
  34. package/dist/fonts/noto-sans-latin-700.woff2 +0 -0
  35. package/dist/fonts/noto-sans-latin-ext-400.woff2 +0 -0
  36. package/dist/fonts/noto-sans-latin-ext-500.woff2 +0 -0
  37. package/dist/fonts/noto-sans-latin-ext-700.woff2 +0 -0
  38. package/dist/fonts/noto-sans-thai-thai-400.woff2 +0 -0
  39. package/dist/fonts/noto-sans-thai-thai-500.woff2 +0 -0
  40. package/dist/fonts/noto-sans-thai-thai-700.woff2 +0 -0
  41. package/dist/fonts/noto-sans-vietnamese-400.woff2 +0 -0
  42. package/dist/fonts/noto-sans-vietnamese-500.woff2 +0 -0
  43. package/dist/fonts/noto-sans-vietnamese-700.woff2 +0 -0
  44. package/dist/fonts/roboto-cyrillic-400.woff2 +0 -0
  45. package/dist/fonts/roboto-cyrillic-500.woff2 +0 -0
  46. package/dist/fonts/roboto-cyrillic-700.woff2 +0 -0
  47. package/dist/fonts/roboto-cyrillic-ext-400.woff2 +0 -0
  48. package/dist/fonts/roboto-cyrillic-ext-500.woff2 +0 -0
  49. package/dist/fonts/roboto-cyrillic-ext-700.woff2 +0 -0
  50. package/dist/fonts/roboto-greek-400.woff2 +0 -0
  51. package/dist/fonts/roboto-greek-500.woff2 +0 -0
  52. package/dist/fonts/roboto-greek-700.woff2 +0 -0
  53. package/dist/fonts/roboto-greek-ext-400.woff2 +0 -0
  54. package/dist/fonts/roboto-greek-ext-500.woff2 +0 -0
  55. package/dist/fonts/roboto-greek-ext-700.woff2 +0 -0
  56. package/dist/fonts/roboto-latin-700.woff2 +0 -0
  57. package/dist/fonts/roboto-latin-ext-400.woff2 +0 -0
  58. package/dist/fonts/roboto-latin-ext-500.woff2 +0 -0
  59. package/dist/fonts/roboto-latin-ext-700.woff2 +0 -0
  60. package/dist/fonts/roboto-vietnamese-400.woff2 +0 -0
  61. package/dist/fonts/roboto-vietnamese-500.woff2 +0 -0
  62. package/dist/fonts/roboto-vietnamese-700.woff2 +0 -0
  63. package/dist/js/chunks/chunk-2CS6TITK.mjs +219 -0
  64. package/dist/js/chunks/chunk-2CS6TITK.mjs.map +7 -0
  65. package/dist/js/chunks/chunk-2RLBDFH4.mjs +108 -0
  66. package/dist/js/chunks/chunk-2RLBDFH4.mjs.map +7 -0
  67. package/dist/js/chunks/chunk-3L3QIYLC.mjs +85 -0
  68. package/dist/js/chunks/chunk-3L3QIYLC.mjs.map +7 -0
  69. package/dist/js/chunks/chunk-4EWGD4V2.mjs +75 -0
  70. package/dist/js/chunks/chunk-4EWGD4V2.mjs.map +7 -0
  71. package/dist/js/chunks/chunk-4IKVPCSU.mjs +7 -0
  72. package/dist/js/chunks/chunk-4IKVPCSU.mjs.map +7 -0
  73. package/dist/js/chunks/chunk-4PIXLDNJ.mjs +127 -0
  74. package/dist/js/chunks/chunk-4PIXLDNJ.mjs.map +7 -0
  75. package/dist/js/chunks/{chunk-A7ALMYUR.mjs → chunk-4QUCNFSD.mjs} +68 -125
  76. package/dist/js/chunks/chunk-4QUCNFSD.mjs.map +7 -0
  77. package/dist/js/chunks/{chunk-4TKTLGEM.mjs → chunk-4TRZ2AER.mjs} +35 -41
  78. package/dist/js/chunks/chunk-4TRZ2AER.mjs.map +7 -0
  79. package/dist/js/chunks/{chunk-BG6ZRB5H.mjs → chunk-5KIHWJI2.mjs} +40 -26
  80. package/dist/js/chunks/chunk-5KIHWJI2.mjs.map +7 -0
  81. package/dist/js/chunks/{chunk-YDCS5S3J.mjs → chunk-67ZPPKXS.mjs} +20 -33
  82. package/dist/js/chunks/chunk-67ZPPKXS.mjs.map +7 -0
  83. package/dist/js/chunks/{chunk-3DHK5CZU.mjs → chunk-6FSEUFVW.mjs} +40 -29
  84. package/dist/js/chunks/chunk-6FSEUFVW.mjs.map +7 -0
  85. package/dist/js/chunks/chunk-752ADW4M.mjs +225 -0
  86. package/dist/js/chunks/chunk-752ADW4M.mjs.map +7 -0
  87. package/dist/js/chunks/{chunk-GVGT6MIU.mjs → chunk-75E5EDJF.mjs} +3 -11
  88. package/dist/js/chunks/chunk-75E5EDJF.mjs.map +7 -0
  89. package/dist/js/chunks/{chunk-TBM3FT7G.mjs → chunk-7NLUI3RR.mjs} +148 -78
  90. package/dist/js/chunks/chunk-7NLUI3RR.mjs.map +7 -0
  91. package/dist/js/chunks/chunk-7W7TV6NY.mjs +108 -0
  92. package/dist/js/chunks/chunk-7W7TV6NY.mjs.map +7 -0
  93. package/dist/js/chunks/chunk-7YQBHTK3.mjs +225 -0
  94. package/dist/js/chunks/chunk-7YQBHTK3.mjs.map +7 -0
  95. package/dist/js/chunks/chunk-7YZ5CN3V.mjs +33 -0
  96. package/dist/js/chunks/chunk-7YZ5CN3V.mjs.map +7 -0
  97. package/dist/js/chunks/chunk-AI73GJKG.mjs +28 -0
  98. package/dist/js/chunks/chunk-AI73GJKG.mjs.map +7 -0
  99. package/dist/js/chunks/{chunk-NS2UMNZV.mjs → chunk-ANKFWNWT.mjs} +21 -45
  100. package/dist/js/chunks/chunk-ANKFWNWT.mjs.map +7 -0
  101. package/dist/js/chunks/{chunk-GIW4K4SE.mjs → chunk-B7DQFHA5.mjs} +37 -53
  102. package/dist/js/chunks/chunk-B7DQFHA5.mjs.map +7 -0
  103. package/dist/js/chunks/chunk-BIGU5RCJ.mjs +153 -0
  104. package/dist/js/chunks/chunk-BIGU5RCJ.mjs.map +7 -0
  105. package/dist/js/chunks/{chunk-GUB3TNO2.mjs → chunk-BPF3I2MN.mjs} +109 -27
  106. package/dist/js/chunks/chunk-BPF3I2MN.mjs.map +7 -0
  107. package/dist/js/chunks/chunk-CMGXGYUC.mjs +74 -0
  108. package/dist/js/chunks/chunk-CMGXGYUC.mjs.map +7 -0
  109. package/dist/js/chunks/{chunk-JIDMQGK6.mjs → chunk-CSYWKEK3.mjs} +322 -223
  110. package/dist/js/chunks/chunk-CSYWKEK3.mjs.map +7 -0
  111. package/dist/js/chunks/chunk-CZSQHXEV.mjs +227 -0
  112. package/dist/js/chunks/chunk-CZSQHXEV.mjs.map +7 -0
  113. package/dist/js/chunks/chunk-DZYVU75J.mjs +121 -0
  114. package/dist/js/chunks/chunk-DZYVU75J.mjs.map +7 -0
  115. package/dist/js/chunks/{chunk-QDAL4IYN.mjs → chunk-EC26RU2D.mjs} +11 -29
  116. package/dist/js/chunks/chunk-EC26RU2D.mjs.map +7 -0
  117. package/dist/js/chunks/{chunk-3GVFZ4XO.mjs → chunk-EVCVFEV3.mjs} +238 -152
  118. package/dist/js/chunks/chunk-EVCVFEV3.mjs.map +7 -0
  119. package/dist/js/chunks/chunk-FCNF4GRJ.mjs +445 -0
  120. package/dist/js/chunks/chunk-FCNF4GRJ.mjs.map +7 -0
  121. package/dist/js/chunks/chunk-GCWWEZKO.mjs +342 -0
  122. package/dist/js/chunks/chunk-GCWWEZKO.mjs.map +7 -0
  123. package/dist/js/chunks/chunk-GNRSYMVH.mjs +1 -0
  124. package/dist/js/chunks/chunk-GVZQH2H5.mjs +54 -0
  125. package/dist/js/chunks/chunk-GVZQH2H5.mjs.map +7 -0
  126. package/dist/js/chunks/chunk-GWZ76SR4.mjs +435 -0
  127. package/dist/js/chunks/chunk-GWZ76SR4.mjs.map +7 -0
  128. package/dist/js/chunks/{chunk-ZAS25YFD.mjs → chunk-ILDRRG7T.mjs} +21 -23
  129. package/dist/js/chunks/chunk-ILDRRG7T.mjs.map +7 -0
  130. package/dist/js/chunks/chunk-INLZWHLY.mjs +80 -0
  131. package/dist/js/chunks/chunk-INLZWHLY.mjs.map +7 -0
  132. package/dist/js/chunks/chunk-JUKBBN6P.mjs +175 -0
  133. package/dist/js/chunks/chunk-JUKBBN6P.mjs.map +7 -0
  134. package/dist/js/chunks/chunk-KYIEG4U3.mjs +730 -0
  135. package/dist/js/chunks/chunk-KYIEG4U3.mjs.map +7 -0
  136. package/dist/js/chunks/{chunk-KHV6DZXX.mjs → chunk-KZPSAXIU.mjs} +156 -46
  137. package/dist/js/chunks/chunk-KZPSAXIU.mjs.map +7 -0
  138. package/dist/js/chunks/chunk-LDXCC2L3.mjs +438 -0
  139. package/dist/js/chunks/chunk-LDXCC2L3.mjs.map +7 -0
  140. package/dist/js/chunks/chunk-NAC72P7R.mjs +137 -0
  141. package/dist/js/chunks/chunk-NAC72P7R.mjs.map +7 -0
  142. package/dist/js/chunks/chunk-NBJAUGPP.mjs +244 -0
  143. package/dist/js/chunks/chunk-NBJAUGPP.mjs.map +7 -0
  144. package/dist/js/chunks/chunk-NNHVANQA.mjs +113 -0
  145. package/dist/js/chunks/chunk-NNHVANQA.mjs.map +7 -0
  146. package/dist/js/chunks/chunk-NVQ5EHCU.mjs +376 -0
  147. package/dist/js/chunks/chunk-NVQ5EHCU.mjs.map +7 -0
  148. package/dist/js/chunks/{chunk-Z2NRKI7R.mjs → chunk-OP43LLIC.mjs} +44 -73
  149. package/dist/js/chunks/chunk-OP43LLIC.mjs.map +7 -0
  150. package/dist/js/chunks/chunk-OUCHKSAW.mjs +63 -0
  151. package/dist/js/chunks/chunk-OUCHKSAW.mjs.map +7 -0
  152. package/dist/js/chunks/{chunk-PM655FXL.mjs → chunk-OYNUDOHR.mjs} +20 -48
  153. package/dist/js/chunks/chunk-OYNUDOHR.mjs.map +7 -0
  154. package/dist/js/chunks/{chunk-UEZUJQ66.mjs → chunk-P6DRQ6KS.mjs} +36 -31
  155. package/dist/js/chunks/chunk-P6DRQ6KS.mjs.map +7 -0
  156. package/dist/js/chunks/chunk-PA7NU5AK.mjs +99 -0
  157. package/dist/js/chunks/chunk-PA7NU5AK.mjs.map +7 -0
  158. package/dist/js/chunks/chunk-QACZ6TUP.mjs +224 -0
  159. package/dist/js/chunks/chunk-QACZ6TUP.mjs.map +7 -0
  160. package/dist/js/chunks/{chunk-5HQSGDZ5.mjs → chunk-QXKWVHBD.mjs} +286 -203
  161. package/dist/js/chunks/chunk-QXKWVHBD.mjs.map +7 -0
  162. package/dist/js/chunks/{chunk-DAIU5SLG.mjs → chunk-ROH2HDB4.mjs} +7 -6
  163. package/dist/js/chunks/chunk-ROH2HDB4.mjs.map +7 -0
  164. package/dist/js/chunks/chunk-S23RJ3XY.mjs +86 -0
  165. package/dist/js/chunks/chunk-S23RJ3XY.mjs.map +7 -0
  166. package/dist/js/chunks/{chunk-FS7XY3HT.mjs → chunk-SPPHF7YZ.mjs} +36 -29
  167. package/dist/js/chunks/chunk-SPPHF7YZ.mjs.map +7 -0
  168. package/dist/js/chunks/chunk-T3BNSRP3.mjs +152 -0
  169. package/dist/js/chunks/chunk-T3BNSRP3.mjs.map +7 -0
  170. package/dist/js/chunks/chunk-TFABTUAZ.mjs +108 -0
  171. package/dist/js/chunks/chunk-TFABTUAZ.mjs.map +7 -0
  172. package/dist/js/chunks/chunk-U4B3VHFS.mjs +507 -0
  173. package/dist/js/chunks/chunk-U4B3VHFS.mjs.map +7 -0
  174. package/dist/js/chunks/chunk-UGJHCHXG.mjs +341 -0
  175. package/dist/js/chunks/chunk-UGJHCHXG.mjs.map +7 -0
  176. package/dist/js/chunks/chunk-VFV75DHF.mjs +70 -0
  177. package/dist/js/chunks/chunk-VFV75DHF.mjs.map +7 -0
  178. package/dist/js/chunks/{chunk-4HZMB7LI.mjs → chunk-VGY4M57S.mjs} +281 -135
  179. package/dist/js/chunks/chunk-VGY4M57S.mjs.map +7 -0
  180. package/dist/js/chunks/chunk-VH4BMAZS.mjs +167 -0
  181. package/dist/js/chunks/chunk-VH4BMAZS.mjs.map +7 -0
  182. package/dist/js/chunks/chunk-VJVQIXHC.mjs +123 -0
  183. package/dist/js/chunks/chunk-VJVQIXHC.mjs.map +7 -0
  184. package/dist/js/chunks/{chunk-S3XDFGSZ.mjs → chunk-VMY55K2X.mjs} +92 -141
  185. package/dist/js/chunks/chunk-VMY55K2X.mjs.map +7 -0
  186. package/dist/js/chunks/{chunk-UEXCIMJZ.mjs → chunk-VR3L2WN5.mjs} +11 -17
  187. package/dist/js/chunks/chunk-VR3L2WN5.mjs.map +7 -0
  188. package/dist/js/chunks/chunk-W6FAL3TI.mjs +38 -0
  189. package/dist/js/chunks/chunk-W6FAL3TI.mjs.map +7 -0
  190. package/dist/js/chunks/chunk-WU7XJ4RR.mjs +450 -0
  191. package/dist/js/chunks/chunk-WU7XJ4RR.mjs.map +7 -0
  192. package/dist/js/chunks/chunk-X7SDA2J5.mjs +116 -0
  193. package/dist/js/chunks/chunk-X7SDA2J5.mjs.map +7 -0
  194. package/dist/js/chunks/chunk-Y6H2X7ZC.mjs +209 -0
  195. package/dist/js/chunks/chunk-Y6H2X7ZC.mjs.map +7 -0
  196. package/dist/js/chunks/chunk-Y6TLRA3U.mjs +129 -0
  197. package/dist/js/chunks/chunk-Y6TLRA3U.mjs.map +7 -0
  198. package/dist/js/chunks/chunk-Z4GICXR2.mjs +190 -0
  199. package/dist/js/chunks/chunk-Z4GICXR2.mjs.map +7 -0
  200. package/dist/js/chunks/chunk-Z4OARDZ7.mjs +442 -0
  201. package/dist/js/chunks/chunk-Z4OARDZ7.mjs.map +7 -0
  202. package/dist/js/chunks/{chunk-MZ6Z24BX.mjs → chunk-ZJNLAGY5.mjs} +19 -34
  203. package/dist/js/chunks/chunk-ZJNLAGY5.mjs.map +7 -0
  204. package/dist/js/chunks/chunk-ZKWUWBUB.mjs +81 -0
  205. package/dist/js/chunks/chunk-ZKWUWBUB.mjs.map +7 -0
  206. package/dist/js/chunks/chunk-ZM3XBHWV.mjs +746 -0
  207. package/dist/js/chunks/chunk-ZM3XBHWV.mjs.map +7 -0
  208. package/dist/js/chunks/chunk-ZO6ZLHFF.mjs +48 -0
  209. package/dist/js/chunks/chunk-ZO6ZLHFF.mjs.map +7 -0
  210. package/dist/js/chunks/chunk-ZVLOUDIJ.mjs +251 -0
  211. package/dist/js/chunks/chunk-ZVLOUDIJ.mjs.map +7 -0
  212. package/dist/js/expressive.cjs +10333 -4070
  213. package/dist/js/expressive.cjs.map +4 -4
  214. package/dist/js/expressive.js +10333 -4070
  215. package/dist/js/expressive.js.map +4 -4
  216. package/dist/js/expressive.min.js +23 -25
  217. package/dist/js/expressive.min.js.map +4 -4
  218. package/dist/js/expressive.mjs +184 -69
  219. package/dist/js/expressive.mjs.map +2 -2
  220. package/dist/js/internal/behaviors/bottomSheets.mjs +4 -3
  221. package/dist/js/internal/behaviors/copy.mjs +9 -0
  222. package/dist/js/internal/behaviors/copy.mjs.map +7 -0
  223. package/dist/js/internal/behaviors/dataTables.mjs +10 -0
  224. package/dist/js/internal/behaviors/dataTables.mjs.map +7 -0
  225. package/dist/js/internal/behaviors/dialogs.mjs +2 -2
  226. package/dist/js/internal/behaviors/forms.mjs +2 -2
  227. package/dist/js/internal/behaviors/imageCompare.mjs +8 -0
  228. package/dist/js/internal/behaviors/imageCompare.mjs.map +7 -0
  229. package/dist/js/internal/behaviors/lists.mjs +8 -0
  230. package/dist/js/internal/behaviors/lists.mjs.map +7 -0
  231. package/dist/js/internal/behaviors/paneResize.mjs +8 -0
  232. package/dist/js/internal/behaviors/paneResize.mjs.map +7 -0
  233. package/dist/js/internal/behaviors/sheetDrag.mjs +7 -2
  234. package/dist/js/internal/behaviors/sideSheets.mjs +4 -3
  235. package/dist/js/internal/behaviors/sortable.mjs +8 -0
  236. package/dist/js/internal/behaviors/sortable.mjs.map +7 -0
  237. package/dist/js/internal/behaviors/theme.mjs +8 -0
  238. package/dist/js/internal/behaviors/theme.mjs.map +7 -0
  239. package/dist/js/internal/behaviors/tour.mjs +8 -0
  240. package/dist/js/internal/behaviors/tour.mjs.map +7 -0
  241. package/dist/js/internal/behaviors/transferList.mjs +8 -0
  242. package/dist/js/internal/behaviors/transferList.mjs.map +7 -0
  243. package/dist/js/internal/components/appBar.mjs +3 -2
  244. package/dist/js/internal/components/autocomplete.mjs +4 -4
  245. package/dist/js/internal/components/backToTop.mjs +9 -0
  246. package/dist/js/internal/components/backToTop.mjs.map +7 -0
  247. package/dist/js/internal/components/barChart.mjs +5 -4
  248. package/dist/js/internal/components/buttonGroup.mjs +3 -2
  249. package/dist/js/internal/components/buttons.mjs +3 -3
  250. package/dist/js/internal/components/cards.mjs +3 -3
  251. package/dist/js/internal/components/carousel.mjs +3 -3
  252. package/dist/js/internal/components/cascader.mjs +10 -0
  253. package/dist/js/internal/components/cascader.mjs.map +7 -0
  254. package/dist/js/internal/components/characterCounter.mjs +3 -2
  255. package/dist/js/internal/components/chips.mjs +6 -5
  256. package/dist/js/internal/components/colorPicker.mjs +9 -0
  257. package/dist/js/internal/components/colorPicker.mjs.map +7 -0
  258. package/dist/js/internal/components/columnChart.mjs +4 -3
  259. package/dist/js/internal/components/commandPalette.mjs +3 -3
  260. package/dist/js/internal/components/confetti.mjs +3 -2
  261. package/dist/js/internal/components/currencyInput.mjs +9 -0
  262. package/dist/js/internal/components/currencyInput.mjs.map +7 -0
  263. package/dist/js/internal/components/datepicker.mjs +11 -8
  264. package/dist/js/internal/components/expandingCard.mjs +3 -3
  265. package/dist/js/internal/components/funnelChart.mjs +10 -0
  266. package/dist/js/internal/components/funnelChart.mjs.map +7 -0
  267. package/dist/js/internal/components/heatmapChart.mjs +4 -3
  268. package/dist/js/internal/components/hoverCard.mjs +9 -0
  269. package/dist/js/internal/components/hoverCard.mjs.map +7 -0
  270. package/dist/js/internal/components/index.mjs +133 -64
  271. package/dist/js/internal/components/inputMask.mjs +9 -0
  272. package/dist/js/internal/components/inputMask.mjs.map +7 -0
  273. package/dist/js/internal/components/keypad.mjs +9 -0
  274. package/dist/js/internal/components/keypad.mjs.map +7 -0
  275. package/dist/js/internal/components/lightbox.mjs +3 -3
  276. package/dist/js/internal/components/lineChart.mjs +29 -4
  277. package/dist/js/internal/components/loadingOverlay.mjs +9 -0
  278. package/dist/js/internal/components/loadingOverlay.mjs.map +7 -0
  279. package/dist/js/internal/components/mapView.mjs +3 -3
  280. package/dist/js/internal/components/menu.mjs +3 -3
  281. package/dist/js/internal/components/menubar.mjs +10 -0
  282. package/dist/js/internal/components/menubar.mjs.map +7 -0
  283. package/dist/js/internal/components/messageScroller.mjs +3 -3
  284. package/dist/js/internal/components/mixedChart.mjs +5 -4
  285. package/dist/js/internal/components/navigationRail.mjs +3 -2
  286. package/dist/js/internal/components/particles.mjs +3 -2
  287. package/dist/js/internal/components/pieChart.mjs +4 -3
  288. package/dist/js/internal/components/pullToRefresh.mjs +9 -0
  289. package/dist/js/internal/components/pullToRefresh.mjs.map +7 -0
  290. package/dist/js/internal/components/questionnaire.mjs +3 -3
  291. package/dist/js/internal/components/radarChart.mjs +4 -3
  292. package/dist/js/internal/components/radialChart.mjs +4 -3
  293. package/dist/js/internal/components/registry.mjs +59 -40
  294. package/dist/js/internal/components/richTextEditor.mjs +3 -3
  295. package/dist/js/internal/components/sankeyChart.mjs +10 -0
  296. package/dist/js/internal/components/sankeyChart.mjs.map +7 -0
  297. package/dist/js/internal/components/scatterChart.mjs +10 -0
  298. package/dist/js/internal/components/scatterChart.mjs.map +7 -0
  299. package/dist/js/internal/components/scrollspy.mjs +3 -2
  300. package/dist/js/internal/components/select.mjs +4 -4
  301. package/dist/js/internal/components/showMore.mjs +9 -0
  302. package/dist/js/internal/components/showMore.mjs.map +7 -0
  303. package/dist/js/internal/components/slider.mjs +3 -3
  304. package/dist/js/internal/components/snackbar.mjs +2 -2
  305. package/dist/js/internal/components/swipeActions.mjs +9 -0
  306. package/dist/js/internal/components/swipeActions.mjs.map +7 -0
  307. package/dist/js/internal/components/tabs.mjs +3 -4
  308. package/dist/js/internal/components/timepicker.mjs +5 -4
  309. package/dist/js/internal/components/tooltip.mjs +3 -3
  310. package/dist/js/internal/components/treeSelect.mjs +13 -0
  311. package/dist/js/internal/components/treeSelect.mjs.map +7 -0
  312. package/dist/js/internal/components/treemapChart.mjs +10 -0
  313. package/dist/js/internal/components/treemapChart.mjs.map +7 -0
  314. package/dist/js/internal/core/component.mjs +2 -1
  315. package/dist/js/internal/core/formControl.mjs +12 -0
  316. package/dist/js/internal/core/formControl.mjs.map +7 -0
  317. package/dist/js/internal/core/spring.mjs +11 -0
  318. package/dist/js/internal/core/spring.mjs.map +7 -0
  319. package/dist/js/internal/core/utils.mjs +11 -3
  320. package/dist/js/internal/plugins/dockedDisplayPlugin.mjs +2 -2
  321. package/dist/js/internal/plugins/modalDisplayPlugin.mjs +13 -0
  322. package/dist/js/internal/plugins/modalDisplayPlugin.mjs.map +7 -0
  323. package/dist/js/modular.mjs +175 -69
  324. package/dist/types/behaviors/bottomSheets.d.ts +19 -3
  325. package/dist/types/behaviors/copy.d.ts +18 -0
  326. package/dist/types/behaviors/dataTables.d.ts +129 -0
  327. package/dist/types/behaviors/dialogs.d.ts +27 -1
  328. package/dist/types/behaviors/forms.d.ts +68 -2
  329. package/dist/types/behaviors/imageCompare.d.ts +12 -0
  330. package/dist/types/behaviors/lists.d.ts +12 -0
  331. package/dist/types/behaviors/paneResize.d.ts +29 -0
  332. package/dist/types/behaviors/sheetDrag.d.ts +18 -0
  333. package/dist/types/behaviors/sideSheets.d.ts +1 -1
  334. package/dist/types/behaviors/sortable.d.ts +28 -0
  335. package/dist/types/behaviors/theme.d.ts +22 -0
  336. package/dist/types/behaviors/tour.d.ts +36 -0
  337. package/dist/types/behaviors/transferList.d.ts +51 -0
  338. package/dist/types/components/appBar.d.ts +5 -6
  339. package/dist/types/components/autocomplete.d.ts +92 -17
  340. package/dist/types/components/backToTop.d.ts +36 -0
  341. package/dist/types/components/barChart.d.ts +3 -6
  342. package/dist/types/components/buttonGroup.d.ts +2 -4
  343. package/dist/types/components/buttons.d.ts +5 -5
  344. package/dist/types/components/cards.d.ts +3 -16
  345. package/dist/types/components/carousel.d.ts +9 -15
  346. package/dist/types/components/cascader.d.ts +130 -0
  347. package/dist/types/components/characterCounter.d.ts +2 -15
  348. package/dist/types/components/chips.d.ts +65 -19
  349. package/dist/types/components/colorPicker.d.ts +42 -0
  350. package/dist/types/components/columnChart.d.ts +23 -10
  351. package/dist/types/components/commandPalette.d.ts +11 -16
  352. package/dist/types/components/confetti.d.ts +2 -4
  353. package/dist/types/components/currencyInput.d.ts +59 -0
  354. package/dist/types/components/datepicker.d.ts +59 -36
  355. package/dist/types/components/expandingCard.d.ts +6 -6
  356. package/dist/types/components/funnelChart.d.ts +38 -0
  357. package/dist/types/components/heatmapChart.d.ts +39 -8
  358. package/dist/types/components/hoverCard.d.ts +58 -0
  359. package/dist/types/components/index.d.ts +17 -1
  360. package/dist/types/components/inputMask.d.ts +30 -0
  361. package/dist/types/components/keypad.d.ts +66 -0
  362. package/dist/types/components/lightbox.d.ts +17 -25
  363. package/dist/types/components/lineChart.d.ts +176 -10
  364. package/dist/types/components/loadingOverlay.d.ts +42 -0
  365. package/dist/types/components/mapView.d.ts +26 -17
  366. package/dist/types/components/menu.d.ts +61 -22
  367. package/dist/types/components/menubar.d.ts +37 -0
  368. package/dist/types/components/messageScroller.d.ts +2 -14
  369. package/dist/types/components/mixedChart.d.ts +15 -6
  370. package/dist/types/components/navigationRail.d.ts +16 -5
  371. package/dist/types/components/particles.d.ts +8 -4
  372. package/dist/types/components/pieChart.d.ts +32 -7
  373. package/dist/types/components/pullToRefresh.d.ts +80 -0
  374. package/dist/types/components/questionnaire.d.ts +58 -16
  375. package/dist/types/components/radarChart.d.ts +10 -6
  376. package/dist/types/components/radialChart.d.ts +58 -8
  377. package/dist/types/components/registry.d.ts +77 -3
  378. package/dist/types/components/richTextEditor.d.ts +6 -14
  379. package/dist/types/components/sankeyChart.d.ts +72 -0
  380. package/dist/types/components/scatterChart.d.ts +102 -0
  381. package/dist/types/components/scrollspy.d.ts +3 -5
  382. package/dist/types/components/select.d.ts +43 -30
  383. package/dist/types/components/showMore.d.ts +51 -0
  384. package/dist/types/components/slider.d.ts +5 -15
  385. package/dist/types/components/snackbar.d.ts +62 -0
  386. package/dist/types/components/swipeActions.d.ts +81 -0
  387. package/dist/types/components/tabs.d.ts +93 -27
  388. package/dist/types/components/timepicker.d.ts +114 -20
  389. package/dist/types/components/tooltip.d.ts +56 -20
  390. package/dist/types/components/treeSelect.d.ts +106 -0
  391. package/dist/types/components/treemapChart.d.ts +56 -0
  392. package/dist/types/core/component.d.ts +43 -25
  393. package/dist/types/core/formControl.d.ts +21 -0
  394. package/dist/types/core/spring.d.ts +20 -0
  395. package/dist/types/core/utils.d.ts +85 -72
  396. package/dist/types/modular.d.ts +33 -1
  397. package/dist/types/plugins/dockedDisplayPlugin.d.ts +10 -7
  398. package/dist/types/plugins/modalDisplayPlugin.d.ts +32 -0
  399. package/package.json +10 -8
  400. package/src/sass/README.md +27 -18
  401. package/src/sass/abstracts/_breakpoints.scss +0 -1
  402. package/src/sass/abstracts/_elevation.scss +13 -7
  403. package/src/sass/abstracts/_index.scss +1 -0
  404. package/src/sass/abstracts/_mixins.scss +438 -92
  405. package/src/sass/abstracts/_spring.scss +63 -0
  406. package/src/sass/abstracts/_variables.scss +43 -15
  407. package/src/sass/base/_fonts.scss +61 -48
  408. package/src/sass/base/_global.scss +105 -34
  409. package/src/sass/base/_index.scss +3 -1
  410. package/src/sass/base/_normalize.scss +59 -114
  411. package/src/sass/base/_print.scss +21 -0
  412. package/src/sass/base/_prose.scss +68 -0
  413. package/src/sass/base/_typography.scss +9 -5
  414. package/src/sass/components/_accordion.scss +9 -16
  415. package/src/sass/components/_alert.scss +102 -0
  416. package/src/sass/components/_aura.scss +8 -3
  417. package/src/sass/components/_avatar.scss +3 -3
  418. package/src/sass/components/_back-to-top.scss +38 -0
  419. package/src/sass/components/_badges.scss +7 -13
  420. package/src/sass/components/_bar-chart.scss +41 -19
  421. package/src/sass/components/_bottom-sheet.scss +44 -16
  422. package/src/sass/components/_breadcrumb.scss +8 -1
  423. package/src/sass/components/_button-groups.scss +44 -89
  424. package/src/sass/components/_buttons.scss +156 -63
  425. package/src/sass/components/_calendar.scss +246 -0
  426. package/src/sass/components/_cards.scss +41 -68
  427. package/src/sass/components/_carousel.scss +43 -158
  428. package/src/sass/components/_cascader.scss +142 -0
  429. package/src/sass/components/_chips.scss +36 -52
  430. package/src/sass/components/_column-chart.scss +19 -12
  431. package/src/sass/components/_command-palette.scss +4 -7
  432. package/src/sass/components/_confetti.scss +0 -2
  433. package/src/sass/components/_countdown.scss +1 -1
  434. package/src/sass/components/_data-table.scss +162 -27
  435. package/src/sass/components/_datepicker.scss +57 -62
  436. package/src/sass/components/_description-list.scss +85 -0
  437. package/src/sass/components/_dialog.scss +42 -44
  438. package/src/sass/components/_docked-display.scss +1 -3
  439. package/src/sass/components/_drag-handle.scss +16 -20
  440. package/src/sass/components/_expanding-card.scss +20 -9
  441. package/src/sass/components/_fab-menu.scss +44 -32
  442. package/src/sass/components/_funnel-chart.scss +124 -0
  443. package/src/sass/components/_heatmap-chart.scss +113 -24
  444. package/src/sass/components/_icon-buttons.scss +7 -8
  445. package/src/sass/components/_icons-material-design.scss +2 -2
  446. package/src/sass/components/_image-compare.scss +108 -0
  447. package/src/sass/components/_index.scss +21 -0
  448. package/src/sass/components/_keypad.scss +182 -0
  449. package/src/sass/components/_kpi.scss +6 -11
  450. package/src/sass/components/_lightbox.scss +26 -20
  451. package/src/sass/components/_line-chart.scss +16 -2
  452. package/src/sass/components/_list.scss +59 -14
  453. package/src/sass/components/_loading-indicator.scss +1 -0
  454. package/src/sass/components/_loading-overlay.scss +105 -0
  455. package/src/sass/components/_map.scss +35 -13
  456. package/src/sass/components/_marquee.scss +3 -2
  457. package/src/sass/components/_mega-menu.scss +137 -0
  458. package/src/sass/components/_menu.scss +159 -182
  459. package/src/sass/components/_menubar.scss +59 -0
  460. package/src/sass/components/_message-scroller.scss +2 -2
  461. package/src/sass/components/_message.scss +3 -3
  462. package/src/sass/components/_mixed-chart.scss +37 -9
  463. package/src/sass/components/_modal-display.scss +21 -0
  464. package/src/sass/components/_navbar.scss +43 -65
  465. package/src/sass/components/_navigation-bar.scss +15 -77
  466. package/src/sass/components/_navigation-rail.scss +171 -121
  467. package/src/sass/components/_org-chart.scss +192 -0
  468. package/src/sass/components/_page-footer.scss +16 -13
  469. package/src/sass/components/_pagination.scss +6 -13
  470. package/src/sass/components/_panes.scss +33 -31
  471. package/src/sass/components/_particles.scss +0 -2
  472. package/src/sass/components/_pie-chart.scss +91 -11
  473. package/src/sass/components/_popover.scss +18 -5
  474. package/src/sass/components/_progress.scss +158 -35
  475. package/src/sass/components/_pull-to-refresh.scss +90 -0
  476. package/src/sass/components/_questionnaire.scss +74 -3
  477. package/src/sass/components/_radar-chart.scss +38 -10
  478. package/src/sass/components/_radial-chart.scss +113 -5
  479. package/src/sass/components/_rich-text-editor.scss +2 -2
  480. package/src/sass/components/_sankey-chart.scss +114 -0
  481. package/src/sass/components/_scatter-chart.scss +153 -0
  482. package/src/sass/components/_scrim.scss +0 -2
  483. package/src/sass/components/_scrollspy.scss +0 -2
  484. package/src/sass/components/_search.scss +26 -22
  485. package/src/sass/components/_show-more.scss +8 -0
  486. package/src/sass/components/_side-sheet.scss +23 -40
  487. package/src/sass/components/_skeleton.scss +2 -4
  488. package/src/sass/components/_snackbar.scss +27 -21
  489. package/src/sass/components/_split-button.scss +5 -5
  490. package/src/sass/components/_stat.scss +3 -8
  491. package/src/sass/components/_stepper.scss +1 -5
  492. package/src/sass/components/_swipe-actions.scss +71 -0
  493. package/src/sass/components/_tabs.scss +51 -32
  494. package/src/sass/components/_timeline.scss +12 -12
  495. package/src/sass/components/_timepicker.scss +111 -112
  496. package/src/sass/components/_toolbar.scss +35 -47
  497. package/src/sass/components/_tooltip.scss +21 -12
  498. package/src/sass/components/_tour.scss +89 -0
  499. package/src/sass/components/_transfer-list.scss +73 -0
  500. package/src/sass/components/_transitions.scss +4 -4
  501. package/src/sass/components/_tree.scss +3 -16
  502. package/src/sass/components/_treemap-chart.scss +122 -0
  503. package/src/sass/components/forms/_checkboxes.scss +140 -86
  504. package/src/sass/components/forms/_color-picker.scss +135 -0
  505. package/src/sass/components/forms/_color-swatches.scss +85 -0
  506. package/src/sass/components/forms/_drop-zone.scss +15 -9
  507. package/src/sass/components/forms/_fieldset.scss +10 -10
  508. package/src/sass/components/forms/_file-input.scss +6 -9
  509. package/src/sass/components/forms/_index.scss +3 -1
  510. package/src/sass/components/forms/_input-fields.scss +254 -90
  511. package/src/sass/components/forms/_radio-buttons.scss +40 -127
  512. package/src/sass/components/forms/_rating.scss +2 -32
  513. package/src/sass/components/forms/_select.scss +199 -23
  514. package/src/sass/components/forms/_slider.scss +140 -330
  515. package/src/sass/components/forms/_switches.scss +53 -164
  516. package/src/sass/custom.scss +10 -1
  517. package/src/sass/expressive.scss +3 -63
  518. package/src/sass/tokens/_contrast.scss +94 -0
  519. package/src/sass/tokens/_elevation.scss +16 -0
  520. package/src/sass/tokens/_index.scss +5 -0
  521. package/src/sass/tokens/_motion.scss +109 -0
  522. package/src/sass/tokens/_reference.scss +72 -141
  523. package/src/sass/tokens/_shape.scss +38 -0
  524. package/src/sass/tokens/_stacking.scss +27 -0
  525. package/src/sass/tokens/_state.scss +2 -4
  526. package/src/sass/tokens/_theme.scss +11 -2
  527. package/src/sass/tokens/_vibrant.scss +2 -5
  528. package/src/sass/utilities/_colors.scss +6 -1
  529. package/src/sass/utilities/_defer-render.scss +17 -0
  530. package/src/sass/utilities/_helpers.scss +183 -26
  531. package/src/sass/utilities/_index.scss +2 -1
  532. package/src/sass/utilities/_scroll-area.scss +0 -2
  533. package/src/sass/utilities/_spacing.scss +52 -34
  534. package/src/sass/utilities/_typescale.scss +8 -1
  535. package/src/sass/utilities/_visibility.scss +47 -76
  536. package/src/sass/utilities/_z-depth.scss +7 -4
  537. package/dist/js/chunks/chunk-3DHK5CZU.mjs.map +0 -7
  538. package/dist/js/chunks/chunk-3GVFZ4XO.mjs.map +0 -7
  539. package/dist/js/chunks/chunk-4HZMB7LI.mjs.map +0 -7
  540. package/dist/js/chunks/chunk-4KMNFIFZ.mjs +0 -270
  541. package/dist/js/chunks/chunk-4KMNFIFZ.mjs.map +0 -7
  542. package/dist/js/chunks/chunk-4TKTLGEM.mjs.map +0 -7
  543. package/dist/js/chunks/chunk-5BKHWHYY.mjs +0 -292
  544. package/dist/js/chunks/chunk-5BKHWHYY.mjs.map +0 -7
  545. package/dist/js/chunks/chunk-5HQSGDZ5.mjs.map +0 -7
  546. package/dist/js/chunks/chunk-6N2XAEFK.mjs +0 -125
  547. package/dist/js/chunks/chunk-6N2XAEFK.mjs.map +0 -7
  548. package/dist/js/chunks/chunk-A7ALMYUR.mjs.map +0 -7
  549. package/dist/js/chunks/chunk-BG6ZRB5H.mjs.map +0 -7
  550. package/dist/js/chunks/chunk-CUQPB25U.mjs +0 -55
  551. package/dist/js/chunks/chunk-CUQPB25U.mjs.map +0 -7
  552. package/dist/js/chunks/chunk-DAIU5SLG.mjs.map +0 -7
  553. package/dist/js/chunks/chunk-FS7XY3HT.mjs.map +0 -7
  554. package/dist/js/chunks/chunk-GIW4K4SE.mjs.map +0 -7
  555. package/dist/js/chunks/chunk-GUB3TNO2.mjs.map +0 -7
  556. package/dist/js/chunks/chunk-GVGT6MIU.mjs.map +0 -7
  557. package/dist/js/chunks/chunk-GZKEFWPM.mjs +0 -181
  558. package/dist/js/chunks/chunk-GZKEFWPM.mjs.map +0 -7
  559. package/dist/js/chunks/chunk-HKT2S7VM.mjs +0 -48
  560. package/dist/js/chunks/chunk-HKT2S7VM.mjs.map +0 -7
  561. package/dist/js/chunks/chunk-ILP3PDTL.mjs +0 -187
  562. package/dist/js/chunks/chunk-ILP3PDTL.mjs.map +0 -7
  563. package/dist/js/chunks/chunk-JIDMQGK6.mjs.map +0 -7
  564. package/dist/js/chunks/chunk-KBNN3QDH.mjs +0 -7
  565. package/dist/js/chunks/chunk-KBNN3QDH.mjs.map +0 -7
  566. package/dist/js/chunks/chunk-KHV6DZXX.mjs.map +0 -7
  567. package/dist/js/chunks/chunk-KY6U46SM.mjs +0 -345
  568. package/dist/js/chunks/chunk-KY6U46SM.mjs.map +0 -7
  569. package/dist/js/chunks/chunk-LRZMJZ3T.mjs +0 -291
  570. package/dist/js/chunks/chunk-LRZMJZ3T.mjs.map +0 -7
  571. package/dist/js/chunks/chunk-LTWPGFBR.mjs +0 -59
  572. package/dist/js/chunks/chunk-LTWPGFBR.mjs.map +0 -7
  573. package/dist/js/chunks/chunk-MNPROCZF.mjs +0 -328
  574. package/dist/js/chunks/chunk-MNPROCZF.mjs.map +0 -7
  575. package/dist/js/chunks/chunk-MZ6Z24BX.mjs.map +0 -7
  576. package/dist/js/chunks/chunk-NS2UMNZV.mjs.map +0 -7
  577. package/dist/js/chunks/chunk-O5XPWXIQ.mjs +0 -406
  578. package/dist/js/chunks/chunk-O5XPWXIQ.mjs.map +0 -7
  579. package/dist/js/chunks/chunk-PM655FXL.mjs.map +0 -7
  580. package/dist/js/chunks/chunk-QDAL4IYN.mjs.map +0 -7
  581. package/dist/js/chunks/chunk-QERLECVU.mjs +0 -572
  582. package/dist/js/chunks/chunk-QERLECVU.mjs.map +0 -7
  583. package/dist/js/chunks/chunk-QJABDLSD.mjs +0 -112
  584. package/dist/js/chunks/chunk-QJABDLSD.mjs.map +0 -7
  585. package/dist/js/chunks/chunk-RHRQKTTX.mjs +0 -139
  586. package/dist/js/chunks/chunk-RHRQKTTX.mjs.map +0 -7
  587. package/dist/js/chunks/chunk-S3XDFGSZ.mjs.map +0 -7
  588. package/dist/js/chunks/chunk-SPETGK25.mjs +0 -59
  589. package/dist/js/chunks/chunk-SPETGK25.mjs.map +0 -7
  590. package/dist/js/chunks/chunk-TBM3FT7G.mjs.map +0 -7
  591. package/dist/js/chunks/chunk-UEXCIMJZ.mjs.map +0 -7
  592. package/dist/js/chunks/chunk-UEZUJQ66.mjs.map +0 -7
  593. package/dist/js/chunks/chunk-VGZSAFTX.mjs +0 -173
  594. package/dist/js/chunks/chunk-VGZSAFTX.mjs.map +0 -7
  595. package/dist/js/chunks/chunk-X7OCHZVF.mjs +0 -76
  596. package/dist/js/chunks/chunk-X7OCHZVF.mjs.map +0 -7
  597. package/dist/js/chunks/chunk-YDCS5S3J.mjs.map +0 -7
  598. package/dist/js/chunks/chunk-YMSXJON6.mjs +0 -79
  599. package/dist/js/chunks/chunk-YMSXJON6.mjs.map +0 -7
  600. package/dist/js/chunks/chunk-Z2NRKI7R.mjs.map +0 -7
  601. package/dist/js/chunks/chunk-ZAS25YFD.mjs.map +0 -7
  602. package/dist/js/chunks/chunk-ZKZKNSLC.mjs +0 -1
  603. /package/dist/js/chunks/{chunk-ZKZKNSLC.mjs.map → chunk-GNRSYMVH.mjs.map} +0 -0
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../src/ts/components/showMore.ts"],
4
+ "sourcesContent": ["import { Utils, restoreAttribute } from \"../core/utils\";\nimport { Component, BaseOptions } from \"../core/component\";\n\nexport interface ShowMoreI18nOptions {\n /** The button's label while the full text shows. */\n showLess: string;\n}\n\nexport interface ShowMoreOptions extends BaseOptions {\n /** Called after the full text shows. */\n onOpen: ((el: Element) => void) | null;\n /** Called after the text is clamped again. */\n onClose: ((el: Element) => void) | null;\n /** The open label; `data-show-less` on the button overrides it. */\n i18n: Partial<ShowMoreI18nOptions>;\n}\n\nconst _defaults: ShowMoreOptions = {\n onOpen: null,\n onClose: null,\n i18n: { showLess: \"Show less\" },\n};\n\n// Inline, because the utilities layer beats any component rule and a\n// prefixed clamp such as medium:line-clamp-2 would beat .line-clamp-none.\nconst CLAMP_PROPERTIES = [\"-webkit-line-clamp\", \"line-clamp\"];\nconst BUTTON_ATTRIBUTES = [\"aria-expanded\", \"aria-controls\", \"hidden\"];\n\n/** The button's last label text, skipping aria-hidden icons. */\nfunction labelNode(button: HTMLElement): Text | null {\n const walker = button.ownerDocument.createTreeWalker(button, NodeFilter.SHOW_TEXT);\n let label: Text | null = null;\n for (let node = walker.nextNode(); node; node = walker.nextNode()) {\n if (node.textContent.trim() && !node.parentElement.closest('[aria-hidden=\"true\"]')) label = node as Text;\n }\n return label;\n}\n\n/**\n * Clamped text with a button that shows all of it. A `.show-more` holds text\n * with a `line-clamp-1`, `-2` or `-3` class and a `<button>`. The button\n * hides while the clamped text fits.\n */\nexport class ShowMore extends Component<ShowMoreOptions> {\n static key = \"Expressive_ShowMore\";\n isOpen = false;\n private readonly text: HTMLElement | null;\n private readonly button: HTMLButtonElement | null;\n // Attributes as they were before init, so destroy() can restore them.\n private _initial: Record<string, string | null> = {};\n private _initialId: string | null = null;\n private _label: Text | null = null;\n private _moreLabel = \"\";\n private _observer: ResizeObserver | null = null;\n\n constructor(el: HTMLElement, options: Partial<ShowMoreOptions>) {\n super(el, options);\n this.text = el.querySelector(\":scope > :is(.line-clamp-1, .line-clamp-2, .line-clamp-3)\");\n this.button = el.querySelector(\":scope > button\");\n if (!this.text || !this.button) return;\n this._wire();\n const { signal } = this._events;\n this.button.addEventListener(\"click\", this._toggle, { signal });\n this.button.addEventListener(\"blur\", this._fit, { signal });\n this._observer = new ResizeObserver(this._fit);\n this._observer.observe(this.text);\n // A web font that swaps in can change what fits without resizing the\n // clamped box, so the observer would not report it.\n el.ownerDocument.fonts?.ready.then(this._fit);\n }\n\n static get defaults(): ShowMoreOptions {\n return _defaults;\n }\n\n /** Shows the full text. */\n open = () => {\n if (this.isOpen || !this.button) return;\n this._show(true);\n this._notify(\"open\", this.options.onOpen, { current: () => this.isOpen });\n };\n\n /** Clamps the text again. */\n close = () => {\n if (!this.isOpen) return;\n this._show(false);\n this._notify(\"close\", this.options.onClose, { current: () => !this.isOpen });\n };\n\n destroy() {\n if (this.button) {\n this._observer.disconnect();\n if (this.isOpen) this._show(false);\n for (const name of BUTTON_ATTRIBUTES) restoreAttribute(this.button, name, this._initial[name]);\n restoreAttribute(this.text, \"id\", this._initialId);\n }\n super.destroy();\n }\n\n /** Records what destroy() restores, then points the button at the text. */\n private _wire() {\n for (const name of BUTTON_ATTRIBUTES) this._initial[name] = this.button.getAttribute(name);\n this._initialId = this.text.getAttribute(\"id\");\n if (!this.text.id) this.text.id = `show-more-${Utils.guid()}`;\n this._label = labelNode(this.button);\n if (this._label) this._moreLabel = this._label.data;\n this.button.ariaExpanded = \"false\";\n this.button.setAttribute(\"aria-controls\", this.text.id);\n }\n\n private _toggle = () => (this.isOpen ? this.close() : this.open());\n\n /**\n * Hides the button while the clamped text fits. Open text keeps it. So does\n * focus, so a resize cannot hide the button someone is on and drop focus on\n * the page. The check runs again on blur, which also hides a button whose\n * text was collapsed after it widened to fit, since collapsing it then\n * leaves the box the same size.\n */\n private _fit = () => {\n if (this.isOpen || this.button.matches(\":focus\") || ShowMore.getInstance(this.el) !== this) return;\n // Firefox rounds a fractional line height up in scrollHeight only.\n this.button.hidden = this.text.scrollHeight - this.text.clientHeight <= 1;\n };\n\n private _show(open: boolean) {\n this.isOpen = open;\n this.button.ariaExpanded = String(open);\n if (this._label) this._label.data = open ? this._lessLabel() : this._moreLabel;\n this._clamp(!open);\n }\n\n private _lessLabel() {\n return this.button.dataset.showLess || this.options.i18n.showLess;\n }\n\n private _clamp(on: boolean) {\n if (on) this._restoreClamp();\n else for (const property of CLAMP_PROPERTIES) this.text.style.setProperty(property, \"unset\");\n }\n\n private _restoreClamp() {\n for (const property of CLAMP_PROPERTIES) this.text.style.removeProperty(property);\n // Leave no empty style attribute on text that had none.\n if (!this.text.style.length) this.text.removeAttribute(\"style\");\n }\n}\n"],
5
+ "mappings": "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",
6
+ "names": []
7
+ }
@@ -0,0 +1,209 @@
1
+ import {
2
+ Component
3
+ } from "./chunk-CMGXGYUC.mjs";
4
+ import {
5
+ Utils
6
+ } from "./chunk-ZVLOUDIJ.mjs";
7
+
8
+ // src/ts/components/swipeActions.ts
9
+ var _defaults = {
10
+ onToggle: null
11
+ };
12
+ var SLOP = 4;
13
+ var FLICK_VELOCITY = 0.5;
14
+ var FLICK_TIMEOUT = 100;
15
+ var flick = (swipe) => Date.now() - swipe.lastT < FLICK_TIMEOUT ? swipe.velocity * swipe.sign : 0;
16
+ var opensOnRelease = (swipe) => {
17
+ const velocity = flick(swipe);
18
+ if (Math.abs(velocity) > FLICK_VELOCITY) return velocity > 0;
19
+ return swipe.reveal > swipe.width / 2;
20
+ };
21
+ var SwipeActions = class extends Component {
22
+ constructor(el, options) {
23
+ super(el, options);
24
+ /** The open row, if any. */
25
+ this._open = null;
26
+ /** The touch in progress, while it may still become a swipe or is one. */
27
+ this._swipe = null;
28
+ this._onStart = (event) => {
29
+ if (event.touches.length !== 1) {
30
+ this._cancel();
31
+ return;
32
+ }
33
+ const row = this._rowFor(Utils.eventTarget(event));
34
+ if (!row) return;
35
+ const { clientX: x, clientY: y } = event.touches[0];
36
+ const width = this._width(row);
37
+ const base = row === this._open ? width : 0;
38
+ this._swipe = { row, x, y, sign: this._sign(row), width, base, reveal: base, swiping: false, last: x, lastT: Date.now(), velocity: 0 };
39
+ };
40
+ this._onMove = (event) => {
41
+ const swipe = this._swipe;
42
+ if (!swipe) return;
43
+ const { clientX, clientY } = event.touches[0];
44
+ if (swipe.swiping || this._decide(swipe, clientX - swipe.x, clientY - swipe.y)) this._drag(event, swipe, clientX);
45
+ };
46
+ this._onEnd = () => {
47
+ const swipe = this._swipe;
48
+ this._swipe = null;
49
+ if (!swipe?.swiping) return;
50
+ swipe.row.classList.remove("swiping");
51
+ this._settle(swipe.row, opensOnRelease(swipe));
52
+ };
53
+ this._onCancel = () => this._cancel();
54
+ this._onClick = (event) => {
55
+ const target = Utils.eventTarget(event);
56
+ if (target.closest(".swipe-actions button")) this._closeFrom(target.closest("li"));
57
+ else if (target.closest("[data-swipe-toggle]")) this._toggle(this._rowFor(target));
58
+ };
59
+ this._onKeydown = (event) => {
60
+ if (event.key !== "Escape") return;
61
+ this._closeFrom(this._rowFor(Utils.eventTarget(event)));
62
+ };
63
+ /** Focus on an action opens its row; focus anywhere outside the open row closes it. */
64
+ this._onFocusin = (event) => {
65
+ const target = Utils.eventTarget(event);
66
+ if (target?.closest(".swipe-actions")) this.open(this._rowFor(target));
67
+ else this._closeOutside(target);
68
+ };
69
+ /** A tap or click outside the open row closes it. */
70
+ this._onPointerdown = (event) => this._closeOutside(Utils.eventTarget(event));
71
+ this._rows().forEach((row) => this._toggleFor(row)?.setAttribute("aria-expanded", "false"));
72
+ const signal = this._events.signal;
73
+ const doc = el.ownerDocument;
74
+ el.addEventListener("click", this._onClick, { signal });
75
+ el.addEventListener("keydown", this._onKeydown, { signal });
76
+ el.addEventListener("touchstart", this._onStart, { passive: true, signal });
77
+ el.addEventListener("touchmove", this._onMove, { passive: false, signal });
78
+ el.addEventListener("touchcancel", this._onCancel, { signal });
79
+ el.addEventListener("touchend", this._onEnd, { signal });
80
+ doc.addEventListener("focusin", this._onFocusin, { signal });
81
+ doc.addEventListener("pointerdown", this._onPointerdown, { signal });
82
+ }
83
+ static get defaults() {
84
+ return _defaults;
85
+ }
86
+ /** Opens a row of this list, closing the one that was open. */
87
+ open(row) {
88
+ if (!this._isRow(row)) return;
89
+ this._place(row, this._width(row));
90
+ if (this._open === row) return;
91
+ this.close();
92
+ this._open = row;
93
+ row.classList.add("swipe-open");
94
+ this._toggleFor(row)?.setAttribute("aria-expanded", "true");
95
+ this._fire(row, true);
96
+ }
97
+ /** Closes the open row, if there is one. */
98
+ close() {
99
+ const row = this._open;
100
+ if (!row) return;
101
+ this._open = null;
102
+ this._shut(row);
103
+ this._fire(row, false);
104
+ }
105
+ destroy() {
106
+ const rows = [this._swipe?.row, this._open];
107
+ this._swipe = null;
108
+ this._open = null;
109
+ rows.forEach((row) => row && this._shut(row));
110
+ this._rows().forEach((row) => this._toggleFor(row)?.removeAttribute("aria-expanded"));
111
+ super.destroy();
112
+ }
113
+ _rows() {
114
+ return [...this.el.querySelectorAll(":scope > li:has(> .swipe-actions)")];
115
+ }
116
+ /** Whether `row` is a row of this list with actions. */
117
+ _isRow(row) {
118
+ return !!row && row.parentElement === this.el && !!row.querySelector(":scope > .swipe-actions");
119
+ }
120
+ _rowFor(target) {
121
+ const row = target?.closest("li") ?? null;
122
+ return this._isRow(row) ? row : null;
123
+ }
124
+ _toggleFor(row) {
125
+ return row.querySelector("[data-swipe-toggle]");
126
+ }
127
+ _width(row) {
128
+ return row.querySelector(":scope > .swipe-actions").offsetWidth;
129
+ }
130
+ /** -1 when rows open toward the left, 1 when they open toward the right. */
131
+ _sign(row) {
132
+ return getComputedStyle(row).direction === "rtl" ? 1 : -1;
133
+ }
134
+ /** Slides a row `reveal` pixels open. */
135
+ _place(row, reveal) {
136
+ row.style.setProperty("--swipe-offset", `${reveal * this._sign(row)}px`);
137
+ }
138
+ /** Puts a row back closed, without telling anyone. */
139
+ _shut(row) {
140
+ row.classList.remove("swipe-open", "swiping");
141
+ row.style.removeProperty("--swipe-offset");
142
+ this._toggleFor(row)?.setAttribute("aria-expanded", "false");
143
+ }
144
+ _fire(row, open) {
145
+ const detail = { row, open };
146
+ this._notify("swipetoggle", this.options.onToggle, { args: [detail], detail });
147
+ }
148
+ /**
149
+ * Swipes once the finger moves sideways, or leaves the touch to scrolling
150
+ * when it moves up or down first. Returns whether it is now a swipe.
151
+ */
152
+ _decide(swipe, dx, dy) {
153
+ if (Math.max(Math.abs(dx), Math.abs(dy)) <= SLOP) return false;
154
+ swipe.swiping = Math.abs(dx) > Math.abs(dy);
155
+ if (!swipe.swiping) this._swipe = null;
156
+ return swipe.swiping;
157
+ }
158
+ /** Slides the row with the finger, no farther than its actions reach. */
159
+ _drag(event, swipe, x) {
160
+ if (event.cancelable) event.preventDefault();
161
+ const now = Date.now();
162
+ if (x !== swipe.last) {
163
+ swipe.velocity = (x - swipe.last) / Math.max(1, now - swipe.lastT);
164
+ swipe.last = x;
165
+ swipe.lastT = now;
166
+ }
167
+ swipe.reveal = Math.min(Math.max(swipe.base + (x - swipe.x) * swipe.sign, 0), swipe.width);
168
+ swipe.row.classList.add("swiping");
169
+ this._place(swipe.row, swipe.reveal);
170
+ }
171
+ /** Leaves a released row open or closed, putting its offset where that state has it. */
172
+ _settle(row, open) {
173
+ if (open) this.open(row);
174
+ else if (row === this._open) this.close();
175
+ else this._shut(row);
176
+ }
177
+ /** Ends a swipe without deciding anything: the row goes back to how it was. */
178
+ _cancel() {
179
+ const swipe = this._swipe;
180
+ this._swipe = null;
181
+ if (!swipe?.swiping) return;
182
+ swipe.row.classList.remove("swiping");
183
+ this._settle(swipe.row, swipe.row === this._open);
184
+ }
185
+ /** open() ignores anything that is not a row of this list. */
186
+ _toggle(row) {
187
+ if (row === this._open) this.close();
188
+ else this.open(row);
189
+ }
190
+ /** Closes the open row from inside it, moving focus off an action so it does not stay on a hidden button. */
191
+ _closeFrom(row) {
192
+ if (!row || row !== this._open) return;
193
+ const focused = row.querySelector(":scope > .swipe-actions").contains(row.ownerDocument.activeElement);
194
+ this.close();
195
+ if (focused) this._focusToggle(row);
196
+ }
197
+ _focusToggle(row) {
198
+ this._toggleFor(row)?.focus();
199
+ }
200
+ _closeOutside(target) {
201
+ if (this._open && !this._open.contains(target)) this.close();
202
+ }
203
+ };
204
+ SwipeActions.key = "Expressive_SwipeActions";
205
+
206
+ export {
207
+ SwipeActions
208
+ };
209
+ //# sourceMappingURL=chunk-Y6H2X7ZC.mjs.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../src/ts/components/swipeActions.ts"],
4
+ "sourcesContent": ["import { Component, BaseOptions } from '../core/component';\nimport { Utils } from '../core/utils';\n\n/** What `expressive:swipetoggle` carries, and what `onToggle` receives. */\nexport interface SwipeActionsDetail {\n /** The row that opened or closed. */\n row: HTMLElement;\n /** Whether it is now open. */\n open: boolean;\n}\n\nexport interface SwipeActionsOptions extends BaseOptions {\n /**\n * Called when a row opens or closes, with the event's detail.\n * @default null\n */\n onToggle: ((detail: SwipeActionsDetail) => void) | null;\n}\n\nconst _defaults: SwipeActionsOptions = {\n onToggle: null\n};\n\n/** Past this the finger was moving, not resting. Hand jitter, in pixels. */\nconst SLOP = 4;\n/** Past this a flick opens or closes whatever the distance, in pixels per millisecond. The sheets use the same. */\nconst FLICK_VELOCITY = 0.5;\n/** Ignore a flick after the finger has rested for this many milliseconds. */\nconst FLICK_TIMEOUT = 100;\n\n/** One touch on a row, from the finger going down until it lifts. */\ninterface Swipe {\n row: HTMLElement;\n x: number;\n y: number;\n /** -1 when the row opens toward the left, 1 toward the right (right-to-left pages). */\n sign: 1 | -1;\n /** How far the actions reach, which is as far as the row slides. */\n width: number;\n /** How far open the row was when the finger went down, 0 to `width`. */\n base: number;\n /** How far open it is now. */\n reveal: number;\n /** Set once the finger moves sideways first; until then the touch may still scroll. */\n swiping: boolean;\n last: number;\n lastT: number;\n velocity: number;\n}\n\n/** The pointer's velocity toward opening at release, or 0 once it has rested past the flick window. */\nconst flick = (swipe: Swipe) => (Date.now() - swipe.lastT < FLICK_TIMEOUT ? swipe.velocity * swipe.sign : 0);\n\n/** Whether a released swipe leaves the row open: a flick decides, else whether it is past halfway. */\nconst opensOnRelease = (swipe: Swipe) => {\n const velocity = flick(swipe);\n if (Math.abs(velocity) > FLICK_VELOCITY) return velocity > 0;\n return swipe.reveal > swipe.width / 2;\n};\n\n/**\n * Swipe actions. In a `.list.swipeable`, a touch swipe toward a row's inline\n * start slides the row and reveals its `.swipe-actions` group at the inline\n * end. A swipe only reveals; nothing runs until a person presses an action.\n * The row's `[data-swipe-toggle]` button opens and closes it without a\n * swipe, and focus on an action opens its row, so keyboard and single-pointer\n * users reach the same actions. One row in the list is open at a time.\n *\n * Touch events rather than pointer events, as in PullToRefresh: a pointer\n * drag the browser takes for a pan ends in `pointercancel`. A mouse never\n * fires touch events, so it never swipes.\n */\nexport class SwipeActions extends Component<SwipeActionsOptions> {\n static key = 'Expressive_SwipeActions';\n /** The open row, if any. */\n private _open: HTMLElement | null = null;\n /** The touch in progress, while it may still become a swipe or is one. */\n private _swipe: Swipe | null = null;\n\n constructor(el: HTMLElement, options: Partial<SwipeActionsOptions>) {\n super(el, options);\n this._rows().forEach((row) => this._toggleFor(row)?.setAttribute('aria-expanded', 'false'));\n const signal = this._events.signal;\n const doc = el.ownerDocument;\n el.addEventListener('click', this._onClick, { signal });\n el.addEventListener('keydown', this._onKeydown, { signal });\n el.addEventListener('touchstart', this._onStart, { passive: true, signal });\n // Not passive: a swipe cancels the move so nothing scrolls sideways under it.\n el.addEventListener('touchmove', this._onMove, { passive: false, signal });\n el.addEventListener('touchcancel', this._onCancel, { signal });\n el.addEventListener('touchend', this._onEnd, { signal });\n doc.addEventListener('focusin', this._onFocusin, { signal });\n doc.addEventListener('pointerdown', this._onPointerdown, { signal });\n }\n\n static get defaults(): SwipeActionsOptions {\n return _defaults;\n }\n\n /** Opens a row of this list, closing the one that was open. */\n open(row: HTMLElement) {\n if (!this._isRow(row)) return;\n // Also puts back a row a swipe left part-way open.\n this._place(row, this._width(row));\n if (this._open === row) return;\n this.close();\n this._open = row;\n row.classList.add('swipe-open');\n this._toggleFor(row)?.setAttribute('aria-expanded', 'true');\n this._fire(row, true);\n }\n\n /** Closes the open row, if there is one. */\n close() {\n const row = this._open;\n if (!row) return;\n this._open = null;\n this._shut(row);\n this._fire(row, false);\n }\n\n destroy() {\n // A row part-way through a swipe goes back too, not only the open one.\n const rows = [this._swipe?.row, this._open];\n this._swipe = null;\n this._open = null;\n rows.forEach((row) => row && this._shut(row));\n this._rows().forEach((row) => this._toggleFor(row)?.removeAttribute('aria-expanded'));\n super.destroy();\n }\n\n private _rows() {\n return [...this.el.querySelectorAll<HTMLElement>(':scope > li:has(> .swipe-actions)')];\n }\n\n /** Whether `row` is a row of this list with actions. */\n private _isRow(row: Element | null): row is HTMLElement {\n return !!row && row.parentElement === this.el && !!row.querySelector(':scope > .swipe-actions');\n }\n\n private _rowFor(target: Element | null) {\n const row = target?.closest('li') ?? null;\n return this._isRow(row) ? row : null;\n }\n\n private _toggleFor(row: HTMLElement) {\n return row.querySelector<HTMLElement>('[data-swipe-toggle]');\n }\n\n private _width(row: HTMLElement) {\n return row.querySelector<HTMLElement>(':scope > .swipe-actions')!.offsetWidth;\n }\n\n /** -1 when rows open toward the left, 1 when they open toward the right. */\n private _sign(row: HTMLElement): 1 | -1 {\n return getComputedStyle(row).direction === 'rtl' ? 1 : -1;\n }\n\n /** Slides a row `reveal` pixels open. */\n private _place(row: HTMLElement, reveal: number) {\n row.style.setProperty('--swipe-offset', `${reveal * this._sign(row)}px`);\n }\n\n /** Puts a row back closed, without telling anyone. */\n private _shut(row: HTMLElement) {\n row.classList.remove('swipe-open', 'swiping');\n row.style.removeProperty('--swipe-offset');\n this._toggleFor(row)?.setAttribute('aria-expanded', 'false');\n }\n\n private _fire(row: HTMLElement, open: boolean) {\n const detail: SwipeActionsDetail = { row, open };\n this._notify('swipetoggle', this.options.onToggle, { args: [detail], detail });\n }\n\n private _onStart = (event: TouchEvent) => {\n // A second finger is a pinch or a mistake, not a swipe.\n if (event.touches.length !== 1) {\n this._cancel();\n return;\n }\n const row = this._rowFor(Utils.eventTarget(event));\n if (!row) return;\n const { clientX: x, clientY: y } = event.touches[0];\n const width = this._width(row);\n const base = row === this._open ? width : 0;\n this._swipe = { row, x, y, sign: this._sign(row), width, base, reveal: base, swiping: false, last: x, lastT: Date.now(), velocity: 0 };\n };\n\n private _onMove = (event: TouchEvent) => {\n const swipe = this._swipe;\n if (!swipe) return;\n const { clientX, clientY } = event.touches[0];\n if (swipe.swiping || this._decide(swipe, clientX - swipe.x, clientY - swipe.y)) this._drag(event, swipe, clientX);\n };\n\n /**\n * Swipes once the finger moves sideways, or leaves the touch to scrolling\n * when it moves up or down first. Returns whether it is now a swipe.\n */\n private _decide(swipe: Swipe, dx: number, dy: number) {\n if (Math.max(Math.abs(dx), Math.abs(dy)) <= SLOP) return false;\n swipe.swiping = Math.abs(dx) > Math.abs(dy);\n if (!swipe.swiping) this._swipe = null;\n return swipe.swiping;\n }\n\n /** Slides the row with the finger, no farther than its actions reach. */\n private _drag(event: TouchEvent, swipe: Swipe, x: number) {\n if (event.cancelable) event.preventDefault();\n const now = Date.now();\n if (x !== swipe.last) {\n swipe.velocity = (x - swipe.last) / Math.max(1, now - swipe.lastT);\n swipe.last = x;\n swipe.lastT = now;\n }\n swipe.reveal = Math.min(Math.max(swipe.base + (x - swipe.x) * swipe.sign, 0), swipe.width);\n swipe.row.classList.add('swiping');\n this._place(swipe.row, swipe.reveal);\n }\n\n private _onEnd = () => {\n const swipe = this._swipe;\n this._swipe = null;\n if (!swipe?.swiping) return;\n swipe.row.classList.remove('swiping');\n this._settle(swipe.row, opensOnRelease(swipe));\n };\n\n /** Leaves a released row open or closed, putting its offset where that state has it. */\n private _settle(row: HTMLElement, open: boolean) {\n if (open) this.open(row);\n else if (row === this._open) this.close();\n else this._shut(row);\n }\n\n private _onCancel = () => this._cancel();\n\n /** Ends a swipe without deciding anything: the row goes back to how it was. */\n private _cancel() {\n const swipe = this._swipe;\n this._swipe = null;\n if (!swipe?.swiping) return;\n swipe.row.classList.remove('swiping');\n this._settle(swipe.row, swipe.row === this._open);\n }\n\n private _onClick = (event: MouseEvent) => {\n const target = Utils.eventTarget(event)!;\n // Not _rowFor(): an action may already have removed its row from the list.\n if (target.closest('.swipe-actions button')) this._closeFrom(target.closest('li'));\n else if (target.closest('[data-swipe-toggle]')) this._toggle(this._rowFor(target));\n };\n\n /** open() ignores anything that is not a row of this list. */\n private _toggle(row: HTMLElement | null) {\n if (row === this._open) this.close();\n else this.open(row as HTMLElement);\n }\n\n /** Closes the open row from inside it, moving focus off an action so it does not stay on a hidden button. */\n private _closeFrom(row: HTMLElement | null) {\n if (!row || row !== this._open) return;\n // A row an action removed holds no focus, so it is left alone.\n const focused = row.querySelector(':scope > .swipe-actions')!.contains(row.ownerDocument.activeElement);\n this.close();\n if (focused) this._focusToggle(row);\n }\n\n private _focusToggle(row: HTMLElement) {\n this._toggleFor(row)?.focus();\n }\n\n private _onKeydown = (event: KeyboardEvent) => {\n if (event.key !== 'Escape') return;\n this._closeFrom(this._rowFor(Utils.eventTarget(event)));\n };\n\n /** Focus on an action opens its row; focus anywhere outside the open row closes it. */\n private _onFocusin = (event: FocusEvent) => {\n const target = Utils.eventTarget(event);\n // open() ignores anything that is not a row of this list.\n if (target?.closest('.swipe-actions')) this.open(this._rowFor(target)!);\n else this._closeOutside(target);\n };\n\n /** A tap or click outside the open row closes it. */\n private _onPointerdown = (event: PointerEvent) => this._closeOutside(Utils.eventTarget(event));\n\n private _closeOutside(target: Element | null) {\n if (this._open && !this._open.contains(target)) this.close();\n }\n}\n"],
5
+ "mappings": "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",
6
+ "names": []
7
+ }
@@ -0,0 +1,129 @@
1
+ import {
2
+ Component
3
+ } from "./chunk-CMGXGYUC.mjs";
4
+ import {
5
+ Utils
6
+ } from "./chunk-ZVLOUDIJ.mjs";
7
+
8
+ // src/ts/components/currencyInput.ts
9
+ var _defaults = Object.freeze({ i18n: Object.freeze({ invalid: "Enter an amount." }) });
10
+ var LATIN = "9876543210";
11
+ function split(clean, digits) {
12
+ const mark = Math.max(clean.lastIndexOf("."), clean.lastIndexOf(","));
13
+ const fraction = clean.slice(mark + 1);
14
+ return mark >= 0 && fraction.length <= digits ? [clean.slice(0, mark), fraction] : [clean, ""];
15
+ }
16
+ function parse(text, digits) {
17
+ const clean = text.replace(/[^\d.,]/g, "").replace(/[.,]+$/, "");
18
+ if (!/\d/.test(clean)) return null;
19
+ const [whole, fraction] = split(clean, digits);
20
+ const sign = /^\D*[-−]/.test(text) ? -1 : 1;
21
+ return sign * Number(`${whole.replace(/[.,]/g, "")}.${fraction}`);
22
+ }
23
+ var CurrencyInput = class extends Component {
24
+ constructor(el, options) {
25
+ super(el, options);
26
+ this._format = () => {
27
+ this._show(this.value);
28
+ };
29
+ /**
30
+ * Enter fires change while the field keeps focus. Formatting then would
31
+ * put the next keystroke after the currency sign, so the field waits for
32
+ * blur.
33
+ */
34
+ this._onChange = () => {
35
+ if (!this.el.matches(":focus")) this._format();
36
+ };
37
+ /** Shows the amount as a plain number to edit, with the caret at the end. */
38
+ this._onFocus = () => {
39
+ const amount = this.value;
40
+ if (amount === null) return;
41
+ const text = this._edit.format(amount);
42
+ this.el.value = text;
43
+ this.el.setSelectionRange(text.length, text.length);
44
+ };
45
+ /** Marks text that holds no amount invalid, and clears the mark once it holds one or is empty. */
46
+ this._validate = () => {
47
+ const { el } = this;
48
+ const invalid = el.value.trim() !== "" && this.value === null;
49
+ el.setCustomValidity(invalid ? this.options.i18n.invalid : "");
50
+ };
51
+ this._onReset = (e) => {
52
+ if (e.target === this.el.form) setTimeout(this._afterReset);
53
+ };
54
+ this._afterReset = () => {
55
+ if (!this._events.signal.aborted) this._start();
56
+ };
57
+ /** Puts the plain number in the form data in place of the formatted text. */
58
+ this._onFormData = (e) => {
59
+ if (!this._submitsTo(e.target)) return;
60
+ e.formData.set(this.el.name, String(this.value ?? this.el.value));
61
+ };
62
+ const locale = Utils.locale(el);
63
+ try {
64
+ this._display = new Intl.NumberFormat(locale, { style: "currency", currency: el.dataset.currency });
65
+ } catch {
66
+ return;
67
+ }
68
+ this._digits = this._display.resolvedOptions().maximumFractionDigits;
69
+ this._edit = new Intl.NumberFormat(locale, { useGrouping: false, maximumFractionDigits: this._digits });
70
+ this._plain = new Intl.NumberFormat("en", { useGrouping: false, maximumFractionDigits: this._digits });
71
+ this._native = new Intl.NumberFormat(locale, { useGrouping: false }).format(9876543210);
72
+ this._decimal = new Intl.NumberFormat(locale).formatToParts(0.5).find((part) => part.type === "decimal").value;
73
+ const signal = this._events.signal;
74
+ el.addEventListener("change", this._onChange, { capture: true, signal });
75
+ el.addEventListener("blur", this._format, { signal });
76
+ el.addEventListener("focus", this._onFocus, { signal });
77
+ el.addEventListener("input", this._validate, { signal });
78
+ const root = el.getRootNode();
79
+ const scope = "host" in root ? root : el.ownerDocument;
80
+ scope.addEventListener("formdata", this._onFormData, { capture: true, signal });
81
+ scope.addEventListener("reset", this._onReset, { capture: true, signal });
82
+ this._start();
83
+ }
84
+ static get defaults() {
85
+ return _defaults;
86
+ }
87
+ /** The amount the field holds, rounded as it shows, or null when it is empty or holds no digit. */
88
+ get value() {
89
+ return this._round(this._read(this.el.value));
90
+ }
91
+ /** Reads text in the locale's digits, or full-width ones from an IME, as an amount. */
92
+ _read(text) {
93
+ const latin = Array.from(text.normalize("NFKC"), (ch) => ch === this._decimal ? "." : LATIN[this._native.indexOf(ch)] ?? ch);
94
+ return parse(latin.join(""), this._digits);
95
+ }
96
+ _round(amount) {
97
+ return amount === null ? null : Number(this._plain.format(amount));
98
+ }
99
+ /**
100
+ * Formats the starting value without events. It reads as a plain number
101
+ * first, the form the field submits, so a saved `1.234` stays 1.234.
102
+ */
103
+ _start() {
104
+ const text = this.el.value;
105
+ const number = Number(text);
106
+ this._show(this._round(text.trim() && Number.isFinite(number) ? number : this._read(text)));
107
+ }
108
+ /** Shows `amount` in the locale and currency, leaving text that reads as no amount as it is. */
109
+ _show(amount) {
110
+ if (amount !== null) this.el.value = this._display.format(amount);
111
+ this._validate();
112
+ }
113
+ /** Whether the field has an entry in `form`'s data. */
114
+ _submitsTo(form) {
115
+ const { el } = this;
116
+ return form === el.form && el.name !== "" && !el.matches(":disabled");
117
+ }
118
+ /** Stops formatting and clears the validity message, leaving the text as it is. */
119
+ destroy() {
120
+ super.destroy();
121
+ this.el.setCustomValidity("");
122
+ }
123
+ };
124
+ CurrencyInput.key = "Expressive_CurrencyInput";
125
+
126
+ export {
127
+ CurrencyInput
128
+ };
129
+ //# sourceMappingURL=chunk-Y6TLRA3U.mjs.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../src/ts/components/currencyInput.ts"],
4
+ "sourcesContent": ["import { Component, BaseOptions } from '../core/component';\nimport { Utils } from '../core/utils';\n\nexport interface CurrencyInputOptions extends BaseOptions {\n /** `invalid` is the validity message for text that holds no amount. */\n i18n: Partial<{ invalid: string }>;\n}\n\nconst _defaults: CurrencyInputOptions = Object.freeze({ i18n: Object.freeze({ invalid: 'Enter an amount.' }) });\n\n/** Latin digits in the order `_native` holds them, to map a locale's own digits back. */\nconst LATIN = '9876543210';\n\n/**\n * Splits digits and separators into whole and fraction digits. The last `.`\n * or `,` is the decimal mark when no more than `digits` digits follow it, so\n * `1.234,5` and `1,234.50` both split at the end; any other separator groups.\n */\nfunction split(clean: string, digits: number): [string, string] {\n const mark = Math.max(clean.lastIndexOf('.'), clean.lastIndexOf(','));\n const fraction = clean.slice(mark + 1);\n return mark >= 0 && fraction.length <= digits ? [clean.slice(0, mark), fraction] : [clean, ''];\n}\n\n/**\n * Reads text in Latin digits as an amount, or null when it holds no digit.\n * Signs, spaces and letters are ignored, and a `-` or `\u2212` before the first\n * digit makes the amount negative. A separator after the last digit is\n * dropped, since it belongs to a symbol such as `kr.`.\n */\nfunction parse(text: string, digits: number): number | null {\n const clean = text.replace(/[^\\d.,]/g, '').replace(/[.,]+$/, '');\n if (!/\\d/.test(clean)) return null;\n const [whole, fraction] = split(clean, digits);\n const sign = /^\\D*[-\u2212]/.test(text) ? -1 : 1;\n return sign * Number(`${whole.replace(/[.,]/g, '')}.${fraction}`);\n}\n\n/**\n * Currency input. Shows a text field's amount in the page's locale and the\n * currency its `data-currency` attribute names once the field loses focus,\n * shows the plain number while it has focus, and puts the plain number in the\n * form data.\n */\nexport class CurrencyInput extends Component<CurrencyInputOptions> {\n declare el: HTMLInputElement;\n static key = 'Expressive_CurrencyInput';\n private _display: Intl.NumberFormat;\n /** Writes an amount for editing: the locale's digits and mark, no grouping or sign. */\n private _edit: Intl.NumberFormat;\n /** Writes an amount as the form submits it: Latin digits, a `.` mark, no grouping. */\n private _plain: Intl.NumberFormat;\n private _digits: number;\n /** The locale's digits for 9876543210, and its decimal mark. */\n private _native: string;\n private _decimal: string;\n\n constructor(el: HTMLInputElement, options: Partial<CurrencyInputOptions>) {\n super(el, options);\n const locale = Utils.locale(el);\n try {\n this._display = new Intl.NumberFormat(locale, { style: 'currency', currency: el.dataset.currency });\n } catch {\n // A malformed code leaves the field a plain text input.\n return;\n }\n this._digits = this._display.resolvedOptions().maximumFractionDigits;\n this._edit = new Intl.NumberFormat(locale, { useGrouping: false, maximumFractionDigits: this._digits });\n this._plain = new Intl.NumberFormat('en', { useGrouping: false, maximumFractionDigits: this._digits });\n this._native = new Intl.NumberFormat(locale, { useGrouping: false }).format(9876543210);\n this._decimal = new Intl.NumberFormat(locale).formatToParts(0.5).find((part) => part.type === 'decimal').value;\n const signal = this._events.signal;\n // Capture, so a page's change listener on the field reads the formatted\n // text. Blur covers a visit that changed nothing, which fires no change.\n el.addEventListener('change', this._onChange, { capture: true, signal });\n el.addEventListener('blur', this._format, { signal });\n el.addEventListener('focus', this._onFocus, { signal });\n el.addEventListener('input', this._validate, { signal });\n // Neither formdata nor reset leaves a shadow root, so a field in one\n // listens there. Otherwise the document, so the listener follows the\n // field into another form.\n const root = el.getRootNode() as Document | ShadowRoot;\n const scope = 'host' in root ? root : el.ownerDocument;\n scope.addEventListener('formdata', this._onFormData, { capture: true, signal });\n // The form resets its fields after the reset event, so the field formats\n // the restored value a task later.\n scope.addEventListener('reset', this._onReset, { capture: true, signal });\n this._start();\n }\n\n static get defaults(): CurrencyInputOptions {\n return _defaults;\n }\n\n /** The amount the field holds, rounded as it shows, or null when it is empty or holds no digit. */\n get value(): number | null {\n return this._round(this._read(this.el.value));\n }\n\n /** Reads text in the locale's digits, or full-width ones from an IME, as an amount. */\n private _read(text: string) {\n const latin = Array.from(text.normalize('NFKC'), (ch) => (ch === this._decimal ? '.' : (LATIN[this._native.indexOf(ch)] ?? ch)));\n return parse(latin.join(''), this._digits);\n }\n\n private _round(amount: number | null) {\n return amount === null ? null : Number(this._plain.format(amount));\n }\n\n /**\n * Formats the starting value without events. It reads as a plain number\n * first, the form the field submits, so a saved `1.234` stays 1.234.\n */\n private _start() {\n const text = this.el.value;\n const number = Number(text);\n this._show(this._round(text.trim() && Number.isFinite(number) ? number : this._read(text)));\n }\n\n private _format = () => {\n this._show(this.value);\n };\n\n /**\n * Enter fires change while the field keeps focus. Formatting then would\n * put the next keystroke after the currency sign, so the field waits for\n * blur.\n */\n private _onChange = () => {\n if (!this.el.matches(':focus')) this._format();\n };\n\n /** Shows `amount` in the locale and currency, leaving text that reads as no amount as it is. */\n private _show(amount: number | null) {\n if (amount !== null) this.el.value = this._display.format(amount);\n this._validate();\n }\n\n /** Shows the amount as a plain number to edit, with the caret at the end. */\n private _onFocus = () => {\n const amount = this.value;\n if (amount === null) return;\n const text = this._edit.format(amount);\n this.el.value = text;\n this.el.setSelectionRange(text.length, text.length);\n };\n\n /** Marks text that holds no amount invalid, and clears the mark once it holds one or is empty. */\n private _validate = () => {\n const { el } = this;\n const invalid = el.value.trim() !== '' && this.value === null;\n el.setCustomValidity(invalid ? this.options.i18n.invalid : '');\n };\n\n private _onReset = (e: Event) => {\n if (e.target === this.el.form) setTimeout(this._afterReset);\n };\n\n private _afterReset = () => {\n if (!this._events.signal.aborted) this._start();\n };\n\n /** Puts the plain number in the form data in place of the formatted text. */\n private _onFormData = (e: FormDataEvent) => {\n if (!this._submitsTo(e.target)) return;\n // ponytail: set() collapses fields that share this name into one entry; a\n // per-field swap if a form ever repeats a currency field's name.\n e.formData.set(this.el.name, String(this.value ?? this.el.value));\n };\n\n /** Whether the field has an entry in `form`'s data. */\n private _submitsTo(form: EventTarget) {\n const { el } = this;\n return form === el.form && el.name !== '' && !el.matches(':disabled');\n }\n\n /** Stops formatting and clears the validity message, leaving the text as it is. */\n destroy(): void {\n super.destroy();\n this.el.setCustomValidity('');\n }\n}\n"],
5
+ "mappings": "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",
6
+ "names": []
7
+ }
@@ -0,0 +1,190 @@
1
+ import {
2
+ Component
3
+ } from "./chunk-CMGXGYUC.mjs";
4
+
5
+ // src/ts/components/navigationRail.ts
6
+ var _defaults = {
7
+ onOpenStart: null,
8
+ onOpenEnd: null,
9
+ onCloseStart: null,
10
+ onCloseEnd: null
11
+ };
12
+ var COMPACT = "(width < 600px)";
13
+ var HOVER_DELAY = 200;
14
+ function deepActiveElement(root) {
15
+ let active = root.activeElement;
16
+ while (active?.shadowRoot?.activeElement) active = active.shadowRoot.activeElement;
17
+ return active;
18
+ }
19
+ var NavigationRail = class extends Component {
20
+ constructor(el, options) {
21
+ super(el, options);
22
+ this._hoverPanel = null;
23
+ /**
24
+ * Expands the rail. On compact windows the overlay (scrim) is CSS.
25
+ */
26
+ this.expand = () => {
27
+ if (this.isExpanded) return;
28
+ if (!this._notify("open", this.options.onOpenStart, { current: () => !this.isExpanded })) return;
29
+ this.isExpanded = true;
30
+ this.el.classList.add("expanded");
31
+ this._sync();
32
+ this._notify("opened", this.options.onOpenEnd, { current: () => this.isExpanded });
33
+ };
34
+ /**
35
+ * Collapses the rail.
36
+ */
37
+ this.collapse = () => {
38
+ if (!this.isExpanded) return;
39
+ if (!this._notify("close", this.options.onCloseStart, { current: () => this.isExpanded })) return;
40
+ this.isExpanded = false;
41
+ this.el.classList.remove("expanded");
42
+ this._sync();
43
+ this._notify("closed", this.options.onCloseEnd, { current: () => !this.isExpanded });
44
+ };
45
+ /**
46
+ * Toggles expanded / collapsed.
47
+ */
48
+ this.toggle = () => {
49
+ if (this.isExpanded) this.collapse();
50
+ else this.expand();
51
+ };
52
+ this._onPointerOver = (e) => {
53
+ if (e.pointerType !== "mouse") return;
54
+ clearTimeout(this._hoverTimer);
55
+ const target = e.target;
56
+ const panel = this._panelAt(target);
57
+ if (!panel) this._hoverClose(target);
58
+ else if (panel !== this._hoverPanel) {
59
+ this._hoverTimer = setTimeout(() => this._hoverOpen(target), HOVER_DELAY);
60
+ }
61
+ };
62
+ // The panel is a descendant, so moving onto it does not leave the rail.
63
+ this._onPointerLeave = (e) => {
64
+ if (e.pointerType !== "mouse") return;
65
+ clearTimeout(this._hoverTimer);
66
+ this._hoverClose();
67
+ };
68
+ this._onClick = (e) => {
69
+ const target = e.target;
70
+ if (!(target instanceof Node) || this._pinPanel(e)) return;
71
+ if (this._toggle?.contains(target)) {
72
+ this.toggle();
73
+ e.preventDefault();
74
+ return;
75
+ }
76
+ if (this._isScrimClick(e) && this.isExpanded && this._isModal()) {
77
+ this.collapse();
78
+ }
79
+ };
80
+ this._onKeyDown = (e) => {
81
+ if (e.key !== "Escape" || e.defaultPrevented || this._escapePanel(e)) return;
82
+ if (this.isExpanded && this._isModal()) {
83
+ const root = this.el.getRootNode();
84
+ const restoreFocus = this.el.contains(root.activeElement);
85
+ const focused = deepActiveElement(root);
86
+ this.collapse();
87
+ if (!this.isExpanded && restoreFocus && deepActiveElement(root) === focused) {
88
+ this._toggle?.focus();
89
+ }
90
+ }
91
+ };
92
+ this._toggle = this._findToggle();
93
+ this._mql = window.matchMedia(COMPACT);
94
+ this.isExpanded = this.el.classList.contains("expanded");
95
+ this._sync();
96
+ const { signal } = this._events;
97
+ this.el.addEventListener("click", this._onClick, { signal });
98
+ this.el.addEventListener("pointerover", this._onPointerOver, { signal });
99
+ this.el.addEventListener("pointerleave", this._onPointerLeave, { signal });
100
+ document.addEventListener("keydown", this._onKeyDown, { signal });
101
+ }
102
+ static get defaults() {
103
+ return _defaults;
104
+ }
105
+ destroy() {
106
+ clearTimeout(this._hoverTimer);
107
+ super.destroy();
108
+ }
109
+ _findToggle() {
110
+ const first = this.el.querySelector(":scope > button:not(.button, [popovertarget])");
111
+ return first instanceof HTMLButtonElement ? first : null;
112
+ }
113
+ _isCompact() {
114
+ return this._mql.matches;
115
+ }
116
+ _isModal() {
117
+ return this.el.classList.contains("modal") || this._isCompact();
118
+ }
119
+ _sync() {
120
+ this.el.setAttribute("aria-expanded", this.isExpanded ? "true" : "false");
121
+ this._toggle?.setAttribute("aria-expanded", this.isExpanded ? "true" : "false");
122
+ }
123
+ /** The side panel of the enabled destination around `target`, if any. */
124
+ _panelAt(target) {
125
+ const trigger = target instanceof Element ? target.closest("button[popovertarget]:enabled") : null;
126
+ const panel = trigger?.popoverTargetElement;
127
+ return panel?.classList.contains("navigation-rail-panel") ? panel : null;
128
+ }
129
+ // Looks the panel up again because the trigger can be disabled during the delay.
130
+ _hoverOpen(target) {
131
+ const panel = this._panelAt(target);
132
+ if (!panel || panel.matches(":popover-open")) return;
133
+ panel.showPopover.call(panel, {
134
+ source: target.closest("button[popovertarget]")
135
+ });
136
+ this._hoverPanel = panel;
137
+ }
138
+ // Closes the hover-opened panel after the delay, unless the pointer is still inside it.
139
+ _hoverClose(target = null) {
140
+ const panel = this._hoverPanel;
141
+ if (!panel || panel.contains(target)) return;
142
+ this._hoverTimer = setTimeout(() => {
143
+ const root = this.el.getRootNode();
144
+ if (panel.matches(":popover-open") && !panel.contains(root.activeElement)) panel.hidePopover();
145
+ if (this._hoverPanel === panel) this._hoverPanel = null;
146
+ }, HOVER_DELAY);
147
+ }
148
+ // Clicking a hover-opened panel's trigger keeps it open instead of toggling
149
+ // it shut; either way the panel no longer follows the pointer.
150
+ _pinPanel(e) {
151
+ const panel = this._panelAt(e.target);
152
+ if (!panel) return false;
153
+ clearTimeout(this._hoverTimer);
154
+ if (panel === this._hoverPanel && panel.matches(":popover-open")) e.preventDefault();
155
+ this._hoverPanel = null;
156
+ return true;
157
+ }
158
+ // Escape closes an open side panel before the rail, and reports whether a
159
+ // panel took the key. A hover-opened panel has no focus to return to, so
160
+ // focus inside it goes back to its trigger.
161
+ _escapePanel(e) {
162
+ clearTimeout(this._hoverTimer);
163
+ this._hoverPanel = null;
164
+ const panel = Array.from(this.el.querySelectorAll(".navigation-rail-panel")).find(
165
+ (el) => el.matches(":popover-open")
166
+ );
167
+ if (!panel) return false;
168
+ if (panel.querySelector(":popover-open")) return true;
169
+ const root = this.el.getRootNode();
170
+ const hadFocus = panel.contains(root.activeElement);
171
+ panel.hidePopover();
172
+ if (hadFocus) panel.previousElementSibling?.focus();
173
+ e.preventDefault();
174
+ return true;
175
+ }
176
+ // The scrim is the rail's own ::before, so a click on blank space inside the
177
+ // rail targets the rail just as a scrim click does. Only a click beside the
178
+ // rail's box landed on the scrim; a modal rail spans the full height.
179
+ _isScrimClick(e) {
180
+ if (e.target !== this.el) return false;
181
+ const { left, right } = this.el.getBoundingClientRect();
182
+ return e.clientX < left || e.clientX > right;
183
+ }
184
+ };
185
+ NavigationRail.key = "Expressive_NavigationRail";
186
+
187
+ export {
188
+ NavigationRail
189
+ };
190
+ //# sourceMappingURL=chunk-Z4GICXR2.mjs.map