本页目录

  • 如何放置
  • 输入与输出
  • DepthAI v3 ToF 架构
  • ToF 相机的设置差异
  • ToF 设置
  • 快速调优指南:深度图像滤波器
  • 步骤 1:空白状态
  • 步骤 2:时间滤波器(从此开始)
  • 步骤 3:散斑滤波器
  • 步骤 4:空间滤波器
  • 步骤 5:中值滤波器
  • 调优快速参考
  • ToF 运动模糊
  • 最大距离
  • ToF 帧率
  • 使用示例
  • 示例
  • 参考

ToF

Supported on:RVC2
ToF节点将原始飞行时间传感器数据转换为深度图,并输出原始结果及滤波后的结果。该节点适用于集成ToF传感器的设备,例如:ToF深度可直接用于空间节点,例如SpatialDetectionNetworkSpatialLocationCalculator关于与立体视觉的深度质量对比,请参阅ToF深度精度

如何放置

Python

Python
1pipeline = dai.Pipeline()
2tof = pipeline.create(dai.node.ToF)

C++

C++
1dai::Pipeline pipeline;
2auto tof = pipeline.create<dai::node::ToF>();

输入与输出

DepthAI v3 ToF 架构

DepthAI v3 ToF 流水线可理解为两层:
  1. ToF 基础解码 将传感器测量值转换为基础信号(rawDepthamplitudeintensityphase),并处理ToF特定的解码设置,如相位解缠。
  2. 滤波阶段 通过ToF定向滤波预设和运行时滤波器配置,生成滤波后的深度输出(depth)。
RVC2 上,滤波阶段由主机运行。

ToF 相机的设置差异

许多 OAK 深度示例假设经典立体布局(一个彩色摄像头 + 位于 CAM_* 插槽的立体对)。 ToF 相机通常配置为 ToF + 彩色摄像头(两个功能摄像头源),深度来自 dai.node.ToF,而非 StereoDepth通用应用中的常见集成陷阱:
  • 不要将ToF传感器当作普通的彩色预览源。
  • 不要在仅ToF设备上自动创建默认的立体对流。
  • 通过 ToF 构建深度,仅在需要时添加彩色流(例如对齐/叠加)。

ToF 设置

常见基础解码设置(来自 ToFConfig):
  • 光学校正:将径向距离转换为深度(Z-map),使其行为与立体深度一致。
  • 去畸变:默认对 depthamplitude 进行去畸变。
  • 相位解缠:通过增加噪声代价扩展量程。
  • 相位混洗时域滤波:通过合并混洗/非混洗捕获来降低噪声。
  • 突发模式:避免帧复用解码,以牺牲输出帧率为代价减少运动伪影。
不同解缠级别对应的近似量程:
  • 0(禁用):最远约1.87米(80 MHz)
  • 1:最远约3.0米
  • 2:最远约4.5米
  • 3:最远约6.0米
  • 4:最远约7.5米
后处理通过 ImageFiltersImageFiltersConfig 配置。对于基于置信度的清理,请参阅 ToFDepthConfidenceFilterConfig

快速调优指南:深度图像滤波器

调优目标是平衡深度图的干净无噪与运动物体的快速准确更新。 对于ToF深度输出,delta 通常以深度单位(通常为毫米)表示,而 alpha[0.0, 1.0] 范围内的混合因子。 将所有以下数值视为起点,并根据实际场景进行调优。

步骤 1:空白状态

开始调优前,先禁用所有滤波器。 这有助于您测量基准噪声、验证传感器放置/照明条件,并避免用软件滤波掩盖设置问题。

步骤 2:时间滤波器(从此开始)

首先调整 TemporalFilterParams,因为它控制随时间变化的动态平滑。
  • delta:判断深度变化是显著变化还是噪声的阈值。
    • 初始值设为 delta = 15
    • 对于较大物体(例如 ~50 mm 物体高度),使用 delta = 25 以使运动更新更快。
    • 对于小物体,收紧至 delta = 10
  • alpha:当前帧与历史数据的混合权重。
    • 较低的 alpha(例如 0.1)输出更平滑,但可能带来延迟/拖影。
    • 较高的 alpha(例如 0.4)更新更快,但平滑效果减弱。
  • 重要提示delta = 0 会使几乎所有变化都变得显著,并基本绕过时间混合。

步骤 3:散斑滤波器

使用 SpeckleFilterParams 去除单帧中的孤立斑点和椒盐噪声。
  • differenceThreshold(别名:max_diff):判断相邻像素是否属于同一区域的阈值。
  • speckleRange(别名:max_speckle_size):要移除的最大区域大小。
  • 调优策略:逐渐增加 speckleRange 以去除更大的浮动斑点,但避免设值过大导致删除真实小物体。

步骤 4:空间滤波器

使用 SpatialFilterParams 在保留边缘的同时平滑物体表面。
  • alpha:平滑强度(通常较低的值平滑效果更强)。
  • delta:边缘保留阈值;较大的深度跳变被视为边缘,不进行混合。
  • holeFillingRadius:用周围有效数据填充无效(0)像素的半径。
  • numIterations:多次迭代可在轻微处理代价下优化输出。

