@0001-labs/design-system-1 0.3.0-alpha.13 → 0.3.0-alpha.15

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 (722) hide show
  1. package/DS1/0-face/calendar.ts +194 -0
  2. package/DS1/0-face/carousel.ts +623 -0
  3. package/DS1/0-face/component-visibility.ts +14 -0
  4. package/DS1/0-face/copy-text.ts +96 -0
  5. package/DS1/0-face/device.ts +8 -58
  6. package/DS1/0-face/dialog-swipe.ts +249 -0
  7. package/DS1/0-face/dialogs.ts +208 -0
  8. package/DS1/0-face/drawer.ts +258 -0
  9. package/DS1/0-face/feedback-words.ts +36 -0
  10. package/DS1/0-face/feedback.ts +40 -0
  11. package/DS1/0-face/format.ts +700 -0
  12. package/DS1/0-face/generated/toast-assets.ts +18 -0
  13. package/DS1/0-face/grid-fit.ts +1 -1
  14. package/DS1/0-face/grid.ts +3 -2
  15. package/DS1/0-face/header.ts +78 -0
  16. package/DS1/0-face/i18n.ts +93 -18
  17. package/DS1/0-face/keys.ts +276 -0
  18. package/DS1/0-face/languages.ts +4 -4
  19. package/DS1/0-face/layout-inspector.ts +6 -6
  20. package/DS1/0-face/library-styles.ts +33 -0
  21. package/DS1/0-face/load-toaster.ts +7 -0
  22. package/DS1/0-face/preference-options.ts +29 -0
  23. package/DS1/0-face/preferences.ts +3 -11
  24. package/DS1/0-face/pricing.ts +98 -43
  25. package/DS1/0-face/scaling.ts +160 -4
  26. package/DS1/0-face/shared-words.ts +9 -4
  27. package/DS1/0-face/sidebar.ts +201 -0
  28. package/DS1/0-face/theme-bootstrap.js +184 -0
  29. package/DS1/0-face/theme.ts +89 -47
  30. package/DS1/0-face/toast-queue.ts +157 -0
  31. package/DS1/0-face/toaster.ts +384 -0
  32. package/DS1/0-face/tooltips.ts +157 -15
  33. package/DS1/0-face/translations/da.json +60 -1
  34. package/DS1/0-face/translations/de.json +60 -1
  35. package/DS1/0-face/translations/en.json +60 -1
  36. package/DS1/0-face/translations/es.json +60 -1
  37. package/DS1/0-face/translations/fi.json +60 -1
  38. package/DS1/0-face/translations/fr.json +60 -1
  39. package/DS1/0-face/translations/is.json +60 -1
  40. package/DS1/0-face/translations/it.json +60 -1
  41. package/DS1/0-face/translations/ja.json +60 -1
  42. package/DS1/0-face/translations/ko.json +60 -1
  43. package/DS1/0-face/translations/nb.json +60 -1
  44. package/DS1/0-face/translations/pt-BR.json +60 -1
  45. package/DS1/0-face/translations/pt.json +60 -1
  46. package/DS1/0-face/translations/sv.json +60 -1
  47. package/DS1/0-face/translations/zh.json +60 -1
  48. package/DS1/0-face/translations-format.ts +3 -4
  49. package/DS1/1-root/card.css +192 -0
  50. package/DS1/1-root/carousel.css +136 -0
  51. package/DS1/1-root/cjk.css +23 -0
  52. package/DS1/1-root/component-metrics.css +1 -0
  53. package/DS1/1-root/component-tokens.css +51 -8
  54. package/DS1/1-root/controls.css +891 -14
  55. package/DS1/1-root/dialog-placement.css +191 -0
  56. package/DS1/1-root/document.css +183 -0
  57. package/DS1/1-root/drawer.css +83 -0
  58. package/DS1/1-root/empty.css +83 -0
  59. package/DS1/1-root/figures.css +141 -0
  60. package/DS1/1-root/fonts/Iosevka-LICENSE.md +3 -1
  61. package/DS1/1-root/fonts/Iosevka-Regular.woff2 +0 -0
  62. package/DS1/1-root/fonts.css +69 -0
  63. package/DS1/1-root/footer.css +186 -0
  64. package/DS1/1-root/header.css +165 -0
  65. package/DS1/1-root/library-tokens.ts +91 -0
  66. package/DS1/1-root/measures.ts +53 -0
  67. package/DS1/1-root/notice.css +165 -0
  68. package/DS1/1-root/one.css +14 -84
  69. package/DS1/1-root/one.semantic.css +200 -148
  70. package/DS1/1-root/palette.css +58 -0
  71. package/DS1/1-root/palette.ts +19 -0
  72. package/DS1/1-root/progress.css +356 -0
  73. package/DS1/1-root/prose.css +202 -0
  74. package/DS1/1-root/row.css +300 -0
  75. package/DS1/1-root/table.css +111 -0
  76. package/DS1/1-root/text.css +70 -0
  77. package/DS1/2-core/button-split.ts +55 -0
  78. package/DS1/2-core/chart/chart.css +169 -0
  79. package/DS1/2-core/chart/grid-chart.ts +554 -0
  80. package/DS1/2-core/ds-avatar.ts +25 -6
  81. package/DS1/2-core/ds-badge.ts +10 -10
  82. package/DS1/2-core/ds-button.ts +111 -26
  83. package/DS1/2-core/ds-card.ts +135 -105
  84. package/DS1/2-core/ds-chart.ts +327 -0
  85. package/DS1/2-core/ds-composer.ts +8 -2
  86. package/DS1/2-core/ds-cycle.ts +97 -21
  87. package/DS1/2-core/ds-empty.ts +120 -0
  88. package/DS1/2-core/ds-icon.ts +11 -2
  89. package/DS1/2-core/ds-input.ts +165 -6
  90. package/DS1/2-core/ds-message.ts +218 -0
  91. package/DS1/2-core/ds-notice.ts +10 -0
  92. package/DS1/2-core/ds-progress.ts +380 -0
  93. package/DS1/2-core/ds-stat.ts +174 -0
  94. package/DS1/2-core/ds-switch.ts +1 -0
  95. package/DS1/2-core/ds-text.ts +15 -2
  96. package/DS1/2-core/ds-toast.ts +354 -0
  97. package/DS1/2-core/figures.ts +105 -0
  98. package/DS1/2-core/generated/ds-icon-map.ts +238 -128
  99. package/DS1/2-core/generated/icon-avatar.ts +2 -0
  100. package/DS1/2-core/generated/icons-extra.ts +120 -65
  101. package/DS1/2-core/generated/icons-immediate.ts +1 -1
  102. package/DS1/2-core/styles/ds-avatar.css +9 -8
  103. package/DS1/2-core/styles/ds-button-host.css +26 -3
  104. package/DS1/2-core/styles/ds-button-split.css +67 -0
  105. package/DS1/2-core/styles/ds-button.css +49 -15
  106. package/DS1/2-core/styles/ds-card.css +34 -0
  107. package/DS1/2-core/styles/ds-composer.css +13 -0
  108. package/DS1/2-core/styles/ds-cycle.css +10 -0
  109. package/DS1/2-core/styles/ds-empty.css +18 -0
  110. package/DS1/2-core/styles/ds-gap.css +1 -0
  111. package/DS1/2-core/styles/ds-icon.css +1 -0
  112. package/DS1/2-core/styles/ds-input.css +59 -6
  113. package/DS1/2-core/styles/ds-notice.css +32 -0
  114. package/DS1/2-core/styles/ds-progress.css +25 -0
  115. package/DS1/2-core/styles/ds-select.css +2 -2
  116. package/DS1/2-core/styles/ds-split.css +2 -62
  117. package/DS1/2-core/styles/ds-stat.css +34 -0
  118. package/DS1/2-core/styles/ds-switch.css +16 -1
  119. package/DS1/2-core/styles/ds-text.css +43 -12
  120. package/DS1/2-core/styles/ds-toast.css +182 -0
  121. package/DS1/2-core/styles/ds-tooltip.css +1 -0
  122. package/DS1/3-unit/calendar-base.ts +263 -0
  123. package/DS1/3-unit/ds-accordion.ts +9 -1
  124. package/DS1/3-unit/ds-avatar-group.ts +1 -0
  125. package/DS1/3-unit/ds-calendar-large.ts +349 -0
  126. package/DS1/3-unit/ds-calendar.ts +344 -0
  127. package/DS1/3-unit/ds-carousel.ts +368 -0
  128. package/DS1/3-unit/ds-date-picker.ts +540 -0
  129. package/DS1/3-unit/ds-form.ts +45 -37
  130. package/DS1/3-unit/ds-list.ts +48 -1
  131. package/DS1/3-unit/ds-matrix.ts +318 -0
  132. package/DS1/3-unit/ds-menu.ts +8 -4
  133. package/DS1/3-unit/ds-row.ts +84 -1
  134. package/DS1/3-unit/ds-sidebar.ts +366 -0
  135. package/DS1/3-unit/ds-table.ts +75 -34
  136. package/DS1/3-unit/styles/ds-accordion.css +1 -0
  137. package/DS1/3-unit/styles/ds-avatar-group.css +2 -4
  138. package/DS1/3-unit/styles/ds-calendar-large.css +165 -0
  139. package/DS1/3-unit/styles/ds-calendar.css +238 -0
  140. package/DS1/3-unit/styles/ds-carousel.css +30 -0
  141. package/DS1/3-unit/styles/ds-date-picker.css +124 -0
  142. package/DS1/3-unit/styles/ds-list.css +1 -0
  143. package/DS1/3-unit/styles/ds-matrix.css +203 -0
  144. package/DS1/3-unit/styles/ds-menu.css +31 -6
  145. package/DS1/3-unit/styles/ds-row.css +84 -2
  146. package/DS1/3-unit/styles/ds-sidebar.css +134 -0
  147. package/DS1/3-unit/styles/ds-table.css +3 -74
  148. package/DS1/4-page/ds-dialog.ts +40 -4
  149. package/DS1/4-page/ds-document.ts +240 -0
  150. package/DS1/4-page/ds-footer.ts +165 -0
  151. package/DS1/4-page/ds-grid.ts +39 -59
  152. package/DS1/4-page/ds-header.ts +171 -0
  153. package/DS1/4-page/ds-page.ts +184 -0
  154. package/DS1/4-page/email.ts +2 -3
  155. package/DS1/4-page/styles/ds-container.css +1 -0
  156. package/DS1/4-page/styles/ds-document.css +18 -0
  157. package/DS1/4-page/styles/ds-footer.css +29 -0
  158. package/DS1/4-page/styles/ds-grid.css +31 -85
  159. package/DS1/4-page/styles/ds-header.css +57 -0
  160. package/DS1/4-page/styles/ds-page.css +214 -0
  161. package/DS1/components.ts +7 -1
  162. package/DS1/index.ts +24 -6
  163. package/DS1/react/avatar.ts +4 -5
  164. package/DS1/react/button-split.ts +29 -0
  165. package/DS1/react/button.ts +32 -13
  166. package/DS1/react/carousel.ts +76 -0
  167. package/DS1/react/dialog.ts +36 -5
  168. package/DS1/react/document.ts +14 -0
  169. package/DS1/react/empty.ts +32 -0
  170. package/DS1/react/footer.ts +17 -0
  171. package/DS1/react/header.ts +15 -0
  172. package/DS1/react/input.ts +28 -17
  173. package/DS1/react/message.ts +73 -0
  174. package/DS1/react/notice.ts +59 -0
  175. package/DS1/react/page.ts +13 -0
  176. package/DS1/react/progress.ts +99 -0
  177. package/DS1/react/sidebar.ts +71 -0
  178. package/DS1/react/stat.ts +73 -0
  179. package/DS1/react/toast.ts +82 -0
  180. package/DS1/x-icon/Tabler-LICENSE.md +27 -0
  181. package/DS1/x-icon/airtable.svg +5 -0
  182. package/DS1/x-icon/attach.svg +3 -0
  183. package/DS1/x-icon/audio.svg +3 -0
  184. package/DS1/x-icon/bag-alt.svg +3 -0
  185. package/DS1/x-icon/bank.svg +3 -0
  186. package/DS1/x-icon/banknote.svg +3 -0
  187. package/DS1/x-icon/bolt.svg +3 -0
  188. package/DS1/x-icon/book-alt.svg +3 -0
  189. package/DS1/x-icon/book.svg +4 -0
  190. package/DS1/x-icon/box.svg +3 -0
  191. package/DS1/x-icon/briefcase.svg +3 -0
  192. package/DS1/x-icon/building.svg +4 -0
  193. package/DS1/x-icon/car.svg +3 -0
  194. package/DS1/x-icon/card.svg +3 -0
  195. package/DS1/x-icon/cart.svg +3 -0
  196. package/DS1/x-icon/{ezo-android-screen-stats.svg → chevron-down.svg} +1 -1
  197. package/DS1/x-icon/{ezo-item-button-start.svg → chevron-left.svg} +1 -1
  198. package/DS1/x-icon/{ezo-android-screen-lists.svg → chevron-right.svg} +1 -1
  199. package/DS1/x-icon/{ezo-item-button-reopen.svg → chevron-up.svg} +1 -1
  200. package/DS1/x-icon/cloud.svg +3 -0
  201. package/DS1/x-icon/coffee.svg +3 -0
  202. package/DS1/x-icon/coins.svg +3 -0
  203. package/DS1/x-icon/cursor.svg +3 -0
  204. package/DS1/x-icon/curve.svg +7 -0
  205. package/DS1/x-icon/dislike.svg +4 -0
  206. package/DS1/x-icon/dot-bank.svg +3 -0
  207. package/DS1/x-icon/dot-banknote.svg +3 -0
  208. package/DS1/x-icon/dot-banknotes.svg +3 -0
  209. package/DS1/x-icon/dot-card.svg +3 -0
  210. package/DS1/x-icon/dot-coin.svg +3 -0
  211. package/DS1/x-icon/dot-coins.svg +3 -0
  212. package/DS1/x-icon/dot-receipt.svg +3 -0
  213. package/DS1/x-icon/dot-safe.svg +3 -0
  214. package/DS1/x-icon/dot-transfer.svg +3 -0
  215. package/DS1/x-icon/dot-wallet.svg +3 -0
  216. package/DS1/x-icon/download.svg +4 -0
  217. package/DS1/x-icon/drive.svg +5 -0
  218. package/DS1/x-icon/drop.svg +3 -0
  219. package/DS1/x-icon/dropbox.svg +3 -0
  220. package/DS1/x-icon/dumbbell.svg +3 -0
  221. package/DS1/x-icon/eye-off.svg +3 -0
  222. package/DS1/x-icon/eye.svg +3 -0
  223. package/DS1/x-icon/facebook.svg +3 -0
  224. package/DS1/x-icon/figma.svg +5 -0
  225. package/DS1/x-icon/flame.svg +3 -0
  226. package/DS1/x-icon/flip.svg +5 -0
  227. package/DS1/x-icon/food.svg +3 -0
  228. package/DS1/x-icon/fuel.svg +3 -0
  229. package/DS1/x-icon/game.svg +3 -0
  230. package/DS1/x-icon/gift.svg +3 -0
  231. package/DS1/x-icon/github.svg +3 -0
  232. package/DS1/x-icon/heart.svg +3 -0
  233. package/DS1/x-icon/history.svg +3 -0
  234. package/DS1/x-icon/home-alt.svg +3 -0
  235. package/DS1/x-icon/income.svg +3 -0
  236. package/DS1/x-icon/info.svg +5 -0
  237. package/DS1/x-icon/instagram.svg +5 -0
  238. package/DS1/x-icon/jpbank.svg +3 -0
  239. package/DS1/x-icon/key.svg +4 -0
  240. package/DS1/x-icon/keyboard.svg +3 -0
  241. package/DS1/x-icon/like.svg +4 -0
  242. package/DS1/x-icon/linkedin.svg +7 -0
  243. package/DS1/x-icon/loom.svg +6 -0
  244. package/DS1/x-icon/map.svg +4 -0
  245. package/DS1/x-icon/medical.svg +3 -0
  246. package/DS1/x-icon/minus.svg +3 -0
  247. package/DS1/x-icon/moon.svg +3 -0
  248. package/DS1/x-icon/move.svg +3 -0
  249. package/DS1/x-icon/music-alt.svg +3 -0
  250. package/DS1/x-icon/music.svg +5 -0
  251. package/DS1/x-icon/notion.svg +6 -0
  252. package/DS1/x-icon/offline.svg +3 -0
  253. package/DS1/x-icon/pause.svg +4 -0
  254. package/DS1/x-icon/paw.svg +3 -0
  255. package/DS1/x-icon/pdf.svg +3 -0
  256. package/DS1/x-icon/people.svg +5 -0
  257. package/DS1/x-icon/percent.svg +3 -0
  258. package/DS1/x-icon/phone.svg +3 -0
  259. package/DS1/x-icon/pill.svg +3 -0
  260. package/DS1/x-icon/plane.svg +3 -0
  261. package/DS1/x-icon/postal.svg +3 -0
  262. package/DS1/x-icon/present.svg +4 -0
  263. package/DS1/x-icon/reaction.svg +5 -0
  264. package/DS1/x-icon/receipt.svg +3 -0
  265. package/DS1/x-icon/refresh.svg +3 -0
  266. package/DS1/x-icon/refund.svg +3 -0
  267. package/DS1/x-icon/repeat.svg +3 -0
  268. package/DS1/x-icon/rotate.svg +4 -0
  269. package/DS1/x-icon/safe.svg +3 -0
  270. package/DS1/x-icon/school-alt.svg +3 -0
  271. package/DS1/x-icon/shield-alt.svg +3 -0
  272. package/DS1/x-icon/shield.svg +4 -0
  273. package/DS1/x-icon/shirt.svg +3 -0
  274. package/DS1/x-icon/shop.svg +3 -0
  275. package/DS1/x-icon/sign-in.svg +3 -0
  276. package/DS1/x-icon/sign-out.svg +3 -0
  277. package/DS1/x-icon/slack.svg +6 -0
  278. package/DS1/x-icon/sparkle.svg +3 -0
  279. package/DS1/x-icon/start.svg +4 -0
  280. package/DS1/x-icon/stop.svg +3 -0
  281. package/DS1/x-icon/sun.svg +3 -0
  282. package/DS1/x-icon/system.svg +4 -0
  283. package/DS1/x-icon/tag.svg +3 -0
  284. package/DS1/x-icon/ticket.svg +3 -0
  285. package/DS1/x-icon/title-struck.svg +4 -0
  286. package/DS1/x-icon/train.svg +3 -0
  287. package/DS1/x-icon/transfer.svg +3 -0
  288. package/DS1/x-icon/tv.svg +3 -0
  289. package/DS1/x-icon/upload.svg +4 -0
  290. package/DS1/x-icon/video.svg +4 -0
  291. package/DS1/x-icon/vimeo.svg +3 -0
  292. package/DS1/x-icon/wallet.svg +3 -0
  293. package/DS1/x-icon/wifi.svg +3 -0
  294. package/DS1/x-icon/window.svg +4 -0
  295. package/DS1/x-icon/wrench.svg +3 -0
  296. package/DS1/x-icon/x-brand.svg +4 -0
  297. package/DS1/x-icon/youtube.svg +4 -0
  298. package/README.md +3 -3
  299. package/dist/0-face/calendar.d.ts +75 -0
  300. package/dist/0-face/calendar.d.ts.map +1 -0
  301. package/dist/0-face/calendar.js +149 -0
  302. package/dist/0-face/carousel.d.ts +174 -0
  303. package/dist/0-face/carousel.d.ts.map +1 -0
  304. package/dist/0-face/carousel.js +583 -0
  305. package/dist/0-face/component-visibility.d.ts +7 -0
  306. package/dist/0-face/component-visibility.d.ts.map +1 -0
  307. package/dist/0-face/component-visibility.js +11 -0
  308. package/dist/0-face/copy-text.d.ts +11 -0
  309. package/dist/0-face/copy-text.d.ts.map +1 -0
  310. package/dist/0-face/copy-text.js +97 -0
  311. package/dist/0-face/device.d.ts +3 -7
  312. package/dist/0-face/device.d.ts.map +1 -1
  313. package/dist/0-face/device.js +7 -41
  314. package/dist/0-face/dialog-swipe.d.ts +49 -0
  315. package/dist/0-face/dialog-swipe.d.ts.map +1 -0
  316. package/dist/0-face/dialog-swipe.js +239 -0
  317. package/dist/0-face/dialogs.d.ts +33 -0
  318. package/dist/0-face/dialogs.d.ts.map +1 -0
  319. package/dist/0-face/dialogs.js +173 -0
  320. package/dist/0-face/drawer.d.ts +64 -0
  321. package/dist/0-face/drawer.d.ts.map +1 -0
  322. package/dist/0-face/drawer.js +256 -0
  323. package/dist/0-face/feedback-words.d.ts +21 -0
  324. package/dist/0-face/feedback-words.d.ts.map +1 -0
  325. package/dist/0-face/feedback-words.js +30 -0
  326. package/dist/0-face/feedback.d.ts +41 -0
  327. package/dist/0-face/feedback.d.ts.map +1 -0
  328. package/dist/0-face/feedback.js +35 -0
  329. package/dist/0-face/format.d.ts +166 -0
  330. package/dist/0-face/format.d.ts.map +1 -0
  331. package/dist/0-face/format.js +445 -0
  332. package/dist/0-face/generated/toast-assets.d.ts +11 -0
  333. package/dist/0-face/generated/toast-assets.d.ts.map +1 -0
  334. package/dist/0-face/generated/toast-assets.js +14 -0
  335. package/dist/0-face/grid-fit.js +1 -1
  336. package/dist/0-face/grid.d.ts.map +1 -1
  337. package/dist/0-face/grid.js +2 -1
  338. package/dist/0-face/header.d.ts +38 -0
  339. package/dist/0-face/header.d.ts.map +1 -0
  340. package/dist/0-face/header.js +80 -0
  341. package/dist/0-face/i18n.d.ts +32 -2
  342. package/dist/0-face/i18n.d.ts.map +1 -1
  343. package/dist/0-face/i18n.js +65 -19
  344. package/dist/0-face/keys.d.ts +104 -0
  345. package/dist/0-face/keys.d.ts.map +1 -0
  346. package/dist/0-face/keys.js +253 -0
  347. package/dist/0-face/languages.d.ts +2 -2
  348. package/dist/0-face/languages.js +3 -3
  349. package/dist/0-face/layout-inspector.js +6 -6
  350. package/dist/0-face/library-styles.d.ts +7 -0
  351. package/dist/0-face/library-styles.d.ts.map +1 -0
  352. package/dist/0-face/library-styles.js +29 -0
  353. package/dist/0-face/load-toaster.d.ts +8 -0
  354. package/dist/0-face/load-toaster.d.ts.map +1 -0
  355. package/dist/0-face/load-toaster.js +7 -0
  356. package/dist/0-face/preference-options.d.ts +34 -0
  357. package/dist/0-face/preference-options.d.ts.map +1 -0
  358. package/dist/0-face/preference-options.js +1 -0
  359. package/dist/0-face/preferences.d.ts +3 -12
  360. package/dist/0-face/preferences.d.ts.map +1 -1
  361. package/dist/0-face/pricing.d.ts +19 -9
  362. package/dist/0-face/pricing.d.ts.map +1 -1
  363. package/dist/0-face/pricing.js +81 -40
  364. package/dist/0-face/scaling.d.ts +71 -1
  365. package/dist/0-face/scaling.d.ts.map +1 -1
  366. package/dist/0-face/scaling.js +108 -3
  367. package/dist/0-face/shared-words.d.ts +9 -4
  368. package/dist/0-face/shared-words.d.ts.map +1 -1
  369. package/dist/0-face/sidebar.d.ts +69 -0
  370. package/dist/0-face/sidebar.d.ts.map +1 -0
  371. package/dist/0-face/sidebar.js +191 -0
  372. package/dist/0-face/theme-bootstrap.d.ts +1 -0
  373. package/dist/0-face/theme-bootstrap.d.ts.map +1 -0
  374. package/dist/0-face/theme-bootstrap.js +214 -0
  375. package/dist/0-face/theme.d.ts +32 -0
  376. package/dist/0-face/theme.d.ts.map +1 -1
  377. package/dist/0-face/theme.js +69 -43
  378. package/dist/0-face/toast-queue.d.ts +110 -0
  379. package/dist/0-face/toast-queue.d.ts.map +1 -0
  380. package/dist/0-face/toast-queue.js +98 -0
  381. package/dist/0-face/toaster.d.ts +27 -0
  382. package/dist/0-face/toaster.d.ts.map +1 -0
  383. package/dist/0-face/toaster.js +373 -0
  384. package/dist/0-face/tooltips.d.ts +24 -1
  385. package/dist/0-face/tooltips.d.ts.map +1 -1
  386. package/dist/0-face/tooltips.js +155 -16
  387. package/dist/0-face/translations/da.json +60 -1
  388. package/dist/0-face/translations/de.json +60 -1
  389. package/dist/0-face/translations/en.json +60 -1
  390. package/dist/0-face/translations/es.json +60 -1
  391. package/dist/0-face/translations/fi.json +60 -1
  392. package/dist/0-face/translations/fr.json +60 -1
  393. package/dist/0-face/translations/is.json +60 -1
  394. package/dist/0-face/translations/it.json +60 -1
  395. package/dist/0-face/translations/ja.json +60 -1
  396. package/dist/0-face/translations/ko.json +60 -1
  397. package/dist/0-face/translations/nb.json +60 -1
  398. package/dist/0-face/translations/pt-BR.json +60 -1
  399. package/dist/0-face/translations/pt.json +60 -1
  400. package/dist/0-face/translations/sv.json +60 -1
  401. package/dist/0-face/translations/zh.json +60 -1
  402. package/dist/0-face/translations-format.d.ts.map +1 -1
  403. package/dist/0-face/translations-format.js +3 -4
  404. package/dist/1-root/library-tokens.d.ts +31 -0
  405. package/dist/1-root/library-tokens.d.ts.map +1 -0
  406. package/dist/1-root/library-tokens.js +84 -0
  407. package/dist/1-root/measures.d.ts +52 -0
  408. package/dist/1-root/measures.d.ts.map +1 -0
  409. package/dist/1-root/measures.js +49 -0
  410. package/dist/1-root/palette.d.ts +5 -0
  411. package/dist/1-root/palette.d.ts.map +1 -1
  412. package/dist/1-root/palette.js +18 -0
  413. package/dist/2-core/button-split.d.ts +21 -0
  414. package/dist/2-core/button-split.d.ts.map +1 -0
  415. package/dist/2-core/button-split.js +48 -0
  416. package/dist/2-core/chart/grid-chart.d.ts +113 -0
  417. package/dist/2-core/chart/grid-chart.d.ts.map +1 -0
  418. package/dist/2-core/chart/grid-chart.js +466 -0
  419. package/dist/2-core/ds-avatar.d.ts +20 -3
  420. package/dist/2-core/ds-avatar.d.ts.map +1 -1
  421. package/dist/2-core/ds-avatar.js +19 -5
  422. package/dist/2-core/ds-badge.js +10 -13
  423. package/dist/2-core/ds-button.d.ts +76 -0
  424. package/dist/2-core/ds-button.d.ts.map +1 -1
  425. package/dist/2-core/ds-button.js +101 -26
  426. package/dist/2-core/ds-card.d.ts +76 -11
  427. package/dist/2-core/ds-card.d.ts.map +1 -1
  428. package/dist/2-core/ds-card.js +129 -105
  429. package/dist/2-core/ds-chart.d.ts +105 -0
  430. package/dist/2-core/ds-chart.d.ts.map +1 -0
  431. package/dist/2-core/ds-chart.js +390 -0
  432. package/dist/2-core/ds-composer.d.ts +7 -0
  433. package/dist/2-core/ds-composer.d.ts.map +1 -1
  434. package/dist/2-core/ds-composer.js +1 -1
  435. package/dist/2-core/ds-cycle.d.ts +36 -2
  436. package/dist/2-core/ds-cycle.d.ts.map +1 -1
  437. package/dist/2-core/ds-cycle.js +95 -18
  438. package/dist/2-core/ds-empty.d.ts +74 -0
  439. package/dist/2-core/ds-empty.d.ts.map +1 -0
  440. package/dist/2-core/ds-empty.js +96 -0
  441. package/dist/2-core/ds-icon.d.ts +6 -0
  442. package/dist/2-core/ds-icon.d.ts.map +1 -1
  443. package/dist/2-core/ds-icon.js +12 -2
  444. package/dist/2-core/ds-input.d.ts +39 -1
  445. package/dist/2-core/ds-input.d.ts.map +1 -1
  446. package/dist/2-core/ds-input.js +150 -6
  447. package/dist/2-core/ds-message.d.ts +154 -0
  448. package/dist/2-core/ds-message.d.ts.map +1 -0
  449. package/dist/2-core/ds-message.js +177 -0
  450. package/dist/2-core/ds-notice.d.ts +13 -0
  451. package/dist/2-core/ds-notice.d.ts.map +1 -0
  452. package/dist/2-core/ds-notice.js +11 -0
  453. package/dist/2-core/ds-progress.d.ts +200 -0
  454. package/dist/2-core/ds-progress.d.ts.map +1 -0
  455. package/dist/2-core/ds-progress.js +319 -0
  456. package/dist/2-core/ds-stat.d.ts +126 -0
  457. package/dist/2-core/ds-stat.d.ts.map +1 -0
  458. package/dist/2-core/ds-stat.js +137 -0
  459. package/dist/2-core/ds-switch.d.ts +1 -0
  460. package/dist/2-core/ds-switch.d.ts.map +1 -1
  461. package/dist/2-core/ds-switch.js +1 -0
  462. package/dist/2-core/ds-text.d.ts +15 -2
  463. package/dist/2-core/ds-text.d.ts.map +1 -1
  464. package/dist/2-core/ds-text.js +13 -0
  465. package/dist/2-core/ds-toast.d.ts +139 -0
  466. package/dist/2-core/ds-toast.d.ts.map +1 -0
  467. package/dist/2-core/ds-toast.js +329 -0
  468. package/dist/2-core/figures.d.ts +56 -0
  469. package/dist/2-core/figures.d.ts.map +1 -0
  470. package/dist/2-core/figures.js +70 -0
  471. package/dist/2-core/generated/ds-icon-map.d.ts +120 -65
  472. package/dist/2-core/generated/ds-icon-map.d.ts.map +1 -1
  473. package/dist/2-core/generated/ds-icon-map.js +238 -128
  474. package/dist/2-core/generated/icon-avatar.d.ts +2 -0
  475. package/dist/2-core/generated/icon-avatar.d.ts.map +1 -0
  476. package/dist/2-core/generated/icon-avatar.js +2 -0
  477. package/dist/2-core/generated/icons-extra.d.ts.map +1 -1
  478. package/dist/2-core/generated/icons-extra.js +120 -65
  479. package/dist/2-core/generated/icons-immediate.d.ts +1 -1
  480. package/dist/2-core/generated/icons-immediate.d.ts.map +1 -1
  481. package/dist/2-core/generated/icons-immediate.js +1 -1
  482. package/dist/3-unit/calendar-base.d.ts +149 -0
  483. package/dist/3-unit/calendar-base.d.ts.map +1 -0
  484. package/dist/3-unit/calendar-base.js +172 -0
  485. package/dist/3-unit/ds-accordion.d.ts +9 -0
  486. package/dist/3-unit/ds-accordion.d.ts.map +1 -1
  487. package/dist/3-unit/ds-accordion.js +7 -1
  488. package/dist/3-unit/ds-avatar-group.d.ts +1 -0
  489. package/dist/3-unit/ds-avatar-group.d.ts.map +1 -1
  490. package/dist/3-unit/ds-calendar-large.d.ts +138 -0
  491. package/dist/3-unit/ds-calendar-large.d.ts.map +1 -0
  492. package/dist/3-unit/ds-calendar-large.js +305 -0
  493. package/dist/3-unit/ds-calendar.d.ts +175 -0
  494. package/dist/3-unit/ds-calendar.d.ts.map +1 -0
  495. package/dist/3-unit/ds-calendar.js +303 -0
  496. package/dist/3-unit/ds-carousel.d.ts +182 -0
  497. package/dist/3-unit/ds-carousel.d.ts.map +1 -0
  498. package/dist/3-unit/ds-carousel.js +327 -0
  499. package/dist/3-unit/ds-date-picker.d.ts +203 -0
  500. package/dist/3-unit/ds-date-picker.d.ts.map +1 -0
  501. package/dist/3-unit/ds-date-picker.js +499 -0
  502. package/dist/3-unit/ds-form.d.ts.map +1 -1
  503. package/dist/3-unit/ds-form.js +38 -28
  504. package/dist/3-unit/ds-list.d.ts +12 -0
  505. package/dist/3-unit/ds-list.d.ts.map +1 -1
  506. package/dist/3-unit/ds-list.js +52 -1
  507. package/dist/3-unit/ds-matrix.d.ts +146 -0
  508. package/dist/3-unit/ds-matrix.d.ts.map +1 -0
  509. package/dist/3-unit/ds-matrix.js +248 -0
  510. package/dist/3-unit/ds-menu.d.ts +1 -1
  511. package/dist/3-unit/ds-menu.d.ts.map +1 -1
  512. package/dist/3-unit/ds-menu.js +7 -4
  513. package/dist/3-unit/ds-row.d.ts +66 -0
  514. package/dist/3-unit/ds-row.d.ts.map +1 -1
  515. package/dist/3-unit/ds-row.js +80 -1
  516. package/dist/3-unit/ds-sidebar.d.ts +149 -0
  517. package/dist/3-unit/ds-sidebar.d.ts.map +1 -0
  518. package/dist/3-unit/ds-sidebar.js +342 -0
  519. package/dist/3-unit/ds-table.d.ts +28 -10
  520. package/dist/3-unit/ds-table.d.ts.map +1 -1
  521. package/dist/3-unit/ds-table.js +53 -25
  522. package/dist/4-page/ds-dialog.d.ts +16 -1
  523. package/dist/4-page/ds-dialog.d.ts.map +1 -1
  524. package/dist/4-page/ds-dialog.js +39 -3
  525. package/dist/4-page/ds-document.d.ts +98 -0
  526. package/dist/4-page/ds-document.d.ts.map +1 -0
  527. package/dist/4-page/ds-document.js +213 -0
  528. package/dist/4-page/ds-footer.d.ts +100 -0
  529. package/dist/4-page/ds-footer.d.ts.map +1 -0
  530. package/dist/4-page/ds-footer.js +119 -0
  531. package/dist/4-page/ds-grid.d.ts +32 -12
  532. package/dist/4-page/ds-grid.d.ts.map +1 -1
  533. package/dist/4-page/ds-grid.js +30 -39
  534. package/dist/4-page/ds-header.d.ts +84 -0
  535. package/dist/4-page/ds-header.d.ts.map +1 -0
  536. package/dist/4-page/ds-header.js +143 -0
  537. package/dist/4-page/ds-page.d.ts +110 -0
  538. package/dist/4-page/ds-page.d.ts.map +1 -0
  539. package/dist/4-page/ds-page.js +155 -0
  540. package/dist/4-page/email.d.ts +2 -3
  541. package/dist/4-page/email.d.ts.map +1 -1
  542. package/dist/4-page/email.js +2 -3
  543. package/dist/components.d.ts +4 -1
  544. package/dist/components.d.ts.map +1 -1
  545. package/dist/components.js +4 -1
  546. package/dist/design-system-1.bundle.js +12322 -5523
  547. package/dist/design-system-1.bundle.js.map +1 -1
  548. package/dist/design-system-1.bundle.min.js +8771 -4115
  549. package/dist/design-system-1.bundle.min.js.map +1 -1
  550. package/dist/design-system-1.css +1 -1
  551. package/dist/feedback.js +541 -0
  552. package/dist/feedback.js.map +1 -0
  553. package/dist/{icons-extra-BoAACA4X.js → icons-extra-CiDDs7_-.js} +404 -312
  554. package/dist/icons-extra-CiDDs7_-.js.map +1 -0
  555. package/dist/{icons-extra-DlxTo_Y4.js → icons-extra-hauwCx07.js} +121 -66
  556. package/dist/icons-extra-hauwCx07.js.map +1 -0
  557. package/dist/index.d.ts +21 -6
  558. package/dist/index.d.ts.map +1 -1
  559. package/dist/index.js +21 -6
  560. package/dist/react/avatar.d.ts +5 -9
  561. package/dist/react/avatar.d.ts.map +1 -1
  562. package/dist/react/avatar.js +2 -2
  563. package/dist/react/button-split.d.ts +19 -0
  564. package/dist/react/button-split.d.ts.map +1 -0
  565. package/dist/react/{split.js → button-split.js} +12 -9
  566. package/dist/react/button.d.ts +18 -7
  567. package/dist/react/button.d.ts.map +1 -1
  568. package/dist/react/button.js +13 -4
  569. package/dist/react/carousel.d.ts +63 -0
  570. package/dist/react/carousel.d.ts.map +1 -0
  571. package/dist/react/carousel.js +47 -0
  572. package/dist/react/choice.d.ts +1 -1
  573. package/dist/react/context-menu.d.ts +337 -337
  574. package/dist/react/dialog.d.ts +684 -678
  575. package/dist/react/dialog.d.ts.map +1 -1
  576. package/dist/react/dialog.js +29 -3
  577. package/dist/react/document.d.ts +11 -0
  578. package/dist/react/document.d.ts.map +1 -0
  579. package/dist/react/document.js +10 -0
  580. package/dist/react/empty.d.ts +34 -0
  581. package/dist/react/empty.d.ts.map +1 -0
  582. package/dist/react/empty.js +8 -0
  583. package/dist/react/file-picker.d.ts +1 -1
  584. package/dist/react/footer.d.ts +13 -0
  585. package/dist/react/footer.d.ts.map +1 -0
  586. package/dist/react/footer.js +12 -0
  587. package/dist/react/header.d.ts +12 -0
  588. package/dist/react/header.d.ts.map +1 -0
  589. package/dist/react/header.js +11 -0
  590. package/dist/react/input.d.ts +31 -9
  591. package/dist/react/input.d.ts.map +1 -1
  592. package/dist/react/input.js +94 -94
  593. package/dist/react/message.d.ts +66 -0
  594. package/dist/react/message.d.ts.map +1 -0
  595. package/dist/react/message.js +37 -0
  596. package/dist/react/notice.d.ts +45 -0
  597. package/dist/react/notice.d.ts.map +1 -0
  598. package/dist/react/notice.js +34 -0
  599. package/dist/react/page.d.ts +10 -0
  600. package/dist/react/page.d.ts.map +1 -0
  601. package/dist/react/page.js +9 -0
  602. package/dist/react/progress.d.ts +107 -0
  603. package/dist/react/progress.d.ts.map +1 -0
  604. package/dist/react/progress.js +47 -0
  605. package/dist/react/sidebar.d.ts +54 -0
  606. package/dist/react/sidebar.d.ts.map +1 -0
  607. package/dist/react/sidebar.js +48 -0
  608. package/dist/react/stat.d.ts +78 -0
  609. package/dist/react/stat.d.ts.map +1 -0
  610. package/dist/react/stat.js +25 -0
  611. package/dist/react/toast.d.ts +37 -0
  612. package/dist/react/toast.d.ts.map +1 -0
  613. package/dist/react/toast.js +55 -0
  614. package/dist/shared-words-CyZYc_De.js +1818 -0
  615. package/dist/shared-words-CyZYc_De.js.map +1 -0
  616. package/dist/shared-words-DAVSET4Z.js +1800 -0
  617. package/dist/shared-words-DAVSET4Z.js.map +1 -0
  618. package/package.json +19 -6
  619. package/DS1/2-core/ds-banner.ts +0 -122
  620. package/DS1/2-core/ds-date.ts +0 -24
  621. package/DS1/2-core/ds-language.ts +0 -94
  622. package/DS1/2-core/ds-pagedots.ts +0 -52
  623. package/DS1/2-core/ds-split.ts +0 -122
  624. package/DS1/2-core/ds-textarea.ts +0 -136
  625. package/DS1/2-core/styles/ds-banner.css +0 -77
  626. package/DS1/2-core/styles/ds-date.css +0 -9
  627. package/DS1/2-core/styles/ds-language.css +0 -78
  628. package/DS1/2-core/styles/ds-pagedots.css +0 -31
  629. package/DS1/2-core/styles/ds-textarea.css +0 -27
  630. package/DS1/4-page/ds-layout.ts +0 -949
  631. package/DS1/4-page/styles/ds-layout.css +0 -246
  632. package/DS1/react/split.ts +0 -42
  633. package/DS1/x-icon/ezo-accordion-chevron.svg +0 -11
  634. package/DS1/x-icon/ezo-account-close.svg +0 -1
  635. package/DS1/x-icon/ezo-android-screen-archive.svg +0 -4
  636. package/DS1/x-icon/ezo-android-screen-calendar.svg +0 -6
  637. package/DS1/x-icon/ezo-android-screen-camera.svg +0 -5
  638. package/DS1/x-icon/ezo-android-screen-check.svg +0 -3
  639. package/DS1/x-icon/ezo-android-screen-compose.svg +0 -4
  640. package/DS1/x-icon/ezo-android-screen-globe.svg +0 -1
  641. package/DS1/x-icon/ezo-android-screen-shared.svg +0 -5
  642. package/DS1/x-icon/ezo-android-screen-store.svg +0 -4
  643. package/DS1/x-icon/ezo-android-screen-views.svg +0 -4
  644. package/DS1/x-icon/ezo-android-screen-work.svg +0 -3
  645. package/DS1/x-icon/ezo-arrow-cursor.svg +0 -8
  646. package/DS1/x-icon/ezo-block-accordion.svg +0 -1
  647. package/DS1/x-icon/ezo-block-divider.svg +0 -1
  648. package/DS1/x-icon/ezo-block-group.svg +0 -1
  649. package/DS1/x-icon/ezo-block-image.svg +0 -1
  650. package/DS1/x-icon/ezo-block-section.svg +0 -1
  651. package/DS1/x-icon/ezo-block-table.svg +0 -1
  652. package/DS1/x-icon/ezo-code.svg +0 -14
  653. package/DS1/x-icon/ezo-down.svg +0 -3
  654. package/DS1/x-icon/ezo-figma-premium-star.svg +0 -5
  655. package/DS1/x-icon/ezo-item-button-complete.svg +0 -4
  656. package/DS1/x-icon/ezo-item-button-header.svg +0 -3
  657. package/DS1/x-icon/ezo-item-button-open.svg +0 -3
  658. package/DS1/x-icon/ezo-item-button-star.svg +0 -3
  659. package/DS1/x-icon/ezo-item-button-unheader.svg +0 -7
  660. package/DS1/x-icon/ezo-item-button-unstar.svg +0 -5
  661. package/DS1/x-icon/ezo-item-star.svg +0 -5
  662. package/DS1/x-icon/ezo-left.svg +0 -3
  663. package/DS1/x-icon/ezo-logo.svg +0 -1
  664. package/DS1/x-icon/ezo-mic.svg +0 -8
  665. package/DS1/x-icon/ezo-move-column.svg +0 -14
  666. package/DS1/x-icon/ezo-move-row.svg +0 -18
  667. package/DS1/x-icon/ezo-navigation-check.svg +0 -1
  668. package/DS1/x-icon/ezo-note-back.svg +0 -5
  669. package/DS1/x-icon/ezo-note-menu-complete.svg +0 -11
  670. package/DS1/x-icon/ezo-note-menu-delete.svg +0 -4
  671. package/DS1/x-icon/ezo-note-menu-duplicate.svg +0 -8
  672. package/DS1/x-icon/ezo-note-menu-note.svg +0 -5
  673. package/DS1/x-icon/ezo-note-menu-page.svg +0 -3
  674. package/DS1/x-icon/ezo-note-menu-star.svg +0 -5
  675. package/DS1/x-icon/ezo-note-menu-start.svg +0 -6
  676. package/DS1/x-icon/ezo-note-menu-stop.svg +0 -6
  677. package/DS1/x-icon/ezo-note-more.svg +0 -7
  678. package/DS1/x-icon/ezo-note-star.svg +0 -5
  679. package/DS1/x-icon/ezo-pattern-call-to-action.svg +0 -1
  680. package/DS1/x-icon/ezo-play.svg +0 -5
  681. package/DS1/x-icon/ezo-premium-star.svg +0 -5
  682. package/DS1/x-icon/ezo-setting-1xdots.svg +0 -13
  683. package/DS1/x-icon/ezo-setting-1xgrid.svg +0 -10
  684. package/DS1/x-icon/ezo-setting-1xlines.svg +0 -7
  685. package/DS1/x-icon/ezo-setting-2xdots.svg +0 -8
  686. package/DS1/x-icon/ezo-setting-2xgrid.svg +0 -8
  687. package/DS1/x-icon/ezo-setting-2xlines.svg +0 -6
  688. package/DS1/x-icon/ezo-setting-blank.svg +0 -5
  689. package/DS1/x-icon/ezo-store-chevron.svg +0 -1
  690. package/DS1/x-icon/ezo-upgrade-close.svg +0 -5
  691. package/DS1/x-icon/product-sources.json +0 -2557
  692. package/dist/2-core/ds-banner.d.ts +0 -68
  693. package/dist/2-core/ds-banner.d.ts.map +0 -1
  694. package/dist/2-core/ds-banner.js +0 -98
  695. package/dist/2-core/ds-date.d.ts +0 -16
  696. package/dist/2-core/ds-date.d.ts.map +0 -1
  697. package/dist/2-core/ds-date.js +0 -15
  698. package/dist/2-core/ds-language.d.ts +0 -75
  699. package/dist/2-core/ds-language.d.ts.map +0 -1
  700. package/dist/2-core/ds-language.js +0 -74
  701. package/dist/2-core/ds-pagedots.d.ts +0 -32
  702. package/dist/2-core/ds-pagedots.d.ts.map +0 -1
  703. package/dist/2-core/ds-pagedots.js +0 -36
  704. package/dist/2-core/ds-split.d.ts +0 -75
  705. package/dist/2-core/ds-split.d.ts.map +0 -1
  706. package/dist/2-core/ds-split.js +0 -101
  707. package/dist/2-core/ds-textarea.d.ts +0 -46
  708. package/dist/2-core/ds-textarea.d.ts.map +0 -1
  709. package/dist/2-core/ds-textarea.js +0 -121
  710. package/dist/4-page/ds-layout.d.ts +0 -31
  711. package/dist/4-page/ds-layout.d.ts.map +0 -1
  712. package/dist/4-page/ds-layout.js +0 -930
  713. package/dist/icons-extra-BoAACA4X.js.map +0 -1
  714. package/dist/icons-extra-DlxTo_Y4.js.map +0 -1
  715. package/dist/react/split.d.ts +0 -15
  716. package/dist/react/split.d.ts.map +0 -1
  717. package/dist/shared-words-Cg6Phtx0.js +0 -915
  718. package/dist/shared-words-Cg6Phtx0.js.map +0 -1
  719. package/dist/shared-words-Ddz0yUEF.js +0 -933
  720. package/dist/shared-words-Ddz0yUEF.js.map +0 -1
  721. /package/DS1/x-icon/{ezo-password-visibility-see.svg → password-see.svg} +0 -0
  722. /package/DS1/x-icon/{ezo-password-visibility-unsee.svg → password-unsee.svg} +0 -0
