@zaly/tui 0.0.6 → 0.0.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (206) hide show
  1. package/assets/schemas/theme.schema.json +272 -270
  2. package/assets/themes/kanagawa-dragon.json +3 -0
  3. package/assets/themes/kanagawa-wave.json +3 -0
  4. package/dist/{actions-CnVzKVID.d.mts → actions-DFboj3g5.d.mts} +4 -4
  5. package/dist/{actions-CnVzKVID.d.mts.map → actions-DFboj3g5.d.mts.map} +1 -1
  6. package/dist/ansi.d.mts +10 -11
  7. package/dist/ansi.d.mts.map +1 -1
  8. package/dist/ansi.mjs +1 -2
  9. package/dist/{autocomplete-Dfw-yQDa.d.mts → autocomplete-CxzetPOo.d.mts} +4 -4
  10. package/dist/{autocomplete-Dfw-yQDa.d.mts.map → autocomplete-CxzetPOo.d.mts.map} +1 -1
  11. package/dist/{box-DepqUtuo.mjs → box-DLEcEvDH.mjs} +18 -11
  12. package/dist/box-DLEcEvDH.mjs.map +1 -0
  13. package/dist/{builder-DTz5mppV.mjs → builder-IkMf7I8z.mjs} +5 -4
  14. package/dist/builder-IkMf7I8z.mjs.map +1 -0
  15. package/dist/{callbacks-DcMBGQEO.mjs → callbacks-D132G8dy.mjs} +7 -6
  16. package/dist/callbacks-D132G8dy.mjs.map +1 -0
  17. package/dist/{client-BBdtbLp4.mjs → client-C2GXKfJ1.mjs} +63 -9
  18. package/dist/client-C2GXKfJ1.mjs.map +1 -0
  19. package/dist/client-bzdHIDL2.mjs +1 -0
  20. package/dist/{clipboard-l_TWxxTf.mjs → clipboard-CNPBTX7j.mjs} +9 -7
  21. package/dist/{clipboard-l_TWxxTf.mjs.map → clipboard-CNPBTX7j.mjs.map} +1 -1
  22. package/dist/clipboard.d.mts +6 -7
  23. package/dist/clipboard.d.mts.map +1 -1
  24. package/dist/clipboard.mjs +1 -2
  25. package/dist/{ctx-DjJ1zSbs.mjs → ctx-CXjkWABc.mjs} +3 -3
  26. package/dist/{ctx-DjJ1zSbs.mjs.map → ctx-CXjkWABc.mjs.map} +1 -1
  27. package/dist/ctx-Dh6slUVy.mjs +1 -0
  28. package/dist/{divider-cclEAdPx.mjs → divider-l0-JPEIm.mjs} +2 -2
  29. package/dist/{divider-cclEAdPx.mjs.map → divider-l0-JPEIm.mjs.map} +1 -1
  30. package/dist/{files-Aw3iWpXD.d.mts → files-BUsa-RVl.d.mts} +3 -3
  31. package/dist/{files-Aw3iWpXD.d.mts.map → files-BUsa-RVl.d.mts.map} +1 -1
  32. package/dist/{github-DS00VoOj.d.mts → github-D89A3F9U.d.mts} +3 -3
  33. package/dist/{github-DS00VoOj.d.mts.map → github-D89A3F9U.d.mts.map} +1 -1
  34. package/dist/{image-BTxDPPiT.d.mts → image-34bU73bW.d.mts} +2 -2
  35. package/dist/{image-BTxDPPiT.d.mts.map → image-34bU73bW.d.mts.map} +1 -1
  36. package/dist/image.d.mts +14 -15
  37. package/dist/image.d.mts.map +1 -1
  38. package/dist/image.mjs +1 -2
  39. package/dist/index.d.mts +13 -13
  40. package/dist/index.d.mts.map +1 -1
  41. package/dist/index.mjs +5 -5
  42. package/dist/{input-CRBuTrsL.mjs → input-D7fQEUdt.mjs} +3 -3
  43. package/dist/input-D7fQEUdt.mjs.map +1 -0
  44. package/dist/{input-B5Vy-iaa.d.mts → input-Dylds_sI.d.mts} +3 -3
  45. package/dist/input-Dylds_sI.d.mts.map +1 -0
  46. package/dist/{inspect-D6FW_QUo.d.mts → inspect-DPLRum7L.d.mts} +2 -2
  47. package/dist/{inspect-D6FW_QUo.d.mts.map → inspect-DPLRum7L.d.mts.map} +1 -1
  48. package/dist/{inspect-DE5goDzB.mjs → inspect-xR9KKdk9.mjs} +3 -3
  49. package/dist/{inspect-DE5goDzB.mjs.map → inspect-xR9KKdk9.mjs.map} +1 -1
  50. package/dist/kitty-JbCJC0iQ.mjs.map +1 -1
  51. package/dist/{log-Djvrxqk0.mjs → log-CnewrxAc.mjs} +4 -4
  52. package/dist/{log-Djvrxqk0.mjs.map → log-CnewrxAc.mjs.map} +1 -1
  53. package/dist/{logger-DDrt03So.mjs → logger-CWEGIWaG.mjs} +3 -3
  54. package/dist/logger-CWEGIWaG.mjs.map +1 -0
  55. package/dist/{markdown-CTlPe5ks.mjs → markdown-C6UVXJoj.mjs} +7 -7
  56. package/dist/markdown-C6UVXJoj.mjs.map +1 -0
  57. package/dist/markdown.d.mts +5 -5
  58. package/dist/markdown.d.mts.map +1 -1
  59. package/dist/markdown.mjs +1 -2
  60. package/dist/md.bun.d.mts +1 -2
  61. package/dist/md.bun.d.mts.map +1 -1
  62. package/dist/md.node.d.mts +1 -2
  63. package/dist/md.node.d.mts.map +1 -1
  64. package/dist/node-BZ7f6HzU.mjs.map +1 -1
  65. package/dist/{overlay-9xNgsuuy.mjs → overlay-9WXYiGgW.mjs} +2 -2
  66. package/dist/{overlay-9xNgsuuy.mjs.map → overlay-9WXYiGgW.mjs.map} +1 -1
  67. package/dist/{picker-cH-rc7-X.mjs → picker-BqHINl_a.mjs} +4 -4
  68. package/dist/picker-BqHINl_a.mjs.map +1 -0
  69. package/dist/{picker-D8OLb6kZ.d.mts → picker-JL8lZfRH.d.mts} +5 -5
  70. package/dist/{picker-D8OLb6kZ.d.mts.map → picker-JL8lZfRH.d.mts.map} +1 -1
  71. package/dist/queries-B_lOwEiE.mjs.map +1 -1
  72. package/dist/{queries-DH3bj74K.d.mts → queries-Cvalgu6P.d.mts} +3 -3
  73. package/dist/queries-Cvalgu6P.d.mts.map +1 -0
  74. package/dist/reactive-f7NpAi69.mjs.map +1 -1
  75. package/dist/{registry-w_w7gZr_.mjs → registry-JjYaWUZz.mjs} +2 -2
  76. package/dist/registry-JjYaWUZz.mjs.map +1 -0
  77. package/dist/{render-F8pVXN7h.mjs → render-DtRw_LwV.mjs} +2 -2
  78. package/dist/{render-F8pVXN7h.mjs.map → render-DtRw_LwV.mjs.map} +1 -1
  79. package/dist/{renderer-uMeDzF9B.mjs → renderer-BOqnFB5U.mjs} +7 -7
  80. package/dist/renderer-BOqnFB5U.mjs.map +1 -0
  81. package/dist/renderer-BSMOuiLM.mjs +1 -0
  82. package/dist/{renderer-qSMVeNSV.mjs → renderer-DesbRwjQ.mjs} +2 -2
  83. package/dist/renderer-DesbRwjQ.mjs.map +1 -0
  84. package/dist/select-m7NE6Rwa.mjs.map +1 -1
  85. package/dist/{select-CbmAZdpt.d.mts → select-zGd5pbiB.d.mts} +3 -3
  86. package/dist/{select-CbmAZdpt.d.mts.map → select-zGd5pbiB.d.mts.map} +1 -1
  87. package/dist/services/logger.d.mts +1 -1
  88. package/dist/services/logger.mjs +1 -2
  89. package/dist/services/notifier.d.mts +3 -4
  90. package/dist/services/notifier.d.mts.map +1 -1
  91. package/dist/services/notifier.mjs +2 -2
  92. package/dist/services/notifier.mjs.map +1 -1
  93. package/dist/services/picker.d.mts +8 -9
  94. package/dist/services/picker.d.mts.map +1 -1
  95. package/dist/services/picker.mjs +10 -8
  96. package/dist/services/picker.mjs.map +1 -1
  97. package/dist/services/prompt.d.mts +8 -9
  98. package/dist/services/prompt.d.mts.map +1 -1
  99. package/dist/services/prompt.mjs +9 -7
  100. package/dist/services/prompt.mjs.map +1 -1
  101. package/dist/shiki/server.d.mts +1 -1
  102. package/dist/shiki/server.mjs +6 -2
  103. package/dist/shiki/server.mjs.map +1 -1
  104. package/dist/{shiki-BK-v9CtF.mjs → shiki--ASSYv4_.mjs} +3 -3
  105. package/dist/{shiki-BK-v9CtF.mjs.map → shiki--ASSYv4_.mjs.map} +1 -1
  106. package/dist/{shiki-B5NwIiot.mjs → shiki-D7l5--zz.mjs} +19 -5
  107. package/dist/shiki-D7l5--zz.mjs.map +1 -0
  108. package/dist/show-DR2x1YFc.mjs.map +1 -1
  109. package/dist/style.d.mts +7 -7
  110. package/dist/style.d.mts.map +1 -1
  111. package/dist/style.mjs +2 -2
  112. package/dist/{text-DILrol9j.mjs → text-BLz1tRoC.mjs} +4 -3
  113. package/dist/{text-DILrol9j.mjs.map → text-BLz1tRoC.mjs.map} +1 -1
  114. package/dist/{text-9lwQeqYr.d.mts → text-BefiXAFW.d.mts} +3 -3
  115. package/dist/{text-9lwQeqYr.d.mts.map → text-BefiXAFW.d.mts.map} +1 -1
  116. package/dist/{text-q26V6_Sc.mjs → text-CRZD9KTN.mjs} +3 -2
  117. package/dist/{text-q26V6_Sc.mjs.map → text-CRZD9KTN.mjs.map} +1 -1
  118. package/dist/text.d.mts +1 -1
  119. package/dist/text.mjs +1 -2
  120. package/dist/{theme.config-BptYUq4K.mjs → theme.config-DHgHWQ9t.mjs} +273 -242
  121. package/dist/theme.config-DHgHWQ9t.mjs.map +1 -0
  122. package/dist/themes.d.mts +8 -9
  123. package/dist/themes.d.mts.map +1 -1
  124. package/dist/themes.mjs +1 -2
  125. package/dist/tree-Bo1afYhe.mjs.map +1 -1
  126. package/dist/{tree-C28QOVIK.d.mts → tree-CArtDRec.d.mts} +3 -3
  127. package/dist/{tree-C28QOVIK.d.mts.map → tree-CArtDRec.d.mts.map} +1 -1
  128. package/dist/{types-B9Eh7k2v.d.mts → types-C0EOLZDc.d.mts} +7 -2
  129. package/dist/types-C0EOLZDc.d.mts.map +1 -0
  130. package/dist/{widget-M7jD8Rgg.d.mts → widget-DtJU2-BJ.d.mts} +2 -2
  131. package/dist/{widget-M7jD8Rgg.d.mts.map → widget-DtJU2-BJ.d.mts.map} +1 -1
  132. package/dist/widgets/autocomplete.d.mts +1 -1
  133. package/dist/widgets/autocomplete.mjs +2 -2
  134. package/dist/widgets/autocomplete.mjs.map +1 -1
  135. package/dist/widgets/box.d.mts +1 -1
  136. package/dist/widgets/box.mjs +1 -2
  137. package/dist/widgets/code.d.mts +4 -5
  138. package/dist/widgets/code.d.mts.map +1 -1
  139. package/dist/widgets/code.mjs +5 -5
  140. package/dist/widgets/completions/actions.d.mts +1 -1
  141. package/dist/widgets/completions/actions.mjs +1 -2
  142. package/dist/widgets/completions/files.d.mts +1 -1
  143. package/dist/widgets/completions/files.mjs +1 -2
  144. package/dist/widgets/completions/github.d.mts +1 -1
  145. package/dist/widgets/completions/github.mjs +1 -2
  146. package/dist/widgets/completions/index.d.mts +3 -3
  147. package/dist/widgets/diff.d.mts +5 -6
  148. package/dist/widgets/diff.d.mts.map +1 -1
  149. package/dist/widgets/diff.mjs +3 -3
  150. package/dist/widgets/diff.mjs.map +1 -1
  151. package/dist/widgets/divider.d.mts +4 -5
  152. package/dist/widgets/divider.d.mts.map +1 -1
  153. package/dist/widgets/divider.mjs +1 -2
  154. package/dist/widgets/image.d.mts +1 -1
  155. package/dist/widgets/image.mjs +1 -1
  156. package/dist/widgets/image.mjs.map +1 -1
  157. package/dist/widgets/input.d.mts +1 -1
  158. package/dist/widgets/input.mjs +1 -2
  159. package/dist/widgets/log.d.mts +1 -1
  160. package/dist/widgets/log.mjs +1 -2
  161. package/dist/widgets/markdown.d.mts +8 -9
  162. package/dist/widgets/markdown.d.mts.map +1 -1
  163. package/dist/widgets/markdown.mjs +1 -2
  164. package/dist/widgets/overlay.d.mts +1 -1
  165. package/dist/widgets/overlay.mjs +1 -2
  166. package/dist/widgets/picker.d.mts +1 -1
  167. package/dist/widgets/picker.mjs +1 -2
  168. package/dist/widgets/progress.d.mts +5 -6
  169. package/dist/widgets/progress.d.mts.map +1 -1
  170. package/dist/widgets/select.d.mts +1 -1
  171. package/dist/widgets/select.mjs +1 -2
  172. package/dist/widgets/show.d.mts +7 -7
  173. package/dist/widgets/show.d.mts.map +1 -1
  174. package/dist/widgets/show.mjs +1 -2
  175. package/dist/widgets/spinner.d.mts +7 -8
  176. package/dist/widgets/spinner.d.mts.map +1 -1
  177. package/dist/widgets/spinner.mjs.map +1 -1
  178. package/dist/widgets/text.d.mts +1 -1
  179. package/dist/widgets/text.mjs +1 -2
  180. package/dist/widgets/tree.d.mts +1 -1
  181. package/dist/widgets/tree.mjs +1 -2
  182. package/dist/widgets/widget.d.mts +1 -1
  183. package/dist/widgets/widget.mjs +1 -2
  184. package/dist/worker-C01jK2Ip.mjs +1 -0
  185. package/dist/worker-T6SdPzUH.mjs.map +1 -1
  186. package/package.json +11 -12
  187. package/dist/box-DepqUtuo.mjs.map +0 -1
  188. package/dist/builder-DTz5mppV.mjs.map +0 -1
  189. package/dist/callbacks-DcMBGQEO.mjs.map +0 -1
  190. package/dist/client-BBdtbLp4.mjs.map +0 -1
  191. package/dist/client-cIckDgAj.mjs +0 -2
  192. package/dist/ctx-Bt4VlRPg.mjs +0 -2
  193. package/dist/input-B5Vy-iaa.d.mts.map +0 -1
  194. package/dist/input-CRBuTrsL.mjs.map +0 -1
  195. package/dist/logger-DDrt03So.mjs.map +0 -1
  196. package/dist/markdown-CTlPe5ks.mjs.map +0 -1
  197. package/dist/picker-cH-rc7-X.mjs.map +0 -1
  198. package/dist/queries-DH3bj74K.d.mts.map +0 -1
  199. package/dist/registry-w_w7gZr_.mjs.map +0 -1
  200. package/dist/renderer-Dgj_qEOA.mjs +0 -2
  201. package/dist/renderer-qSMVeNSV.mjs.map +0 -1
  202. package/dist/renderer-uMeDzF9B.mjs.map +0 -1
  203. package/dist/shiki-B5NwIiot.mjs.map +0 -1
  204. package/dist/theme.config-BptYUq4K.mjs.map +0 -1
  205. package/dist/types-B9Eh7k2v.d.mts.map +0 -1
  206. package/dist/worker-BvRm4OsW.mjs +0 -2
