You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于已标定OpenCV C++相机实现物体真实尺寸测量的问题

嘿,我来帮你搞定单目相机像素转真实尺寸的问题!你已经有了标定好的内参、畸变系数和外参,其实核心是利用相机投影模型的逆过程来计算,不过单目相机有个关键点:必须知道物体到相机的深度(或者有一个已知尺寸的参照物),因为透视投影下,同样大的物体离得越远像素越小。结合你的测量场景,我给你具体的实现思路和步骤:

核心实现步骤

1. 先校正畸变像素点

首先得把你检测到的物体边缘像素点,用畸变系数校正成无畸变的像素坐标,这一步是基础,避免畸变带来的误差,用OpenCV的undistortPoints()函数就能搞定:

import cv2
import numpy as np

# 假设你检测到物体的两个端点像素坐标是p1=(x1,y1)、p2=(x2,y2)
pixels = np.array([[x1,y1], [x2,y2]], dtype=np.float32)
# 替换成你自己的内参camera_matrix和畸变系数dist_coeffs
undistorted_pixels = cv2.undistortPoints(pixels, camera_matrix, dist_coeffs)

2. 利用外参将像素点转换到世界坐标系

你手里的外参(旋转向量rvec+平移向量tvec)是相机相对于世界坐标系(比如标定板所在平面为Z=0的坐标系)的姿态。如果你的测量物体和标定板在同一个平面(Z=0),那可以直接用这个外参来计算:

方法一:通过射线与平面交点计算

先把旋转向量转成旋转矩阵R:

R, _ = cv2.Rodrigues(rvec)

然后把校正后的像素点转换成相机坐标系下的射线方向,再计算这条射线与Z=0世界平面的交点(也就是物体在世界坐标系的位置):

# 计算内参的逆矩阵
K_inv = np.linalg.inv(camera_matrix)
# 取第一个校正后的像素点(u,v)
u, v = undistorted_pixels[0][0]
# 转成归一化相机坐标(齐次形式)
normalized_point = np.dot(K_inv, np.array([u, v, 1]))
# 得到相机坐标系下的单位方向向量
camera_dir = normalized_point / np.linalg.norm(normalized_point)

# 计算射线与Z=0世界平面的交点深度Z_c
# 推导公式:世界坐标Z=0,结合相机到世界的转换关系得到
Z_c = -(R[2,0]*tvec[0] + R[2,1]*tvec[1] + R[2,2]*tvec[2]) / (R[2,0]*camera_dir[0] + R[2,1]*camera_dir[1] + R[2,2]*camera_dir[2])

# 得到相机坐标系下的点
P_camera = tvec + Z_c * camera_dir
# 转换到世界坐标系
P1_world = R.T @ (P_camera - tvec)

用同样的方法计算第二个端点P2_world。

方法二:用单应性矩阵简化计算

如果物体在标定平面(Z=0),可以直接计算单应性矩阵H,它能直接把像素坐标转成世界坐标:

# 单应性矩阵H = 内参K @ 旋转矩阵R @ [单位矩阵I | -平移向量tvec/相机到平面的深度]
# 这里tvec[2]就是相机到Z=0平面的深度(世界原点在相机坐标系的Z值)
H = camera_matrix @ np.hstack((R, -tvec.reshape(3,1)/tvec[2]))

然后把像素点转成齐次坐标,乘以H的逆矩阵得到世界坐标:

# 第一个像素点转齐次形式
p1_hom = np.array([x1, y1, 1], dtype=np.float32)
# 转换到世界坐标齐次形式
p1_world_hom = np.dot(np.linalg.inv(H), p1_hom)
# 归一化得到世界坐标(X,Y)
P1_world = p1_world_hom[:2] / p1_world_hom[2]

3. 计算真实尺寸

得到两个端点的世界坐标后,计算它们的欧氏距离就是物体的真实尺寸,单位和你标定时用的世界坐标系单位一致(比如你标定时用mm,结果就是mm):

real_size = np.linalg.norm(P1_world - P2_world)
关键注意事项
  • 单位一致性:标定时世界坐标系的单位必须是你想要的mm,否则记得最后转换单位(比如标定时用cm,结果要乘10)。
  • 外参匹配:确保你用的外参是测量物体时的相机姿态,而不是标定时的固定姿态——如果相机移动了,需要重新用标定板估计当前的rvec和tvec。
  • 深度问题:如果物体不在标定平面上,单目相机无法直接得到尺寸,你需要额外的深度信息(比如用已知尺寸的参照物,或者结合双目/结构光),因为透视投影会丢失深度维度。

内容的提问来源于stack exchange,提问作者Lương Hữu Huân

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 08:11:04