diff --git a/README.md b/README.md
index c685044..9f1794a 100644
--- a/README.md
+++ b/README.md
@@ -8,6 +8,7 @@
|---|---|
| [`exam/`](exam/) | 期末考试**试卷**与**参考答案及评分标准**模板(XeLaTeX) |
| [`form/`](form/) | 教职工**年度考核登记表**模板(XeLaTeX) |
+| [`form2/`](form2/) | **劳务发放说明表**模板(XeLaTeX) |
## 说明
diff --git a/form2/README.md b/form2/README.md
new file mode 100644
index 0000000..3089c01
--- /dev/null
+++ b/form2/README.md
@@ -0,0 +1,177 @@
+# form2/ — 中国海洋大学 劳务发放说明表(LaTeX 版)
+
+把实验室用的《劳务发放说明表》Word 版复刻为 LaTeX 模板。版式与原 `.docx`
+逐项对齐,**不含任何真人信息**:姓名、人数、项目名称、单位名称一律 `×` 占位。
+
+## 文件
+
+| 文件 | 说明 |
+| :-- | :-- |
+| `劳务发放说明表.tex` | 主文件。填表只改第 1 节(4 个变量) |
+| `ouclw.sty` | 版式包。页面/字体/列宽/行高/全部尺寸写在这里,附换算注释 |
+
+## 编译
+
+```bash
+xelatex 劳务发放说明表.tex
+```
+
+单页,跑一遍即可(无交叉引用)。
+
+需要 **XeLaTeX**,并安装 `ctex`、`geometry`、`fontspec`、`xeCJK`、`tabularray`。
+实测环境:TeX Live 2022 + `tabularray 2022A`。
+
+## 改内容
+
+```latex
+\newcommand{\lwunit}{{\songti ××××××××}} % 用工单位(学部 / 学院)
+\newcommand{\lwreason}{{\songti ××××}} % 用工事由
+\newcommand{\lwnote}{} % 备注(可留空)
+\newcommand{\lwwork}{%
+ 聘请{\songti ×××}等{\songti ×}位研究生参与《{\songti ×××}》项目的研究工作。}
+```
+
+### 关于 `\lwwork` 的句式
+
+原文是「聘请秦依康等 2 位研究生参与《观测数据驱动的渤海生态系统健康评估
+关键技术研发》项目的研究工作。」——真人姓名、人数、真实项目名已替换为
+`×××` / `×`,**句式一字未动**。填表时把三处 `×` 换成实际内容即可:
+
+| 占位 | 换成 |
+| :-- | :-- |
+| 第一个 `×××` | 第一位研究生的姓名("等"字后面若只有一人,可删"等×位") |
+| `×`(位) | 研究生人数 |
+| 《`×××`》 | 项目全称 |
+
+## 版式数据来源
+
+全部尺寸从原 `.docx` 的 OOXML 里量出来,换算关系:
+
+- 长度:`mm = twips ÷ 1440 × 25.4`,`pt = twips ÷ 20`
+- 字号:`w:sz` 是半磅值,`sz=28` ⇒ 14 pt
+- 行距:`docGrid linePitch=312` twips ⇒ 15.6 pt
+
+| 项目 | docx 原值 | 换算 |
+| :-- | :-- | :-- |
+| 纸张 | `pgSz 11906×16838` | A4 210×297 mm |
+| 页边距(上下) | `pgMar top/bottom 1361` | 24.01 mm |
+| 页边距(左右) | `pgMar left/right 1797` | 31.70 mm |
+| 表宽 | `tblW 8522` | 150.32 mm |
+| 列宽 c1..c4 | `1384, 1418, 2883, 2837` | 24.41 / 25.01 / 50.85 / 50.04 mm |
+| 单元格内边距(左右) | `tblCellMar 108` | 1.905 mm |
+| 边框 | `tblBorders sz=4` | 0.5 pt |
+| 字号 | `w:sz 28` | 14 pt,宋体 |
+| 行距 | `linePitch 312` | 15.6 pt |
+
+各行行高由**段落数**决定(原表没有 `trHeight`),每段一个行距 15.6 pt:
+
+| 行 | 段数 | 高度 |
+| :-- | :-- | :-- |
+| R0 用工单位 | 2(`用工单位` / `(公章)`) | 31.2 pt = 11.01 mm |
+| R1 用工事由 | 1 | 15.6 pt = 5.50 mm |
+| R2 具体工作 | 9(长句 + 8 空段) | 140.4 pt = 49.53 mm |
+| R3 三方签字 | 4(标签 + 2 空段 + 日期) | 62.4 pt = 22.01 mm |
+| R4 备注 | 2 | 31.2 pt = 11.01 mm |
+| 合计 | | 280.8 pt = 99.06 mm |
+
+### 为什么左右页边距不对称
+
+原表宽 150.32 mm,比 docx 版心(146.68 mm)宽 3.71 mm,而 `tblPr` 里**没有
+`jc`、`tblInd` 又是 0** —— Word 按左对齐处理:表从左边距 31.70 mm 起排,
+右端溢进右侧页边距 3.71 mm。
+
+所以本模板照实复现这个不对称:`left = 31.70mm`、`totalwidth = 150.32mm`,
+右边界自然落到 `210 − 31.70 − 150.32 = 27.98 mm`。**不要**改成左右等边距
+(那样表会整体左移 1.86 mm,与 Word 里看到的位置不符)。
+
+## 四个必须知道的坑
+
+### 1. ctex 的 `\linespread ≈ 1.3` 会吃掉你设的行距
+
+```latex
+\fontsize{14}{15.6}\selectfont % \baselineskip = 20.28pt ✗
+\linespread{1}\relax\fontsize{14}{15.6}\selectfont % = 15.60pt ✓
+```
+
+`\fontsize` 第二个参数本该直接设定 `\baselineskip`,但 `\selectfont` 时会
+**再乘一次 `\linespread`**。ctex 默认 `\linespread ≈ 1.3`,于是 15.6 pt 被放大
+成 20.28 pt,五行表从 99 mm 涨到 129 mm,`ht=` 也压不住(内容本身就那么高,
+tabularray 只能被动撑开)。
+
+本包的对策是 `\lwbodyfont`:
+
+```latex
+\newcommand{\lwbodyfont}{\linespread{1}\relax\fontsize{14}{15.6}\selectfont}
+\AtBeginDocument{\lwbodyfont}
+```
+
+`\AtBeginDocument` 那一次不能省——ctex 在 begin document 时会重设 `\linespread`。
+
+### 2. 合并格 `{c}` 是不折行的 LR 模式
+
+`cell{r}{c}={c=n}{c}` 的 `{c}` 是 **LR 模式**,不是段落模式:
+
+- 格内文字比所跨各列合计更宽时,它**不折行**,而是把列撑宽、整表超出版心;
+- 合并格里的 `\hsize` **没有**被重设成该跨度宽度,仍是外层版心宽,
+ 长文本会按版心折行、冲出格子。
+
+⇒ 合并格里的文字一律包定宽 `\parbox`,本表提供 `\lwcell` / `\lwcellv` /
+`\lwstack` / `\lwsign` 四个入口,`.tex` 里只要有内容就用它们,别裸写。
+
+### 3. 合并格的“内容可用宽”要补回 `2·colsep·(n−1)`
+
+单列的内容宽 = `wd`(左右两半 `colsep` 已被 colspec 扣掉);
+但跨 n 列合并后,**n 列之间的 (n−1) 组内边距会被回收进内容宽**:
+
+```
+内容可用宽 = Σ 所跨各列 wd + 2 · colsep · (n − 1)
+```
+
+漏算的后果很隐蔽:`\parbox` 比真实格宽窄,短文本看不出问题,长文本会
+**提前折行**。本表「批准单位负责人签字」共 9 字 × 14 pt = 44.45 mm,
+而 c1+c2 只有 41.37 mm,就曾被折成「批准单位负责人签」+「字」两行,
+docx 里明明是一行。正确值是 `41.3653 + 2×1.905 = 45.1753mm`。
+
+### 4. `\parbox[t]` 会让行高超目标
+
+tabularray 给每个单元格垫了 strut,`[t]` 生成的盒子顶部与 strut 顶部相加,
+实测每行白白多出 **3.6 pt**(R0 从 31.67 → 35.26)。
+
+原表 R0C1 / R2C1 之所以“贴顶”,不是靠 `vAlign=top`(它们其实没写 `vAlign`),
+而是靠**段落数把行高填满**(2 段 = 31.2 pt、9 段 = 140.4 pt,正好等于行高)。
+内容高度已等于行高时,`[c]` 居中的结果就等同于贴顶。
+
+⇒ `.tex` 里用 `\lwcellv{内容\lwblank{n}}` 补足段落数,`\parbox` 保持 `[c]`。
+
+## 与 docx 的已知差异
+
+| 项 | docx | 本模板 | 说明 |
+| :-- | :-- | :-- | :-- |
+| 表宽 | 150.319 mm | 150.137 mm | 差 0.18 mm。tabularray 计宽按 n−1 根竖线、画宽按 n 根,系统性差 0.5 pt,为消除 Overfull 微调了列宽 |
+| 行高 | 11.01 / 5.50 / 49.53 / 22.01 / 11.01 mm | 每行 +0.15 mm | 同上,竖线计入行高 |
+| 字体 | 宋体 | SimSun | 同一字体。缺字体时用 `fc-list` 找替代 |
+| 标题 | 宋体 14 pt **加粗** | 同 | 字号与正文相同,只靠加粗区分 |
+
+## 校验方法
+
+不用肉眼看 PDF,直接量矢量:
+
+```bash
+pdftocairo -svg 劳务发放说明表.pdf out.svg # 取线条精确坐标
+pdftotext -bbox 劳务发放说明表.pdf out.xml # 取每个字块的坐标
+```
+
+SVG 里解析 ``,按
+「`|Δy|<0.9` 且 `|Δx|>10` = 横线」「`|Δx|<0.9` 且 `|Δy|>2` = 竖线」分类去重,
+即可得到每条线的精确端点。本模板的实测结果:
+
+```
+表宽 150.137 mm (目标 150.319,差 −0.18)
+表左 31.662 mm (目标 31.700,差 −0.04)
+表右 181.799 mm (目标 182.019,差 −0.22)
+R0 11.172 / R1 5.668 / R2 49.646 / R3 22.159 / R4 11.172 mm 全部达标
+```
+
+三个签字格的标签基线完全重合(`rel-top 1.06 pt`),日期行也完全重合
+(`rel-top 47.69 pt`)——这一条是特意做的:合并格与普通列的垂直居中算法
+不同,若不统一包 `\parbox`,第一格会比另两格低 1.55 pt。
\ No newline at end of file
diff --git a/form2/ouclw.sty b/form2/ouclw.sty
new file mode 100644
index 0000000..bc6558a
--- /dev/null
+++ b/form2/ouclw.sty
@@ -0,0 +1,343 @@
+%======================================================================
+% ouclw.sty — 中国海洋大学 劳务发放说明表 版式包
+%
+% 依据:实验室管理/劳务补贴/劳务发放说明表.docx(Word 2007+ 保存)
+% 目标:版式与原 docx 逐项对齐。所有尺寸都由 docx 内部数值换算:
+% twips → mm : mm = twips / 1440 * 25.4
+% twips → pt : pt = twips / 20 (1 pt = 1/72 in)
+% w:sz : 半磅值,÷ 2 即 pt
+%
+% 用法见同目录 劳务发放说明表.tex,说明见 README.md
+%======================================================================
+\NeedsTeXFormat{LaTeX2e}
+\ProvidesPackage{ouclw}[2026/10/26 v1.0 OUC labor payment form]
+
+\RequirePackage{geometry}
+\RequirePackage{fontspec}
+\RequirePackage{xeCJK}
+\RequirePackage{tabularray}
+
+%======================================================================
+% 1. 页面与版心
+%
+% 原 docx sectPr:
+% pgSz 11906 × 16838 twips = 210.02 × 297.05 mm → A4
+% pgMar top/bottom 1361 = 24.01 mm
+% left/right 1797 = 31.70 mm
+% header 851 / footer 992 = 15.01 / 17.51 mm
+% docGrid linePitch 312 → 行距 15.6 pt
+%
+% 原表 tblW 8522 twips = 150.32 mm,比 docx 版心(146.68 mm)宽 3.71 mm。
+% docx 的 tblPr 里【没有 jc】,tblInd = 0 ⇒ Word 是按左对齐处理的:
+% 表从左边距 31.70 mm 起排,右端溢出到右侧页边距里 3.71 mm。
+% 实测原表左右边距就是 pgMar 的 1797 twips = 31.70 mm,并不对称。
+%
+% ⇒ 本包照实复现这个“不对称”:
+% left = 31.70 mm (= docx pgMar left)
+% 表宽 = 150.32 mm
+% ⇒ 右边界自然落在 210 − 31.70 − 150.32 = 27.98 mm
+%
+% ⚠️ 为什么不写成 left = right = 29.84 mm(把表居中):
+% 那样表会整体左移 1.86 mm,与 Word 里看到的位置不符。
+% 代价是 \textwidth 变成 150.32 mm 而非 docx 的 146.68 mm ——
+% 本表除标题外没有通栏正文,标题是居中的,
+% 居中后中心仍在 31.70 + 75.16 = 106.86 mm,
+% 与 docx 的 31.70 + 73.34 = 105.04 mm 差 0.04 mm(取整误差级)。
+%======================================================================
+\geometry{
+ paperwidth = 210mm,
+ paperheight = 297mm,
+ left = 31.70mm, % = docx pgMar left 1797 twips
+ totalwidth = 150.32mm, % = 表宽,精确;geometry 由此算出 right=27.98mm
+ top = 24.01mm,
+ bottom = 24.01mm,
+ headheight = 0pt,
+ headsep = 0pt,
+ footskip = 17.51mm,
+}
+\setlength{\parindent}{0pt}
+\setlength{\parskip}{0pt}
+\pagestyle{empty} % 原 docx 无页眉页脚,故不排页码
+
+%======================================================================
+% 2. 字体与字号
+%
+% 全文 宋体 14pt (w:sz=28) ← 注意是宋体,不是仿宋
+% 大标题 宋体 14pt 加粗(w:b + w:sz=28),居中
+% 行距 15.6pt (docGrid linePitch=312 twips)
+%
+% ⚠️ 本表字号只有 14pt 一档,没有 .docx 里那种混排小字。
+%
+%----------------------------------------------------------------------
+% ⚠️⚠️⚠️【最要命的一条】ctex 默认 \linespread 约 1.3,会把
+% \fontsize{14}{15.6} 的 15.6pt 行距放大成 20.28pt!
+%
+% 实测:
+% \fontsize{14}{15.6}\selectfont → \baselineskip = 20.28pt ✗
+% 加 \linespread{1} 之后 → \baselineskip = 15.60pt ✓
+%
+% 后果:所有行都高 30%,五行表从 99mm 涨到 129mm,行高全对不上
+% (R0 35.66 vs 31.2、R3 69.3 vs 62.4)。而且 ht= 也压不住 ——
+% 内容本身就那么高,tabularray 只能被动撑开。
+%
+% \fontsize 的第二个参数【本来是】用来设 \baselineskip 的,但
+% \selectfont 时会再乘一次 \linespread,所以必须先把 \linespread
+% 归 1。这一步不能省,也必须在 \AtBeginDocument 之后再设一次
+% (ctex 在 begin document 时会重设)。
+%======================================================================
+\setmainfont{Times New Roman}
+\setCJKmainfont{SimSun}[AutoFakeBold=2.5]
+\newCJKfontfamily\songti{SimSun}[AutoFakeBold=2.5]
+\newCJKfontfamily\heiti{SimHei}
+\newCJKfontfamily\fangsong{FangSong}[AutoFakeBold=2.5]
+
+\newcommand{\lwbodyfont}{%
+ \linespread{1}\relax
+ \fontsize{14}{15.6}\selectfont}
+
+%----------------------------------------------------------------------
+% ⚠️ xeCJK 陷阱:局部字体切换命令若紧邻 \par(或落在段落末尾),段末的
+% 字体状态会“溢出”到后面段落。故局部切换一律用带 \normalfont 收尾的
+% 包装,不要直接写 {\heiti ...\par}。
+%----------------------------------------------------------------------
+\newcommand{\LWFS}[1]{{\fangsong #1\normalfont}}
+\newcommand{\LWHT}[1]{{\heiti #1\normalfont}}
+
+%======================================================================
+% 3. 列的宽度模型
+%
+% 原 docx tblGrid(4 个网格列,twips → mm):
+% c1 1384 → 24.4122 c2 1418 → 25.0119
+% c3 2883 → 50.8529 c4 2837 → 50.0415
+% 合计 8522 twips = 150.3186 mm(与 tblW 一致)
+%
+% 各行合并跨度(docx gridSpan):
+% R0/R1/R2/R4 c1 | c2-c4(span 3)
+% R3 c1-c2(span 2)| c3 | c4
+%
+%----------------------------------------------------------------------
+% ⚠️ 本表与年度考核表(form/)的关键差别:**可以用 colsep 真实还原内边距**。
+%
+% docx 的 tblCellMar 是 top/bottom = 0、left/right = 108 twips(1.905 mm)。
+% 年度考核表里有个只有 1.41 mm 宽的 c10,比两倍内边距还窄,所以只能取
+% colsep=0 并放弃内边距。本表最窄的列也有 24.41 mm,完全可以照实还原:
+%
+% colsep = 1.905mm
+%
+% tabularray 的 colsep 计在每列【左右两侧】,故 4 列共 +8×1.905 = 15.24 mm;
+% 竖线 5 根(左右边界 + 3 内部)× 0.5pt = 2.5pt = 0.882 mm。
+% 要让 Σwd + 15.24 + 0.882 = 150.3186,需
+% Σwd = 134.197 mm
+% 而 (gridCol − 2×1.905) 之和为 135.079 mm,两者差 0.882 mm 正好是竖线宽,
+% 故每列再减 0.882/4 = 0.2204 mm:
+%
+% wd = gridCol(mm) − 3.81 − 0.2204
+%
+% ⚠️ 上式只是理论值。tabularray 的计宽与画宽之间有约 0.45 pt 的取整差,
+% 实测需再微调(见 3.2 的实测标定值),否则一直报
+% “Table width is too small, need 0.45pt more!” 外加一条 Overfull \hbox。
+%
+%----------------------------------------------------------------------
+% ⚠️ 两条通用结论(在 form/ 里踩过,这里同样适用):
+%
+% (a) 合并单元格 cell{r}{c}={c=n}{c} 的单元类型 {c} 是【不折行的 LR 模式】。
+% 格内文字若比所跨各列合计更宽,它不会在列内折行,而是【把这些列撑宽】,
+% 整张表随之超出版心。⇒ 合并格里的文字一律包定宽 \parbox(见 \lwfit)。
+% 单列 Q[c,m,wd=…] 没有这个问题:超出时只溢出、列宽不变。
+%
+% (b) 合并单元格里的 \hsize【没有】被重设成该跨度的宽度,仍是外层版心宽。
+% ⇒ 凡是内容较长或含多段的跨列单元格,必须用固定宽 \parbox 包起来。
+%======================================================================
+\newcommand{\lwlwval}{0.5pt} % docx tblBorders sz=4 ⇒ 0.5pt(sz 单位 1/8pt)
+\newcommand{\lwcolsep}{1.905mm} % docx tblCellMar left/right 108 twips
+
+\newlength{\lwtblw}
+\setlength{\lwtblw}{150.32mm} % 表宽(含 5 根竖线与 8 处内边距)
+
+%----------------------------------------------------------------------
+% 3.1 各列宽(= gridCol − 3.81mm − 0.2204mm 的理论值)
+% 与 lwtable 环境里 colspec 的 wd 必须逐字一致。
+%----------------------------------------------------------------------
+\newcommand{\lwwa}{20.3828mm} % c1 24.4122 − 4.0304
+\newcommand{\lwwb}{20.9825mm} % c2 25.0119 − 4.0304
+\newcommand{\lwwc}{46.8235mm} % c3 50.8529 − 4.0304
+\newcommand{\lwwd}{46.0121mm} % c4 50.0415 − 4.0304
+
+%----------------------------------------------------------------------
+% 3.2 各跨度的【内容可用宽】
+%
+% ⚠️⚠️ 这里有一个必踩的坑:合并单元格(cell{r}{c}={c=n}{c})合并后,
+% n 列之间的 (n−1) 组内边距【会被回收进内容宽】。
+% ⇒ 内容可用宽 = Σ 所跨各列 wd + 2·colsep·(n−1)
+%
+% 只有 1 列时(\lwwa…\lwwd)内容宽 = wd,因为左右两半 colsep 已被
+% colspec 扣掉;跨 n 列时则不然,必须补回来。
+%
+% 漏算的后果非常隐蔽:\parbox 比真实格宽窄,短文本看不出问题,
+% 长文本会【提前折行】——本表“批准单位负责人签字”就曾被折成
+% “批准单位负责人签”+“字”两行,而 docx 里是一行。
+%----------------------------------------------------------------------
+% c1-c2 = 20.3828 + 20.9825 + 2×1.905 = 45.1753mm(“批准单位负责人签字”)
+\newcommand{\lwspanA}{45.1753mm}
+% c2-c4 = 20.9825 + 46.8235 + 46.0121 + 4×1.905 = 121.4381mm(长句等)
+\newcommand{\lwspanB}{121.4381mm}
+
+%======================================================================
+% 4. 行高
+%
+% 原 docx 各行【没有 trHeight】,高度全由段数决定
+% (每段 = 1 个行距 15.6 pt):
+% R0 2 段 → 31.2 pt = 11.01 mm
+% R1 1 段 → 15.6 pt = 5.50 mm
+% R2 9 段 → 140.4 pt = 49.53 mm ← 长句 1 段 + 8 个空段
+% R3 4 段 → 62.4 pt = 22.01 mm ← 标题 1 + 空 2 + “年 月 日” 1
+% R4 2 段 → 31.2 pt = 11.01 mm
+% 合计 280.8 pt = 99.06 mm
+%
+% ⚠️ tabularray 的 ht= 经实测同为“最小行高”,与 Word 的 atLeast 语义一致。
+% 本表直接把这些值写成 ht=,行高即固定;内容更多的行会自然长高。
+%======================================================================
+
+%======================================================================
+% 5. 表格环境
+%
+% ⚠️ 用 tblr 而非 longtblr:本表总高约 100 mm,一页装得下,
+% 不需要断页,也就不需要清 caption 模板。
+%
+% ⚠️⚠️ colspec 与 row{} 必须字面写在这里,不能先存进宏再展开:
+% tabularray 的列类型解析在宏展开之外进行,会报
+% “Unexpandable command \xxx inside column type”。
+% (所以 3.1 节那些 \lwwa… 只作文档用,不能拼进 colspec。)
+%
+% ⚠️⚠️⚠️ 跨度用 cell{r}{c}={c=n}{c} 声明,不要用行内 \SetCell[c=n]{c}:
+% \SetCell 之后要补若干个空 &,补几个取决于该格跨几列,一旦数错一位,
+% 同行后面所有单元格会整体错列到窄列,报出难以定位的 Overfull。
+% ⚠️ 正确写法只有 {c=n}{c};={c=n}、={n}{c}、={span=n}{c} 都不认。
+%
+% docx 各行的 gridSpan:
+% R0/R1/R2/R4 1,3 R3 2,1,1
+%
+% ⚠️ 选项里的宏名一律不带 @:tabularray 解析选项时 @ 不是字母。
+%======================================================================
+\newenvironment{lwtable}{%
+ \par\begingroup
+ \begin{tblr}[label=none]{
+ colspec={
+ Q[c,m,wd=20.3828mm] Q[c,m,wd=20.9825mm]
+ Q[c,m,wd=46.8235mm] Q[c,m,wd=46.0121mm]
+ },
+ colsep=1.905mm, rowsep=0pt, stretch=0,
+ hline{1-Z}={\lwlwval}, vline{1-Z}={\lwlwval},
+ row{1}={ht=11.01mm}, row{2}={ht=5.50mm}, row{3}={ht=49.53mm},
+ row{4}={ht=22.01mm}, row{5}={ht=11.01mm},
+ %---- R0/R1/R2/R4 c1 | c2-c4
+ cell{1}{2}={c=3}{c}, cell{2}{2}={c=3}{c}, cell{3}{2}={c=3}{c},
+ cell{5}{2}={c=3}{c},
+ %---- R3 c1-c2 | c3 | c4
+ cell{4}{1}={c=2}{},
+ }%
+}{%
+ \end{tblr}\par\endgroup}
+
+%======================================================================
+% 6. 单元格内容包装(见 3 节结论 a / b)
+%
+% 统一入口,.tex 里只用下面几个宏,不要直接把长文字写进 & 之间。
+%======================================================================
+% \lwfit{跨度宽宏}{内容} —— 定宽、水平居中、可折行(用于合并格里的标签)
+\newcommand{\lwfit}[2]{\parbox{#1}{\centering #2}}
+
+% \lwcell{内容} —— c2-c4 内容栏,左对齐、可折行
+%
+% ⚠️⚠️ 这里【必须】保持 \parbox 默认的 [c],不要改成 [t]。
+% 原因:tabularray 会给每个单元格垫一个 strut,[t] 生成的盒子顶部
+% 与 strut 顶部相加,实测每行白白多出 3.6pt(R0 从 31.67 → 35.26)。
+%
+% docx 里 R0C1 / R2C1 / R4C1 都没有 (按 OOXML 语义是顶部对齐),
+% 但它们靠【段落数把行高填满】实现“贴顶”:
+% R0C1 2 段 = 31.2pt = 行高
+% R2C1 9 段 = 140.4pt = 行高
+% 内容高度已等于行高,[c] 居中的结果就是贴顶,等价。
+% ⇒ 场合决定用法:段落数够 → \lwcellv{内容 + \lwblank{n}};
+% 段落数不够(如 R1 只有 1 段)→ 也正是 vAlign=center。
+\newcommand{\lwcell}[1]{\parbox{\lwspanB}{\raggedright #1}}
+
+% \lwcellv{内容} —— 同上(保留别名,语义上表示“垂直居中”)
+\newcommand{\lwcellv}[1]{\parbox[c]{\lwspanB}{\raggedright #1}}
+
+% \lwstack{内容} —— c1-c2 合并格(通用,任意多段)
+\newcommand{\lwstack}[1]{\parbox{\lwspanA}{\centering #1}}
+
+%----------------------------------------------------------------------
+% \lwsign{格宽}{签字标签} —— R3 的签字格
+%
+% docx 里 R3 每格都是 4 段:
+% 标签 / 空 / 空 / “年 月 日”
+% 即标签与日期之间有【2 个空行距 = 31.2pt】的签名留白,不是 1 行。
+% 4 段 × 15.6pt = 62.4pt = 22.01mm,正好等于行高,故 vAlign 取哪个都一样。
+%
+% ⚠️ R3 第一格是合并格(c1-c2),另外两格是普通列。tabularray 对这两种格
+% 的垂直居中算法【不一样】:合并格内容整体偏低 1.55 pt。
+% 三个格分别裸写内容时,实测基线为
+% 批准单位负责人签字 y = 280.65
+% 用工单位负责人签字 y = 279.10
+% 经办人签字 y = 279.10
+% 肉眼勉强看得出参差。把所有格都包成【同一种】\parbox 后,
+% 垂直居中的对象变成同一个盒子高度,三格自然对齐(实测 y 完全相同)。
+% 故本表三个签字格一律走这个宏。
+%----------------------------------------------------------------------
+\newcommand{\lwsign}[2]{%
+ \parbox[c]{#1}{\centering #2\par\vspace*{31.2pt}\lwdate}}
+
+%======================================================================
+% 7. 签字栏的“年 月 日”
+%
+% docx 里是右对齐,字间用 3 个半角空格(Times New Roman):
+% “年 月 日”,jc=right
+% R3C1 另加 firstLine=700 twips / firstLineChars=250(2.5 字)缩进,
+% 但既然整段右对齐,缩进只影响折行,不影响位置,故忽略。
+%
+% ⚠️ 用固定宽 \parbox 内的 \raggedleft,不要用 \hfill:
+% \hfill 在跨越 \par 的段尾会撑满 \hsize,若 \hsize 与 parbox 宽
+% 不一致就会冲出格子。
+%======================================================================
+\newcommand{\lwdate}{%
+ \par\noindent
+ \makebox[\linewidth][r]{年\hspace{1.5em}月\hspace{1.5em}日}}
+
+% 空段落:\lwblank{n} ⇒ 追加 n 个空行
+%
+% ⚠️ 不要用 \par\null:实测在 tabularray 单元格里,9 个 \par\null 会排成
+% 192.07pt,而 docx 里 9 个空段落只有 140.4pt。原因是 \null 是一个
+% 有高度的盒子,每个都按“汉字 + 行距”算钱;Word 的空段落只贡献行距。
+% ⇒ 行高统一交给 tabularray 的 ht=(实测 ht=49.53mm 排出 140.73pt,与
+% docx 的 140.4pt 差 0.33pt,可忽略),本宏只用于确有需要的场合。
+\newcommand{\lwblank}[1]{%
+ \par
+ \@tempcnta=0
+ \loop\ifnum\@tempcnta<#1\relax
+ \mbox{}\par\advance\@tempcnta by 1
+ \repeat}
+
+%======================================================================
+% 8. 表外标题
+%
+% 原 docx 第 1 段:宋体、加粗、sz=28(14pt)、jc=center
+% 注意字号与正文相同,只靠加粗区分,不是常见的大标题。
+%======================================================================
+\newcommand{\lwtitle}{%
+ \par
+ \begingroup
+ \centering
+ {\songti\bfseries\fontsize{14}{15.6}\selectfont 劳务发放说明表\par}%
+ \endgroup}
+
+%======================================================================
+% 9. 表后空行
+%
+% 原 docx 表格之后还有一个 jc=center 的空段落。
+%======================================================================
+\newcommand{\lwtail}{\par\null\par}
+
+\AtBeginDocument{\lwbodyfont}
+\endinput
\ No newline at end of file
diff --git a/form2/劳务发放说明表.pdf b/form2/劳务发放说明表.pdf
new file mode 100644
index 0000000..f3bc389
Binary files /dev/null and b/form2/劳务发放说明表.pdf differ
diff --git a/form2/劳务发放说明表.tex b/form2/劳务发放说明表.tex
new file mode 100644
index 0000000..8f3b21e
--- /dev/null
+++ b/form2/劳务发放说明表.tex
@@ -0,0 +1,85 @@
+%======================================================================
+% 中国海洋大学 劳务发放说明表
+%
+% 编译: xelatex 劳务发放说明表.tex
+%
+% 本模板不含真人信息:姓名、人数、项目名称一律用 × 占位。
+% 填表时只改下面【第 1 节】。
+%
+% 版式来源:SynologyDrive/实验室管理/劳务补贴/劳务发放说明表.docx
+% 所有尺寸已在 ouclw.sty 内注明换算过程;要改版式请改 sty。
+%======================================================================
+\documentclass[UTF8,fontset=none]{ctexart}
+\usepackage{ouclw}
+
+%======================================================================
+% 1. 表格内容(填表时只改这一段)
+%======================================================================
+\newcommand{\lwunit}{{\songti ××××××××}} % 用工单位(学部/学院)
+\newcommand{\lwreason}{{\songti ××××}} % 用工事由
+\newcommand{\lwnote}{} % 备注(可留空)
+
+% 劳务人员从事的具体工作。
+% ⚠️ 原来写的是“聘请秦依康等 2 位研究生参与《观测数据驱动的渤海生态系统
+% 健康评估关键技术研发》项目的研究工作。”——真人姓名与真实项目名已换成
+% × 占位,句式保持不变。
+\newcommand{\lwwork}{%
+ 聘请{\songti ×××}等{\songti ×}位研究生参与《{\songti ×××}》项目的研究工作。}
+
+%======================================================================
+% 2. 正文
+%======================================================================
+\begin{document}
+
+\lwtitle
+
+%======================================================================
+% 3. 表格主体
+%
+% ⚠️⚠️ 每行写满 4 个格子 + 结尾 \\,跨度不用管(已写死在 ouclw.sty 里)。
+% 若某格是合并的起点,它后面要补 (n−1) 个空 &,凑满 4 格。
+%
+% ⚠️⚠️⚠️ 合并格里的文字【必须】用 \lwfit / \lwcell 等定宽 \parbox 包起来。
+% 因为 cell{r}{c}={c=n}{c} 的 {c} 是【不折行的 LR 模式】:
+% 文字比所跨各列合计更宽时,它不折行,而是把列撑宽、整表超出版心。
+%======================================================================
+\begin{lwtable}
+
+%---- R0 用工单位 | 单位名 ---------------------------------------------
+% docx 里两格都是 2 段:C0 “用工单位”/“(公章)”,C1 单位名 + 1 个空段。
+% 两格内容都刚好填满行高 ⇒ vAlign 取 center 还是 top 结果相同。
+% ⚠️ 必须把那个空段补出来,否则 C1 只剩 1 段(高 12.6pt),会被
+% m 居中到格子中部,单位名比 C0 低 7mm 左右。
+用工单位\par (公章)
+ & \lwcellv{\lwunit\lwblank{1}}
+ & & \\
+
+%---- R1 用工事由 | 事由 -----------------------------------------------
+% 唯一一个 vAlign=center 的值格,只有 1 段。
+用工事由
+ & \lwcellv{\lwreason}
+ & & \\
+
+%---- R2 劳务人员从事的具体工作 | 说明 ---------------------------------
+% C0 3 段(“劳务人员”/“从事的具”/“体工作”),vAlign=center。
+% C1 共 9 段:长句 + 8 个空段 = 140.4pt,刚好等于行高 ⇒ 贴顶、下方留白。
+% ⚠️ 这 8 个空段不能省,否则长句会被居中到 140pt 格里的一半处(下移 64pt)。
+劳务人员\par 从事的具\par 体工作
+ & \lwcellv{\lwwork\lwblank{8}}
+ & & \\
+
+%---- R3 三方签字 ------------------------------------------------------
+\lwsign{\lwspanA}{批准单位负责人签字}
+ & & \lwsign{\lwwc}{用工单位负责人签字}
+ & \lwsign{\lwwd}{经办人签字} \\
+
+%---- R4 备注 | 内容 --------------------------------------------------
+备注
+ & \lwcell{\lwnote}
+ & & \\
+
+\end{lwtable}
+
+\lwtail
+
+\end{document}
\ No newline at end of file