@@ -2,11 +2,17 @@ import { LitElement, css, html, unsafeCSS } from "lit";
2
2
  import { define } from "../0-face/define";
3
3
  import "../2-core/ds-button";
4
4
  import "../2-core/ds-icon";
5
+ import { bindDialogSwipe, type DialogPlacement } from "../0-face/dialog-swipe";
5
6
  import "./styles/ds-dialog.css";
6
- import dialogStyles from "./styles/ds-dialog.css?inline";
7
+ import "../1-root/dialog-placement.css";
8
+ import frameStyles from "./styles/ds-dialog.css?inline";
9
+ import placementStyles from "../1-root/dialog-placement.css?inline";
7
10
  import metrics from "../1-root/component-metrics.css?inline";
8
11
 
9
- export type DialogCloseReason = "escape" | "backdrop" | "outside" | "button" | "native";
12
+ export type { DialogPlacement } from "../0-face/dialog-swipe";
13
+ export type DialogCloseReason = "escape" | "backdrop" | "outside" | "button" | "native" | "swipe";
14
+ const dialogStyles = `${frameStyles}\n${placementStyles}`;
15
+ const PLACEMENTS = new Set<string>(["sheet", "end", "start"]);
10
16
  const openDialogs = new WeakMap<Document, Set<Dialog>>();
