@bendyline/docblocks-react 1.1.2 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (335) hide show
  1. package/README.md +31 -5
  2. package/dist/AppMenu/AppMenu.d.ts +29 -2
  3. package/dist/AppMenu/AppMenu.d.ts.map +1 -1
  4. package/dist/AppMenu/AppMenu.js +41 -2
  5. package/dist/AppMenu/AppMenu.js.map +1 -1
  6. package/dist/AppMenu/index.d.ts +1 -1
  7. package/dist/AppMenu/index.d.ts.map +1 -1
  8. package/dist/DocBlocksShell/DocBlocksShell.d.ts +15 -2
  9. package/dist/DocBlocksShell/DocBlocksShell.d.ts.map +1 -1
  10. package/dist/DocBlocksShell/DocBlocksShell.js +1677 -298
  11. package/dist/DocBlocksShell/DocBlocksShell.js.map +1 -1
  12. package/dist/DocBlocksShell/LazyEditorShell.d.ts +3 -0
  13. package/dist/DocBlocksShell/LazyEditorShell.d.ts.map +1 -0
  14. package/dist/DocBlocksShell/LazyEditorShell.js +3 -0
  15. package/dist/DocBlocksShell/LazyEditorShell.js.map +1 -0
  16. package/dist/DocBlocksShell/UpdateAvailableNotice.d.ts +13 -0
  17. package/dist/DocBlocksShell/UpdateAvailableNotice.d.ts.map +1 -0
  18. package/dist/DocBlocksShell/UpdateAvailableNotice.js +16 -0
  19. package/dist/DocBlocksShell/UpdateAvailableNotice.js.map +1 -0
  20. package/dist/DocBlocksShell/document-title.d.ts +3 -0
  21. package/dist/DocBlocksShell/document-title.d.ts.map +1 -0
  22. package/dist/DocBlocksShell/document-title.js +17 -0
  23. package/dist/DocBlocksShell/document-title.js.map +1 -0
  24. package/dist/DocBlocksShell/workspace-authority-barrier.d.ts +14 -0
  25. package/dist/DocBlocksShell/workspace-authority-barrier.d.ts.map +1 -0
  26. package/dist/DocBlocksShell/workspace-authority-barrier.js +23 -0
  27. package/dist/DocBlocksShell/workspace-authority-barrier.js.map +1 -0
  28. package/dist/Export/DeferredExportToolbarControls.d.ts +5 -0
  29. package/dist/Export/DeferredExportToolbarControls.d.ts.map +1 -0
  30. package/dist/Export/DeferredExportToolbarControls.js +10 -0
  31. package/dist/Export/DeferredExportToolbarControls.js.map +1 -0
  32. package/dist/Export/ExportDialog.d.ts +10 -1
  33. package/dist/Export/ExportDialog.d.ts.map +1 -1
  34. package/dist/Export/ExportDialog.js +20 -18
  35. package/dist/Export/ExportDialog.js.map +1 -1
  36. package/dist/Export/ExportToolbarControls.d.ts +21 -1
  37. package/dist/Export/ExportToolbarControls.d.ts.map +1 -1
  38. package/dist/Export/ExportToolbarControls.js +96 -11
  39. package/dist/Export/ExportToolbarControls.js.map +1 -1
  40. package/dist/Export/export-destination.d.ts +3 -0
  41. package/dist/Export/export-destination.d.ts.map +1 -0
  42. package/dist/Export/export-destination.js +32 -0
  43. package/dist/Export/export-destination.js.map +1 -0
  44. package/dist/Export/index.d.ts +8 -4
  45. package/dist/Export/index.d.ts.map +1 -1
  46. package/dist/Export/index.js +4 -1
  47. package/dist/Export/index.js.map +1 -1
  48. package/dist/Export/public-api.d.ts +12 -0
  49. package/dist/Export/public-api.d.ts.map +1 -0
  50. package/dist/Export/public-api.js +9 -0
  51. package/dist/Export/public-api.js.map +1 -0
  52. package/dist/Export/run-export.d.ts +3 -1
  53. package/dist/Export/run-export.d.ts.map +1 -1
  54. package/dist/Export/run-export.js +30 -13
  55. package/dist/Export/run-export.js.map +1 -1
  56. package/dist/ExportDialog-MEUISWZX.js +9 -0
  57. package/dist/ExportDialog-MEUISWZX.js.map +1 -0
  58. package/dist/ExportToolbarControls-D2YDWOXW.js +373 -0
  59. package/dist/ExportToolbarControls-D2YDWOXW.js.map +1 -0
  60. package/dist/FileExplorer/FileExplorer.d.ts +26 -4
  61. package/dist/FileExplorer/FileExplorer.d.ts.map +1 -1
  62. package/dist/FileExplorer/FileExplorer.js +204 -29
  63. package/dist/FileExplorer/FileExplorer.js.map +1 -1
  64. package/dist/FileExplorer/FileTreeNode.d.ts +24 -3
  65. package/dist/FileExplorer/FileTreeNode.d.ts.map +1 -1
  66. package/dist/FileExplorer/FileTreeNode.js +27 -8
  67. package/dist/FileExplorer/FileTreeNode.js.map +1 -1
  68. package/dist/FileExplorer/index.d.ts +1 -1
  69. package/dist/FileExplorer/index.d.ts.map +1 -1
  70. package/dist/FileExplorer/useFileTree.d.ts +5 -3
  71. package/dist/FileExplorer/useFileTree.d.ts.map +1 -1
  72. package/dist/FileExplorer/useFileTree.js +173 -13
  73. package/dist/FileExplorer/useFileTree.js.map +1 -1
  74. package/dist/Git/GitAuthGuidanceDialog.d.ts +18 -0
  75. package/dist/Git/GitAuthGuidanceDialog.d.ts.map +1 -0
  76. package/dist/Git/GitAuthGuidanceDialog.js +27 -0
  77. package/dist/Git/GitAuthGuidanceDialog.js.map +1 -0
  78. package/dist/Git/GitBranchesDialog.d.ts +13 -0
  79. package/dist/Git/GitBranchesDialog.d.ts.map +1 -0
  80. package/dist/Git/GitBranchesDialog.js +59 -0
  81. package/dist/Git/GitBranchesDialog.js.map +1 -0
  82. package/dist/Git/GitCloneDialog.d.ts +14 -0
  83. package/dist/Git/GitCloneDialog.d.ts.map +1 -0
  84. package/dist/Git/GitCloneDialog.js +79 -0
  85. package/dist/Git/GitCloneDialog.js.map +1 -0
  86. package/dist/Git/GitCommitDialog.d.ts +12 -0
  87. package/dist/Git/GitCommitDialog.d.ts.map +1 -0
  88. package/dist/Git/GitCommitDialog.js +38 -0
  89. package/dist/Git/GitCommitDialog.js.map +1 -0
  90. package/dist/Git/GitConflictsDialog.d.ts +12 -0
  91. package/dist/Git/GitConflictsDialog.d.ts.map +1 -0
  92. package/dist/Git/GitConflictsDialog.js +17 -0
  93. package/dist/Git/GitConflictsDialog.js.map +1 -0
  94. package/dist/Git/GitContext.d.ts +89 -0
  95. package/dist/Git/GitContext.d.ts.map +1 -0
  96. package/dist/Git/GitContext.js +15 -0
  97. package/dist/Git/GitContext.js.map +1 -0
  98. package/dist/Git/GitDiffDialog.d.ts +20 -0
  99. package/dist/Git/GitDiffDialog.d.ts.map +1 -0
  100. package/dist/Git/GitDiffDialog.js +100 -0
  101. package/dist/Git/GitDiffDialog.js.map +1 -0
  102. package/dist/Git/GitDiffView.d.ts +23 -0
  103. package/dist/Git/GitDiffView.d.ts.map +1 -0
  104. package/dist/Git/GitDiffView.js +77 -0
  105. package/dist/Git/GitDiffView.js.map +1 -0
  106. package/dist/Git/GitHistoryDialog.d.ts +15 -0
  107. package/dist/Git/GitHistoryDialog.d.ts.map +1 -0
  108. package/dist/Git/GitHistoryDialog.js +107 -0
  109. package/dist/Git/GitHistoryDialog.js.map +1 -0
  110. package/dist/Git/GitStatusBar.d.ts +8 -0
  111. package/dist/Git/GitStatusBar.d.ts.map +1 -0
  112. package/dist/Git/GitStatusBar.js +49 -0
  113. package/dist/Git/GitStatusBar.js.map +1 -0
  114. package/dist/Git/GitToolbarControl.d.ts +15 -0
  115. package/dist/Git/GitToolbarControl.d.ts.map +1 -0
  116. package/dist/Git/GitToolbarControl.js +51 -0
  117. package/dist/Git/GitToolbarControl.js.map +1 -0
  118. package/dist/Git/GitUI.d.ts +14 -0
  119. package/dist/Git/GitUI.d.ts.map +1 -0
  120. package/dist/Git/GitUI.js +21 -0
  121. package/dist/Git/GitUI.js.map +1 -0
  122. package/dist/Git/commit-selection.d.ts +22 -0
  123. package/dist/Git/commit-selection.d.ts.map +1 -0
  124. package/dist/Git/commit-selection.js +47 -0
  125. package/dist/Git/commit-selection.js.map +1 -0
  126. package/dist/Git/git-clone-utils.d.ts +8 -0
  127. package/dist/Git/git-clone-utils.d.ts.map +1 -0
  128. package/dist/Git/git-clone-utils.js +26 -0
  129. package/dist/Git/git-clone-utils.js.map +1 -0
  130. package/dist/Git/git-status.d.ts +24 -0
  131. package/dist/Git/git-status.d.ts.map +1 -0
  132. package/dist/Git/git-status.js +105 -0
  133. package/dist/Git/git-status.js.map +1 -0
  134. package/dist/Git/useGit.d.ts +15 -0
  135. package/dist/Git/useGit.d.ts.map +1 -0
  136. package/dist/Git/useGit.js +206 -0
  137. package/dist/Git/useGit.js.map +1 -0
  138. package/dist/Git/useGitStatus.d.ts +17 -0
  139. package/dist/Git/useGitStatus.d.ts.map +1 -0
  140. package/dist/Git/useGitStatus.js +63 -0
  141. package/dist/Git/useGitStatus.js.map +1 -0
  142. package/dist/GitToolbarControl-LMIR4R7I.js +117 -0
  143. package/dist/GitToolbarControl-LMIR4R7I.js.map +1 -0
  144. package/dist/GitUI-KGF5MSNV.js +1048 -0
  145. package/dist/GitUI-KGF5MSNV.js.map +1 -0
  146. package/dist/LazyEditorShell-EF2BWRXU.js +6 -0
  147. package/dist/LazyEditorShell-EF2BWRXU.js.map +1 -0
  148. package/dist/Settings/Settings.d.ts +23 -0
  149. package/dist/Settings/Settings.d.ts.map +1 -0
  150. package/dist/Settings/Settings.js +22 -0
  151. package/dist/Settings/Settings.js.map +1 -0
  152. package/dist/Settings/public-api.d.ts +3 -0
  153. package/dist/Settings/public-api.d.ts.map +1 -0
  154. package/dist/Settings/public-api.js +2 -0
  155. package/dist/Settings/public-api.js.map +1 -0
  156. package/dist/WorkspacePicker/WorkspacePicker.d.ts +6 -1
  157. package/dist/WorkspacePicker/WorkspacePicker.d.ts.map +1 -1
  158. package/dist/WorkspacePicker/WorkspacePicker.js +16 -5
  159. package/dist/WorkspacePicker/WorkspacePicker.js.map +1 -1
  160. package/dist/chunk-3SAXDU2U.js +157 -0
  161. package/dist/chunk-3SAXDU2U.js.map +1 -0
  162. package/dist/chunk-4XXSWN3T.js +13 -0
  163. package/dist/chunk-4XXSWN3T.js.map +1 -0
  164. package/dist/chunk-5A4KEWKT.js +97 -0
  165. package/dist/chunk-5A4KEWKT.js.map +1 -0
  166. package/dist/chunk-AOVTHZU7.js +321 -0
  167. package/dist/chunk-AOVTHZU7.js.map +1 -0
  168. package/dist/chunk-DD4VFJQI.js +51 -0
  169. package/dist/chunk-DD4VFJQI.js.map +1 -0
  170. package/dist/chunk-GSNZSCIK.js +55 -0
  171. package/dist/chunk-GSNZSCIK.js.map +1 -0
  172. package/dist/chunk-VHDP4IPL.js +70 -0
  173. package/dist/chunk-VHDP4IPL.js.map +1 -0
  174. package/dist/chunk-ZI56BNB7.js +270 -0
  175. package/dist/chunk-ZI56BNB7.js.map +1 -0
  176. package/dist/components/Dialog.d.ts +22 -0
  177. package/dist/components/Dialog.d.ts.map +1 -0
  178. package/dist/components/Dialog.js +33 -0
  179. package/dist/components/Dialog.js.map +1 -0
  180. package/dist/editor.d.ts +10 -0
  181. package/dist/editor.d.ts.map +1 -0
  182. package/dist/editor.js +70 -0
  183. package/dist/editor.js.map +1 -0
  184. package/dist/export/index.d.ts +87 -0
  185. package/dist/export/index.js +26 -0
  186. package/dist/export/index.js.map +1 -0
  187. package/dist/hooks/index.d.ts +2 -1
  188. package/dist/hooks/index.d.ts.map +1 -1
  189. package/dist/hooks/index.js +1 -1
  190. package/dist/hooks/index.js.map +1 -1
  191. package/dist/hooks/useDocumentSession.d.ts +16 -0
  192. package/dist/hooks/useDocumentSession.d.ts.map +1 -0
  193. package/dist/hooks/useDocumentSession.js +18 -0
  194. package/dist/hooks/useDocumentSession.js.map +1 -0
  195. package/dist/icons.d.ts +11 -6
  196. package/dist/icons.d.ts.map +1 -1
  197. package/dist/icons.js +21 -20
  198. package/dist/icons.js.map +1 -1
  199. package/dist/index.d.ts +8 -5
  200. package/dist/index.d.ts.map +1 -1
  201. package/dist/index.js +4 -2
  202. package/dist/index.js.map +1 -1
  203. package/dist/preferences/theme.d.ts +18 -0
  204. package/dist/preferences/theme.d.ts.map +1 -0
  205. package/dist/preferences/theme.js +63 -0
  206. package/dist/preferences/theme.js.map +1 -0
  207. package/dist/provider-lease.d.ts +10 -0
  208. package/dist/provider-lease.d.ts.map +1 -0
  209. package/dist/provider-lease.js +42 -0
  210. package/dist/provider-lease.js.map +1 -0
  211. package/dist/run-export-ICTZITXC.js +10 -0
  212. package/dist/run-export-ICTZITXC.js.map +1 -0
  213. package/dist/settings/index.d.ts +28 -0
  214. package/dist/settings/index.js +12 -0
  215. package/dist/settings/index.js.map +1 -0
  216. package/package.json +24 -9
  217. package/src/AppMenu/AppMenu.tsx +169 -99
  218. package/src/AppMenu/index.ts +1 -1
  219. package/src/DocBlocksShell/DocBlocksShell.tsx +2157 -537
  220. package/src/DocBlocksShell/LazyEditorShell.ts +2 -0
  221. package/src/DocBlocksShell/UpdateAvailableNotice.tsx +60 -0
  222. package/src/DocBlocksShell/document-title.ts +19 -0
  223. package/src/DocBlocksShell/workspace-authority-barrier.ts +26 -0
  224. package/src/Export/DeferredExportToolbarControls.tsx +23 -0
  225. package/src/Export/ExportDialog.tsx +74 -20
  226. package/src/Export/ExportToolbarControls.tsx +238 -40
  227. package/src/Export/export-destination.ts +30 -0
  228. package/src/Export/index.ts +18 -4
  229. package/src/Export/public-api.ts +17 -0
  230. package/src/Export/run-export.ts +36 -11
  231. package/src/FileExplorer/FileExplorer.tsx +284 -38
  232. package/src/FileExplorer/FileTreeNode.tsx +100 -8
  233. package/src/FileExplorer/index.ts +1 -1
  234. package/src/FileExplorer/useFileTree.ts +190 -16
  235. package/src/Git/GitAuthGuidanceDialog.tsx +84 -0
  236. package/src/Git/GitBranchesDialog.tsx +144 -0
  237. package/src/Git/GitCloneDialog.tsx +200 -0
  238. package/src/Git/GitCommitDialog.tsx +119 -0
  239. package/src/Git/GitConflictsDialog.tsx +62 -0
  240. package/src/Git/GitContext.tsx +88 -0
  241. package/src/Git/GitDiffDialog.tsx +147 -0
  242. package/src/Git/GitDiffView.tsx +105 -0
  243. package/src/Git/GitHistoryDialog.tsx +195 -0
  244. package/src/Git/GitStatusBar.tsx +157 -0
  245. package/src/Git/GitToolbarControl.tsx +123 -0
  246. package/src/Git/GitUI.tsx +68 -0
  247. package/src/Git/commit-selection.ts +63 -0
  248. package/src/Git/git-clone-utils.ts +23 -0
  249. package/src/Git/git-status.ts +113 -0
  250. package/src/Git/useGit.ts +279 -0
  251. package/src/Git/useGitStatus.ts +78 -0
  252. package/src/Settings/Settings.tsx +118 -0
  253. package/src/Settings/public-api.ts +8 -0
  254. package/src/WorkspacePicker/WorkspacePicker.tsx +62 -8
  255. package/src/components/Dialog.tsx +81 -0
  256. package/src/editor.ts +72 -0
  257. package/src/hooks/index.ts +2 -1
  258. package/src/hooks/useDocumentSession.ts +37 -0
  259. package/src/icons.tsx +33 -55
  260. package/src/index.ts +35 -5
  261. package/src/preferences/theme.ts +67 -0
  262. package/src/provider-lease.ts +52 -0
  263. package/src/styles/docblocks.css +2174 -79
  264. package/src/types/pwa-dom.d.ts +31 -0
  265. package/dist/hooks/useAutoSave.d.ts +0 -15
  266. package/dist/hooks/useAutoSave.d.ts.map +0 -1
  267. package/dist/hooks/useAutoSave.js +0 -83
  268. package/dist/hooks/useAutoSave.js.map +0 -1
  269. package/dist/monaco-slim.d.ts +0 -19
  270. package/dist/monaco-slim.d.ts.map +0 -1
  271. package/dist/monaco-slim.js +0 -19
  272. package/dist/monaco-slim.js.map +0 -1
  273. package/src/fonts/fonts.css +0 -362
  274. package/src/fonts/licenses/LICENSE-cormorant-garamond.txt +0 -93
  275. package/src/fonts/licenses/LICENSE-crimson-text.txt +0 -93
  276. package/src/fonts/licenses/LICENSE-dm-sans.txt +0 -93
  277. package/src/fonts/licenses/LICENSE-dm-serif-display.txt +0 -93
  278. package/src/fonts/licenses/LICENSE-hanken-grotesk.txt +0 -94
  279. package/src/fonts/licenses/LICENSE-ibm-plex-sans.txt +0 -93
  280. package/src/fonts/licenses/LICENSE-inter.txt +0 -93
  281. package/src/fonts/licenses/LICENSE-jetbrains-mono.txt +0 -93
  282. package/src/fonts/licenses/LICENSE-lora.txt +0 -93
  283. package/src/fonts/licenses/LICENSE-merriweather.txt +0 -93
  284. package/src/fonts/licenses/LICENSE-oswald.txt +0 -93
  285. package/src/fonts/licenses/LICENSE-playfair-display.txt +0 -93
  286. package/src/fonts/licenses/LICENSE-pt-serif.txt +0 -93
  287. package/src/fonts/licenses/LICENSE-roboto.txt +0 -93
  288. package/src/fonts/licenses/LICENSE-source-serif-4.txt +0 -93
  289. package/src/fonts/woff2/cormorant-garamond-400.woff2 +0 -0
  290. package/src/fonts/woff2/cormorant-garamond-700.woff2 +0 -0
  291. package/src/fonts/woff2/crimson-text-400.woff2 +0 -0
  292. package/src/fonts/woff2/crimson-text-400i.woff2 +0 -0
  293. package/src/fonts/woff2/crimson-text-700.woff2 +0 -0
  294. package/src/fonts/woff2/dm-sans-400.woff2 +0 -0
  295. package/src/fonts/woff2/dm-sans-400i.woff2 +0 -0
  296. package/src/fonts/woff2/dm-sans-500.woff2 +0 -0
  297. package/src/fonts/woff2/dm-sans-700.woff2 +0 -0
  298. package/src/fonts/woff2/dm-serif-display-400.woff2 +0 -0
  299. package/src/fonts/woff2/hanken-grotesk-400.woff2 +0 -0
  300. package/src/fonts/woff2/hanken-grotesk-400i.woff2 +0 -0
  301. package/src/fonts/woff2/hanken-grotesk-500.woff2 +0 -0
  302. package/src/fonts/woff2/hanken-grotesk-600.woff2 +0 -0
  303. package/src/fonts/woff2/hanken-grotesk-700.woff2 +0 -0
  304. package/src/fonts/woff2/ibm-plex-sans-400.woff2 +0 -0
  305. package/src/fonts/woff2/ibm-plex-sans-400i.woff2 +0 -0
  306. package/src/fonts/woff2/ibm-plex-sans-500.woff2 +0 -0
  307. package/src/fonts/woff2/ibm-plex-sans-600.woff2 +0 -0
  308. package/src/fonts/woff2/ibm-plex-sans-700.woff2 +0 -0
  309. package/src/fonts/woff2/inter-400.woff2 +0 -0
  310. package/src/fonts/woff2/inter-400i.woff2 +0 -0
  311. package/src/fonts/woff2/inter-500.woff2 +0 -0
  312. package/src/fonts/woff2/inter-600.woff2 +0 -0
  313. package/src/fonts/woff2/inter-700.woff2 +0 -0
  314. package/src/fonts/woff2/jetbrains-mono-400.woff2 +0 -0
  315. package/src/fonts/woff2/jetbrains-mono-400i.woff2 +0 -0
  316. package/src/fonts/woff2/jetbrains-mono-700.woff2 +0 -0
  317. package/src/fonts/woff2/lora-400.woff2 +0 -0
  318. package/src/fonts/woff2/lora-400i.woff2 +0 -0
  319. package/src/fonts/woff2/lora-700.woff2 +0 -0
  320. package/src/fonts/woff2/merriweather-400.woff2 +0 -0
  321. package/src/fonts/woff2/merriweather-700.woff2 +0 -0
  322. package/src/fonts/woff2/oswald-400.woff2 +0 -0
  323. package/src/fonts/woff2/oswald-700.woff2 +0 -0
  324. package/src/fonts/woff2/playfair-display-400.woff2 +0 -0
  325. package/src/fonts/woff2/playfair-display-700.woff2 +0 -0
  326. package/src/fonts/woff2/pt-serif-400.woff2 +0 -0
  327. package/src/fonts/woff2/pt-serif-700.woff2 +0 -0
  328. package/src/fonts/woff2/roboto-400.woff2 +0 -0
  329. package/src/fonts/woff2/roboto-400i.woff2 +0 -0
  330. package/src/fonts/woff2/roboto-700.woff2 +0 -0
  331. package/src/fonts/woff2/source-serif-4-400.woff2 +0 -0
  332. package/src/fonts/woff2/source-serif-4-400i.woff2 +0 -0
  333. package/src/fonts/woff2/source-serif-4-700.woff2 +0 -0
  334. package/src/hooks/useAutoSave.ts +0 -116
  335. package/src/monaco-slim.ts +0 -20
