“你的视线追踪系统准确率是多少?”每次被问到这个问题,我都会反问一句:“你说的准确率,是在什么条件、什么数据集、什么误差定义下算出来的?”这不是抬杠,而是这两年做视线追踪(gaze tracking)评估框架时踩了一堆坑之后最真实的反应。单独抛出一个“95%”或者“误差小于1度”的数字,在视线追踪这个领域里几乎没有任何可比较的意义——测量口径不同,结果能差出一个数量级。
这篇内容我打算把两件事讲透:一是视线追踪的基础知识,尤其是误差从哪来、评估的是什么;二是性能评估框架怎么搭,从指标定义到数据集选择,再到实施时最容易翻车的地方。不管你是刚接触这个方向的学生、准备在交互产品里集成视线追踪的工程师,还是想复现论文结果的研究者,这套内容应该都能帮你少走不少弯路。我会把自己在实际评估过程中遇到的坑也一起放进来,那些在论文里看不到的细节,往往才是决定评估结论是否可信的关键。
1. 视线追踪到底在测什么:先搞懂误差从哪来
1.1 从眼球成像到视线方向:一条完整的技术链路
视线追踪的本质,是通过摄像头捕捉眼部图像,推断人的注视方向或注视点位置。听起来简单,但实际上这条链路上任何一个环节出问题,最终评估出来的误差都会大幅上升。
先看最主流的方案:基于瞳孔和角膜反射的方法。摄像机拍摄人眼时,角膜表面会对红外光源产生反射,形成一个亮斑,叫作普尔钦斑(Purkinje image)。瞳孔中心的位置和角膜反射点的相对向量,会随着眼球转动而变化——这个向量和屏幕上注视点之间存在着一个映射关系。这就是2D映射法(2D mapping)的物理基础。
另一种是3D模型法。它建立眼球的三维几何模型,利用瞳孔中心和角膜反射数据重建光轴(optical axis),再通过个人的校准参数补偿视轴(visual axis)与光轴之间的夹角(kappa角),最终输出三维视线方向。3D方法的优势在于更鲁棒,允许头部在一定范围内自由移动,但代价是标定和模型参数更复杂。
还有一类是外观法(appearance-based)和基于深度学习的方法。这类方法不再显式提取几何特征,而是直接用CNN或Transformer从眼部图像回归出视线方向。训练数据来自大量标注样本,典型代表就是MPIIGaze、GazeCapture、ETH-XGaze这些数据集上训练出的模型。深度学习方法的优势是可以在无红外设备、普通RGB摄像头下工作,硬件成本低,但数据依赖性强,跨人、跨场景的泛化能力始终是个问题。
1.2 光轴与视轴:很多人忽略的关键概念
在做视线追踪评估之前,必须区分光轴和视轴。角膜表面中心和瞳孔中心的连线是光轴,它表示的是一种几何上的眼球朝向。但人眼真正看东西的方向是视轴,它经过中心凹(fovea),与光轴之间存在一个偏移角,也就是kappa角。kappa角的个体差异很大,通常在1到7度之间,少数人可能更大。
这意味着什么?如果你做的系统不经过个人校准,直接拿光轴方向当作注视方向,那么理论上所有人的系统误差起点就已经有几度了。这也是为什么绝大多数消费级视线追踪设备都要求做一次个人校准——校准的核心目的之一就是估算并补偿kappa角,把个体差异带来的系统性偏差降下来。所以在评估框架里,校准流程的设计几乎是决定精度的第一关键因素。
1.3 误差的三个来源层次
我把影响评估结果的误差来源分成三层,调试和评估时逐层排查比较有效:
- 信号源误差:图像分辨率低、眼部区域像素太少、光照变化导致瞳孔分割不准。这一层属于底层信号质量,摄像头的物理参数决定了误差下限。
- 模型误差:映射模型复杂度不够、深度学习模型容量不足、训练数据分布与测试场景不匹配。
- 系统误差:摄像头与屏幕相对位置标定不准、头部运动后几何关系变化、校准漂移、延时导致的时间错位。
实际评估时,很多人测出来的精度不太好,第一反应是换更厉害的深度学习模型,但其实检查一下发现往往是屏幕和摄像头的相对位姿标定出了偏差。这个顺序搞反了,会浪费大量时间。
2. 性能评估的核心指标:别只盯着一个“准确率”
2.1 角度误差:视线追踪的“通用货币”
视线追踪的性能评估,最核心也最通用的指标是角度误差(angular error),单位是度。它衡量的是估计视线方向与真实视线方向之间的夹角。
为什么不用像素误差或者屏幕距离误差?因为视线是一个三维方向问题。同一个视线方向,在距离屏幕60厘米和80厘米的两个人身上,投射在屏幕上的注视点会相差很远。用屏幕像素误差来评估,设备距离一变数值就不具有可比性了。角度误差与设备距离无关,是标准化的度量,所以不管是论文还是商业设备的规格书,都优先报告角度误差。
角度误差的数学定义是:两个单位向量之间的夹角,等于它们点积的反余弦值。具体到评估中,就是把每一帧的预测视线方向和真值视线方向都归一化为单位向量,逐帧计算夹角,最后对全部帧取平均。
需要注意,平均值不能代表一切。视线追踪误差分布通常不是正态的,而是近似类似长尾分布——大部分帧误差很低,但存在一部分“坏帧”误差极大。这种情况下,均值容易被少数异常值拉高,中位数(percentile 50)更能反映典型表现。很多商用设备只在规格书里报均值,不报分布,就是利用了这个统计特性。
2.2 精度(Precision)、RMS抖动与数据有效性
除了accuracy(准确度,衡量系统性偏差),还要看precision(精度,衡量随机性抖动),直白一点说就是:测出来的注视点稳不稳。
精度通常用RMS(均方根)标准差表示,即连续采集固定注视点时,估计点的分布离散程度。打个比方,如果准确度差但精度高,说明你瞄得歪但很稳,可以通过简单校准修正;如果精度差,即使平均值看起来不错,实际使用体验也会很糟糕——在交互场景里用户会明显感觉到光标在飘。
另外还有一个经常被忽视的指标:数据有效性(data validity),或者叫数据缺失率。视线追踪不是每一帧都能成功估计视线的。眨眼、头部大幅度转动、镜片反光、眼睛太小或遮挡、光照强烈变化,都可能导致追踪丢失或输出置信度极低的帧。一个系统如果把所有失效帧的误差都记成超大误差,平均值会很难看;但反过来,如果系统选择性地输出结果,只报“我有把握的那些帧”,精度数字才能好看。
所以评估框架里必须约定两个东西:一是追踪失败的定义(超过多少角度误差算失败,或连续多少帧丢失算失效),二是覆盖率,即有效帧数占总帧数的比例。这两个指标结合,才能还原真实性能。
2.3 回归指标与分类指标怎么搭配
视线追踪本质上是一个回归任务,输出连续向量。但学界和实践里也会借用一些分类任务的指标来观察性质。
- AUC和曲线下面积:适用于眼动分类任务,比如区分“正在看目标A”还是“正在看目标B”,或者评估视点检测任务的质量。
- DLC 阈值通过率(如精度在0.5度、1度、2度内的占比):比起单一均值,这个指标更直观,也更容易与产品需求对应起来。例如医疗和科研场景常要求误差在0.5度内,而消费级应用1到2度基本可用。
- Pearson相关系数:评价估计视线与真实视线的线性相关程度,能反映趋势追踪能力,但注意相关性和绝对误差是两个维度,相关性很高不代表绝对偏差小。
在实际报告里,我建议至少同时给出:平均角度误差、角度误差中位数、RMS精度、数据有效性/覆盖率、2度内误差占比。这样一份完整性能报告才能支撑起后续的横向对比。
3. 搭建评估框架:数据、任务与流程设计
3.1 数据采集与标注:评估的地基
一个性能评估框架,最先要确定的是评价数据怎么来。数据采集的协议直接决定了评估结论的外推范围。
第一点是场景定义。你的系统是面向桌面办公、车载监控、还是手机前摄?每个场景下摄像头的机位、朝向、距离、光照条件完全不同。针对特定场景采集数据来评估,结论只能在该场景下成立。
第二点是标定真值(ground truth)。视线追踪的真值不像图像分类那样天然存在,它需要一套外部装置来定义。最常见的方案是让用户注视屏幕上特定位置(标定点),利用屏幕上的已知坐标反推真实视线方向;在3D方案里还需要屏幕坐标系与摄像头坐标系的标定参数。另一种方案是用头动式眼动仪(如头戴式设备)作为参考标准,来评估远程式或嵌入式的跟踪系统。
推荐一个落地策略:采集时同步录制场景摄像头画面、眼部近景画面、标定点的屏幕坐标和时间戳。时间戳同步非常关键,缺失了它,后续评估里的每一帧的对应关系都会错位,误差数据基本没法用。
3.2 数据划分策略:跨人、跨设备与跨数据集
评估框架里最容易犯的错误是数据划分不合理。
很多人训练时把一个人采集的数据随机分成训练集和测试集,结果测试帧和训练帧来自同一个人的同一段视频。眼睛的形状、虹膜颜色、眼睑形态等等个体特征都会被模型记住,导致测试误差低得离谱。这种叫同身份泄漏(identity leakage)。正确做法是按人划分(leave-one-person-out):训练集中绝不能出现测试集中任何人的图像。
更严格的评估还要做跨数据集测试。在其训练场景A上表现很好的模型,换到场景B(不同摄像头、不同光照、不同人群)精度往往会大幅下降。论文报告里常见的“在MPIIGaze上达到5度以内”并不算什么,真正考验的是在ETH-XGaze上训练、直接在MPIIGaze上测试,这类跨域评估才是副本难度。
推荐评估矩阵设计:
| 维度 | 方案 | 目的 |
|---|---|---|
| 按人划分 | 训练测试人员完全隔离 | 测试跨人泛化 |
| 按场所划分 | 训练与测试场景不同 | 测试环境鲁棒性 |
| 按设备划分 | 换摄像头或屏幕 | 测试设备无关性 |
| 按头部范围 | 分头部静止和自由移动 | 测试头动解耦性能 |
3.3 一次标准评估流程的完整清单
把过去方法整理下来,目前在项目里固定执行的评估流程大致是这个顺序,你可以直接拿着用:
- 确定评估任务:注视点估计(屏幕坐标)还是视线方向估计(空间方向),两者用的真值和误差口径不同。
- 准备评估数据集:至少包含60人以上的数据,性别、戴镜与否、肤色、年龄段分布尽量均匀,同时保证头部姿态和光照多样性。
- 定义指标口径:统一角度误差的计算方式(方向向量归一化方式),统一坐标系的定义(左眼坐标系还是右眼坐标系、摄像机坐标系是不是OpenCV规范)。
- 划分数据集:按人划分训练测试集,测试集绝对不能混入训练帧;必要时额外划分出超域测试集。
- 跑通基准管线:用开源模型跑一遍baseline,确认管线一致性,再评估自己的模型。
- 记录完整统计量:均值、中位数、标准差、RMS、覆盖率、阈值通过率,一张都不要省。
- 保存随机种子和数据版本:确保实验可复现。
特别注意,第5步我非常推荐先跑baseline再跑自己的模型,否则无法判断你的评估管线是否与其他发表工作对齐。管线上差一个小数点,误差就能差出0.5度以上。
4. 常用数据集与基准:选对战场再打分
4.1 几个公开数据集的定位对比
视线追踪领域里,不同数据集的数据规模、采集条件和标注格式差异巨大,先看当前使用最广泛的几个:
| 数据集 | 人数 | 特性 | 标注类型 | 适用场景 |
|---|---|---|---|---|
| MPIIGaze | 15人(约21万帧) | 日常使用笔记本电脑场景,自然光照 | 屏幕注视采样点(近似3D视线) | 小规模baseline,跨人评估 |
| GazeCapture | 超过1450人(约200万帧以上) | 移动端众包采集,设备种类多样 | 屏幕注视点 | 深度学习模型训练 |
| ETH-XGaze | 110人(约100万帧) | 高分辨率近景RGB图像,可控照明 | 3D视线方向(左/右眼分别) | 训练鲁棒模型、3D视线估计 |
| Columbia Gaze | 56人(约5880帧) | 头部固定,控制注视角度网格 | 屏幕注视点+头部方向 | 早期几何方法评估 |
每个数据集都有自己的倾向。MPIIGaze帧数不小,但采集的是日常环境图像,光照混乱、噪声多,这恰恰是评估真实场景泛化能力的好材料。ETH-XGaze图像干净、分辨率高、标定严格,适合训练模型,但如果在它上面测出的误差很低,只能说明在该数据集定义的理想环境里性能好,不代表真实场景。
4.2 数据集选择如何影响评估结论
很多刚入门的人拿到数据集直接用,也没有思考过数据集的“评估难度”。这种做法很容易得出误导性结论。
例如,在MPIIGaze上做同数据集评估,如果按人划分,平均角度误差通常在5到7度;但如果数据划分时不做人员隔离,误差可以降到3度左右。这不是模型变强了,而是评估协议变了。反过来,在ETH-XGaze上训练的模型在MPIIGaze上做跨域测试,平均误差到9度以上都是常见的。
所以我给的建议是:评估结论必须附带三个上下文——数据集名称、划分方式和是否校准。写报告时这三点写清楚,比单纯写一个“精度达到多少”有价值得多。
4.3 算法复现与结果对比的注意事项
如果你参考论文里的数值,需要特别小心几个细节:
一是是否使用个人校准。很多学术方法在测试时对每个用户做一次性校准(few-shot校准,比如取5到9个标定点),这会大幅降低误差。但产品落地时往往不允许每次换人都校准,两种条件下的结果不能直接比。
二是误差是否包含头部姿态误差。头部姿态估计本身有误差,视线方向由头部朝向和眼球朝向叠加而成。一部分工作报告的是纯眼球贡献,另一部分则是端到端的总误差,两者的口径完全不同。
三是图像输入格式。是用整张脸输入还是只用眼部裁剪图,输入分辨率多少,灰度还是彩色,都会影响最终结果。复现时先把这些对齐,再谈性能比较。
5. 实际评估中的四个大坑与我的排查经验
5.1 头部姿态与视线误差的耦合
这是评估框架里最大的一个坑。视线方向 = 头部姿态向量 + 眼球姿态向量,分别在头部坐标系和世界坐标系中定义。如果头部姿态估不准,即使眼球估计再准,最终方向合成时也一样会错。
排查经验:做受控消融评估。设计一组头部静止条件下的测试,再设计一组头部自由运动条件下的测试,两组一对比就能拆出头部姿态引入的误差有多少。如果头部自由组比头部静止组误差高很多,说明问题主要出在头部姿态链路。另外,测试时记录头部姿态估计的误差,会极大加速定位问题所在。
5.2 校准与漂移问题
视线追踪里有一个普遍存在的现象:用户刚校准完,精度还不错;用了5到10分钟后,误差慢慢变大。原因主要是眼球和面部肌肉的细微状态变化、坐姿改变导致头部与摄像头的相对位姿漂移、以及光照变化造成的瞳孔中心检测偏移。
评估时如果不限制测试时长,数据里的后半段会包含大量漂移帧。我的处理方法是:分时间段分别统计误差,看看第1分钟、第5分钟、第10分钟的性能衰减情况。产品化时要能接受“校准后15分钟误差不超过某个阈值”这一指标,这个指标通常比单纯精度更能反映用户实际体验。
此外,校准点的数量和布局也有讲究。9点校准显然比5点校准精度高,但操作成本高。如果是个消费产品,很可能会选择1点或隐式校准(例如用鼠标点击位置作为隐式校准点),这时的性能评估就必须包含这种“弱校准”配置下的表现。
5.3 光照与个体差异的隐藏影响
大多数学术数据集在受控光照下采集,但真实光照场景千变万化。我在评估时发现一个规律:白天自然光充足时系统表现很好,晚上在昏暗的台灯下误差暴涨。解决方案是在评估数据集里专门加入一个“光照挑战子集”,记录光照强度(lux值)和光源色温,并在报告中把光照条件和误差的对应关系列出来。
个体差异就更复杂了。单眼皮用户在部分深度学习模型上的误差比双眼皮用户高20%以上,佩戴框架眼镜会影响红外方案(反光)和外观方案(遮挡),瞳孔颜色深浅也会影响外观法的特征提取。所以评估群体必须做到人群多样性,否则你测出来的可能是“某一类人群的性能”。
5.4 时间同步与延迟误差
很多人忽略的一个隐蔽误差源是时间戳不对齐。摄像头采集到眼睛图像后,数据处理耗时、屏幕刷新率、GPU推理速度等综合起来会产生一个几十毫秒到几百毫秒的延迟。用户在扫视目标时,眼睛运动速度很快(扫视速度最高可达每秒500度以上),哪怕100毫秒的延迟,在快速扫视过程中就能带来好几度的等效误差。
排查逻辑:如果在测试视频里发现误差峰值总是出现在注视点跳变之后的一帧或几帧,大概率就是时序错位问题。解决方法是让评估数据的录制端统一使用硬件时钟同步(如PTP),或者在后期用插值对齐各信号源的时间戳。延迟是视线追踪系统体验的大敌,评估时我建议除以追踪状态还要专门记录系统端到端延迟,交互类应用里延迟往往比精度更影响用户感受。
6. 跑通自己的评估流水线:最小可行配置建议
理论说了一堆,最后给一个可以直接上手搭起来的最小评估流水线骨架。
如果你只在笔记本上工作,可以用普通的RGB摄像头采集用户注视屏幕时的图像,屏幕上依次显示标定点(通常用5点或9点),采集得到“眼睛图像 + 对应的屏幕注视点真值”。利用OpenFace或MediaPipe的FaceMesh提取眼部和面部关键点,计算注视方向作为预测结果,与真值对比得出误差。数据集规模不需要大,但一定要保证至少10个人、每人两次采集(一次校准序列一次测试序列),这样得到的数据已经有初步参考意义。
在此基础上,按下面的步骤逐步扩展:
- 先跑通离线评估:把采集的图像离线跑完,打印出平均角度误差、RMS、覆盖率,不追求实时。
- 再接入实时管线:用相同的算法做线上推理,对比同一批数据离线结果与在线结果的差异,重点排查延迟对误差的影响。
- 最后加入校准流程:设计一个几秒钟的快速校准,看校准后的误差变化,以及校准的起始误差和漂移趋势。
对于想更严谨做研究的人,建议直接用已有的公开数据集做交叉验证,并且在GPU资源允许的情况下跑多组随机划分取均值,避免随机性带来的结论偏差。
我在实际测试中最常遇到的情况是:模型改进了,误差曲线看起来波动很大,很难判断到底是不是真的变好了。后来养成了一个习惯——固定同一批测试视频和同一份真值文件,任何改动都在这份固定测试集上做AB对比。这样评估出来的置信度高很多,也方便向团队或上级解释性能变化。这套流水线虽然简陋,但“固定测试集+相同指标口径+多人多样性数据”这三点,就是可靠性能评估的精髓。
最后再分享一点:视线追踪的性能评估不是一个一次性的工作,而是一个持续迭代的体系。每次换了摄像头、改了算法、变了目标人群,评估结果都应该被重新审视。不要迷信论文里某个漂亮数字,真正要看的是你的系统在你自己定义的场景、指标和用户群里的表现。把基础概念吃透,把口径定清楚,把流程固定下来,比堆任何花哨的深度模型更值得花时间。