@heycys/gallery 0.0.0-stage → 0.1.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 (785) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +50 -2
  3. package/THIRD-PARTY-NOTICES.md +3253 -0
  4. package/assets/writing-preferences.md +107 -0
  5. package/bin/gallery.mjs +10 -0
  6. package/browser/editor/components/bookmark/icons.mjs +6 -0
  7. package/browser/editor/components/bookmark/index.mjs +80 -0
  8. package/browser/editor/components/bookmark/page.mjs +147 -0
  9. package/browser/editor/components/builders.mjs +19 -0
  10. package/browser/editor/components/callout/index.mjs +39 -0
  11. package/browser/editor/components/callout/page.mjs +13 -0
  12. package/browser/editor/components/code/index.mjs +327 -0
  13. package/browser/editor/components/code/page.mjs +561 -0
  14. package/browser/editor/components/colors.mjs +50 -0
  15. package/browser/editor/components/columns/index.mjs +104 -0
  16. package/browser/editor/components/columns/page.mjs +297 -0
  17. package/browser/editor/components/details/index.mjs +72 -0
  18. package/browser/editor/components/details/page.mjs +86 -0
  19. package/browser/editor/components/dialog/index.mjs +83 -0
  20. package/browser/editor/components/dialog/page.mjs +219 -0
  21. package/browser/editor/components/divider/index.mjs +48 -0
  22. package/browser/editor/components/embed/icons.mjs +11 -0
  23. package/browser/editor/components/embed/index.mjs +123 -0
  24. package/browser/editor/components/embed/page.mjs +309 -0
  25. package/browser/editor/components/figure/index.mjs +87 -0
  26. package/browser/editor/components/figure/page.mjs +33 -0
  27. package/browser/editor/components/file/icons.mjs +14 -0
  28. package/browser/editor/components/file/index.mjs +77 -0
  29. package/browser/editor/components/file/page.mjs +114 -0
  30. package/browser/editor/components/flowchart/add.mjs +123 -0
  31. package/browser/editor/components/flowchart/index.mjs +246 -0
  32. package/browser/editor/components/flowchart/page.mjs +453 -0
  33. package/browser/editor/components/heading/index.mjs +51 -0
  34. package/browser/editor/components/highlight/index.mjs +79 -0
  35. package/browser/editor/components/icon/index.mjs +57 -0
  36. package/browser/editor/components/icon/page.mjs +286 -0
  37. package/browser/editor/components/icons.mjs +45 -0
  38. package/browser/editor/components/image/crop.mjs +189 -0
  39. package/browser/editor/components/image/index.mjs +104 -0
  40. package/browser/editor/components/image/page.mjs +385 -0
  41. package/browser/editor/components/image/viewer.mjs +213 -0
  42. package/browser/editor/components/installed/index.mjs +133 -0
  43. package/browser/editor/components/installed/page.mjs +422 -0
  44. package/browser/editor/components/installed/served.mjs +35 -0
  45. package/browser/editor/components/kit.mjs +64 -0
  46. package/browser/editor/components/list/index.mjs +194 -0
  47. package/browser/editor/components/list/join.mjs +68 -0
  48. package/browser/editor/components/list/numbers.mjs +107 -0
  49. package/browser/editor/components/list/page.mjs +632 -0
  50. package/browser/editor/components/math/index.mjs +88 -0
  51. package/browser/editor/components/math/page.mjs +236 -0
  52. package/browser/editor/components/math/tex-logo.mjs +6 -0
  53. package/browser/editor/components/media/icons.mjs +19 -0
  54. package/browser/editor/components/media/page.mjs +162 -0
  55. package/browser/editor/components/media/parts.mjs +60 -0
  56. package/browser/editor/components/media/size.mjs +20 -0
  57. package/browser/editor/components/media/toolbar.mjs +37 -0
  58. package/browser/editor/components/media/write.mjs +7 -0
  59. package/browser/editor/components/pages.mjs +46 -0
  60. package/browser/editor/components/paragraph/index.mjs +43 -0
  61. package/browser/editor/components/paragraph/page.mjs +52 -0
  62. package/browser/editor/components/placeholder-bar.mjs +17 -0
  63. package/browser/editor/components/placeholder.mjs +128 -0
  64. package/browser/editor/components/quote/index.mjs +33 -0
  65. package/browser/editor/components/registry.mjs +833 -0
  66. package/browser/editor/components/rows.mjs +16 -0
  67. package/browser/editor/components/section/index.mjs +41 -0
  68. package/browser/editor/components/section/page.mjs +141 -0
  69. package/browser/editor/components/sheets/index.mjs +137 -0
  70. package/browser/editor/components/sheets/page.mjs +227 -0
  71. package/browser/editor/components/sheets/pills.mjs +226 -0
  72. package/browser/editor/components/table/grid.mjs +73 -0
  73. package/browser/editor/components/table/index.mjs +306 -0
  74. package/browser/editor/components/table/page.mjs +672 -0
  75. package/browser/editor/components/table/slots.mjs +41 -0
  76. package/browser/editor/components/widget/index.mjs +50 -0
  77. package/browser/editor/page/annotate/anchors.mjs +229 -0
  78. package/browser/editor/page/annotate/card.mjs +102 -0
  79. package/browser/editor/page/annotate/index.mjs +1629 -0
  80. package/browser/editor/page/at-menu/index.mjs +317 -0
  81. package/browser/editor/page/autosave.mjs +977 -0
  82. package/browser/editor/page/beside.mjs +21 -0
  83. package/browser/editor/page/block-info.mjs +63 -0
  84. package/browser/editor/page/block-menu/colors.mjs +82 -0
  85. package/browser/editor/page/block-menu/index.mjs +215 -0
  86. package/browser/editor/page/blocks.mjs +246 -0
  87. package/browser/editor/page/caret.mjs +679 -0
  88. package/browser/editor/page/chip-fills.mjs +126 -0
  89. package/browser/editor/page/clipboard/import/colors.mjs +192 -0
  90. package/browser/editor/page/clipboard/import/html.mjs +792 -0
  91. package/browser/editor/page/clipboard/import/inline.mjs +232 -0
  92. package/browser/editor/page/clipboard/import/languages.mjs +42 -0
  93. package/browser/editor/page/clipboard/import/markdown.mjs +760 -0
  94. package/browser/editor/page/clipboard/import/math.mjs +100 -0
  95. package/browser/editor/page/clipboard/import/office.mjs +245 -0
  96. package/browser/editor/page/clipboard/import/read.mjs +120 -0
  97. package/browser/editor/page/clipboard/import/rich.mjs +29 -0
  98. package/browser/editor/page/clipboard/import/to-blocks.mjs +290 -0
  99. package/browser/editor/page/clipboard/index.mjs +797 -0
  100. package/browser/editor/page/clipboard/own/blocks.mjs +202 -0
  101. package/browser/editor/page/clipboard/own/chart-keys.mjs +58 -0
  102. package/browser/editor/page/clipboard/own/describe.mjs +115 -0
  103. package/browser/editor/page/clipboard/own/export.mjs +167 -0
  104. package/browser/editor/page/clipboard/own/ids.mjs +39 -0
  105. package/browser/editor/page/clipboard/own/index.mjs +13 -0
  106. package/browser/editor/page/clipboard/own/rules.mjs +44 -0
  107. package/browser/editor/page/clipboard/own/selection.mjs +159 -0
  108. package/browser/editor/page/clipboard/own/writers.mjs +326 -0
  109. package/browser/editor/page/columns/index.mjs +360 -0
  110. package/browser/editor/page/commit.mjs +1798 -0
  111. package/browser/editor/page/conflicts.mjs +269 -0
  112. package/browser/editor/page/convert.mjs +830 -0
  113. package/browser/editor/page/core.mjs +1655 -0
  114. package/browser/editor/page/drag/drop.mjs +307 -0
  115. package/browser/editor/page/drag/index.mjs +335 -0
  116. package/browser/editor/page/drag/preview.mjs +121 -0
  117. package/browser/editor/page/edge-scroll.mjs +50 -0
  118. package/browser/editor/page/editor.mjs +1725 -0
  119. package/browser/editor/page/emoji-picker/emoji-tab.mjs +278 -0
  120. package/browser/editor/page/emoji-picker/glyph-html.mjs +26 -0
  121. package/browser/editor/page/emoji-picker/grid.mjs +79 -0
  122. package/browser/editor/page/emoji-picker/icon-tab.mjs +217 -0
  123. package/browser/editor/page/emoji-picker/icons.mjs +32 -0
  124. package/browser/editor/page/emoji-picker/index.mjs +164 -0
  125. package/browser/editor/page/emoji-picker/styles.mjs +2 -0
  126. package/browser/editor/page/emoji-picker/support.mjs +202 -0
  127. package/browser/editor/page/emoji-picker/upload.mjs +235 -0
  128. package/browser/editor/page/export-report.mjs +23 -0
  129. package/browser/editor/page/fills.mjs +60 -0
  130. package/browser/editor/page/find/index.mjs +107 -0
  131. package/browser/editor/page/flags.mjs +70 -0
  132. package/browser/editor/page/format-bar/bar.mjs +448 -0
  133. package/browser/editor/page/format-bar/brush.mjs +77 -0
  134. package/browser/editor/page/format-bar/colors.mjs +46 -0
  135. package/browser/editor/page/format-bar/index.mjs +404 -0
  136. package/browser/editor/page/formula/index.mjs +236 -0
  137. package/browser/editor/page/formula/panel.mjs +336 -0
  138. package/browser/editor/page/formula/symbols.mjs +156 -0
  139. package/browser/editor/page/frame.mjs +74 -0
  140. package/browser/editor/page/frames.mjs +196 -0
  141. package/browser/editor/page/geometry.mjs +400 -0
  142. package/browser/editor/page/gesture.mjs +45 -0
  143. package/browser/editor/page/handle/index.mjs +639 -0
  144. package/browser/editor/page/handle-sizes.mjs +14 -0
  145. package/browser/editor/page/hints/index.mjs +84 -0
  146. package/browser/editor/page/history.mjs +401 -0
  147. package/browser/editor/page/insert/index.mjs +243 -0
  148. package/browser/editor/page/kept.mjs +38 -0
  149. package/browser/editor/page/links/address.mjs +40 -0
  150. package/browser/editor/page/links/index.mjs +866 -0
  151. package/browser/editor/page/links/pages.mjs +131 -0
  152. package/browser/editor/page/links/views.mjs +369 -0
  153. package/browser/editor/page/look.mjs +65 -0
  154. package/browser/editor/page/made.mjs +24 -0
  155. package/browser/editor/page/margin.mjs +352 -0
  156. package/browser/editor/page/markdown/index.mjs +88 -0
  157. package/browser/editor/page/markdown/rules.mjs +33 -0
  158. package/browser/editor/page/marks.mjs +377 -0
  159. package/browser/editor/page/media-menu/index.mjs +158 -0
  160. package/browser/editor/page/menu.mjs +500 -0
  161. package/browser/editor/page/merge.mjs +100 -0
  162. package/browser/editor/page/notices.mjs +142 -0
  163. package/browser/editor/page/offered.mjs +32 -0
  164. package/browser/editor/page/outline/folds.mjs +52 -0
  165. package/browser/editor/page/outline/index.mjs +697 -0
  166. package/browser/editor/page/outline/list.mjs +172 -0
  167. package/browser/editor/page/outline/read.mjs +201 -0
  168. package/browser/editor/page/outline/strip.mjs +281 -0
  169. package/browser/editor/page/outline/tree.mjs +248 -0
  170. package/browser/editor/page/overlay-layer.mjs +227 -0
  171. package/browser/editor/page/overlays.mjs +205 -0
  172. package/browser/editor/page/own.mjs +28 -0
  173. package/browser/editor/page/pads.mjs +71 -0
  174. package/browser/editor/page/page-objects.mjs +105 -0
  175. package/browser/editor/page/panel.mjs +64 -0
  176. package/browser/editor/page/placement.mjs +58 -0
  177. package/browser/editor/page/post.mjs +41 -0
  178. package/browser/editor/page/present-links.mjs +50 -0
  179. package/browser/editor/page/quiet.mjs +48 -0
  180. package/browser/editor/page/resize/index.mjs +327 -0
  181. package/browser/editor/page/select-all/index.mjs +262 -0
  182. package/browser/editor/page/selection/delete.mjs +59 -0
  183. package/browser/editor/page/selection/index.mjs +157 -0
  184. package/browser/editor/page/selection/marquee.mjs +174 -0
  185. package/browser/editor/page/session.mjs +117 -0
  186. package/browser/editor/page/slash-menu/index.mjs +291 -0
  187. package/browser/editor/page/storage.mjs +48 -0
  188. package/browser/editor/page/sync-state.mjs +267 -0
  189. package/browser/editor/page/table/aligns.mjs +29 -0
  190. package/browser/editor/page/table/cell-bar.mjs +138 -0
  191. package/browser/editor/page/table/cells.mjs +527 -0
  192. package/browser/editor/page/table/icons.mjs +40 -0
  193. package/browser/editor/page/table/index.mjs +985 -0
  194. package/browser/editor/page/table/lists.mjs +187 -0
  195. package/browser/editor/page/table/widths.mjs +308 -0
  196. package/browser/editor/page/tex.mjs +32 -0
  197. package/browser/editor/page/text-select/index.mjs +656 -0
  198. package/browser/editor/page/tooltip.mjs +98 -0
  199. package/browser/editor/page/type-grid.mjs +82 -0
  200. package/browser/editor/page/typing/code-edges.mjs +228 -0
  201. package/browser/editor/page/typing/index.mjs +276 -0
  202. package/browser/editor/page/typing/leave.mjs +68 -0
  203. package/browser/editor/page/ui.mjs +160 -0
  204. package/browser/shared/annotations.mjs +571 -0
  205. package/browser/shared/code-folds.mjs +10 -0
  206. package/browser/shared/code-languages.mjs +70 -0
  207. package/browser/shared/code-lines.mjs +30 -0
  208. package/browser/shared/colors.mjs +28 -0
  209. package/browser/shared/component-catalog.mjs +559 -0
  210. package/browser/shared/components/bookmark.mjs +26 -0
  211. package/browser/shared/components/callout.mjs +7 -0
  212. package/browser/shared/components/chart.mjs +20 -0
  213. package/browser/shared/components/code.mjs +37 -0
  214. package/browser/shared/components/columns.mjs +16 -0
  215. package/browser/shared/components/details.mjs +15 -0
  216. package/browser/shared/components/dialog.mjs +28 -0
  217. package/browser/shared/components/diff.mjs +18 -0
  218. package/browser/shared/components/divider.mjs +6 -0
  219. package/browser/shared/components/embed.mjs +25 -0
  220. package/browser/shared/components/figure.mjs +14 -0
  221. package/browser/shared/components/file.mjs +23 -0
  222. package/browser/shared/components/heading.mjs +6 -0
  223. package/browser/shared/components/highlight.mjs +9 -0
  224. package/browser/shared/components/icon.mjs +18 -0
  225. package/browser/shared/components/image.mjs +39 -0
  226. package/browser/shared/components/index.mjs +342 -0
  227. package/browser/shared/components/installed.mjs +162 -0
  228. package/browser/shared/components/list.mjs +146 -0
  229. package/browser/shared/components/math.mjs +49 -0
  230. package/browser/shared/components/mention.mjs +33 -0
  231. package/browser/shared/components/page.mjs +37 -0
  232. package/browser/shared/components/paragraph.mjs +9 -0
  233. package/browser/shared/components/quote.mjs +6 -0
  234. package/browser/shared/components/section.mjs +8 -0
  235. package/browser/shared/components/sheets.mjs +80 -0
  236. package/browser/shared/components/state.mjs +20 -0
  237. package/browser/shared/components/table.mjs +49 -0
  238. package/browser/shared/components/text.mjs +14 -0
  239. package/browser/shared/components/widget.mjs +10 -0
  240. package/browser/shared/copy-ids.mjs +72 -0
  241. package/browser/shared/css-references.mjs +110 -0
  242. package/browser/shared/emoji/custom.mjs +91 -0
  243. package/browser/shared/emoji/data/LICENSE-mingcute.txt +202 -0
  244. package/browser/shared/emoji/data/LICENSE-tabler.txt +21 -0
  245. package/browser/shared/emoji/data/README.md +26 -0
  246. package/browser/shared/emoji/data/categories.json +1 -0
  247. package/browser/shared/emoji/data/icons.json +1 -0
  248. package/browser/shared/emoji/data/keywords-en.json +1 -0
  249. package/browser/shared/emoji/data/keywords-zh.json +1 -0
  250. package/browser/shared/emoji/data/names.json +1 -0
  251. package/browser/shared/emoji/data/positions.json +1 -0
  252. package/browser/shared/emoji/data/twemoji-index.json +1 -0
  253. package/browser/shared/emoji/data/twemoji-svg.bin +0 -0
  254. package/browser/shared/emoji/data.mjs +196 -0
  255. package/browser/shared/emoji/emoji.mjs +37 -0
  256. package/browser/shared/emoji/glyphs.mjs +134 -0
  257. package/browser/shared/emoji/icon-value.mjs +90 -0
  258. package/browser/shared/escape.mjs +20 -0
  259. package/browser/shared/export-wrap.mjs +89 -0
  260. package/browser/shared/files.mjs +33 -0
  261. package/browser/shared/html-tree.mjs +53 -0
  262. package/browser/shared/http.mjs +22 -0
  263. package/browser/shared/i18n/en.mjs +1164 -0
  264. package/browser/shared/i18n/index.mjs +132 -0
  265. package/browser/shared/ids.mjs +24 -0
  266. package/browser/shared/import-types.mjs +23 -0
  267. package/browser/shared/inline-spacing.mjs +97 -0
  268. package/browser/shared/layers.mjs +42 -0
  269. package/browser/shared/media.mjs +162 -0
  270. package/browser/shared/new-names.mjs +64 -0
  271. package/browser/shared/number-reading.mjs +92 -0
  272. package/browser/shared/old-names.mjs +143 -0
  273. package/browser/shared/page-address.mjs +140 -0
  274. package/browser/shared/page-links.mjs +86 -0
  275. package/browser/shared/paths.mjs +73 -0
  276. package/browser/shared/preferences.mjs +110 -0
  277. package/browser/shared/preview-server.mjs +247 -0
  278. package/browser/shared/qa-levels.mjs +93 -0
  279. package/browser/shared/reading-place.mjs +91 -0
  280. package/browser/shared/renamed-storage.mjs +220 -0
  281. package/browser/shared/reports.mjs +46 -0
  282. package/browser/shared/search.mjs +85 -0
  283. package/browser/shared/session.mjs +76 -0
  284. package/browser/shared/table-chart.mjs +113 -0
  285. package/browser/shared/table-hides.mjs +120 -0
  286. package/browser/shared/table-slots.mjs +75 -0
  287. package/browser/shared/words.mjs +23 -0
  288. package/browser/shared/workspace.mjs +535 -0
  289. package/browser/shared/writing-preferences.mjs +68 -0
  290. package/browser/shared/zoom.mjs +57 -0
  291. package/dist/chunk-2B5E4CDJ.mjs +2 -0
  292. package/dist/chunk-2PBALTR3.mjs +57 -0
  293. package/dist/chunk-342HXE3Q.mjs +2 -0
  294. package/dist/chunk-3LA3EMDE.mjs +15 -0
  295. package/dist/chunk-43B75J5T.mjs +2 -0
  296. package/dist/chunk-4K5KC6V2.mjs +2 -0
  297. package/dist/chunk-5FRMCDPY.mjs +16 -0
  298. package/dist/chunk-5L7RYZCL.mjs +2 -0
  299. package/dist/chunk-5LEK2CBS.mjs +2 -0
  300. package/dist/chunk-5OFN5AHC.mjs +2 -0
  301. package/dist/chunk-5SIYS5HN.mjs +2 -0
  302. package/dist/chunk-5TEK3RAD.mjs +2 -0
  303. package/dist/chunk-6CYG3Z4V.mjs +2 -0
  304. package/dist/chunk-6U2SLSDN.mjs +3 -0
  305. package/dist/chunk-742D2WWJ.mjs +19 -0
  306. package/dist/chunk-7GHT2UCA.mjs +15 -0
  307. package/dist/chunk-7QQBR7PB.mjs +2 -0
  308. package/dist/chunk-A55HN5OK.mjs +2 -0
  309. package/dist/chunk-ACOPDCNB.mjs +2 -0
  310. package/dist/chunk-AGDILNWB.mjs +2 -0
  311. package/dist/chunk-ATCJYAR4.mjs +2 -0
  312. package/dist/chunk-B3VTYBYR.mjs +960 -0
  313. package/dist/chunk-C564NU2H.mjs +77 -0
  314. package/dist/chunk-C7HWOBIF.mjs +2 -0
  315. package/dist/chunk-DB4WKGYF.mjs +7 -0
  316. package/dist/chunk-E7VYDG2X.mjs +2 -0
  317. package/dist/chunk-EUX7IC5J.mjs +48 -0
  318. package/dist/chunk-EVJ3BX3M.mjs +2 -0
  319. package/dist/chunk-EZY3WC6Z.mjs +15 -0
  320. package/dist/chunk-FQGQH4KM.mjs +2 -0
  321. package/dist/chunk-G7TOXONE.mjs +6 -0
  322. package/dist/chunk-GPF4YWWB.mjs +9 -0
  323. package/dist/chunk-GRAXKKG4.mjs +2 -0
  324. package/dist/chunk-GYQV7Y4J.mjs +120 -0
  325. package/dist/chunk-HMHK3EQ6.mjs +2 -0
  326. package/dist/chunk-HQQMJCQJ.mjs +10 -0
  327. package/dist/chunk-HYMEEXKN.mjs +4 -0
  328. package/dist/chunk-IERUOGC3.mjs +6 -0
  329. package/dist/chunk-ITNLYXXV.mjs +3 -0
  330. package/dist/chunk-L4DVONOG.mjs +2 -0
  331. package/dist/chunk-LAE5NQ4B.mjs +2 -0
  332. package/dist/chunk-LC7YNQFG.mjs +2 -0
  333. package/dist/chunk-LHTFLRB6.mjs +4 -0
  334. package/dist/chunk-LKX55H76.mjs +2 -0
  335. package/dist/chunk-MAFIGVXY.mjs +2 -0
  336. package/dist/chunk-NFIBI4IP.mjs +26 -0
  337. package/dist/chunk-NSKUTQ5J.mjs +5 -0
  338. package/dist/chunk-O52JMOCZ.mjs +2 -0
  339. package/dist/chunk-P2CAZPDP.mjs +3 -0
  340. package/dist/chunk-QAIHRH3I.mjs +13 -0
  341. package/dist/chunk-QMQUXTU4.mjs +12 -0
  342. package/dist/chunk-QR6A54KJ.mjs +3 -0
  343. package/dist/chunk-QVWVFC5K.mjs +6 -0
  344. package/dist/chunk-QYKCJ7FG.mjs +8 -0
  345. package/dist/chunk-QZY6Q64C.mjs +2 -0
  346. package/dist/chunk-TDQP3DKQ.mjs +10 -0
  347. package/dist/chunk-TMYZB6AV.mjs +2 -0
  348. package/dist/chunk-TX6JH7TR.mjs +2 -0
  349. package/dist/chunk-U3SSPL4K.mjs +8 -0
  350. package/dist/chunk-UH4SIXTR.mjs +2 -0
  351. package/dist/chunk-UNUEWH4S.mjs +2 -0
  352. package/dist/chunk-UXUK4PMC.mjs +27 -0
  353. package/dist/chunk-V4CPWKMZ.mjs +2 -0
  354. package/dist/chunk-V6XZ4VIR.mjs +2 -0
  355. package/dist/chunk-VACRB2NE.mjs +3 -0
  356. package/dist/chunk-W63L7367.mjs +7 -0
  357. package/dist/chunk-W7CXPCRV.mjs +6 -0
  358. package/dist/chunk-W7XHE4CT.mjs +2 -0
  359. package/dist/chunk-XINNG4F2.mjs +4 -0
  360. package/dist/chunk-Y34NR5JL.mjs +2 -0
  361. package/dist/chunk-YEY3RSFQ.mjs +2 -0
  362. package/dist/chunk-YL2DPWVS.mjs +4 -0
  363. package/dist/chunk-YXAUQPVK.mjs +8 -0
  364. package/dist/chunk-YZ5Z6H4W.mjs +4 -0
  365. package/dist/chunk-Z52HTUW7.mjs +4 -0
  366. package/dist/chunk-ZBIM6ARY.mjs +216 -0
  367. package/dist/cli.mjs +2 -0
  368. package/dist/server.mjs +2 -0
  369. package/dist/worker.mjs +5 -0
  370. package/kit/charts.js +355 -0
  371. package/kit/code.js +164 -0
  372. package/kit/dialogs.js +157 -0
  373. package/kit/math.js +1988 -0
  374. package/kit/report.css +2821 -0
  375. package/kit/runtime.js +1707 -0
  376. package/kit/sheets.js +123 -0
  377. package/kit/state.js +217 -0
  378. package/kit/tables.js +1449 -0
  379. package/kit/tokens.js +29 -0
  380. package/kit/ui.js +561 -0
  381. package/package.json +41 -4
  382. package/release.json +25 -0
  383. package/sdk/column-widths.d.ts +56 -0
  384. package/sdk/doc-charts.d.ts +82 -0
  385. package/sdk/doc-code.d.ts +28 -0
  386. package/sdk/doc-dialogs.d.ts +4 -0
  387. package/sdk/doc-kit.d.ts +141 -0
  388. package/sdk/doc-math.d.ts +3 -0
  389. package/sdk/doc-sheets.d.ts +15 -0
  390. package/sdk/doc-state.d.ts +41 -0
  391. package/sdk/doc-tables.d.ts +24 -0
  392. package/sdk/doc-tokens.d.ts +22 -0
  393. package/sdk/index.d.ts +30 -0
  394. package/skill/SKILL.md +138 -0
  395. package/skill/agents/openai.yaml +5 -0
  396. package/skill/references/building-components.md +327 -0
  397. package/skill/references/example-report.html +356 -0
  398. package/skill/references/writing-html.md +187 -0
  399. package/skill/sdk/column-widths.d.ts +56 -0
  400. package/skill/sdk/doc-charts.d.ts +82 -0
  401. package/skill/sdk/doc-code.d.ts +28 -0
  402. package/skill/sdk/doc-dialogs.d.ts +4 -0
  403. package/skill/sdk/doc-kit.d.ts +141 -0
  404. package/skill/sdk/doc-math.d.ts +3 -0
  405. package/skill/sdk/doc-sheets.d.ts +15 -0
  406. package/skill/sdk/doc-state.d.ts +41 -0
  407. package/skill/sdk/doc-tables.d.ts +24 -0
  408. package/skill/sdk/doc-tokens.d.ts +22 -0
  409. package/skill/sdk/index.d.ts +30 -0
  410. package/starter/doc.html +21 -0
  411. package/starter/doc.json +5 -0
  412. package/vendor/d3.v7.9.0.min.js +2 -0
  413. package/vendor/katex/auto-render.min.js +1 -0
  414. package/vendor/katex/contrib/mhchem.min.js +1 -0
  415. package/vendor/katex/fonts/KaTeX_AMS-Regular.woff2 +0 -0
  416. package/vendor/katex/fonts/KaTeX_Caligraphic-Bold.woff2 +0 -0
  417. package/vendor/katex/fonts/KaTeX_Caligraphic-Regular.woff2 +0 -0
  418. package/vendor/katex/fonts/KaTeX_Fraktur-Bold.woff2 +0 -0
  419. package/vendor/katex/fonts/KaTeX_Fraktur-Regular.woff2 +0 -0
  420. package/vendor/katex/fonts/KaTeX_Main-Bold.woff2 +0 -0
  421. package/vendor/katex/fonts/KaTeX_Main-BoldItalic.woff2 +0 -0
  422. package/vendor/katex/fonts/KaTeX_Main-Italic.woff2 +0 -0
  423. package/vendor/katex/fonts/KaTeX_Main-Regular.woff2 +0 -0
  424. package/vendor/katex/fonts/KaTeX_Math-BoldItalic.woff2 +0 -0
  425. package/vendor/katex/fonts/KaTeX_Math-Italic.woff2 +0 -0
  426. package/vendor/katex/fonts/KaTeX_SansSerif-Bold.woff2 +0 -0
  427. package/vendor/katex/fonts/KaTeX_SansSerif-Italic.woff2 +0 -0
  428. package/vendor/katex/fonts/KaTeX_SansSerif-Regular.woff2 +0 -0
  429. package/vendor/katex/fonts/KaTeX_Script-Regular.woff2 +0 -0
  430. package/vendor/katex/fonts/KaTeX_Size1-Regular.woff2 +0 -0
  431. package/vendor/katex/fonts/KaTeX_Size2-Regular.woff2 +0 -0
  432. package/vendor/katex/fonts/KaTeX_Size3-Regular.woff2 +0 -0
  433. package/vendor/katex/fonts/KaTeX_Size4-Regular.woff2 +0 -0
  434. package/vendor/katex/fonts/KaTeX_Typewriter-Regular.woff2 +0 -0
  435. package/vendor/katex/katex.min.css +1 -0
  436. package/vendor/katex/katex.min.js +1 -0
  437. package/vendor/pdfjs/LICENSE +177 -0
  438. package/vendor/pdfjs/cmaps/78-EUC-H.bcmap +0 -0
  439. package/vendor/pdfjs/cmaps/78-EUC-V.bcmap +0 -0
  440. package/vendor/pdfjs/cmaps/78-H.bcmap +0 -0
  441. package/vendor/pdfjs/cmaps/78-RKSJ-H.bcmap +0 -0
  442. package/vendor/pdfjs/cmaps/78-RKSJ-V.bcmap +0 -0
  443. package/vendor/pdfjs/cmaps/78-V.bcmap +0 -0
  444. package/vendor/pdfjs/cmaps/78ms-RKSJ-H.bcmap +0 -0
  445. package/vendor/pdfjs/cmaps/78ms-RKSJ-V.bcmap +0 -0
  446. package/vendor/pdfjs/cmaps/83pv-RKSJ-H.bcmap +0 -0
  447. package/vendor/pdfjs/cmaps/90ms-RKSJ-H.bcmap +0 -0
  448. package/vendor/pdfjs/cmaps/90ms-RKSJ-V.bcmap +0 -0
  449. package/vendor/pdfjs/cmaps/90msp-RKSJ-H.bcmap +0 -0
  450. package/vendor/pdfjs/cmaps/90msp-RKSJ-V.bcmap +0 -0
  451. package/vendor/pdfjs/cmaps/90pv-RKSJ-H.bcmap +0 -0
  452. package/vendor/pdfjs/cmaps/90pv-RKSJ-V.bcmap +0 -0
  453. package/vendor/pdfjs/cmaps/Add-H.bcmap +0 -0
  454. package/vendor/pdfjs/cmaps/Add-RKSJ-H.bcmap +0 -0
  455. package/vendor/pdfjs/cmaps/Add-RKSJ-V.bcmap +0 -0
  456. package/vendor/pdfjs/cmaps/Add-V.bcmap +0 -0
  457. package/vendor/pdfjs/cmaps/Adobe-CNS1-0.bcmap +0 -0
  458. package/vendor/pdfjs/cmaps/Adobe-CNS1-1.bcmap +0 -0
  459. package/vendor/pdfjs/cmaps/Adobe-CNS1-2.bcmap +0 -0
  460. package/vendor/pdfjs/cmaps/Adobe-CNS1-3.bcmap +0 -0
  461. package/vendor/pdfjs/cmaps/Adobe-CNS1-4.bcmap +0 -0
  462. package/vendor/pdfjs/cmaps/Adobe-CNS1-5.bcmap +0 -0
  463. package/vendor/pdfjs/cmaps/Adobe-CNS1-6.bcmap +0 -0
  464. package/vendor/pdfjs/cmaps/Adobe-CNS1-UCS2.bcmap +0 -0
  465. package/vendor/pdfjs/cmaps/Adobe-GB1-0.bcmap +0 -0
  466. package/vendor/pdfjs/cmaps/Adobe-GB1-1.bcmap +0 -0
  467. package/vendor/pdfjs/cmaps/Adobe-GB1-2.bcmap +0 -0
  468. package/vendor/pdfjs/cmaps/Adobe-GB1-3.bcmap +0 -0
  469. package/vendor/pdfjs/cmaps/Adobe-GB1-4.bcmap +0 -0
  470. package/vendor/pdfjs/cmaps/Adobe-GB1-5.bcmap +0 -0
  471. package/vendor/pdfjs/cmaps/Adobe-GB1-UCS2.bcmap +0 -0
  472. package/vendor/pdfjs/cmaps/Adobe-Japan1-0.bcmap +0 -0
  473. package/vendor/pdfjs/cmaps/Adobe-Japan1-1.bcmap +0 -0
  474. package/vendor/pdfjs/cmaps/Adobe-Japan1-2.bcmap +0 -0
  475. package/vendor/pdfjs/cmaps/Adobe-Japan1-3.bcmap +0 -0
  476. package/vendor/pdfjs/cmaps/Adobe-Japan1-4.bcmap +0 -0
  477. package/vendor/pdfjs/cmaps/Adobe-Japan1-5.bcmap +0 -0
  478. package/vendor/pdfjs/cmaps/Adobe-Japan1-6.bcmap +0 -0
  479. package/vendor/pdfjs/cmaps/Adobe-Japan1-UCS2.bcmap +0 -0
  480. package/vendor/pdfjs/cmaps/Adobe-Korea1-0.bcmap +0 -0
  481. package/vendor/pdfjs/cmaps/Adobe-Korea1-1.bcmap +0 -0
  482. package/vendor/pdfjs/cmaps/Adobe-Korea1-2.bcmap +0 -0
  483. package/vendor/pdfjs/cmaps/Adobe-Korea1-UCS2.bcmap +0 -0
  484. package/vendor/pdfjs/cmaps/B5-H.bcmap +0 -0
  485. package/vendor/pdfjs/cmaps/B5-V.bcmap +0 -0
  486. package/vendor/pdfjs/cmaps/B5pc-H.bcmap +0 -0
  487. package/vendor/pdfjs/cmaps/B5pc-V.bcmap +0 -0
  488. package/vendor/pdfjs/cmaps/CNS-EUC-H.bcmap +0 -0
  489. package/vendor/pdfjs/cmaps/CNS-EUC-V.bcmap +0 -0
  490. package/vendor/pdfjs/cmaps/CNS1-H.bcmap +0 -0
  491. package/vendor/pdfjs/cmaps/CNS1-V.bcmap +0 -0
  492. package/vendor/pdfjs/cmaps/CNS2-H.bcmap +0 -0
  493. package/vendor/pdfjs/cmaps/CNS2-V.bcmap +3 -0
  494. package/vendor/pdfjs/cmaps/ETHK-B5-H.bcmap +0 -0
  495. package/vendor/pdfjs/cmaps/ETHK-B5-V.bcmap +0 -0
  496. package/vendor/pdfjs/cmaps/ETen-B5-H.bcmap +0 -0
  497. package/vendor/pdfjs/cmaps/ETen-B5-V.bcmap +0 -0
  498. package/vendor/pdfjs/cmaps/ETenms-B5-H.bcmap +3 -0
  499. package/vendor/pdfjs/cmaps/ETenms-B5-V.bcmap +0 -0
  500. package/vendor/pdfjs/cmaps/EUC-H.bcmap +0 -0
  501. package/vendor/pdfjs/cmaps/EUC-V.bcmap +0 -0
  502. package/vendor/pdfjs/cmaps/Ext-H.bcmap +0 -0
  503. package/vendor/pdfjs/cmaps/Ext-RKSJ-H.bcmap +0 -0
  504. package/vendor/pdfjs/cmaps/Ext-RKSJ-V.bcmap +0 -0
  505. package/vendor/pdfjs/cmaps/Ext-V.bcmap +0 -0
  506. package/vendor/pdfjs/cmaps/GB-EUC-H.bcmap +0 -0
  507. package/vendor/pdfjs/cmaps/GB-EUC-V.bcmap +0 -0
  508. package/vendor/pdfjs/cmaps/GB-H.bcmap +4 -0
  509. package/vendor/pdfjs/cmaps/GB-V.bcmap +0 -0
  510. package/vendor/pdfjs/cmaps/GBK-EUC-H.bcmap +0 -0
  511. package/vendor/pdfjs/cmaps/GBK-EUC-V.bcmap +0 -0
  512. package/vendor/pdfjs/cmaps/GBK2K-H.bcmap +0 -0
  513. package/vendor/pdfjs/cmaps/GBK2K-V.bcmap +0 -0
  514. package/vendor/pdfjs/cmaps/GBKp-EUC-H.bcmap +0 -0
  515. package/vendor/pdfjs/cmaps/GBKp-EUC-V.bcmap +0 -0
  516. package/vendor/pdfjs/cmaps/GBT-EUC-H.bcmap +0 -0
  517. package/vendor/pdfjs/cmaps/GBT-EUC-V.bcmap +0 -0
  518. package/vendor/pdfjs/cmaps/GBT-H.bcmap +0 -0
  519. package/vendor/pdfjs/cmaps/GBT-V.bcmap +0 -0
  520. package/vendor/pdfjs/cmaps/GBTpc-EUC-H.bcmap +0 -0
  521. package/vendor/pdfjs/cmaps/GBTpc-EUC-V.bcmap +0 -0
  522. package/vendor/pdfjs/cmaps/GBpc-EUC-H.bcmap +0 -0
  523. package/vendor/pdfjs/cmaps/GBpc-EUC-V.bcmap +0 -0
  524. package/vendor/pdfjs/cmaps/H.bcmap +0 -0
  525. package/vendor/pdfjs/cmaps/HKdla-B5-H.bcmap +0 -0
  526. package/vendor/pdfjs/cmaps/HKdla-B5-V.bcmap +0 -0
  527. package/vendor/pdfjs/cmaps/HKdlb-B5-H.bcmap +0 -0
  528. package/vendor/pdfjs/cmaps/HKdlb-B5-V.bcmap +0 -0
  529. package/vendor/pdfjs/cmaps/HKgccs-B5-H.bcmap +0 -0
  530. package/vendor/pdfjs/cmaps/HKgccs-B5-V.bcmap +0 -0
  531. package/vendor/pdfjs/cmaps/HKm314-B5-H.bcmap +0 -0
  532. package/vendor/pdfjs/cmaps/HKm314-B5-V.bcmap +0 -0
  533. package/vendor/pdfjs/cmaps/HKm471-B5-H.bcmap +0 -0
  534. package/vendor/pdfjs/cmaps/HKm471-B5-V.bcmap +0 -0
  535. package/vendor/pdfjs/cmaps/HKscs-B5-H.bcmap +0 -0
  536. package/vendor/pdfjs/cmaps/HKscs-B5-V.bcmap +0 -0
  537. package/vendor/pdfjs/cmaps/Hankaku.bcmap +0 -0
  538. package/vendor/pdfjs/cmaps/Hiragana.bcmap +0 -0
  539. package/vendor/pdfjs/cmaps/KSC-EUC-H.bcmap +0 -0
  540. package/vendor/pdfjs/cmaps/KSC-EUC-V.bcmap +0 -0
  541. package/vendor/pdfjs/cmaps/KSC-H.bcmap +0 -0
  542. package/vendor/pdfjs/cmaps/KSC-Johab-H.bcmap +0 -0
  543. package/vendor/pdfjs/cmaps/KSC-Johab-V.bcmap +0 -0
  544. package/vendor/pdfjs/cmaps/KSC-V.bcmap +0 -0
  545. package/vendor/pdfjs/cmaps/KSCms-UHC-H.bcmap +0 -0
  546. package/vendor/pdfjs/cmaps/KSCms-UHC-HW-H.bcmap +0 -0
  547. package/vendor/pdfjs/cmaps/KSCms-UHC-HW-V.bcmap +0 -0
  548. package/vendor/pdfjs/cmaps/KSCms-UHC-V.bcmap +0 -0
  549. package/vendor/pdfjs/cmaps/KSCpc-EUC-H.bcmap +0 -0
  550. package/vendor/pdfjs/cmaps/KSCpc-EUC-V.bcmap +0 -0
  551. package/vendor/pdfjs/cmaps/Katakana.bcmap +0 -0
  552. package/vendor/pdfjs/cmaps/LICENSE +36 -0
  553. package/vendor/pdfjs/cmaps/NWP-H.bcmap +0 -0
  554. package/vendor/pdfjs/cmaps/NWP-V.bcmap +0 -0
  555. package/vendor/pdfjs/cmaps/RKSJ-H.bcmap +0 -0
  556. package/vendor/pdfjs/cmaps/RKSJ-V.bcmap +0 -0
  557. package/vendor/pdfjs/cmaps/Roman.bcmap +0 -0
  558. package/vendor/pdfjs/cmaps/UniCNS-UCS2-H.bcmap +0 -0
  559. package/vendor/pdfjs/cmaps/UniCNS-UCS2-V.bcmap +0 -0
  560. package/vendor/pdfjs/cmaps/UniCNS-UTF16-H.bcmap +0 -0
  561. package/vendor/pdfjs/cmaps/UniCNS-UTF16-V.bcmap +0 -0
  562. package/vendor/pdfjs/cmaps/UniCNS-UTF32-H.bcmap +0 -0
  563. package/vendor/pdfjs/cmaps/UniCNS-UTF32-V.bcmap +0 -0
  564. package/vendor/pdfjs/cmaps/UniCNS-UTF8-H.bcmap +0 -0
  565. package/vendor/pdfjs/cmaps/UniCNS-UTF8-V.bcmap +0 -0
  566. package/vendor/pdfjs/cmaps/UniGB-UCS2-H.bcmap +0 -0
  567. package/vendor/pdfjs/cmaps/UniGB-UCS2-V.bcmap +0 -0
  568. package/vendor/pdfjs/cmaps/UniGB-UTF16-H.bcmap +0 -0
  569. package/vendor/pdfjs/cmaps/UniGB-UTF16-V.bcmap +0 -0
  570. package/vendor/pdfjs/cmaps/UniGB-UTF32-H.bcmap +0 -0
  571. package/vendor/pdfjs/cmaps/UniGB-UTF32-V.bcmap +0 -0
  572. package/vendor/pdfjs/cmaps/UniGB-UTF8-H.bcmap +0 -0
  573. package/vendor/pdfjs/cmaps/UniGB-UTF8-V.bcmap +0 -0
  574. package/vendor/pdfjs/cmaps/UniJIS-UCS2-H.bcmap +0 -0
  575. package/vendor/pdfjs/cmaps/UniJIS-UCS2-HW-H.bcmap +0 -0
  576. package/vendor/pdfjs/cmaps/UniJIS-UCS2-HW-V.bcmap +0 -0
  577. package/vendor/pdfjs/cmaps/UniJIS-UCS2-V.bcmap +0 -0
  578. package/vendor/pdfjs/cmaps/UniJIS-UTF16-H.bcmap +0 -0
  579. package/vendor/pdfjs/cmaps/UniJIS-UTF16-V.bcmap +0 -0
  580. package/vendor/pdfjs/cmaps/UniJIS-UTF32-H.bcmap +0 -0
  581. package/vendor/pdfjs/cmaps/UniJIS-UTF32-V.bcmap +0 -0
  582. package/vendor/pdfjs/cmaps/UniJIS-UTF8-H.bcmap +0 -0
  583. package/vendor/pdfjs/cmaps/UniJIS-UTF8-V.bcmap +0 -0
  584. package/vendor/pdfjs/cmaps/UniJIS2004-UTF16-H.bcmap +0 -0
  585. package/vendor/pdfjs/cmaps/UniJIS2004-UTF16-V.bcmap +0 -0
  586. package/vendor/pdfjs/cmaps/UniJIS2004-UTF32-H.bcmap +0 -0
  587. package/vendor/pdfjs/cmaps/UniJIS2004-UTF32-V.bcmap +0 -0
  588. package/vendor/pdfjs/cmaps/UniJIS2004-UTF8-H.bcmap +0 -0
  589. package/vendor/pdfjs/cmaps/UniJIS2004-UTF8-V.bcmap +0 -0
  590. package/vendor/pdfjs/cmaps/UniJISPro-UCS2-HW-V.bcmap +0 -0
  591. package/vendor/pdfjs/cmaps/UniJISPro-UCS2-V.bcmap +0 -0
  592. package/vendor/pdfjs/cmaps/UniJISPro-UTF8-V.bcmap +0 -0
  593. package/vendor/pdfjs/cmaps/UniJISX0213-UTF32-H.bcmap +0 -0
  594. package/vendor/pdfjs/cmaps/UniJISX0213-UTF32-V.bcmap +0 -0
  595. package/vendor/pdfjs/cmaps/UniJISX02132004-UTF32-H.bcmap +0 -0
  596. package/vendor/pdfjs/cmaps/UniJISX02132004-UTF32-V.bcmap +0 -0
  597. package/vendor/pdfjs/cmaps/UniKS-UCS2-H.bcmap +0 -0
  598. package/vendor/pdfjs/cmaps/UniKS-UCS2-V.bcmap +0 -0
  599. package/vendor/pdfjs/cmaps/UniKS-UTF16-H.bcmap +0 -0
  600. package/vendor/pdfjs/cmaps/UniKS-UTF16-V.bcmap +0 -0
  601. package/vendor/pdfjs/cmaps/UniKS-UTF32-H.bcmap +0 -0
  602. package/vendor/pdfjs/cmaps/UniKS-UTF32-V.bcmap +0 -0
  603. package/vendor/pdfjs/cmaps/UniKS-UTF8-H.bcmap +0 -0
  604. package/vendor/pdfjs/cmaps/UniKS-UTF8-V.bcmap +0 -0
  605. package/vendor/pdfjs/cmaps/V.bcmap +0 -0
  606. package/vendor/pdfjs/cmaps/WP-Symbol.bcmap +0 -0
  607. package/vendor/pdfjs/legacy/build/pdf.min.mjs +27 -0
  608. package/vendor/pdfjs/legacy/build/pdf.worker.min.mjs +27 -0
  609. package/vendor/pdfjs/standard_fonts/FoxitDingbats.pfb +0 -0
  610. package/vendor/pdfjs/standard_fonts/FoxitFixed.pfb +0 -0
  611. package/vendor/pdfjs/standard_fonts/FoxitFixedBold.pfb +0 -0
  612. package/vendor/pdfjs/standard_fonts/FoxitFixedBoldItalic.pfb +0 -0
  613. package/vendor/pdfjs/standard_fonts/FoxitFixedItalic.pfb +0 -0
  614. package/vendor/pdfjs/standard_fonts/FoxitSerif.pfb +0 -0
  615. package/vendor/pdfjs/standard_fonts/FoxitSerifBold.pfb +0 -0
  616. package/vendor/pdfjs/standard_fonts/FoxitSerifBoldItalic.pfb +0 -0
  617. package/vendor/pdfjs/standard_fonts/FoxitSerifItalic.pfb +0 -0
  618. package/vendor/pdfjs/standard_fonts/FoxitSymbol.pfb +0 -0
  619. package/vendor/pdfjs/standard_fonts/LICENSE_FOXIT +27 -0
  620. package/vendor/pdfjs/standard_fonts/LICENSE_LIBERATION +363 -0
  621. package/vendor/pdfjs/standard_fonts/LiberationSans-Bold.ttf +0 -0
  622. package/vendor/pdfjs/standard_fonts/LiberationSans-BoldItalic.ttf +0 -0
  623. package/vendor/pdfjs/standard_fonts/LiberationSans-Italic.ttf +0 -0
  624. package/vendor/pdfjs/standard_fonts/LiberationSans-Regular.ttf +0 -0
  625. package/vendor/types/@types/d3/LICENSE +21 -0
  626. package/vendor/types/@types/d3/index.d.ts +39 -0
  627. package/vendor/types/@types/d3/package.json +81 -0
  628. package/vendor/types/@types/d3-array/LICENSE +21 -0
  629. package/vendor/types/@types/d3-array/index.d.ts +1118 -0
  630. package/vendor/types/@types/d3-array/package.json +56 -0
  631. package/vendor/types/@types/d3-axis/LICENSE +21 -0
  632. package/vendor/types/@types/d3-axis/index.d.ts +293 -0
  633. package/vendor/types/@types/d3-axis/package.json +47 -0
  634. package/vendor/types/@types/d3-brush/LICENSE +21 -0
  635. package/vendor/types/@types/d3-brush/index.d.ts +255 -0
  636. package/vendor/types/@types/d3-brush/package.json +42 -0
  637. package/vendor/types/@types/d3-chord/LICENSE +21 -0
  638. package/vendor/types/@types/d3-chord/index.d.ts +471 -0
  639. package/vendor/types/@types/d3-chord/package.json +40 -0
  640. package/vendor/types/@types/d3-color/LICENSE +21 -0
  641. package/vendor/types/@types/d3-color/index.d.ts +669 -0
  642. package/vendor/types/@types/d3-color/package.json +55 -0
  643. package/vendor/types/@types/d3-contour/LICENSE +21 -0
  644. package/vendor/types/@types/d3-contour/index.d.ts +222 -0
  645. package/vendor/types/@types/d3-contour/package.json +38 -0
  646. package/vendor/types/@types/d3-delaunay/LICENSE +21 -0
  647. package/vendor/types/@types/d3-delaunay/index.d.ts +316 -0
  648. package/vendor/types/@types/d3-delaunay/package.json +30 -0
  649. package/vendor/types/@types/d3-dispatch/LICENSE +21 -0
  650. package/vendor/types/@types/d3-dispatch/index.d.ts +96 -0
  651. package/vendor/types/@types/d3-dispatch/package.json +51 -0
  652. package/vendor/types/@types/d3-drag/LICENSE +21 -0
  653. package/vendor/types/@types/d3-drag/index.d.ts +395 -0
  654. package/vendor/types/@types/d3-drag/package.json +42 -0
  655. package/vendor/types/@types/d3-dsv/LICENSE +21 -0
  656. package/vendor/types/@types/d3-dsv/index.d.ts +482 -0
  657. package/vendor/types/@types/d3-dsv/package.json +45 -0
  658. package/vendor/types/@types/d3-ease/LICENSE +21 -0
  659. package/vendor/types/@types/d3-ease/index.d.ts +316 -0
  660. package/vendor/types/@types/d3-ease/package.json +40 -0
  661. package/vendor/types/@types/d3-fetch/LICENSE +21 -0
  662. package/vendor/types/@types/d3-fetch/index.d.ts +282 -0
  663. package/vendor/types/@types/d3-fetch/package.json +37 -0
  664. package/vendor/types/@types/d3-force/LICENSE +21 -0
  665. package/vendor/types/@types/d3-force/index.d.ts +899 -0
  666. package/vendor/types/@types/d3-force/package.json +45 -0
  667. package/vendor/types/@types/d3-format/LICENSE +21 -0
  668. package/vendor/types/@types/d3-format/index.d.ts +337 -0
  669. package/vendor/types/@types/d3-format/package.json +45 -0
  670. package/vendor/types/@types/d3-geo/LICENSE +21 -0
  671. package/vendor/types/@types/d3-geo/index.d.ts +1371 -0
  672. package/vendor/types/@types/d3-geo/package.json +48 -0
  673. package/vendor/types/@types/d3-hierarchy/LICENSE +21 -0
  674. package/vendor/types/@types/d3-hierarchy/index.d.ts +928 -0
  675. package/vendor/types/@types/d3-hierarchy/package.json +50 -0
  676. package/vendor/types/@types/d3-interpolate/LICENSE +21 -0
  677. package/vendor/types/@types/d3-interpolate/index.d.ts +387 -0
  678. package/vendor/types/@types/d3-interpolate/package.json +47 -0
  679. package/vendor/types/@types/d3-path/LICENSE +21 -0
  680. package/vendor/types/@types/d3-path/index.d.ts +108 -0
  681. package/vendor/types/@types/d3-path/package.json +41 -0
  682. package/vendor/types/@types/d3-polygon/LICENSE +21 -0
  683. package/vendor/types/@types/d3-polygon/index.d.ts +41 -0
  684. package/vendor/types/@types/d3-polygon/package.json +40 -0
  685. package/vendor/types/@types/d3-quadtree/LICENSE +21 -0
  686. package/vendor/types/@types/d3-quadtree/index.d.ts +204 -0
  687. package/vendor/types/@types/d3-quadtree/package.json +45 -0
  688. package/vendor/types/@types/d3-random/LICENSE +21 -0
  689. package/vendor/types/@types/d3-random/index.d.ts +313 -0
  690. package/vendor/types/@types/d3-random/package.json +41 -0
  691. package/vendor/types/@types/d3-scale/LICENSE +21 -0
  692. package/vendor/types/@types/d3-scale/index.d.ts +2669 -0
  693. package/vendor/types/@types/d3-scale/package.json +53 -0
  694. package/vendor/types/@types/d3-scale-chromatic/LICENSE +21 -0
  695. package/vendor/types/@types/d3-scale-chromatic/index.d.ts +520 -0
  696. package/vendor/types/@types/d3-scale-chromatic/package.json +46 -0
  697. package/vendor/types/@types/d3-selection/LICENSE +21 -0
  698. package/vendor/types/@types/d3-selection/index.d.ts +1210 -0
  699. package/vendor/types/@types/d3-selection/package.json +56 -0
  700. package/vendor/types/@types/d3-shape/LICENSE +21 -0
  701. package/vendor/types/@types/d3-shape/index.d.ts +2792 -0
  702. package/vendor/types/@types/d3-shape/package.json +53 -0
  703. package/vendor/types/@types/d3-time/LICENSE +21 -0
  704. package/vendor/types/@types/d3-time/index.d.ts +697 -0
  705. package/vendor/types/@types/d3-time/package.json +46 -0
  706. package/vendor/types/@types/d3-time-format/LICENSE +21 -0
  707. package/vendor/types/@types/d3-time-format/index.d.ts +202 -0
  708. package/vendor/types/@types/d3-time-format/package.json +40 -0
  709. package/vendor/types/@types/d3-timer/LICENSE +21 -0
  710. package/vendor/types/@types/d3-timer/index.d.ts +68 -0
  711. package/vendor/types/@types/d3-timer/package.json +45 -0
  712. package/vendor/types/@types/d3-transition/LICENSE +21 -0
  713. package/vendor/types/@types/d3-transition/index.d.ts +664 -0
  714. package/vendor/types/@types/d3-transition/package.json +47 -0
  715. package/vendor/types/@types/d3-zoom/LICENSE +21 -0
  716. package/vendor/types/@types/d3-zoom/index.d.ts +611 -0
  717. package/vendor/types/@types/d3-zoom/package.json +48 -0
  718. package/vendor/types/@types/geojson/LICENSE +21 -0
  719. package/vendor/types/@types/geojson/index.d.ts +202 -0
  720. package/vendor/types/@types/geojson/package.json +46 -0
  721. package/vendor/typescript/LICENSE.txt +55 -0
  722. package/vendor/typescript/lib.decorators.d.ts +384 -0
  723. package/vendor/typescript/lib.decorators.legacy.d.ts +22 -0
  724. package/vendor/typescript/lib.dom.d.ts +39429 -0
  725. package/vendor/typescript/lib.dom.iterable.d.ts +571 -0
  726. package/vendor/typescript/lib.es2015.collection.d.ts +147 -0
  727. package/vendor/typescript/lib.es2015.core.d.ts +597 -0
  728. package/vendor/typescript/lib.es2015.d.ts +28 -0
  729. package/vendor/typescript/lib.es2015.generator.d.ts +77 -0
  730. package/vendor/typescript/lib.es2015.iterable.d.ts +605 -0
  731. package/vendor/typescript/lib.es2015.promise.d.ts +81 -0
  732. package/vendor/typescript/lib.es2015.proxy.d.ts +128 -0
  733. package/vendor/typescript/lib.es2015.reflect.d.ts +144 -0
  734. package/vendor/typescript/lib.es2015.symbol.d.ts +46 -0
  735. package/vendor/typescript/lib.es2015.symbol.wellknown.d.ts +326 -0
  736. package/vendor/typescript/lib.es2016.array.include.d.ts +116 -0
  737. package/vendor/typescript/lib.es2016.d.ts +21 -0
  738. package/vendor/typescript/lib.es2016.intl.d.ts +31 -0
  739. package/vendor/typescript/lib.es2017.arraybuffer.d.ts +21 -0
  740. package/vendor/typescript/lib.es2017.d.ts +26 -0
  741. package/vendor/typescript/lib.es2017.date.d.ts +31 -0
  742. package/vendor/typescript/lib.es2017.intl.d.ts +44 -0
  743. package/vendor/typescript/lib.es2017.object.d.ts +49 -0
  744. package/vendor/typescript/lib.es2017.sharedmemory.d.ts +135 -0
  745. package/vendor/typescript/lib.es2017.string.d.ts +45 -0
  746. package/vendor/typescript/lib.es2017.typedarrays.d.ts +53 -0
  747. package/vendor/typescript/lib.es2018.asyncgenerator.d.ts +77 -0
  748. package/vendor/typescript/lib.es2018.asynciterable.d.ts +53 -0
  749. package/vendor/typescript/lib.es2018.d.ts +24 -0
  750. package/vendor/typescript/lib.es2018.intl.d.ts +83 -0
  751. package/vendor/typescript/lib.es2018.promise.d.ts +30 -0
  752. package/vendor/typescript/lib.es2018.regexp.d.ts +37 -0
  753. package/vendor/typescript/lib.es2019.array.d.ts +79 -0
  754. package/vendor/typescript/lib.es2019.d.ts +24 -0
  755. package/vendor/typescript/lib.es2019.intl.d.ts +23 -0
  756. package/vendor/typescript/lib.es2019.object.d.ts +33 -0
  757. package/vendor/typescript/lib.es2019.string.d.ts +37 -0
  758. package/vendor/typescript/lib.es2019.symbol.d.ts +24 -0
  759. package/vendor/typescript/lib.es2020.bigint.d.ts +765 -0
  760. package/vendor/typescript/lib.es2020.d.ts +27 -0
  761. package/vendor/typescript/lib.es2020.date.d.ts +42 -0
  762. package/vendor/typescript/lib.es2020.intl.d.ts +474 -0
  763. package/vendor/typescript/lib.es2020.number.d.ts +28 -0
  764. package/vendor/typescript/lib.es2020.promise.d.ts +47 -0
  765. package/vendor/typescript/lib.es2020.sharedmemory.d.ts +99 -0
  766. package/vendor/typescript/lib.es2020.string.d.ts +44 -0
  767. package/vendor/typescript/lib.es2020.symbol.wellknown.d.ts +41 -0
  768. package/vendor/typescript/lib.es2021.d.ts +23 -0
  769. package/vendor/typescript/lib.es2021.intl.d.ts +166 -0
  770. package/vendor/typescript/lib.es2021.promise.d.ts +48 -0
  771. package/vendor/typescript/lib.es2021.string.d.ts +33 -0
  772. package/vendor/typescript/lib.es2021.weakref.d.ts +78 -0
  773. package/vendor/typescript/lib.es2022.array.d.ts +121 -0
  774. package/vendor/typescript/lib.es2022.d.ts +25 -0
  775. package/vendor/typescript/lib.es2022.error.d.ts +75 -0
  776. package/vendor/typescript/lib.es2022.intl.d.ts +145 -0
  777. package/vendor/typescript/lib.es2022.object.d.ts +26 -0
  778. package/vendor/typescript/lib.es2022.regexp.d.ts +39 -0
  779. package/vendor/typescript/lib.es2022.string.d.ts +25 -0
  780. package/vendor/typescript/lib.es5.d.ts +4601 -0
  781. package/vendor/typescript/package.json +4 -0
  782. package/vendor/typescript/typescript.js +446 -0
  783. package/web/assets/index-B6Ai3wsa.js +13 -0
  784. package/web/assets/index-SYPC3EZy.css +1 -0
  785. package/web/index.html +14 -0