@@ -0,0 +1,70 @@
1
+ // src/editor.ts
2
+ var EMPTY_DOCUMENT_PROMPTS = [
3
+ "Start typing your content, or drop images on top of me...",
4
+ "Write anything -- paste markdown, drag in images, or just start typing...",
5
+ "Type away. Markdown syntax works too...",
6
+ "Chapter 1 begins here...",
7
+ "Once upon a time...",
8
+ "A blank page. Exciting, isn't it?",
9
+ "The first word is always the hardest...",
10
+ "Plot twist: this is where it all starts...",
11
+ "Write something the future you will thank you for...",
12
+ "Begin at the beginning...",
13
+ "Let's begin.",
14
+ "We can be heroes...",
15
+ "Here comes the sun...",
16
+ "And so it begins...",
17
+ "Let it be, let it be...",
18
+ "Don't stop believing...",
19
+ "Started from the bottom...",
20
+ "This is the start of something new...",
21
+ "Ground control to Major Tom...",
22
+ "Come as you are...",
23
+ "Every new beginning...",
24
+ "Hello, is it me you're looking for?",
25
+ "Imagine all the people...",
26
+ "Anything you want, you got it...",
27
+ "Rise above...",
28
+ "Do you have the time...",
29
+ "Here we are now, entertain us...",
30
+ "All the small things...",
31
+ "Should I stay or should I go?",
32
+ "I am a patient boy -- I wait, I wait, I wait...",
33
+ "Destination unknown...",
34
+ "Easy like Sunday morning...",
35
+ "Dance, dance, dance to the radio...",
36
+ "New day rising...",
37
+ "Visit the world...",
38
+ "Positive mental attitude...",
39
+ "Better I sing than I cry...",
40
+ "Disconnect for a minute...",
41
+ "We need new noise...",
42
+ "Shoot the moon...",
43
+ "I'll surprise you sometime -- I'll come around...",
44
+ "Coming out of my cage, and doing just fine...",
45
+ "Throw me to the wolves -- I'll come back, leading the pack...",
46
+ "There comes a time -- no excuses...",
47
+ "It's up to me now, turn on the bright lights...",
48
+ "Do what you want...",
49
+ "Fingers crossed...",
50
+ "This is the start of how it all ends...",
51
+ "It has to start somewhere, it has to start sometime -- what better place than here? what better time than now?",
52
+ "I know myself, and I'll begin again...",
53
+ "Dig me out, dig me in...",
54
+ "Everybody's full of sugar, honey, ice and tea...",
55
+ "Take time with a wounded hand, 'cause it likes to heal...",
56
+ "Grab a brush and put on a little makeup...",
57
+ "Amber is the color of your energy...",
58
+ "Wait -- they don't love it like I love it...",
59
+ "A world's been buried, where love is the law; a you-topia..."
60
+ ];
61
+ function pickEmptyDocumentPrompt(random = Math.random) {
62
+ const index = Math.floor(random() * EMPTY_DOCUMENT_PROMPTS.length);
63
+ return EMPTY_DOCUMENT_PROMPTS[index] ?? EMPTY_DOCUMENT_PROMPTS[0];
64
+ }
65
+
66
+ export {
67
+ EMPTY_DOCUMENT_PROMPTS,
68
+ pickEmptyDocumentPrompt
69
+ };
70
+ //# sourceMappingURL=chunk-VHDP4IPL.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/editor.ts"],"sourcesContent":["/**\n * Placeholder prompts shown by DocBlocks when a Markdown document is empty.\n * Hosts pick one prompt for each mounted document generation and pass it to\n * Squisq, so the copy remains stable while that document is open.\n */\nexport const EMPTY_DOCUMENT_PROMPTS = [\n 'Start typing your content, or drop images on top of me...',\n 'Write anything -- paste markdown, drag in images, or just start typing...',\n 'Type away. Markdown syntax works too...',\n 'Chapter 1 begins here...',\n 'Once upon a time...',\n \"A blank page. Exciting, isn't it?\",\n 'The first word is always the hardest...',\n 'Plot twist: this is where it all starts...',\n 'Write something the future you will thank you for...',\n 'Begin at the beginning...',\n \"Let's begin.\",\n 'We can be heroes...',\n 'Here comes the sun...',\n 'And so it begins...',\n 'Let it be, let it be...',\n \"Don't stop believing...\",\n 'Started from the bottom...',\n 'This is the start of something new...',\n 'Ground control to Major Tom...',\n 'Come as you are...',\n 'Every new beginning...',\n \"Hello, is it me you're looking for?\",\n 'Imagine all the people...',\n 'Anything you want, you got it...',\n 'Rise above...',\n 'Do you have the time...',\n 'Here we are now, entertain us...',\n 'All the small things...',\n 'Should I stay or should I go?',\n 'I am a patient boy -- I wait, I wait, I wait...',\n 'Destination unknown...',\n 'Easy like Sunday morning...',\n 'Dance, dance, dance to the radio...',\n 'New day rising...',\n 'Visit the world...',\n 'Positive mental attitude...',\n 'Better I sing than I cry...',\n 'Disconnect for a minute...',\n 'We need new noise...',\n 'Shoot the moon...',\n \"I'll surprise you sometime -- I'll come around...\",\n 'Coming out of my cage, and doing just fine...',\n \"Throw me to the wolves -- I'll come back, leading the pack...\",\n 'There comes a time -- no excuses...',\n \"It's up to me now, turn on the bright lights...\",\n 'Do what you want...',\n 'Fingers crossed...',\n 'This is the start of how it all ends...',\n 'It has to start somewhere, it has to start sometime -- what better place than here? what better time than now?',\n \"I know myself, and I'll begin again...\",\n 'Dig me out, dig me in...',\n \"Everybody's full of sugar, honey, ice and tea...\",\n \"Take time with a wounded hand, 'cause it likes to heal...\",\n 'Grab a brush and put on a little makeup...',\n 'Amber is the color of your energy...',\n \"Wait -- they don't love it like I love it...\",\n \"A world's been buried, where love is the law; a you-topia...\",\n] as const;\n\nexport type EmptyDocumentPrompt = (typeof EMPTY_DOCUMENT_PROMPTS)[number];\n\n/** Pick a prompt using the supplied random source, or `Math.random`. */\nexport function pickEmptyDocumentPrompt(random: () => number = Math.random): EmptyDocumentPrompt {\n const index = Math.floor(random() * EMPTY_DOCUMENT_PROMPTS.length);\n return EMPTY_DOCUMENT_PROMPTS[index] ?? EMPTY_DOCUMENT_PROMPTS[0];\n}\n"],"mappings":";AAKO,IAAM,yBAAyB;AAAA,EACpC;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF;AAKO,SAAS,wBAAwB,SAAuB,KAAK,QAA6B;AAC/F,QAAM,QAAQ,KAAK,MAAM,OAAO,IAAI,uBAAuB,MAAM;AACjE,SAAO,uBAAuB,KAAK,KAAK,uBAAuB,CAAC;AAClE;","names":[]}
@@ -0,0 +1,270 @@
1
+ import {
2
+ FORMAT_EXTENSIONS
3
+ } from "./chunk-DD4VFJQI.js";
4
+
5
+ // src/Export/run-export.ts
6
+ import { parseMarkdown } from "@bendyline/squisq/markdown";
7
+ var MIME_TYPES = {
8
+ docx: "application/vnd.openxmlformats-officedocument.wordprocessingml.document",
9
+ pdf: "application/pdf",
10
+ pptx: "application/vnd.openxmlformats-officedocument.presentationml.presentation",
11
+ md: "text/markdown",
12
+ html: "text/html"
13
+ };
14
+ function downloadBlob(blob, filename) {
15
+ const url = URL.createObjectURL(blob);
16
+ const a = document.createElement("a");
17
+ a.href = url;
18
+ a.download = filename;
19
+ a.click();
20
+ URL.revokeObjectURL(url);
21
+ }
22
+ async function saveExportBlob(blob, filename, saveBlob) {
23
+ if (saveBlob) {
24
+ await saveBlob(blob, filename);
25
+ return;
26
+ }
27
+ downloadBlob(blob, filename);
28
+ }
29
+ function buildFilename(selectedFile, format) {
30
+ const base = selectedFile ? selectedFile.replace(/^\//, "").replace(/\.[^.]+$/, "") : "document";
31
+ return base + FORMAT_EXTENSIONS[format];
32
+ }
33
+ function buildExportFilename(selectedFile, options) {
34
+ const base = selectedFile ? selectedFile.replace(/^\//, "").replace(/\.[^.]+$/, "") : "document";
35
+ if (options.format === "html") {
36
+ if (options.includeLinkedDocs || options.htmlBundle === "zip") return `${base}.zip`;
37
+ if (options.entryAsIndex) return "index.html";
38
+ }
39
+ return base + FORMAT_EXTENSIONS[options.format];
40
+ }
41
+ async function runExport(markdown, selectedFile, options, mediaContainer, saveBlob) {
42
+ const filename = buildFilename(selectedFile, options.format);
43
+ const themeId = options.themeId !== "standard" ? options.themeId : void 0;
44
+ if (options.format === "md") {
45
+ await saveExportBlob(new Blob([markdown], { type: MIME_TYPES.md }), filename, saveBlob);
46
+ return;
47
+ }
48
+ if (options.format === "html") {
49
+ await runHtmlExport(markdown, filename, options, mediaContainer, selectedFile, saveBlob);
50
+ return;
51
+ }
52
+ const doc = parseMarkdown(markdown);
53
+ if (options.format === "docx") {
54
+ const { markdownDocToDocx } = await import("@bendyline/squisq-formats/docx");
55
+ const images = mediaContainer ? await resolveImages(doc, mediaContainer) : void 0;
56
+ const buf = await markdownDocToDocx(doc, { themeId, images });
57
+ await saveExportBlob(new Blob([buf], { type: MIME_TYPES.docx }), filename, saveBlob);
58
+ return;
59
+ }
60
+ if (options.format === "pdf") {
61
+ const { markdownDocToPdf } = await import("@bendyline/squisq-formats/pdf");
62
+ const buf = await markdownDocToPdf(doc, {
63
+ themeId,
64
+ pageSize: options.pageSize
65
+ });
66
+ await saveExportBlob(new Blob([buf], { type: MIME_TYPES.pdf }), filename, saveBlob);
67
+ return;
68
+ }
69
+ if (options.format === "pptx") {
70
+ const [{ markdownToDoc }, { applyTransform }, { docToPptx }] = await Promise.all([
71
+ import("@bendyline/squisq/doc"),
72
+ import("@bendyline/squisq/transform"),
73
+ import("@bendyline/squisq-formats/pptx")
74
+ ]);
75
+ const baseDoc = markdownToDoc(doc);
76
+ const transformed = applyTransform(baseDoc, options.transformStyle);
77
+ const enrichedDoc = transformed.doc;
78
+ if (themeId) {
79
+ enrichedDoc.themeId = themeId;
80
+ }
81
+ const buf = await docToPptx(enrichedDoc, { themeId });
82
+ await saveExportBlob(new Blob([buf], { type: MIME_TYPES.pptx }), filename, saveBlob);
83
+ return;
84
+ }
85
+ }
86
+ async function runHtmlExport(markdown, htmlFilename, options, mediaContainer, selectedFile, saveBlob) {
87
+ const baseName = htmlFilename.replace(/\.html$/, "");
88
+ const zipName = `${baseName}.zip`;
89
+ const singleHtmlFilename = options.entryAsIndex ? "index.html" : htmlFilename;
90
+ const themeId = options.themeId !== "standard" ? options.themeId : void 0;
91
+ if (options.includeLinkedDocs && mediaContainer && selectedFile) {
92
+ const entryPath = basenameForBundle(selectedFile);
93
+ if (options.htmlStyle === "rendered") {
94
+ const [{ markdownDocsToHtmlBundle }, { PLAYER_BUNDLE }] = await Promise.all([
95
+ import("@bendyline/squisq-formats/html"),
96
+ import("@bendyline/squisq-react/standalone-source")
97
+ ]);
98
+ const blob2 = await markdownDocsToHtmlBundle({
99
+ entryPath,
100
+ readDocument: (path) => readDocumentFromContainer(mediaContainer, path),
101
+ readBinary: (path) => mediaContainer.readFile(path),
102
+ playerScript: PLAYER_BUNDLE,
103
+ title: baseName,
104
+ themeId,
105
+ mode: "static",
106
+ entryAsIndex: options.entryAsIndex
107
+ });
108
+ await saveExportBlob(blob2, zipName, saveBlob);
109
+ return;
110
+ }
111
+ const { markdownDocsToPlainHtmlBundle } = await import("@bendyline/squisq-formats/html");
112
+ const blob = await markdownDocsToPlainHtmlBundle({
113
+ entryPath,
114
+ readDocument: (path) => readDocumentFromContainer(mediaContainer, path),
115
+ readBinary: (path) => mediaContainer.readFile(path),
116
+ title: baseName,
117
+ themeId,
118
+ entryAsIndex: options.entryAsIndex
119
+ });
120
+ await saveExportBlob(blob, zipName, saveBlob);
121
+ return;
122
+ }
123
+ if (options.htmlStyle === "rendered") {
124
+ const [{ markdownToDoc }, { docToHtml, docToHtmlZip, collectImagePaths }, { PLAYER_BUNDLE }] = await Promise.all([
125
+ import("@bendyline/squisq/doc"),
126
+ import("@bendyline/squisq-formats/html"),
127
+ import("@bendyline/squisq-react/standalone-source")
128
+ ]);
129
+ const mdDoc2 = parseMarkdown(markdown);
130
+ const baseDoc = markdownToDoc(mdDoc2);
131
+ if (themeId) baseDoc.themeId = themeId;
132
+ const images = mediaContainer ? await resolveDocImages(baseDoc, mediaContainer, collectImagePaths) : void 0;
133
+ if (options.htmlBundle === "zip") {
134
+ const blob = await docToHtmlZip(baseDoc, {
135
+ playerScript: PLAYER_BUNDLE,
136
+ images,
137
+ mode: "static",
138
+ title: baseName
139
+ });
140
+ await saveExportBlob(blob, zipName, saveBlob);
141
+ return;
142
+ }
143
+ const html2 = docToHtml(baseDoc, {
144
+ playerScript: PLAYER_BUNDLE,
145
+ images,
146
+ mode: "static",
147
+ title: baseName
148
+ });
149
+ await saveExportBlob(new Blob([html2], { type: MIME_TYPES.html }), singleHtmlFilename, saveBlob);
150
+ return;
151
+ }
152
+ const mdDoc = parseMarkdown(markdown);
153
+ const referencedImages = collectMarkdownImageUrls(mdDoc);
154
+ const localImages = referencedImages.filter((u) => !isExternalUrl(u));
155
+ if (options.htmlBundle === "zip" && mediaContainer && localImages.length > 0) {
156
+ const [{ markdownDocToPlainHtml: markdownDocToPlainHtml2 }, { MemoryContentContainer }, { containerToZip }] = await Promise.all([
157
+ import("@bendyline/squisq-formats/html"),
158
+ import("@bendyline/squisq/storage"),
159
+ import("@bendyline/squisq-formats/container")
160
+ ]);
161
+ const html2 = markdownDocToPlainHtml2(mdDoc, { title: baseName, themeId });
162
+ const container = new MemoryContentContainer();
163
+ await container.writeFile("index.html", new TextEncoder().encode(html2));
164
+ for (const url of localImages) {
165
+ const data = await mediaContainer.readFile(url);
166
+ if (!data) continue;
167
+ const cleanPath = url.replace(/^\/+/, "");
168
+ await container.writeFile(cleanPath, new Uint8Array(data));
169
+ }
170
+ const blob = await containerToZip(container);
171
+ await saveExportBlob(blob, zipName, saveBlob);
172
+ return;
173
+ }
174
+ const { markdownDocToPlainHtml } = await import("@bendyline/squisq-formats/html");
175
+ const inlineMap = /* @__PURE__ */ new Map();
176
+ if (mediaContainer) {
177
+ for (const url of localImages) {
178
+ const data = await mediaContainer.readFile(url);
179
+ if (!data) continue;
180
+ inlineMap.set(url, arrayBufferToDataUrl(data, url));
181
+ }
182
+ }
183
+ const html = markdownDocToPlainHtml(mdDoc, {
184
+ title: baseName,
185
+ images: inlineMap.size > 0 ? inlineMap : void 0,
186
+ themeId
187
+ });
188
+ await saveExportBlob(new Blob([html], { type: MIME_TYPES.html }), singleHtmlFilename, saveBlob);
189
+ }
190
+ var IMAGE_MIME = {
191
+ png: "image/png",
192
+ jpg: "image/jpeg",
193
+ jpeg: "image/jpeg",
194
+ gif: "image/gif",
195
+ webp: "image/webp",
196
+ bmp: "image/bmp",
197
+ svg: "image/svg+xml"
198
+ };
199
+ function isExternalUrl(url) {
200
+ return url.startsWith("http://") || url.startsWith("https://") || url.startsWith("data:") || url.startsWith("blob:");
201
+ }
202
+ function arrayBufferToDataUrl(data, url) {
203
+ const ext = url.slice(url.lastIndexOf(".") + 1).toLowerCase();
204
+ const mime = IMAGE_MIME[ext] ?? "application/octet-stream";
205
+ const bytes = new Uint8Array(data);
206
+ let binary = "";
207
+ const CHUNK = 32768;
208
+ for (let i = 0; i < bytes.length; i += CHUNK) {
209
+ binary += String.fromCharCode(...bytes.subarray(i, i + CHUNK));
210
+ }
211
+ return `data:${mime};base64,${btoa(binary)}`;
212
+ }
213
+ function collectMarkdownImageUrls(doc) {
214
+ const urls = [];
215
+ function walkBlocks(nodes) {
216
+ for (const node of nodes) {
217
+ if ("children" in node && Array.isArray(node.children)) {
218
+ for (const child of node.children) {
219
+ if (child.type === "image") {
220
+ urls.push(child.url);
221
+ } else if ("children" in child && Array.isArray(child.children)) {
222
+ walkBlocks(child.children);
223
+ }
224
+ }
225
+ }
226
+ }
227
+ }
228
+ walkBlocks(doc.children);
229
+ return Array.from(new Set(urls));
230
+ }
231
+ async function resolveImages(doc, container) {
232
+ const urls = collectMarkdownImageUrls(doc);
233
+ const map = /* @__PURE__ */ new Map();
234
+ for (const url of urls) {
235
+ if (map.has(url)) continue;
236
+ if (isExternalUrl(url)) continue;
237
+ const data = await container.readFile(url);
238
+ if (!data) continue;
239
+ const ext = url.slice(url.lastIndexOf(".") + 1).toLowerCase();
240
+ const contentType = IMAGE_MIME[ext] || "image/png";
241
+ map.set(url, { data, contentType });
242
+ }
243
+ return map;
244
+ }
245
+ function basenameForBundle(selectedFile) {
246
+ const clean = selectedFile.replace(/^\/+/, "");
247
+ const idx = clean.lastIndexOf("/");
248
+ return idx === -1 ? clean : clean.slice(idx + 1);
249
+ }
250
+ async function readDocumentFromContainer(container, path) {
251
+ const data = await container.readFile(path);
252
+ if (!data) return null;
253
+ return new TextDecoder("utf-8").decode(data);
254
+ }
255
+ async function resolveDocImages(doc, container, collectImagePaths) {
256
+ const paths = collectImagePaths(doc);
257
+ const map = /* @__PURE__ */ new Map();
258
+ for (const path of paths) {
259
+ const data = await container.readFile(path);
260
+ if (!data) continue;
261
+ map.set(path, data);
262
+ }
263
+ return map;
264
+ }
265
+
266
+ export {
267
+ buildExportFilename,
268
+ runExport
269
+ };
270
+ //# sourceMappingURL=chunk-ZI56BNB7.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/Export/run-export.ts"],"sourcesContent":["/**\n * Execute an export using @bendyline/squisq-formats.\n */\n\nimport type {\n MarkdownDocument,\n MarkdownBlockNode,\n MarkdownInlineNode,\n} from '@bendyline/squisq/markdown';\nimport { parseMarkdown } from '@bendyline/squisq/markdown';\nimport type { Doc } from '@bendyline/squisq/schemas';\nimport type { ContentContainer } from '@bendyline/squisq/storage';\nimport type { ExportOptions, ExportFormat } from './export-options.js';\nimport { FORMAT_EXTENSIONS } from './export-options.js';\n\nexport type ExportBlobSaver = (blob: Blob, filename: string) => Promise<void> | void;\n\nconst MIME_TYPES: Record<ExportFormat, string> = {\n docx: 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',\n pdf: 'application/pdf',\n pptx: 'application/vnd.openxmlformats-officedocument.presentationml.presentation',\n md: 'text/markdown',\n html: 'text/html',\n};\n\n/** Trigger a browser download for a Blob. */\nfunction downloadBlob(blob: Blob, filename: string): void {\n const url = URL.createObjectURL(blob);\n const a = document.createElement('a');\n a.href = url;\n a.download = filename;\n a.click();\n URL.revokeObjectURL(url);\n}\n\nasync function saveExportBlob(\n blob: Blob,\n filename: string,\n saveBlob?: ExportBlobSaver,\n): Promise<void> {\n if (saveBlob) {\n await saveBlob(blob, filename);\n return;\n }\n downloadBlob(blob, filename);\n}\n\n/** Derive a filename from the selected file path and export format. */\nfunction buildFilename(selectedFile: string | null, format: ExportFormat): string {\n const base = selectedFile ? selectedFile.replace(/^\\//, '').replace(/\\.[^.]+$/, '') : 'document';\n return base + FORMAT_EXTENSIONS[format];\n}\n\nexport function buildExportFilename(selectedFile: string | null, options: ExportOptions): string {\n const base = selectedFile ? selectedFile.replace(/^\\//, '').replace(/\\.[^.]+$/, '') : 'document';\n if (options.format === 'html') {\n if (options.includeLinkedDocs || options.htmlBundle === 'zip') return `${base}.zip`;\n if (options.entryAsIndex) return 'index.html';\n }\n return base + FORMAT_EXTENSIONS[options.format];\n}\n\n/** Run the export and trigger a download. */\nexport async function runExport(\n markdown: string,\n selectedFile: string | null,\n options: ExportOptions,\n mediaContainer?: ContentContainer | null,\n saveBlob?: ExportBlobSaver,\n): Promise<void> {\n const filename = buildFilename(selectedFile, options.format);\n const themeId = options.themeId !== 'standard' ? options.themeId : undefined;\n\n if (options.format === 'md') {\n await saveExportBlob(new Blob([markdown], { type: MIME_TYPES.md }), filename, saveBlob);\n return;\n }\n\n if (options.format === 'html') {\n await runHtmlExport(markdown, filename, options, mediaContainer, selectedFile, saveBlob);\n return;\n }\n\n const doc = parseMarkdown(markdown);\n\n if (options.format === 'docx') {\n const { markdownDocToDocx } = await import('@bendyline/squisq-formats/docx');\n const images = mediaContainer ? await resolveImages(doc, mediaContainer) : undefined;\n const buf = await markdownDocToDocx(doc, { themeId, images });\n await saveExportBlob(new Blob([buf], { type: MIME_TYPES.docx }), filename, saveBlob);\n return;\n }\n\n if (options.format === 'pdf') {\n const { markdownDocToPdf } = await import('@bendyline/squisq-formats/pdf');\n const buf = await markdownDocToPdf(doc, {\n themeId,\n pageSize: options.pageSize,\n });\n await saveExportBlob(new Blob([buf], { type: MIME_TYPES.pdf }), filename, saveBlob);\n return;\n }\n\n if (options.format === 'pptx') {\n const [{ markdownToDoc }, { applyTransform }, { docToPptx }] = await Promise.all([\n import('@bendyline/squisq/doc'),\n import('@bendyline/squisq/transform'),\n import('@bendyline/squisq-formats/pptx'),\n ]);\n // Use the full transform pipeline: markdown -> Doc -> transform -> PPTX\n const baseDoc = markdownToDoc(doc);\n const transformed = applyTransform(baseDoc, options.transformStyle);\n const enrichedDoc = transformed.doc;\n if (themeId) {\n enrichedDoc.themeId = themeId;\n }\n const buf = await docToPptx(enrichedDoc, { themeId });\n await saveExportBlob(new Blob([buf], { type: MIME_TYPES.pptx }), filename, saveBlob);\n return;\n }\n}\n\n/** Run the HTML export branch — handles all four htmlStyle × htmlBundle combinations. */\nasync function runHtmlExport(\n markdown: string,\n htmlFilename: string,\n options: ExportOptions,\n mediaContainer?: ContentContainer | null,\n selectedFile?: string | null,\n saveBlob?: ExportBlobSaver,\n): Promise<void> {\n const baseName = htmlFilename.replace(/\\.html$/, '');\n const zipName = `${baseName}.zip`;\n // When `entryAsIndex` is on, a single-doc HTML download lands on\n // disk as `index.html` so it drops straight into a static host. The\n // recursive ZIP path doesn't care — squisq's bundle helpers handle\n // the inside-zip rename and the cross-doc link rewrite themselves.\n const singleHtmlFilename = options.entryAsIndex ? 'index.html' : htmlFilename;\n const themeId = options.themeId !== 'standard' ? options.themeId : undefined;\n\n // Recursive HTML bundle: when the user opted in, ask squisq to walk\n // this doc's relative .md links and emit a ZIP with every reachable\n // page rendered + cross-doc hrefs rewritten. Two pipelines:\n // • Plain → `markdownDocsToPlainHtmlBundle` (semantic HTML)\n // • Rendered → `markdownDocsToHtmlBundle` (SquisqPlayer-rendered,\n // shared `squisq-player.js`, Doc-tree link rewrites)\n // Both consume the workspace container to resolve sibling files —\n // `mediaContainer` is already scoped to the selected file's parent\n // dir, which is exactly the bundle's scope root. Falls back to the\n // single-doc path if either prerequisite is missing rather than\n // silently skipping the recursion.\n if (options.includeLinkedDocs && mediaContainer && selectedFile) {\n const entryPath = basenameForBundle(selectedFile);\n if (options.htmlStyle === 'rendered') {\n const [{ markdownDocsToHtmlBundle }, { PLAYER_BUNDLE }] = await Promise.all([\n import('@bendyline/squisq-formats/html'),\n import('@bendyline/squisq-react/standalone-source'),\n ]);\n const blob = await markdownDocsToHtmlBundle({\n entryPath,\n readDocument: (path) => readDocumentFromContainer(mediaContainer, path),\n readBinary: (path) => mediaContainer.readFile(path),\n playerScript: PLAYER_BUNDLE,\n title: baseName,\n themeId,\n mode: 'static',\n entryAsIndex: options.entryAsIndex,\n });\n await saveExportBlob(blob, zipName, saveBlob);\n return;\n }\n const { markdownDocsToPlainHtmlBundle } = await import('@bendyline/squisq-formats/html');\n const blob = await markdownDocsToPlainHtmlBundle({\n entryPath,\n readDocument: (path) => readDocumentFromContainer(mediaContainer, path),\n readBinary: (path) => mediaContainer.readFile(path),\n title: baseName,\n themeId,\n entryAsIndex: options.entryAsIndex,\n });\n await saveExportBlob(blob, zipName, saveBlob);\n return;\n }\n\n if (options.htmlStyle === 'rendered') {\n const [{ markdownToDoc }, { docToHtml, docToHtmlZip, collectImagePaths }, { PLAYER_BUNDLE }] =\n await Promise.all([\n import('@bendyline/squisq/doc'),\n import('@bendyline/squisq-formats/html'),\n import('@bendyline/squisq-react/standalone-source'),\n ]);\n const mdDoc = parseMarkdown(markdown);\n const baseDoc = markdownToDoc(mdDoc);\n if (themeId) baseDoc.themeId = themeId;\n\n const images = mediaContainer\n ? await resolveDocImages(baseDoc, mediaContainer, collectImagePaths)\n : undefined;\n\n if (options.htmlBundle === 'zip') {\n const blob = await docToHtmlZip(baseDoc, {\n playerScript: PLAYER_BUNDLE,\n images,\n mode: 'static',\n title: baseName,\n });\n await saveExportBlob(blob, zipName, saveBlob);\n return;\n }\n\n const html = docToHtml(baseDoc, {\n playerScript: PLAYER_BUNDLE,\n images,\n mode: 'static',\n title: baseName,\n });\n await saveExportBlob(new Blob([html], { type: MIME_TYPES.html }), singleHtmlFilename, saveBlob);\n return;\n }\n\n // Plain semantic HTML\n const mdDoc = parseMarkdown(markdown);\n const referencedImages = collectMarkdownImageUrls(mdDoc);\n const localImages = referencedImages.filter((u) => !isExternalUrl(u));\n\n if (options.htmlBundle === 'zip' && mediaContainer && localImages.length > 0) {\n const [{ markdownDocToPlainHtml }, { MemoryContentContainer }, { containerToZip }] =\n await Promise.all([\n import('@bendyline/squisq-formats/html'),\n import('@bendyline/squisq/storage'),\n import('@bendyline/squisq-formats/container'),\n ]);\n // Mirror the markdown's relative paths inside the zip so <img src=\"...\"> still resolves.\n const html = markdownDocToPlainHtml(mdDoc, { title: baseName, themeId });\n const container = new MemoryContentContainer();\n await container.writeFile('index.html', new TextEncoder().encode(html));\n for (const url of localImages) {\n const data = await mediaContainer.readFile(url);\n if (!data) continue;\n const cleanPath = url.replace(/^\\/+/, '');\n await container.writeFile(cleanPath, new Uint8Array(data));\n }\n const blob = await containerToZip(container);\n await saveExportBlob(blob, zipName, saveBlob);\n return;\n }\n\n const { markdownDocToPlainHtml } = await import('@bendyline/squisq-formats/html');\n // Single-file plain HTML — embed local images as base64 data URIs.\n const inlineMap = new Map<string, string>();\n if (mediaContainer) {\n for (const url of localImages) {\n const data = await mediaContainer.readFile(url);\n if (!data) continue;\n inlineMap.set(url, arrayBufferToDataUrl(data, url));\n }\n }\n const html = markdownDocToPlainHtml(mdDoc, {\n title: baseName,\n images: inlineMap.size > 0 ? inlineMap : undefined,\n themeId,\n });\n await saveExportBlob(new Blob([html], { type: MIME_TYPES.html }), singleHtmlFilename, saveBlob);\n}\n\nconst IMAGE_MIME: Record<string, string> = {\n png: 'image/png',\n jpg: 'image/jpeg',\n jpeg: 'image/jpeg',\n gif: 'image/gif',\n webp: 'image/webp',\n bmp: 'image/bmp',\n svg: 'image/svg+xml',\n};\n\nfunction isExternalUrl(url: string): boolean {\n return (\n url.startsWith('http://') ||\n url.startsWith('https://') ||\n url.startsWith('data:') ||\n url.startsWith('blob:')\n );\n}\n\nfunction arrayBufferToDataUrl(data: ArrayBuffer, url: string): string {\n const ext = url.slice(url.lastIndexOf('.') + 1).toLowerCase();\n const mime = IMAGE_MIME[ext] ?? 'application/octet-stream';\n // btoa requires a binary string; chunk to avoid call-stack issues on large files.\n const bytes = new Uint8Array(data);\n let binary = '';\n const CHUNK = 0x8000;\n for (let i = 0; i < bytes.length; i += CHUNK) {\n binary += String.fromCharCode(...bytes.subarray(i, i + CHUNK));\n }\n return `data:${mime};base64,${btoa(binary)}`;\n}\n\n/** Walk the markdown AST and collect all image URLs. */\nfunction collectMarkdownImageUrls(doc: MarkdownDocument): string[] {\n const urls: string[] = [];\n function walkBlocks(nodes: MarkdownBlockNode[]): void {\n for (const node of nodes) {\n if ('children' in node && Array.isArray(node.children)) {\n for (const child of node.children as (MarkdownBlockNode | MarkdownInlineNode)[]) {\n if (child.type === 'image') {\n urls.push((child as { url: string }).url);\n } else if ('children' in child && Array.isArray(child.children)) {\n walkBlocks(child.children as MarkdownBlockNode[]);\n }\n }\n }\n }\n }\n walkBlocks(doc.children);\n return Array.from(new Set(urls));\n}\n\n/** Resolve image URLs (markdown → docx) to binary data from a ContentContainer. */\nasync function resolveImages(\n doc: MarkdownDocument,\n container: ContentContainer,\n): Promise<Map<string, { data: ArrayBuffer | Uint8Array; contentType: string }>> {\n const urls = collectMarkdownImageUrls(doc);\n const map = new Map<string, { data: ArrayBuffer | Uint8Array; contentType: string }>();\n\n for (const url of urls) {\n if (map.has(url)) continue;\n if (isExternalUrl(url)) continue;\n const data = await container.readFile(url);\n if (!data) continue;\n const ext = url.slice(url.lastIndexOf('.') + 1).toLowerCase();\n const contentType = IMAGE_MIME[ext] || 'image/png';\n map.set(url, { data, contentType });\n }\n\n return map;\n}\n\n/** Container-relative path for the bundle's entry document. `mediaContainer`\n * is already scoped to the selected file's parent directory, so the bundle\n * needs the basename (\"docs/home.md\" → \"home.md\"). */\nfunction basenameForBundle(selectedFile: string): string {\n const clean = selectedFile.replace(/^\\/+/, '');\n const idx = clean.lastIndexOf('/');\n return idx === -1 ? clean : clean.slice(idx + 1);\n}\n\n/** Read a UTF-8 text document from a ContentContainer. Returns null when\n * the file is missing — preserves the bundle's \"abort with error\" contract\n * for unreachable .md links. */\nasync function readDocumentFromContainer(\n container: ContentContainer,\n path: string,\n): Promise<string | null> {\n const data = await container.readFile(path);\n if (!data) return null;\n return new TextDecoder('utf-8').decode(data);\n}\n\n/** Resolve image paths referenced by a squisq Doc to ArrayBuffers for HTML export. */\nasync function resolveDocImages(\n doc: Doc,\n container: ContentContainer,\n collectImagePaths: (doc: Doc) => Iterable<string>,\n): Promise<Map<string, ArrayBuffer>> {\n const paths = collectImagePaths(doc);\n const map = new Map<string, ArrayBuffer>();\n for (const path of paths) {\n const data = await container.readFile(path);\n if (!data) continue;\n map.set(path, data);\n }\n return map;\n}\n"],"mappings":"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","names":["blob","mdDoc","html","markdownDocToPlainHtml"]}
@@ -0,0 +1,22 @@
1
+ /**
2
+ * Dialog — shared modal primitive.
3
+ *
4
+ * Promotes the `db-dialog-overlay` / `db-dialog` pattern used by the
5
+ * settings dialogs into a reusable component, adding aria-modal and
6
+ * initial focus. Escape and (by default) backdrop clicks close it.
7
+ */
8
+ export interface DialogProps {
9
+ title: string;
10
+ onClose: () => void;
11
+ /** default 380px / wide 560px / full min(1100px, 94vw) column. */
12
+ size?: 'default' | 'wide' | 'full';
13
+ children: React.ReactNode;
14
+ /** Right-aligned action row below the body. */
15
+ footer?: React.ReactNode;
16
+ /** Element to focus on open; defaults to the close button. */
17
+ initialFocusRef?: React.RefObject<HTMLElement | null>;
18
+ /** Set false when a stray backdrop click would lose user input. */
19
+ closeOnBackdrop?: boolean;
20
+ }
21
+ export declare function Dialog({ title, onClose, size, children, footer, initialFocusRef, closeOnBackdrop, }: DialogProps): import("react/jsx-runtime").JSX.Element;
22
+ //# sourceMappingURL=Dialog.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Dialog.d.ts","sourceRoot":"","sources":["../../src/components/Dialog.tsx"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAIH,MAAM,WAAW,WAAW;IAC1B,KAAK,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,MAAM,IAAI,CAAC;IACpB,kEAAkE;IAClE,IAAI,CAAC,EAAE,SAAS,GAAG,MAAM,GAAG,MAAM,CAAC;IACnC,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B,+CAA+C;IAC/C,MAAM,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IACzB,8DAA8D;IAC9D,eAAe,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IACtD,mEAAmE;IACnE,eAAe,CAAC,EAAE,OAAO,CAAC;CAC3B;AAED,wBAAgB,MAAM,CAAC,EACrB,KAAK,EACL,OAAO,EACP,IAAgB,EAChB,QAAQ,EACR,MAAM,EACN,eAAe,EACf,eAAsB,GACvB,EAAE,WAAW,2CAgDb"}
@@ -0,0 +1,33 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ /**
3
+ * Dialog — shared modal primitive.
4
+ *
5
+ * Promotes the `db-dialog-overlay` / `db-dialog` pattern used by the
6
+ * settings dialogs into a reusable component, adding aria-modal and
7
+ * initial focus. Escape and (by default) backdrop clicks close it.
8
+ */
9
+ import { useCallback, useEffect, useRef } from 'react';
10
+ export function Dialog({ title, onClose, size = 'default', children, footer, initialFocusRef, closeOnBackdrop = true, }) {
11
+ const closeButtonRef = useRef(null);
12
+ useEffect(() => {
13
+ const onKey = (e) => {
14
+ if (e.key === 'Escape')
15
+ onClose();
16
+ };
17
+ window.addEventListener('keydown', onKey);
18
+ return () => window.removeEventListener('keydown', onKey);
19
+ }, [onClose]);
20
+ useEffect(() => {
21
+ const target = initialFocusRef?.current ?? closeButtonRef.current;
22
+ target?.focus();
23
+ // Focus only on mount — refocusing on every re-render would fight the user.
24
+ // eslint-disable-next-line react-hooks/exhaustive-deps
25
+ }, []);
26
+ const handleBackdropClick = useCallback((e) => {
27
+ if (closeOnBackdrop && e.target === e.currentTarget)
28
+ onClose();
29
+ }, [closeOnBackdrop, onClose]);
30
+ const sizeClass = size === 'wide' ? ' db-dialog--wide' : size === 'full' ? ' db-dialog--full' : '';
31
+ return (_jsx("div", { className: "db-dialog-overlay", onClick: handleBackdropClick, children: _jsxs("div", { className: `db-dialog${sizeClass}`, role: "dialog", "aria-modal": "true", "aria-label": title, children: [_jsxs("div", { className: "db-dialog-header", children: [_jsx("h2", { className: "db-dialog-title", children: title }), _jsx("button", { ref: closeButtonRef, type: "button", className: "db-dialog-close", onClick: onClose, "aria-label": "Close", children: "\u00D7" })] }), _jsx("div", { className: "db-dialog-body", children: children }), footer && _jsx("div", { className: "db-dialog-footer", children: footer })] }) }));
32
+ }
33
+ //# sourceMappingURL=Dialog.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Dialog.js","sourceRoot":"","sources":["../../src/components/Dialog.tsx"],"names":[],"mappings":";AAAA;;;;;;GAMG;AAEH,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,MAAM,EAAE,MAAM,OAAO,CAAC;AAgBvD,MAAM,UAAU,MAAM,CAAC,EACrB,KAAK,EACL,OAAO,EACP,IAAI,GAAG,SAAS,EAChB,QAAQ,EACR,MAAM,EACN,eAAe,EACf,eAAe,GAAG,IAAI,GACV;IACZ,MAAM,cAAc,GAAG,MAAM,CAAoB,IAAI,CAAC,CAAC;IAEvD,SAAS,CAAC,GAAG,EAAE;QACb,MAAM,KAAK,GAAG,CAAC,CAAgB,EAAE,EAAE;YACjC,IAAI,CAAC,CAAC,GAAG,KAAK,QAAQ;gBAAE,OAAO,EAAE,CAAC;QACpC,CAAC,CAAC;QACF,MAAM,CAAC,gBAAgB,CAAC,SAAS,EAAE,KAAK,CAAC,CAAC;QAC1C,OAAO,GAAG,EAAE,CAAC,MAAM,CAAC,mBAAmB,CAAC,SAAS,EAAE,KAAK,CAAC,CAAC;IAC5D,CAAC,EAAE,CAAC,OAAO,CAAC,CAAC,CAAC;IAEd,SAAS,CAAC,GAAG,EAAE;QACb,MAAM,MAAM,GAAG,eAAe,EAAE,OAAO,IAAI,cAAc,CAAC,OAAO,CAAC;QAClE,MAAM,EAAE,KAAK,EAAE,CAAC;QAChB,4EAA4E;QAC5E,uDAAuD;IACzD,CAAC,EAAE,EAAE,CAAC,CAAC;IAEP,MAAM,mBAAmB,GAAG,WAAW,CACrC,CAAC,CAAmB,EAAE,EAAE;QACtB,IAAI,eAAe,IAAI,CAAC,CAAC,MAAM,KAAK,CAAC,CAAC,aAAa;YAAE,OAAO,EAAE,CAAC;IACjE,CAAC,EACD,CAAC,eAAe,EAAE,OAAO,CAAC,CAC3B,CAAC;IAEF,MAAM,SAAS,GACb,IAAI,KAAK,MAAM,CAAC,CAAC,CAAC,kBAAkB,CAAC,CAAC,CAAC,IAAI,KAAK,MAAM,CAAC,CAAC,CAAC,kBAAkB,CAAC,CAAC,CAAC,EAAE,CAAC;IAEnF,OAAO,CACL,cAAK,SAAS,EAAC,mBAAmB,EAAC,OAAO,EAAE,mBAAmB,YAC7D,eAAK,SAAS,EAAE,YAAY,SAAS,EAAE,EAAE,IAAI,EAAC,QAAQ,gBAAY,MAAM,gBAAa,KAAK,aACxF,eAAK,SAAS,EAAC,kBAAkB,aAC/B,aAAI,SAAS,EAAC,iBAAiB,YAAE,KAAK,GAAM,EAC5C,iBACE,GAAG,EAAE,cAAc,EACnB,IAAI,EAAC,QAAQ,EACb,SAAS,EAAC,iBAAiB,EAC3B,OAAO,EAAE,OAAO,gBACL,OAAO,uBAGX,IACL,EACN,cAAK,SAAS,EAAC,gBAAgB,YAAE,QAAQ,GAAO,EAC/C,MAAM,IAAI,cAAK,SAAS,EAAC,kBAAkB,YAAE,MAAM,GAAO,IACvD,GACF,CACP,CAAC;AACJ,CAAC"}
@@ -0,0 +1,10 @@
1
+ /**
2
+ * Placeholder prompts shown by DocBlocks when a Markdown document is empty.
3
+ * Hosts pick one prompt for each mounted document generation and pass it to
4
+ * Squisq, so the copy remains stable while that document is open.
5
+ */
6
+ export declare const EMPTY_DOCUMENT_PROMPTS: readonly ["Start typing your content, or drop images on top of me...", "Write anything -- paste markdown, drag in images, or just start typing...", "Type away. Markdown syntax works too...", "Chapter 1 begins here...", "Once upon a time...", "A blank page. Exciting, isn't it?", "The first word is always the hardest...", "Plot twist: this is where it all starts...", "Write something the future you will thank you for...", "Begin at the beginning...", "Let's begin.", "We can be heroes...", "Here comes the sun...", "And so it begins...", "Let it be, let it be...", "Don't stop believing...", "Started from the bottom...", "This is the start of something new...", "Ground control to Major Tom...", "Come as you are...", "Every new beginning...", "Hello, is it me you're looking for?", "Imagine all the people...", "Anything you want, you got it...", "Rise above...", "Do you have the time...", "Here we are now, entertain us...", "All the small things...", "Should I stay or should I go?", "I am a patient boy -- I wait, I wait, I wait...", "Destination unknown...", "Easy like Sunday morning...", "Dance, dance, dance to the radio...", "New day rising...", "Visit the world...", "Positive mental attitude...", "Better I sing than I cry...", "Disconnect for a minute...", "We need new noise...", "Shoot the moon...", "I'll surprise you sometime -- I'll come around...", "Coming out of my cage, and doing just fine...", "Throw me to the wolves -- I'll come back, leading the pack...", "There comes a time -- no excuses...", "It's up to me now, turn on the bright lights...", "Do what you want...", "Fingers crossed...", "This is the start of how it all ends...", "It has to start somewhere, it has to start sometime -- what better place than here? what better time than now?", "I know myself, and I'll begin again...", "Dig me out, dig me in...", "Everybody's full of sugar, honey, ice and tea...", "Take time with a wounded hand, 'cause it likes to heal...", "Grab a brush and put on a little makeup...", "Amber is the color of your energy...", "Wait -- they don't love it like I love it...", "A world's been buried, where love is the law; a you-topia..."];
7
+ export type EmptyDocumentPrompt = (typeof EMPTY_DOCUMENT_PROMPTS)[number];
8
+ /** Pick a prompt using the supplied random source, or `Math.random`. */
9
+ export declare function pickEmptyDocumentPrompt(random?: () => number): EmptyDocumentPrompt;
10
+ //# sourceMappingURL=editor.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"editor.d.ts","sourceRoot":"","sources":["../src/editor.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AACH,eAAO,MAAM,sBAAsB,+mEA0DzB,CAAC;AAEX,MAAM,MAAM,mBAAmB,GAAG,CAAC,OAAO,sBAAsB,CAAC,CAAC,MAAM,CAAC,CAAC;AAE1E,wEAAwE;AACxE,wBAAgB,uBAAuB,CAAC,MAAM,GAAE,MAAM,MAAoB,GAAG,mBAAmB,CAG/F"}
package/dist/editor.js ADDED
@@ -0,0 +1,70 @@
1
+ /**
2
+ * Placeholder prompts shown by DocBlocks when a Markdown document is empty.
3
+ * Hosts pick one prompt for each mounted document generation and pass it to
4
+ * Squisq, so the copy remains stable while that document is open.
5
+ */
6
+ export const EMPTY_DOCUMENT_PROMPTS = [
7
+ 'Start typing your content, or drop images on top of me...',
8
+ 'Write anything -- paste markdown, drag in images, or just start typing...',
9
+ 'Type away. Markdown syntax works too...',
10
+ 'Chapter 1 begins here...',
11
+ 'Once upon a time...',
12
+ "A blank page. Exciting, isn't it?",
13
+ 'The first word is always the hardest...',
14
+ 'Plot twist: this is where it all starts...',
15
+ 'Write something the future you will thank you for...',
16
+ 'Begin at the beginning...',
17
+ "Let's begin.",
18
+ 'We can be heroes...',
19
+ 'Here comes the sun...',
20
+ 'And so it begins...',
21
+ 'Let it be, let it be...',
22
+ "Don't stop believing...",
23
+ 'Started from the bottom...',
24
+ 'This is the start of something new...',
25
+ 'Ground control to Major Tom...',
26
+ 'Come as you are...',
27
+ 'Every new beginning...',
28
+ "Hello, is it me you're looking for?",
29
+ 'Imagine all the people...',
30
+ 'Anything you want, you got it...',
31
+ 'Rise above...',
32
+ 'Do you have the time...',
33
+ 'Here we are now, entertain us...',
34
+ 'All the small things...',
35
+ 'Should I stay or should I go?',
36
+ 'I am a patient boy -- I wait, I wait, I wait...',
37
+ 'Destination unknown...',
38
+ 'Easy like Sunday morning...',
39
+ 'Dance, dance, dance to the radio...',
40
+ 'New day rising...',
41
+ 'Visit the world...',
42
+ 'Positive mental attitude...',
43
+ 'Better I sing than I cry...',
44
+ 'Disconnect for a minute...',
45
+ 'We need new noise...',
46
+ 'Shoot the moon...',
47
+ "I'll surprise you sometime -- I'll come around...",
48
+ 'Coming out of my cage, and doing just fine...',
49
+ "Throw me to the wolves -- I'll come back, leading the pack...",
50
+ 'There comes a time -- no excuses...',
51
+ "It's up to me now, turn on the bright lights...",
52
+ 'Do what you want...',
53
+ 'Fingers crossed...',
54
+ 'This is the start of how it all ends...',
55
+ 'It has to start somewhere, it has to start sometime -- what better place than here? what better time than now?',
56
+ "I know myself, and I'll begin again...",
57
+ 'Dig me out, dig me in...',
58
+ "Everybody's full of sugar, honey, ice and tea...",
59
+ "Take time with a wounded hand, 'cause it likes to heal...",
60
+ 'Grab a brush and put on a little makeup...',
61
+ 'Amber is the color of your energy...',
62
+ "Wait -- they don't love it like I love it...",
63
+ "A world's been buried, where love is the law; a you-topia...",
64
+ ];
65
+ /** Pick a prompt using the supplied random source, or `Math.random`. */
66
+ export function pickEmptyDocumentPrompt(random = Math.random) {
67
+ const index = Math.floor(random() * EMPTY_DOCUMENT_PROMPTS.length);
68
+ return EMPTY_DOCUMENT_PROMPTS[index] ?? EMPTY_DOCUMENT_PROMPTS[0];
69
+ }
70
+ //# sourceMappingURL=editor.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"editor.js","sourceRoot":"","sources":["../src/editor.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AACH,MAAM,CAAC,MAAM,sBAAsB,GAAG;IACpC,2DAA2D;IAC3D,2EAA2E;IAC3E,yCAAyC;IACzC,0BAA0B;IAC1B,qBAAqB;IACrB,mCAAmC;IACnC,yCAAyC;IACzC,4CAA4C;IAC5C,sDAAsD;IACtD,2BAA2B;IAC3B,cAAc;IACd,qBAAqB;IACrB,uBAAuB;IACvB,qBAAqB;IACrB,yBAAyB;IACzB,yBAAyB;IACzB,4BAA4B;IAC5B,uCAAuC;IACvC,gCAAgC;IAChC,oBAAoB;IACpB,wBAAwB;IACxB,qCAAqC;IACrC,2BAA2B;IAC3B,kCAAkC;IAClC,eAAe;IACf,yBAAyB;IACzB,kCAAkC;IAClC,yBAAyB;IACzB,+BAA+B;IAC/B,iDAAiD;IACjD,wBAAwB;IACxB,6BAA6B;IAC7B,qCAAqC;IACrC,mBAAmB;IACnB,oBAAoB;IACpB,6BAA6B;IAC7B,6BAA6B;IAC7B,4BAA4B;IAC5B,sBAAsB;IACtB,mBAAmB;IACnB,mDAAmD;IACnD,+CAA+C;IAC/C,+DAA+D;IAC/D,qCAAqC;IACrC,iDAAiD;IACjD,qBAAqB;IACrB,oBAAoB;IACpB,yCAAyC;IACzC,gHAAgH;IAChH,wCAAwC;IACxC,0BAA0B;IAC1B,kDAAkD;IAClD,2DAA2D;IAC3D,4CAA4C;IAC5C,sCAAsC;IACtC,8CAA8C;IAC9C,8DAA8D;CACtD,CAAC;AAIX,wEAAwE;AACxE,MAAM,UAAU,uBAAuB,CAAC,SAAuB,IAAI,CAAC,MAAM;IACxE,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM,EAAE,GAAG,sBAAsB,CAAC,MAAM,CAAC,CAAC;IACnE,OAAO,sBAAsB,CAAC,KAAK,CAAC,IAAI,sBAAsB,CAAC,CAAC,CAAC,CAAC;AACpE,CAAC"}
@@ -0,0 +1,87 @@
1
+ import * as react_jsx_runtime from 'react/jsx-runtime';
2
+ import { ContentContainer } from '@bendyline/squisq/storage';
3
+
4
+ /**
5
+ * Export option types and localStorage persistence for quick-export.
6
+ */
7
+ type ExportFormat = 'docx' | 'pdf' | 'pptx' | 'md' | 'html';
8
+ /** Visual style for HTML export. */
9
+ type HtmlStyle =
10
+ /** Render via SquisqPlayer (themed, embeds player bundle). */
11
+ 'rendered'
12
+ /** Plain semantic HTML — small, no JS, no playback. */
13
+ | 'plain';
14
+ /** Packaging for HTML export. */
15
+ type HtmlBundle =
16
+ /** Single self-contained .html file (images base64-embedded). */
17
+ 'single'
18
+ /** ZIP containing index.html + asset files. */
19
+ | 'zip';
20
+ interface ExportOptions {
21
+ format: ExportFormat;
22
+ themeId: string;
23
+ /** Transform style for PPTX — controls how content is segmented and styled. */
24
+ transformStyle: string;
25
+ /** Only applies to PDF */
26
+ pageSize: 'letter' | 'a4';
27
+ /** HTML rendering style. Only applies to format=html. */
28
+ htmlStyle: HtmlStyle;
29
+ /** HTML bundle layout. Only applies to format=html. */
30
+ htmlBundle: HtmlBundle;
31
+ /**
32
+ * Recursive HTML bundle: walk relative `.md` links from the entry
33
+ * document, render every reachable sibling/child page, and rewrite
34
+ * cross-doc links from `.md` → `.html`. The output is a ZIP
35
+ * regardless of `htmlBundle` because multi-doc output needs a
36
+ * directory tree. Supported for both plain (`markdownDocsToPlainHtmlBundle`)
37
+ * and rendered (`markdownDocsToHtmlBundle`) HTML styles. Only
38
+ * meaningful when `format === 'html'`.
39
+ */
40
+ includeLinkedDocs: boolean;
41
+ /**
42
+ * Rename the entry page from `<basename>.html` to `index.html` so the
43
+ * export drops straight into a static-site host that expects an
44
+ * `index.html` landing page. For recursive bundles, cross-doc links
45
+ * targeting the entry also rewrite to `index.html` so siblings don't
46
+ * 404. For a single-doc HTML download, this just renames the file.
47
+ * Only meaningful when `format === 'html'`.
48
+ */
49
+ entryAsIndex: boolean;
50
+ }
51
+ declare const FORMAT_LABELS: Record<ExportFormat, string>;
52
+ declare const FORMAT_EXTENSIONS: Record<ExportFormat, string>;
53
+ declare const DEFAULT_OPTIONS: ExportOptions;
54
+ declare function loadLastExportOptions(): ExportOptions | null;
55
+ declare function saveExportOptions(options: ExportOptions): void;
56
+
57
+ /**
58
+ * Execute an export using @bendyline/squisq-formats.
59
+ */
60
+
61
+ type ExportBlobSaver = (blob: Blob, filename: string) => Promise<void> | void;
62
+ declare function buildExportFilename(selectedFile: string | null, options: ExportOptions): string;
63
+ /** Run the export and trigger a download. */
64
+ declare function runExport(markdown: string, selectedFile: string | null, options: ExportOptions, mediaContainer?: ContentContainer | null, saveBlob?: ExportBlobSaver): Promise<void>;
65
+
66
+ interface ExportDialogProps {
67
+ /** Initial options (pre-populated from last export). */
68
+ initial: ExportOptions;
69
+ /** Whether the export is currently running. */
70
+ exporting: boolean;
71
+ /** Optional host-provided destination path control. */
72
+ destination?: ExportDestinationControl;
73
+ /** Called when the user confirms the export. */
74
+ onExport: (options: ExportOptions) => void;
75
+ /** Called whenever the currently selected options change. */
76
+ onOptionsChange?: (options: ExportOptions) => void;
77
+ /** Called when the dialog is dismissed. */
78
+ onClose: () => void;
79
+ }
80
+ interface ExportDestinationControl {
81
+ value: string;
82
+ onPick: (options: ExportOptions) => void | Promise<void>;
83
+ hint?: string;
84
+ }
85
+ declare function ExportDialog({ initial, exporting, destination, onExport, onOptionsChange, onClose, }: ExportDialogProps): react_jsx_runtime.JSX.Element;
86
+
87
+ export { DEFAULT_OPTIONS, type ExportBlobSaver, type ExportDestinationControl, ExportDialog, type ExportDialogProps, type ExportFormat, type ExportOptions, FORMAT_EXTENSIONS, FORMAT_LABELS, type HtmlBundle, type HtmlStyle, buildExportFilename, loadLastExportOptions, runExport, saveExportOptions };