@@ -1 +0,0 @@
1
- {"version":3,"file":"callbacks-DcMBGQEO.mjs","names":[],"sources":["../src/markdown/code.ts","../src/markdown/list.ts","../src/markdown/table.ts","../src/markdown/callbacks.ts"],"sourcesContent":["import type { MarkdownCtx } from \"./renderer.ts\"\nimport type { MdCallbacks } from \"./types.ts\"\n\nimport { stringWidth } from \"@zaly/shared/ansi\"\nimport { formatText } from \"../layout/text.ts\"\n\n/**\n * Build the `code` callback. The returned closure captures ctx/style/highlighter\n * and renders each fenced block: syntax-highlight (if available), pad lines to\n * widest-content + 1, apply `mdCodeBlock` as a bg-only backdrop, and prefix an\n * optional title line from `title=\"...\"`.\n */\nexport function createCodeCallback(ctx: MarkdownCtx): NonNullable<MdCallbacks[\"code\"]> {\n const s = ctx.style\n return (text, meta) => {\n text = text.replace(/\\n+$/, \"\") // trim to avoid extra blank lines after the block\n const highlighted = ctx.highlight?.(text, meta?.language) ?? text\n\n // For highlighted output the per-token fgs would clash with the slot's\n // fg; override fg with `\"inherit\"` so only bg + attrs wrap each row\n // and shiki's per-token colors show through on top of the backdrop.\n const wrap = highlighted === text ? s.mdCodeBlock : s.mdCodeBlock.fg(\"inherit\")\n const hpad = 2\n const maxWidth = ctx.width\n const lines = formatText(`\\n${highlighted}\\n`, {\n width: maxWidth - hpad * 2,\n wrap: \"word\",\n })\n let width = Math.max(...lines.map(stringWidth)) + hpad * 2\n width = Math.min(width, maxWidth) // leave room for the border\n // Left-align with a fixed `hpad` of leading whitespace; pad the\n // right to fill the bg out to `width`. Centering would push short\n // lines toward the middle, which reads as visually misaligned code.\n // Lines wider than the available room (width − hpad) drop the\n // leading pad so the bg ends at the cap rather than overshooting.\n const padded = lines.map((line) => {\n const w = stringWidth(line)\n if (w >= width - hpad) return wrap(line)\n return wrap(`${\" \".repeat(hpad)}${line}${\" \".repeat(width - w - hpad)}`)\n })\n const titleLine = meta?.title === undefined ? \"\" : `${s.mdCodeBlockTitle(meta.title)}\\n`\n // Leading `\\n` guards against raw-text siblings that don't emit a\n // paragraph-wrap (e.g. some inline-only list items where the parser\n // drops the paragraph). Containers (`listItem`, document) collapse\n // `\\n{3,}` → `\\n\\n` so paragraph + code doesn't double up.\n return `\\n${titleLine}${padded.join(\"\\n\")}\\n\\n`\n }\n}\n","import type { RenderCtx } from \"../core/ctx.ts\"\nimport type { MdCallbacks } from \"./types.ts\"\n\nimport { splitAnsi, stringWidth } from \"@zaly/shared/ansi\"\n\ninterface ListState {\n block: boolean\n items: string[]\n /** Formatted output, set when the list closes. The parent `listItem`\n * pulls it via `stack[depth+1]` and splices it onto its own body. */\n rendered?: string\n}\n\nconst BULLETS = [\"●\", \"○\", \"◆\", \"◇\"] as const\n\ntype ListCallbacks = Pick<MdCallbacks, \"list\" | \"listItem\">\n\n/**\n * Stack-based list renderer. Each depth has its own `ListState`. Inner\n * lists return `\"\"` and stash their formatted output on `state.rendered`;\n * the parent `listItem` pulls + splices, so inner output never reaches\n * the parent's `children` string. That keeps each level's loose-vs-tight\n * verdict independent — `children.endsWith(\"\\n\\n\")` is then the per-item\n * loose signal (parser only emits `<p>` for items in loose lists).\n *\n * Nested list lands at the end of its parent's body — `text, list, more`\n * is rare in real markdown and not worth the extra plumbing.\n */\nexport function createListCallbacks(ctx: RenderCtx): ListCallbacks {\n const s = ctx.style\n // Lazy-pushed on the first `listItem` at a given depth; consumed\n // either by the parent `listItem` (nested) or by `list(0)` (top).\n const stack: (ListState | undefined)[] = []\n\n return {\n list: (_children, meta) => {\n const state = stack[meta.depth]\n if (state === undefined || state.items.length === 0) return \"\"\n state.rendered = state.items.join(state.block ? \"\\n\\n\" : \"\\n\")\n if (meta.depth > 0) return \"\"\n // Top-level: defensive stack reset + block-contract `\\n\\n` trailer.\n stack.length = 0\n return `${state.rendered}\\n\\n`\n },\n\n listItem: (children, meta) => {\n let marker = s.mdListBullet(\n meta.ordered ? `${(meta.start ?? 1) + meta.index}.` : BULLETS[meta.depth % BULLETS.length]\n )\n if (meta.checked !== undefined) {\n const ref = meta.checked ? \"mdListChecked\" : \"mdListUnchecked\"\n marker += ` ${s.add(ref)(meta.checked ? \"[x]\" : \"[ ]\")}`\n }\n const indent = \" \".repeat(stringWidth(marker))\n // Pull nested list output (if any) off the stack.\n const nested = stack[meta.depth + 1]\n stack[meta.depth + 1] = undefined\n // Trailing `\\n\\n` = loose signal. Nested output is in `rendered`,\n // not `children`, so it can't pollute this check.\n const block = children.endsWith(\"\\n\\n\")\n const trimmed = children.replace(/\\s*\\n+$/, \"\").replace(/\\n{3,}/g, \"\\n\\n\")\n // Splice nested after the prose; loose item adds a blank-row gap.\n let body = trimmed\n if (nested?.rendered !== undefined) {\n const sep = block ? \"\\n\\n\" : \"\\n\"\n body = trimmed === \"\" ? nested.rendered : `${trimmed}${sep}${nested.rendered}`\n }\n const lines = splitAnsi(body)\n const content = lines\n .map((line, l) => {\n if (l === 0) return `${marker} ${line}`\n // Bare empty lines so loose `\\n\\n` separators stay clean.\n return line === \"\" ? \"\" : `${indent}${line}`\n })\n .join(\"\\n\")\n\n const state = (stack[meta.depth] ??= { block: false, items: [] })\n state.block ||= block\n state.items.push(content)\n return \"\"\n },\n }\n}\n","import type { RenderCtx } from \"../core/ctx.ts\"\nimport type { Layout } from \"../core/state.ts\"\nimport type { RowItem } from \"../layout/flex.ts\"\nimport type { MdCallbacks } from \"./types.ts\"\n\nimport { stringWidth } from \"@zaly/shared/ansi\"\nimport { allocateRow } from \"../layout/flex.ts\"\nimport { calcLayout, formatText } from \"../layout/text.ts\"\n\ntype CellAlign = \"left\" | \"center\" | \"right\"\n\ninterface TableCell {\n text: string\n align: CellAlign | undefined\n}\n\ninterface TableState {\n header: TableCell[][]\n body: TableCell[][]\n pending: TableCell[]\n pendingIsHeader: boolean\n}\n\ntype TableCallbacks = Pick<MdCallbacks, \"table\" | \"tbody\" | \"td\" | \"th\" | \"thead\" | \"tr\">\n\n/**\n * Build the table-related callbacks. They share a closure-local\n * `TableState` accumulator: `th`/`td` push cells, `tr` commits rows into\n * header or body, and `table` runs the final layout + reset. Tables can't\n * nest in markdown, so a single top-level slot is enough.\n */\nexport function createTableCallbacks(ctx: RenderCtx): TableCallbacks {\n const { style } = ctx\n let state: TableState | undefined\n const begin = (): TableState =>\n (state ??= { body: [], header: [], pending: [], pendingIsHeader: false })\n\n return {\n table: () => {\n // Children of th/td/tr/thead/tbody are empty strings; all content is\n // in `state`. Format, reset, emit.\n if (state === undefined) return \"\"\n const out = formatTable(state, ctx)\n state = undefined\n return `${out}\\n\\n`\n },\n\n tbody: () => \"\",\n\n td: (children, meta) => {\n const t = begin()\n t.pending.push({ align: meta?.align, text: children })\n t.pendingIsHeader = false\n return \"\"\n },\n\n th: (children, meta) => {\n const t = begin()\n t.pending.push({ align: meta?.align, text: style.mdTableHeader(children) })\n t.pendingIsHeader = true\n return \"\"\n },\n\n thead: () => \"\",\n\n tr: () => {\n if (state === undefined || state.pending.length === 0) return \"\"\n if (state.pendingIsHeader) state.header.push(state.pending)\n else state.body.push(state.pending)\n state.pending = []\n return \"\"\n },\n }\n}\n\nfunction formatTable(state: TableState, ctx: RenderCtx): string {\n const cols: Layout[] = []\n const cells = [...state.header, ...state.body]\n const colCount = Math.max(...cells.map((r) => r.length))\n\n // 1. Calculate min-content and max-content for each column\n for (let c = 0; c < colCount; c++) {\n for (const row of cells) {\n const cell = row[c] as TableCell | undefined\n if (!cell) continue // Safety guard for ragged rows\n const l = calcLayout(cell.text)\n cols[c] ??= { ...l }\n cols[c].width = Math.max(cols[c].width, l.width)\n cols[c].minWidth = Math.max(cols[c].minWidth, l.minWidth)\n }\n }\n const chromeWidth = 3 * colCount + 1\n\n const items: RowItem[] = cols.map((c) => ({\n flex: 1,\n intrinsicMin: c.minWidth,\n natural: c.width,\n }))\n\n const widths = allocateRow(items, { contentWidth: ctx.width - chromeWidth, gap: 0 })\n\n // 4. Render output string using the exact final Column Widths\n // Pre-style each piece of chrome once. Each column span on a rule row is\n // `widths[i] + 2` dashes (one cell of padding on each side of the cell).\n const style = ctx.style\n const v = style.mdTable(\"│\")\n const ruleRow = (left: string, mid: string, right: string): string =>\n style.mdTable(left + widths.map((w) => \"─\".repeat(w + 2)).join(mid) + right)\n const top = ruleRow(\"┌\", \"┬\", \"┐\")\n const sep = ruleRow(\"├\", \"┼\", \"┤\")\n const bot = ruleRow(\"└\", \"┴\", \"┘\")\n\n const renderRow = (row: TableCell[]): string => {\n const formatted = row.map((cell, c) =>\n formatText(cell.text, { indent: false, width: widths[c], wrapBg: false })\n )\n const rows: string[] = []\n const rowCount = Math.max(...formatted.map((r) => r.length))\n for (let r = 0; r < rowCount; r++) {\n const line: string[] = []\n for (let c = 0; c < colCount; c++) {\n const t = formatted[c]?.[r] ?? \"\"\n line.push(padCell(t, widths[c], row[c]?.align))\n }\n rows.push(`${v} ${line.join(` ${v} `)} ${v}`)\n }\n\n return rows.join(\"\\n\")\n }\n\n const lines: string[] = [top]\n for (const row of state.header) lines.push(renderRow(row))\n if (state.header.length > 0 && state.body.length > 0) lines.push(sep)\n for (const row of state.body) lines.push(renderRow(row))\n lines.push(bot)\n return lines.join(\"\\n\")\n}\n\nfunction padCell(text: string, width: number, align: CellAlign | undefined): string {\n const slack = Math.max(0, width - stringWidth(text))\n if (align === \"right\") return \" \".repeat(slack) + text\n if (align === \"center\") {\n const left = Math.floor(slack / 2)\n return \" \".repeat(left) + text + \" \".repeat(slack - left)\n }\n return text + \" \".repeat(slack)\n}\n","import type { AnyStyle } from \"../style/types.ts\"\nimport type { MarkdownCtx } from \"./renderer.ts\"\nimport type { MdCallbacks } from \"./types.ts\"\n\nimport { stringWidth } from \"@zaly/shared/ansi\"\nimport { capitalize } from \"../layout/text.ts\"\nimport { hyperlink } from \"../style/ansi.ts\"\nimport { createCodeCallback } from \"./code.ts\"\nimport { createListCallbacks } from \"./list.ts\"\nimport { createTableCallbacks } from \"./table.ts\"\n\nconst icons = {\n hr: \"─\",\n quote: \"┃\",\n} as const\n\ntype AlertType = \"NOTE\" | \"TIP\" | \"WARNING\" | \"IMPORTANT\" | \"CAUTION\"\nconst alerts: Record<AlertType, { icon: string; style: AnyStyle }> = {\n CAUTION: { icon: \"✖ \", style: \"error\" },\n IMPORTANT: { icon: \"‼\", style: \"syntaxConstant\" },\n NOTE: { icon: \"ℹ \", style: \"info\" },\n TIP: { icon: \"🛈 \", style: \"success\" },\n WARNING: { icon: \"⚠\", style: \"warn\" },\n}\n\nconst alertRe = /^\\s*\\[!(NOTE|TIP|WARNING|IMPORTANT|CAUTION)\\]\\s*$/\n\n/**\n * Build the `MdCallbacks` that drive the theme-aware rendering. Exposed so\n * callers can invoke `renderMarkdown` directly when they need the string\n * output without the wrapping `Markdown` node (e.g. to embed markdown inside\n * a custom `Text` content function).\n * @internal\n */\nexport function createCallbacks(ctx: MarkdownCtx): MdCallbacks {\n const s = ctx.style\n\n return {\n blockquote: (children) => {\n const lines = children.replace(/\\n+$/, \"\").split(\"\\n\")\n let lineStyle: AnyStyle = \"mdQuote\"\n\n const m = lines.length >= 1 ? lines[0].match(alertRe) : undefined\n if (m) {\n const alertType = m[1] as AlertType\n const alert = alerts[alertType]\n lineStyle = alert.style\n const name = capitalize(alertType.toLowerCase())\n lines[0] = s.add(lineStyle)(`${alert.icon} ${name}`)\n }\n\n // Inner blocks (typically a paragraph) end with trailing newlines; if\n // we prefix those empty lines with \"│ \" they render as styled empty\n // rows between the last line of the quote and the block separator.\n // Trim first so the quote stops cleanly.\n const prefixed = lines.map((line) => `${s.add(lineStyle)(icons.quote)} ${line}`).join(\"\\n\")\n return `${prefixed}\\n\\n`\n },\n\n code: createCodeCallback(ctx),\n\n codespan: (text) => s.mdCode(text),\n\n emphasis: (children) => s.mdItalic(children),\n\n heading: (children, { level }) => {\n const width = ctx.width\n const padded = children\n .split(\"\\n\")\n .map((line) => line + \" \".repeat(Math.max(0, width - stringWidth(line))))\n .join(\"\\n\")\n return `${s.add(`mdHeading${level}`)(padded)}\\n\\n`\n },\n\n hr: () => `${s.mdHr(icons.hr.repeat(ctx.width))}\\n\\n`,\n\n html: (children) => children,\n\n link: (children, { href }) => hyperlink(href, s.mdLink(children)),\n\n paragraph: (children) => `${children}\\n\\n`,\n\n strikethrough: (children) => s.mdStrikethrough(children),\n\n strong: (children) => s.mdBold(children),\n\n ...createListCallbacks(ctx),\n ...createTableCallbacks(ctx),\n }\n}\n"],"mappings":";;;;;;;;;;;AAYA,SAAgB,mBAAmB,KAAoD;CACrF,MAAM,IAAI,IAAI;CACd,QAAQ,MAAM,SAAS;EACrB,OAAO,KAAK,QAAQ,QAAQ,EAAE;EAC9B,MAAM,cAAc,IAAI,YAAY,MAAM,MAAM,QAAQ,KAAK;EAK7D,MAAM,OAAO,gBAAgB,OAAO,EAAE,cAAc,EAAE,YAAY,GAAG,SAAS;EAC9E,MAAM,OAAO;EACb,MAAM,WAAW,IAAI;EACrB,MAAM,QAAQ,WAAW,KAAK,YAAY,KAAK;GAC7C,OAAO,WAAW,OAAO;GACzB,MAAM;EACR,CAAC;EACD,IAAI,QAAQ,KAAK,IAAI,GAAG,MAAM,IAAI,WAAW,CAAC,IAAI,OAAO;EACzD,QAAQ,KAAK,IAAI,OAAO,QAAQ;EAMhC,MAAM,SAAS,MAAM,KAAK,SAAS;GACjC,MAAM,IAAI,YAAY,IAAI;GAC1B,IAAI,KAAK,QAAQ,MAAM,OAAO,KAAK,IAAI;GACvC,OAAO,KAAK,GAAG,IAAI,OAAO,IAAI,IAAI,OAAO,IAAI,OAAO,QAAQ,IAAI,IAAI,GAAG;EACzE,CAAC;EAMD,OAAO,KALW,MAAM,UAAU,KAAA,IAAY,KAAK,GAAG,EAAE,iBAAiB,KAAK,KAAK,EAAE,MAK7D,OAAO,KAAK,IAAI,EAAE;CAC5C;AACF;;;AClCA,MAAM,UAAU;CAAC;CAAK;CAAK;CAAK;AAAG;;;;;;;;;;;;AAenC,SAAgB,oBAAoB,KAA+B;CACjE,MAAM,IAAI,IAAI;CAGd,MAAM,QAAmC,CAAC;CAE1C,OAAO;EACL,OAAO,WAAW,SAAS;GACzB,MAAM,QAAQ,MAAM,KAAK;GACzB,IAAI,UAAU,KAAA,KAAa,MAAM,MAAM,WAAW,GAAG,OAAO;GAC5D,MAAM,WAAW,MAAM,MAAM,KAAK,MAAM,QAAQ,SAAS,IAAI;GAC7D,IAAI,KAAK,QAAQ,GAAG,OAAO;GAE3B,MAAM,SAAS;GACf,OAAO,GAAG,MAAM,SAAS;EAC3B;EAEA,WAAW,UAAU,SAAS;GAC5B,IAAI,SAAS,EAAE,aACb,KAAK,UAAU,IAAI,KAAK,SAAS,KAAK,KAAK,MAAM,KAAK,QAAQ,KAAK,QAAQ,QAAQ,OACrF;GACA,IAAI,KAAK,YAAY,KAAA,GAAW;IAC9B,MAAM,MAAM,KAAK,UAAU,kBAAkB;IAC7C,UAAU,IAAI,EAAE,IAAI,GAAG,CAAC,CAAC,KAAK,UAAU,QAAQ,KAAK;GACvD;GACA,MAAM,SAAS,KAAK,OAAO,YAAY,MAAM,CAAC;GAE9C,MAAM,SAAS,MAAM,KAAK,QAAQ;GAClC,MAAM,KAAK,QAAQ,KAAK,KAAA;GAGxB,MAAM,QAAQ,SAAS,SAAS,MAAM;GACtC,MAAM,UAAU,SAAS,QAAQ,WAAW,EAAE,CAAC,CAAC,QAAQ,WAAW,MAAM;GAEzE,IAAI,OAAO;GACX,IAAI,QAAQ,aAAa,KAAA,GAEvB,OAAO,YAAY,KAAK,OAAO,WAAW,GAAG,UADjC,QAAQ,SAAS,OACgC,OAAO;GAGtE,MAAM,UADQ,UAAU,IACJ,CAAC,CAClB,KAAK,MAAM,MAAM;IAChB,IAAI,MAAM,GAAG,OAAO,GAAG,OAAO,GAAG;IAEjC,OAAO,SAAS,KAAK,KAAK,GAAG,SAAS;GACxC,CAAC,CAAC,CACD,KAAK,IAAI;GAEZ,MAAM,QAAS,MAAM,KAAK,WAAW;IAAE,OAAO;IAAO,OAAO,CAAC;GAAE;GAC/D,MAAM,UAAU;GAChB,MAAM,MAAM,KAAK,OAAO;GACxB,OAAO;EACT;CACF;AACF;;;;;;;;;ACnDA,SAAgB,qBAAqB,KAAgC;CACnE,MAAM,EAAE,UAAU;CAClB,IAAI;CACJ,MAAM,cACH,UAAU;EAAE,MAAM,CAAC;EAAG,QAAQ,CAAC;EAAG,SAAS,CAAC;EAAG,iBAAiB;CAAM;CAEzE,OAAO;EACL,aAAa;GAGX,IAAI,UAAU,KAAA,GAAW,OAAO;GAChC,MAAM,MAAM,YAAY,OAAO,GAAG;GAClC,QAAQ,KAAA;GACR,OAAO,GAAG,IAAI;EAChB;EAEA,aAAa;EAEb,KAAK,UAAU,SAAS;GACtB,MAAM,IAAI,MAAM;GAChB,EAAE,QAAQ,KAAK;IAAE,OAAO,MAAM;IAAO,MAAM;GAAS,CAAC;GACrD,EAAE,kBAAkB;GACpB,OAAO;EACT;EAEA,KAAK,UAAU,SAAS;GACtB,MAAM,IAAI,MAAM;GAChB,EAAE,QAAQ,KAAK;IAAE,OAAO,MAAM;IAAO,MAAM,MAAM,cAAc,QAAQ;GAAE,CAAC;GAC1E,EAAE,kBAAkB;GACpB,OAAO;EACT;EAEA,aAAa;EAEb,UAAU;GACR,IAAI,UAAU,KAAA,KAAa,MAAM,QAAQ,WAAW,GAAG,OAAO;GAC9D,IAAI,MAAM,iBAAiB,MAAM,OAAO,KAAK,MAAM,OAAO;QACrD,MAAM,KAAK,KAAK,MAAM,OAAO;GAClC,MAAM,UAAU,CAAC;GACjB,OAAO;EACT;CACF;AACF;AAEA,SAAS,YAAY,OAAmB,KAAwB;CAC9D,MAAM,OAAiB,CAAC;CACxB,MAAM,QAAQ,CAAC,GAAG,MAAM,QAAQ,GAAG,MAAM,IAAI;CAC7C,MAAM,WAAW,KAAK,IAAI,GAAG,MAAM,KAAK,MAAM,EAAE,MAAM,CAAC;CAGvD,KAAK,IAAI,IAAI,GAAG,IAAI,UAAU,KAC5B,KAAK,MAAM,OAAO,OAAO;EACvB,MAAM,OAAO,IAAI;EACjB,IAAI,CAAC,MAAM;EACX,MAAM,IAAI,WAAW,KAAK,IAAI;EAC9B,KAAK,OAAO,EAAE,GAAG,EAAE;EACnB,KAAK,EAAE,CAAC,QAAQ,KAAK,IAAI,KAAK,EAAE,CAAC,OAAO,EAAE,KAAK;EAC/C,KAAK,EAAE,CAAC,WAAW,KAAK,IAAI,KAAK,EAAE,CAAC,UAAU,EAAE,QAAQ;CAC1D;CAEF,MAAM,cAAc,IAAI,WAAW;CAQnC,MAAM,SAAS,YANU,KAAK,KAAK,OAAO;EACxC,MAAM;EACN,cAAc,EAAE;EAChB,SAAS,EAAE;CACb,EAE+B,GAAG;EAAE,cAAc,IAAI,QAAQ;EAAa,KAAK;CAAE,CAAC;CAKnF,MAAM,QAAQ,IAAI;CAClB,MAAM,IAAI,MAAM,QAAQ,GAAG;CAC3B,MAAM,WAAW,MAAc,KAAa,UAC1C,MAAM,QAAQ,OAAO,OAAO,KAAK,MAAM,IAAI,OAAO,IAAI,CAAC,CAAC,CAAC,CAAC,KAAK,GAAG,IAAI,KAAK;CAC7E,MAAM,MAAM,QAAQ,KAAK,KAAK,GAAG;CACjC,MAAM,MAAM,QAAQ,KAAK,KAAK,GAAG;CACjC,MAAM,MAAM,QAAQ,KAAK,KAAK,GAAG;CAEjC,MAAM,aAAa,QAA6B;EAC9C,MAAM,YAAY,IAAI,KAAK,MAAM,MAC/B,WAAW,KAAK,MAAM;GAAE,QAAQ;GAAO,OAAO,OAAO;GAAI,QAAQ;EAAM,CAAC,CAC1E;EACA,MAAM,OAAiB,CAAC;EACxB,MAAM,WAAW,KAAK,IAAI,GAAG,UAAU,KAAK,MAAM,EAAE,MAAM,CAAC;EAC3D,KAAK,IAAI,IAAI,GAAG,IAAI,UAAU,KAAK;GACjC,MAAM,OAAiB,CAAC;GACxB,KAAK,IAAI,IAAI,GAAG,IAAI,UAAU,KAAK;IACjC,MAAM,IAAI,UAAU,EAAE,GAAG,MAAM;IAC/B,KAAK,KAAK,QAAQ,GAAG,OAAO,IAAI,IAAI,EAAE,EAAE,KAAK,CAAC;GAChD;GACA,KAAK,KAAK,GAAG,EAAE,GAAG,KAAK,KAAK,IAAI,EAAE,EAAE,EAAE,GAAG,GAAG;EAC9C;EAEA,OAAO,KAAK,KAAK,IAAI;CACvB;CAEA,MAAM,QAAkB,CAAC,GAAG;CAC5B,KAAK,MAAM,OAAO,MAAM,QAAQ,MAAM,KAAK,UAAU,GAAG,CAAC;CACzD,IAAI,MAAM,OAAO,SAAS,KAAK,MAAM,KAAK,SAAS,GAAG,MAAM,KAAK,GAAG;CACpE,KAAK,MAAM,OAAO,MAAM,MAAM,MAAM,KAAK,UAAU,GAAG,CAAC;CACvD,MAAM,KAAK,GAAG;CACd,OAAO,MAAM,KAAK,IAAI;AACxB;AAEA,SAAS,QAAQ,MAAc,OAAe,OAAsC;CAClF,MAAM,QAAQ,KAAK,IAAI,GAAG,QAAQ,YAAY,IAAI,CAAC;CACnD,IAAI,UAAU,SAAS,OAAO,IAAI,OAAO,KAAK,IAAI;CAClD,IAAI,UAAU,UAAU;EACtB,MAAM,OAAO,KAAK,MAAM,QAAQ,CAAC;EACjC,OAAO,IAAI,OAAO,IAAI,IAAI,OAAO,IAAI,OAAO,QAAQ,IAAI;CAC1D;CACA,OAAO,OAAO,IAAI,OAAO,KAAK;AAChC;;;ACvIA,MAAM,QAAQ;CACZ,IAAI;CACJ,OAAO;AACT;AAGA,MAAM,SAA+D;CACnE,SAAS;EAAE,MAAM;EAAM,OAAO;CAAQ;CACtC,WAAW;EAAE,MAAM;EAAK,OAAO;CAAiB;CAChD,MAAM;EAAE,MAAM;EAAM,OAAO;CAAO;CAClC,KAAK;EAAE,MAAM;EAAO,OAAO;CAAU;CACrC,SAAS;EAAE,MAAM;EAAK,OAAO;CAAO;AACtC;AAEA,MAAM,UAAU;;;;;;;;AAShB,SAAgB,gBAAgB,KAA+B;CAC7D,MAAM,IAAI,IAAI;CAEd,OAAO;EACL,aAAa,aAAa;GACxB,MAAM,QAAQ,SAAS,QAAQ,QAAQ,EAAE,CAAC,CAAC,MAAM,IAAI;GACrD,IAAI,YAAsB;GAE1B,MAAM,IAAI,MAAM,UAAU,IAAI,MAAM,EAAE,CAAC,MAAM,OAAO,IAAI,KAAA;GACxD,IAAI,GAAG;IACL,MAAM,YAAY,EAAE;IACpB,MAAM,QAAQ,OAAO;IACrB,YAAY,MAAM;IAClB,MAAM,OAAO,WAAW,UAAU,YAAY,CAAC;IAC/C,MAAM,KAAK,EAAE,IAAI,SAAS,CAAC,CAAC,GAAG,MAAM,KAAK,GAAG,MAAM;GACrD;GAOA,OAAO,GADU,MAAM,KAAK,SAAS,GAAG,EAAE,IAAI,SAAS,CAAC,CAAC,MAAM,KAAK,EAAE,GAAG,MAAM,CAAC,CAAC,KAAK,IACrE,EAAE;EACrB;EAEA,MAAM,mBAAmB,GAAG;EAE5B,WAAW,SAAS,EAAE,OAAO,IAAI;EAEjC,WAAW,aAAa,EAAE,SAAS,QAAQ;EAE3C,UAAU,UAAU,EAAE,YAAY;GAChC,MAAM,QAAQ,IAAI;GAClB,MAAM,SAAS,SACZ,MAAM,IAAI,CAAC,CACX,KAAK,SAAS,OAAO,IAAI,OAAO,KAAK,IAAI,GAAG,QAAQ,YAAY,IAAI,CAAC,CAAC,CAAC,CAAC,CACxE,KAAK,IAAI;GACZ,OAAO,GAAG,EAAE,IAAI,YAAY,OAAO,CAAC,CAAC,MAAM,EAAE;EAC/C;EAEA,UAAU,GAAG,EAAE,KAAK,MAAM,GAAG,OAAO,IAAI,KAAK,CAAC,EAAE;EAEhD,OAAO,aAAa;EAEpB,OAAO,UAAU,EAAE,WAAW,UAAU,MAAM,EAAE,OAAO,QAAQ,CAAC;EAEhE,YAAY,aAAa,GAAG,SAAS;EAErC,gBAAgB,aAAa,EAAE,gBAAgB,QAAQ;EAEvD,SAAS,aAAa,EAAE,OAAO,QAAQ;EAEvC,GAAG,oBAAoB,GAAG;EAC1B,GAAG,qBAAqB,GAAG;CAC7B;AACF"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"client-BBdtbLp4.mjs","names":["#id","#cache","#queue","#rejectAll","#request","#running","#createWorker","#worker","#workerPromise","#results","#updateScheduled","#update"],"sources":["../src/shiki/client.ts"],"sourcesContent":["import type { ShikiJob, ShikiOpts, ShikiRequest, ShikiResult, ShikiWorkerRequest } from \"./types.ts\"\nimport type { WorkerInstance } from \"./worker.ts\"\n\nimport { hash } from \"@zaly/shared\"\nimport { hasColors } from \"@zaly/shared/env\"\nimport { isShikiLang } from \"../schemas/gen/shiki.ts\"\n\nfunction isJob(s: ShikiJob | ShikiResult): s is ShikiJob {\n return \"key\" in s && \"lang\" in s\n}\n\nconst MAX_CACHE_SIZE = 100\n// Max jobs posted to the worker. Worker still processes serially.\nconst MAX_RUNNING = 2\n\nexport class ShikiWorkerClient {\n #id = 0\n #cache = new Map<string, ShikiJob>()\n #queue = new Map<number, ShikiJob>()\n #running = new Map<number, ShikiJob>()\n #results: ShikiResult[] = []\n #worker?: WorkerInstance<ShikiWorkerRequest, ShikiResult>\n #workerPromise?: Promise<WorkerInstance<ShikiWorkerRequest, ShikiResult>>\n // oxlint-disable-next-line no-unused-private-class-members\n #updateScheduled: Promise<void> | undefined = undefined\n\n key(req: ShikiRequest): string {\n return req.key ?? hash(`${req.lang}:${req.code}:${req.theme ?? \"default\"}`)\n }\n\n toJob(req: ShikiRequest): ShikiJob | ShikiResult {\n const id = ++this.#id\n const key = this.key(req)\n if (!hasColors) return { error: \"terminal does not support colors\", id, key, value: req.code }\n if (!isShikiLang(req.lang))\n return { error: `unsupported language: ${req.lang}`, id, key, value: req.code }\n const cached = this.#cache.get(key)\n if (cached) {\n this.#cache.delete(key)\n this.#cache.set(key, cached) // bump to end of LRU\n return cached\n }\n while (this.#cache.size > MAX_CACHE_SIZE) this.#cache.delete(this.#cache.keys().next().value!)\n const ret: ShikiJob = { ...req, id, key, lang: req.lang, ...Promise.withResolvers() }\n this.#cache.set(key, ret)\n return ret\n }\n\n highlight(code: string, lang: string, opts: ShikiOpts = {}): Promise<ShikiResult> {\n const req: ShikiRequest = { code, lang, signal: opts.signal, theme: opts.theme }\n const job = this.toJob(req)\n if (!isJob(job)) return Promise.resolve(job)\n if (!job.scheduled) {\n this.#queue.set(job.id, job)\n job.signal?.addEventListener(\"abort\", () => this.update(), { once: true })\n this.update()\n }\n return job.promise\n }\n\n dispose(): void {\n const error = new Error(\"Shiki worker disposed\")\n this.#rejectAll(error)\n }\n\n async #request(job: ShikiJob): Promise<void> {\n job.scheduled = true\n this.#running.set(job.id, job)\n const worker = await this.#createWorker()\n const { signal: _s, promise: _prom, resolve: _res, reject: _rej, ...msg } = job\n // oxlint-disable-next-line unicorn/require-post-message-target-origin\n worker.postMessage(msg)\n }\n\n async #createWorker(): Promise<WorkerInstance<ShikiWorkerRequest, ShikiResult>> {\n if (this.#worker) return this.#worker\n this.#workerPromise ??= (async () => {\n const { createWorker } = await import(\"./worker.ts\")\n const worker = await createWorker<ShikiWorkerRequest, ShikiResult>()\n worker.on(\"message\", (event) => {\n this.#running.delete(event.id)\n this.#results.push(event)\n this.update()\n })\n worker.on(\"error\", (error) => {\n this.#rejectAll(error)\n })\n return worker\n })()\n return (this.#worker = await this.#workerPromise)\n }\n\n update() {\n this.#updateScheduled ??= this.#update().finally(() => {\n this.#updateScheduled = undefined\n })\n }\n\n async #update() {\n // Resolve pending results\n while (this.#results.length) {\n const result = this.#results.shift()!\n const job = this.#queue.get(result.id)\n if (job) {\n if (result.error) job.reject(new Error(result.error))\n else job.resolve(result)\n\n // oxlint-disable-next-line no-await-in-loop\n await new Promise((resolve) => setImmediate(resolve)) // yield to event loop between batches\n this.#queue.delete(job.id)\n }\n }\n\n // Clean up aborted jobs\n for (const job of this.#queue.values()) {\n if (job.signal?.aborted && !job.scheduled) {\n job.reject(new Error(\"Job aborted\"))\n this.#queue.delete(job.id)\n this.#cache.delete(job.key)\n }\n }\n\n if (this.#running.size >= MAX_RUNNING || this.#queue.size === 0) return\n\n // Schedule new jobs up to concurrency limit, prioritizing the most recently requested ones (LIFO)\n const todo = [...this.#queue.values()]\n .filter((j) => !j.scheduled)\n .slice(-(MAX_RUNNING - this.#running.size))\n await Promise.all(todo.map((j) => this.#request(j)))\n }\n\n #rejectAll(error: unknown): void {\n for (const { reject } of this.#queue.values()) reject(error)\n this.#cache.clear()\n this.#queue.clear()\n this.#running.clear()\n this.#results = []\n this.#worker?.terminate()\n this.#worker = undefined\n }\n}\n\nexport const shikiWorker = new ShikiWorkerClient()\n"],"mappings":"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"}
@@ -1,2 +0,0 @@
1
- import { n as shikiWorker } from "./client-BBdtbLp4.mjs";
2
- export { shikiWorker };
@@ -1,2 +0,0 @@
1
- import { t as createCtx } from "./ctx-DjJ1zSbs.mjs";
2
- export { createCtx };
@@ -1 +0,0 @@
1
- {"version":3,"file":"input-B5Vy-iaa.d.mts","names":[],"sources":["../src/widgets/input.ts"],"mappings":";;;;;UAoBiB,mBAAmB;;EAElC;;EAEA,cAAc;;EAEd;;EAEA,QAAQ;;EAER;;EAEA;EACA;EACA,aAAa,MAAM;EACnB,UAAU,eAAe;IAAO,OAAO;QAAmB;EAC1D,YAAY;;KAGF;EAAe;EAAe,aAAa;;;KAMlD;EAAU;EAAe;;;KAGlB,kBAAkB;EAAiB;;KAEnC,cAAc;;EAExB;IAAW;IAAmB;;;EAE9B;IAAU;IAAe,aAAa;;;;;;;;;;EAStC;IAAU,YAAY;;;;;;;;;;;;;;;;;;;;;;;;;;;;;cA+BX,cAAc,KAAK,YAAY;;;kBAE1B;WAEE;;;;;;;EAgBT;;;;;;;;;;;;;;;EAyJT,YAAY,UAAS;MA2BjB;MAIA,QAAQ;EAKZ,OAAO,KAAK,kBAAkB;EAqB9B,MAAM;EASN,OAAO;EAWP,QAAQ;;;;EAQR,WAAW;EA2BX,WAAW;YAqHK,QAAQ,KAAK,YAAY;;;;;;;;;;;;iBAyD3B,MAAM,QAAO,aAAkB"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"input-CRBuTrsL.mjs","names":["#cursor","#historyNext","#preferredCol","#historyPrev","#historyEdit","#markerRange","#deleteRange","#historyAdd","#history","#handleKey","#focused","#historyIndex","#staged","#historyDraft","#historySet","#formatCache","#streamingFormat","#formatGen","#format"],"sources":["../src/widgets/input.ts"],"sourcesContent":["import type { MaybePromise } from \"@zaly/shared\"\nimport type { DetectedFile } from \"@zaly/shared/detect\"\nimport type { RenderCtx } from \"../core/ctx.ts\"\nimport type { BaseEvents } from \"../core/node.ts\"\nimport type { Reactive } from \"../core/reactive.ts\"\nimport type { StyleState } from \"../core/state.ts\"\nimport type { NodeActionMap } from \"../input/actions.ts\"\nimport type { RoutedKey } from \"../input/router.ts\"\nimport type { Size } from \"../layout/size.ts\"\nimport type { StyleBuilder } from \"../style/builder.ts\"\n\nimport { hash, isPromiseLike } from \"@zaly/shared\"\nimport { sliceAnsi, splitAnsi, stringWidth } from \"@zaly/shared/ansi\"\nimport { fileDetect } from \"@zaly/shared/detect\"\nimport { basename } from \"pathe\"\nimport { Node } from \"../core/node.ts\"\nimport { untrack, unwrap } from \"../core/reactive.ts\"\nimport { clipboard } from \"../input/clipboard.ts\"\nimport { formatText } from \"../layout/text.ts\"\n\nexport interface InputState extends StyleState {\n /** Current text content. May include `\\n` for multi-line input. */\n value?: string\n /** Shown dim when `value` is empty. */\n placeholder?: Reactive<string | undefined>\n /** Cursor position as a char index in `value`. Clamped to `[0, value.length]`. */\n cursor?: number\n /** Render width. Defaults to `fill`. */\n width?: Size\n /** Submitted input history, newest last. */\n history?: readonly string[]\n /** Threshold for showing pasted content as an attachment rather than raw text */\n pasteMaxLines?: number\n pasteMaxChars?: number\n canAttach?: (file: InputAttachment) => boolean\n format?: (value: string, ctx: { style: StyleBuilder }) => MaybePromise<string>\n validate?: (value: string) => boolean\n}\n\nexport type InputValue = { value: string; attachments: InputAttachment[] }\n\nconst PASTE_MAX_LINES = 5\nconst PASTE_MAX_CHARS = 1000\n\n/** A clipboard or bracketed paste that exceeds the `pasteMax*` thresholds. **/\ntype Paste = { type: \"paste\"; text: string }\n\n/** A file or image attachment detected from the clipboard. */\nexport type InputAttachment = DetectedFile & { path: string }\n\nexport type InputEvents = BaseEvents & {\n /** Fired when the submitted history changes. */\n history: { history: string[]; added: string }\n /** Fired when plain Enter is pressed. Payload is the current value. */\n submit: { value: string; attachments: InputAttachment[] }\n /** Fired when the user pastes a non-text resource via the\n * `input.paste` action. Images and file references both land here,\n * discriminated by `attachment.kind`. One event fires per image\n * paste; one per file in a multi-file paste.\n *\n * Wrapped under `attachment` because `InputAttachment` carries its\n * own `type` field (MIME) that would shadow the envelope's `type`\n * discriminator if spread directly. */\n attach: { attachment: InputAttachment }\n}\n\ntype FormatEntry = { promise?: Promise<void>; result?: string; input: string }\n\n/**\n * Multi-line text input with auto-grow.\n *\n * Editing commands (`cursorLeft`, `deleteWordBack`, `submit`, …) live on\n * `this.actions` as zero-arg methods. The input router maps keymap\n * bindings like `\"input.cursorLeft\"` onto those methods — users bind\n * different keys by configuring the keymap, not by patching the class.\n * The methods are also callable directly (`input.actions.submit()`),\n * which is handy in tests or for higher-level macros.\n *\n * What this class *still* handles via its `key` event listener:\n * - **Printable character insertion.** An unbound keystroke whose\n * `text` is set and has no ctrl/alt/meta modifier becomes a literal\n * insert at the cursor. There's no action for every printable char\n * in the keymap; the raw-key fallback handles them.\n * - **Paste events.** Whole payload inserted at cursor; always.\n *\n * Everything else (navigation, editing, submit/newline) goes through\n * the router → actions pipeline. Unbound non-printable keys fall back\n * to `emit(\"key\", …)` and bubble to the parent chain.\n *\n * Rendering word-wraps each logical line to `ctx.width`, so long\n * messages naturally grow vertically. The UI surface resizes its\n * reserved footer when the Input's row count changes, so the stream\n * above shifts accordingly.\n */\nexport class Input extends Node<InputState, InputEvents> {\n /** Class-level scope tag used by the input router to bind keymaps. */\n static readonly type = \"input\"\n\n override readonly type = Input.type\n #focused = false\n #history: string[] = []\n #historyDraft = \"\"\n #historyIndex: number | undefined\n #preferredCol: number | undefined\n #staged: ((InputAttachment | Paste) & { id: number; marker: string })[] = []\n #formatCache: Map<string, FormatEntry> & { version?: number } = new Map<string, FormatEntry>()\n #formatGen = 0\n\n /**\n * Editing actions. Parameterless — they close over `this` — so both\n * the router (via keymap dispatch) and application code can invoke\n * them. Add to the keymap in `src/input/actions.ts` to give them\n * default key bindings.\n */\n override actions = {\n \"input.cursorDown\": (): void => {\n const v = this.state.value ?? \"\"\n const { col, line } = posToLineCol(v, this.#cursor())\n if (line >= countLines(v) - 1) {\n this.#historyNext()\n return\n }\n this.#preferredCol ??= col\n this.state.cursor = lineColToPos(v, line + 1, this.#preferredCol)\n },\n \"input.cursorLeft\": (): void => {\n const c = this.#cursor()\n this.#preferredCol = undefined\n this.state.cursor = c > 0 ? c - 1 : c\n },\n \"input.cursorLineEnd\": (): void => {\n const v = this.state.value ?? \"\"\n this.#preferredCol = undefined\n this.state.cursor = lineEndPos(v, this.#cursor())\n },\n \"input.cursorLineStart\": (): void => {\n const v = this.state.value ?? \"\"\n const { line } = posToLineCol(v, this.#cursor())\n this.#preferredCol = undefined\n this.state.cursor = lineColToPos(v, line, 0)\n },\n \"input.cursorRight\": (): void => {\n const v = this.state.value ?? \"\"\n const c = this.#cursor()\n this.#preferredCol = undefined\n this.state.cursor = c < v.length ? c + 1 : c\n },\n \"input.cursorUp\": (): void => {\n const v = this.state.value ?? \"\"\n const { col, line } = posToLineCol(v, this.#cursor())\n if (line === 0) {\n this.#historyPrev()\n return\n }\n this.#preferredCol ??= col\n this.state.cursor = lineColToPos(v, line - 1, this.#preferredCol)\n },\n \"input.deleteCharBack\": (): void => {\n const v = this.state.value ?? \"\"\n const c = this.#cursor()\n this.#preferredCol = undefined\n if (c === 0) return\n this.#historyEdit()\n const marker = this.#markerRange(c, \"back\")\n if (marker) return this.#deleteRange(marker.start, marker.end)\n this.state.set({ cursor: c - 1, value: v.slice(0, c - 1) + v.slice(c) })\n },\n \"input.deleteCharForward\": (): void => {\n const v = this.state.value ?? \"\"\n const c = this.#cursor()\n this.#preferredCol = undefined\n if (c >= v.length) return\n this.#historyEdit()\n const marker = this.#markerRange(c, \"forward\")\n if (marker) return this.#deleteRange(marker.start, marker.end)\n this.state.value = v.slice(0, c) + v.slice(c + 1)\n },\n \"input.deleteWordBack\": (): void => {\n const v = this.state.value ?? \"\"\n const c = this.#cursor()\n this.#preferredCol = undefined\n let i = c\n while (i > 0 && isWhitespace(v[i - 1])) i--\n while (i > 0 && !isWhitespace(v[i - 1])) i--\n if (i === c) return\n this.#historyEdit()\n this.state.set({ cursor: i, value: v.slice(0, i) + v.slice(c) })\n },\n \"input.insertNewline\": (): void => {\n // Smart indent: copy the leading whitespace of the current\n // logical line onto the new line so continuations stay aligned\n // with the bullet / quote / prefix the user typed.\n const v = this.state.value ?? \"\"\n const c = this.#cursor()\n this.#preferredCol = undefined\n let lineStart = c\n while (lineStart > 0 && v[lineStart - 1] !== \"\\n\") lineStart--\n let indent = \"\"\n for (let i = lineStart; i < c; i++) {\n const ch = v[i]\n if (ch === \" \" || ch === \"\\t\") indent += ch\n else break\n }\n const insert = `\\n${indent}`\n this.#historyEdit()\n this.state.set({\n cursor: c + insert.length,\n value: v.slice(0, c) + insert + v.slice(c),\n })\n },\n \"input.insertTab\": (): void => {\n // Two spaces rather than `\\t` — terminal tab stops are\n // unpredictable (often 8 cells) and play badly with our per-row\n // layout. Soft tabs are the safer default; users wanting real\n // tabs can override the action.\n const v = this.state.value ?? \"\"\n const c = this.#cursor()\n this.#preferredCol = undefined\n const tab = \" \"\n this.#historyEdit()\n this.state.set({ cursor: c + tab.length, value: v.slice(0, c) + tab + v.slice(c) })\n },\n // `ctrl-v` queries the OS clipboard (via xclip / wl-paste / pbpaste /\n // PowerShell depending on platform). The richest content wins:\n //\n // - **image bytes** → one `attach` event with a temp PNG path.\n // - **file references** → one `attach` event per file.\n // - **plain text** → inserted at the cursor like a regular paste.\n //\n // Fire-and-forget async — we await the probe and commit the\n // result in a microtask.\n \"input.paste\": (): void => {\n void (async (): Promise<void> => {\n const content = await clipboard.read()\n if (!content) return\n\n // Route through the regular paste handler\n if (content.kind === \"text\") {\n void this.emit(\"paste\", {\n paste: {\n stop: () => void 0,\n stopped: false,\n text: content.text,\n },\n })\n return\n }\n\n const paths: string[] = content.kind === \"image\" ? [content.path] : content.paths\n const files = await Promise.all(paths.map((path) => fileDetect({ path })))\n for (let i = 0; i < paths.length; i++) {\n const path = paths[i]\n const file = files[i]\n if (!file) continue\n this.attach({ ...file, path })\n }\n })()\n },\n \"input.submit\": (): void => {\n const value = this.state.value ?? \"\"\n if (this.state.validate?.(value) === false) return\n const ret = this.consume()\n this.#historyAdd(ret.value)\n void this.emit(\"submit\", ret)\n },\n } satisfies NodeActionMap\n\n constructor(initial: InputState = {}) {\n const value = initial.value ?? \"\"\n super({ cursor: value.length, value, ...initial })\n this.#history = [...(initial.history ?? [])]\n this.on(\"key\", ({ key }) => {\n this.#handleKey(key)\n })\n this.on(\"paste\", ({ paste }) => {\n this.paste(paste.text)\n paste.stop()\n })\n this.on(\"focus\", () => {\n this.#focused = true\n this.invalidate()\n })\n this.on(\"blur\", () => {\n this.#focused = false\n this.invalidate()\n })\n\n this.on(\"mount\", () => {\n this.ctx?.input.events.on(\"terminal-focus\", () => this.invalidate(), {\n signal: this.mountSignal,\n })\n })\n }\n\n get history(): readonly string[] {\n return this.#history\n }\n\n set history(v: readonly string[]) {\n this.#history = [...v]\n this.#historyIndex = undefined\n }\n\n attach(att: InputAttachment | Paste): void {\n if (att.type !== \"paste\" && this.state.canAttach?.(att) === false) {\n // Caller doesn't want this attachment (e.g. model doesn't support it) — fall\n // back to pasting the path as plain text\n return this.insert(att.path)\n }\n\n const id = this.#staged.length + 1\n let prefix = att.type[0].toUpperCase() + att.type.slice(1)\n let suffix = \"\"\n if (att.type === \"paste\") {\n prefix = \"Pasted text\"\n suffix = ` +${countLines(att.text)} lines`\n } else if (![\"image\", \"pdf\"].includes(att.type)) suffix = ` ${basename(att.path)}`\n const marker = `[${prefix} #${id}${suffix}]`\n this.#staged.push({ ...att, id, marker })\n this.insert(marker)\n\n if (att.type !== \"paste\") void this.emit(\"attach\", { attachment: att })\n }\n\n paste(text: string): void {\n if (\n countLines(text) > (this.state.pasteMaxLines ?? PASTE_MAX_LINES) ||\n stringWidth(text) > (this.state.pasteMaxChars ?? PASTE_MAX_CHARS)\n )\n return this.attach({ text, type: \"paste\" })\n this.insert(text)\n }\n\n insert(text: string): void {\n const v = this.state.value ?? \"\"\n const c = this.#cursor()\n this.#historyEdit()\n this.#preferredCol = undefined\n this.state.set({\n cursor: c + text.length,\n value: v.slice(0, c) + text + v.slice(c),\n })\n }\n\n replace(text: string): void {\n this.state.value = \"\"\n this.insert(text)\n }\n\n /** Consume the input's current value and attachments.\n * Pastes are replaced inline with their text; file/image\n * attachments are returned in the `attachments` array and removed from the value. */\n consume(): InputValue {\n let value = this.state.value ?? \"\"\n const atts: InputAttachment[] = []\n for (const att of this.#staged) {\n if (!value.includes(att.marker)) continue\n if (att.type === \"paste\") {\n value = value.replace(att.marker, att.text)\n } else atts.push(att)\n }\n this.#staged = []\n this.#preferredCol = undefined\n this.state.set({ cursor: 0, value: \"\" })\n return { attachments: atts, value }\n }\n\n #cursor(): number {\n const v = this.state.value ?? \"\"\n return Math.max(0, Math.min(v.length, this.state.cursor ?? 0))\n }\n\n #deleteRange(start: number, end: number): void {\n const v = this.state.value ?? \"\"\n this.#historyEdit()\n this.#preferredCol = undefined\n this.state.set({ cursor: start, value: v.slice(0, start) + v.slice(end) })\n }\n\n historyAdd(value: string): void {\n this.#historyAdd(value)\n }\n\n #historyAdd(value: string): void {\n if (value.trim() === \"\") return\n if (this.#history.at(-1) !== value) {\n this.#history.push(value)\n void this.emit(\"history\", { added: value, history: [...this.#history] })\n }\n this.#historyDraft = \"\"\n this.#historyIndex = undefined\n }\n\n #historyEdit(): void {\n this.#historyDraft = \"\"\n this.#historyIndex = undefined\n }\n\n #historyNext(): void {\n if (this.#historyIndex === undefined) return\n const next = this.#historyIndex + 1\n if (next >= this.#history.length) {\n this.#historySet(this.#historyDraft)\n this.#historyDraft = \"\"\n this.#historyIndex = undefined\n return\n }\n this.#historyIndex = next\n this.#historySet(this.#history[next])\n }\n\n #historyPrev(): void {\n if (this.#history.length === 0) return\n if (this.#historyIndex === undefined) {\n this.#historyDraft = this.state.value ?? \"\"\n this.#historyIndex = this.#history.length - 1\n } else if (this.#historyIndex > 0) this.#historyIndex--\n this.#historySet(this.#history[this.#historyIndex])\n }\n\n #historySet(value: string): void {\n this.#preferredCol = undefined\n this.state.set({ cursor: value.length, value })\n }\n\n #markerRange(pos: number, dir: \"back\" | \"forward\"): { start: number; end: number } | undefined {\n const value = this.state.value ?? \"\"\n for (const att of this.#staged) {\n const start = value.indexOf(att.marker)\n if (start === -1) continue\n const end = start + att.marker.length\n if (dir === \"back\" && pos > start && pos <= end) return { end, start }\n if (dir === \"forward\" && pos >= start && pos < end) return { end, start }\n }\n }\n\n // Fallback path for anything the router couldn't resolve to a named\n // action: printable characters go straight into the value. Any other\n // unbound key (f7, unclaimed ctrl-combos, etc.) bubbles untouched.\n #handleKey(ev: RoutedKey): void {\n if (ev.text === undefined || ev.ctrl || ev.alt || ev.meta) return\n this.insert(ev.text)\n ev.stop()\n }\n\n #format(value: string, ctx: RenderCtx): string {\n const format = this.state.format\n if (!format) return value\n\n if (ctx.version !== this.#formatCache.version) {\n this.#formatCache.clear()\n this.#formatCache.version = ctx.version\n }\n\n const key = hash(value)\n const cached = this.#formatCache.get(key)\n if (cached?.result !== undefined) return cached.result\n const streaming = this.#streamingFormat(value)\n if (cached?.promise) return streaming ?? value\n\n const ret = format(value, { style: ctx.style })\n if (!isPromiseLike(ret)) return ret\n\n const gen = ++this.#formatGen\n const entry: FormatEntry = { input: value }\n entry.promise = ret.then(\n (result) => {\n if (this.#formatCache.get(key) !== entry) return\n entry.result = result\n entry.promise = undefined\n if (this.#formatGen === gen && result !== value) untrack(() => this.invalidate())\n },\n () => {\n if (this.#formatCache.get(key) === entry) this.#formatCache.delete(key)\n }\n )\n this.#formatCache.set(key, entry)\n while (this.#formatCache.size > 100)\n this.#formatCache.delete(this.#formatCache.keys().next().value!)\n return streaming ?? value\n }\n\n /** Reuse a highlighted prefix while async formatting catches up. */\n #streamingFormat(value: string): string | undefined {\n let ret: [string, FormatEntry] | undefined\n for (const [key, cached] of this.#formatCache) {\n if (cached.result === undefined) continue\n if (value.startsWith(cached.input) && cached.input.length > (ret?.[1].input.length ?? 0))\n ret = [key, cached]\n }\n if (ret === undefined) return\n this.#formatCache.delete(ret[0])\n this.#formatCache.set(ret[0], ret[1]) // bump to end of LRU\n return ret[1].result + value.slice(ret[1].input.length)\n }\n\n protected async _render(ctx: RenderCtx): Promise<string[]> {\n const value = this.state.value ?? \"\"\n const placeholder = this.state.placeholder ?? \"\"\n const cursor = this.#cursor()\n const focused = this.#focused\n\n // Build the styled content string. Layout (word-wrap, split into\n // rows, pad to width) is delegated to `Text` below — wrap-ansi knows\n // how to close+reopen SGR across line breaks, so the inverse-cursor\n // span survives wrapping.\n let content: string\n if (value === \"\") {\n const ph = unwrap(placeholder)\n content = ph ? ` ${ctx.style.quiet(ph)}` : \"\"\n } else {\n content = value\n for (const att of this.#staged) {\n if (!content.includes(att.marker)) continue\n content = content.replace(att.marker, ctx.style.accent(att.marker))\n }\n content = this.#format(content, ctx)\n }\n\n // Fake cursor. `cursor` is an absolute index in the raw value, while\n // rendering is line-oriented: newlines consume string indices but not\n // cells in any rendered row. Project the cursor to line/column before\n // slicing the formatted line.\n if (focused && this.ctx?.input.terminalFocus) {\n const { col, line } = posToLineCol(value, cursor)\n const lines = splitAnsi(content)\n const target = Math.max(0, Math.min(line, lines.length - 1))\n const row = lines[target] ?? \"\"\n const head = sliceAnsi(row, 0, col)\n const at = sliceAnsi(row, col, col + 1) || \" \"\n const tail = sliceAnsi(row, col + 1)\n lines[target] = head + ctx.style.inverse(at) + tail\n content = lines.join(\"\\n\")\n }\n\n return formatText(content, {\n style: ctx.style.add(this.state),\n width: ctx.width,\n wrap: \"word\",\n })\n }\n}\n\n/**\n * Factory for `Input`. All fields optional; default is an empty,\n * focusable input that fills `ctx.width` and has no placeholder.\n *\n * ```ts\n * input({ placeholder: \"type a message…\" })\n * const i = input({ value: \"draft\" })\n * i.on(\"submit\", (text) => console.log(\"user typed\", text))\n * ```\n */\nexport function input(state: InputState = {}): Input {\n return new Input(state)\n}\n\n// ---------- helpers ----------\n\nfunction isWhitespace(ch: string | undefined): boolean {\n return ch !== undefined && (ch === \" \" || ch === \"\\t\" || ch === \"\\n\")\n}\n\nfunction posToLineCol(value: string, cursor: number): { line: number; col: number } {\n let line = 0\n let col = 0\n for (let i = 0; i < cursor; i++) {\n if (value[i] === \"\\n\") {\n line++\n col = 0\n } else col++\n }\n return { col, line }\n}\n\nfunction lineColToPos(value: string, line: number, col: number): number {\n const lines = value.split(\"\\n\")\n const clampLine = Math.max(0, Math.min(line, lines.length - 1))\n let abs = 0\n for (let i = 0; i < clampLine; i++) abs += lines[i].length + 1\n return abs + Math.min(col, lines[clampLine].length)\n}\n\nfunction lineEndPos(value: string, cursor: number): number {\n let i = cursor\n while (i < value.length && value[i] !== \"\\n\") i++\n return i\n}\n\nfunction countLines(value: string): number {\n let n = 1\n for (const ch of value) if (ch === \"\\n\") n++\n return n\n}\n"],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"logger-DDrt03So.mjs","names":["#opts","#factory","#defaultFactory","#stream","#writeFallback"],"sources":["../src/services/logger.ts"],"sourcesContent":["import type { LogEntry, LogLevel, LogReporter } from \"@zaly/shared/logger\"\nimport type { InspectOpts } from \"../style/inspect.ts\"\nimport type { LogState } from \"../widgets/log.ts\"\n\nimport { Node } from \"../core/node.ts\"\nimport { inspectFormat, isMarkdown } from \"../style/inspect.ts\"\nimport { log } from \"../widgets/log.ts\"\n\n/** Minimal stream surface the logger needs. Stream satisfies this. */\nexport interface LoggerStream {\n append: (node: () => Node) => unknown\n}\n\nexport type LogEntryFactory = (level: LogLevel, msg: unknown[]) => Node\n\nexport type LogStyleOverride = Omit<LogState, \"level\" | \"content\">\n\nexport interface TuiReporterOpts extends InspectOpts {\n /** Render string messages as markdown when they look like it.\n * Default: `true`. */\n markdown?: boolean\n /** Per-level overrides for the default `log()` widget style fields. */\n styles?: Partial<Record<LogLevel, LogStyleOverride>>\n /** Override the node produced per entry. Default uses `log()`. */\n factory?: LogEntryFactory\n wrap?: (node: Node) => Node\n /** Fallback writer for when no stream is attached. Defaults to\n * `process.stdout/stderr`. Injectable for tests. */\n write?: (text: string, kind: \"stdout\" | \"stderr\") => void\n}\n\nconst ERR_LEVELS = new Set<LogLevel>([\"error\", \"fatal\", \"warn\"])\n\nfunction defaultWrite(text: string, kind: \"stdout\" | \"stderr\"): void {\n if (typeof process === \"undefined\") return\n const stream = kind === \"stderr\" ? process.stderr : process.stdout\n stream.write(text)\n}\n\nexport class TuiReporter implements LogReporter {\n #stream?: LoggerStream\n #opts: TuiReporterOpts\n #factory: LogEntryFactory\n\n constructor(opts: TuiReporterOpts = {}) {\n this.#opts = opts\n this.#factory = opts.factory ?? ((level, msg) => this.#defaultFactory(level, msg))\n }\n\n attach(stream: LoggerStream): this {\n this.#stream = stream\n return this\n }\n\n detach(): this {\n this.#stream = undefined\n return this\n }\n\n $log({ level, msg }: LogEntry): void {\n if (this.#stream) {\n this.#stream.append(() => {\n const node = this.#factory(level, msg)\n return this.#opts.wrap?.(node) ?? node\n })\n return\n }\n this.#writeFallback(level, msg)\n }\n\n #defaultFactory(level: LogLevel, msg: unknown[]): Node {\n const nodes = msg.filter((m): m is Node => m instanceof Node)\n msg = msg.filter((m) => !(m instanceof Node))\n\n // Convert Error objects to their message unless stacktrace is requested.\n msg = this.#opts.stacktrace ? msg : msg.map((v) => (v instanceof Error ? v.message : v))\n\n // If all remaining messages are strings, join them into one string for the log content.\n if (msg.length && msg.every((m) => typeof m === \"string\")) msg = [msg.join(\" \")]\n\n // If there's exactly one string message, use it as the log content;\n // otherwise, leave it undefined to be formatted with `inspect()`.\n // Text allow markdown if the message looks like markdown and the option is enabled.\n let text = msg.length === 1 && typeof msg[0] === \"string\" ? msg[0] : undefined\n if (msg.length === 0) text = \"\"\n const markdown = (this.#opts.markdown ?? true) && text !== undefined && isMarkdown(text)\n const overrides = this.#opts.styles?.[level] ?? {}\n return log(\n {\n content: text ?? ((ctx) => inspectFormat(msg, { ...this.#opts, style: ctx.style })),\n level,\n markdown,\n ...overrides,\n },\n ...nodes\n )\n }\n\n /** String path for the no-stream fallback — builds a plain inspected\n * line (no prefix chrome) and writes it to stdout/stderr. Keeps the\n * fallback synchronous and ordered. */\n #writeFallback(level: LogLevel, msg: unknown[]): void {\n const str = inspectFormat(msg, this.#opts)\n const kind: \"stdout\" | \"stderr\" = ERR_LEVELS.has(level) ? \"stderr\" : \"stdout\"\n const write = this.#opts.write ?? defaultWrite\n write(`${str}\\n`, kind)\n }\n}\n"],"mappings":";;;;AA+BA,MAAM,6BAAa,IAAI,IAAc;CAAC;CAAS;CAAS;AAAM,CAAC;AAE/D,SAAS,aAAa,MAAc,MAAiC;CACnE,IAAI,OAAO,YAAY,aAAa;CAEpC,CADe,SAAS,WAAW,QAAQ,SAAS,QAAQ,OAAA,CACrD,MAAM,IAAI;AACnB;AAEA,IAAa,cAAb,MAAgD;CAC9C;CACA;CACA;CAEA,YAAY,OAAwB,CAAC,GAAG;EACtC,KAAKA,QAAQ;EACb,KAAKC,WAAW,KAAK,aAAa,OAAO,QAAQ,KAAKC,gBAAgB,OAAO,GAAG;CAClF;CAEA,OAAO,QAA4B;EACjC,KAAKC,UAAU;EACf,OAAO;CACT;CAEA,SAAe;EACb,KAAKA,UAAU,KAAA;EACf,OAAO;CACT;CAEA,KAAK,EAAE,OAAO,OAAuB;EACnC,IAAI,KAAKA,SAAS;GAChB,KAAKA,QAAQ,aAAa;IACxB,MAAM,OAAO,KAAKF,SAAS,OAAO,GAAG;IACrC,OAAO,KAAKD,MAAM,OAAO,IAAI,KAAK;GACpC,CAAC;GACD;EACF;EACA,KAAKI,eAAe,OAAO,GAAG;CAChC;CAEA,gBAAgB,OAAiB,KAAsB;EACrD,MAAM,QAAQ,IAAI,QAAQ,MAAiB,aAAa,IAAI;EAC5D,MAAM,IAAI,QAAQ,MAAM,EAAE,aAAa,KAAK;EAG5C,MAAM,KAAKJ,MAAM,aAAa,MAAM,IAAI,KAAK,MAAO,aAAa,QAAQ,EAAE,UAAU,CAAE;EAGvF,IAAI,IAAI,UAAU,IAAI,OAAO,MAAM,OAAO,MAAM,QAAQ,GAAG,MAAM,CAAC,IAAI,KAAK,GAAG,CAAC;EAK/E,IAAI,OAAO,IAAI,WAAW,KAAK,OAAO,IAAI,OAAO,WAAW,IAAI,KAAK,KAAA;EACrE,IAAI,IAAI,WAAW,GAAG,OAAO;EAC7B,MAAM,YAAY,KAAKA,MAAM,YAAY,SAAS,SAAS,KAAA,KAAa,WAAW,IAAI;EACvF,MAAM,YAAY,KAAKA,MAAM,SAAS,UAAU,CAAC;EACjD,OAAO,IACL;GACE,SAAS,UAAU,QAAQ,cAAc,KAAK;IAAE,GAAG,KAAKA;IAAO,OAAO,IAAI;GAAM,CAAC;GACjF;GACA;GACA,GAAG;EACL,GACA,GAAG,KACL;CACF;;;;CAKA,eAAe,OAAiB,KAAsB;EACpD,MAAM,MAAM,cAAc,KAAK,KAAKA,KAAK;EACzC,MAAM,OAA4B,WAAW,IAAI,KAAK,IAAI,WAAW;EAErE,CADc,KAAKA,MAAM,SAAS,aAAA,CAC5B,GAAG,IAAI,KAAK,IAAI;CACxB;AACF"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"markdown-CTlPe5ks.mjs","names":["#images","#worker","#update","#code","#gen","#streamingHighlight","#renderer","#highlight"],"sources":["../src/widgets/markdown.ts"],"sourcesContent":["import type { RenderCtx } from \"../core/ctx.ts\"\nimport type { Accessor } from \"../core/reactive.ts\"\nimport type { State } from \"../core/state.ts\"\nimport type { WrapMode } from \"../layout/text.ts\"\nimport type { MarkdownRenderer } from \"../markdown/renderer.ts\"\nimport type { MdOptions } from \"../markdown/types.ts\"\nimport type { ShikiTheme } from \"../shiki/types.ts\"\nimport type { AnyStyle } from \"../style/types.ts\"\nimport type { Image } from \"./image.ts\"\nimport type { TextContent } from \"./text.ts\"\n\nimport { hasColors } from \"@zaly/shared/env\"\nimport { Node } from \"../core/node.ts\"\nimport { createAsync, signal, unwrap, useContext } from \"../core/reactive.ts\"\nimport { RenderContext } from \"../core/render.ts\"\nimport { calcLayout, expandTabs, formatText } from \"../layout/text.ts\"\nimport { shikiWorker } from \"../shiki/client.ts\"\nimport { codeToAnsi } from \"../shiki/shiki.ts\"\nimport { textContent } from \"./text.ts\"\n\nexport interface MarkdownState {\n /** Markdown source. Accepts a plain string or a reactive accessor —\n * pass `signal()` / `memo()` for streaming content that re-parses on\n * each render and subscribes the node to the signal. */\n content: TextContent\n /** Options forwarded to `renderMarkdown`. */\n options?: MdOptions\n /**\n * Enable shiki-backed syntax highlighting for fenced code blocks. Defaults\n * to `true` — code blocks get per-token colors from the shiki theme, with\n * `mdCodeBlock`'s bg applied as a backdrop. Unknown languages fall through\n * as plain text.\n */\n syntax?: boolean\n wrap?: WrapMode\n style?: AnyStyle\n}\n\ntype ShikiCode = {\n key: string\n code: string\n lang: string\n theme?: ShikiTheme\n inflight?: Promise<string>\n ac?: AbortController\n result?: string\n gen: number\n}\n\nexport class Markdown extends Node<MarkdownState> {\n // Image nodes cached per-src per-Markdown-instance. Re-rendering the\n // same markdown (streaming updates) reuses the same `Image` — same\n // `placementId`, which the KGP spec guarantees is a flicker-free\n // move/resize of the existing placement.\n readonly images = new Map<string, Image>()\n\n #renderer?: MarkdownRenderer\n #code = new Map<string, ShikiCode>()\n #update = signal(0)\n #gen = 0\n #worker: Accessor<number>\n #images?: Accessor<boolean>\n\n constructor(state: State<MarkdownState>) {\n super(state)\n\n const context = useContext(RenderContext)\n this.#images = context?.images\n\n this.#worker = createAsync(\n async () => {\n const update = this.#update.get() // track\n const todo = [...this.#code.values()].filter((c) => c.gen === this.#gen && !c.result)\n if (!todo.length) return update // nothing to do, skip\n await Promise.all(\n todo.map(async (req) => {\n req.ac ??= new AbortController()\n req.inflight ??= codeToAnsi(req.code, req.lang, {\n signal: req.ac.signal,\n theme: req.theme,\n })\n try {\n req.result = await req.inflight\n } catch (error) {\n if (req.ac.signal.aborted) {\n if (this.#code.get(req.key) === req) this.#code.delete(req.key)\n } else throw error\n }\n })\n )\n return update + 1\n },\n { initialValue: 0 }\n )\n }\n\n /** Find a highlighted result for a prefix of `code` in the cache. This\n * handles streaming updates where the full code block isn't available yet\n * and prevents flashing un-highlighted text on each update. */\n #streamingHighlight(code: string, lang: string, theme?: ShikiTheme) {\n let ret: ShikiCode | undefined\n for (const c of this.#code.values()) {\n if (!c.result || c.lang !== lang || c.theme !== theme) continue\n if (code.startsWith(c.code) && c.code.length > (ret?.code.length ?? 0)) ret = c\n }\n if (ret) ret.gen = this.#gen // bump gen to keep it alive in cache\n return ret?.result ? ret.result + code.slice(ret.code.length) : code\n }\n\n #highlight(code: string, lang?: string, theme?: ShikiTheme): string {\n if (!lang) return code\n const key = shikiWorker.key({ code, lang, theme })\n const ret = this.#code.get(key)\n if (ret) ret.gen = this.#gen // bump gen to keep it alive in cache\n if (ret?.result) return ret.result\n else if (!ret) this.#code.set(key, { code, gen: this.#gen, key, lang, theme })\n return this.#streamingHighlight(code, lang, theme)\n }\n\n protected async _render(ctx: RenderCtx): Promise<string[]> {\n if (!this.#renderer) {\n const { MarkdownRenderer } = await import(\"../markdown/renderer.ts\")\n this.#renderer = new MarkdownRenderer({ ...this.state.options, parent: this })\n }\n let source = await textContent(this.state.content, ctx)\n source = expandTabs(source)\n let formatted: string\n\n if (!hasColors) formatted = this.#renderer.normalizeEol(source, source)\n else {\n this.#gen++ // bump generation to track what is still used\n\n formatted = await this.#renderer.render(source, {\n ...ctx,\n highlight: (code, lang) => this.#highlight(code, lang, ctx.style.theme.shiki),\n images: unwrap(this.#images) ?? true,\n })\n\n // prune old entries\n for (const [k, c] of this.#code.entries())\n if (c.gen !== this.#gen) {\n c.ac?.abort()\n if (c.result !== undefined) this.#code.delete(k)\n }\n\n // Trigger the worker if needed\n if (this.#code.values().some((c) => !c.inflight)) {\n this.#update.set(this.#gen) // trigger worker\n this.#worker() // tracked\n }\n }\n\n return formatText(formatted, {\n indent: true,\n style: this.state.style ? ctx.style.add(this.state.style) : undefined,\n width: ctx.width,\n wrap: this.state.wrap,\n wrapBg: true,\n })\n }\n\n override async layout(ctx: RenderCtx) {\n return calcLayout(await textContent(this.state.content, ctx))\n }\n}\n\n/**\n * Render a markdown string as a TUI node. Produces ANSI-styled text that\n * resolves per-element styling through theme slots (`mdHeading1`, `mdCode`,\n * `mdLink`, …). Links become clickable in terminals that support OSC 8.\n *\n * ```ts\n * markdown(\"# Hello\\n\\nThis is **bold** and *italic*.\")\n * markdown({ content, wrap: \"word\", fg: \"fg\" })\n * ```\n */\nexport function markdown(\n content: TextContent,\n style?: Omit<State<MarkdownState>, \"content\">\n): Markdown\nexport function markdown(state: State<MarkdownState>): Markdown\nexport function markdown(\n first: TextContent | MarkdownState,\n style?: Omit<State<MarkdownState>, \"content\">\n): Markdown {\n // Plain strings and accessor functions go through the content path;\n // a non-function object is the full state form.\n if (typeof first === \"string\" || typeof first === \"function\") {\n return new Markdown({ content: first, ...style })\n }\n return new Markdown(first)\n}\n"],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"picker-cH-rc7-X.mjs","names":["#opts","#bonusMatrix","#bonusBoundaryWhite","#bonusBoundaryDelimiter","#computeBonus","#score","#str","#consecutive","#prevClass","#prev","#firstBonus","#prepare","#match","#fuzzyPositions","#regex","#fuzzy","#fuzzyFind","#opts","#sorter","#matcher","#search","#ac"],"sources":["../src/search/score.ts","../src/search/matcher.ts","../src/search/sort.ts","../src/search/search.ts","../src/widgets/picker.ts"],"sourcesContent":["export type ScoreOptions = {\n filenameBonus?: boolean\n historyBonus?: boolean\n}\n\nconst SCORE_MATCH = 16\nconst SCORE_GAP_START = -3\nconst SCORE_GAP_EXTENSION = -1\n\nconst BONUS_BOUNDARY = SCORE_MATCH / 2\nconst BONUS_NONWORD = SCORE_MATCH / 2\nconst BONUS_CAMEL_123 = BONUS_BOUNDARY - 1\nconst BONUS_CONSECUTIVE = -(SCORE_GAP_START + SCORE_GAP_EXTENSION)\nconst BONUS_FIRST_CHAR_MULTIPLIER = 2\nconst BONUS_NO_PATH_SEP = BONUS_BOUNDARY - 2\n\nconst CHAR_WHITE = 0\nconst CHAR_NONWORD = 1\nconst CHAR_DELIMITER = 2\nconst CHAR_LOWER = 3\nconst CHAR_UPPER = 4\nconst CHAR_LETTER = 5\nconst CHAR_NUMBER = 6\n\nconst PATH_SEPS = new Set([\"/\", \"\\\\\"])\n\nconst CHAR_CLASS = Array.from({ length: 256 }, (_, b) => {\n const ch = String.fromCharCode(b)\n if (/\\s/.test(ch)) return CHAR_WHITE\n if (String.raw`/\\,:;|`.includes(ch)) return CHAR_DELIMITER\n if (b >= 48 && b <= 57) return CHAR_NUMBER\n if (b >= 65 && b <= 90) return CHAR_UPPER\n if (b >= 97 && b <= 122) return CHAR_LOWER\n return CHAR_NONWORD\n})\n\nfunction charClass(str: string, pos: number): number {\n const code = str.charCodeAt(pos)\n return code <= 255 ? (CHAR_CLASS[code] ?? CHAR_NONWORD) : CHAR_LETTER\n}\n\nexport class Score {\n readonly #opts: ScoreOptions\n readonly #bonusMatrix: number[][] = []\n readonly #bonusBoundaryWhite: number\n readonly #bonusBoundaryDelimiter: number\n\n #consecutive = 0\n #firstBonus = 0\n #prev: number | undefined\n #prevClass = CHAR_WHITE\n #score = 0\n #str = \"\"\n\n isFile = false\n\n constructor(opts: ScoreOptions = {}) {\n this.#opts = opts\n this.#bonusBoundaryWhite = opts.historyBonus ? BONUS_BOUNDARY : BONUS_BOUNDARY + 2\n this.#bonusBoundaryDelimiter = opts.historyBonus ? BONUS_BOUNDARY : BONUS_BOUNDARY + 1\n for (let prev = 0; prev <= 6; prev++) {\n this.#bonusMatrix[prev] = []\n for (let curr = 0; curr <= 6; curr++) {\n this.#bonusMatrix[prev][curr] = this.#computeBonus(prev, curr)\n }\n }\n }\n\n get score(): number {\n return this.#score\n }\n\n isLeftBoundary(str: string, pos: number): boolean {\n return pos === 0 || charClass(str, pos - 1) < CHAR_LOWER\n }\n\n isRightBoundary(str: string, pos: number): boolean {\n return pos === str.length - 1 || charClass(str, pos + 1) < CHAR_LOWER\n }\n\n init(str: string, first: number): void {\n this.#str = str\n this.#score = 0\n this.#consecutive = 0\n this.#prevClass = first > 0 ? charClass(str, first - 1) : CHAR_WHITE\n this.#prev = undefined\n this.#firstBonus = 0\n\n if (this.isFile && this.#opts.filenameBonus && !hasPathSepAfter(str, first)) {\n this.#score += BONUS_NO_PATH_SEP\n }\n this.update(first)\n }\n\n update(pos: number): void {\n const cls = charClass(this.#str, pos)\n const gap = this.#prev === undefined ? 0 : pos - this.#prev - 1\n let bonus = 0\n\n if (gap > 0) {\n this.#prevClass = charClass(this.#str, pos - 1)\n bonus = this.#bonusMatrix[this.#prevClass]?.[cls] ?? 0\n this.#score += SCORE_GAP_START + (gap - 1) * SCORE_GAP_EXTENSION\n this.#consecutive = 0\n this.#firstBonus = 0\n } else {\n bonus = this.#bonusMatrix[this.#prevClass]?.[cls] ?? 0\n if (this.#consecutive === 0) {\n this.#firstBonus = bonus\n } else {\n if (bonus >= BONUS_BOUNDARY && bonus > this.#firstBonus) this.#firstBonus = bonus\n bonus = Math.max(bonus, this.#firstBonus, BONUS_CONSECUTIVE)\n }\n this.#consecutive++\n }\n\n if (this.#prev === undefined) bonus *= BONUS_FIRST_CHAR_MULTIPLIER\n this.#score += SCORE_MATCH + bonus\n this.#prevClass = cls\n this.#prev = pos\n }\n\n get(str: string, from: number, to: number): number {\n this.init(str, from)\n for (let i = from + 1; i <= to; i++) this.update(i)\n return this.#score\n }\n\n #computeBonus(prev: number, curr: number): number {\n if (curr > CHAR_NONWORD) {\n if (prev === CHAR_WHITE) return this.#bonusBoundaryWhite\n if (prev === CHAR_DELIMITER) return this.#bonusBoundaryDelimiter\n if (prev === CHAR_NONWORD) return BONUS_BOUNDARY\n }\n if (\n (prev === CHAR_LOWER && curr === CHAR_UPPER) ||\n (prev !== CHAR_NUMBER && curr === CHAR_NUMBER)\n ) {\n return BONUS_CAMEL_123\n }\n if (curr === CHAR_NONWORD || curr === CHAR_DELIMITER) return BONUS_NONWORD\n if (curr === CHAR_WHITE) return BONUS_BOUNDARY + 2\n return 0\n }\n}\n\nfunction hasPathSepAfter(str: string, first: number): boolean {\n for (let i = first + 1; i < str.length; i++) if (PATH_SEPS.has(str[i])) return true\n return false\n}\n","import type { ScoreOptions } from \"./score.ts\"\n\nimport { Score } from \"./score.ts\"\n\nexport type SearchItem = {\n idx?: number\n score?: number\n file?: string\n text: string\n}\n\nexport type ScoredItem<T extends SearchItem = SearchItem> = T & {\n score: number\n topk?: boolean\n}\n\nexport type MatcherOptions = ScoreOptions & {\n fuzzy?: boolean\n ignorecase?: boolean\n regex?: boolean\n smartcase?: boolean\n}\n\ntype Mod = {\n chars: string[]\n entropy: number\n exactPrefix?: boolean\n exactSuffix?: boolean\n field?: string\n fuzzy?: boolean\n ignorecase?: boolean\n inverse?: boolean\n pattern: string\n re?: RegExp\n regex?: boolean\n word?: boolean\n}\n\ntype Match = {\n from: number\n score: number\n search: string\n str: string\n to: number\n}\n\nexport class Matcher<T extends SearchItem = SearchItem> {\n readonly opts: Required<Pick<MatcherOptions, \"fuzzy\" | \"ignorecase\" | \"smartcase\">> &\n MatcherOptions\n readonly score: Score\n mods: Mod[][] = []\n one: Mod | undefined\n pattern = \"\"\n tick = 0\n\n constructor(opts: MatcherOptions = {}) {\n this.opts = {\n fuzzy: true,\n ignorecase: true,\n smartcase: true,\n ...opts,\n }\n this.score = new Score(opts)\n }\n\n empty(): boolean {\n return this.mods.length === 0\n }\n\n init(pattern: string): boolean {\n pattern = pattern.trim()\n if (pattern === this.pattern) return false\n\n this.pattern = pattern\n this.tick++\n this.mods = []\n this.one = undefined\n if (pattern === \"\") return true\n\n if (this.opts.regex) {\n this.mods = [[this.#prepare(pattern)]]\n } else {\n let isOr = false\n for (const part of pattern.split(/ +/)) {\n if (part === \"|\") {\n isOr = true\n continue\n }\n const mod = this.#prepare(part)\n if (mod.pattern === \"\") continue\n if (isOr && this.mods.length > 0) this.mods.at(-1)?.push(mod)\n else this.mods.push([mod])\n isOr = false\n }\n }\n\n this.mods = this.mods.map((ors) => ors.toSorted((a, b) => a.entropy - b.entropy))\n this.mods = this.mods.toSorted((a, b) => (b[0]?.entropy ?? 0) - (a[0]?.entropy ?? 0))\n if (this.mods.length === 1 && this.mods[0]?.length === 1) this.one = this.mods[0][0]\n return true\n }\n\n match(input: T | string): number {\n if (this.empty()) return 1000\n const item = typeof input === \"string\" ? { text: input } : input\n if (this.one) return this.#match(item, this.one)?.score ?? 0\n\n let score = 0\n for (const any of this.mods) {\n let match: Match | undefined\n for (const mod of any) {\n match = this.#match(item, mod)\n if (match) break\n }\n if (!match) return 0\n score += match.score\n }\n return score\n }\n\n update(item: T): ScoredItem<T> {\n const score = this.match(item)\n const it = item as ScoredItem<T>\n it.score = score\n return it\n }\n\n positions(input: T | string): number[] {\n if (this.empty()) return []\n const item = typeof input === \"string\" ? { text: input } : input\n const ret: number[] = []\n const all = this.mods.flat()\n for (const mod of all) {\n const match = this.#match(item, mod)\n if (!match) continue\n if (mod.fuzzy) ret.push(...this.#fuzzyPositions(match.search, mod.chars, match.from))\n else for (let i = match.from; i <= match.to; i++) ret.push(i)\n }\n return [...new Set(ret)].toSorted((a, b) => a - b)\n }\n\n fields(): string[] {\n const ret = new Set<string>()\n for (const mod of this.mods.flat()) ret.add(mod.field ?? \"text\")\n return [...ret]\n }\n\n #prepare(pattern: string): Mod {\n const mod: Mod = { chars: [], entropy: 0, pattern }\n\n if (this.opts.regex) {\n mod.regex = true\n const isLower = mod.pattern.toLowerCase() === mod.pattern\n mod.ignorecase = this.opts.smartcase ? isLower : this.opts.ignorecase\n try {\n mod.re = new RegExp(mod.pattern, mod.ignorecase ? \"i\" : undefined)\n } catch {\n mod.re = undefined\n }\n } else {\n const file = parseFilePattern(pattern)\n if (file) {\n mod.field = \"file\"\n mod.pattern = `${file}$`\n }\n\n const field = mod.pattern.match(/^([\\w_][\\w_]+):(.*)$/)\n if (field) {\n mod.field = field[1]\n mod.pattern = field[2]\n }\n\n mod.ignorecase = this.opts.ignorecase\n const isLower = mod.pattern.toLowerCase() === mod.pattern\n if (this.opts.smartcase) mod.ignorecase = isLower\n mod.fuzzy = this.opts.fuzzy\n if (!mod.fuzzy) mod.entropy += 10\n\n if (mod.pattern.startsWith(\"!\")) {\n mod.fuzzy = false\n mod.inverse = true\n mod.pattern = mod.pattern.slice(1)\n mod.entropy -= 1\n }\n if (mod.pattern.startsWith(\"'\")) {\n mod.fuzzy = false\n mod.pattern = mod.pattern.slice(1)\n mod.entropy += 10\n if (mod.pattern.endsWith(\"'\")) {\n mod.word = true\n mod.pattern = mod.pattern.slice(0, -1)\n mod.entropy += 10\n }\n } else if (mod.pattern.startsWith(\"^\")) {\n mod.fuzzy = false\n mod.exactPrefix = true\n mod.pattern = mod.pattern.slice(1)\n mod.entropy += 20\n }\n if (mod.pattern.endsWith(\"$\")) {\n mod.fuzzy = false\n mod.exactSuffix = true\n mod.pattern = mod.pattern.slice(0, -1)\n mod.entropy += 20\n }\n\n const rareChars = (mod.pattern.match(/[^\\w\\s]/g) ?? []).length\n mod.entropy += Math.min(mod.pattern.length, 20) + rareChars * 2\n if (!mod.ignorecase && !isLower) mod.entropy *= 2\n if (mod.ignorecase) mod.pattern = mod.pattern.toLowerCase()\n }\n\n // oxlint-disable-next-line typescript/no-misused-spread\n mod.chars = [...mod.pattern]\n return mod\n }\n\n #match(item: SearchItem, mod: Mod): Match | undefined {\n this.score.isFile = itemField(item, \"file\") !== undefined\n let str = item.text\n\n if (mod.field) {\n const value = itemField(item, mod.field)\n if (value === undefined)\n return mod.inverse ? { from: 0, score: 1000, search: str, str, to: 0 } : undefined\n str = value\n }\n\n const original = str\n if (mod.ignorecase) str = str.toLowerCase()\n\n if (mod.regex) return this.#regex(original, mod)\n if (mod.fuzzy) return this.#fuzzy(str, original, mod.chars)\n\n let from = -1\n let to = -1\n if (mod.exactPrefix) {\n if (str.startsWith(mod.pattern)) {\n from = 0\n to = mod.pattern.length - 1\n }\n } else if (mod.exactSuffix) {\n if (str.endsWith(mod.pattern)) {\n from = str.length - mod.pattern.length\n to = str.length - 1\n }\n } else {\n from = str.indexOf(mod.pattern)\n to = from + mod.pattern.length - 1\n while (mod.word && from >= 0) {\n if (this.score.isLeftBoundary(str, from) && this.score.isRightBoundary(str, to)) break\n from = str.indexOf(mod.pattern, to + 1)\n to = from + mod.pattern.length - 1\n }\n }\n\n if (mod.inverse)\n return from === -1 ? { from: 0, score: 1000, search: str, str: original, to: 0 } : undefined\n if (from >= 0)\n return { from, score: this.score.get(original, from, to), search: str, str: original, to }\n return undefined\n }\n\n #regex(str: string, mod: Mod): Match | undefined {\n const match = mod.re?.exec(str)\n if (!match?.[0]) return undefined\n const from = match.index\n const to = from + match[0].length - 1\n return { from, score: this.score.get(str, from, to), search: str, str, to }\n }\n\n #fuzzyFind(\n str: string,\n original: string,\n pattern: string[],\n init = 0\n ): Pick<Match, \"from\" | \"to\" | \"score\"> | undefined {\n const from = str.indexOf(pattern[0] ?? \"\", init)\n if (from === -1) return undefined\n this.score.init(original, from)\n let last = from\n for (let i = 1; i < pattern.length; i++) {\n last = str.indexOf(pattern[i], last + 1)\n // Bail before reading the score: a partial accumulation never\n // escapes this method, so `#fuzzy` only ever sees a score that\n // corresponds to a fully-matched window.\n if (last === -1) return undefined\n this.score.update(last)\n }\n return { from, score: this.score.score, to: last }\n }\n\n #fuzzy(str: string, original: string, pattern: string[]): Match | undefined {\n // Anchor on every occurrence of the first char and keep the\n // highest-scoring window. The score rides in the return value rather\n // than being read off the shared `this.score`, so there's no\n // \"is the accumulator aligned with `best` right now?\" invariant.\n let best = this.#fuzzyFind(str, original, pattern)\n if (!best) return undefined\n for (\n let next = this.#fuzzyFind(str, original, pattern, best.from + 1);\n next;\n next = this.#fuzzyFind(str, original, pattern, next.from + 1)\n ) {\n if (next.score > best.score) best = next\n }\n return { from: best.from, score: best.score, search: str, str: original, to: best.to }\n }\n\n #fuzzyPositions(str: string, pattern: string[], from: number): number[] {\n const ret = [from]\n let last = from\n for (let i = 1; i < pattern.length; i++) {\n last = str.indexOf(pattern[i], last + 1)\n if (last === -1) break\n ret.push(last)\n }\n return ret\n }\n}\n\nfunction itemField(item: SearchItem, field: string): string | undefined {\n const value = item[field as keyof SearchItem] as unknown\n if (value === undefined || value === null) return undefined\n if (typeof value === \"string\") return value\n if (typeof value === \"number\" || typeof value === \"boolean\" || typeof value === \"bigint\")\n return String(value)\n if (Array.isArray(value)) return value.join(\" \")\n return\n}\n\nfunction parseFilePattern(pattern: string): string | undefined {\n return (\n pattern.match(/^(.*[/\\\\].*):\\d*:?:?\\d*$/)?.[1] ??\n pattern.match(/^(.+\\.[a-z_]+):\\d*:?:?\\d*$/)?.[1]\n )\n}\n","import type { ScoredItem, SearchItem } from \"./matcher.ts\"\n\ntype SortKey<T extends SearchItem> = Extract<keyof (ScoredItem<T> & SearchItem), string>\n\nexport type SortField<T extends SearchItem = SearchItem> =\n | SortKey<T>\n | `#${SortKey<T>}`\n | `${SortKey<T>}:desc`\n\nexport type ParsedField<T extends SearchItem = SearchItem> = {\n desc?: boolean\n len?: boolean\n name: SortKey<T>\n}\n\nexport type Sorter<T extends SearchItem = SearchItem> = (\n a: ScoredItem<T>,\n b: ScoredItem<T>\n) => number\n\nfunction parse<T extends SearchItem>(field: SortField<T>): ParsedField<T> {\n const len = field.startsWith(\"#\")\n const desc = field.endsWith(\":desc\")\n const name = field.replace(/^#/, \"\").replace(/:desc$/, \"\") as SortKey<T>\n return { desc, len, name }\n}\n\nexport function sorter<T extends SearchItem>(\n fields: readonly SortField<T>[] = [\"score:desc\", \"#text\", \"idx\"]\n): Sorter<T> {\n const parsed: ParsedField<T>[] = fields.map(parse)\n return (a, b) => {\n for (const field of parsed) {\n let av: unknown = a[field.name]\n let bv: unknown = b[field.name]\n if (av === undefined || bv === undefined) continue\n if (field.len) {\n av = typeof av === \"string\" || Array.isArray(av) ? av.length : 0\n bv = typeof bv === \"string\" || Array.isArray(bv) ? bv.length : 0\n }\n if (av === bv) continue\n if (typeof av === \"boolean\" && typeof bv === \"boolean\") {\n av = av ? 0 : 1\n bv = bv ? 0 : 1\n }\n return compare(av, bv) * (field.desc ? -1 : 1)\n }\n return 0\n }\n}\n\nfunction compare(a: unknown, b: unknown): number {\n if (typeof a === \"number\" && typeof b === \"number\") return a - b\n if (typeof a === \"string\" && typeof b === \"string\") return a.localeCompare(b)\n return String(a).localeCompare(String(b))\n}\n","// oxlint-disable no-await-in-loop\nimport type { MaybePromise } from \"@zaly/shared\"\nimport type { MatcherOptions, ScoredItem, SearchItem } from \"./matcher.ts\"\nimport type { Sorter, SortField } from \"./sort.ts\"\n\nimport { TopK } from \"@zaly/shared/minheap\"\nimport { Matcher } from \"./matcher.ts\"\nimport { sorter } from \"./sort.ts\"\n\nexport type SearchOptions<T extends SearchItem = SearchItem> = MatcherOptions & {\n sort?: boolean | readonly SortField<T>[]\n filter?: boolean\n sortEmpty?: boolean\n frecency?: () => (file: string) => number\n limit?: number\n throttle?: number\n}\n\nexport type SearchFn<T extends SearchItem = SearchItem> = (\n query: string,\n match: Match<T>\n) => MaybePromise<ScoredItem<T>[]>\n\nexport type SearchItems<T extends SearchItem = SearchItem> = readonly T[] | SearchFn<T>\n\n/** Match function handed to `complete`. Returns `0` for no match,\n * positive integer otherwise — so both `match(s) > 0` and the\n * idiomatic `.filter(match(s))` work (0 is falsy). The magnitude is a\n * score the source can use to rank its own candidates when it cares\n * about order. */\nexport type Match<T extends SearchItem = SearchItem> = (s: string | T) => number\n\nconst BONUS_FRECENCY = 8\nconst SEARCH_LIMIT = 1000\nconst aborted = Symbol(\"search.aborted\")\n\nexport class Searcher<T extends SearchItem = SearchItem> {\n #opts: SearchOptions<T>\n #sorter?: Sorter<T>\n #matcher: Matcher<T>\n #ac?: AbortController\n\n constructor(opts: SearchOptions<T>) {\n this.#opts = opts\n const sortOpts = opts.sort === true ? undefined : opts.sort\n this.#sorter = sortOpts === false ? undefined : sorter(sortOpts)\n this.#matcher = new Matcher(opts)\n }\n\n /** Create a match function bound to the current pattern. If the\n * matcher has been updated since the search started, match will\n * return `0` to indicate no match, to prevent stale results */\n createMatch(opts: { signal: AbortSignal }): Match<T> {\n const m = this.#matcher\n return (s: string | T) => (opts.signal.aborted ? 0 : m.match(s))\n }\n\n async search(\n items: SearchItems<T>,\n query = \"\",\n opts: { progress?: (results: ScoredItem<T>[]) => MaybePromise } = {}\n ): Promise<ScoredItem<T>[]> {\n try {\n return await this.#search(items, query, opts)\n } catch (error) {\n if (error === aborted) return []\n throw error\n }\n }\n\n get limit(): number {\n return this.#opts.limit ?? (this.#sorter ? SEARCH_LIMIT : Infinity)\n }\n\n async #search(\n items: SearchItems<T>,\n query = \"\",\n opts: { progress?: (results: ScoredItem<T>[]) => MaybePromise } = {}\n ): Promise<ScoredItem<T>[]> {\n this.#ac?.abort(aborted)\n const ac = (this.#ac = new AbortController())\n\n const m = this.#matcher\n m.init(query)\n const f = this.#opts.frecency?.()\n const s = this.#sorter\n const limit = this.limit\n const ret: ScoredItem<T>[] = []\n let match = (item: T) => this.#matcher.update(item)\n const topk =\n s && (this.#opts.sortEmpty || !m.empty())\n ? new TopK<ScoredItem<T>>(limit, (a, b) => -s(a, b))\n : undefined\n\n if (typeof items === \"function\") {\n match = (item: T) => item as ScoredItem<T>\n items = await items(query, this.createMatch({ signal: ac.signal }))\n ac.signal.throwIfAborted()\n }\n\n if (items.length === 0) return []\n\n const results = () => topk?.sorted() ?? ret\n\n // Process items in three phases, so that the results in the UI stabilize faster:\n // - previous topk results (topk)\n // - scored items (score)\n // - unscored items (rest)\n const todo: [T[], T[], T[]] = [[], [], []]\n let idx = 0\n if (!topk) todo[0] = items as T[]\n else {\n for (const item of items) {\n item.idx = idx++\n const it = item as ScoredItem<T>\n if (it.topk) todo[0].push(item)\n else if (it.score) todo[1].push(item)\n else todo[2].push(item)\n }\n }\n\n const doFilter = !m.empty() && (this.#opts.filter ?? true)\n\n let lastYield = performance.now()\n let dirty = false\n let count = 0\n\n loop: for (const todos of todo) {\n for (const item of todos) {\n ac.signal.throwIfAborted()\n if (count++ % 256 === 0) {\n const now = performance.now()\n if (now - lastYield >= (this.#opts.throttle ?? 16)) {\n lastYield = now\n await new Promise((r) => setImmediate(r))\n if (opts.progress && dirty) {\n dirty = false\n await opts.progress(results())\n }\n }\n }\n const si = match(item)\n if (si.file && si.score && f) {\n const frecency = f(si.file)\n si.score += (1 - 1 / (1 + frecency)) * BONUS_FRECENCY\n }\n if (doFilter && si.score === 0) continue\n if (topk) {\n si.topk = false\n const ta = topk.add(si)\n if (ta.added) {\n si.topk = true\n dirty = true\n if (ta.evicted) ta.evicted.topk = false\n }\n } else {\n ret.push(si)\n dirty = true\n if (ret.length >= limit) break loop\n }\n }\n }\n\n return results()\n }\n\n positions(s: string | T): number[] {\n return this.#matcher.positions(s)\n }\n}\n","import type { Reactive, Ref } from \"../core/reactive.ts\"\nimport type { State } from \"../core/state.ts\"\nimport type { NodeActionMap } from \"../input/actions.ts\"\nimport type { ScoredItem, SearchItem } from \"../search/matcher.ts\"\nimport type { SearchItems, SearchOptions } from \"../search/search.ts\"\nimport type { Option, Select, SelectState } from \"./select.ts\"\nimport type { TreeItem, TreeProps } from \"./tree.ts\"\n\nimport { sliceAnsi, stripAnsi } from \"@zaly/shared/ansi\"\nimport { createProgressive, effect, memo, untrack, unwrap } from \"../core/reactive.ts\"\nimport { Searcher } from \"../search/search.ts\"\nimport { Input } from \"./input.ts\"\nimport { select } from \"./select.ts\"\nimport { tree } from \"./tree.ts\"\nimport { widget } from \"./widget.ts\"\n\nexport type PickerItem = Option & SearchItem\nexport type PickerActions = keyof ReturnType<typeof picker>[\"actions\"]\n\ntype PickerBaseProps<T extends PickerItem = PickerItem> = SearchOptions<T> & {\n /** The `Input` to watch. Pass the node directly, or a `Ref<Input>`\n * populated by `node.ref(ref)` elsewhere in the tree — the latter\n * enables fully inline composition where the input doesn't need a\n * local binding. The ref is dereferenced on mount, so wiring is\n * type-safe and ordering-flexible (autocomplete can be constructed\n * before the Input is). */\n input?: Input | Ref<Input>\n pattern?: Reactive<string>\n reverse?: boolean\n actions?: NodeActionMap<Select<T>>\n}\n\nexport type PickerSelectProps<T extends PickerItem = PickerItem> = PickerBaseProps<T> &\n Omit<SelectState<T>, \"items\"> & {\n items: Reactive<SearchItems<T>>\n tree?: never\n }\n\nexport type PickerTreeProps<T extends TreeItem = TreeItem> = PickerBaseProps<T> &\n TreeProps<T> & {\n items?: never\n }\n\nfunction isTree<T extends Option = Option>(\n props: PickerTreeProps<T> | PickerSelectProps<T>\n): props is PickerTreeProps<T> {\n return \"tree\" in props\n}\n\nexport const picker = widget(\n <T extends PickerItem = PickerItem>(props: State<PickerSelectProps<T> | PickerTreeProps<T>>) => {\n const pattern = memo(() => {\n if (props.pattern !== undefined) return unwrap(props.pattern)\n const inp = props.input instanceof Input ? props.input : props.input?.()\n return inp?.state.value ?? \"\"\n })\n\n let node: Select<T>\n let items: Reactive<SearchItems<T>>\n if (isTree(props)) {\n props = { filter: false, fuzzy: false, sort: false, ...props }\n const t = tree(props)\n node = t\n items = t.items\n } else {\n node = select({ ...props, items: [] })\n items = props.items\n }\n const searcher = new Searcher<T>(props)\n\n node.extendRenderer((prev) => (item, ctx) => {\n let row = prev(item, ctx)\n if (!item.score) return row\n const stripped = stripAnsi(row)\n const positions = searcher.positions(stripped).toSorted((a, b) => b - a)\n while (positions.length > 0) {\n const from = positions.pop()!\n let to = from\n while (positions.length && positions.at(-1) === to + 1) to = positions.pop()!\n row =\n sliceAnsi(row, 0, from) +\n ctx.style.accent(stripped.slice(from, to + 1)) +\n sliceAnsi(row, to + 1)\n }\n return row\n })\n\n const results = createProgressive<ScoredItem<T>[]>(\n async ({ set }) =>\n await searcher.search(unwrap(items), pattern(), { progress: (r) => set(r) }),\n {\n initialValue: [],\n }\n )\n node.state.items = results\n if (props.input) node.bind(props.input)\n\n const matches = () =>\n unwrap(node.state.items)\n .map((item, i) => [item, i] as const)\n .filter(([item]) => item.score)\n .map(([, i]) => i)\n\n effect(() => {\n const m = matches()\n node.state.more = m.length >= searcher.limit\n if (m.length === 0 || pattern() === \"\") return\n untrack(() => {\n // When filtering, go to the first (best) match.\n // When not filtering, go to the first match that is at or after the current active index, or the first match if none are after.\n if (props.filter === false) {\n const active = node.active\n node.active = m.find((i) => i >= active) ?? m[0]\n } else node.active = 0\n })\n })\n\n return node.withActions({\n ...props.actions,\n \"picker.next\": () => {\n const active = node.active\n const m = matches()\n if (m.length === 0) return node.action(\"select.next\")\n node.active = node.state.reverse\n ? (m.toReversed().find((i) => i < active) ?? m.at(-1)!)\n : (m.find((i) => i > active) ?? m[0])\n },\n \"picker.prev\": () => {\n const active = node.active\n const m = matches()\n if (m.length === 0) return node.action(\"select.prev\")\n node.active = node.state.reverse\n ? (m.find((i) => i > active) ?? m[0])\n : (m.toReversed().find((i) => i < active) ?? m.at(-1)!)\n },\n })\n }\n)\n"],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"queries-DH3bj74K.d.mts","names":[],"sources":["../src/input/keys.ts","../src/input/decoder.ts","../src/input/actions.ts","../src/layout/size.ts","../src/core/reactive.ts","../src/core/state.ts","../src/layout/border.ts","../src/widgets/text.ts","../src/widgets/box.ts","../src/widgets/overlay.ts","../src/core/ctx.ts","../src/widgets/log.ts","../src/services/logger.ts","../src/renderer/terminal.ts","../src/renderer/frame.ts","../src/renderer/surface.ts","../src/renderer/overlay.ts","../src/renderer/selection.ts","../src/renderer/stream.ts","../src/renderer/ui.ts","../src/renderer/renderer.ts","../src/core/node.ts","../src/input/router.ts","../src/input/queries.ts"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;UA0BiB;;EAEf;;;;;;;EAOA;EACA;EACA;EACA;EACA;;;KAIU;;;;;KAMA,yBAAyB;cAEvB;;KAGF;YAAkC;;cAGxC;cAuCO,wBAAwB;EACnC,YAAY,iBAAiB;;iBAgDf,aAAa,YAAY,KAAK;;;;;;;;iBAgB9B,UAAU,yBAAyB,WAAW;;;;;;;iBAkB9C,WAAW,IAAI,UAAU;;;;;;;;;;;;KCvK7B;KAEA;EACV;EACA;EACA;EACA;EACA;EACA;EACA;;EAEI;EAAgB;;EAChB;EAA8B,QAAQ;EAAa;;KAG7C;EACN;EAAuB;EAAa;EAAkB;EAAgB;;EACtE;EAAuB;EAA6B;EAAkB;;KAEhE;EACN;EAAa,OAAO;;EACpB;EAAe;;EACf;EAAe;IACjB,wBACA;;;;;;;;KCrBQ,UAAU,UAAU,WAAW,UAAU;;WAE1C;WACA,OAAO;;;;WAIP,SAAS;;WAET;;WAEA,MAAM;EACf,OAAO,WAAW;KACf,UAAU;;;;WAKA,MAAM;;KAIT,SAAS,UAAU,WAAW,UAAU,aAClD,KAAK,UAAU,GAAG,OACf;KAEO,aAAa,KAAK;EAC5B;EACA,IAAI;EACJ;;;;;;;;;;;;;;;UAgBe,UAAU,UAAU,WAAW,UAAU;EACxD;EACA;EACA;EACA;EACA,OAAO;EACP;EACA,KAAK,SAAS,GAAG;;;EAGjB;;KAGU,OAAO,UAAU,WAAW,UAAU,YAAY,UAAU,GAAG;EAAO;;KAEtE,YAAY,eAAe;KAE3B;EACV;EACA,cAAc;EACd;EACA;EACA,UAAU,MAAM;;;;;;;;;;;KA0BN,WAAW,UAAU,OAAO,QACpC,SAAS,UAAU,MAClB,UAAU,UAAU;EAAO,IAAI,SAAS,UAAU;;;KAG3C,cAAc,UAAU,OAAO,QAAQ,eAAe,WAAW;KAExE;EACH;;;;;;;;;;;;;;;;;;;;cAqBW,gBAAgB,QAAQ;;EASnC,YAAY,SAAS;;EAOrB,kBAAkB,UAAU;EAI5B,KAAK,SAAS;;;;;;;;;;;;;EAsBd,SAAS,SAAS,YAAY,UAAU;IAAQ;;;EAyBhD,OAAO,mBAAmB;EAS1B,IAAI,aAAa;EAIjB,KAAK,OAAO,eAAe;EAM3B,KAAK,OAAO,eAAe;;;;;;;;;;EAa3B,SAAS,YAAY,MAAM,QAAQ;EAEnC,SAAS,QAAQ,QAAQ,MAAM,QAAQ;EAyBvC,YAAY,QAAQ,WAAW;IAAQ;IAAgB;;EA+CvD,SAAS,MAAM,MAAM;IAAQ,SAAS;OAAuB;IAAW;;;;;;KCrT9D;;;;;;;;;;KAWA,gBAAgB;;;;;;;;;;;;;;;;;;;;;;iBCuDZ,QAAQ,GAAG,UAAU,IAAI;;;iBAMzB,KAAK,GAAG,GAAG,SAAS,KAAK;;;;;;;;;;;;;;;;;;;;;;;;;;UA+BxB,QAAQ;WACd;WACA,cAAc;;iBAGT,cAAc,MAAM,QAAQ;iBAC5B,cAAc,GAAG,cAAc,IAAI,QAAQ;;;;iBAQ3C,eAAe,GAAG,KAAK,QAAQ,IAAI,OAAO;;;;iBAW1C,WAAW,GAAG,KAAK,QAAQ,KAAK;;;;cAa1C;KAEM,OAAO,eAAe,KAAK,SAAS,IAAI,KAAK,OAAO;WACrD,KAAK,SAAS;WACd,KAAK,OAAO;;;;KAKX,SAAS,YAAY;YAAiB;;;;KAItC,OAAO,OAAO,MAAM,MAAM,MAAM,MAAM;YAA2B;;;KAGjE,SAAS,KAAK,IAAI,SAAS;;;;;iBAMvB,WAAW,GAAG,aAAa,KAAK,SAAS;;;;;;iBASzC,OAAO,GAAG,GAAG,SAAS,KAAK;;;;;;;;;;;;;;;;;;;;;;cAuC9B;;EACX,SAAS;EAKT,YAAY,SAAS;MAIjB;;;MAMA,YAAY;EAIhB,WAAW,YAAY;;EAKvB,WAAW;;EASX;;;;;;;;;;;;;;iBA+Bc,eAAe,GAAG,MAAM,MAAM,UAAU,IAAI;;;;;;;iBAU5C,UAAU,GAAG,OAAO,OAAO,UAAU,IAAI;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;iBA+CzC,WAAW,GAAG,KAAK,wBAAwB,IAAI;;;;;;;;;;;;;;;;;;;iBAwB/C,WAAW,UAAU,MAAM,UAAU,IAAI;;;;;;;;;;;;;;;iBAkBzC,UAAU;;;;;iBAYV,kBAAkB;;;;;;;;;;;;iBAelB,kBAAkB,MAAM;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;iBA2CxB,OAAO,GACrB,SAAS,GACT;EAAQ,mBAAmB,MAAM,GAAG,MAAM;IACzC,OAAO;;;;;;;;;;;;;;;iBAwCM,WAAW,GAAG,UAAU,IAAI,SAAS;;;;;;;;;;;;;;;;;;;iBAwBrC,OAAO;;;;;;;;;;;;;;;;iBA+DP,KAAK,GAAG,UAAU,IAAI,SAAS;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;KA8CnC,YAAY,oBAAoB;;;;;EAK1C,MAAM,OAAO,QAAQ,OAAO,SAAS,MAAM,QAAQ;;iBAGrC,YAAY,kBAAkB,SAAS,IAAI,YAAY;;;;;;;;;;;;;;;;;KAmE3D;EACV;EACA;EACA;EACA,gBAAgB;;;;;cAML,iBAAe,QAAA;;;;;;;;;iBAUZ,uBAAuB,SAAS,mBAAmB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;iBA4DnD,YAAY,GAC1B,KAAK,MAAM,kBAAkB,QAAQ,IACrC;EAAQ,cAAc;IACrB,SAAS;iBACI,YAAY,GAC1B,KAAK,MAAM,kBAAkB,QAAQ,IACrC;EAAS,eAAe;IACvB,SAAS;KAgCA,YAAY,KAAK,SAAS;WAC3B,SAAS;EAClB,gBAAgB;;iBAGF,kBAAkB,GAChC,KAAK;EAAO,QAAQ;EAAa,MAAM,OAAO;MAAiB,aAAa,IAC5E;EAAQ;EAAmB,cAAc;IACxC,YAAY;iBACC,kBAAkB,GAChC,KAAK;EAAO,QAAQ;EAAa,MAAM,OAAO;MAAiB,aAAa,IAC5E;EAAQ;EAAmB,eAAe;IACzC,YAAY;iBAmEC,eAAe,GAC7B,KAAK;EAAO,QAAQ;MAAkB,cAAc,aAAa,MACjE;EAAQ;EAAmB,wBAAwB;IAClD,qBAAqB;UAeP,IAAI;MACf;MACA,SAAS;MACT,MAAM,OAAO;;iBAGH,UAAU,GACxB,QAAQ,GACR;EAAQ,SAAS,OAAO,GAAG,MAAM;IAChC,IAAI;;;;;;;;;;;;;UC54BG,kBAAkB,WAAW;;EAErC;;KAGU,MAAM,6BAA6B,IAAI;;;;;;KAOvC,aAAa;UAER;EACf,UAAU;;;;;;;;;;;;UAaK;;;EAGf,QAAQ;;;EAGR,WAAW;;EAEX,WAAW;;;EAGX;;;;EAIA;;UAGe;EACf;EACA;;;;;;;;UCtDe;EACf;EACA;EACA;EACA;EACA;EACA;;KAGU,yDAAyD;KAmBzD;;;;;;;;;;;;;;;;;;;;;KCRA,cAAc,qBAAqB,KAAK,cAAc,aAAa;UAE9D,kBAAkB;EACjC,SAAS;EACT;;cAGW,aAAa,KAAK;YACb,QAAQ,KAAK,YAAY;EAS1B,OAAO,KAAK,YAAS,QAAT;;iBAKb,YAAY,SAAS,aAAa,KAAK,YAAY;iBACnD,YAAY,SAAS,yBAAyB,KAAK,YAAY;;;;;;;;;;;;;iBAsB/D,KAAK,SAAS,aAAa,QAAQ,KAAK,MAAM,yBAAyB;iBACvE,KAAK,OAAO,MAAM,aAAa;;;KC3DnC,6BAEE,WAAW,uBACX,WAAW,WAAW,WAAW;UAE9B,iBAAiB;EAChC;EACA;;;;;;EAMA;;;;;;EAMA;EACA,UAAU;EACV,SAAS;EACT,cAAc;;EAEd,mBAAmB;;;;;;EAMnB,uBAAuB;;;;;EAKvB,4BAA4B;;cAGjB,IAAI,+BAA+B,KAAK,WAAW;;YAC9C,QAAQ,KAAK,YAAY;;;;;;;;;;;;;;;;;;;EAuG1B,OAAO,KAAK,YAAS;;;;;KAgLjC,QAAQ;;;;;;;;;;iBAWG,IAAI,OAAO,MAAM,cAAc,UAAU,UAAU;;;UCjVlD;;EAEf;;EAEA;;EAEA;EACA;EACA;EACA;;;;EAIA;;KAGG;EACH;;KAGU,QAAQ,UAAU,SAAS,UAAU,IAAI;EACnD,UAAU;IACR,QAAQ;iBAEI,QAAQ,UAAU,SAAS,QACzC,OAAO,MAAM,eAAe,cACzB,UAAU,IACZ,QAAQ;;;;;;;;;;;;;;UCTM;EACf;EACA,OAAO;EACP;;;;;;WAMS,WAAW;;;;;;;;;;;;;UAcL;;WAEN,SAAS;;;WAIT;aACE,MAAM,SAAS;aACf,SAAS,GAAG;;;;;;WAOd;aACE;aACA,QAAQ,QAAQ;aAChB,MAAM;;aAEN,QAAQ,MAAM;;aAEd,OAAO,MAAM;aACb,SAAS;;;;;;WAOX,SAAS;;;;WAKT,UAAU,eAAe;;;;WAIzB,WAAW,kBAAkB,GAAG,sBAAsB;EAE/D,QAAQ;;;;KC3EE;UAEK;EACf,OAAO;EACP,SAAS;EACT;;EAEA,QAAQ;;EAER;;EAEA,QAAQ;;EAER;;EAEA,YAAY;EACZ;;;;;;;;;;;;cAyEW,MAAG,OAAkB,MAAM,cAAS,UAAe,WAAA;;;;UC9F/C;EACf,SAAS,YAAY;;KAGX,mBAAmB,OAAO,UAAU,mBAAmB;KAEvD,mBAAmB,KAAK;UAEnB,wBAAwB;;;EAGvC;;EAEA,SAAS,QAAQ,OAAO,UAAU;;EAElC,UAAU;EACV,QAAQ,MAAM,SAAS;;;EAGvB,SAAS,cAAc;;cAWZ,uBAAuB;;EAKlC,YAAY,OAAM;EAKlB,OAAO,QAAQ;EAKf;EAKA,OAAO,OAAO,OAAO;;;;;;;;;;;;UChDN;WACN;WACA;WACA;EACT,QAAQ;;UAGO;WACN;EACT,cAAc;EACd;EACA;EACA,KAAK,eAAe,cAAc;EAClC,MAAM,eAAe,cAAc;EACnC;EACA;;UAiBe;EACf,QAAQ;EACR,SAAS;;EAET;;EAEA;;EAEA;;EAEA;;KAGG,kBAAkB,cAAc;;cAOxB;;EAmBX,YAAY,OAAM;;MAUd;;MAKA;;MAKA;;MAKA;;MAKA;MAIA;MAIA;MAIA,MAAM;;;;;EAeV;EA8DA,aAAa;IAAQ;;;EASrB;;;;;;;;EAyCA,YAAY,mBAAmB;EAC/B,YAAY,2BAA2B;EACvC,YAAY;;EAmCZ,iBAAiB;;EAYjB,MAAM;;;EA4BN,gBAAgB;;;EAMhB;;EAOA,OAAO,aAAa;;EAKpB;;EAKA;;EAKA,SAAS;;;;;;;EAUT,WAAW;;EAKX,YAAY;;EAKZ,gBAAgB,aAAa;;EAK7B;;;;;;;EAUA,KAAK;EAYL,SAAS,IAAI;;;;KC7YH,WAAW,UAAU;KAErB;EACV;EACA;EACA;;cAkBW;;WAIU,UAAU;EAA/B,YAAqB,UAAU;EAE/B,MAAM;EAKN,SAAS;EAMT,MACE,aACA,0BACA,wBACA,iBACC;;cAKQ;;WAKA,UAAU;WACV;WACA;EAHX,YACW,UAAU,UACV,iCACA;EAKX,IAAI;EAIJ,IAAI,aAAa;EAKjB,MAAM;EAIN,QAAQ,aAAa,aAAa;EAUlC,MACE,aACA,0BACA,wBACA,iBACC;EAKH,UACE,aACA,0BACA,wBACA,KAAK,YACJ;EAWH,MAAM,IAAI;EAIV;EAIA;EAYA,SAAS,aAAa,gBAAgB,eAAe,IAAI;EAezD,WAAW,aAAa,gBAAgB,eAAe,IAAI;EAe3D;IAAW;IAAc;;;;;;;;;;;;KCxJf;KAEA;EACV;EACA;;;;;;;;;;;;;;;;;uBAkBoB,QAAQ,8BAA8B,QAAQ,eAAe;;oBAC/D,MAAM;EAIxB,IAAI;;WAGK;IAAU;IAAa;;EAEhC,YAAY,UAAU;;EAkBtB,SAAS,OAAO;MAKZ;EAIJ,MAAM,YAAY;;EAKlB;;;gBAQc;;;;gBAOA,YAAY;;;qBAMP,SAAS,KAAK;;;qBAId;;eAGN,kBAAkB;;;WAItB,QAAQ,OAAO,cAAc;EAEhC,OAAO,QAAQ,cAAc;;;;KCvGzB;EACV;EACA;EACA;EACA;EACA;EACA,MAAM;;KAGI;EACV,eAAe;;;;;;;;;;;;;;;;;;;cAoBJ,uBAAuB,QAAQ;;WACjC;MAKL,kBAAkB;MAIlB;IAAY;IAAa;;MAIhB;;MAKT,mBAAmB;;EAKvB,KAAK,KAAK,OAAO,QAAQ;EAQhB,SAAS,OAAO;;;EAMzB,IAAI,UAAU,SAAS,eAAe,IAAI;EAa1C,OAAO,SAAS;EAWhB,KAAK,UAAU,UAAU,SAAS,eAAe,IAAI;EAIrD,MAAM,SAAS;;MAOX,kBAAkB;YAIZ,SAAS,KAAK;YAId;;;;;;;EAYJ,QAAQ,OAAO,cAAc;;;;KC1HzB;KAEA;EACV;EACA,MAAM;EACN,SAAS;EACT,IAAI;;KAQM;EACV;IAAU,YAAY;IAAW,OAAO;;EACxC;IAAa;IAAc,WAAW;;;cAG3B,uBAAuB,QAAQ;;EAK1C,IAAI;EAEJ,YAAY,UAAU;MAKlB,aAAa;MAIb,UAAU,OAAO;MAcjB;MAIA,KAAK;EAaT;EAKA,MAAM,OAAO;EAiCb;EAKA,OAAO,QAAQ,OAAO;EAetB,aAAa,OAAO,aAAa,KAAK;EAItC,aAAa,OAAO,aAAa,KAAK;EAItC,OAAO,OAAO,aAAa,KAAK;;;;KC5HtB;EACV;EACA;IAAU;IAAgB;IAAe;;;KAyC/B;EACV;;;;;;;;;;;;EAYA;;cAqCW,eAAe,QAAQ;;WACzB;EAiBT,YAAY,UAAU,UAAU,OAAM,QAAQ;MAS1C;IAAY;IAAa;;MAIzB,YAAY;;;;;;;;;;EAahB,OAAO,UAAU,MAAM,YAAY,IAAI;;MA4CnC;;MAKA,kBAAkB;EAIhB,YAAY;;;;;;MAUd;EAIJ,OAAO;EAIP,WAAW,OAAO,QAAQ;EAM1B,SAAS,OAAO,QAAQ;EAUxB;EAWA,OAAO,iBAAc;EAoDf,gBAAgB;EAUtB,aAAa;EAIb,SAAS,iBAAc;EAIvB,WAAW,iBAAc;EAgDnB,QAAQ,OAAO,cAAc;MA4L/B;MAIA;;;;;;;;;;;EAcJ;EAIA;EAcA,MAAM;IAAQ;;YAYJ,SAAS,KAAK;YAId;;;;;;;;;;;;;;;;;cC7kBC,WAAW;;WACb;EAIT,YAAY,UAAU;;MAQlB,QAAQ;MAIR,YAJQ;;;;;;;;EAeZ,IAAI,UAAU,MAAM,aAAa,IAAI;;MAOjC;;;;;;;MAUA;;;;;;;;;;EAaE,QAAQ,OAAO,cAAc;;;;;;;;EAkCnC;;MAMI,kBAAkB;YAIZ,SAAS,KAAK;YAId;MAIN;IAAY;IAAa;;;;;UC7Fd;EACf,QAAQ;EACR,SAAS;EACT,SAAS;EACT,QAAQ;;;;;;;;;EASR;;;EAGA;;EAEA;EACA,SAAS;;EAET;EACA,WAAW;;KAGD;EACV;EACA;EACA;;KAGU;;KAGA,eAAe,MAAM;cAEpB;;;EAIX,IAAI,cAAc;EAIlB,IAAI,cAAc;EAIlB,OAAO;;;;;;;;;;;;;;;;cAmBI,iBAAiB,QAAQ;;WAC3B,QAAQ;WACR,IAAI;WACJ,SAAS;WACT,WAAW;WACX,UAAU;WACV,OAAO;WACP,OAAO;;;;WAIP,QAAQ;EAqBjB,SAAS;;;;WAKA,SAAS;EAClB,OAAK;;;;;;EAOL;;MAEI;;;EAOJ,YAAY,OAAM;;;;;;;MAsHd,OAAO;MAgBP,aAAa;MAIb;MAIA,MAAM;MAIN;MAIA,MAAM;;;;MASN;;;;EAOJ,MAAM;;;;;MAMF,MAAM,OAAO;;MAUb,SAAS;EAIb;EAuBA;;EAiBA,QAAQ,aAAa;;;;;;EAerB,SAAS,kBAAkB,MAAM,oBAAoB;;;;;EAarD,KAAK,OAAO;;;;EAsBZ,SAAS,SAAS,cAAc;;;;;EA0E1B,UAAU;;;;;;KCjfN;EACV;EACA;EACA;EACA;EACA;EACA;EACA;EACA;IAAO,KAAK;;EACZ;IAAS,OAAO;;EAChB;IAAc,OAAO;;EACrB;IAAgB,OAAO;;;;;;;;;;;;;;;;;;;;;uBAqBH,KAAK,2BAA2B,2BAA2B,QAC/E,YACA;;EAkBA,UAAU;EACV;YACU,QAAQ,KAAK,YAAY,aAAa;EAEhD,YAAY,OAAO,MAAM,OAAO,UAAU;EAkB1C,WAAW,6BAA6B,QAAQ;EAIhD,YAAY,UAAU,eAAe,SAAS;IAAa,SAAS;;EAKpE,OAAO,UAAU,uCAAuC,OAAO,QAAQ;MAQnE,eAAe;MAKf,SAAS,YAAY,KAAK,MAAM;MAIhC,qBAAqB;gBAIX,wCAAM;;;;;;;YAQV,IAAI,GAAG,UAAU,IAAI,UAAU;;;;;;;;;;;;YAiB/B,4BAA4B;MAGlC,UAAU;;;;;MAQV,OAAO;MAIP,WAAW;MAIX;;;;;;;;;;;;;;EAiBJ;EACA,GAAG;EAOG,UAAU,KAAK,YAAY,QAAQ;MAKrC,wBAAwB;EAO5B,gBAAgB,MAAM;EAKtB,mBAAmB,MAAM;MAKrB,iBAAiB,SAAS;EAI9B;EAgCA,KAAK,GAAG,UAAU,IAAI;EAIhB,OAAO,KAAK,YAAY;qBA4DX,QAAQ,KAAK,YAAY;EAE5C,IAAI,OAAO;EAKX,OAAO,OAAO;EAOd,OAAO,eAAe,wBAAwB,OAAO;EA2CrD;EAKA,MAAM,KAAK;EAkCX;;;;;;;;;EAmBA;;EAUA;MAKI;EAIJ;EAOA;EAOA;EAKA,IAAI,UAAU,MAAM,MAAM,iBAAiB,IAAI;EAK/C;;;;;iBAQc,OAAO,aAAa,KAAK;;;KCld7B,cAAc,sBAAsB;KACpC,cAAc,IAAI;;;;;KAMlB,uBAAuB;;;;;;;UAQlB;EACf;EACA;EACA;EACA;EACA;EACA;;;EAGA;EACA;EACA;;;UAIe;EACf;EACA;EACA;;KAGU;EACV;IAAoB;;EACpB;IAAO,OAAO;;EACd;IAAS,OAAO;;EAChB;IAAmB,OAAO;;EAC1B;IAAS,MAAM;;EACf;IAAQ,MAAM;;;;;;;;;;;;;;;;;;;;;cAqBH,oBAAoB,QAAQ;;EASvC,YAAY,SAAS;;EAMrB,WAAW,SAAS;;MAKhB,WAAW;;;;;;EAUf,MAAM,MAAM;;;EAqBZ,KAAK,MAAM;MAoBP;;;;EAOJ,SAAS,IAAI;;;;KCnJH,cAAc,IAAI,yBAAyB;EACrD;EACA,QAAQ,OAAO,0BAA0B;;KAG/B;EACV;EACA,QAAQ;;KAGL;EACH,QAAQ;;cAGG;;EAIX,YAAY,QAAQ,aAAa,UAAU;EAK3C,MAAM,GAAG,OAAO,cAAc,KAAK,QAAQ;EAwB3C,wBAAwB,OAAM,oBAAsB,SAAA;;;EAWpD,0BAA0B,OAAM,oBAAsB,SAAA;;;EAWtD,UAAU,OAAM,oBAAsB,SAAA;;;;;iBAcxB,WAAW"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"registry-w_w7gZr_.mjs","names":["moonJson"],"sources":["../assets/themes/tokyonight-moon.json","../src/themes/builtin.ts","../src/themes/default.ts","../src/themes/registry.ts"],"sourcesContent":["","// AUTO-GENERATED by `scripts/gen-themes.ts`. DO NOT EDIT.\n// Re-run `bun scripts/gen-themes.ts` after adding/renaming a theme.\n\nimport type { ThemeLoader } from \"./registry.ts\"\nimport type { Theme } from \"./types.ts\"\n\nconst importTheme = (path: string): Promise<Partial<Theme>> =>\n import(`#assets/themes/${path}.json`, { with: { type: \"json\" } }).then(\n (m) => m.default as Partial<Theme>\n )\n\n/**\n * Async loader map for every built-in theme. Each entry returns the\n * raw JSON; `themes/index.ts` wraps these with `resolveTheme` to\n * produce a fully-resolved `Theme` from the registry. Bundlers\n * code-split each `import(\"…json\")` into its own chunk, so apps only\n * pull the theme they actually load.\n *\n * `as const satisfies Record<string, ThemeLoader>` keeps the keys\n * narrow (so `BuiltinThemeName` is a literal union) but lets the\n * value type widen to `Partial<Theme>` — themes have no per-key\n * narrow types worth preserving, and the satisfies clause means\n * `themes/index.ts` can pass this map straight to `themeRegistry`\n * with no cast.\n */\nexport const builtin = {\n \"ayu-dark\": () => importTheme(\"ayu-dark\"),\n \"catppuccin-frappe\": () => importTheme(\"catppuccin-frappe\"),\n \"catppuccin-latte\": () => importTheme(\"catppuccin-latte\"),\n \"catppuccin-macchiato\": () => importTheme(\"catppuccin-macchiato\"),\n \"catppuccin-mocha\": () => importTheme(\"catppuccin-mocha\"),\n dracula: () => importTheme(\"dracula\"),\n \"dracula-soft\": () => importTheme(\"dracula-soft\"),\n \"everforest-dark\": () => importTheme(\"everforest-dark\"),\n \"everforest-light\": () => importTheme(\"everforest-light\"),\n \"github-dark\": () => importTheme(\"github-dark\"),\n \"github-light\": () => importTheme(\"github-light\"),\n \"gruvbox-dark-medium\": () => importTheme(\"gruvbox-dark-medium\"),\n \"kanagawa-dragon\": () => importTheme(\"kanagawa-dragon\"),\n \"kanagawa-wave\": () => importTheme(\"kanagawa-wave\"),\n \"material-theme-palenight\": () => importTheme(\"material-theme-palenight\"),\n \"min-dark\": () => importTheme(\"min-dark\"),\n \"min-light\": () => importTheme(\"min-light\"),\n monokai: () => importTheme(\"monokai\"),\n \"night-owl\": () => importTheme(\"night-owl\"),\n nord: () => importTheme(\"nord\"),\n \"one-dark-pro\": () => importTheme(\"one-dark-pro\"),\n \"one-light\": () => importTheme(\"one-light\"),\n poimandres: () => importTheme(\"poimandres\"),\n \"rose-pine\": () => importTheme(\"rose-pine\"),\n \"solarized-dark\": () => importTheme(\"solarized-dark\"),\n \"solarized-light\": () => importTheme(\"solarized-light\"),\n \"synthwave-84\": () => importTheme(\"synthwave-84\"),\n \"tokyonight-day\": () => importTheme(\"tokyonight-day\"),\n \"tokyonight-moon\": () => importTheme(\"tokyonight-moon\"),\n \"tokyonight-night\": () => importTheme(\"tokyonight-night\"),\n \"tokyonight-storm\": () => importTheme(\"tokyonight-storm\"),\n vesper: () => importTheme(\"vesper\"),\n \"vitesse-dark\": () => importTheme(\"vitesse-dark\"),\n \"vitesse-light\": () => importTheme(\"vitesse-light\"),\n} as const satisfies Record<string, ThemeLoader>\n","// oxlint-disable typescript/no-deprecated\nimport type { Theme } from \"./types.ts\"\n\n/**\n * Slot-level fallbacks. Every Theme value is shallow-merged on top of\n * this record by `resolveTheme`, so partial JSON themes only need to\n * declare slots that diverge from these defaults.\n *\n * Distinct from `defaultTheme` — that's the precomputed `tokyonight-moon`\n * Theme bundled as the default palette for `createCtx()` etc.\n */\n// oxlint-disable-next-line sort-keys\nexport const defaults: Omit<Theme, \"id\"> = {\n // base colors\n primary: \"blue\",\n accent: \"brightMagenta\",\n\n // text\n text: \"inherit\",\n muted: { dim: true },\n quiet: { dim: true, fg: \"muted\", italic: true },\n comment: { fg: \"muted\", italic: true },\n title: { bold: true, fg: \"primary\" },\n delim: \"muted\",\n\n // surface & structure\n subtle: \"brightBlack\",\n ui: { bg: \"subtle\" },\n overlay: { bg: \"subtle\" },\n highlight: { bg: \"subtle\" },\n\n // ui primitives\n divider: \"subtle\",\n selection: { bg: \"brightBlue\", fg: \"black\" },\n gutter: \"subtle\",\n prompt: \"inherit\",\n border: \"black\",\n borderTitle: \"title\",\n\n // code\n code: { bg: \"subtle\" },\n codeTitle: \"title\",\n\n // log levels\n success: \"green\",\n info: \"cyan\",\n warn: \"yellow\",\n error: \"red\",\n\n // syntax\n syntaxNumber: \"brightBlue\",\n syntaxString: \"green\",\n syntaxBoolean: \"yellow\",\n syntaxFunction: \"blue\",\n syntaxField: \"white\",\n syntaxConstant: \"magenta\",\n syntaxSpecial: \"red\",\n syntaxDelimiter: \"delim\",\n syntaxBracket: \"delim\",\n\n // markdown\n mdBold: { bold: true },\n mdCode: { bg: \"primary+10\", fg: \"black\" },\n mdCodeBlock: { bg: \"highlight\", fg: \"primary\" },\n mdCodeBlockTitle: \"title\",\n mdHeading1: \"mdHeading\",\n mdHeading2: { bold: true, fg: \"accent\" },\n mdHeading3: \"mdHeading2\",\n mdHeading4: \"mdHeading2\",\n mdHeading5: \"mdHeading2\",\n mdHeading6: \"mdHeading2\",\n mdHeading: \"title\",\n mdHr: \"accent\",\n mdItalic: { italic: true },\n mdLink: { fg: \"primary\", underline: true },\n mdListBullet: \"accent\",\n mdListChecked: \"primary\",\n mdListUnchecked: \"primary\",\n mdQuote: \"muted\",\n mdStrikethrough: { strikethrough: true },\n mdTable: \"accent\",\n mdTableHeader: \"title\",\n\n // menu\n optionActive: \"selection\",\n optionDesc: \"muted\",\n optionName: \"primary\",\n\n // diff\n diffAdd: { bg: \"success-50\", fg: \"success\" },\n diffContext: \"muted\",\n diffDel: { bg: \"error-50\", fg: \"error\" },\n diffLine: \"gutter\",\n diffTitle: \"title\",\n}\n\n// oxlint-disable-next-line sort-keys\nexport const ansi: Theme = {\n id: \"ansi\",\n name: \"ANSI\",\n ...defaults,\n subtle: \"inherit\",\n divider: \"brightBlue\",\n border: \"brightBlue\",\n highlight: { bg: \"brightBlack\" },\n ui: { bg: \"brightBlack\" },\n selection: { inverse: true },\n diffAdd: { fg: \"success\" },\n diffDel: { fg: \"error\" },\n}\n","import type { Theme } from \"./types.ts\"\n\nimport { withError } from \"@zaly/shared\"\nimport { createRegistry } from \"@zaly/shared/registry\"\nimport { readFileSync } from \"node:fs\"\nimport { basename } from \"pathe\"\nimport moonJson from \"../../assets/themes/tokyonight-moon.json\" with { type: \"json\" }\nimport { builtin } from \"./builtin.ts\"\nimport { defaults, ansi } from \"./default.ts\"\n\n/** Built-in theme names plus the synthetic `\"ansi\"` palette (no JSON\n * — falls back to `defaults` only). */\nexport type BuiltinTheme = keyof typeof builtin | \"ansi\"\nexport type AnyTheme = BuiltinTheme | (string & {})\nexport type ThemeLoader = () => Promise<Partial<Theme>>\n\nconst DEFAULT_THEME: BuiltinTheme = \"tokyonight-moon\"\n\n/**\n * Registry of built-in themes plus any registered at runtime. The\n * registry never awaits — loaders return `Promise<Partial<Theme>>` so\n * callers `await` explicitly.\n */\nexport const themeRegistry = createRegistry<ThemeLoader>(\"theme\").from(builtin)\n// NOTE: remove the ansi theme for now, since it looks kinda broken and not really possible\n// to fix properly\nthemeRegistry.register(\"ansi\", async () => ({ ...ansi }))\n\n/**\n * Load a theme by name or path.\n */\nexport async function loadTheme(name?: string): Promise<Theme>\nexport async function loadTheme(opts: { name?: string; path?: string }): Promise<Theme>\nexport async function loadTheme(o?: string | { name?: string; path?: string }): Promise<Theme> {\n o ??= DEFAULT_THEME\n const opts = typeof o === \"string\" ? { name: o } : o\n\n if (opts.name?.endsWith(\".json\")) return loadTheme({ path: opts.name })\n if (opts.path) return loadThemeFile(opts.path)\n if (opts.name) {\n if (opts.name === DEFAULT_THEME) return defaultTheme\n if (themeRegistry.has(opts.name))\n return resolveTheme(await themeRegistry.load(opts.name), opts.name)\n throw new Error(`Theme \"${opts.name}\" not found.`)\n }\n\n return defaultTheme\n}\n\n/**\n * Fill defaults on a raw theme object. Built-in JSON is dev-controlled\n * so we don't pay typia's ~3MB of generated assertions at startup;\n * user-supplied JSON goes through `loadThemeFile` which validates.\n */\nfunction resolveTheme(theme: unknown, id: string): Theme {\n const { $schema: _, ...rest } = theme as Partial<Theme> & { $schema?: unknown }\n return { ...defaults, id, name: id, ...rest }\n}\n\n/**\n * Load a theme directly from a file path. No directory search happens —\n * this is the escape hatch for CLIs that accept an explicit `--theme\n * /path/to/theme.json` argument.\n *\n * Async because typia's generated `validateTheme` (a few thousand\n * unrolled assertions) is dynamically imported here — it's only needed\n * for user-supplied JSON and should stay off the main startup path.\n */\nasync function loadThemeFile(path: string): Promise<Theme> {\n const raw = withError(() => readFileSync(path, \"utf8\"), `Failed to read theme file at ${path}`)\n const data = withError(() => JSON.parse(raw), `Failed to parse theme JSON at ${path}`)\n const { validateTheme } = await import(\"../schemas/gen/theme.config.ts\")\n return resolveTheme(validateTheme(data), basename(path, \".json\"))\n}\n\n/** TokyoNight Moon — the default. Sourced from `assets/themes/tokyonight-moon.json`. */\nexport const defaultTheme = resolveTheme(moonJson, \"tokyonight-moon\")\n"],"mappings":"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"}
@@ -1,2 +0,0 @@
1
- import { t as MarkdownRenderer } from "./renderer-qSMVeNSV.mjs";
2
- export { MarkdownRenderer };
@@ -1 +0,0 @@
1
- {"version":3,"file":"renderer-qSMVeNSV.mjs","names":["#opts","#parent","#render","#images"],"sources":["../src/markdown/renderer.ts"],"sourcesContent":["import type { RenderCtx } from \"../core/ctx.ts\"\nimport type { Node } from \"../core/node.ts\"\nimport type { Image } from \"../widgets/image.ts\"\nimport type { MdOptions, RenderMarkdown } from \"./types.ts\"\n\nexport type MarkdownOptions = MdOptions & {\n parent?: Node\n}\n\nexport type MarkdownCtx = RenderCtx & {\n images?: boolean\n highlight?: (code: string, lang?: string) => string\n}\n\nexport class MarkdownRenderer {\n #render?: RenderMarkdown\n #images = new Map<string, Image>()\n #parent?: Node\n #opts: MarkdownOptions\n\n constructor(opts: MarkdownOptions = {}) {\n this.#opts = opts\n this.#parent = opts.parent\n }\n\n async render(source: string, ctx: MarkdownCtx): Promise<string> {\n // oxlint-disable-next-line unicorn/no-await-expression-member\n this.#render ??= this.#opts.render ?? (await import(\"#md\")).renderMarkdown\n\n const [{ createCallbacks }, { createImageCallback }] = await Promise.all([\n import(\"./callbacks.ts\"),\n import(\"./image.ts\"),\n ])\n\n const callbacks = createCallbacks(ctx)\n\n // Image handling: the callback emits `<img id=N>` markers during\n // rendering; a post-processing resolver then renders the referenced\n // images concurrently and splices their rows back in. Keeps the\n // markdown callback surface synchronous while supporting async\n // image preparation.\n const image =\n (ctx.images ?? true)\n ? createImageCallback({\n add: (child) => this.#parent?.add(child),\n images: this.#images,\n remove: (child) => this.#parent?.remove(child) ?? child.unmount(),\n })\n : undefined\n\n if (image) callbacks.image = image.cb\n\n let rendered = this.#render(source, callbacks, this.#opts)\n if (image) rendered = await image.resolve(ctx, rendered)\n return this.normalizeEol(source, rendered)\n }\n\n /** Mirror the source's trailing newlines: the renderer adds its own\n /* padding after blocks (`\\n\\n` after paragraphs, etc.) which would\n /* leave stray blank rows. Normalizing to what the caller typed keeps\n /* single-line inputs compact and preserves explicit spacing when\n /* they asked for it. */\n normalizeEol(source: string, rendered: string): string {\n // Collapse multiple blank lines to a maximum of one\n rendered = rendered.replace(/\\n\\n+/g, \"\\n\\n\")\n // Trim leading blank lines\n rendered = rendered.replace(/^\\s*\\n/, \"\")\n const trailing = /\\n*$/.exec(source)?.[0] ?? \"\"\n return rendered.replace(/\\n+$/, trailing)\n }\n}\n"],"mappings":";AAcA,IAAa,mBAAb,MAA8B;CAC5B;CACA,0BAAU,IAAI,IAAmB;CACjC;CACA;CAEA,YAAY,OAAwB,CAAC,GAAG;EACtC,KAAKA,QAAQ;EACb,KAAKC,UAAU,KAAK;CACtB;CAEA,MAAM,OAAO,QAAgB,KAAmC;EAE9D,KAAKC,YAAY,KAAKF,MAAM,WAAW,MAAM,OAAO,OAAA,CAAQ;EAE5D,MAAM,CAAC,EAAE,mBAAmB,EAAE,yBAAyB,MAAM,QAAQ,IAAI,CACvE,OAAO,6BACP,OAAO,uBACT,CAAC;EAED,MAAM,YAAY,gBAAgB,GAAG;EAOrC,MAAM,QACH,IAAI,UAAU,OACX,oBAAoB;GAClB,MAAM,UAAU,KAAKC,SAAS,IAAI,KAAK;GACvC,QAAQ,KAAKE;GACb,SAAS,UAAU,KAAKF,SAAS,OAAO,KAAK,KAAK,MAAM,QAAQ;EAClE,CAAC,IACD,KAAA;EAEN,IAAI,OAAO,UAAU,QAAQ,MAAM;EAEnC,IAAI,WAAW,KAAKC,QAAQ,QAAQ,WAAW,KAAKF,KAAK;EACzD,IAAI,OAAO,WAAW,MAAM,MAAM,QAAQ,KAAK,QAAQ;EACvD,OAAO,KAAK,aAAa,QAAQ,QAAQ;CAC3C;;;;;;CAOA,aAAa,QAAgB,UAA0B;EAErD,WAAW,SAAS,QAAQ,UAAU,MAAM;EAE5C,WAAW,SAAS,QAAQ,UAAU,EAAE;EACxC,MAAM,WAAW,OAAO,KAAK,MAAM,CAAC,GAAG,MAAM;EAC7C,OAAO,SAAS,QAAQ,QAAQ,QAAQ;CAC1C;AACF"}