@heroiclands/package-build 23.13.0 → 24.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 (233) hide show
  1. package/CHANGELOG.md +36 -0
  2. package/README.md +2 -1
  3. package/assets/preview/gitea.ini +12 -7
  4. package/assets/styles/content-base.css +150 -1
  5. package/bin/content-commands.mjs +356 -210
  6. package/bin/package-build.mjs +3 -2
  7. package/ci/check-banners.mjs +7 -7
  8. package/config.mjs +21 -6
  9. package/content-config.mjs +199 -80
  10. package/docs/api.md +93 -72
  11. package/docs/authoring/links-and-markup.md +316 -78
  12. package/docs/commands.md +244 -78
  13. package/docs/configuration.md +210 -102
  14. package/docs/content-format.md +2 -2
  15. package/docs/diagnostics.md +2 -2
  16. package/docs/getting-started.md +1 -1
  17. package/docs/guides/icons.md +1 -1
  18. package/docs/guides/module-project.md +5 -8
  19. package/docs/guides/release-and-deploy.md +2 -2
  20. package/docs/guides/site.md +112 -23
  21. package/docs/guides/system-project.md +1 -1
  22. package/docs/guides/writing-in-invented-scripts.md +1247 -0
  23. package/docs/index.md +1 -0
  24. package/docs/project-setup.md +28 -30
  25. package/docs/reference/format-details.md +589 -308
  26. package/docs/reference/note-types.md +40 -10
  27. package/docs/reference/theme-pages.md +127 -108
  28. package/docs/source-preview.md +15 -1
  29. package/engine/asset-shipping.mjs +22 -10
  30. package/engine/base-compiler.mjs +62 -104
  31. package/engine/changelog-lint.mjs +1 -1
  32. package/engine/content-address.mjs +1 -1
  33. package/engine/content-alerts.mjs +8 -4
  34. package/engine/content-blocks.mjs +26 -11
  35. package/engine/content-embeds.mjs +1 -1
  36. package/engine/content-expand.mjs +376 -0
  37. package/engine/content-figures.mjs +13 -6
  38. package/engine/content-format.yaml +8 -0
  39. package/engine/content-glyphs.mjs +213 -0
  40. package/engine/content-images.mjs +6 -7
  41. package/engine/content-links.mjs +3 -3
  42. package/engine/content-lint.mjs +1 -1
  43. package/engine/content-render.mjs +453 -0
  44. package/engine/content-scripts.mjs +326 -27
  45. package/engine/content-spans.mjs +4 -1
  46. package/engine/content-styles.mjs +91 -0
  47. package/engine/content-symbols.mjs +186 -0
  48. package/engine/content-verse.mjs +6 -18
  49. package/engine/core-report.mjs +169 -0
  50. package/engine/core-vocabulary.mjs +208 -0
  51. package/engine/dictionary-html.mjs +119 -0
  52. package/engine/field-reference.mjs +1 -1
  53. package/engine/frontmatter-lint.mjs +1 -1
  54. package/engine/heading-attributes.mjs +89 -0
  55. package/engine/helpers.mjs +61 -101
  56. package/engine/homepage.mjs +17 -29
  57. package/engine/html-minify.mjs +70 -0
  58. package/engine/index.mjs +8 -5
  59. package/engine/language-rows.mjs +8 -2
  60. package/engine/language-terms.mjs +115 -14
  61. package/engine/language-words.mjs +12 -0
  62. package/engine/logographic.mjs +255 -0
  63. package/engine/map-lexicon.mjs +221 -25
  64. package/engine/map-places.mjs +5 -4
  65. package/engine/markdown-expressions.mjs +0 -2
  66. package/engine/markdownlint-run.mjs +9 -3
  67. package/engine/markup-validation.mjs +21 -0
  68. package/engine/metre-declaration.mjs +134 -0
  69. package/engine/note-matter.mjs +2 -2
  70. package/engine/note-vocabulary.mjs +187 -3
  71. package/engine/pdf-build.mjs +68 -133
  72. package/engine/pdf-render.mjs +102 -44
  73. package/engine/post-fields.mjs +157 -0
  74. package/engine/preview-index.mjs +130 -0
  75. package/engine/preview-source.mjs +450 -0
  76. package/engine/project-init.mjs +5 -12
  77. package/engine/prose-config.mjs +3 -3
  78. package/engine/run-words.mjs +3 -2
  79. package/engine/script-emphasis-terms.mjs +38 -0
  80. package/engine/script-emphasis.mjs +295 -0
  81. package/engine/script-font-delivery.mjs +4 -4
  82. package/engine/site-build.mjs +259 -314
  83. package/engine/site-config.mjs +26 -238
  84. package/engine/site-files.mjs +175 -0
  85. package/engine/site-index.mjs +9 -4
  86. package/engine/site-preview.mjs +50 -523
  87. package/engine/site-render.mjs +593 -0
  88. package/engine/site-root.mjs +22 -13
  89. package/engine/site-search.mjs +161 -0
  90. package/engine/site-serve.mjs +273 -0
  91. package/engine/site-theme-banner.mjs +154 -0
  92. package/engine/site-theme-urls.mjs +125 -0
  93. package/engine/site-theme.mjs +926 -0
  94. package/engine/text-maps.mjs +57 -10
  95. package/engine/typographer.mjs +248 -0
  96. package/engine/verse-metre.mjs +357 -0
  97. package/engine/wikilink-syntax.mjs +29 -47
  98. package/engine/wikilinks.mjs +758 -279
  99. package/engine/word-forms.mjs +39 -24
  100. package/engine/word-rows.mjs +12 -2
  101. package/engine/word-terms.mjs +29 -4
  102. package/manifest.mjs +3 -4
  103. package/package.json +10 -7
  104. package/{hugo-theme → site-theme}/data/banners.yaml +6 -10
  105. package/site-theme/layouts/base.hbs +31 -0
  106. package/site-theme/layouts/blog-list.hbs +30 -0
  107. package/site-theme/layouts/blog-post.hbs +40 -0
  108. package/site-theme/layouts/home.hbs +35 -0
  109. package/site-theme/layouts/list.hbs +20 -0
  110. package/site-theme/layouts/not-found.hbs +31 -0
  111. package/site-theme/layouts/page.hbs +7 -0
  112. package/site-theme/partials/copy-buttons.hbs +37 -0
  113. package/site-theme/partials/draft-notice.hbs +5 -0
  114. package/site-theme/partials/exturl.hbs +2 -0
  115. package/{hugo-theme/layouts/partials/footer.html → site-theme/partials/footer.hbs} +10 -7
  116. package/site-theme/partials/header.hbs +44 -0
  117. package/site-theme/partials/hero-banner.hbs +11 -0
  118. package/site-theme/partials/infobox-entry.hbs +2 -0
  119. package/site-theme/partials/infobox-section.hbs +31 -0
  120. package/site-theme/partials/infobox-value.hbs +2 -0
  121. package/site-theme/partials/infobox.hbs +18 -0
  122. package/site-theme/partials/list-members.hbs +9 -0
  123. package/site-theme/partials/nav-links.hbs +5 -0
  124. package/site-theme/partials/page-body.hbs +48 -0
  125. package/site-theme/partials/page-list.hbs +14 -0
  126. package/site-theme/partials/related.hbs +24 -0
  127. package/site-theme/partials/search-meta.hbs +6 -0
  128. package/site-theme/partials/search-names.hbs +2 -0
  129. package/site-theme/partials/search.hbs +52 -0
  130. package/site-theme/partials/tags.hbs +4 -0
  131. package/site-theme/partials/toc.hbs +7 -0
  132. package/{hugo-theme → site-theme}/static/css/style.css +14 -0
  133. package/stage.mjs +1 -2
  134. package/types/config.d.mts +8 -4
  135. package/types/content-config.d.mts +15 -15
  136. package/types/engine/asset-shipping.d.mts +5 -2
  137. package/types/engine/base-compiler.d.mts +20 -2
  138. package/types/engine/content-address.d.mts +1 -1
  139. package/types/engine/content-alerts.d.mts +8 -2
  140. package/types/engine/content-blocks.d.mts +11 -4
  141. package/types/engine/content-expand.d.mts +288 -0
  142. package/types/engine/content-figures.d.mts +11 -3
  143. package/types/engine/content-glyphs.d.mts +85 -0
  144. package/types/engine/content-images.d.mts +6 -7
  145. package/types/engine/content-links.d.mts +1 -1
  146. package/types/engine/content-render.d.mts +199 -0
  147. package/types/engine/content-scripts.d.mts +62 -0
  148. package/types/engine/content-spans.d.mts +1 -1
  149. package/types/engine/content-styles.d.mts +33 -0
  150. package/types/engine/content-symbols.d.mts +35 -0
  151. package/types/engine/core-report.d.mts +45 -0
  152. package/types/engine/core-vocabulary.d.mts +53 -0
  153. package/types/engine/dictionary-html.d.mts +8 -0
  154. package/types/engine/field-reference.d.mts +1 -1
  155. package/types/engine/heading-attributes.d.mts +20 -0
  156. package/types/engine/helpers.d.mts +3 -10
  157. package/types/engine/homepage.d.mts +11 -24
  158. package/types/engine/html-minify.d.mts +9 -0
  159. package/types/engine/index.d.mts +2 -1
  160. package/types/engine/language-terms.d.mts +24 -2
  161. package/types/engine/logographic.d.mts +45 -0
  162. package/types/engine/map-lexicon.d.mts +48 -8
  163. package/types/engine/map-places.d.mts +8 -0
  164. package/types/engine/markdown-expressions.d.mts +0 -2
  165. package/types/engine/metre-declaration.d.mts +39 -0
  166. package/types/engine/pdf-render.d.mts +6 -2
  167. package/types/engine/post-fields.d.mts +44 -0
  168. package/types/engine/preview-index.d.mts +72 -0
  169. package/types/engine/preview-source.d.mts +51 -0
  170. package/types/engine/script-emphasis-terms.d.mts +21 -0
  171. package/types/engine/script-emphasis.d.mts +84 -0
  172. package/types/engine/script-font-delivery.d.mts +4 -4
  173. package/types/engine/site-build.d.mts +71 -113
  174. package/types/engine/site-config.d.mts +14 -134
  175. package/types/engine/site-files.d.mts +73 -0
  176. package/types/engine/site-index.d.mts +11 -3
  177. package/types/engine/site-preview.d.mts +15 -19
  178. package/types/engine/site-render.d.mts +171 -0
  179. package/types/engine/site-root.d.mts +12 -4
  180. package/types/engine/site-search.d.mts +54 -0
  181. package/types/engine/site-serve.d.mts +44 -0
  182. package/types/engine/site-theme-banner.d.mts +51 -0
  183. package/types/engine/site-theme-urls.d.mts +60 -0
  184. package/types/engine/site-theme.d.mts +127 -0
  185. package/types/engine/text-maps.d.mts +17 -3
  186. package/types/engine/typographer.d.mts +11 -0
  187. package/types/engine/verse-metre.d.mts +131 -0
  188. package/types/engine/wikilink-syntax.d.mts +30 -48
  189. package/types/engine/wikilinks.d.mts +330 -14
  190. package/types/engine/word-forms.d.mts +3 -2
  191. package/types/manifest.d.mts +3 -4
  192. package/types/stage.d.mts +1 -2
  193. package/types/vendor/markdownlint.d.mts +8 -0
  194. package/vendor/markdownlint.mjs +20388 -0
  195. package/engine/web-wikilinks.mjs +0 -594
  196. package/hugo-theme/layouts/404.html +0 -85
  197. package/hugo-theme/layouts/_default/baseof.html +0 -67
  198. package/hugo-theme/layouts/_default/list.html +0 -139
  199. package/hugo-theme/layouts/_default/single.html +0 -4
  200. package/hugo-theme/layouts/blog/list.html +0 -54
  201. package/hugo-theme/layouts/blog-post/single.html +0 -36
  202. package/hugo-theme/layouts/index.html +0 -75
  203. package/hugo-theme/layouts/partials/banner-url.html +0 -141
  204. package/hugo-theme/layouts/partials/cdn-url.html +0 -36
  205. package/hugo-theme/layouts/partials/dictionary-lists.html +0 -58
  206. package/hugo-theme/layouts/partials/draft-notice.html +0 -41
  207. package/hugo-theme/layouts/partials/draft-state.html +0 -26
  208. package/hugo-theme/layouts/partials/header.html +0 -35
  209. package/hugo-theme/layouts/partials/hero-banner.html +0 -85
  210. package/hugo-theme/layouts/partials/infobox/entry.html +0 -18
  211. package/hugo-theme/layouts/partials/infobox/items.html +0 -26
  212. package/hugo-theme/layouts/partials/infobox/section.html +0 -56
  213. package/hugo-theme/layouts/partials/infobox/value.html +0 -43
  214. package/hugo-theme/layouts/partials/infobox.html +0 -57
  215. package/hugo-theme/layouts/partials/page-body.html +0 -152
  216. package/hugo-theme/layouts/partials/related.html +0 -138
  217. package/hugo-theme/layouts/partials/search.html +0 -84
  218. package/hugo-theme/layouts/partials/site-url.html +0 -32
  219. package/hugo-theme/layouts/partials/tags.html +0 -30
  220. package/hugo-theme/layouts/partials/toc.html +0 -28
  221. package/hugo-theme/layouts/partials/warn-missing-banner.html +0 -3
  222. package/hugo-theme/layouts/shortcodes/cartouche.html +0 -64
  223. package/hugo-theme/layouts/shortcodes/exturl.html +0 -12
  224. package/hugo-theme/layouts/shortcodes/glyph.html +0 -43
  225. package/hugo-theme/layouts/shortcodes/pagelist.html +0 -63
  226. package/hugo-theme/theme.toml +0 -11
  227. package/types/engine/web-wikilinks.d.mts +0 -107
  228. /package/{hugo-theme → site-theme}/data/banner-kinds.yaml +0 -0
  229. /package/{hugo-theme → site-theme}/static/css/sohl-icons.css +0 -0
  230. /package/{hugo-theme → site-theme}/static/fonts/game-icons-kb.woff2 +0 -0
  231. /package/{hugo-theme → site-theme}/static/img/banners/takheperu-hieroglyphs.svg +0 -0
  232. /package/{hugo-theme → site-theme}/static/img/cartouches/takheperu.svg +0 -0
  233. /package/{hugo-theme → site-theme}/static/js/inline-spoilers.js +0 -0
