关于 lovstudio:any2pdf
lovstudio:any2pdf 是一项将 Markdown 文档排版为 PDF 的技能,面向需要制作正式报告或出版文档的用户。它使用 reportlab,并处理 CJK 混排、代码块、表格和多种文档元素。
主要功能
- 01将 Markdown 转为排版 PDF
- 02支持中日韩与拉丁文字混排
- 03处理代码块、表格和嵌套列表
- 04支持图片、提示框、表情符号与公式
- 05提供封面、目录、水印和主题选项
适用场景
- 01将技术报告导出为 PDF
- 02制作含 CJK 内容的文档
- 03为 PDF 添加封面、目录或水印
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ lovstudio/ any2pdf --skill lovstudio:any2pdf安装后在 Claude Code 中输入/lovstudio:any2pdf确认已加载。
附带文件references/themes.mdscripts/md2pdf.py
详细介绍
any2pdf — Markdown 转专业 PDF
此技能使用 Python 的 reportlab 库,将任意 Markdown 文件转换为出版级 PDF。它经过多轮迭代打磨,基于真实的中文技术报告开发,解决了朴素的 Markdown→PDF 转换器常常处理不当的几个难题。
适用场景
- 用户想将
.md转换为.pdf - 用户有一份 Markdown 报告/文档,并希望获得专业的排版效果
- 文档包含中日韩字符与拉丁文本混排
- 文档包含围栏代码块、Markdown 表格或嵌套列表
- 文档包含本地/远程图片、Obsidian 提示框、表情符号或数学公式
- 用户希望在 PDF 中添加封面页、目录或水印
快速开始
python md2pdf/scripts/md2pdf.py \
--input report.md \
--output report.pdf \
--title "My Report" \
--author "Author Name" \
--theme warm-academic
除 --input 外,所有参数均为可选项,并会应用合理的默认值。
转换前选项(必选)
重要:运行转换前,必须使用 AskUserQuestion 工具询问这些问题。不要以纯文本列出选项——请使用该工具,以便用户获得适当的交互式提示。请在一次 AskUserQuestion 调用中询问所有选项。
使用以下模板调用 AskUserQuestion。语气应友好、简洁——像设计助手,而不是配置表单:
开始转 PDF!先帮你确认几个选项 👇
━━━ 📐 设计风格 ━━━
a) 暖学术 — 陶土色调,温润典雅,适合人文/社科报告
b) 经典论文 — 棕色调,灵感源自 LaTeX classicthesis,适合学术论文
c) Tufte — 极简留白,深红点缀,适合数据叙事/技术写作
d) 期刊蓝 — 藏蓝严谨,灵感源自 IEEE,适合正式发表风格
e) 精装书 — 咖啡色调,书卷气,适合长篇专著/技术书
f) 中国红 — 朱红配暖纸,适合中文正式报告/白皮书
g) 水墨 — 纯灰黑,素雅克制,适合文学/设计类内容
h) GitHub — 蓝白极简,程序员熟悉的风格
i) Nord 冰霜 — 蓝灰北欧风,清爽现代
j) 海洋 — 青绿色调,清新自然
━━━ 🖼 扉页图片(封面之后的全页插图) ━━━
1) 跳过
2) 我提供本地图片路径
3) AI 根据内容自动生成一张
━━━ 💧 水印 ━━━
1) 不加
2) 自定义文字(如 "DRAFT"、"内部资料")
━━━ 📇 封底物料(名片/二维码/品牌) ━━━
1) 跳过
2) 我提供图片
3) 纯文字信息
示例回复:"a, 扉页跳过, 水印:仅供学习参考, 封底图片:/path/qr.png"
直接说人话就行,不用记编号 😄
将用户选择映射到 CLI 参数
| 选择 | CLI 参数 |
|---|---|
| 设计风格 a-j | --theme,取值见下表 |
| 本地扉页 | --frontispiece <path> |
| AI 扉页 | 先生成图片,然后使用 --frontispiece /tmp/frontispiece.png |
| 水印文字 | --watermark "文字" |
| 封底图片 | --banner <path> |
| 封底文字 | --disclaimer "声明" 和/或 --copyright "© 信息" |
主题名称映射
| 选择 | --theme 取值 | 灵感来源 |
|---|---|---|
| a) 暖学术 | warm-academic | Lovstudio 设计系统 |
| b) 经典论文 | classic-thesis | LaTeX classicthesis |
| c) Tufte | tufte | Edward Tufte 的书籍 |
| d) 期刊蓝 | ieee-journal | IEEE 期刊格式 |
| e) 精装书 | elegant-book | LaTeX ElegantBook |
| f) 中国红 | chinese-red | 中国正式文件 |
| g) 水墨 | ink-wash | 水墨画 |
| h) GitHub | github-light | GitHub Markdown 风格 |
| i) Nord | nord-frost | Nord 配色方案 |
| j) 海洋 | ocean-breeze | — |
处理 AI 生成的扉页
如果用户选择 AI 生成:读取文档标题和首段内容,使用图像生成工具创作与所选设计风格相符的主题插画,展示给用户确认,然后通过 --frontispiece /path/to/image.png 传入
架构
Markdown → Preprocess (split merged headings) → Parse (code-fence-aware) → Story (reportlab flowables) → PDF build
主要组件:
- 字体系统:macOS 上使用 Palatino(拉丁文正文)、Songti SC(中日韩正文)、Menlo(代码);Linux 上自动回退
- 中日韩文字包装器:
_font_wrap()将中日韩字符片段包装在<font>标签中,以便自动切换字体 - 混排文本渲染器:
_draw_mixed()在画布上处理中日韩与拉丁文本混排(封面、页眉、页脚) - 代码块处理器:
esc_code()在 reportlab Paragraph 中保留缩进和换行 - 智能表格宽度:根据内容长度按比例设置列宽,最小宽度为 18mm
- 书签系统:
ChapterMark流动对象可创建 PDF 侧边栏书签和命名锚点 - 标题预处理器:
_preprocess_md()将# Part## Chapter这类合并标题拆分为独立行 - 图片处理器:将本地、相对路径、
file://和远程 Markdown 图片缩放至正文区域;出错时显示备用文本 - 提示框渲染器:将 Obsidian 风格的
> [!NOTE]块渲染为带主题样式的框式提示 - 公式渲染器:显示公式可使用可选的 matplotlib mathtext 图片;若不可用,则回退为带样式的文本
- 表情符号回退:有可用的缓存 Twemoji PNG 时使用其渲染表情符号,否则回退到本地表情符号字体
来之不易的经验
CJK 字符显示为 □
reportlab 的 Paragraph 只使用 ParagraphStyle 中的字体。如果 fontName="Mono",但文本包含中文,中文就会显示为 □。修复方法:对所有可能包含 CJK 字符的文本(包括代码块)始终应用 _font_wrap()。
代码块丢失换行
reportlab 会将 \n 视为空白字符。修复方法:esc_code() 会将 \n 转换为 <br/>,并将所有空格转换为 ,在应用 _font_wrap() 前保留缩进和行内对齐。
CJK/拉丁文本换行
reportlab 默认只在空格处换行,导致出现“Claude\nCode”这类不自然的断行。修复方法:在正文和项目符号样式中设置 wordWrap='CJK',以支持在 CJK 字符边界处换行。
包含 CJK 字符的画布文本(封面/页脚)
使用拉丁字体调用 drawString() / drawCentredString() 无法呈现年/月/日等字符。修复方法:对所有画布上的用户内容文本(日期、统计信息、免责声明)使用 _draw_mixed()。
配置参考
大多数选项也可以在文件顶部的 YAML 风格 frontmatter 中设置。显式 CLI 参数的优先级高于 frontmatter 值。
| 参数 | Frontmatter 键 | 默认值 | 说明 |
|---|---|---|---|
--input | — | (必需) | Markdown 文件路径 |
--output | — | output.pdf | 输出 PDF 路径 |
--title | title | 取自第一个 H1 | 封面上的文档标题 |
--subtitle | subtitle | "" | 副标题文本 |
--author | author | "" | 作者姓名 |
--date | date | 今天 | 日期字符串 |
--version | version | "" | 封面上的版本字符串 |
--watermark | watermark | "" | 水印文本(空值 = 无) |
--theme | theme | warm-academic | 配色主题名称 |
--theme-file | — | "" | 自定义主题 JSON 文件路径 |
--cover | cover | true | 生成封面 |
--toc | toc | true | 生成目录 |
--page-size | page-size | A4 | 页面尺寸(A4 或 Letter) |
--frontispiece | frontispiece | "" | 封面后的整页图片 |
--banner | banner | "" | 封底横幅图片 |
--header-title | header-title | "" | 页眉中的报告标题 |
--footer-left | footer-left | author | 页脚中的品牌/作者 |
--stats-line | stats-line | "" | 封面上的统计信息 |
--stats-line2 | stats-line2 | "" | 第二行统计信息 |
--edition-line | edition-line | "" | 封面底部的版本行 |
--disclaimer | disclaimer | "" | 封底免责声明 |
--copyright | copyright | "" | 封底版权信息 |
--code-max-lines | code-max-lines | 30 | 每个代码块的最大行数 |
主题
可用主题:warm-academic、nord-frost、github-light、solarized-light、
paper-classic、ocean-breeze。
每个主题定义:页面背景、墨色、强调色、淡化文本、边框、代码背景、水印色调。
依赖项
pip install reportlab --break-system-packages
# Optional formula rendering:
pip install matplotlib --break-system-packages
推荐的 Ubuntu/Debian 字体:
sudo apt install fonts-dejavu-core fonts-liberation fonts-freefont-ttf fonts-noto fonts-noto-cjk fonts-noto-color-emoji