# Ruanzhu Kit

> 当用户需要为软件著作权登记准备申报材料时调用：生成风格统一的「用户手册 PDF（36页）」「源程序 PDF（36页）」「软件著作权登记申请表 PDF（2页）」。手册必须嵌入真实界面截图。覆盖截图、字体、分页、封面/页眉页脚、页数校准等全部实现细节与踩坑点。

- Skill: `sangjiexun/ruanzhu-kit` (Agent Skill, multi-file: 4 files)
- Install (CLI): `npx skillmds@latest add sangjiexun/ruanzhu-kit`
- Raw SKILL.md: https://api.skillmd.com/api/skills/sangjiexun/ruanzhu-kit/raw
- Safety review: pending
- Works with: Claude Code, Claude.ai, OpenAI Codex
- Category: Docs & Writing
- Author: sangjiexun (https://skillmd.com/u/sangjiexun)
- Updated: 2026-09-17
- Page: https://skillmd.com/skills/sangjiexun/ruanzhu-kit

---


# 软著申报材料三件套生成 (ruanzhu-kit)

为软件著作权登记生成三件套 PDF：**用户操作手册**、**源程序（代码）**、**软件著作权登记申请表**。
全部用 `reportlab` 离线生成（不依赖 Word / 浏览器 headless / 在线 CDN），中文字体走系统 `Heiti SC` / `Songti SC`。

## 三件套定位
1. **用户操作手册** — 产品介绍 + 安装 + 界面 + 功能 + **真实截图** + FAQ + 架构 + 部署 + 附录。要求：封面、页眉页脚、目录、配图（真实截图，禁止纯占位/循环灌水）、**36 页**。避免大段空白。
2. **源程序（源代码）** — 完整源文件，带行号、等宽字体、中文注释完整。要求：封面、页眉页脚、**36 页**（软著常见提交量）。
3. **软件著作权登记申请表** — 软件全称/简称/版本、著作权人、权利取得方式、鉴别材料、待填项用下划线占位。2 页。

默认页数：**手册 36 / 源程序 36 / 申请表 2**。封面均写「共 36 页」（申请表除外）。用户若指定其他页数，以用户为准。

## 关键踩坑点（必读，省数小时）
- **PingFang 不能嵌入**：PingFang.ttc 是 CFF/PostScript 轮廓，reportlab 的 `TTFont` 无法嵌入 → 报错。改用 **Heiti SC（黑体，正文）** 与 **Songti SC（宋体，标题/封面）**，它们是 TrueType 轮廓可被 reportlab 嵌入。注册示例：
  ```python
  from reportlab.pdfbase import pdfmetrics
  from reportlab.pdfbase.ttfonts import TTFont
  pdfmetrics.registerFont(TTFont("Heiti", "/System/Library/Fonts/STHeiti Medium.ttc", subfontIndex=1))
  pdfmetrics.registerFont(TTFont("Songti", "/System/Library/Fonts/Supplemental/Songti.ttc", subfontIndex=6))
  pdfmetrics.registerFont(TTFont("SongtiSB", "/System/Library/Fonts/Supplemental/Songti.ttc", subfontIndex=1))
  ```
- **中文行必须换字体**：等宽 `Courier` 不含中文字形。代码 PDF 中，若某行含中文（注释/字符串），整行用 `Heiti` 渲染，否则用 `Courier`。逐行用正则 `[\u4e00-\u9fff]` 判断切换。
- **手册必须先截真实图再排版**：桌面应用用 **1440×900、deviceScaleFactor=2**；手机壳应用才用 420×900。按 App 实际选择器点页签（`.nav-btn[data-view]` / `.tab[data-view]` / `switchView()`）。脚本见 `scripts/shot_app_tabs.js`。必须 `dangerouslyDisableSandbox:true` 才能启动本机 Edge。
- **图片嵌入与防空白**：桌面截图宽约 **450–500pt**，高按 1440×900 比例；`KeepTogether(Image + 图注)`，避免图与标题跨页拉开大空白。不要用空 `touch` 出来的假 PNG。不要用「第 N 章功能模块详解 N」这种循环灌水凑页。
- **目标页数微调（必须用 pypdf 闭环，禁止目测）**：
  - 源代码：整文件一张大 Table 自动分页。用 `FS`/`LH`/padding 循环试到正好 36 页（长源码先略降 FS/LH；短源码略升）。2414 行量级可从 `FS≈6.15, LH≈9.2` 起步。
  - 用户手册：先写真实章节 + 真实截图，再用 pypdf 读页数；少则补「图册 / 教案 / 速查表」，多则略收 leading 或缩小截图，直到 36。禁止删页凑数。
- **`Polygon` 坐标要平铺列表**：reportlab 的 `Polygon(points)` 接收 `[x0,y0,x1,y1,...]`，不是 `[(x,y),...]` 元组列表。传元组会静默错位或空图形。
- **目录页码**：`TableOfContents` 必须 `doc.multiBuild()` 两次排版才能回填。目录可用更稳妥的手动 `Table` + 固定页码。
- **单表自动分页优于手动每页 50 行**：手动把 50 行塞进一张 Table 再 `PageBreak`，长行折行会溢出页数。

## 整体流程
1. **确认素材**：目标 App/网页（单文件 HTML 最佳）、项目名、软件全称/简称、版本号、著作权人。
2. **真实截图**：用 `scripts/shot_app_tabs.js`（或项目内专用脚本）截各模块 PNG。桌面默认 1440×900。核对 PNG 尺寸与画面，禁止空文件。
3. **生成用户手册**：基于 `scripts/build_manual_template.py` 改写成**当前项目**文案（不要留「航程雷达」占位），嵌入真实截图，调到 **36 页**，避免大段空白。
4. **生成源代码**：基于 `scripts/build_source_pdf_template.py`，读源码自动分页带行号、封面（项目名 / 源代码 / V1.0 / 著作权人 / 共 36 页），循环微调到 **36 页**。
5. **生成申请表**：基于 `scripts/build_application_form_template.py`，填软件信息、著作权人、鉴别材料页码（手册 1–36、源程序 1–36）。
6. **校验**：`pypdf` 查页数；`pymupdf.get_text()` 核封面（项目名、用户手册/源代码、著作权人、共 36 页）。必要时渲染关键页。

## 封面定稿样式
- 大标题：**项目名**
- 小标题：仅 **用户手册** / **源代码**（不带产品名）
- 元数据：软件版本 V1.0、著作权人
- 手册与源程序封面均写：**共 36 页**（不放英文行、不放开发语言行）

## 校验清单
- [ ] 页数达标（手册 36 / 代码 36 / 申请表 2）
- [ ] 封面中文、项目名、著作权人、共 36 页正确
- [ ] 操作手册：目录页码正确、配图为真实截图、页眉页脚完整、无大段空白、无循环灌水章节
- [ ] 源代码：行号连续、中文注释完整、等宽字体、末页可不足整页
- [ ] 申请表：待填字段用下划线占位，鉴别材料页码范围与另两份一致

## 复用模板
- `scripts/build_manual_template.py` — 操作手册骨架（须改成当前项目文案 + 真实截图）
- `scripts/build_source_pdf_template.py` — 源代码生成（整文件单表自动分页 + 行号）
- `scripts/build_application_form_template.py` — 登记申请表生成
- `scripts/shot_app_tabs.js` — puppeteer-core 截单文件 App 各页签；支持桌面/手机视口与 data-view 自动发现

> 模板内项目名/著作权人等为占位值，使用前按实际申报信息改封面与元数据。不要把某个 App 的页签名写死进通用脚本后不改回来。

