postext 1.14.1 → 1.15.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 (489) hide show
  1. package/dist/__tests__/arabic/blockLanguageDigits.test.d.ts +2 -0
  2. package/dist/__tests__/arabic/blockLanguageDigits.test.d.ts.map +1 -0
  3. package/dist/__tests__/arabic/blockLanguageDigits.test.js +54 -0
  4. package/dist/__tests__/arabic/blockLanguageDigits.test.js.map +1 -0
  5. package/dist/__tests__/arabic/emphasis.test.d.ts +2 -0
  6. package/dist/__tests__/arabic/emphasis.test.d.ts.map +1 -0
  7. package/dist/__tests__/arabic/emphasis.test.js +206 -0
  8. package/dist/__tests__/arabic/emphasis.test.js.map +1 -0
  9. package/dist/__tests__/arabic/footnotes.test.d.ts +2 -0
  10. package/dist/__tests__/arabic/footnotes.test.d.ts.map +1 -0
  11. package/dist/__tests__/arabic/footnotes.test.js +118 -0
  12. package/dist/__tests__/arabic/footnotes.test.js.map +1 -0
  13. package/dist/__tests__/arabic/harakat.test.d.ts +2 -0
  14. package/dist/__tests__/arabic/harakat.test.d.ts.map +1 -0
  15. package/dist/__tests__/arabic/harakat.test.js +167 -0
  16. package/dist/__tests__/arabic/harakat.test.js.map +1 -0
  17. package/dist/__tests__/arabic/ornateBrackets.test.d.ts +2 -0
  18. package/dist/__tests__/arabic/ornateBrackets.test.d.ts.map +1 -0
  19. package/dist/__tests__/arabic/ornateBrackets.test.js +71 -0
  20. package/dist/__tests__/arabic/ornateBrackets.test.js.map +1 -0
  21. package/dist/__tests__/arabic/tashkil.test.d.ts +2 -0
  22. package/dist/__tests__/arabic/tashkil.test.d.ts.map +1 -0
  23. package/dist/__tests__/arabic/tashkil.test.js +106 -0
  24. package/dist/__tests__/arabic/tashkil.test.js.map +1 -0
  25. package/dist/__tests__/arabicLocale.test.d.ts +2 -0
  26. package/dist/__tests__/arabicLocale.test.d.ts.map +1 -0
  27. package/dist/__tests__/arabicLocale.test.js +232 -0
  28. package/dist/__tests__/arabicLocale.test.js.map +1 -0
  29. package/dist/__tests__/arabicNumberWords.test.d.ts +2 -0
  30. package/dist/__tests__/arabicNumberWords.test.d.ts.map +1 -0
  31. package/dist/__tests__/arabicNumberWords.test.js +176 -0
  32. package/dist/__tests__/arabicNumberWords.test.js.map +1 -0
  33. package/dist/__tests__/arabicNumbering.test.d.ts +2 -0
  34. package/dist/__tests__/arabicNumbering.test.d.ts.map +1 -0
  35. package/dist/__tests__/arabicNumbering.test.js +257 -0
  36. package/dist/__tests__/arabicNumbering.test.js.map +1 -0
  37. package/dist/__tests__/arabicWords.test.d.ts +2 -0
  38. package/dist/__tests__/arabicWords.test.d.ts.map +1 -0
  39. package/dist/__tests__/arabicWords.test.js +302 -0
  40. package/dist/__tests__/arabicWords.test.js.map +1 -0
  41. package/dist/__tests__/bidi.test.d.ts +2 -0
  42. package/dist/__tests__/bidi.test.d.ts.map +1 -0
  43. package/dist/__tests__/bidi.test.js +282 -0
  44. package/dist/__tests__/bidi.test.js.map +1 -0
  45. package/dist/__tests__/blockHints.test.d.ts +2 -0
  46. package/dist/__tests__/blockHints.test.d.ts.map +1 -0
  47. package/dist/__tests__/blockHints.test.js +79 -0
  48. package/dist/__tests__/blockHints.test.js.map +1 -0
  49. package/dist/__tests__/chineseLocale.test.js +2 -2
  50. package/dist/__tests__/chineseLocale.test.js.map +1 -1
  51. package/dist/__tests__/cjk/grid.test.js +2 -2
  52. package/dist/__tests__/cjk/grid.test.js.map +1 -1
  53. package/dist/__tests__/cjk/justifyRender.test.js +2 -1
  54. package/dist/__tests__/cjk/justifyRender.test.js.map +1 -1
  55. package/dist/__tests__/defaults/folio.test.js +16 -1
  56. package/dist/__tests__/defaults/folio.test.js.map +1 -1
  57. package/dist/__tests__/direction.test.d.ts +2 -0
  58. package/dist/__tests__/direction.test.d.ts.map +1 -0
  59. package/dist/__tests__/direction.test.js +117 -0
  60. package/dist/__tests__/direction.test.js.map +1 -0
  61. package/dist/__tests__/exports.test.js +29 -0
  62. package/dist/__tests__/exports.test.js.map +1 -1
  63. package/dist/__tests__/headingLetterSpacing.test.js +1 -1
  64. package/dist/__tests__/headingLetterSpacing.test.js.map +1 -1
  65. package/dist/__tests__/headingNumberPosition.test.d.ts +2 -0
  66. package/dist/__tests__/headingNumberPosition.test.d.ts.map +1 -0
  67. package/dist/__tests__/headingNumberPosition.test.js +87 -0
  68. package/dist/__tests__/headingNumberPosition.test.js.map +1 -0
  69. package/dist/__tests__/htmlCopyText.test.d.ts +2 -0
  70. package/dist/__tests__/htmlCopyText.test.d.ts.map +1 -0
  71. package/dist/__tests__/htmlCopyText.test.js +153 -0
  72. package/dist/__tests__/htmlCopyText.test.js.map +1 -0
  73. package/dist/__tests__/kashida.test.d.ts +2 -0
  74. package/dist/__tests__/kashida.test.d.ts.map +1 -0
  75. package/dist/__tests__/kashida.test.js +281 -0
  76. package/dist/__tests__/kashida.test.js.map +1 -0
  77. package/dist/__tests__/kashidaPatterns.test.d.ts +2 -0
  78. package/dist/__tests__/kashidaPatterns.test.d.ts.map +1 -0
  79. package/dist/__tests__/kashidaPatterns.test.js +143 -0
  80. package/dist/__tests__/kashidaPatterns.test.js.map +1 -0
  81. package/dist/__tests__/links.test.js +3 -1
  82. package/dist/__tests__/links.test.js.map +1 -1
  83. package/dist/__tests__/parse/containers.test.js +1 -1
  84. package/dist/__tests__/parse/containers.test.js.map +1 -1
  85. package/dist/__tests__/rtl/designText.test.d.ts +2 -0
  86. package/dist/__tests__/rtl/designText.test.d.ts.map +1 -0
  87. package/dist/__tests__/rtl/designText.test.js +301 -0
  88. package/dist/__tests__/rtl/designText.test.js.map +1 -0
  89. package/dist/__tests__/rtl/designTextPaint.test.d.ts +2 -0
  90. package/dist/__tests__/rtl/designTextPaint.test.d.ts.map +1 -0
  91. package/dist/__tests__/rtl/designTextPaint.test.js +140 -0
  92. package/dist/__tests__/rtl/designTextPaint.test.js.map +1 -0
  93. package/dist/__tests__/rtl/htmlRtl.test.d.ts +2 -0
  94. package/dist/__tests__/rtl/htmlRtl.test.d.ts.map +1 -0
  95. package/dist/__tests__/rtl/htmlRtl.test.js +175 -0
  96. package/dist/__tests__/rtl/htmlRtl.test.js.map +1 -0
  97. package/dist/__tests__/rtl/mirroredFrame.test.d.ts +2 -0
  98. package/dist/__tests__/rtl/mirroredFrame.test.d.ts.map +1 -0
  99. package/dist/__tests__/rtl/mirroredFrame.test.js +313 -0
  100. package/dist/__tests__/rtl/mirroredFrame.test.js.map +1 -0
  101. package/dist/__tests__/rtl/mirroredPaint.test.d.ts +2 -0
  102. package/dist/__tests__/rtl/mirroredPaint.test.d.ts.map +1 -0
  103. package/dist/__tests__/rtl/mirroredPaint.test.js +116 -0
  104. package/dist/__tests__/rtl/mirroredPaint.test.js.map +1 -0
  105. package/dist/__tests__/rtl/oppositeBlocks.test.d.ts +2 -0
  106. package/dist/__tests__/rtl/oppositeBlocks.test.d.ts.map +1 -0
  107. package/dist/__tests__/rtl/oppositeBlocks.test.js +273 -0
  108. package/dist/__tests__/rtl/oppositeBlocks.test.js.map +1 -0
  109. package/dist/__tests__/rtl/segmentLang.test.d.ts +2 -0
  110. package/dist/__tests__/rtl/segmentLang.test.d.ts.map +1 -0
  111. package/dist/__tests__/rtl/segmentLang.test.js +54 -0
  112. package/dist/__tests__/rtl/segmentLang.test.js.map +1 -0
  113. package/dist/__tests__/rtlLines.test.d.ts +2 -0
  114. package/dist/__tests__/rtlLines.test.d.ts.map +1 -0
  115. package/dist/__tests__/rtlLines.test.js +180 -0
  116. package/dist/__tests__/rtlLines.test.js.map +1 -0
  117. package/dist/__tests__/tocNumberColumn.test.d.ts +2 -0
  118. package/dist/__tests__/tocNumberColumn.test.d.ts.map +1 -0
  119. package/dist/__tests__/tocNumberColumn.test.js +67 -0
  120. package/dist/__tests__/tocNumberColumn.test.js.map +1 -0
  121. package/dist/__tests__/verse.test.d.ts +2 -0
  122. package/dist/__tests__/verse.test.d.ts.map +1 -0
  123. package/dist/__tests__/verse.test.js +232 -0
  124. package/dist/__tests__/verse.test.js.map +1 -0
  125. package/dist/__tests__/vertical/geometry.test.js +2 -2
  126. package/dist/__tests__/vertical/geometry.test.js.map +1 -1
  127. package/dist/__tests__/vertical/htmlTurnedCells.test.js +2 -2
  128. package/dist/__tests__/vertical/htmlTurnedCells.test.js.map +1 -1
  129. package/dist/arabicMarks.d.ts +80 -0
  130. package/dist/arabicMarks.d.ts.map +1 -0
  131. package/dist/arabicMarks.js +267 -0
  132. package/dist/arabicMarks.js.map +1 -0
  133. package/dist/arabicNumberWords.d.ts +43 -0
  134. package/dist/arabicNumberWords.d.ts.map +1 -0
  135. package/dist/arabicNumberWords.js +163 -0
  136. package/dist/arabicNumberWords.js.map +1 -0
  137. package/dist/arabicNumerals.d.ts +54 -0
  138. package/dist/arabicNumerals.d.ts.map +1 -0
  139. package/dist/arabicNumerals.js +143 -0
  140. package/dist/arabicNumerals.js.map +1 -0
  141. package/dist/bidi.d.ts +186 -0
  142. package/dist/bidi.d.ts.map +1 -0
  143. package/dist/bidi.js +851 -0
  144. package/dist/bidi.js.map +1 -0
  145. package/dist/bidiData.d.ts +13 -0
  146. package/dist/bidiData.d.ts.map +1 -0
  147. package/dist/bidiData.js +318 -0
  148. package/dist/bidiData.js.map +1 -0
  149. package/dist/canvas-backend/blockRender.d.ts.map +1 -1
  150. package/dist/canvas-backend/blockRender.js +58 -27
  151. package/dist/canvas-backend/blockRender.js.map +1 -1
  152. package/dist/canvas-backend/chip.d.ts.map +1 -1
  153. package/dist/canvas-backend/chip.js +16 -2
  154. package/dist/canvas-backend/chip.js.map +1 -1
  155. package/dist/canvas-backend/headerFooter.d.ts.map +1 -1
  156. package/dist/canvas-backend/headerFooter.js +7 -3
  157. package/dist/canvas-backend/headerFooter.js.map +1 -1
  158. package/dist/canvas-backend/index.d.ts.map +1 -1
  159. package/dist/canvas-backend/index.js +9 -4
  160. package/dist/canvas-backend/index.js.map +1 -1
  161. package/dist/canvas-backend/mirrorFrame.d.ts +38 -0
  162. package/dist/canvas-backend/mirrorFrame.d.ts.map +1 -0
  163. package/dist/canvas-backend/mirrorFrame.js +129 -0
  164. package/dist/canvas-backend/mirrorFrame.js.map +1 -0
  165. package/dist/canvas-backend/renderResourceBlock.d.ts.map +1 -1
  166. package/dist/canvas-backend/renderResourceBlock.js +16 -5
  167. package/dist/canvas-backend/renderResourceBlock.js.map +1 -1
  168. package/dist/canvas-backend/runDirection.d.ts +21 -0
  169. package/dist/canvas-backend/runDirection.d.ts.map +1 -0
  170. package/dist/canvas-backend/runDirection.js +46 -0
  171. package/dist/canvas-backend/runDirection.js.map +1 -0
  172. package/dist/canvas-backend/wordRuns.d.ts +49 -0
  173. package/dist/canvas-backend/wordRuns.d.ts.map +1 -0
  174. package/dist/canvas-backend/wordRuns.js +111 -0
  175. package/dist/canvas-backend/wordRuns.js.map +1 -0
  176. package/dist/columnClip.d.ts +4 -1
  177. package/dist/columnClip.d.ts.map +1 -1
  178. package/dist/columnClip.js +8 -3
  179. package/dist/columnClip.js.map +1 -1
  180. package/dist/configWarnings.d.ts +3 -1
  181. package/dist/configWarnings.d.ts.map +1 -1
  182. package/dist/configWarnings.js +59 -5
  183. package/dist/configWarnings.js.map +1 -1
  184. package/dist/defaults/bodyText.d.ts +28 -6
  185. package/dist/defaults/bodyText.d.ts.map +1 -1
  186. package/dist/defaults/bodyText.js +158 -30
  187. package/dist/defaults/bodyText.js.map +1 -1
  188. package/dist/defaults/calloutStyles.js +1 -1
  189. package/dist/defaults/calloutStyles.js.map +1 -1
  190. package/dist/defaults/captionStyle.js +5 -5
  191. package/dist/defaults/captionStyle.js.map +1 -1
  192. package/dist/defaults/folio.d.ts +4 -0
  193. package/dist/defaults/folio.d.ts.map +1 -1
  194. package/dist/defaults/folio.js +12 -1
  195. package/dist/defaults/folio.js.map +1 -1
  196. package/dist/defaults/footnotes.d.ts.map +1 -1
  197. package/dist/defaults/footnotes.js +12 -2
  198. package/dist/defaults/footnotes.js.map +1 -1
  199. package/dist/defaults/headerFooter.d.ts.map +1 -1
  200. package/dist/defaults/headerFooter.js +1 -0
  201. package/dist/defaults/headerFooter.js.map +1 -1
  202. package/dist/defaults/headingStyles.d.ts.map +1 -1
  203. package/dist/defaults/headingStyles.js +2 -1
  204. package/dist/defaults/headingStyles.js.map +1 -1
  205. package/dist/defaults/headings.d.ts.map +1 -1
  206. package/dist/defaults/headings.js +9 -2
  207. package/dist/defaults/headings.js.map +1 -1
  208. package/dist/defaults/index.d.ts +1 -1
  209. package/dist/defaults/index.d.ts.map +1 -1
  210. package/dist/defaults/index.js +7 -1
  211. package/dist/defaults/index.js.map +1 -1
  212. package/dist/defaults/indexConfig.d.ts +6 -2
  213. package/dist/defaults/indexConfig.d.ts.map +1 -1
  214. package/dist/defaults/indexConfig.js +25 -5
  215. package/dist/defaults/indexConfig.js.map +1 -1
  216. package/dist/defaults/page.d.ts +7 -4
  217. package/dist/defaults/page.d.ts.map +1 -1
  218. package/dist/defaults/page.js +10 -7
  219. package/dist/defaults/page.js.map +1 -1
  220. package/dist/defaults/paragraphStyles.js +2 -2
  221. package/dist/defaults/paragraphStyles.js.map +1 -1
  222. package/dist/defaults/parts.d.ts.map +1 -1
  223. package/dist/defaults/parts.js +2 -1
  224. package/dist/defaults/parts.js.map +1 -1
  225. package/dist/defaults/resourceTypes.d.ts +1 -1
  226. package/dist/defaults/resourceTypes.d.ts.map +1 -1
  227. package/dist/defaults/resourceTypes.js +10 -2
  228. package/dist/defaults/resourceTypes.js.map +1 -1
  229. package/dist/defaults/shared.d.ts +9 -0
  230. package/dist/defaults/shared.d.ts.map +1 -1
  231. package/dist/defaults/shared.js +15 -0
  232. package/dist/defaults/shared.js.map +1 -1
  233. package/dist/defaults/tableStyle.d.ts.map +1 -1
  234. package/dist/defaults/tableStyle.js +5 -1
  235. package/dist/defaults/tableStyle.js.map +1 -1
  236. package/dist/design/bidiText.d.ts +89 -0
  237. package/dist/design/bidiText.d.ts.map +1 -0
  238. package/dist/design/bidiText.js +165 -0
  239. package/dist/design/bidiText.js.map +1 -0
  240. package/dist/design/layout.d.ts +20 -0
  241. package/dist/design/layout.d.ts.map +1 -1
  242. package/dist/design/layout.js +46 -5
  243. package/dist/design/layout.js.map +1 -1
  244. package/dist/design/placeholders.d.ts +7 -1
  245. package/dist/design/placeholders.d.ts.map +1 -1
  246. package/dist/design/placeholders.js +6 -3
  247. package/dist/design/placeholders.js.map +1 -1
  248. package/dist/design/richText.d.ts +5 -2
  249. package/dist/design/richText.d.ts.map +1 -1
  250. package/dist/design/richText.js +35 -2
  251. package/dist/design/richText.js.map +1 -1
  252. package/dist/emphasisOverline.d.ts +27 -0
  253. package/dist/emphasisOverline.d.ts.map +1 -0
  254. package/dist/emphasisOverline.js +107 -0
  255. package/dist/emphasisOverline.js.map +1 -0
  256. package/dist/frontmatter.d.ts +25 -6
  257. package/dist/frontmatter.d.ts.map +1 -1
  258. package/dist/frontmatter.js +51 -10
  259. package/dist/frontmatter.js.map +1 -1
  260. package/dist/html-backend.d.ts +4 -1
  261. package/dist/html-backend.d.ts.map +1 -1
  262. package/dist/html-backend.js +363 -87
  263. package/dist/html-backend.js.map +1 -1
  264. package/dist/hyphenate.d.ts.map +1 -1
  265. package/dist/hyphenate.js +4 -1
  266. package/dist/hyphenate.js.map +1 -1
  267. package/dist/index.d.ts +11 -8
  268. package/dist/index.d.ts.map +1 -1
  269. package/dist/index.js +6 -4
  270. package/dist/index.js.map +1 -1
  271. package/dist/knuthPlass/breakpoints.d.ts.map +1 -1
  272. package/dist/knuthPlass/breakpoints.js +3 -0
  273. package/dist/knuthPlass/breakpoints.js.map +1 -1
  274. package/dist/knuthPlass/pretextAdapter.d.ts.map +1 -1
  275. package/dist/knuthPlass/pretextAdapter.js +9 -3
  276. package/dist/knuthPlass/pretextAdapter.js.map +1 -1
  277. package/dist/knuthPlass/richAdapter.d.ts +11 -0
  278. package/dist/knuthPlass/richAdapter.d.ts.map +1 -1
  279. package/dist/knuthPlass/richAdapter.js +11 -4
  280. package/dist/knuthPlass/richAdapter.js.map +1 -1
  281. package/dist/knuthPlass/tracking.d.ts +2 -1
  282. package/dist/knuthPlass/tracking.d.ts.map +1 -1
  283. package/dist/knuthPlass/tracking.js +5 -2
  284. package/dist/knuthPlass/tracking.js.map +1 -1
  285. package/dist/knuthPlass/types.d.ts +4 -0
  286. package/dist/knuthPlass/types.d.ts.map +1 -1
  287. package/dist/locale.d.ts +63 -9
  288. package/dist/locale.d.ts.map +1 -1
  289. package/dist/locale.js +129 -12
  290. package/dist/locale.js.map +1 -1
  291. package/dist/measure/bidiLines.d.ts +91 -0
  292. package/dist/measure/bidiLines.d.ts.map +1 -0
  293. package/dist/measure/bidiLines.js +293 -0
  294. package/dist/measure/bidiLines.js.map +1 -0
  295. package/dist/measure/cache.d.ts.map +1 -1
  296. package/dist/measure/cache.js +10 -4
  297. package/dist/measure/cache.js.map +1 -1
  298. package/dist/measure/joining.d.ts +39 -0
  299. package/dist/measure/joining.d.ts.map +1 -0
  300. package/dist/measure/joining.js +91 -0
  301. package/dist/measure/joining.js.map +1 -0
  302. package/dist/measure/joiningGroups.d.ts +7 -0
  303. package/dist/measure/joiningGroups.d.ts.map +1 -0
  304. package/dist/measure/joiningGroups.js +110 -0
  305. package/dist/measure/joiningGroups.js.map +1 -0
  306. package/dist/measure/kashida.d.ts +97 -0
  307. package/dist/measure/kashida.d.ts.map +1 -0
  308. package/dist/measure/kashida.js +285 -0
  309. package/dist/measure/kashida.js.map +1 -0
  310. package/dist/measure/kashidaPatterns.d.ts +109 -0
  311. package/dist/measure/kashidaPatterns.d.ts.map +1 -0
  312. package/dist/measure/kashidaPatterns.js +519 -0
  313. package/dist/measure/kashidaPatterns.js.map +1 -0
  314. package/dist/measure/links.d.ts.map +1 -1
  315. package/dist/measure/links.js +5 -2
  316. package/dist/measure/links.js.map +1 -1
  317. package/dist/measure/plain.d.ts.map +1 -1
  318. package/dist/measure/plain.js +31 -0
  319. package/dist/measure/plain.js.map +1 -1
  320. package/dist/measure/rich.d.ts +24 -0
  321. package/dist/measure/rich.d.ts.map +1 -1
  322. package/dist/measure/rich.js +250 -22
  323. package/dist/measure/rich.js.map +1 -1
  324. package/dist/measure/types.d.ts +14 -0
  325. package/dist/measure/types.d.ts.map +1 -1
  326. package/dist/measure/types.js.map +1 -1
  327. package/dist/numberWords.d.ts +17 -4
  328. package/dist/numberWords.d.ts.map +1 -1
  329. package/dist/numberWords.js +19 -13
  330. package/dist/numberWords.js.map +1 -1
  331. package/dist/numbering.d.ts +49 -11
  332. package/dist/numbering.d.ts.map +1 -1
  333. package/dist/numbering.js +117 -21
  334. package/dist/numbering.js.map +1 -1
  335. package/dist/parse/annotations.d.ts +6 -3
  336. package/dist/parse/annotations.d.ts.map +1 -1
  337. package/dist/parse/annotations.js +31 -7
  338. package/dist/parse/annotations.js.map +1 -1
  339. package/dist/parse/attrs.d.ts +3 -3
  340. package/dist/parse/attrs.d.ts.map +1 -1
  341. package/dist/parse/attrs.js +5 -4
  342. package/dist/parse/attrs.js.map +1 -1
  343. package/dist/parse/blockParser.d.ts.map +1 -1
  344. package/dist/parse/blockParser.js +158 -14
  345. package/dist/parse/blockParser.js.map +1 -1
  346. package/dist/parse/index.d.ts +1 -1
  347. package/dist/parse/index.d.ts.map +1 -1
  348. package/dist/parse/index.js.map +1 -1
  349. package/dist/parse/inlineFormatting.d.ts.map +1 -1
  350. package/dist/parse/inlineFormatting.js +5 -4
  351. package/dist/parse/inlineFormatting.js.map +1 -1
  352. package/dist/parse/types.d.ts +63 -1
  353. package/dist/parse/types.d.ts.map +1 -1
  354. package/dist/pipeline/build.d.ts.map +1 -1
  355. package/dist/pipeline/build.js +161 -43
  356. package/dist/pipeline/build.js.map +1 -1
  357. package/dist/pipeline/buildBlockKind.d.ts +2 -0
  358. package/dist/pipeline/buildBlockKind.d.ts.map +1 -1
  359. package/dist/pipeline/buildBlockKind.js +67 -2
  360. package/dist/pipeline/buildBlockKind.js.map +1 -1
  361. package/dist/pipeline/buildHelpers.d.ts +22 -1
  362. package/dist/pipeline/buildHelpers.d.ts.map +1 -1
  363. package/dist/pipeline/buildHelpers.js +55 -5
  364. package/dist/pipeline/buildHelpers.js.map +1 -1
  365. package/dist/pipeline/calloutLayout.d.ts +6 -1
  366. package/dist/pipeline/calloutLayout.d.ts.map +1 -1
  367. package/dist/pipeline/calloutLayout.js +63 -18
  368. package/dist/pipeline/calloutLayout.js.map +1 -1
  369. package/dist/pipeline/citations.d.ts +2 -1
  370. package/dist/pipeline/citations.d.ts.map +1 -1
  371. package/dist/pipeline/citations.js +29 -9
  372. package/dist/pipeline/citations.js.map +1 -1
  373. package/dist/pipeline/cjkGrid.d.ts +3 -2
  374. package/dist/pipeline/cjkGrid.d.ts.map +1 -1
  375. package/dist/pipeline/cjkGrid.js +3 -2
  376. package/dist/pipeline/cjkGrid.js.map +1 -1
  377. package/dist/pipeline/config.d.ts +13 -1
  378. package/dist/pipeline/config.d.ts.map +1 -1
  379. package/dist/pipeline/config.js +32 -3
  380. package/dist/pipeline/config.js.map +1 -1
  381. package/dist/pipeline/contentWarnings.d.ts +10 -0
  382. package/dist/pipeline/contentWarnings.d.ts.map +1 -1
  383. package/dist/pipeline/contentWarnings.js +88 -0
  384. package/dist/pipeline/contentWarnings.js.map +1 -1
  385. package/dist/pipeline/continuation.d.ts.map +1 -1
  386. package/dist/pipeline/continuation.js +1 -1
  387. package/dist/pipeline/continuation.js.map +1 -1
  388. package/dist/pipeline/crossRefs.d.ts.map +1 -1
  389. package/dist/pipeline/crossRefs.js +2 -0
  390. package/dist/pipeline/crossRefs.js.map +1 -1
  391. package/dist/pipeline/floatPlacement.d.ts.map +1 -1
  392. package/dist/pipeline/floatPlacement.js +2 -1
  393. package/dist/pipeline/floatPlacement.js.map +1 -1
  394. package/dist/pipeline/footnotes.d.ts +13 -5
  395. package/dist/pipeline/footnotes.d.ts.map +1 -1
  396. package/dist/pipeline/footnotes.js +19 -8
  397. package/dist/pipeline/footnotes.js.map +1 -1
  398. package/dist/pipeline/headerFooter.d.ts +4 -0
  399. package/dist/pipeline/headerFooter.d.ts.map +1 -1
  400. package/dist/pipeline/headerFooter.js +41 -13
  401. package/dist/pipeline/headerFooter.js.map +1 -1
  402. package/dist/pipeline/headingDesignCuts.d.ts +1 -1
  403. package/dist/pipeline/headingDesignCuts.d.ts.map +1 -1
  404. package/dist/pipeline/headingDesignCuts.js +2 -1
  405. package/dist/pipeline/headingDesignCuts.js.map +1 -1
  406. package/dist/pipeline/headingStyles.d.ts +10 -0
  407. package/dist/pipeline/headingStyles.d.ts.map +1 -1
  408. package/dist/pipeline/headingStyles.js +46 -0
  409. package/dist/pipeline/headingStyles.js.map +1 -1
  410. package/dist/pipeline/indexDirective.d.ts.map +1 -1
  411. package/dist/pipeline/indexDirective.js +33 -6
  412. package/dist/pipeline/indexDirective.js.map +1 -1
  413. package/dist/pipeline/indexGroups.d.ts +23 -1
  414. package/dist/pipeline/indexGroups.d.ts.map +1 -1
  415. package/dist/pipeline/indexGroups.js +50 -1
  416. package/dist/pipeline/indexGroups.js.map +1 -1
  417. package/dist/pipeline/lists.d.ts +16 -4
  418. package/dist/pipeline/lists.d.ts.map +1 -1
  419. package/dist/pipeline/lists.js +51 -12
  420. package/dist/pipeline/lists.js.map +1 -1
  421. package/dist/pipeline/measureContentBlock.d.ts +5 -0
  422. package/dist/pipeline/measureContentBlock.d.ts.map +1 -1
  423. package/dist/pipeline/measureContentBlock.js +63 -4
  424. package/dist/pipeline/measureContentBlock.js.map +1 -1
  425. package/dist/pipeline/mirrorFrame.d.ts +37 -0
  426. package/dist/pipeline/mirrorFrame.d.ts.map +1 -0
  427. package/dist/pipeline/mirrorFrame.js +143 -0
  428. package/dist/pipeline/mirrorFrame.js.map +1 -0
  429. package/dist/pipeline/outline.d.ts +2 -2
  430. package/dist/pipeline/outline.d.ts.map +1 -1
  431. package/dist/pipeline/outline.js +33 -6
  432. package/dist/pipeline/outline.js.map +1 -1
  433. package/dist/pipeline/paragraphContainers.d.ts +5 -0
  434. package/dist/pipeline/paragraphContainers.d.ts.map +1 -1
  435. package/dist/pipeline/paragraphContainers.js +12 -0
  436. package/dist/pipeline/paragraphContainers.js.map +1 -1
  437. package/dist/pipeline/parts.d.ts +1 -1
  438. package/dist/pipeline/parts.d.ts.map +1 -1
  439. package/dist/pipeline/parts.js +3 -2
  440. package/dist/pipeline/parts.js.map +1 -1
  441. package/dist/pipeline/placeholders.d.ts +13 -6
  442. package/dist/pipeline/placeholders.d.ts.map +1 -1
  443. package/dist/pipeline/placeholders.js +15 -11
  444. package/dist/pipeline/placeholders.js.map +1 -1
  445. package/dist/pipeline/placement.d.ts +3 -2
  446. package/dist/pipeline/placement.d.ts.map +1 -1
  447. package/dist/pipeline/placement.js +18 -6
  448. package/dist/pipeline/placement.js.map +1 -1
  449. package/dist/pipeline/resourceLayout.d.ts.map +1 -1
  450. package/dist/pipeline/resourceLayout.js +70 -7
  451. package/dist/pipeline/resourceLayout.js.map +1 -1
  452. package/dist/pipeline/resourceNumbering.d.ts +5 -3
  453. package/dist/pipeline/resourceNumbering.d.ts.map +1 -1
  454. package/dist/pipeline/resourceNumbering.js +11 -8
  455. package/dist/pipeline/resourceNumbering.js.map +1 -1
  456. package/dist/pipeline/styles.d.ts +6 -1
  457. package/dist/pipeline/styles.d.ts.map +1 -1
  458. package/dist/pipeline/styles.js +44 -14
  459. package/dist/pipeline/styles.js.map +1 -1
  460. package/dist/pipeline/tashkil.d.ts +27 -0
  461. package/dist/pipeline/tashkil.d.ts.map +1 -0
  462. package/dist/pipeline/tashkil.js +161 -0
  463. package/dist/pipeline/tashkil.js.map +1 -0
  464. package/dist/pipeline/toc.d.ts +12 -0
  465. package/dist/pipeline/toc.d.ts.map +1 -1
  466. package/dist/pipeline/toc.js +64 -4
  467. package/dist/pipeline/toc.js.map +1 -1
  468. package/dist/pipeline/verse.d.ts +65 -0
  469. package/dist/pipeline/verse.d.ts.map +1 -0
  470. package/dist/pipeline/verse.js +252 -0
  471. package/dist/pipeline/verse.js.map +1 -0
  472. package/dist/pipeline/verticalMetrics.d.ts +1 -1
  473. package/dist/pipeline/verticalMetrics.d.ts.map +1 -1
  474. package/dist/pipeline/verticalMetrics.js +7 -5
  475. package/dist/pipeline/verticalMetrics.js.map +1 -1
  476. package/dist/table/model.d.ts +4 -3
  477. package/dist/table/model.d.ts.map +1 -1
  478. package/dist/table/model.js.map +1 -1
  479. package/dist/types.d.ts +286 -36
  480. package/dist/types.d.ts.map +1 -1
  481. package/dist/uprightArabic.d.ts +39 -0
  482. package/dist/uprightArabic.d.ts.map +1 -0
  483. package/dist/uprightArabic.js +105 -0
  484. package/dist/uprightArabic.js.map +1 -0
  485. package/dist/vdt.d.ts +276 -11
  486. package/dist/vdt.d.ts.map +1 -1
  487. package/dist/vdt.js +46 -9
  488. package/dist/vdt.js.map +1 -1
  489. package/package.json +1 -1
