36 共聚焦成像与聚焦法测高
Part VIII 走到这里,前面五种三维成像各凭一条几何或光学约束把高度换算成可测的图像量:双目靠视差、结构光与相位偏折靠相位、激光三角靠位移、光度立体靠明暗。它们有一个共同点——都把镜头的景深(depth of field)当成越大越好的友军,恨不得整个测量范围内处处清晰。本章反其道而行,把景深有限这件”坏事”当成测量手段:镜头只有恰好对焦的物面才清晰,那么沿光轴逐层扫描、看每个像素在第几层最清晰,那一层的 Z 位置就是该点的高度。一句话——“什么时候最清楚,物体就在那个高度”。这就是聚焦法测高(focus variation,又称 shape from focus),以及与它同源、靠针孔在物理上排除离焦光的共聚焦显微(confocal microscopy)。它们速度慢、视场小,却是显微尺度形貌测量的主力:表面粗糙度、刀具刃口圆弧、微结构台阶高度,量到亚微米靠的就是这一族方法。
图 36.1 是本章的出发点——同一个阶梯面在三个对焦高度下采集的切片。注意观察:随着对焦面上移,左、中、右三段台阶依次变清晰,而图中那一块始终平滑模糊的区域,正是本章后半要重点讨论的”失效区”。
36.1 聚焦法测高原理
回忆 章节 3 关于景深与清晰度的讨论:一个物点只有落在对焦平面附近的景深范围内,才在像面上汇聚成清晰的点;偏离对焦面越远,弥散圆越大,图像越模糊。把这件事量化:若物点高度为 \(h\),对焦面位于 \(z\),则离焦量 \(|z-h|\) 越大,该点邻域的高频细节被抹得越平。本章的合成数据正是按这个物理建模——每张切片对每个像素施加标准差 \(\sigma=0.4\,\text{px}\) 每 10 μm 离焦的空变高斯模糊,对焦处 \(\sigma\to 0\)、纹理最锐。
于是测高的流程清晰了:沿光轴方向以固定间距采集一摞图像,构成焦点堆栈(focus stack);对每个像素,逐层计算一个清晰度(focus measure)数值,得到一条沿 \(z\) 的清晰度曲线;曲线的峰值位置对应的 \(z\),就是该像素的高度。
清晰度算子要回答”这个邻域有多锐”,本质上是在度量局部高频能量——这与 章节 13 的梯度算子同根同源。工程上常用两类:Tenengrad(Sobel 梯度幅值平方和)与改进拉普拉斯之和(sum of modified Laplacian, SML)。本章实现采用后者:先对每像素取 x、y 两个方向二阶差分的绝对值之和
\[ \text{ML}(x,y) = \big|\,2I(x,y) - I(x{-}1,y) - I(x{+}1,y)\,\big| + \big|\,2I(x,y) - I(x,y{-}1) - I(x,y{+}1)\,\big|, \]
之所以取绝对值再相加(而非像普通拉普拉斯那样直接相加),是为了避免 x、y 方向曲率反号时相互抵消;再在每像素周围 \(9\times 9\) 窗口内把 ML 求和,得到该像素在该层的清晰度。窗口求和是关键的一步——单像素的二阶差分对噪声极敏感,必须靠邻域聚合把清晰度曲线”压平滑”,峰才稳。
为什么聚焦法只测相对于堆栈的高度,而不需要外部标定尺?因为它问的不是”这点离相机多远”,而是”这点在第几层最清晰”——层号乘以已知的切片间距就是物理高度。Z 轴精度因此完全由扫描台的步进精度决定,与镜头的横向标定无关。这也是它在显微尺度能轻松做到亚微米的原因:把一个机械步进量做准,比把一套成像几何标定准容易得多。
图 36.2 把这条清晰度曲线画了出来。蓝色那条来自一个有纹理的清晰像素(C 平台,真实高度 100 μm):清晰度随 \(z\) 先升后降,在 \(z\approx 100\,\mu\text{m}\) 处形成一个明确的尖峰——峰在哪里,高度就在哪里。灰色那条留待 小节 36.3 讨论。
36.2 量化与亚像素
直接取”清晰度最大的那一层”作为高度,会立刻撞上一个精度上限:切片间距本身就是量化(quantization)步长。本章堆栈 21 层、间距 10 μm,于是粗高度只能是 …、90、100、110… 这些 10 的整数倍(叠加一个 −7 μm 的台原点偏移),相邻高度差不到 10 μm 的细节全被并到同一层。图 36.3 把粗高度图画出来——本该是连续过渡的斜坡,被切成了一道道 10 μm 宽的等高条带(terracing),活像等高线地形图。这正是量化误差的形状。
突破量化的办法,是本书反复出现的亚像素三联思路(章节 14 的边缘、章节 20 的卡尺都用过):真正的峰几乎从不恰好落在采样点上,但峰附近的曲线形状里藏着它的真实位置。具体做法是对峰值层 \(k_p\) 及其左右两邻层的清晰度 \((f_{k_p-1}, f_{k_p}, f_{k_p+1})\) 拟合一条抛物线,取顶点作为亚层峰位:
\[ \delta = \frac{1}{2}\,\frac{f_{k_p-1} - f_{k_p+1}}{f_{k_p-1} - 2f_{k_p} + f_{k_p+1}}, \qquad h = (k_p + \delta)\cdot \Delta z + z_0, \]
其中 \(\delta\in[-1,1]\) 是相对峰值层的亚层偏移,\(\Delta z=10\,\mu\text{m}\) 为切片间距。这一步把高度从”10 μm 的整数倍”解放成连续值。图 36.4 是细化后的高度图——条带消失了,斜坡恢复成平滑过渡,三段平台也变得干净。
数字是诚实的。在三段平坦平台上,高度 RMS 误差从量化的 3.000 μm 降到亚像素的 0.342 μm,改善 8.8 倍;右侧斜坡区从 2.933 μm 降到 0.442 μm,改善 6.6 倍。台阶高度(三平台亚像素高度均值之差)测得 B−A = 49.935 μm、C−B = 50.044 μm、C−A = 99.980 μm,对照真值 50 / 50 / 100 μm 基本精确——亚微米的台阶测量,就是这样从 10 μm 的量化栅格里”插”出来的。
抛物线插值的前提是峰附近曲线近似对称、二阶可导。当切片采样太稀(峰只覆盖两三层)或曲线被噪声啃出毛刺时,这个假设会松动,\(\delta\) 估计随之失真。工程上有两条对策:扫描时把切片间距取得密一些(让峰跨越 5 层以上),以及对清晰度曲线先做轻度平滑再插值。本章 1.5 灰阶的读出噪声正是为了让这种亚像素增益经得起噪声检验——干净无噪的合成数据会高估真实精度。
36.3 纹理依赖
聚焦法有一个致命前提,图 36.2 的灰色曲线已经剧透了:清晰度曲线要先有纹理,才会有峰。清晰度算子度量的是局部高频能量随离焦的衰减;可如果某个像素邻域本身就没有高频内容——一块均匀、抛光、无纹理的表面——那么不论对焦与否,它的清晰度都接近一个低平的常数。曲线没有峰,“峰位=高度”的整条逻辑链就断了:算法只能在一片噪声里随便挑个最大值当峰,给出的高度纯属随机。
图 36.5 是置信度掩膜:以峰显著度(归一化峰高)0.5 为阈值,把不可信像素涂黑。结果很直观——B 平台里那块纹理贫乏区被整片遮掉了。量化对比同样鲜明:贫纹理区的有效率仅 18.7%(1232/6600),而有正常花岗岩程序纹理的区域有效率达 100%(14700/14700)。这块失效区不是凭空设计的反例,它就是同一立体表面上的一块无纹理区——现实里抛光面、镜面、大面积平整漆面,处处都是它。
对策无非两条,与双目、结构光如出一辙:要么主动制造纹理——投结构照明、喷哑光剂,给表面”种”上高频;要么老实承认失效——用置信度门槛把不可信点剔除,绝不让随机峰位污染下游测量。把无纹理区的垃圾高度当真,比留一个空洞危险得多。
36.4 共聚焦的光学层切
前面四节讲的都是聚焦法,靠的是算法在事后的焦点堆栈里找清晰峰。真正的共聚焦(confocal)则在光学物理层面解决同一个问题,二者必须诚实区分——本章实验做的是前者,这一节描述的后者无配套仿真。
共聚焦的核心是一对共轭针孔(conjugate pinhole)。点光源经针孔照明、聚焦到物面上的一个点;该点反射或荧光发出的光,再经物镜汇聚,穿过一个与照明针孔光学共轭的探测针孔才能到达探测器。关键在于:只有来自对焦面那个点的光,才恰好汇聚在探测针孔上、顺利通过;来自对焦面上方或下方的离焦光,在针孔平面上是一个弥散斑,绝大部分被针孔挡掉。这样探测器收到的信号几乎只来自当前对焦的薄薄一层——这就是光学层切(optical sectioning)。逐点扫描(点扫描共聚焦靠振镜或转盘扫过整个视场)、再逐层改变焦面高度,就能把三维结构一层层”切”出来。
与聚焦法对照,区别一目了然:共聚焦靠针孔在光路里物理排除离焦光,每一层信号本身就只含对焦面信息,轴向分辨率由光学衍射极限决定,可达亚微米甚至更高;聚焦法靠算法在含离焦的完整图像里事后找清晰峰,离焦光始终参与成像,精度受清晰度算子与纹理质量制约。各有适用:共聚焦精度高、层切干净,但点扫描慢、设备贵,且仍需要被测面返回足够信号;聚焦法用普通显微镜加 Z 扫描台即可、面阵单层一次成像因而快得多,代价是严重依赖表面纹理。一句话——精度优先选共聚焦,速度优先且表面有纹理选聚焦法。
36.5 SciVision 实现
值得专门记一笔:在本书三维部分一连串”模块静默无输出/崩溃”的 SDK 之后(相位测量、激光三角、光度立体无一可用),SCIMV::SciSv3DFocus 是罕见的可用案例——它真的返回了有效深度图。流程是两步:CalGradArray 先把焦点堆栈逐层算成梯度(清晰度)图栈,CalDepthMapByFocusStack 再据此输出一张 SciRangeImage 深度图。
SCIMV::SciSv3DFocus fo;
SciImageArray grad;
fo.CalGradArray(arr, 21, &grad); // 焦点栈逐层清晰度(梯度)图,meanSize=21
SciRangeImage depth; SciImage color;
fo.CalDepthMapByFocusStack(arr, grad, 31, 31, // 平滑窗 31×31
1.0, 1.0, ZSTEP, // x/y 分辨率、z 切片间距(μm)
0, false, 1,
&depth, &color);
double z = depth.GetValue(row, col) * depth.ResolutionZ() + depth.OffsetZ();但它有一个明确的短板:深度按最近切片量化、没有亚像素。在采样点上验证可见,SDK 给出的高度恰好读到 10 / 60 / 110 这些切片整数倍上,完全没有 小节 36.2 的亚层插值。这构成一个诚实而难得的有利对照:手写的抛物线插值(亚微米)严格优于 SDK 的 10 μm 量化输出——不是因为 SDK 崩了,而是因为它只做到了”取最近层”这一步。本章的代码因此两条腿走路:用 SDK 验证堆栈测高这条路通,再用手写清晰度算子加峰插值把精度推到亚微米。下面是手写部分的两段核心——清晰度(SML 窗口求和)与峰的抛物线插值:
// 改进拉普拉斯:x/y 二阶差分取绝对值后相加(避免反号抵消)
float lx = std::fabs(2.0f*I[c] - I[c-1] - I[c+1]);
float ly = std::fabs(2.0f*I[c] - I[c-W] - I[c+W]);
ml[c] = lx + ly; // 再在 9×9 窗内求和得 SML 清晰度
// 抛物线顶点 → 亚层峰位 δ ∈ [-1,1]
double den = a - 2*b + c; // a,b,c = 峰左/峰/峰右三层清晰度
if (std::fabs(den) > 1e-9) delta = 0.5*(a - c)/den;
double h = (kp + delta)*ZSTEP + ZBASE; // 连续高度(μm)工业案例:刀具刃口的微观测量
硬质合金铣刀的刃口质量直接决定切削寿命,需要量到微米级的刃口圆弧半径与崩刃缺口。某产线用聚焦法在显微镜下对刃口快速成焦点堆栈,几秒钟就能出一张高度图,节拍远胜逐点共聚焦扫描。问题出在抛光过的刃口背面:那里表面光洁、局部纹理不足,清晰度曲线平坦,高度图上出现成片的随机跳变,把本该平滑的刃面”测”出了根本不存在的沟壑。对策分两层:一是给刃口加一束结构照明,在光洁面上投出可供清晰度算子抓取的高频纹理;二是用峰显著度门槛把仍不可信的点剔除,宁可留空也不输出垃圾。教训很直接——聚焦法的速度优势以纹理为前提,遇到无纹理处,要么造纹理,要么换共聚焦。
36.6 小结
本章把”景深有限”从缺陷变成了测高手段,要点如下。
- 峰即高度。沿光轴采集焦点堆栈,对每像素算逐层清晰度曲线,峰位对应的 Z 就是高度;清晰度算子(Tenengrad / 改进拉普拉斯)本质是局部高频能量度量,与边缘梯度同源。
- 切片间距就是量化步长。直接取峰值层只能给出 10 μm 整数倍的台阶状高度;对峰附近三层做抛物线插值即得亚层峰位,本章实测把平坦区 RMS 从 3.000 μm 降到 0.342 μm(8.8 倍),台阶测量精确到 49.935 / 50.044 / 99.980 μm。
- 聚焦法严重依赖纹理。无纹理区的清晰度曲线平坦无峰,峰位由噪声决定(贫纹理区有效率 18.7% vs 纹理区 100%);必须用置信度门槛剔除,或主动投纹理补救——这与双目、结构光的无纹理失效是同一道坎。
- 共聚焦与聚焦法同源而异路。共聚焦靠共轭针孔在光学上排除离焦光、做硬层切,精度亚微米但慢;聚焦法靠算法事后找清晰峰,快但依赖纹理。精度优先选前者,速度优先且有纹理选后者。
- 罕见的 SDK 可用案例。
SciSv3DFocus返回有效深度图,但最近切片量化、无亚像素——手写峰插值严格更优,构成一次诚实的有利对照。
聚焦法的奠基性工作是 Nayar 与 Nakagawa 提出的 Shape from Focus (Nayar 和 Nakagawa 1994);各类清晰度(聚焦测度)算子的系统比较与评测见 Pertuz 等人的研究 (Pertuz, Puig, 和 Garcia 2013)。聚焦法与共聚焦的系统论述(清晰度算子的比较、共聚焦光学的细节)另可参阅 Steger 等人的著作 (Steger, Ulrich, 和 Wiedemann 2018)。至此 Part VIII 的六种三维成像技术全部走完:双目与聚焦法是被动/弱主动,结构光、激光三角、光度立体、相位偏折是主动;激光三角与结构光主攻宏观毫米级、共聚焦专攻微观微米级;前五种各自服务漫反射表面,相位偏折独守镜面。六种技术没有一种通吃——每一种都有自己的失效边界(无纹理、镜面互反射、遮挡、非朗伯、透明、速度),三维选型的本质,就是先认清工件落在谁的失效边界之外。




