阿拉伯文、波斯文导出 PDF 后字母断开、顺序颠倒
简短回答
阿拉伯字母的形状随前后字母变化,并且从右往左书写。如果 PDF 工具按从左到右排版,或逐个字母绘制,就会出现孤立的字母和颠倒的顺序。Pandoc 中加上 -V dir=rtl -V lang=ar(波斯文用 lang=fa)并选用支持阿拉伯文的字体;HTML 类工具中设置 dir="rtl",不要对阿拉伯文使用 letter-spacing。
症状复现

-V mainfont="Segoe UI":单词顺序颠倒,波斯文一行完全错乱。
原因
- 书写方向(双向文本):没有设置从右到左时,整行按从左到右排列,单词和字母就会颠倒。
- 字形拼合:阿拉伯字母有独立、词首、词中、词尾四种形式。不做字形拼合(或逐字绘制)的渲染器只会显示独立形式。
- letter-spacing 与 html2canvas:Chrome 本身在有字间距时仍保持阿拉伯文连写,但 html2canvas(很多“HTML 转 PDF”按钮用它)会改为逐个绘制字形,字母随即散开(见下图)。

letter-spacing: 0.05em 在 Chrome 中仍保持连写,在 html2canvas 1.4.1 中则断开。打开一份阿拉伯文示例
打开阿拉伯文示例Pandoc 中的修法(实测有效)
pandoc input.md -o output.pdf \
--pdf-engine=xelatex \
-V mainfont="Segoe UI" \
-V dir=rtl -V lang=ar
-V dir=rtl -V lang=ar 后:字母连写,从右到左。波斯文用 lang=fa,乌尔都文用 lang=ur。任何包含阿拉伯字形的字体都可以;Linux 上可用 Noto Sans Arabic 或 Noto Naskh Arabic。
HTML / Chromium 类工具中的修法

- 设置方向:把 RTL 段落放进
<div dir="rtl">…</div>,或使用<p dir="auto">让每段自动判断方向。 - 在自定义 CSS 中去掉正文的
letter-spacing。 - 在服务器和 Docker 镜像中安装阿拉伯文字体(Debian/Ubuntu 可装
fonts-noto-core)。
<div dir="rtl">
مرحبا بالعالم. هذا نص عربي.
</div>在 MarkPDF 中
MarkPDF 自动识别阿拉伯文、波斯文和乌尔都文:加载对应的 Noto 字体,每个段落、列表、引用和表格按自身内容确定方向。英文与阿拉伯文混排也不需要额外标记。
常见问题
为什么在编辑器里正常,导出 PDF 就不对?
编辑器和浏览器会自动处理阿拉伯文的字形和方向;很多 PDF 流程需要明确设置方向和语言。
需要特殊字体吗?
需要包含阿拉伯字形和 OpenType 拼合表的字体,Noto Sans Arabic、Noto Naskh Arabic、Segoe UI、Tahoma 都可以。
阿拉伯文中夹杂数字和英文怎么办?
方向设为 RTL 后,双向文本算法会让数字和拉丁单词在行内保持从左到右的顺序。