@@ -1,9 +1,9 @@
1
1
  import { plainTitleBreaks } from '../parse/inlineFormatting';
2
2
  import { dimensionToPx } from '../units';
3
- import { createVDTDocument, createVDTBlock, createBoundingBox, } from '../vdt';
3
+ import { createVDTDocument, createVDTBlock, createBoundingBox, pageIsMirrored, pageIsVertical, } from '../vdt';
4
4
  import { anchorBox } from '../design/layout';
5
5
  import { parseMarkdownMemo, spaceDirectiveLines } from '../parse';
6
- import { buildPageLabels, computeHeadingNumbering, parseNumberFormat, } from '../numbering';
6
+ import { buildPageLabels, computeHeadingNumbering, documentNumeralStyle, parseNumberFormat, } from '../numbering';
7
7
  import { extractFrontmatter, normalizeMetadata } from '../frontmatter';
8
8
  import { collectConfigWarnings } from '../configWarnings';
9
9
  import { initHyphenator } from '../measure';
@@ -11,8 +11,12 @@ import { getCjkLineBreak, setCjkLineBreak } from '../measure/cjkClasses';
11
11
  import { cjkCompositionOf, getCjkComposition, setCjkComposition } from '../measure/cjkPunctuation';
12
12
  import { getMeasureRegion, getMeasureUprightDigits, getMeasureWritingMode, setMeasureUprightDigits, setMeasureWritingMode } from '../measure/vertical';