@@ -0,0 +1,278 @@
1
+ // Taken over from notion-lite (its src/ui/media-picker/emoji-tab.js), as it is: only what it imports is
2
+ // Gallery's own (support.mjs, src/shared/emoji/). Its notes, below, are notion-lite's.
3
+ /* “表情符号”页签(943244 EmojiPicker、885963 选肤色、625478 格子和肤色变体;尺寸是线上实测)。
4
+ * 分组:最近(筛选词为空时)、标注(从标注打开时,固定 26 个)、人物、动物与自然、食物与饮料、活动、旅行与地点、物品、符号、旗帜、
5
+ * 自定义(本机的自定义表情,按名字排;第一个格子是“添加表情符号”的圆形加号)
6
+ * 每行 (408 − 24) / 32 = 12 个;标题 12px / 500、上 6+6 下 8;格子 32×32、圆角 4、表情 24(../emoji/emoji.js)
7
+ * 筛选(943244 W):按关键词打分——筛选词里有这个表情 > “:筛选词” > 关键词等于 > 关键词开头 > 多个词都对上 > 包含,常用的加分;
8
+ * 自定义表情的关键词是它的名字(871871 g)。结果(连同加号)超过 12 × 12 / 2 = 72 个时仍按分组显示,否则拍平成一组按分数排
9
+ * (加号排最后);只剩加号时显示“无结果”和“添加表情符号”按钮
10
+ * 底部分类栏(943244 y):上边一条 --c-borSec,内边距 8 12 10;按钮 32×32、图标 22;当前滚到的分组按钮有底色;
11
+ * 没有表情的分组按钮半透明不可点(“自定义”“添加”总能点);悬停提示分组名(左对齐、在下方);点了把那一组滚到顶上,
12
+ * “添加”打开“添加表情符号”浮层。筛选结果拍平时不显示
13
+ * 最近(943244 F):常用表情按次数、时间排,取 2 行;选中一个表情记一次(../emoji/data.js recordEmojiUse)
14
+ * 格子(625478):没设过肤色时点有肤色变体的表情,先弹出一排变体(选了正好 5 个变体的就记下肤色);
15
+ * 自定义表情(758388)24×24、contain,提示是它的名字
16
+ * 右边按钮(885963):选肤色,28×28、字号 20 的“✋”(设过就是那个肤色的手),点开一排六只手
17
+ * 随机(859941):活动 / 物品 / 旅行与地点里随便一个,选上但不关菜单
18
+ * 添加表情符号(943244 Y → 757573 → 749527 tM):在加号 / 底栏按钮 / 无结果按钮下面打开 ./upload.js 的浮层;
19
+ * 存好以后交给 env.uploaded(选上这个表情、关菜单)
20
+ * 和 Notion 的差别:不是虚拟列表,全部画出来,图片滚到附近才加载。自定义表情是本机的(../emoji/custom.js),总能添加。
21
+ * createEmojiTab(env) → { el, right, load(), render(filter), move(key), activateFocused(), random(), destroy() }
22
+ * env:{ isCallout, submit(value), keepOpenPick(value), uploaded(value), refocus(), openSub(anchor, el, onKey), closeSub() }
23
+ * 依赖:lib/dom、ui(icons、tooltip、popup)、ui/emoji(data、emoji、custom)、./grid、./upload
24
+ */
25
+ import { esc } from './support.mjs';
26
+ import { icon } from './support.mjs';
27
+ import { hoverTooltip, hideTooltip } from './support.mjs';
28
+ import { openPopup, closePopup } from './support.mjs';
29
+ import {
30
+ loadEmojiData, emojiDataLoaded, emojiInfo, emojisInCategory, emojiName, emojiVariations, normalizeFilter, randomEmoji,
31
+ getSkinTone, setSkinTone, withSkinTone, SKIN_TONE_HANDS, SKIN_TONE_VARIATIONS, recordEmojiUse, recentEmojis, frecencyBoost,
32
+ } from '../../../shared/emoji/data.mjs';
33
+ import { emojiHTML } from '../../../shared/emoji/emoji.mjs';
34
+ import { loadCustomEmojis, customEmojiStrings, customEmojiOf, customEmojiKeywords, isCustomEmojiString } from '../../../shared/emoji/custom.mjs';
35
+ import { createGridFocus } from './grid.mjs';
36
+ import { createUploadForm } from './upload.mjs';
37
+ import { t } from "../../../shared/i18n/index.mjs";
38
+
39
+ export const PER_ROW = 12; // 103955 so:(408 − 24) / 32
40
+ const SHOW_CATEGORIES_THRESHOLD = Math.floor(PER_ROW * 12 / 2); // 943244:w2 × uu() / 2 = 72
41
+ const ADD = '__ADD_CUSTOM_EMOJI__'; // 943244 v
42
+ const ADD_LABEL = t("添加表情符号"); // emojiPicker.addCustomEmoji
43
+
44
+ /* 943244 k */
45
+ const CATEGORIES = [
46
+ { id: 'recent', title: t("最近"), icon: 'clock' },
47
+ { id: 'callout', title: t("标注") },
48
+ { id: 'people', category: 'People & Body', title: t("人物"), icon: 'emojiFace' },
49
+ { id: 'nature', category: 'Animals & Nature', title: t("动物与自然"), icon: 'leaf' },
50
+ { id: 'food', category: 'Food & Drink', title: t("食物与饮料"), icon: 'carrot' },
51
+ { id: 'activities', category: 'Activities', title: t("活动"), icon: 'soccerBall' },
52
+ { id: 'travel', category: 'Travel & Places', title: t("旅行与地点"), icon: 'airplane' },
53
+ { id: 'objects', category: 'Objects', title: t("物品"), icon: 'lightBulbBright' },
54
+ { id: 'symbols', category: 'Symbols', title: t("符号"), icon: 'checkmarkCircle' },
55
+ { id: 'flags', category: 'Flags', title: t("旗帜"), icon: 'flag' },
56
+ { id: 'custom', title: t("自定义"), icon: 'squareGrid2X2' },
57
+ { id: 'add', title: ADD_LABEL, icon: 'plusCircle' },
58
+ ];
59
+ const CATEGORY = Object.fromEntries(CATEGORIES.map(c => [c.id, c]));
60
+ /* 943244 M:标注专用的一组 */
61
+ const CALLOUT_EMOJIS = ['💡', '👉', '☝', '👌', '🔑', '🚧', '⚠️', '🔥', '📌', '✂️', '❓', '🚫', '⛔', '⏰', '☎️', '🚨', '♻️', '✅', '🔒', '📎', '📖', '🗣', '➡️', '📢', '🛠', '⚙'];
62
+
63
+ /* 943244 W 里的打分(rank);没对上返回 undefined */
64
+ function rank(emoji, filter, splitFilter) {
65
+ if (filter === '') return 100;
66
+ const info = emojiInfo(emoji);
67
+ let words = info?.keywords || [];
68
+ if (!info && isCustomEmojiString(emoji)) {
69
+ const custom = customEmojiOf(emoji);
70
+ if (!custom) return;
71
+ words = customEmojiKeywords(custom.name);
72
+ }
73
+ const kw = filter.length < 3 || filter.includes(' ') ? words : words.map(w => w.replaceAll(' ', ''));
74
+ const boost = frecencyBoost(emoji);
75
+ const inFilter = filter.indexOf(emoji);
76
+ if (inFilter !== -1) return 100 - inFilter + boost;
77
+ const colon = kw.findIndex(w => w === `:${filter}`);
78
+ if (colon !== -1) return 100 - colon + boost;
79
+ const exact = kw.findIndex(w => w === filter);
80
+ if (exact !== -1) return (10 - exact) * 10 + boost;
81
+ const prefix = kw.findIndex(w => w.startsWith(filter));
82
+ if (prefix !== -1) return 10 - prefix + boost;
83
+ if (splitFilter.length > 1) {
84
+ const unique = info?.uniqueKeywords || [];
85
+ if (splitFilter.every(part => unique.find(w => w.startsWith(part)))) return splitFilter.length + boost;
86
+ }
87
+ if (kw.some(w => w.includes(filter))) return 1 + boost;
88
+ }
89
+
90
+ /* 943244 W:分好组、切成一行行。返回 { categorized, rows: [{ id, title?, emojis }] };只剩加号时 rows 是 [{ emojis: [ADD] }] */
91
+ function buildRows(rawFilter, isCallout, recent) {
92
+ const cats = [!rawFilter.trim() ? CATEGORY.recent : null, isCallout ? CATEGORY.callout : null, ...CATEGORIES.slice(2, 10), CATEGORY.custom].filter(Boolean);
93
+ const filter = normalizeFilter(rawFilter) ?? '';
94
+ const split = rawFilter.split(' ').filter(Boolean);
95
+ const rows = [];
96
+ let total = 0;
97
+ for (const cat of cats) {
98
+ const source = cat.id === 'recent' ? recent : cat.id === 'callout' ? CALLOUT_EMOJIS : cat.id === 'custom' ? customEmojiStrings() : emojisInCategory(cat.category);
99
+ const ranked = source.map(emoji => ({ emoji, rank: rank(emoji, filter, split) })).filter(x => x.rank !== undefined)
100
+ .sort((a, b) => b.rank - a.rank)
101
+ .map(x => ({ rank: x.rank, emoji: withSkinTone(x.emoji) }));
102
+ if (cat.id === 'custom') ranked.unshift({ rank: -Infinity, emoji: ADD }); // 943244:能加自定义表情时,加号排在“自定义”最前
103
+ for (let i = 0; i < ranked.length; i += PER_ROW) rows.push({ id: cat.id, title: i === 0 ? cat.title : undefined, emojis: ranked.slice(i, i + PER_ROW) });
104
+ total += ranked.length;
105
+ }
106
+ if (rawFilter === '' || total > SHOW_CATEGORIES_THRESHOLD) return { categorized: true, rows: rows.map(r => ({ ...r, emojis: r.emojis.map(x => x.emoji) })) };
107
+ const flat = [...new Set(rows.flatMap(r => r.emojis).sort((a, b) => b.rank - a.rank).map(x => x.emoji))];
108
+ const out = [];
109
+ for (let i = 0; i < flat.length; i += PER_ROW) out.push({ emojis: flat.slice(i, i + PER_ROW) });
110
+ return { categorized: false, rows: out };
111
+ }
112
+
113
+ /* 一排表情的小浮层(肤色变体、选肤色;padding 4,横向,←→ / 回车 / Esc) */
114
+ function emojiRow(env, anchor, emojis, initial, onChoose) {
115
+ const row = document.createElement('div');
116
+ row.className = 'nmm-variations';
117
+ row.innerHTML = emojis.map((e, i) => `<div role="gridcell" class="nmm-cell${i === initial ? ' focused' : ''}" data-i="${i}">${emojiHTML(e, { size: 24 })}</div>`).join('');
118
+ let at = initial;
119
+ const focusAt = i => { row.children[at]?.classList.remove('focused'); at = i; row.children[at]?.classList.add('focused'); };
120
+ row.addEventListener('mouseover', e => { const c = e.target.closest('.nmm-cell'); if (c) focusAt(Number(c.dataset.i)); });
121
+ row.addEventListener('click', e => { const c = e.target.closest('.nmm-cell'); if (c) { env.closeSub(); onChoose(emojis[Number(c.dataset.i)], Number(c.dataset.i)); } });
122
+ env.openSub(anchor, row, e => {
123
+ if (e.key === 'ArrowRight' || e.key === 'ArrowLeft') { e.preventDefault(); focusAt(Math.max(0, Math.min(emojis.length - 1, at + (e.key === 'ArrowRight' ? 1 : -1)))); }
124
+ else if (e.key === 'Enter') { e.preventDefault(); env.closeSub(); onChoose(emojis[at], at); }
125
+ else if (e.key === 'Escape') { e.preventDefault(); env.closeSub(); }
126
+ });
127
+ }
128
+
129
+ /* 749527 tM:“添加表情符号”浮层(在 anchor 下面、左对齐)。存好以后 onDone(表情字符串) */
130
+ export function openCustomEmojiPopup(anchor, { onDone, onClose }) {
131
+ hideTooltip();
132
+ const box = document.createElement('div');
133
+ box.className = 'nmm-custom-emoji-popup';
134
+ box.setAttribute('role', 'dialog');
135
+ box.setAttribute('aria-label', t("添加自定义表情符号"));
136
+ let popup = null;
137
+ const form = createUploadForm({
138
+ showTitle: true, largeEmoji: false, allowUrlPaste: false, confirmToAdd: false,
139
+ onCancel: () => closePopup(popup),
140
+ onStart: () => closePopup(popup), // 963369:保存时 757573 L.dismiss()
141
+ onDone,
142
+ });
143
+ box.append(form.el);
144
+ box.addEventListener('keydown', e => { if (e.key === 'Escape') { e.preventDefault(); e.stopPropagation(); closePopup(popup); } });
145
+ popup = openPopup({ origin: anchor.getBoundingClientRect(), placement: 'bottom', align: 'start', content: box, onClose });
146
+ form.focus();
147
+ return popup;
148
+ }
149
+
150
+ export function createEmojiTab(env) {
151
+ const el = document.createElement('div');
152
+ el.className = 'nmm-body';
153
+ el.innerHTML = `<div class="nmm-scroller notion-scroller vertical"><div role="grid" class="nmm-grid"></div></div><div class="nmm-categories"></div>`;
154
+ const grid = el.querySelector('.nmm-grid'), scroller = el.querySelector('.nmm-scroller'), bar = el.querySelector('.nmm-categories');
155
+ const recent = recentEmojis(PER_ROW);
156
+ let view = { categorized: true, rows: [] }, lastFilter = '', addPopup = null;
157
+ const focus = createGridFocus({ scroller, grid, rows: () => view.rows.map(r => r.emojis.length) });
158
+
159
+ /* 943244 D:选中一个表情——记常用,交给调用方(关菜单) */
160
+ const submit = emoji => { recordEmojiUse(emoji); env.submit(emoji); };
161
+
162
+ function cellHTML(emoji, r, c) {
163
+ if (emoji === ADD) {
164
+ return `<div role="gridcell" class="nmm-cell nmm-add-cell" data-add data-r="${r}" data-c="${c}" aria-label="${ADD_LABEL}">${icon('plusSmall', 16)}</div>`;
165
+ }
166
+ if (isCustomEmojiString(emoji)) {
167
+ const custom = customEmojiOf(emoji);
168
+ const img = custom ? `<img class="notion-custom-emoji" alt="${esc(custom.name)}" src="data:image/gif;base64,R0lGODlhAQABAIAAAP///wAAACH5BAEAAAAALAAAAAABAAEAAAICRAEAOw==" data-src="${esc(custom.url)}" draggable="false" style="width:24px;height:24px">` : '';
169
+ return `<div role="gridcell" class="nmm-cell" data-emoji="${esc(emoji)}" data-r="${r}" data-c="${c}" aria-label="${esc(custom?.name || '')}">${img}</div>`;
170
+ }
171
+ return `<div role="gridcell" class="nmm-cell" data-emoji="${esc(emoji)}" data-r="${r}" data-c="${c}" aria-label="${esc(emojiName(emoji) || '')}">${emojiHTML(emoji, { size: 24, lazy: true })}</div>`;
172
+ }
173
+
174
+ function render(filter) {
175
+ lastFilter = filter;
176
+ if (!emojiDataLoaded()) { grid.innerHTML = ''; bar.hidden = true; view = { categorized: true, rows: [] }; return; } // 数据加载完再画
177
+ view = buildRows(filter, env.isCallout, recent);
178
+ const { rows } = view;
179
+ let html = '';
180
+ if (!view.categorized && rows.length === 1 && rows[0].emojis.length === 1 && rows[0].emojis[0] === ADD) {
181
+ // 943244 q:只剩加号——“无结果”和“添加表情符号”按钮(按钮是唯一一个能聚焦的格子)
182
+ html = `<div class="nmm-empty with-add"><div class="nmm-empty-caption"><div>${t("无结果")}</div></div>` +
183
+ `<div role="gridcell" class="nmm-cell nmm-add-button" data-add data-r="0" data-c="0">${icon('plusSmall', 16)}${ADD_LABEL}</div></div>`;
184
+ } else if (!rows.length) html = `<div class="nmm-empty"><div class="nmm-empty-caption"><div>${t("无结果")}</div></div></div>`;
185
+ else if (!view.categorized) {
186
+ html = `<div class="nmm-section"><div class="nmm-rows">${rows.map((row, r) => `<div role="row" class="nmm-row">${row.emojis.map((e, c) => cellHTML(e, r, c)).join('')}</div>`).join('')}</div></div>`;
187
+ } else {
188
+ rows.forEach((row, r) => {
189
+ if (row.title) html += `${r ? '</div></div>' : ''}<div class="nmm-section" data-section="${row.id}"><div class="nmm-section-title"><div class="nmm-section-title-text">${esc(row.title)}</div></div><div class="nmm-rows">`;
190
+ html += `<div role="row" class="nmm-row">${row.emojis.map((e, c) => cellHTML(e, r, c)).join('')}</div>`;
191
+ });
192
+ html += '</div></div>';
193
+ }
194
+ grid.innerHTML = html;
195
+ scroller.scrollTop = 0;
196
+ renderBar();
197
+ focus.reset(!grid.querySelector('.nmm-empty'));
198
+ focus.observeImages();
199
+ }
200
+
201
+ /* 943244 y:分类栏(标注不显示;“自定义”“添加”总能点) */
202
+ function renderBar() {
203
+ bar.hidden = !view.categorized || !view.rows.length;
204
+ if (bar.hidden) return;
205
+ const present = new Set(view.rows.map(r => r.id));
206
+ const enabled = c => c.id === 'custom' || c.id === 'add' || present.has(c.id);
207
+ bar.innerHTML = CATEGORIES.filter(c => c.id !== 'callout').map(c =>
208
+ `<div role="button" tabindex="-1" class="nmm-category${enabled(c) ? '' : ' disabled'}" data-category="${c.id}" aria-label="${t("跳转到类别:{0}", esc(c.category ?? c.id))}" aria-pressed="false"${enabled(c) ? '' : ' aria-disabled="true"'}>${icon(c.icon, 22)}</div>`).join('');
209
+ for (const b of bar.children) hoverTooltip(b, CATEGORY[b.dataset.category].title, { placement: 'bottom', align: 'start' });
210
+ updateBarFocus();
211
+ }
212
+ /* 当前滚到的分组:第一行露出来的那一组 */
213
+ function updateBarFocus() {
214
+ if (bar.hidden) return;
215
+ const top = scroller.getBoundingClientRect().top;
216
+ let id = null;
217
+ for (const s of grid.querySelectorAll('.nmm-section')) if (s.getBoundingClientRect().bottom > top + 1) { id = s.dataset.section; break; }
218
+ for (const b of bar.children) {
219
+ const on = b.dataset.category === id;
220
+ b.classList.toggle('focused', on);
221
+ b.setAttribute('aria-pressed', String(on));
222
+ }
223
+ }
224
+ scroller.addEventListener('scroll', updateBarFocus, { passive: true });
225
+ bar.addEventListener('click', e => {
226
+ const b = e.target.closest('.nmm-category');
227
+ if (!b || b.classList.contains('disabled')) return;
228
+ if (b.dataset.category === 'add') return openAdd(b);
229
+ const s = grid.querySelector(`.nmm-section[data-section="${b.dataset.category}"]`);
230
+ if (s) scroller.scrollTop = s.offsetTop;
231
+ updateBarFocus();
232
+ });
233
+
234
+ /* 943244 Y / 无结果按钮 / 底栏“添加”:757573 setState({ open: true, originRect }) */
235
+ function openAdd(anchor) {
236
+ env.closeSub();
237
+ addPopup = openCustomEmojiPopup(anchor, { onDone: value => env.uploaded(value), onClose: () => { addPopup = null; env.refocus(); } });
238
+ }
239
+
240
+ /* 625478:点一个表情。没设过肤色、又有肤色变体时先弹出一排变体 */
241
+ function activate(cell) {
242
+ if (cell.hasAttribute('data-add')) return openAdd(cell);
243
+ const emoji = cell.dataset.emoji;
244
+ const variations = getSkinTone() === undefined ? emojiVariations(emoji) : [];
245
+ if (!variations.length) return submit(emoji);
246
+ emojiRow(env, cell, [emoji, ...variations], 0, (picked, i) => {
247
+ if (variations.length === SKIN_TONE_VARIATIONS) setSkinTone(i); // 625478:正好 5 个变体时记下肤色
248
+ submit(picked);
249
+ });
250
+ }
251
+ grid.addEventListener('click', e => {
252
+ const cell = e.target.closest('.nmm-cell');
253
+ if (cell) { hideTooltip(); activate(cell); }
254
+ });
255
+
256
+ /* 885963:选肤色 */
257
+ const right = document.createElement('div');
258
+ right.className = 'nmm-skin-wrap';
259
+ right.innerHTML = `<div role="button" tabindex="0" class="nmm-skin" data-act="skin"></div>`;
260
+ const skinBtn = right.firstElementChild;
261
+ const paintSkin = () => { const tone = getSkinTone(); skinBtn.textContent = tone !== undefined ? SKIN_TONE_HANDS[tone] : '✋'; };
262
+ paintSkin();
263
+ hoverTooltip(skinBtn, t("选择肤色"), { placement: 'bottom' });
264
+ skinBtn.addEventListener('click', () => {
265
+ hideTooltip();
266
+ emojiRow(env, skinBtn, SKIN_TONE_HANDS, getSkinTone() ?? 0, (_, i) => { setSkinTone(i); paintSkin(); render(lastFilter); });
267
+ });
268
+
269
+ return {
270
+ el, right,
271
+ load: () => Promise.all([loadEmojiData(), loadCustomEmojis()]),
272
+ render,
273
+ move: key => focus.move(key),
274
+ activateFocused() { const cell = focus.focused(); if (cell) activate(cell); },
275
+ random: () => env.keepOpenPick(randomEmoji()), // 485357:随机的选上但不关菜单,也不记常用
276
+ destroy: () => { focus.destroy(); if (addPopup && !addPopup.closed) closePopup(addPopup); },
277
+ };
278
+ }
@@ -0,0 +1,26 @@
1
+ import { glyphSVG } from '../../../shared/emoji/glyphs.mjs';
2
+ import { esc } from './support.mjs';
3
+ import { language } from '../../../shared/i18n/index.mjs';
4
+
5
+ // What the picker's icon grid draws an icon of the 图标 tab with: its SVG inline (an <img> of a
6
+ // data: URL is a document of its own each: a grid of hundreds held the page up for seconds as a
7
+ // filter was typed), in the theme's colors. The sets' SVGs hold paths only (no ids to make unique).
8
+
9
+ /** Light or dark: the report's theme, the workbench's, else the system's. */
10
+ export function themeMode() {
11
+ const root = globalThis.document?.documentElement;
12
+ const set = root?.getAttribute('data-doc-theme') ?? root?.getAttribute('data-theme');
13
+ if (set === 'dark' || set === 'light') return set;
14
+ return globalThis.matchMedia?.('(prefers-color-scheme: dark)').matches ? 'dark' : 'light';
15
+ }
16
+
17
+ /** What an icon is called in the UI's language: its Chinese name, or in English its name in `set` (the one set it has). */
18
+ export const glyphName = (pair, set) => (language === 'en' ? pair.names[set] ?? pair.names.tabler ?? pair.label : pair.label);
19
+
20
+ /** Pair `pair`'s icon of `set` in `color`, as its SVG inline, `size` px (or as large as where it stands). */
21
+ export function glyphHTML(pair, set, color, { size, mode = themeMode() } = {}) {
22
+ const side = size ? (typeof size === 'number' ? `${size}px` : size) : '100%';
23
+ if (!pair) return `<span style="display:inline-block;width:${side};height:${side}"></span>`;
24
+ return glyphSVG(pair, set, color, mode)
25
+ .replace('<svg ', `<svg class="ge-glyph" role="img" aria-label="${esc(`${glyphName(pair, set)} ${color}`)}" style="width:${side};height:${side};display:block;flex:none" `);
26
+ }
@@ -0,0 +1,79 @@
1
+ // Taken over from notion-lite (its src/ui/media-picker/grid.js), as it is: only what it imports is
2
+ // Gallery's own (support.mjs, src/shared/emoji/). Its notes, below, are notion-lite's.
3
+ /* 表情 / 图标格子共用的焦点(558045 Grid + 625478 / 485357 H 的提示):
4
+ * 鼠标悬停和方向键共用一个焦点(有底色);方向键不绕回,上下按列对齐(短的一行取最后一个);键盘移动时焦点格有蓝色焦点环、
5
+ * 滚进视野,并且一直显示名字(forceVisibleState);鼠标悬停 150ms 后在下方显示名字(closeDelay 0)。
6
+ * 懒加载:格子里 img[data-src] / img[data-svg](表情包里的码点)滚到附近才换成 src(../emoji/emoji.js lazySrc;矢量表情一千多张,一次全做太慢)。
7
+ * 格子是 .nmm-cell[data-r][data-c],提示文字在 data-tip(没有就用 aria-label)。
8
+ * createGridFocus({ scroller, grid, rows }) → { reset(focusFirst), move(key), focused(), observeImages(), destroy() };rows() 返回每行的格子数;
9
+ * reset(false) 不聚焦任何格子(943244 无结果时 unsetFocus,方向键再从第一个开始);没有提示文字的格子不显示提示
10
+ * 依赖:lib/dom、ui/tooltip、ui/emoji/emoji
11
+ */
12
+ import { showTooltip, hideTooltip, isKeyboardMode } from './support.mjs';
13
+ import { lazySrc } from '../../../shared/emoji/emoji.mjs';
14
+
15
+ export function createGridFocus({ scroller, grid, rows }) {
16
+ let focus = null, tipTimer = 0;
17
+ const cellAt = f => f && grid.querySelector(`.nmm-cell[data-r="${f.r}"][data-c="${f.c}"]`);
18
+ const tipOf = cell => cell.dataset.tip ?? cell.getAttribute('aria-label') ?? '';
19
+
20
+ function set(f, byKeyboard) {
21
+ cellAt(focus)?.classList.remove('focused', 'focus-visible');
22
+ focus = f;
23
+ const cell = cellAt(f);
24
+ if (!cell) return;
25
+ cell.classList.add('focused');
26
+ if (!byKeyboard) return;
27
+ cell.classList.add('focus-visible');
28
+ const cr = cell.getBoundingClientRect(), sr = scroller.getBoundingClientRect();
29
+ if (cr.top < sr.top) scroller.scrollTop -= sr.top - cr.top;
30
+ else if (cr.bottom > sr.bottom) scroller.scrollTop += cr.bottom - sr.bottom;
31
+ if (tipOf(cell)) showTooltip(cell.getBoundingClientRect(), tipOf(cell), { placement: 'bottom' });
32
+ }
33
+
34
+ function move(key) {
35
+ const lens = rows();
36
+ if (!lens.length) return;
37
+ if (!focus) return set({ r: 0, c: 0 }, true);
38
+ let { r, c } = focus;
39
+ if (key === 'ArrowRight') { if (c + 1 < lens[r]) c++; else if (r + 1 < lens.length) { r++; c = 0; } }
40
+ else if (key === 'ArrowLeft') { if (c > 0) c--; else if (r > 0) { r--; c = lens[r] - 1; } }
41
+ else if (key === 'ArrowDown') { if (r + 1 < lens.length) { r++; c = Math.min(c, lens[r] - 1); } }
42
+ else if (key === 'ArrowUp') { if (r > 0) { r--; c = Math.min(c, lens[r] - 1); } }
43
+ set({ r, c }, true);
44
+ }
45
+
46
+ const onOver = e => {
47
+ const cell = e.target.closest('.nmm-cell');
48
+ if (!cell || cell === cellAt(focus) && !cell.classList.contains('focus-visible')) return;
49
+ set({ r: Number(cell.dataset.r), c: Number(cell.dataset.c) }, false);
50
+ hideTooltip();
51
+ clearTimeout(tipTimer);
52
+ if (isKeyboardMode()) return;
53
+ if (!tipOf(cell)) return;
54
+ tipTimer = setTimeout(() => { if (cell.isConnected && cellAt(focus) === cell) showTooltip(cell.getBoundingClientRect(), tipOf(cell), { placement: 'bottom' }); }, 150);
55
+ };
56
+ const onLeave = () => { clearTimeout(tipTimer); hideTooltip(); };
57
+ grid.addEventListener('mouseover', onOver);
58
+ grid.addEventListener('mouseleave', onLeave);
59
+ scroller.addEventListener('scroll', hideTooltip, { passive: true });
60
+
61
+ const io = new IntersectionObserver(entries => {
62
+ for (const en of entries) {
63
+ if (!en.isIntersecting) continue;
64
+ const img = en.target;
65
+ img.src = lazySrc(img);
66
+ img.removeAttribute('data-src');
67
+ img.removeAttribute('data-svg');
68
+ io.unobserve(img);
69
+ }
70
+ }, { root: scroller, rootMargin: '160px 0px' });
71
+
72
+ return {
73
+ reset(focusFirst = true) { set(focusFirst && rows().length ? { r: 0, c: 0 } : null, false); },
74
+ move,
75
+ focused: () => cellAt(focus),
76
+ observeImages() { io.disconnect(); for (const img of grid.querySelectorAll('img[data-src], img[data-svg]')) io.observe(img); },
77
+ destroy() { clearTimeout(tipTimer); io.disconnect(); },
78
+ };
79
+ }
@@ -0,0 +1,217 @@
1
+ // The 图标 tab (notion-lite's src/ui/media-picker/icon-tab.js, its grid, colors and sizes as there),
2
+ // its icons Gallery's own: two open-source sets of the same 443 things, MingCute and Tabler, and
3
+ // Tabler's 40 numbers, in 12 categories (src/shared/emoji/glyphs.mjs). Its notes, below, are
4
+ // notion-lite's, the icons' own changed.
5
+ /* “图标”页签(485357 的 Z 列表、H 格子、W / z 颜色变体、q 选颜色按钮、J 存颜色;111012 颜色;尺寸是线上实测)。
6
+ * 分组:最近(没有筛选词、用过的时候;最多 2 × 12 个)、12 个分类(数字与符号……品牌与娱乐,顺序同 icons.json,像表情符号页签的分组那样
7
+ * 一组一个标题);有筛选词时拍平成一组,没有显示“无结果”
8
+ * 每组外面 4px、标题 12px / 500、行高 14.4、左右 8、上 6 下 8;行左右 12,每行 12 个;没有底部分类栏,列表占满 300 高
9
+ * 数字与符号里先是成对的图标,再是 Tabler 的 40 个数字:每套(圆形、方形、圆角方形、六边形)0–9 自成一行
10
+ * 格子:32×32、圆角 8,图片 24(内联 SVG,./glyph-html),悬停 / 键盘提示中文名和这一套里的名字
11
+ * 哪一套:默认 MingCute;随机按钮左边的切换按钮(写着现在这一套的名字)换成 Tabler,每个格子原地换成同一组的另一个
12
+ * (位置、滚动、筛选都不动,方便对比),再点换回来;这个选择存在这个浏览器里
13
+ * 数字只有 Tabler 有:切换时不动,选中的也总是 Tabler 的值(提示里写明 Tabler)
14
+ * 颜色(icon_picker_color):设了就直接用这个颜色插入、格子也显示这个颜色;没设(“每次询问”)时格子显示默认灰色,
15
+ * 点一下先弹出 10 种颜色(两行各 5 个、行内边距 2、间距 1,贴在格子下面)再选
16
+ * 右边按钮(q):选图标颜色——28×28 带边框,圆圈图标描边 / 填充是当前颜色(没设时描边浅灰、填充 --c-icoTer);
17
+ * 菜单 134 宽:两行色块(22×22、圆角 6,没设颜色时这两行半透明)+ 分隔线下“每次询问”开关
18
+ * 随机:随便一组里这一套的图标,颜色用设好的,没设就随便一种;选上但不关菜单
19
+ * 选中一个图标:记进最近(按组记,两套共用),值是 `/icons/<名字>_<颜色>.svg`(MingCute)或 `/icons/tabler/<名字>_<颜色>.svg`(数字总是这个)。
20
+ * createIconTab(env) → { el, left, right, load(), render(filter), move(key), activateFocused(), random() }
21
+ */
22
+ import { esc } from './support.mjs';
23
+ import { hoverTooltip, hideTooltip } from './support.mjs';
24
+ import { glyphHTML, glyphName, themeMode } from './glyph-html.mjs';
25
+ import {
26
+ loadGlyphs, glyphsLoaded, allPairs, glyphCategories, pairOf, onlySetOf, pairValue, searchGlyphs, randomGlyph, getGlyphSet, setGlyphSet, GLYPH_SET_NAMES,
27
+ getIconColor, setIconColor, recentGlyphs, recordGlyphUse, ICON_COLOR_NAMES, ICON_COLOR_BY_THEME,
28
+ } from '../../../shared/emoji/glyphs.mjs';
29
+ import { GLYPH_SETS, ICON_COLORS } from '../../../shared/emoji/icon-value.mjs';
30
+ import { createGridFocus } from './grid.mjs';
31
+ import { PER_ROW } from './emoji-tab.mjs';
32
+ import { language, t } from "../../../shared/i18n/index.mjs";
33
+
34
+ const MAX_RECENT = 2 * 12; // 485357 w2:2 × uu()
35
+ // The ten colors' names (glyphs.mjs ICON_COLOR_NAMES: its Chinese) in the language in use.
36
+ const COLOR_WORDS = { gray: t("默认"), lightgray: t("浅灰色"), brown: t("棕色"), yellow: t("黄色"), orange: t("橙色"), green: t("绿色"), blue: t("蓝色"), purple: t("紫色"), pink: t("粉色"), red: t("红色") };
37
+ const colorWord = (color) => COLOR_WORDS[color] ?? ICON_COLOR_NAMES[color];
38
+ const theme = themeMode; // the report's theme (glyph-html.mjs)
39
+ const CIRCLE_16 = '<circle cx="8" cy="8" r="6.1"/>';
40
+ const CIRCLE_20 = '<circle cx="10" cy="10" r="7.6"/>';
41
+ // The categories' titles, by their names as icons.json has them (Chinese), in the language in use:
42
+ // each written out for t() (and en.mjs). A category not here shows its name as it is.
43
+ const CATEGORY_TITLES = {
44
+ 数字与符号: t("数字与符号"), 办公与学习: t("办公与学习"), 界面与操作: t("界面与操作"), 箭头与导航: t("箭头与导航"),
45
+ 设计与影音: t("设计与影音"), 设备与科技: t("设备与科技"), 沟通与表情: t("沟通与表情"), 交通与建筑: t("交通与建筑"),
46
+ 自然与天气: t("自然与天气"), 生活与消费: t("生活与消费"), 健康与运动: t("健康与运动"), 品牌与娱乐: t("品牌与娱乐"),
47
+ };
48
+
49
+ // A section's keys as rows of PER_ROW: a category's pairs, then each series of the icons one set has
50
+ // alone (a name but its last word: circle-number-0…9) on rows of its own, so 0–9 of a shape read as one
51
+ // row; recent icons and a search's, PER_ROW a row as they come.
52
+ function rowsOf(keys, bySeries) {
53
+ const runs = [];
54
+ let last = null;
55
+ for (const key of keys) {
56
+ const pair = pairOf(key), only = onlySetOf(pair);
57
+ const series = bySeries && only ? pair.names[only].replace(/-[^-]+$/, '') : '';
58
+ if (!runs.length || series !== last) runs.push([]);
59
+ runs[runs.length - 1].push(key);
60
+ last = series;
61
+ }
62
+ return runs.flatMap(run => Array.from({ length: Math.ceil(run.length / PER_ROW) }, (_, i) => run.slice(i * PER_ROW, (i + 1) * PER_ROW)));
63
+ }
64
+
65
+ export function createIconTab(env) {
66
+ const el = document.createElement('div');
67
+ el.className = 'nmm-body';
68
+ el.innerHTML = `<div class="nmm-scroller nmm-icon-scroller notion-scroller vertical"><div role="grid" class="nmm-grid nmm-icon-grid"></div></div>`;
69
+ const grid = el.querySelector('.nmm-grid'), scroller = el.querySelector('.nmm-scroller');
70
+ let rows = [];
71
+ const focus = createGridFocus({ scroller, grid, rows: () => rows.map(r => r.length) });
72
+
73
+ // Its value in the set shown, or in the one set it has (a number: Tabler's, whichever is shown).
74
+ const insert = (key, color) => { recordGlyphUse(key, MAX_RECENT); env.submit(pairValue(pairOf(key), getGlyphSet(), color)); };
75
+
76
+ // A cell's tip: the icon's Chinese name, and its name in the set shown (one only one set has, a
77
+ // number: that set's, named, in either); in English that name alone.
78
+ const tip = (pair, set) => {
79
+ const only = onlySetOf(pair);
80
+ const own = only ? `${GLYPH_SET_NAMES[only]} ${pair.names[only]}` : pair.names[set];
81
+ return language === "en" ? own : `${pair.label}(${own})`;
82
+ };
83
+ const cellHTML = (key, color, r, c) => {
84
+ const pair = pairOf(key), set = getGlyphSet();
85
+ return `<div role="gridcell" class="nmm-cell nmm-icon-cell" data-icon="${esc(key)}" data-r="${r}" data-c="${c}" aria-label="${esc(`${tip(pair, set)} ${color}`)}" data-tip="${esc(tip(pair, set))}">${glyphHTML(pair, set, color, { size: 24 })}</div>`;
86
+ };
87
+
88
+ function render(filter) {
89
+ if (!glyphsLoaded()) { grid.innerHTML = ''; rows = []; return; }
90
+ const color = getIconColor() ?? 'gray';
91
+ const q = filter.trim() ? filter : '';
92
+ const sections = q
93
+ ? [{ keys: searchGlyphs(q) }]
94
+ : [
95
+ { id: 'recent', title: t("最近"), keys: recentGlyphs().filter(k => pairOf(k)) },
96
+ ...glyphCategories().map((name, at) => ({ id: String(at), title: CATEGORY_TITLES[name] ?? name, keys: allPairs().filter(p => p.category === name).map(p => p.key), bySeries: true })),
97
+ ];
98
+ rows = [];
99
+ let html = '';
100
+ for (const s of sections) {
101
+ if (!s.keys.length) continue;
102
+ html += `<div class="nmm-section"${s.id ? ` data-section="${s.id}"` : ''}>${s.title ? `<div class="nmm-section-title"><div class="nmm-section-title-text">${esc(s.title)}</div></div>` : ''}<div class="nmm-rows">`;
103
+ for (const row of rowsOf(s.keys, s.bySeries)) {
104
+ const r = rows.length;
105
+ rows.push(row);
106
+ html += `<div role="row" class="nmm-row">${row.map((k, c) => cellHTML(k, color, r, c)).join('')}</div>`;
107
+ }
108
+ html += '</div></div>';
109
+ }
110
+ grid.innerHTML = html || `<div class="nmm-empty"><div class="nmm-empty-caption"><div>${t("无结果")}</div></div></div>`;
111
+ scroller.scrollTop = 0;
112
+ focus.reset();
113
+ }
114
+
115
+ // The other set, in place: each cell's icon becomes its pair's of that set; where the grid is
116
+ // scrolled to, the filter and the key focus stay. An icon one set has alone (a number) stays as it is.
117
+ function swapSet() {
118
+ env.closeSub();
119
+ hideTooltip();
120
+ setGlyphSet(GLYPH_SETS.find(each => each !== getGlyphSet()));
121
+ const set = getGlyphSet(), color = getIconColor() ?? 'gray';
122
+ for (const cell of grid.querySelectorAll('.nmm-cell[data-icon]')) {
123
+ const pair = pairOf(cell.dataset.icon);
124
+ if (onlySetOf(pair)) continue;
125
+ cell.innerHTML = glyphHTML(pair, set, color, { size: 24 });
126
+ cell.dataset.tip = tip(pair, set);
127
+ cell.setAttribute('aria-label', `${tip(pair, set)} ${color}`);
128
+ }
129
+ paintSet();
130
+ }
131
+
132
+ /* 485357 W / z:没设颜色时先选颜色(两行各 5 个) */
133
+ function activate(cell) {
134
+ const key = cell.dataset.icon, color = getIconColor(), pair = pairOf(key), set = getGlyphSet();
135
+ if (color) return insert(key, color);
136
+ const pop = document.createElement('div');
137
+ pop.className = 'nmm-icon-variations';
138
+ pop.innerHTML = [ICON_COLORS.slice(0, 5), ICON_COLORS.slice(5)].map((row, r) =>
139
+ `<div role="row" class="nmm-icon-variations-row">${row.map((c, i) => `<div role="gridcell" class="nmm-cell nmm-icon-cell${r === 0 && i === 0 ? ' focused' : ''}" data-color="${c}" data-i="${r * 5 + i}" aria-label="${esc(`${glyphName(pair, set)} ${c}`)}">${glyphHTML(pair, set, c, { size: 24 })}</div>`).join('')}</div>`).join('');
140
+ const cells = [...pop.querySelectorAll('.nmm-cell')];
141
+ let at = 0;
142
+ const focusAt = i => { cells[at]?.classList.remove('focused'); at = Math.max(0, Math.min(cells.length - 1, i)); cells[at].classList.add('focused'); };
143
+ pop.addEventListener('mouseover', e => { const c = e.target.closest('.nmm-cell'); if (c) focusAt(Number(c.dataset.i)); });
144
+ pop.addEventListener('click', e => { const c = e.target.closest('.nmm-cell'); if (c) { env.closeSub(); insert(key, c.dataset.color); } });
145
+ env.openSub(cell, pop, e => {
146
+ const step = { ArrowRight: 1, ArrowLeft: -1, ArrowDown: 5, ArrowUp: -5 }[e.key];
147
+ if (step) { e.preventDefault(); focusAt(at + step); }
148
+ else if (e.key === 'Enter') { e.preventDefault(); env.closeSub(); insert(key, cells[at].dataset.color); }
149
+ else if (e.key === 'Escape') { e.preventDefault(); env.closeSub(); }
150
+ }, { gap: 0 });
151
+ }
152
+ grid.addEventListener('click', e => {
153
+ const cell = e.target.closest('.nmm-cell');
154
+ if (cell) { hideTooltip(); activate(cell); }
155
+ });
156
+
157
+ /* Left of 随机: the set shown, a click the other one (in place). */
158
+ const left = document.createElement('div');
159
+ left.className = 'nmm-set-wrap';
160
+ left.innerHTML = `<div role="button" tabindex="0" class="nmm-set-toggle" data-act="glyph-set"></div>`;
161
+ const setBtn = left.firstElementChild;
162
+ function paintSet() {
163
+ const set = getGlyphSet(), other = GLYPH_SETS.find(each => each !== set);
164
+ setBtn.textContent = GLYPH_SET_NAMES[set];
165
+ setBtn.dataset.set = set;
166
+ setBtn.setAttribute('aria-label', t("图标:{0},切换为 {1}", GLYPH_SET_NAMES[set], GLYPH_SET_NAMES[other]));
167
+ setBtn.setAttribute('aria-pressed', String(set !== GLYPH_SETS[0]));
168
+ }
169
+ paintSet();
170
+ hoverTooltip(setBtn, () => t("切换为 {0} 图标", GLYPH_SET_NAMES[GLYPH_SETS.find(each => each !== getGlyphSet())]), { placement: 'bottom' });
171
+ setBtn.addEventListener('click', swapSet);
172
+
173
+ /* 485357 q:选图标颜色 */
174
+ const right = document.createElement('div');
175
+ right.className = 'nmm-skin-wrap';
176
+ right.innerHTML = `<div role="button" tabindex="0" class="nmm-color-button" data-act="icon-color" aria-haspopup="dialog"></div>`;
177
+ const colorBtn = right.firstElementChild;
178
+ function paintColor() {
179
+ const color = getIconColor(), values = ICON_COLOR_BY_THEME[theme()];
180
+ colorBtn.setAttribute('aria-label', t("选择图标颜色,已选定 {0}", color ? colorWord(color) : t("无颜色")));
181
+ colorBtn.innerHTML = `<svg viewBox="0 0 16 16" aria-hidden="true" style="width:14px;height:14px;display:block;stroke:${color ? values[color] : values.lightgray};fill:${color ? values[color] : 'var(--c-icoTer)'}">${CIRCLE_16}</svg>`;
182
+ }
183
+ paintColor();
184
+ hoverTooltip(colorBtn, t("选择图标颜色"), { placement: 'bottom' });
185
+ colorBtn.addEventListener('click', () => { hideTooltip(); openColorMenu(); });
186
+
187
+ function openColorMenu() {
188
+ const color = getIconColor(), values = ICON_COLOR_BY_THEME[theme()];
189
+ const menu = document.createElement('div');
190
+ menu.className = 'nmm-color-menu';
191
+ const swatch = c => `<div role="gridcell" class="nmm-color-swatch${c === color ? ' selected' : ''}" data-color="${c}" aria-label="${t("将颜色设置为{0}", colorWord(c))}">` +
192
+ `<svg viewBox="0 0 20 20" aria-hidden="true" style="width:20px;height:20px;stroke:${values[c]};fill:${values[c]}">${CIRCLE_20}</svg></div>`;
193
+ menu.innerHTML =
194
+ [ICON_COLORS.slice(0, 5), ICON_COLORS.slice(5)].map(row => `<div role="row" class="nmm-color-row${color === undefined ? ' dim' : ''}">${row.map(swatch).join('')}</div>`).join('') +
195
+ `<div role="row" class="nmm-color-ask"><div role="gridcell" class="nmm-color-ask-item" data-act="ask"><div class="nmm-color-ask-label">${t("每次询问")}</div>` +
196
+ `<div class="nmm-switch${color === undefined ? ' on' : ''}"><div class="nmm-switch-knob"></div></div></div></div>`;
197
+ menu.addEventListener('click', e => {
198
+ const sw = e.target.closest('.nmm-color-swatch');
199
+ if (sw) { setIconColor(sw.dataset.color); env.closeSub(); paintColor(); render(env.filter()); return; }
200
+ if (e.target.closest('[data-act="ask"]')) {
201
+ setIconColor(getIconColor() !== undefined ? undefined : 'gray'); // 485357 q:设了颜色 → 清掉(打开“每次询问”);没设 → 设成默认灰(关掉)
202
+ env.closeSub(); paintColor(); render(env.filter());
203
+ }
204
+ });
205
+ env.openSub(colorBtn, menu, e => { if (e.key === 'Escape') { e.preventDefault(); env.closeSub(); } }, { gap: 4 });
206
+ }
207
+
208
+ return {
209
+ el, left, right,
210
+ load: loadGlyphs,
211
+ render,
212
+ move: key => focus.move(key),
213
+ activateFocused() { const cell = focus.focused(); if (cell) activate(cell); },
214
+ random: () => env.keepOpenPick(randomGlyph()),
215
+ destroy: () => focus.destroy(),
216
+ };
217
+ }
@@ -0,0 +1,32 @@
1
+ import { FACE_ICON, PHOTO_ICON, svg } from "../../components/icons.mjs";
2
+
3
+ // The icons the icon picker shows: the editor's own line drawings (components/icons.mjs svg) on 20
4
+ // units, no color of their own. icon(name, size) sets the size they show at; the picker's styles
5
+ // (styles.mjs) set their line and color.
6
+
7
+ const ICONS = {
8
+ clock: svg('<circle cx="10" cy="10" r="7.25"/><path d="M10 5.75V10l3 1.75"/>'),
9
+ emojiFace: FACE_ICON,
10
+ leaf: svg('<path d="M16.25 3.75C9 3.75 4.25 7.4 4.25 12.4c0 1.3.4 2.4 1.1 3.35 6 .2 10.9-3.4 10.9-12z"/><path d="M5.25 15.5 11 9.25"/>'),
11
+ carrot: svg('<path d="M3.75 16.25 7.9 8.1c.5-1 1.8-1.2 2.6-.4l1.9 1.9c.8.8.6 2.1-.4 2.6z"/><path d="M10.2 7.3C9.9 5.2 10.6 3.6 12.3 2.6M11.3 8.4l3.4-3.4M12.6 9.8c2.1-.4 3.6-.1 4.7 1.2"/>'),
12
+ soccerBall: svg('<circle cx="10" cy="10" r="7.5"/><path d="m10 7.4 2.5 1.8-.95 2.95h-3.1L7.5 9.2z"/><path d="M10 7.4V2.5M12.5 9.2l4.6-1.5M11.55 12.15l2.9 4M8.45 12.15l-2.9 4M7.5 9.2 2.9 7.7"/>'),
13
+ airplane: svg('<path d="M17.25 10c0-.9-.8-1.5-1.7-1.5H11L7.5 3.5H5.75l1.75 5H4.25L3 7H2l.75 3L2 13h1l1.25-1.5H7.5l-1.75 5H7.5L11 11.5h4.55c.9 0 1.7-.6 1.7-1.5z"/>'),
14
+ lightBulbBright: svg('<path d="M10 2.75a5 5 0 0 0-3 9c.6.5 1 1.2 1 2v.5h4v-.5c0-.8.4-1.5 1-2a5 5 0 0 0-3-9z"/><path d="M8.25 16.5h3.5"/>'),
15
+ checkmarkCircle: svg('<circle cx="10" cy="10" r="7.25"/><path d="m6.75 10.25 2.4 2.4 4.1-4.9"/>'),
16
+ flag: svg('<path d="M5.25 17V3.75"/><path d="M5.25 4.75c2.5-1.5 4.5 1.5 7 0 1-.6 2-.8 2.75-.7v6.5c-.75-.1-1.75.1-2.75.7-2.5 1.5-4.5-1.5-7 0"/>'),
17
+ squareGrid2X2: svg('<rect x="3.5" y="3.5" width="5" height="5" rx="1.25"/><rect x="11.5" y="3.5" width="5" height="5" rx="1.25"/><rect x="3.5" y="11.5" width="5" height="5" rx="1.25"/><rect x="11.5" y="11.5" width="5" height="5" rx="1.25"/>'),
18
+ plusCircle: svg('<circle cx="10" cy="10" r="7.25"/><path d="M10 6.75v6.5M6.75 10h6.5"/>'),
19
+ xMarkCircle: svg('<circle cx="10" cy="10" r="7.25"/><path d="m7.75 7.75 4.5 4.5m0-4.5-4.5 4.5"/>'),
20
+ photo: PHOTO_ICON,
21
+ plusSmall: svg('<path d="M10 4.5v11M4.5 10h11"/>'),
22
+ magnifyingGlassSmall: svg('<circle cx="9" cy="9" r="5.5"/><path d="m13.25 13.25 3.75 3.75"/>'),
23
+ // Two lines crossing, each ending in an arrow: 随机.
24
+ arrowIntersectRightSmall: svg('<path d="M3 6h2.4c2 0 3.3 1.3 4.6 3.1M11.3 10.9c1.3 1.8 2.6 3.1 4.6 3.1H17M14.75 11.75 17 14l-2.25 2.25"/><path d="M3 14h2.4c2 0 3.3-1.3 4.6-3.1M11.3 9.1C12.6 7.3 13.9 6 15.9 6H17M14.75 3.75 17 6l-2.25 2.25"/>'),
25
+ // A ring with an arrowhead at its open end: 替换.
26
+ arrowCircleLoopBackwardSmall: svg('<path d="M15.5 10a5.5 5.5 0 1 1-1.9-4.15"/><path d="M15.5 4.25v3.25h-3.25"/>'),
27
+ };
28
+
29
+ /** The icon `name` as an svg of `size` px (its own size when none). */
30
+ export function icon(name, size = 20) {
31
+ return ICONS[name].replace("<svg ", `<svg width="${size}" height="${size}" `);
32
+ }