步骤 5:中值滤波器

当仍有残留椒盐噪声时,使用 MedianFilterParams 进行最终强力清理。
  • 此节点支持的模式:MEDIAN_OFFKERNEL_3x3KERNEL_5x5
  • 选择能解决噪声的最小内核,以尽量减少边缘/细节损失。

调优快速参考

滤波器关键参数主要用途权衡
时间delta, alpha平滑随时间变化的动态噪声平滑度 vs 运动延迟
散斑speckleRange, differenceThreshold去除孤立斑点/噪声清洁度 vs 删除小物体
空间delta, alpha, holeFillingRadius, numIterations保留边缘的表面平滑平滑度 vs 处理代价
中值KERNEL_3x3, KERNEL_5x5强力椒盐噪声清理噪声去除 vs 边缘/细节模糊
有关完整参数定义和运行时配置流程,请参阅 ImageFiltersImageFiltersConfigToFDepthConfidenceFilterConfig

ToF 运动模糊

为减少运动模糊:
  • 提高传感器帧率(最高 160 FPS),但需考虑更高系统负载和更短曝光时间。
  • 禁用相位切换时间滤波器(噪声更高)。
  • 禁用相位解包裹(降低最大测程)。
  • 在适用时启用突发模式。

最大距离

最大距离取决于调制频率和相位解包裹设置。
Math
1c = 299792458.0 # 光速,单位 m/s
2
3MAX_80MHZ_M = c / (80000000 * 2) = 1.873 m
4MAX_100MHZ_M = c / (100000000 * 2) = 1.498 m
5
6MAX_DIST_80MHZ_M = (phaseUnwrappingLevel + 1) * 1.873 + (phaseUnwrapErrorThreshold / 2)
7MAX_DIST_100MHZ_M = (phaseUnwrappingLevel + 1) * 1.498 + (phaseUnwrapErrorThreshold / 2)

ToF 帧率

传感器/发射器可运行高达 160 FPS。有效深度输出取决于解码/滤波设置(例如突发模式和相位处理)。

使用示例

Python

Python
1pipeline = dai.Pipeline()
2
3socket = dai.CameraBoardSocket.AUTO
4preset = dai.ImageFiltersPresetMode.TOF_MID_RANGE
5tof = pipeline.create(dai.node.ToF).build(socket, preset)
6
7# 基础输出和滤波输出
8raw_depth_q = tof.rawDepth.createOutputQueue()
9depth_q = tof.depth.createOutputQueue()
10
11# 运行时配置队列(如果所选 API 绑定支持)
12base_cfg_q = tof.tofBaseInputConfig.createInputQueue()
13filters_cfg_q = tof.imageFiltersInputConfig.createInputQueue()

C++

C++
1dai::Pipeline pipeline;
2
3auto tof = pipeline.create<dai::node::ToF>()->build(
4    dai::CameraBoardSocket::AUTO,
5    dai::ImageFiltersPresetMode::TOF_MID_RANGE
6);
7
8auto rawDepthQ = tof->rawDepth.createOutputQueue();
9auto depthQ = tof->depth.createOutputQueue();

示例

参考

class

dai::node::ToF

variable
Subnode< ToFBase > tofBase
variable
Output & rawDepth
Raw depth output from ToF sensor. On RVC2 this is connected to the unfiltered base depth output. On RVC4 this is an unconnected placeholder output.
variable
Output & depth
Filtered depth output
variable
Output & amplitude
Amplitude output
variable
Output & intensity
Intensity output
variable
Output & confidence
Confidence output
variable
Output & phase
Phase output
variable
Output & raw
Raw data coming from the sensor
variable
Input & inputConfig
Runtime ToFConfig input for the ToF base node (decoder on RVC2, IPP on RVC4).RVC4: directly reconfigures the IPP that produces ImageFilters. The host-filter stage that actually produces ImageFiltersConfig to
variable
Input & tofBaseInputConfig
Input config for ToF base node
variable
Input * imageFiltersInputConfig
Input config for image filters
variable
ToFBase & tofBaseNode
ToF base node
variable
ImageFilters * imageFiltersNode
Image filters node
function
ToF(const std::shared_ptr< Device > & device)
function
~ToF()
function
void buildInternal()
function
std::shared_ptr< ToF > build(dai::CameraBoardSocket boardSocket, dai::ImageFiltersPresetMode presetMode, std::optional< float > fps)
Build the ToF node with a specific board socket, legacy preset mode, and optional FPS.
Parameters
  • boardSocket: Board socket to use, or AUTO to select an available ToF socket automatically
  • presetMode: Legacy ToF image filter preset mode
  • fps: Requested ToF camera FPS
function
std::shared_ptr< ToF > build(dai::CameraBoardSocket boardSocket, dai::ToFConfig::Profile presetMode, std::optional< float > fps)
Build the ToF node with a specific board socket, profile, and optional FPS.
Parameters
  • boardSocket: Board socket to use, or AUTO to select an available ToF socket automatically
  • presetMode: ToF processing profile to apply
  • fps: Requested ToF camera FPS
function
void postBuildStage()

需要帮助?

请前往 OAKChina 官网 获取技术支持或解答您的任何疑问。