13
13
  import { stampCentralBaselines } from './verticalMetrics';
14
- import { resolveAllConfig, computeBaselineGrid, resolvedLocale } from './config';
15
- import { createHeadingLevelResolver, deriveSectionGeometryConfig, sectionWritingMode, deriveSectionMeasureContext, headingIsHidden, headingIsNumbered, headingMarksFor, headingStyleOf, planHeadingSections, } from './headingStyles';
14
+ import { orientLinesToFrames } from './mirrorFrame';
15
+ import { verseMarginTopPx } from './buildBlockKind';
16
+ import { resolveAllConfig, computeBaselineGrid, resolvedDirection, resolvedLocale } from './config';
17
+ import { asciiDigits } from '../arabicNumerals';
18
+ import { getMeasureDirection, setMeasureDirection } from '../measure/bidiLines';
19
+ import { createHeadingLevelResolver, deriveSectionGeometryConfig, sectionWritingMode, deriveSectionMeasureContext, headingIsHidden, headingIsNumbered, headingMarksFor, headingStyleOf, numberTitlesFor, planHeadingSections, } from './headingStyles';
16
20
  import { locateAnchors } from './anchors';
17
21
  import { applyCitations, citationLocale, processCitations, withBibliographyStyle } from './citations';
18
22
  import { bookCitationContexts, needsCitationContext } from '../citations/context';