@@ -0,0 +1,288 @@
1
+ /**
2
+ * The note a body belongs to.
3
+ *
4
+ * @typedef {object} ExpandedNote
5
+ * @property {Record<string, any>} fm - Its frontmatter.
6
+ * @property {string} [file] - Its file, which findings name.
7
+ * @property {string} source - What a table's or a link's finding names the
8
+ * note by: its path on the web, its name in Foundry.
9
+ * @property {number} [bodyLine] - The file line its body starts on.
10
+ * @property {number} [bodyColumn] - The column its body starts at on that line.
11
+ */
12
+ /**
13
+ * How a target resolves links, beyond the index.
14
+ *
15
+ * @typedef {object} ExpandLinks
16
+ * @property {string|null} [pack] - `foundry`: the pack the note's own document
17
+ * lands in, which a `[[#slug]]` self-link addresses.
18
+ * @property {string|null} [docPack] - `foundry`: the pack its journal lands in.
19
+ * @property {Map<string, object>} [foreign] - `web` and `book`: the merged
20
+ * foreign index.
21
+ * @property {object} [assets] - `web` and `book`: the address space an embed
22
+ * resolves against, from {@link module:engine/art-fields.assetAddressIndex}.
23
+ * @property {(text: string) => string} [beforeLinks] - `web` and `book`: a pass
24
+ * run on the text outside code before its links resolve.
25
+ * @property {(text: string) => string} [afterLinks] - `web` and `book`: a pass
26
+ * run on the text outside code once its links resolve.
27
+ */
28
+ /**
29
+ * The first two steps of an expansion: the tables, and the figures of the
30
+ * table-expanded body.
31
+ *
32
+ * @typedef {object} ExpandedTables
33
+ * @property {{markdown: string, errors: object[], lineMap: object[],
34
+ * generatedFrom: number|undefined}} tables - From
35
+ * {@link module:engine/content-tables.expandContentTables}.
36
+ * @property {{figures: object[], errors: object[]}} figures - The figure scan
37
+ * of `tables.markdown`. A caller numbering figures across notes replaces
38
+ * `figures.figures` with its numbering before expanding the rest.
39
+ */
40
+ /**
41
+ * Expand a note's tables and scan the result for figures — steps 1 and 2 of
42
+ * {@link expandContent}.
43
+ *
44
+ * @param {string} markdown - The body as authored.
45
+ * @param {object} options
46
+ * @param {string} options.source - What a table's finding names the note by.
47
+ * @param {{sqlTables?: object[], pageLists?: object[]}} [options.prepared] -
48
+ * This note's prepared SQL tables and page lists.
49
+ * @param {(address: string) => string|undefined} [options.resolveRole] - The
50
+ * role an embedded picture takes, which numbers a map apart from a figure.
51
+ * @returns {ExpandedTables} The two steps' results.
52
+ */
53
+ export function expandTables(markdown: string, { source, prepared, resolveRole }: {
54
+ source: string;
55
+ prepared?: {
56
+ sqlTables?: object[];
57
+ pageLists?: object[];
58
+ } | undefined;
59
+ resolveRole?: ((address: string) => string | undefined) | undefined;
60
+ }): ExpandedTables;
61
+ /**
62
+ * The expanded body, and what each step found.
63
+ *
64
+ * @typedef {object} Expansion
65
+ * @property {string} markdown - The whole body, expanded.
66
+ * @property {string} authored - The author's text, expanded. In Foundry it is
67
+ * the whole body.
68
+ * @property {string} generated - The generated sections, expanded apart from
69
+ * the author's text on the web; `""` in Foundry, and wherever there are none.
70
+ * @property {Array<{line: number, generated: boolean}>} lineMap - The authored
71
+ * line, 0-based, each line of the table-expanded body came from.
72
+ * @property {number|undefined} generatedFrom - The 0-based line of the
73
+ * table-expanded body the generated sections start on.
74
+ * @property {{figures: object[], errors: object[]}} figures - The figure scan
75
+ * of the table-expanded body.
76
+ * @property {{tables: object[], captions: object[], expressions: object[], links: object[]}} findings -
77
+ * Each step's findings, as the step reports them: a table's and a caption's
78
+ * by expanded body line, an expression's in file coordinates, a link's by
79
+ * occurrence of its literal.
80
+ * @property {Error|undefined} linkError - `foundry`: the error
81
+ * {@link module:engine/helpers.convertNoteWikilinks} fails a note with,
82
+ * carrying `file` and `position`.
83
+ * @property {object[]} unresolved - `foundry`: the links that did not resolve.
84
+ * @property {object[]} resolved - `web` and `book`: every link that resolved,
85
+ * in order.
86
+ * @property {number} authoredLinks - `web`: how many of `resolved` the
87
+ * author's text made, before the generated sections'.
88
+ */
89
+ /**
90
+ * Expand a note's body for one target.
91
+ *
92
+ * @param {string} markdown - The body as authored.
93
+ * @param {object} options
94
+ * @param {"foundry"|"web"|"book"} options.target - What the body is expanded
95
+ * for.
96
+ * @param {object} options.index - What links resolve against: the compile's
97
+ * link index for `foundry`, the {@link module:engine/site-index.buildSiteIndex}
98
+ * index for `web` and `book`.
99
+ * @param {ExpandedNote} options.note - The note.
100
+ * @param {{sqlTables?: object[], pageLists?: object[], inline?: object[]}} [options.prepared] -
101
+ * This note's prepared SQL tables, page lists and inline query results.
102
+ * @param {object} [options.events] - Every note's events, from
103
+ * {@link module:engine/event-fields.eventNoteIndex}.
104
+ * @param {(address: string) => string|undefined} [options.resolveRole] - The
105
+ * role an embedded picture takes, which numbers a map apart from a figure.
106
+ * @param {Map<string, Map<string, object>>} [options.figuresByAddress] - `web`
107
+ * and `book`: every page's figures, by the address a cross-note `ref` writes.
108
+ * @param {ExpandedTables} [options.tables] - The note's {@link expandTables},
109
+ * already run — with the figures numbered, for the book. Run here when
110
+ * omitted.
111
+ * @param {ExpandLinks} [options.links] - How the target resolves links.
112
+ * @returns {Expansion} The expanded body and the findings.
113
+ * @throws {Error} When `target` is not one of {@link EXPANSION_TARGETS}.
114
+ */
115
+ export function expandContent(markdown: string, { target, index, note, prepared, events, resolveRole, figuresByAddress, tables: staged, links, }: {
116
+ target: "foundry" | "web" | "book";
117
+ index: object;
118
+ note: ExpandedNote;
119
+ prepared?: {
120
+ sqlTables?: object[];
121
+ pageLists?: object[];
122
+ inline?: object[];
123
+ } | undefined;
124
+ events?: object | undefined;
125
+ resolveRole?: ((address: string) => string | undefined) | undefined;
126
+ figuresByAddress?: Map<string, Map<string, object>> | undefined;
127
+ tables?: ExpandedTables | undefined;
128
+ links?: ExpandLinks | undefined;
129
+ }): Expansion;
130
+ /** The targets a body is expanded for. */
131
+ export const EXPANSION_TARGETS: readonly string[];
132
+ /**
133
+ * The note a body belongs to.
134
+ */
135
+ export type ExpandedNote = {
136
+ /**
137
+ * - Its frontmatter.
138
+ */
139
+ fm: Record<string, any>;
140
+ /**
141
+ * - Its file, which findings name.
142
+ */
143
+ file?: string | undefined;
144
+ /**
145
+ * - What a table's or a link's finding names the
146
+ * note by: its path on the web, its name in Foundry.
147
+ */
148
+ source: string;
149
+ /**
150
+ * - The file line its body starts on.
151
+ */
152
+ bodyLine?: number | undefined;
153
+ /**
154
+ * - The column its body starts at on that line.
155
+ */
156
+ bodyColumn?: number | undefined;
157
+ };
158
+ /**
159
+ * How a target resolves links, beyond the index.
160
+ */
161
+ export type ExpandLinks = {
162
+ /**
163
+ * - `foundry`: the pack the note's own document
164
+ * lands in, which a `[[#slug]]` self-link addresses.
165
+ */
166
+ pack?: string | null | undefined;
167
+ /**
168
+ * - `foundry`: the pack its journal lands in.
169
+ */
170
+ docPack?: string | null | undefined;
171
+ /**
172
+ * - `web` and `book`: the merged
173
+ * foreign index.
174
+ */
175
+ foreign?: Map<string, object> | undefined;
176
+ /**
177
+ * - `web` and `book`: the address space an embed
178
+ * resolves against, from {@link module :engine/art-fields.assetAddressIndex}.
179
+ */
180
+ assets?: object | undefined;
181
+ /**
182
+ * - `web` and `book`: a pass
183
+ * run on the text outside code before its links resolve.
184
+ */
185
+ beforeLinks?: ((text: string) => string) | undefined;
186
+ /**
187
+ * - `web` and `book`: a pass
188
+ * run on the text outside code once its links resolve.
189
+ */
190
+ afterLinks?: ((text: string) => string) | undefined;
191
+ };
192
+ /**
193
+ * The first two steps of an expansion: the tables, and the figures of the
194
+ * table-expanded body.
195
+ */
196
+ export type ExpandedTables = {
197
+ /**
198
+ * - From
199
+ * {@link module :engine/content-tables.expandContentTables}.
200
+ */
201
+ tables: {
202
+ markdown: string;
203
+ errors: object[];
204
+ lineMap: object[];
205
+ generatedFrom: number | undefined;
206
+ };
207
+ /**
208
+ * - The figure scan
209
+ * of `tables.markdown`. A caller numbering figures across notes replaces
210
+ * `figures.figures` with its numbering before expanding the rest.
211
+ */
212
+ figures: {
213
+ figures: object[];
214
+ errors: object[];
215
+ };
216
+ };
217
+ /**
218
+ * The expanded body, and what each step found.
219
+ */
220
+ export type Expansion = {
221
+ /**
222
+ * - The whole body, expanded.
223
+ */
224
+ markdown: string;
225
+ /**
226
+ * - The author's text, expanded. In Foundry it is
227
+ * the whole body.
228
+ */
229
+ authored: string;
230
+ /**
231
+ * - The generated sections, expanded apart from
232
+ * the author's text on the web; `""` in Foundry, and wherever there are none.
233
+ */
234
+ generated: string;
235
+ /**
236
+ * - The authored
237
+ * line, 0-based, each line of the table-expanded body came from.
238
+ */
239
+ lineMap: Array<{
240
+ line: number;
241
+ generated: boolean;
242
+ }>;
243
+ /**
244
+ * - The 0-based line of the
245
+ * table-expanded body the generated sections start on.
246
+ */
247
+ generatedFrom: number | undefined;
248
+ /**
249
+ * - The figure scan
250
+ * of the table-expanded body.
251
+ */
252
+ figures: {
253
+ figures: object[];
254
+ errors: object[];
255
+ };
256
+ /**
257
+ * -
258
+ * Each step's findings, as the step reports them: a table's and a caption's
259
+ * by expanded body line, an expression's in file coordinates, a link's by
260
+ * occurrence of its literal.
261
+ */
262
+ findings: {
263
+ tables: object[];
264
+ captions: object[];
265
+ expressions: object[];
266
+ links: object[];
267
+ };
268
+ /**
269
+ * - `foundry`: the error
270
+ * {@link module :engine/helpers.convertNoteWikilinks} fails a note with,
271
+ * carrying `file` and `position`.
272
+ */
273
+ linkError: Error | undefined;
274
+ /**
275
+ * - `foundry`: the links that did not resolve.
276
+ */
277
+ unresolved: object[];
278
+ /**
279
+ * - `web` and `book`: every link that resolved,
280
+ * in order.
281
+ */
282
+ resolved: object[];
283
+ /**
284
+ * - `web`: how many of `resolved` the
285
+ * author's text made, before the generated sections'.
286
+ */
287
+ authoredLinks: number;
288
+ };
@@ -57,18 +57,26 @@ export function scanFigures(source: string, { resolveRole }?: {
57
57
  * @param {string} source - A note body with expanded tables.
58
58
  * @param {(markdown: string) => string} [renderMarkdown] - How to render a
59
59
  * figure's own contents.
60
- * @param {Array<{id: string, label: string}>} [numbers] - Labels assigned by a
61
- * surface that counts across documents, matched by id.
60
+ * @param {Array<{id: string, kind: string, label: string}>} [numbers] - The
61
+ * figures as {@link scanFigures} numbered them, with roles, where the
62
+ * surface counted them: across a note's pages, or in expansion, where a
63
+ * `ref` reads the same label. They are matched in order when they are as many
64
+ * as the text holds, by id otherwise, and the caption takes its number, kind
65
+ * and label from them. Omitted, the text is numbered as it stands.
62
66
  * @param {object} [options] - Options.
63
67
  * @param {(address: string) => string|undefined} [options.resolveRole] - See
64
68
  * {@link scanFigures}.
69
+ * @param {(markdown: string) => string} [options.renderInline] - How a caption
70
+ * is rendered; omitted, a caption is plain inline Markdown.
65
71
  * @returns {{markdown: string, errors: Array<{line: number, column: number, message: string}>}}
66
72
  */
67
73
  export function renderFigureBlocks(source: string, renderMarkdown?: (markdown: string) => string, numbers?: Array<{
68
74
  id: string;
75
+ kind: string;
69
76
  label: string;
70
- }>, { resolveRole }?: {
77
+ }>, { resolveRole, renderInline }?: {
71
78
  resolveRole?: ((address: string) => string | undefined) | undefined;
79
+ renderInline?: ((markdown: string) => string) | undefined;
72
80
  }): {
73
81
  markdown: string;
74
82
  errors: Array<{
@@ -0,0 +1,85 @@
1
+ /**
2
+ * The pathname of a glyph's picture.
3
+ * @param {string} slug - The glyph's slug.
4
+ * @returns {string} The authored pathname.
5
+ */
6
+ export function glyphPathname(slug: string): string;
7
+ /**
8
+ * The pathname of a cartouche's picture.
9
+ * @param {string} slug - The cartouche's slug.
10
+ * @returns {string} The authored pathname.
11
+ */
12
+ export function cartouchePathname(slug: string): string;
13
+ /**
14
+ * A slug as words, for the alt text of a sign whose author wrote none.
15
+ * @param {string} slug - The slug.
16
+ * @returns {string} Title-cased words.
17
+ */
18
+ export function humanizeSlug(slug: string): string;
19
+ /**
20
+ * What is wrong with a glyph's attributes.
21
+ * @param {{id: string, classes: string[], values: Record<string, string>}} parsed - The parsed attributes.
22
+ * @returns {string[]} One message per problem.
23
+ */
24
+ export function glyphProblems(parsed: {
25
+ id: string;
26
+ classes: string[];
27
+ values: Record<string, string>;
28
+ }): string[];
29
+ /**
30
+ * What is wrong with a cartouche's attributes.
31
+ * @param {{id: string, classes: string[], values: Record<string, string>}} parsed - The parsed attributes.
32
+ * @returns {string[]} One message per problem.
33
+ */
34
+ export function cartoucheProblems(parsed: {
35
+ id: string;
36
+ classes: string[];
37
+ values: Record<string, string>;
38
+ }): string[];
39
+ /**
40
+ * A cartouche's height as Typst writes a length.
41
+ * @param {string} height - A validated CSS length.
42
+ * @returns {string} The same length in a unit Typst reads.
43
+ */
44
+ export function typstLength(height: string): string;
45
+ /**
46
+ * A glyph as HTML.
47
+ * @param {{slug: string, alt: string, frame?: string, size?: string}} glyph - Its attributes.
48
+ * @param {string} src - The address the target serves its picture at.
49
+ * @returns {string} A span holding an image.
50
+ */
51
+ export function glyphHtml({ slug, alt, frame, size }: {
52
+ slug: string;
53
+ alt: string;
54
+ frame?: string;
55
+ size?: string;
56
+ }, src: string): string;
57
+ /**
58
+ * A cartouche as HTML.
59
+ * @param {{slug: string, alt?: string, align?: string, height?: string, caption?: string}} cartouche - Its attributes.
60
+ * @param {string} src - The address the target serves its picture at.
61
+ * @returns {string} A figure holding an image and an optional caption, on one
62
+ * line so that it sits inside a paragraph without ending it.
63
+ */
64
+ export function cartoucheHtml({ slug, alt, align, height, caption }: {
65
+ slug: string;
66
+ alt?: string;
67
+ align?: string;
68
+ height?: string;
69
+ caption?: string;
70
+ }, src: string): string;
71
+ /** The frames a glyph may sit in. */
72
+ export const GLYPH_FRAMES: readonly string[];
73
+ /** The sizes a glyph may take. */
74
+ export const GLYPH_SIZES: readonly string[];
75
+ /** The sides a cartouche may float to; absent, it is centred. */
76
+ export const CARTOUCHE_ALIGNS: readonly string[];
77
+ /** The attribute keys a glyph takes. */
78
+ export const GLYPH_KEYS: readonly string[];
79
+ /** The attribute keys a cartouche takes. */
80
+ export const CARTOUCHE_KEYS: readonly string[];
81
+ /**
82
+ * The units a cartouche height may be written in: every one a printed page
83
+ * can honour as well as a screen.
84
+ */
85
+ export const HEIGHT_UNITS: readonly string[];
@@ -73,7 +73,7 @@ export function escapeHtml(text: string): string;
73
73
  *
74
74
  * **The role class and the `width`/`height` attributes are what a stylesheet
75
75
  * elsewhere keys a role's size on.** This module states none — the measure a
76
- * `portrait` fills on a page is a Hugo theme's or a Foundry system's own
76
+ * `portrait` fills on a page is a site theme's or a Foundry system's own
77
77
  * decision — and emits only what the resolved asset record states: a role
78
78
  * class when the picture declares one, and the attributes whenever the
79
79
  * picture resolved to an asset record at all, blank for a vector. The
@@ -239,12 +239,11 @@ export function lintContentImages(contentBase: string, { skipDirectories, config
239
239
  /**
240
240
  * Rewrite every block image in a body into the figure the website publishes.
241
241
  *
242
- * **Hugo is handed markdown, not a rendered page.** The site emitter writes a
243
- * note's body through verbatim, so a `{…}` directive left in it reaches the
244
- * page as its own literal braces: Goldmark's block-attribute parser is off, and
245
- * turning it on would accept `style` and `id` alongside the closed vocabularies,
246
- * which is the injection surface this rule exists to avoid. So the directive is
247
- * resolved here, into markup Goldmark passes through.
242
+ * **The directive is resolved before the markdown is parsed.** A `{…}`
243
+ * directive left in the body would reach the page as its own literal braces: a
244
+ * block-attribute parser would accept `style` and `id` alongside the closed
245
+ * vocabularies, which is the injection surface this rule exists to avoid. So
246
+ * the directive is resolved here, into markup the renderer passes through.
248
247
  *
249
248
  * An image whose directive does not parse is left exactly as written, so the
250
249
  * page shows the braces and the lint says why — the same visible degradation an
@@ -142,7 +142,7 @@ export function auditHomepageLinks(index: ReturnType<typeof buildLinkIndex>): Ar
142
142
  * `"unresolved"`, never `"ambiguous"`: every target here expands to one
143
143
  * canonical address before anything is looked up, so there is no candidate
144
144
  * set for two packages to claim — and every reason is an **error**: the
145
- * three resolvers agree on severity for every class.
145
+ * checker and the resolver agree on severity for every class.
146
146
  */
147
147
  export function auditLinks(index: ReturnType<typeof buildLinkIndex>): {
148
148
  deadAnchors: object[];
@@ -0,0 +1,199 @@
1
+ /**
2
+ * Highlight a fenced block's code for the language it names.
3
+ *
4
+ * @param {string} code - The block's text.
5
+ * @param {string} language - The fence's first word.
6
+ * @returns {string} The code as highlight.js's class-based markup, or `""` when
7
+ * no language is named or highlight.js does not know it, which markdown-it
8
+ * reads as "escape it as plain text".
9
+ */
10
+ export function highlightCode(code: string, language: string): string;
11
+ /**
12
+ * Make the raw HTML an author wrote inert, leaving what markdown reads as a
13
+ * link and anything inside code as written.
14
+ *
15
+ * The `preview` target parses with HTML on, because the stages of
16
+ * {@link Renderer#prepare} write HTML between blank lines. A tag the author
17
+ * wrote must still read as text, so its opening bracket becomes
18
+ * {@link INERT_BRACKET} first, before the stages run and before expansion
19
+ * writes its own markup; the preview renderer writes it back as `&lt;`, and
20
+ * its source view as `<`.
21
+ *
22
+ * @param {string} markdown - Authored markdown.
23
+ * @returns {string} The same markdown with each authored `<` that opens a tag,
24
+ * comment, declaration or processing instruction replaced.
25
+ */
26
+ export function inertHtml(markdown: string): string;
27
+ /**
28
+ * How a target's pictures resolve.
29
+ *
30
+ * @typedef {object} ImageSources
31
+ * @property {(src: string) => string} [resolveSrc] - From a body image's address
32
+ * to the `src` the target draws.
33
+ * @property {(src: string) => ({role?: string, width?: number|"", height?: number|""}|undefined)} [lookupAsset] -
34
+ * From an address to the asset it names.
35
+ */
36
+ /**
37
+ * What a renderer is built with.
38
+ *
39
+ * @typedef {object} RendererOptions
40
+ * @property {() => (object|undefined)|object} [icons] - The icon registry, or a
41
+ * function that returns it, called at each render so a configuration read
42
+ * late is honoured. `foundry`, `web`, `preview` and `book`.
43
+ * @property {ImageSources} [images] - How body images resolve. `foundry`, `web`
44
+ * and `preview`.
45
+ * @property {boolean} [source] - `preview`: show wikilinks, spans, expressions
46
+ * and queries as highlighted authored source, for a buffer with no index.
47
+ * @property {object} [sourceContext] - `preview` with `source`: the buffer's
48
+ * `fm`, `file` and `findings`, which the source view reads.
49
+ */
50
+ /**
51
+ * @typedef {object} RenderEnv
52
+ * @property {import("./content-scripts.mjs").RunContext} [runs] - The package's
53
+ * languages, faces and maps.
54
+ * @property {Array<object>} [figures] - The note's numbered figures, from the
55
+ * figure scan expansion made: matched in order when they are as many as the
56
+ * text holds, by id otherwise.
57
+ * @property {(address: string) => string|undefined} [resolveRole] - From a
58
+ * picture's address to the role its asset declares, used when `figures` is
59
+ * not given.
60
+ * @property {Map<string, number>} [footnoteNumbers] - Footnote numbers shared
61
+ * across the pages of one note.
62
+ * @property {string} [docId] - Threaded into footnote anchors.
63
+ * @property {(src: string) => string} [resolveSrc] - From a glyph's or
64
+ * cartouche's authored pathname to the address this render serves, taking
65
+ * the place of the renderer's own image resolver.
66
+ */
67
+ /**
68
+ * @typedef {object} Renderer
69
+ * @property {RendererTarget} target - The target it renders for.
70
+ * @property {import("markdown-it")} md - The configured parser.
71
+ * @property {readonly string[]} plugins - The names of the plugins installed, in
72
+ * order. Targets that share a configuration share its names.
73
+ * @property {(markdown: string, env?: RenderEnv) => string} prepare - Write the
74
+ * constructs markdown-it has no syntax for as HTML between blank lines.
75
+ * @property {(markdown: string, env?: RenderEnv) => string} render - Prepare,
76
+ * then render to HTML.
77
+ * @property {(markdown: string) => string} renderInline - Render one inline run.
78
+ */
79
+ /** @typedef {"foundry"|"web"|"preview"|"book"} RendererTarget */
80
+ /**
81
+ * Build the renderer for one target.
82
+ *
83
+ * @param {RendererTarget} target - What the markdown is rendered for.
84
+ * @param {RendererOptions} [options] - Per-target inputs.
85
+ * @returns {Renderer} The configured parser and its stages.
86
+ * @throws {Error} When `target` is not one of {@link RENDER_TARGETS}.
87
+ */
88
+ export function createRenderer(target: RendererTarget, options?: RendererOptions): Renderer;
89
+ /** The targets a renderer is built for. */
90
+ export const RENDER_TARGETS: readonly string[];
91
+ /**
92
+ * How a target's pictures resolve.
93
+ */
94
+ export type ImageSources = {
95
+ /**
96
+ * - From a body image's address
97
+ * to the `src` the target draws.
98
+ */
99
+ resolveSrc?: ((src: string) => string) | undefined;
100
+ /**
101
+ * -
102
+ * From an address to the asset it names.
103
+ */
104
+ lookupAsset?: ((src: string) => ({
105
+ role?: string;
106
+ width?: number | "";
107
+ height?: number | "";
108
+ } | undefined)) | undefined;
109
+ };
110
+ /**
111
+ * What a renderer is built with.
112
+ */
113
+ export type RendererOptions = {
114
+ /**
115
+ * - The icon registry, or a
116
+ * function that returns it, called at each render so a configuration read
117
+ * late is honoured. `foundry`, `web`, `preview` and `book`.
118
+ */
119
+ icons?: (() => (object | undefined) | object) | undefined;
120
+ /**
121
+ * - How body images resolve. `foundry`, `web`
122
+ * and `preview`.
123
+ */
124
+ images?: ImageSources | undefined;
125
+ /**
126
+ * - `preview`: show wikilinks, spans, expressions
127
+ * and queries as highlighted authored source, for a buffer with no index.
128
+ */
129
+ source?: boolean | undefined;
130
+ /**
131
+ * - `preview` with `source`: the buffer's
132
+ * `fm`, `file` and `findings`, which the source view reads.
133
+ */
134
+ sourceContext?: object | undefined;
135
+ };
136
+ export type RenderEnv = {
137
+ /**
138
+ * - The package's
139
+ * languages, faces and maps.
140
+ */
141
+ runs?: import("./content-scripts.mjs").RunContext | undefined;
142
+ /**
143
+ * - The note's numbered figures, from the
144
+ * figure scan expansion made: matched in order when they are as many as the
145
+ * text holds, by id otherwise.
146
+ */
147
+ figures?: object[] | undefined;
148
+ /**
149
+ * - From a
150
+ * picture's address to the role its asset declares, used when `figures` is
151
+ * not given.
152
+ */
153
+ resolveRole?: ((address: string) => string | undefined) | undefined;
154
+ /**
155
+ * - Footnote numbers shared
156
+ * across the pages of one note.
157
+ */
158
+ footnoteNumbers?: Map<string, number> | undefined;
159
+ /**
160
+ * - Threaded into footnote anchors.
161
+ */
162
+ docId?: string | undefined;
163
+ /**
164
+ * - From a glyph's or
165
+ * cartouche's authored pathname to the address this render serves, taking
166
+ * the place of the renderer's own image resolver.
167
+ */
168
+ resolveSrc?: ((src: string) => string) | undefined;
169
+ };
170
+ export type Renderer = {
171
+ /**
172
+ * - The target it renders for.
173
+ */
174
+ target: RendererTarget;
175
+ /**
176
+ * - The configured parser.
177
+ */
178
+ md: typeof import("markdown-it");
179
+ /**
180
+ * - The names of the plugins installed, in
181
+ * order. Targets that share a configuration share its names.
182
+ */
183
+ plugins: readonly string[];
184
+ /**
185
+ * - Write the
186
+ * constructs markdown-it has no syntax for as HTML between blank lines.
187
+ */
188
+ prepare: (markdown: string, env?: RenderEnv) => string;
189
+ /**
190
+ * - Prepare,
191
+ * then render to HTML.
192
+ */
193
+ render: (markdown: string, env?: RenderEnv) => string;
194
+ /**
195
+ * - Render one inline run.
196
+ */
197
+ renderInline: (markdown: string) => string;
198
+ };
199
+ export type RendererTarget = "foundry" | "web" | "preview" | "book";