11
17
  type SavedStyle = { style: CSSStyleDeclaration; name: string; value: string; priority: string; locked: string };
12
18
  const scrollStyles = new WeakMap<Document, { declarations: SavedStyle[]; x: number; y: number }>();
@@ -60,6 +66,9 @@ function styleRoot(root: Node) {
60
66
  /** A native light-DOM dialog keeps forms and accessible ID references together.
61
67
  * The browser owns the top layer, inert background and modal focus navigation.
62
68
  * Listen to ds-close-request and preventDefault to control whether it closes.
69
+ * `placement` stands it in the centre (the default), as a sheet from the
70
+ * bottom (`"sheet"`) or as a drawer at the end or start (`"end"`, `"start"`),
71
+ * which slide in and out and a finger swipes away (reason `"swipe"`).
63
72
  */
64
73
  export class Dialog extends LitElement {
65
74
  static properties = {
@@ -70,10 +79,11 @@ export class Dialog extends LitElement {
70
79
  holdScroll: { type: Boolean, attribute: "hold-scroll" },
71
80
  closeOnEscape: { type: Boolean, attribute: "close-on-escape" },
72
81
  closeOnBackdrop: { type: Boolean, attribute: "close-on-backdrop" },
82
+ placement: { type: String, reflect: true },
73
83
  anchor: { attribute: false },
74
84
  returnFocus: { attribute: false },
75
85
  };
76
- static styles = [unsafeCSS(metrics), css`:host { display: contents; }`];
86
+ static styles = [unsafeCSS(metrics), css`:host { display: contents; } :host([hidden]) { display: none !important; }`];
77
87
  declare open: boolean;
78
88
  declare nonModal: boolean;
79
89
  declare closeOnOutside: boolean;
@@ -81,6 +91,8 @@ export class Dialog extends LitElement {
81
91
  declare holdScroll: boolean;
82
92
  declare closeOnEscape: boolean;
83
93
  declare closeOnBackdrop: boolean;
94
+ /** Where it stands: `"center"`, a `"sheet"` from the bottom, or a drawer at the `"end"` or `"start"`. An anchored panel ignores it. */
95
+ declare placement: DialogPlacement;
84
96
  /** A viewport point for a floating panel; null uses ordinary dialog layout. */
85
97
  declare anchor: { x: number; y: number } | null;
86
98
  /** Resolve a replacement opener after the product has rendered its closed state. */
@@ -92,6 +104,7 @@ export class Dialog extends LitElement {
92
104
  private outsidePress: boolean | null = null;
93
105
  private observer = new MutationObserver(() => this.bindDialog());
94
106
  private sizeObserver: ResizeObserver | null = null;
107
+ private unbindSwipe: (() => void) | null = null;
95
108
 
96
109
  constructor() {
97
110
  super();
@@ -102,6 +115,7 @@ export class Dialog extends LitElement {
102
115
  this.holdScroll = false;
103
116
  this.closeOnEscape = true;
104
117
  this.closeOnBackdrop = true;
118
+ this.placement = "center";
105
119
  this.anchor = null;
106
120
  this.returnFocus = null;
107
121
  }
@@ -119,7 +133,25 @@ export class Dialog extends LitElement {
119
133
  super.disconnectedCallback();
120
134
  }
121
135
 
122
- protected updated() { this.syncOpen(); this.place(); }
136
+ protected updated() { this.syncPlacement(); this.syncOpen(); this.place(); }
137
+
138
+ /** Mark the native frame with its placement before it opens, so it slides in from its edge, and let a finger swipe it away. */
139
+ private syncPlacement() {
140
+ const dialog = this.dialog;
141
+ if (!dialog) return;
142
+ const placement = !this.anchor && PLACEMENTS.has(this.placement) ? this.placement : null;
143
+ if (placement) dialog.setAttribute("data-ds-placement", placement);
144
+ else dialog.removeAttribute("data-ds-placement");
145
+ if (placement && !this.unbindSwipe) {
146
+ this.unbindSwipe = bindDialogSwipe(dialog, {
147
+ placement: () => (!this.anchor && PLACEMENTS.has(this.placement) ? this.placement : "center"),
148
+ onDismiss: () => this.requestClose("swipe"),
149
+ });
150
+ } else if (!placement && this.unbindSwipe) {
151
+ this.unbindSwipe();
152
+ this.unbindSwipe = null;
153
+ }
154
+ }
123
155
 
124
156
  /** Keep an anchored panel inside the visible viewport as its content or keyboard changes. */
125
157
  place = () => {
@@ -147,6 +179,7 @@ export class Dialog extends LitElement {
147
179
  dialog?.addEventListener("close", this.onNativeClose);
148
180
  dialog?.addEventListener("pointerdown", this.onPointerDown);
149
181
  dialog?.addEventListener("click", this.onClick);
182
+ this.syncPlacement();
150
183
  this.syncOpen();
151
184
  };
152
185
 
@@ -156,6 +189,9 @@ export class Dialog extends LitElement {
156
189
  dialog?.removeEventListener("close", this.onNativeClose);
157
190
  dialog?.removeEventListener("pointerdown", this.onPointerDown);
158
191
  dialog?.removeEventListener("click", this.onClick);
192
+ this.unbindSwipe?.();
193
+ this.unbindSwipe = null;
194
+ dialog?.removeAttribute("data-ds-placement");
159
195
  if (dialog?.open) dialog.close();
160
196
  this.release();
161
197
  this.dialog = null;
@@ -0,0 +1,240 @@
1
+ // ds-document.ts
2
+ // A document page (terms, a privacy policy, a legal notice, a help article):
3
+ // the writing as prose, with contents built from its headings that mark the
4
+ // section in view. Drawn by 1-root/document.css, the same classes a page
5
+ // without scripts writes; the writing stays in the page and prose.css draws it.
6
+
7
+ import { LitElement, html, nothing, unsafeCSS } from "lit";
8
+ import { getText } from "../0-face/i18n";
9
+ import { define } from "../0-face/define";
10
+ import metrics from "../1-root/component-metrics.css?inline";
11
+ import documentSheet from "../1-root/document.css?inline";
12
+ import documentRules from "../1-root/document.css?raw";
13
+ import proseRules from "../1-root/prose.css?raw";
14
+ import styles from "./styles/ds-document.css?inline";
15
+
16
+ /** The shared word over the contents. */
17
+ export const CONTENTS_LABEL = "Contents";
18
+
19
+ /** One entry in the contents: a heading in the writing. */
20
+ export interface DocumentEntry {
21
+ id: string;
22
+ text: string;
23
+ level: number;
24
+ }
25
+
26
+ /**
27
+ * An id for a heading from its words: letters and digits in any script,
28
+ * joined by hyphens, unique among `taken`. Words with none of either get
29
+ * `section-<n>`.
30
+ */
31
+ export function headingId(text: string, taken: Set<string>, index: number): string {
32
+ const base = text.normalize("NFKC").toLowerCase().trim().replace(/[^\p{L}\p{N}]+/gu, "-").replace(/^-+|-+$/g, "") || `section-${index + 1}`;
33
+ let id = base;
34
+ for (let n = 2; taken.has(id); n++) id = `${base}-${n}`;
35
+ taken.add(id);
36
+ return id;
37
+ }
38
+
39
+ /** The heading levels an attribute names, between 2 and 6: `2` by default, `2 3` for two levels. */
40
+ export function documentLevels(value: string | null | undefined): number[] {
41
+ const levels = [...new Set(String(value ?? "2").split(/[\s,]+/).map(Number).filter(level => Number.isInteger(level) && level >= 2 && level <= 6))].sort();
42
+ return levels.length ? levels : [2];
43
+ }
44
+
45
+ /**
46
+ * The rules for the writing, which stands in the page: prose.css and the
47
+ * definition table, adopted once per root the element stands in. Their
48
+ * imports (the tokens) are left out: the element's host carries the measures,
49
+ * and the writing inherits them.
50
+ */
51
+ const styledRoots = new WeakSet<Document | ShadowRoot>();
52
+ function styleRoot(root: Node) {
53
+ const target = root instanceof ShadowRoot ? root : root instanceof Document ? root : null;
54
+ if (!target || styledRoots.has(target) || typeof CSSStyleSheet === "undefined" || !("adoptedStyleSheets" in target)) return;
55
+ try {
56
+ const sheet = new CSSStyleSheet();
57
+ sheet.replaceSync([proseRules, documentRules].map(css => css.replace(/^@import[^;]*;\s*$/gm, "")).join("\n"));
58
+ target.adoptedStyleSheets = [...target.adoptedStyleSheets, sheet];
59
+ styledRoots.add(target);
60
+ } catch {
61
+ // A browser without constructable sheets keeps the page's own copy of prose.css.
62
+ }
63
+ }
64
+
65
+ /**
66
+ * @element ds-document
67
+ * @prop {string} levels - The heading levels the contents list: `2` by default, `2 3` for two.
68
+ * @prop {string} label - The contents' title: a translation key, the shared word "Contents" by default.
69
+ * @prop {boolean} literal - Show `label` as written, never looked up.
70
+ * @prop {boolean} hideContents - Leave the contents out (`hide-contents`).
71
+ *
72
+ * @slot - The writing: native headings, paragraphs, lists, tables and a
73
+ * definition table (`<dl class="ds-definitions">`), as prose. The element
74
+ * marks itself `data-ds-prose` and brings the prose sheet.
75
+ * @slot contents - Contents of the page's own, in place of the built ones.
76
+ *
77
+ * The contents list the writing's headings at `levels`, giving a heading an
78
+ * id from its words when it has none. A link scrolls to its heading, and the
79
+ * section in view is marked `aria-current="location"`. With fewer than two
80
+ * headings there are no contents.
81
+ *
82
+ * @example
83
+ * <ds-document>
84
+ * <h1>Terms</h1>
85
+ * <h2>Using the service</h2><p>…</p>
86
+ * <h2>Payments</h2><p>…</p>
87
+ * </ds-document>
88
+ */
89
+ export class DocumentPage extends LitElement {
90
+ static properties = {
91
+ levels: { type: String },
92
+ label: { type: String },
93
+ literal: { type: Boolean, reflect: true },
94
+ hideContents: { type: Boolean, attribute: "hide-contents", reflect: true },
95
+ entries: { state: true },
96
+ current: { state: true },
97
+ };
98
+
99
+ static styles = [unsafeCSS(metrics), unsafeCSS(documentSheet), unsafeCSS(styles)];
100
+
101
+ declare levels: string;
102
+ declare label: string | undefined;
103
+ declare literal: boolean;
104
+ declare hideContents: boolean;
105
+ declare entries: DocumentEntry[];
106
+ declare current: string | null;
107
+
108
+ private readonly relabel = () => this.requestUpdate();
109
+ private observer: MutationObserver | null = null;
110
+ private frame = 0;
111
+
112
+ constructor() {
113
+ super();
114
+ this.levels = "2";
115
+ this.literal = false;
116
+ this.hideContents = false;
117
+ this.entries = [];
118
+ this.current = null;
119
+ }
120
+
121
+ connectedCallback() {
122
+ super.connectedCallback();
123
+ styleRoot(this.getRootNode());
124
+ if (!this.hasAttribute("data-ds-prose")) this.setAttribute("data-ds-prose", "");
125
+ window.addEventListener("language-changed", this.relabel);
126
+ window.addEventListener("translations-loaded", this.relabel);
127
+ document.addEventListener("scroll", this.onScroll, { capture: true, passive: true });
128
+ window.addEventListener("resize", this.onScroll, { passive: true });
129
+ this.observer = new MutationObserver(() => this.collect());
130
+ this.observer.observe(this, { childList: true, subtree: true, characterData: true, attributes: true, attributeFilter: ["id"] });
131
+ this.collect();
132
+ }
133
+
134
+ disconnectedCallback() {
135
+ window.removeEventListener("language-changed", this.relabel);
136
+ window.removeEventListener("translations-loaded", this.relabel);
137
+ document.removeEventListener("scroll", this.onScroll, { capture: true });
138
+ window.removeEventListener("resize", this.onScroll);
139
+ this.observer?.disconnect();
140
+ this.observer = null;
141
+ cancelAnimationFrame(this.frame);
142
+ super.disconnectedCallback();
143
+ }
144
+
145
+ protected willUpdate(changed: Map<PropertyKey, unknown>) {
146
+ if (changed.has("levels") && this.hasUpdated) this.collect();
147
+ }
148
+
149
+ /** The headings the contents list, in the order they stand. */
150
+ get headings(): HTMLElement[] {
151
+ const levels = documentLevels(this.levels);
152
+ return [...this.querySelectorAll<HTMLElement>(levels.map(level => `h${level}`).join(","))]
153
+ .filter(heading => !heading.closest("[data-ds-not-prose]") && !heading.closest('[slot="contents"]'));
154
+ }
155
+
156
+ /** Reads the headings again: their words, levels and ids. */
157
+ collect(): void {
158
+ const taken = new Set([...this.querySelectorAll("[id]")].map(element => element.id));
159
+ const entries = this.headings.map((heading, index) => {
160
+ const text = (heading.textContent ?? "").replace(/\s+/g, " ").trim();
161
+ if (!heading.id) {
162
+ // Writing an id is a change the observer would hear; it reads the same.
163
+ heading.id = headingId(text, taken, index);
164
+ }
165
+ return { id: heading.id, text, level: Number(heading.tagName.slice(1)) };
166
+ });
167
+ const same = entries.length === this.entries.length && entries.every((entry, i) => entry.id === this.entries[i]!.id && entry.text === this.entries[i]!.text && entry.level === this.entries[i]!.level);
168
+ if (!same) this.entries = entries;
169
+ this.onScroll();
170
+ }
171
+
172
+ /**
173
+ * The section in view: the last heading at or above a fifth of the way down
174
+ * the view, or, scrolled to the foot of the page, the last heading in view.
175
+ */
176
+ private onScroll = () => {
177
+ cancelAnimationFrame(this.frame);
178
+ this.frame = requestAnimationFrame(() => {
179
+ const view = window.innerHeight || 0;
180
+ // At the foot of the page the last sections cannot reach the line: the last one in view is current.
181
+ const end = document.documentElement;
182
+ const line = view && window.scrollY > 0 && window.scrollY + view >= end.scrollHeight - 1 ? view : view / 5;
183
+ let current: string | null = null;
184
+ for (const entry of this.entries) {
185
+ const heading = this.heading(entry.id);
186
+ if (!heading) continue;
187
+ if (heading.getBoundingClientRect().top <= line) current = entry.id;
188
+ else break;
189
+ }
190
+ this.current = current ?? this.entries[0]?.id ?? null;
191
+ });
192
+ };
193
+
194
+ private heading(id: string): HTMLElement | undefined {
195
+ return this.headings.find(heading => heading.id === id);
196
+ }
197
+
198
+ private follow(event: MouseEvent, id: string) {
199
+ if (event.defaultPrevented || event.button !== 0 || event.metaKey || event.ctrlKey || event.shiftKey || event.altKey) return;
200
+ const heading = this.heading(id);
201
+ if (!heading) return;
202
+ event.preventDefault();
203
+ const smooth = !window.matchMedia?.("(prefers-reduced-motion: reduce)").matches;
204
+ heading.scrollIntoView({ block: "start", behavior: smooth ? "smooth" : "auto" });
205
+ if (!heading.hasAttribute("tabindex")) heading.setAttribute("tabindex", "-1");
206
+ heading.focus({ preventScroll: true });
207
+ history.replaceState(history.state, "", `#${id}`);
208
+ this.current = id;
209
+ }
210
+
211
+ render() {
212
+ const label = this.literal ? this.label || CONTENTS_LABEL : getText(this.label || CONTENTS_LABEL) || this.label || CONTENTS_LABEL;
213
+ const top = Math.min(...this.entries.map(entry => entry.level));
214
+ const own = [...this.children].some(child => child.getAttribute("slot") === "contents");
215
+ const showContents = !this.hideContents && (own || this.entries.length >= 2);
216
+ return html`<div class="ds-document" part="document">
217
+ <nav class="ds-document__toc" part="contents" aria-labelledby="contents-title" ?hidden=${!showContents}>
218
+ <div class="ds-document__contents">
219
+ <p class="ds-document__toc-title" id="contents-title" part="contents-title">${label}</p>
220
+ <slot name="contents" @slotchange=${this.relabel}>
221
+ <ol class="ds-document__toc-list" part="contents-list">
222
+ ${this.entries.map(entry => html`<li class=${entry.level > top ? "ds-document__toc-sub" : nothing}>
223
+ <a href="#${entry.id}" aria-current=${this.current === entry.id ? "location" : nothing} @click=${(event: MouseEvent) => this.follow(event, entry.id)}>${entry.text}</a>
224
+ </li>`)}
225
+ </ol>
226
+ </slot>
227
+ </div>
228
+ </nav>
229
+ <div class="ds-document__body" part="body"><slot></slot></div>
230
+ </div>`;
231
+ }
232
+ }
233
+
234
+ define("ds-document", DocumentPage);
235
+
236
+ declare global {
237
+ interface HTMLElementTagNameMap {
238
+ "ds-document": DocumentPage;
239
+ }
240
+ }
@@ -0,0 +1,165 @@
1
+ // ds-footer.ts
2
+ // A site footer: the brand, columns of links, the language and theme, and the
3
+ // copyright. Drawn by 1-root/footer.css, the same classes a page without
4
+ // scripts writes.
5
+
6
+ import { LitElement, html, nothing, unsafeCSS } from "lit";
7
+ import { getText } from "../0-face/i18n";
8
+ import { define } from "../0-face/define";
9
+ import "../2-core/ds-cycle";
10
+ import metrics from "../1-root/component-metrics.css?inline";
11
+ import controls from "../1-root/controls.css?inline";
12
+ import styles from "./styles/ds-footer.css?inline";
13
+
14
+ /** A link in a footer column. */
15
+ export interface FooterLink {
16
+ /** The words: a translation key, or as written with the footer's `literal`. */
17
+ label: string;
18
+ href: string;
19
+ /** Opens elsewhere: in a new tab, with no referrer. */
20
+ external?: boolean;
21
+ /** The page being read: `aria-current="page"`. */
22
+ current?: boolean;
23
+ }
24
+
25
+ /** A footer column: a heading and its links. */
26
+ export interface FooterColumn {
27
+ heading?: string;
28
+ links: FooterLink[];
29
+ }
30
+
31
+ /** The settings a footer offers, each a `ds-cycle` of that type. */
32
+ export type FooterPreference = "language" | "theme";
33
+ const PREFERENCES: readonly FooterPreference[] = ["language", "theme"];
34
+
35
+ /** The preferences named by an attribute: every one when it is present but empty. */
36
+ export function footerPreferences(value: string | null | undefined): FooterPreference[] {
37
+ if (value == null || value === "false") return [];
38
+ const named = value.split(/[\s,]+/).filter(Boolean);
39
+ if (!named.length || named.includes("true")) return [...PREFERENCES];
40
+ return PREFERENCES.filter(name => named.includes(name));
41
+ }
42
+
43
+ /**
44
+ * @element ds-footer
45
+ * @prop {string} brand - The site's name, a link home: a translation key, or
46
+ * the words as they stand with `literal`. The `brand` slot takes its place.
47
+ * @prop {string} href - Where the brand links. `/` by default.
48
+ * @prop {string} tagline - A line about the site under the brand.
49
+ * @prop {FooterColumn[]} columns - The columns of links, eight squares each.
50
+ * @prop {string} label - The columns' accessible name, as a navigation; without it they are plain lists.
51
+ * @prop {string} owner - Who holds the copyright: the brand by default.
52
+ * @prop {number} year - The copyright's year: this year by default.
53
+ * @prop {string} preferences - `language`, `theme` or both, as `ds-cycle`
54
+ * buttons at the end of the last row; present but empty, both.
55
+ * @prop {boolean} literal - Show the words as written, never looked up.
56
+ *
57
+ * @slot brand - The brand, when it is more than words: a logo, a link of the page's own.
58
+ * @slot preferences - Controls of the page's own beside or in place of the cycles.
59
+ * @slot legal - The last line, in place of the copyright.
60
+ *
61
+ * @example
62
+ * <ds-footer brand="Name" tagline="What it does" preferences literal
63
+ * columns='[{"heading":"Product","links":[{"label":"Download","href":"/download"}]}]'>
64
+ * </ds-footer>
65
+ */
66
+ export class Footer extends LitElement {
67
+ static properties = {
68
+ brand: { type: String },
69
+ href: { type: String },
70
+ tagline: { type: String },
71
+ columns: { type: Array },
72
+ label: { type: String },
73
+ owner: { type: String },
74
+ year: { type: Number },
75
+ preferences: { type: String },
76
+ literal: { type: Boolean, reflect: true },
77
+ };
78
+
79
+ static styles = [unsafeCSS(metrics), unsafeCSS(controls), unsafeCSS(styles)];
80
+
81
+ declare brand: string | undefined;
82
+ declare href: string;
83
+ declare tagline: string | undefined;
84
+ declare columns: FooterColumn[];
85
+ declare label: string | undefined;
86
+ declare owner: string | undefined;
87
+ declare year: number | undefined;
88
+ declare preferences: string | null | undefined;
89
+ declare literal: boolean;
90
+
91
+ private readonly relabel = () => this.requestUpdate();
92
+
93
+ constructor() {
94
+ super();
95
+ this.href = "/";
96
+ this.columns = [];
97
+ this.literal = false;
98
+ }
99
+
100
+ connectedCallback() {
101
+ super.connectedCallback();
102
+ window.addEventListener("language-changed", this.relabel);
103
+ window.addEventListener("translations-loaded", this.relabel);
104
+ }
105
+
106
+ disconnectedCallback() {
107
+ window.removeEventListener("language-changed", this.relabel);
108
+ window.removeEventListener("translations-loaded", this.relabel);
109
+ super.disconnectedCallback();
110
+ }
111
+
112
+ private words(value: string | undefined): string {
113
+ if (!value) return "";
114
+ return this.literal ? value : getText(value) || value;
115
+ }
116
+
117
+ private slotted(name: string): boolean {
118
+ return [...this.children].some(node => node.getAttribute("slot") === name);
119
+ }
120
+
121
+ private link(link: FooterLink) {
122
+ return html`<li><a href=${link.href} aria-current=${link.current ? "page" : nothing}
123
+ target=${link.external ? "_blank" : nothing} rel=${link.external ? "noopener noreferrer" : nothing}>${this.words(link.label)}</a></li>`;
124
+ }
125
+
126
+ render() {
127
+ const columns = (Array.isArray(this.columns) ? this.columns : []).filter(column => column && Array.isArray(column.links));
128
+ const preferences = footerPreferences(this.preferences);
129
+ const hasPreferences = preferences.length > 0 || this.slotted("preferences");
130
+ const owner = this.owner ? this.words(this.owner) : this.words(this.brand);
131
+ const year = Number.isFinite(this.year) ? this.year : new Date().getFullYear();
132
+ const brandSlotted = this.slotted("brand");
133
+ const hasBrand = brandSlotted || Boolean(this.brand) || Boolean(this.tagline);
134
+ const list = columns.map(column => html`<div class="ds-footer__column" part="column">
135
+ ${column.heading ? html`<h2 class="ds-footer__heading" part="heading">${this.words(column.heading)}</h2>` : nothing}
136
+ <ul class="ds-footer__links">${column.links.map(link => this.link(link))}</ul>
137
+ </div>`);
138
+ return html`<footer class="ds-footer" part="footer">
139
+ <div class="ds-footer__brand" part="brand" ?hidden=${!hasBrand}>
140
+ <slot name="brand" @slotchange=${this.relabel}>${this.brand ? html`<a class="ds-footer__mark" href=${this.href || "/"}>${this.words(this.brand)}</a>` : nothing}</slot>
141
+ ${this.tagline ? html`<p class="ds-footer__tagline" part="tagline">${this.words(this.tagline)}</p>` : nothing}
142
+ </div>
143
+ ${columns.length
144
+ ? this.label
145
+ ? html`<nav class="ds-footer__columns" part="columns" aria-label=${this.words(this.label)}>${list}</nav>`
146
+ : html`<div class="ds-footer__columns" part="columns">${list}</div>`
147
+ : nothing}
148
+ <div class="ds-footer__base" part="base">
149
+ <p class="ds-footer__legal" part="legal"><slot name="legal" @slotchange=${this.relabel}>${owner ? `© ${year} ${owner}` : `© ${year}`}</slot></p>
150
+ <div class="ds-footer__preferences" part="preferences" ?hidden=${!hasPreferences}>
151
+ ${preferences.map(type => html`<ds-cycle type=${type}></ds-cycle>`)}
152
+ <slot name="preferences" @slotchange=${this.relabel}></slot>
153
+ </div>
154
+ </div>
155
+ </footer>`;
156
+ }
157
+ }
158
+
159
+ define("ds-footer", Footer);
160
+
161
+ declare global {
162
+ interface HTMLElementTagNameMap {
163
+ "ds-footer": Footer;
164
+ }
165
+ }
@@ -1,74 +1,54 @@
1
- // ds-grid.ts
2
- // Simple grid layout component
3
-
4
1
  import { LitElement, html, unsafeCSS } from "lit";
5
- import { detectMobileDevice } from "../0-face/device";
2
+ import { styleMap } from "lit/directives/style-map.js";
3
+ import { define } from "../0-face/define";
6
4
  import styles from "./styles/ds-grid.css?inline";
7
5
 
8
- declare global {
9
- interface CustomElementRegistry {
10
- define(name: string, constructor: typeof LitElement): void;
11
- }
12
- var customElements: CustomElementRegistry;
13
- }
6
+ export type GridPattern = "grid" | "lines" | "columns" | "dots" | "none";
7
+ const patterns = new Set<GridPattern>(["grid", "lines", "columns", "dots", "none"]);
14
8
 
9
+ /** Decorative paper or an alignment overlay; never arranges or captures content. */
15
10
  export class Grid extends LitElement {
16
11
  static properties = {
17
- align: { type: String },
12
+ align: { type: String, reflect: true },
13
+ pattern: { type: String, reflect: true },
14
+ size: { type: Number },
15
+ rowSize: { type: Number, attribute: "row-size" },
16
+ color: { type: String },
17
+ paper: { type: String },
18
+ contained: { type: Boolean, reflect: true },
18
19
  };
19
-
20
- align?: string;
21
- private resizeObserver?: () => void;
22
- private resizeTimeout?: any;
23
-
20
+ declare align: "left" | "center" | "right";
21
+ declare pattern: GridPattern;
22
+ declare size: number;
23
+ declare rowSize: number | undefined;
24
+ declare color: string;
25
+ declare paper: string;
26
+ declare contained: boolean;
24
27
  static styles = unsafeCSS(styles);
25
28
 
26
- connectedCallback() {
27
- super.connectedCallback();
28
- this.updateMobileClass();
29
-
30
- // Listen for resize events to update mobile class
31
- this.resizeObserver = () => {
32
- if (this.resizeTimeout) {
33
- clearTimeout(this.resizeTimeout);
34
- }
35
- this.resizeTimeout = setTimeout(() => {
36
- this.updateMobileClass();
37
- }, 100);
38
- };
39
- window.addEventListener("resize", this.resizeObserver);
40
- }
41
-
42
- disconnectedCallback() {
43
- super.disconnectedCallback();
44
- if (this.resizeObserver) {
45
- window.removeEventListener("resize", this.resizeObserver);
46
- }
47
- if (this.resizeTimeout) {
48
- clearTimeout(this.resizeTimeout);
49
- }
50
- }
51
-
52
- private updateMobileClass() {
53
- const isMobile = detectMobileDevice();
54
- if (isMobile) {
55
- this.classList.add("mobile");
56
- this.classList.remove("desktop");
57
- } else {
58
- this.classList.add("desktop");
59
- this.classList.remove("mobile");
60
- }
29
+ constructor() {
30
+ super();
31
+ this.align = "center";
32
+ this.pattern = "grid";
33
+ this.size = 20;
34
+ this.rowSize = undefined;
35
+ this.color = "";
36
+ this.paper = "";
37
+ this.contained = false;
61
38
  }
62
39
 
63
40
  render() {
64
- return html``;
41
+ const size = Number.isFinite(this.size) && this.size > 0 ? this.size : 20;
42
+ const row = Number.isFinite(this.rowSize) && this.rowSize! > 0 ? this.rowSize! : size;
43
+ return html`<div aria-hidden="true" class="paper" data-pattern=${patterns.has(this.pattern) ? this.pattern : "grid"}
44
+ style=${styleMap({
45
+ "--pitch-x": `${size}px`,
46
+ "--pitch-y": `${row}px`,
47
+ "--ink": this.color || "var(--ds-grid-color, color-mix(in srgb, var(--ds-text-color, var(--text-color, currentColor)) 12%, transparent))",
48
+ "--paper": this.paper || "var(--ds-grid-paper, transparent)",
49
+ })}></div>`;
65
50
  }
66
51
  }
67
52
 
68
- customElements.define("ds-grid", Grid);
69
-
70
- declare global {
71
- interface HTMLElementTagNameMap {
72
- "ds-grid": Grid;
73
- }
74
- }
53
+ define("ds-grid", Grid);
54
+ declare global { interface HTMLElementTagNameMap { "ds-grid": Grid } }