@@ -21,13 +25,13 @@ import { anchorOutline, computeOutline, hasIndexDirective, hasTocDirective, head
21
25
  import { expandTocDirectives } from './toc';
22
26
  import { expandIndexDirectives, locateIndexMarks } from './indexDirective';
23
27
  import { resolveBodyStyle, resolveBlockquoteStyle, resolveParagraphStyle } from './styles';
24
- import { computeLevelIndentsPx, computeOrderedLevelIndentsPx, computeOrderedListRunMetrics, listBulletPosition, listItemGapPx, listItemSpacingPx, } from './lists';
28
+ import { computeLevelIndentsPx, computeOrderedLevelIndentsPx, computeOrderedListRunMetrics, listBulletPosition, listItemGapPx, listItemSpacingPx, mirrorListMarker, } from './lists';
25
29
  import { resetLinePositions, createPageWithColumns, currentColumn, advanceToNextColumn, advanceToNextPageBoundary, enforcePageParity, placeBlockInColumn, placeAtomicBlock, createPartPage, pageHasContent, sideColumnOf, sideColumns, sideUsedBottom, pageIsOccupied, bandColumns, currentBand, isBandLevel, bandUsedBottom, closeBandAndInsertSpan, pageLayoutOf, } from './placement';
26
30
  import { chooseParagraphSplit } from './orphanWidow';
27
- import { applyStyleAttrs, computePageMetrics, pageMirrored, sheetRectToFlow, isMarkerBlock, nextNonMarkerBlock, spaceLinesAfter, prevNonMarkerBlock, rollbackTrailingBlocks, } from './buildHelpers';
31
+ import { applyStyleAttrs, computePageMetrics, flowPageMirrored, sheetRectToFlow, isMarkerBlock, nextNonMarkerBlock, spaceLinesAfter, prevNonMarkerBlock, rollbackTrailingBlocks, } from './buildHelpers';
28
32
  import { measureContentBlock } from './measureContentBlock';
29
- import { planParagraphContainers } from './paragraphContainers';
30
- import { appendChapterEndNotes, footnoteIdsOfLines, footnoteParagraphStyle, noteContentBlock, numberFootnotes, numberFootnotesByPlacement, sameFootnoteNumbers, splitFootnoteDefinitions, withFootnoteStyle, } from './footnotes';
33
+ import { paragraphStyleIdOf, planParagraphContainers } from './paragraphContainers';
34
+ import { appendChapterEndNotes, footnoteIdsOfLines, footnoteParagraphStyle, noteContentBlock, noteNumberPositionOf, numberFootnotes, numberFootnotesByPlacement, sameFootnoteNumbers, splitFootnoteDefinitions, withFootnoteStyle, } from './footnotes';
31
35
  import { planParts, derivePartMeasureContext } from './parts';
32
36
  import { layoutCallout, offsetCalloutToAbsolute, pickCalloutStyle, planCallouts, resolveCalloutAttrs, } from './calloutLayout';
33
37
  import { layoutResourceBlock, planTableSlice } from './resourceLayout';
@@ -42,8 +46,12 @@ import { chapterNumberCounter, leadingBoldText } from './placeholders';
42
46
  import { proposeBalanceLines, collectColumnGaps, firstDivergentColumn, gapLinesIn, boxRoomIn, boxLeverKeys, pageSegments, MAX_BALANCING_PASSES, MAX_BALANCING_PASSES_PER_DOCUMENT, balanceKey } from './columnBalancing';
43
47
  import { applyBandCap, uncapBand, columnBottom, bandCapLines, bandTop, bareBandTop, resolveBandCapsGen, drainPasses, resolveTrailingCapsGen, bandCapLinesAroundZone, } from './bandCaps';
44
48
  import { raggedLooseLines } from './raggedLines';
45
- import { cjkLooseLineWarnings, collectContentWarnings, locateContentWarnings } from './contentWarnings';
49
+ import { cjkLooseLineWarnings, collectContentWarnings, joiningLetterSpacingWarnings, locateContentWarnings, wordOverflowWarnings } from './contentWarnings';
50
+ import { mostlyJoiningScript } from '../measure/joining';
46
51
  import { annotateDocument } from '../cjkMarks';
52
+ import { annotateArabicMarks } from '../arabicMarks';
53
+ import { tashkilFor } from './tashkil';
54
+ import { overlineEmphasis } from '../emphasisOverline';
47
55
  import { withBookTitleBrackets } from './annotations';
48
56
  import { paperByBlock, stampPagePaper } from './paper';
49
57
  /** Tolerance for "does this block fit" checks against a column's free
@@ -70,7 +78,7 @@ export class BuildCancelledError extends Error {
70
78
  * fed the same fields the placed heading blocks will carry. */
71
79
  function chapterNumbersOfContent(blocks, resolved, prefixes, values, ordinalOffset) {
72
80
  const numberless = new Set(resolved.headingStyles.filter((s) => s.numberingTemplate === '').map((s) => s.id));
73
- const next = chapterNumberCounter(ordinalOffset, (b) => b.styleId !== undefined && numberless.has(b.styleId));
81
+ const next = chapterNumberCounter(ordinalOffset, (b) => b.styleId !== undefined && numberless.has(b.styleId), resolved.numerals);
74
82
  let current = '';
75
83
  return blocks.map((b, i) => {
76
84
  if (b.type === 'heading' && (b.level ?? 1) === 1) {
@@ -119,11 +127,15 @@ function measureLooseParagraph(rawBlock, blockIdx, columnWidth, ctx, styleOverri
119
127
  // The breaker's optimum, before any runt fix (a looseness of 0 skips it).
120
128
  const optimum = measureContentBlock(rawBlock, blockIdx, columnWidth, ctx, { styleOverride, looseness: 0 });
121
129
  const looseness = optimum ? target - optimum.measured.lines.length : extraLines;
130
+ // A paragraph mostly in a joining script (Arabic…) is not tracked: its
131
+ // words take no letter-spacing (`measure/joining.ts`), so only the first
132
+ // rung, word spacing alone, can gain it the line.
133
+ const ladder = trackingLadder.length > 1 && mostlyJoiningScript(rawBlock.text) ? trackingLadder.slice(0, 1) : trackingLadder;
122
134
  const maxWordSpacing = ctx.resolved.bodyText.maxWordSpacing + 1e-9;
123
135
  // A CJK line spread past its tracking cap (`cjkLoose`) is past the
124
136
  // limit too.
125
137
  const withinLimit = (lines) => lines.every((l) => l.isLastLine || ((l.justifiedSpaceRatio === undefined || l.justifiedSpaceRatio <= maxWordSpacing) && !l.cjkLoose));
126
- for (const tracking of trackingLadder) {
138
+ for (const tracking of ladder) {
127
139
  const loose = measureContentBlock(rawBlock, blockIdx, columnWidth, ctx, {
128
140
  styleOverride,
129
141
  looseness,
@@ -160,6 +172,7 @@ export function buildDocumentPass(content, config, cache, options, hints = {}) {
160
172
  const writingMode = getMeasureWritingMode();
161
173
  const region = getMeasureRegion();
162
174
  const uprightDigits = getMeasureUprightDigits();
175
+ const direction = getMeasureDirection();
163
176
  try {
164
177
  return placeDocumentPass(content, config, cache, options, hints);
165
178
  }
@@ -168,6 +181,7 @@ export function buildDocumentPass(content, config, cache, options, hints = {}) {
168
181
  setCjkComposition(composition);
169
182
  setMeasureWritingMode(writingMode, region);
170
183
  setMeasureUprightDigits(uprightDigits);
184
+ setMeasureDirection(direction);
171
185
  }
172
186
  }
173
187
  function placeDocumentPass(content, config, cache, options, hints) {
@@ -215,6 +229,9 @@ function placeDocumentPass(content, config, cache, options, hints) {
215
229
  setMeasureWritingMode(resolved.layout.writingMode, resolved.cjk.region);
216
230
  // Short numbers set in one upright cell (`cjk.uprightDigits`).
217
231
  setMeasureUprightDigits(resolved.cjk.uprightDigits);
232
+ // Paragraphs run in the document's direction unless they set their own
233
+ // (`{dir=…}`): an Arabic book's captions, cells and notes too.
234
+ setMeasureDirection(resolvedDirection(resolved));
218
235
  // Compute baseline grid
219
236
  const baselineGrid = computeBaselineGrid(resolved);
220
237
  // Create document
@@ -256,7 +273,10 @@ function placeDocumentPass(content, config, cache, options, hints) {
256
273
  bleed: sheetRectToFlow(pageMetrics.physical.bleedBox, pageWidthPx),
257
274
  upright: true,
258
275
  };
259
- const designFramesOn = (page) => (page?.flow ? verticalFrames : physicalFrames);
276
+ // A right-to-left page's flow is the sheet mirrored, and the trim and
277
+ // bleed boxes, centred on the sheet, are their own mirror images: the
278
+ // physical frames serve it unchanged.
279
+ const designFramesOn = (page) => (page && pageIsVertical(page) ? verticalFrames : physicalFrames);
260
280
  doc.trimOffset = trimOffset;
261
281
  // A right-bound book (`page.binding`): hosts show its spreads mirrored.
262
282
  if (resolved.page.binding === 'right')
@@ -279,7 +299,9 @@ function placeDocumentPass(content, config, cache, options, hints) {
279
299
  // Citations (#268): formatted against the book's references (or set as
280
300
  // notes under a note style) before the notes leave the flow; the
281
301
  // bibliography takes `:::bibliography`'s place or follows the text.
282
- const parsedBody = headingMarksFor(parseMarkdownMemo(markdownBody), resolved);
302
+ // Arabic vowel marks out of the text when `bodyText.tashkil` says so
303
+ // (#376), for the outline and the layout alike.
304
+ const parsedBody = numberTitlesFor(headingMarksFor(tashkilFor(parseMarkdownMemo(markdownBody), resolved.bodyText.tashkil), resolved), resolved);
283
305
  const citationContext = content.citations
284
306
  ?? (needsCitationContext(parsedBody, frontmatterMeta) ? bookCitationContexts([{ metadata: frontmatterMeta, blocks: parsedBody }])[0] : undefined);
285
307
  const citationsApplied = citationContext
@@ -290,7 +312,8 @@ function placeDocumentPass(content, config, cache, options, hints) {
290
312
  // Numbered by page or column (`numbering: 'page'`), a note takes the
291
313
  // number the previous build gave it where it landed; the first build
292
314
  // numbers by chapter (see `buildDocumentNumbered`).
293
- const footnoteNumbering = numberFootnotes(footnoteSplit.blocks, resolved.footnotes.numbering, resolved.footnotes.numbering === 'document' ? Math.max(0, Math.floor(continuation?.footnoteNumber ?? 0)) : 0, resolved.footnotes.numberFormat);
315
+ // A decimal note number is written in the document's digits.
316
+ const footnoteNumbering = numberFootnotes(footnoteSplit.blocks, resolved.footnotes.numbering, resolved.footnotes.numbering === 'document' ? Math.max(0, Math.floor(continuation?.footnoteNumber ?? 0)) : 0, documentNumeralStyle(resolved.footnotes.numberFormat, resolved.numerals), resolved.footnotes.markerTemplate);
294
317
  if (hints.footnoteNumbers) {
295
318
  for (const [id, number] of hints.footnoteNumbers) {
296
319
  if (footnoteNumbering.numbers.has(id))
@@ -299,7 +322,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
299
322
  }
300
323
  const chapterEndNotes = resolved.footnotes.placement === 'chapterEnd' && footnoteNumbering.numbers.size > 0;
301
324
  const parsedBlocks = chapterEndNotes
302
- ? appendChapterEndNotes(footnoteSplit.blocks, footnoteNumbering, footnoteDefs, resolved.footnotes.markerPosition)
325
+ ? appendChapterEndNotes(footnoteSplit.blocks, footnoteNumbering, footnoteDefs, noteNumberPositionOf(resolved.footnotes))
303
326
  : footnoteSplit.blocks;
304
327
  const headingStart = continuation?.headings;
305
328
  // `:::toc` expands into the entries of the book's outline — the one the
@@ -334,7 +357,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
334
357
  const resourceTypes = config?.resourceTypes ?? defaultResourceTypes(documentLocale(config));
335
358
  const resources = content.resources ?? [];
336
359
  const headingContext = computeHeadingContext(contentBlocks, headingStart, isNumbered);
337
- const resourceNumbering = computeResourceNumbering(contentBlocks, resourceTypes, resources, headingContext, continuation ? { counters: continuation.resourceCounters, numbered: continuation.resourceNumbers } : undefined);
360
+ const resourceNumbering = computeResourceNumbering(contentBlocks, resourceTypes, resources, headingContext, continuation ? { counters: continuation.resourceCounters, numbered: continuation.resourceNumbers } : undefined, resolved.numerals);
338
361
  // Lookups threaded into block-kind resolution + measurement.
339
362
  const resourceById = new Map();
340
363
  for (const r of resources)
@@ -666,11 +689,17 @@ function placeDocumentPass(content, config, cache, options, hints) {
666
689
  /** The rotation of a pending float on a band whose columns keep `avail`
667
690
  * px: the upright frame is as long as the grid multiple within that
668
691
  * room, less the float gap, so the band it takes is `avail` at most. */
669
- const rotationFor = (f, avail, page) => page?.flow
692
+ const rotationFor = (f, avail, page) => page && pageIsVertical(page)
670
693
  ? uprightOn(page)
671
694
  : f.rotate
672
- ? { direction: f.rotate, length: Math.max(1, Math.floor((avail + 0.01) / baselineGrid) * baselineGrid - floatGapPx) }
695
+ ? { direction: flowRotation(f.rotate, page), length: Math.max(1, Math.floor((avail + 0.01) / baselineGrid) * baselineGrid - floatGapPx) }
673
696
  : undefined;
697
+ /** `placement.rotate` keeps its meaning on the sheet: `'ccw'` turns the
698
+ * picture's top to the sheet's left. A right-to-left page's flow is the
699
+ * sheet mirrored, where the same turn on the sheet is the opposite one,
700
+ * so the flow turns the block the other way (the renderers' frame and
701
+ * their counter-flip of the picture compose back to the asked turn). */
702
+ const flowRotation = (rotate, page) => page && pageIsMirrored(page) ? (rotate === 'ccw' ? 'cw' : 'ccw') : rotate;
674
703
  /** A resource on a vertical page stands upright: its frame at most as
675
704
  * wide as the page's flow is tall (the content area's width on the
676
705
  * sheet), the float gap kept. */
@@ -802,7 +831,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
802
831
  /** Whether a rotated float on `page` sits flush to the band's right edge:
803
832
  * with mirrored margins the spine of a page whose spine is on its right
804
833
  * (a verso of a left-bound book, a recto of a right-bound one). */
805
- const rotatedFlushEnd = (page) => pageMirrored(resolved, page.index, pageIndexOffset);
834
+ const rotatedFlushEnd = (page) => flowPageMirrored(resolved, page, pageIndexOffset);
806
835
  /** Float bands reserved per column in this pass (the fresh-page flush
807
836
  * sends single-column floats to the least reserved column). */
808
837
  const floatReserved = new Map();
@@ -951,7 +980,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
951
980
  const slice = sliceOf(f);
952
981
  // A side float never turns: it stacks upright in the side column (on a
953
982
  // vertical page it is counter-rotated to stand upright there too).
954
- const rotated = side && !page.flow ? undefined : rotationFor(f, Math.min(...targetCols.map((c) => c.availableHeight)), page);
983
+ const rotated = side && !pageIsVertical(page) ? undefined : rotationFor(f, Math.min(...targetCols.map((c) => c.availableHeight)), page);
955
984
  // The caption beside the figure, in the band's side column.
956
985
  let aside;
957
986
  let sideCol;
@@ -1573,6 +1602,9 @@ function placeDocumentPass(content, config, cache, options, hints) {
1573
1602
  /** Boxes that left the flow this pass (side column, float band, fixed),
1574
1603
  * by the content index of their opening marker (see `leftFlow`). */
1575
1604
  const calloutsOutOfFlow = new Set();
1605
+ /** Blocks whose style tracks text of a joining script, which is set
1606
+ * untracked (see `BlockMeasureContext.joiningLetterSpacing`). */
1607
+ const joiningLetterSpacing = new Set();
1576
1608
  // Everything per-block measurement needs that is constant for this pass.
1577
1609
  const measureCtx = {
1578
1610
  resolved,
@@ -1596,6 +1628,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
1596
1628
  resourceNumbering,
1597
1629
  floatedIds,
1598
1630
  leftFlow: calloutsOutOfFlow,
1631
+ joiningLetterSpacing,
1599
1632
  ...(footnoteNumbering.numbers.size > 0 ? { footnoteNumbers: footnoteNumbering.numbers } : {}),
1600
1633
  ...(anchorRefContext ? { anchorRefs: anchorRefContext } : {}),
1601
1634
  };
@@ -1625,7 +1658,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
1625
1658
  let m = noteMeasures.get(key);
1626
1659
  if (m === undefined) {
1627
1660
  const number = footnoteNumbering.numbers.get(id) ?? '?';
1628
- m = measureContentBlock(noteContentBlock(footnoteDefs.get(id), id, number, resolved.footnotes.markerPosition), 0, width, measureCtx, { styleOverride: noteStyle });
1661
+ m = measureContentBlock(noteContentBlock(footnoteDefs.get(id), id, number, noteNumberPositionOf(resolved.footnotes)), 0, width, measureCtx, { styleOverride: noteStyle });
1629
1662
  noteMeasures.set(key, m);
1630
1663
  }
1631
1664
  return m;
@@ -1858,6 +1891,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
1858
1891
  blk.lines = resetLinePositions(raggedLooseLines(m.measured.lines, noteStyle.textAlign), noteStyle.lineHeightPx).map((line) => ({
1859
1892
  ...line,
1860
1893
  bbox: createBoundingBox(line.bbox.x + x, line.bbox.y + y, line.bbox.width, line.bbox.height),
1894
+ ...(line.measure ? { measure: { x: line.measure.x + x, width: line.measure.width } } : {}),
1861
1895
  baseline: line.baseline + y,
1862
1896
  }));
1863
1897
  const h = blk.lines.length * noteStyle.lineHeightPx;
@@ -1866,6 +1900,8 @@ function placeDocumentPass(content, config, cache, options, hints) {
1866
1900
  blk.columnIndex = col.index;
1867
1901
  blk.contentIndex = noteAnchor.get(id) ?? 0;
1868
1902
  blk.footnoteNote = id;
1903
+ if (m.contentBlock.direction !== undefined && m.contentBlock.direction !== resolvedDirection(resolved))
1904
+ blk.direction = m.contentBlock.direction;
1869
1905
  blk.dirty = false;
1870
1906
  blk.snappedToGrid = false;
1871
1907
  if (blk.lines.length > 0) {
@@ -1943,6 +1979,19 @@ function placeDocumentPass(content, config, cache, options, hints) {
1943
1979
  blk.footnoteNote = raw.footnoteNote;
1944
1980
  if (raw.bibEntry !== undefined)
1945
1981
  blk.bibEntry = raw.bibEntry;
1982
+ // Metadata for other renditions: the paragraph style the text is set
1983
+ // in, the level of an index entry.
1984
+ const paragraphStyleId = paragraphStyleIdOf(raw, blk.contentIndex !== undefined ? paragraphContainers.byBlock[blk.contentIndex] : undefined, resolved);
1985
+ if (paragraphStyleId !== undefined)
1986
+ blk.paragraphStyleId = paragraphStyleId;
1987
+ if (raw.index)
1988
+ blk.indexLevel = raw.index.level;
1989
+ // A text block whose direction opposes its page frame's, which runs in
1990
+ // the document's direction (a right-to-left document's pages are
1991
+ // mirrored, #370): an Arabic quotation in an English book, an English
1992
+ // one in an Arabic book. Its lines carry their span (`VDTLine.measure`).
1993
+ if (blk.type !== 'resource' && raw.direction !== undefined && raw.direction !== resolvedDirection(resolved))
1994
+ blk.direction = raw.direction;
1946
1995
  if (raw.toc?.kind === 'entry') {
1947
1996
  blk.tocEntry = raw.toc.pageIndex !== undefined ? { pageIndex: raw.toc.pageIndex } : {};
1948
1997
  }
@@ -2529,6 +2578,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
2529
2578
  return layoutCallout({
2530
2579
  style,
2531
2580
  attrs: plan.attrs,
2581
+ ...(contentBlocks[startIdx]?.direction ? { direction: contentBlocks[startIdx].direction } : {}),
2532
2582
  continuation,
2533
2583
  // Any range short of the box's end is a fragment that goes on.
2534
2584
  ...(to.child < children.length || to.line > 0 ? { continues: true } : {}),
@@ -2553,8 +2603,9 @@ function placeDocumentPass(content, config, cache, options, hints) {
2553
2603
  /** Whether a page swaps its mirrored margins (a verso of a left-bound
2554
2604
  * book, a recto of a right-bound one: an `'outer'` corner icon hangs on
2555
2605
  * the left there). A vertical page has no outer side: a box's outer
2556
- * corner stays where the style puts it. */
2557
- const mirroredOf = (page) => !page.flow && pageMirrored(resolved, page.index, pageIndexOffset);
2606
+ * corner stays where the style puts it. A right-to-left page answers in
2607
+ * its flow (`flowPageMirrored`), where its spine side is turned over. */
2608
+ const mirroredOf = (page) => !pageIsVertical(page) && flowPageMirrored(resolved, page, pageIndexOffset);
2558
2609
  /** Where a block's paint ends: its last line's foot (a list tail's box
2559
2610
  * bakes its bottom margin in and may reach past a cut with every line
2560
2611
  * inside it), else its box's. */
@@ -2819,7 +2870,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
2819
2870
  const width = page.contentArea.width;
2820
2871
  const slice = sliceOf(f);
2821
2872
  // On a vertical page the figure stands upright.
2822
- const upright = page.flow ? uprightOn(page) : undefined;
2873
+ const upright = pageIsVertical(page) ? uprightOn(page) : undefined;
2823
2874
  const measure = measureFloat(f.resourceId, width, slice, upright);
2824
2875
  if (!measure) {
2825
2876
  i++;
@@ -3718,7 +3769,10 @@ function placeDocumentPass(content, config, cache, options, hints) {
3718
3769
  while (idx < contentBlocks.length && isMarkerBlock(contentBlocks[idx]))
3719
3770
  idx++;
3720
3771
  const raw = contentBlocks[idx];
3721
- if (!raw || raw.type !== 'listItem')
3772
+ // A poem (#378) after its introducer: its first bayts, by the
3773
+ // paragraph rules.
3774
+ const verse = raw?.verse !== undefined;
3775
+ if (!raw || (raw.type !== 'listItem' && !verse))
3722
3776
  return true;
3723
3777
  const item = measureContentBlock(raw, idx, width, ctx);
3724
3778
  if (!item)
@@ -3731,10 +3785,10 @@ function placeDocumentPass(content, config, cache, options, hints) {
3731
3785
  return false;
3732
3786
  const body = resolved.bodyText;
3733
3787
  return chooseParagraphSplit(lines, fit, {
3734
- avoidOrphans: body.avoidOrphans && body.avoidOrphansInLists,
3788
+ avoidOrphans: body.avoidOrphans && (verse || body.avoidOrphansInLists),
3735
3789
  orphanMinLines: body.orphanMinLines,
3736
3790
  orphanPenalty: body.orphanPenalty,
3737
- avoidWidows: body.avoidWidows && body.avoidWidowsInLists,
3791
+ avoidWidows: body.avoidWidows && (verse || body.avoidWidowsInLists),
3738
3792
  widowMinLines: body.widowMinLines,
3739
3793
  widowPenalty: body.widowPenalty,
3740
3794
  slackWeight: body.slackWeight,
@@ -3818,7 +3872,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
3818
3872
  if (fmt)
3819
3873
  change.format = fmt;
3820
3874
  if (attrs.startAt !== undefined) {
3821
- const n = Number(attrs.startAt);
3875
+ const n = Number(asciiDigits(attrs.startAt));
3822
3876
  if (Number.isInteger(n) && n >= 1)
3823
3877
  change.startAt = n;
3824
3878
  }
@@ -4068,7 +4122,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
4068
4122
  // A resource on a vertical page stands upright, its frame at most as
4069
4123
  // wide as the flow is tall (less the float gap it keeps).
4070
4124
  const blockPage = doc.pages[cursor.pageIndex];
4071
- const upright = blockPage.flow && rawBlock.type === 'resourceBlock'
4125
+ const upright = pageIsVertical(blockPage) && rawBlock.type === 'resourceBlock'
4072
4126
  ? { uprightMaxLength: uprightOn(blockPage).length }
4073
4127
  : {};
4074
4128
  let measuredBlock = tryLoose
@@ -4207,6 +4261,10 @@ function placeDocumentPass(content, config, cache, options, hints) {
4207
4261
  blk.prefixX = blk.bulletOffsetX + (listBullet.prefixOffsetPx ?? 0);
4208
4262
  }
4209
4263
  }
4264
+ // A list set against the document's direction: its marker on the
4265
+ // other side, with its text (#371).
4266
+ if (rawBlock.direction !== undefined && rawBlock.direction !== resolvedDirection(resolved))
4267
+ mirrorListMarker(blk);
4210
4268
  if (strikethroughText)
4211
4269
  blk.strikethroughText = true;
4212
4270
  // Bullet Y = x-height midpoint of the item's first text line.
@@ -4246,6 +4304,9 @@ function placeDocumentPass(content, config, cache, options, hints) {
4246
4304
  && (headingLevels.forBlock(rawBlock)?.snapToGrid ?? resolved.headings.snapToGrid)) ||
4247
4305
  (vdtType === 'listItem' && !nextIsListItem) ||
4248
4306
  (vdtType === 'paragraph' && isContainerTail && paragraphContainer?.snapToGrid !== false) ||
4307
+ // A poem, like a container of one block: its own leading and the
4308
+ // margins of its style are off the grid, the text after it is not.
4309
+ (vdtType === 'paragraph' && rawBlock.verse !== undefined && verseSnaps(rawBlock.verse.attrs.style, resolved)) ||
4249
4310
  vdtType === 'mathDisplay');
4250
4311
  // Place block, splitting across columns/pages if needed.
4251
4312
  // List items may split too — orphan/widow protection per-list is gated by
@@ -4301,6 +4362,10 @@ function placeDocumentPass(content, config, cache, options, hints) {
4301
4362
  && resolved.bodyText.keepColonWithList
4302
4363
  && nextIsListItem
4303
4364
  && /[::︰﹕]\s*$/.test(contentBlock.text);
4365
+ // A poem (#378) after this paragraph, which introduces it («فأنشد
4366
+ // يقول:»): see the lead-in rule below.
4367
+ const nextIsVerse = vdtType === 'paragraph' && contentBlock.verse === undefined
4368
+ && nextBlock?.type === 'paragraph' && nextBlock.verse !== undefined;
4304
4369
  while (remainingLines.length > 0) {
4305
4370
  enterBand(blockIdx, partIndex);
4306
4371
  const curCol = currentColumn(doc, cursor);
@@ -4400,6 +4465,10 @@ function placeDocumentPass(content, config, cache, options, hints) {
4400
4465
  }
4401
4466
  }
4402
4467
  }
4468
+ else if (rawBlock.verse && partIndex === 0) {
4469
+ // A poem: the top margin of the paragraph style its fence names.
4470
+ spacingBefore = Math.max(spacingBefore, style.marginTopPx);
4471
+ }
4403
4472
  else if (rawBlock.toc || rawBlock.index) {
4404
4473
  // A part row or an unnumbered entry of the contents: its top
4405
4474
  // margin (`toc.parts.marginTop`, the level's `marginTop`) applies
@@ -4491,7 +4560,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
4491
4560
  // columns); in-column headings use just the column width.
4492
4561
  const pageArea = doc.pages[cursor.pageIndex].contentArea;
4493
4562
  const measureWidth = lvl.span === 'page' ? pageArea.width : curCol.bbox.width;
4494
- const info = { titleText: title, formattedNumber: pref, numericValue: headingNumber, locale: resolvedLocale(resolved), chapterNumber: chapterNumberByBlock[blockIdx] ?? '', attrs: rawBlock.attrs };
4563
+ const info = { titleText: title, formattedNumber: pref, numericValue: headingNumber, locale: resolvedLocale(resolved), ...(resolved.numerals ? { numerals: resolved.numerals } : {}), chapterNumber: chapterNumberByBlock[blockIdx] ?? '', attrs: rawBlock.attrs };
4495
4564
  const design = measureHeadingDesign(lvl, info, measureWidth, resolved.page.dpi, doc.metadata, cursor.pageIndex, designFramesOn(doc.pages[cursor.pageIndex]), {
4496
4565
  x: lvl.span === 'page' ? pageArea.x : curCol.bbox.x,
4497
4566
  y: curCol.bbox.y + (curCol.bbox.height - curCol.availableHeight) + spacingBefore,
@@ -4630,18 +4699,32 @@ function placeDocumentPass(content, config, cache, options, hints) {
4630
4699
  // The lines left here keep the widow minimum; with fewer, a paragraph
4631
4700
  // that opens here moves on whole, and one already running on from
4632
4701
  // the column before stays (it cannot do better anywhere).
4633
- if (resolved.math.keepWithLeadIn
4702
+ // A poem (#378) is kept with the paragraph that introduces it the
4703
+ // same way: when its first bayts cannot start under the paragraph's
4704
+ // last line (by the orphan and widow rules a poem is split by), that
4705
+ // line goes on with them.
4706
+ const nextIsFormula = resolved.math.keepWithLeadIn && contentBlocks[blockIdx + 1]?.type === 'mathDisplay';
4707
+ if ((nextIsFormula || nextIsVerse)
4634
4708
  && vdtType === 'paragraph'
4635
- && contentBlocks[blockIdx + 1]?.type === 'mathDisplay'
4636
4709
  && totalRemainHeight <= effectiveAvailable + FIT_EPS) {
4637
- const formula = measureContentBlock(contentBlocks[blockIdx + 1], blockIdx + 1, curCol.bbox.width, blockMeasureCtx);
4638
- const formulaHeight = formula ? (formula.measured.lines[0]?.bbox.height ?? formula.measured.totalHeight) : 0;
4639
- const gap = Math.max(style.marginBottomPx, formula?.kind.style.marginTopPx ?? 0);
4640
4710
  const usedHeight = (curCol.bbox.height - curCol.availableHeight) + spacingBefore;
4641
4711
  // As the plain pass saw it: room balancing added above is not room
4642
4712
  // the formula lost.
4643
4713
  const availableAfter = curCol.bbox.height - (usedHeight + totalRemainHeight) + (balanceExtraInColumn.get(curCol) ?? 0);
4644
- if (formula && formulaHeight > 0 && availableAfter + FIT_EPS < gap + formulaHeight) {
4714
+ let goesOn;
4715
+ if (nextIsFormula) {
4716
+ const formula = measureContentBlock(contentBlocks[blockIdx + 1], blockIdx + 1, curCol.bbox.width, blockMeasureCtx);
4717
+ const formulaHeight = formula ? (formula.measured.lines[0]?.bbox.height ?? formula.measured.totalHeight) : 0;
4718
+ const gap = Math.max(style.marginBottomPx, formula?.kind.style.marginTopPx ?? 0);
4719
+ goesOn = !!formula && formulaHeight > 0 && availableAfter + FIT_EPS < gap + formulaHeight;
4720
+ }
4721
+ else {
4722
+ // The poem starts under the larger of this paragraph's bottom
4723
+ // margin and its own style's top margin.
4724
+ const poemGap = Math.max(style.marginBottomPx, verseMarginTopPx(nextBlock?.verse?.attrs.style, resolved));
4725
+ goesOn = !firstListItemStarts(blockIdx, availableAfter - poemGap, curCol.bbox.width, blockMeasureCtx);
4726
+ }
4727
+ if (goesOn) {
4645
4728
  const minKeep = resolved.bodyText.avoidWidows ? Math.max(1, resolved.bodyText.widowMinLines) : 1;
4646
4729
  const splitAt = remainingLines.length - 1;
4647
4730
  if (splitAt >= minKeep) {
@@ -5020,6 +5103,12 @@ function placeDocumentPass(content, config, cache, options, hints) {
5020
5103
  continue;
5021
5104
  }
5022
5105
  }
5106
+ // A poem's bayt set staggered over two lines (or more) stays in one
5107
+ // column (#378): the cut goes before it — in an empty column, which
5108
+ // the poem cannot leave, after its first line at least.
5109
+ while (choice.splitAt > (curCol.blocks.length === 0 ? 1 : 0) && sameBayt(remainingLines[choice.splitAt - 1], remainingLines[choice.splitAt])) {
5110
+ choice = { splitAt: choice.splitAt - 1, demerit: choice.demerit };
5111
+ }
5023
5112
  if (choice.splitAt > 0) {
5024
5113
  // Consume spacing (negative: a container margin pulling the block up)
5025
5114
  if (spacingBefore !== 0) {
@@ -5268,7 +5357,7 @@ function placeDocumentPass(content, config, cache, options, hints) {
5268
5357
  if (paperOfBlock.some((p) => p !== undefined))
5269
5358
  stampPagePaper(doc.pages, paperOfBlock);
5270
5359
  // Stamp page-number info onto every page (including blank parity pages).
5271
- const labels = buildPageLabels(doc.pages.length, pageNumberSegments);
5360
+ const labels = buildPageLabels(doc.pages.length, pageNumberSegments, resolved.numerals);
5272
5361
  for (let i = 0; i < doc.pages.length; i++) {
5273
5362
  const info = labels[i];
5274
5363
  if (!info)
@@ -5300,10 +5389,16 @@ function placeDocumentPass(content, config, cache, options, hints) {
5300
5389
  },
5301
5390
  });
5302
5391
  // Vertical pages: the axis each font's upright characters turn about.
5303
- if (doc.pages.some((p) => p.flow))
5392
+ if (doc.pages.some((p) => pageIsVertical(p)))
5304
5393
  stampCentralBaselines(doc);
5394
+ // Right-to-left pages: lines advance through the mirrored flow in the
5395
+ // reverse of their visual order.
5396
+ if (doc.pages.some((p) => pageIsMirrored(p)))
5397
+ orientLinesToFrames(doc);
5305
5398
  doc.converged = true;
5306
5399
  doc.iterationCount = 1;
5400
+ if (joiningLetterSpacing.size > 0)
5401
+ joiningSpacingWarnings.set(doc, joiningLetterSpacingWarnings(doc, joiningLetterSpacing));
5307
5402
  return { doc, forcedBreakPages, bandCapProposals, spanPlacedInBand, bandCapsApplied, looseOutcome, captionUnderProposals };
5308
5403
  }
5309
5404
  /** Passes a document printing its own contents gets at most, beyond the
@@ -5360,13 +5455,22 @@ export function* buildDocumentGen(content, config, cache, options) {
5360
5455
  const bookCitationKeys = content.citations ? new Set(content.citations.items.map((i) => i.id)) : undefined;
5361
5456
  const found = [...collectContentWarnings(content.markdown, config, content.resources ?? [], bookAnchors, bookCitationKeys), ...(indexWarnings.get(doc) ?? [])];
5362
5457
  const located = found.length > 0 ? locateContentWarnings(doc, found) : [];
5363
- // Justified CJK lines the composer could not fill within its tracking cap.
5364
- const loose = cjkLooseLineWarnings(doc);
5458
+ // Justified CJK lines the composer could not fill within its tracking
5459
+ // cap; words of a joining script that run past their line, and styles
5460
+ // whose letter-spacing such words do not take.
5461
+ const loose = [...cjkLooseLineWarnings(doc), ...wordOverflowWarnings(doc), ...(joiningSpacingWarnings.get(doc) ?? [])];
5365
5462
  // Chinese marks placed where the lines are painted (#193), and the
5366
5463
  // paragraphs whose leading is too tight for their marks or readings.
5367
5464
  const annotations = annotateDocument(doc, doc.config?.cjk);
5368
- if (located.length > 0 || loose.length > 0 || annotations.length > 0)
5369
- doc.contentWarnings = [...located, ...loose, ...annotations];
5465
+ // Arabic vowel marks (#376): how far each vocalised line's ink reaches,
5466
+ // for the column clip, and the paragraphs whose marks meet a
5467
+ // neighbouring line.
5468
+ const harakat = annotateArabicMarks(doc);
5469
+ // The rules over `*…*` runs under `bodyText.emphasis: 'overline'`.
5470
+ overlineEmphasis(doc);
5471
+ if (located.length > 0 || loose.length > 0 || annotations.length > 0 || harakat.length > 0) {
5472
+ doc.contentWarnings = [...located, ...loose, ...annotations, ...harakat];
5473
+ }
5370
5474
  // Config values the build replaced (an unknown number format, a font
5371
5475
  // stack, a side column no column width can take): walked once per build,
5372
5476
  // not per pass — they belong to no page.
@@ -5378,6 +5482,9 @@ export function* buildDocumentGen(content, config, cache, options) {
5378
5482
  /** Warnings the last pass's `:::index` raised, per document (read with
5379
5483
  * the content warnings once the build is done). */
5380
5484
  const indexWarnings = new WeakMap();
5485
+ /** The `joiningScriptLetterSpacing` warnings of the last pass, per
5486
+ * document. */
5487
+ const joiningSpacingWarnings = new WeakMap();
5381
5488
  /** `doc` with the page of each of its index marks (`doc.indexMarks`). */
5382
5489
  function withIndexMarks(doc, content) {
5383
5490
  const { content: body, contentOffset } = extractFrontmatter(content.markdown);
@@ -5461,7 +5568,7 @@ function* buildDocumentNumbered(content, config, cache, options, tocRound = 0) {
5461
5568
  const used = printedFootnoteNumbers(doc);
5462
5569
  if (used.size === 0)
5463
5570
  break;
5464
- const placed = numberFootnotesByPlacement(doc.pages, f.numbering, f.numberFormat).numbers;
5571
+ const placed = numberFootnotesByPlacement(doc.pages, f.numbering, documentNumeralStyle(f.numberFormat, doc.config.numerals), f.markerTemplate).numbers;
5465
5572
  // A note the layout set nowhere keeps the number it had.
5466
5573
  const next = new Map(used);
5467
5574
  for (const [id, number] of placed)
@@ -5898,4 +6005,15 @@ function* buildDocumentBalanced(content, config, cache, options, tocRound = 0, f
5898
6005
  best.doc.converged = segments.every((s) => s.stable || s.bestScore === 0);
5899
6006
  return best.doc;
5900
6007
  }
6008
+ /** Whether two lines set one bayt of a poem (`VDTLine.verse`), which a
6009
+ * column never cuts. */
6010
+ function sameBayt(a, b) {
6011
+ return a?.verse !== undefined && b?.verse !== undefined && a.verse.bayt === b.verse.bayt;
6012
+ }
6013
+ /** Whether the text after a poem goes back to the baseline grid: unless
6014
+ * the paragraph style its fence names says `snapToGrid: false`. */
6015
+ function verseSnaps(styleId, resolved) {
6016
+ const key = styleId?.trim();
6017
+ return !key || resolved.paragraphStyles.find((s) => s.id === key)?.snapToGrid !== false;
6018
+ }
5901
6019
  //# sourceMappingURL=build.js.map