Я пытаюсь получить 3D-координаты с помощью стереокамеры.В чем разница между repjectImageto3D (OpenCV) и несоответствием трехмерным координатам?
Первый метод заключается в вычислении непосредственно с использованием этой формулы.
Второй способ - использовать функцию repjectImageTo3D в opencv.
Но я не знаю принцип этого метода.
Результат не в миллиметрах, поэтому его трудно сопоставить с размером.
Пожалуйста, скажите мне разницу между этими двумя методами.
(Первый из этих кодов заключается в преобразовании характерной точки в 3D-координаты после согласования.) (второй код, чтобы вычислить несоответствие всей стереоизображения с помощью SGBM и рассчитать 3d координаты точечного объекта, используя reprojectImageTo3D.)
* Первый метод
cv::Mat depth(m_input.m_leftImg.size(), CV_32FC3, cv::Scalar::all(0));
int size = feOutput.m_leftKp.size();
for (int i = 0; i < size; i++)
{
cv::Point pt = cv::Point((int)(feOutput.m_leftKp.at(i).pt.x + 0.5f), (int)(feOutput.m_leftKp.at(i).pt.y + 0.5f));
depth.at<cv::Vec3f>(pt)[2] = fX * baseLine/(feOutput.m_leftKp.at(i).pt.x - feOutput.m_rightKp.at(i).pt.x); // Z
depth.at<cv::Vec3f>(pt)[0] = (feOutput.m_leftKp.at(i).pt.x - cX) * depth.at<cv::Vec3f>(pt)[2]/fX; // X
depth.at<cv::Vec3f>(pt)[1] = (feOutput.m_leftKp.at(i).pt.y - cY) * depth.at<cv::Vec3f>(pt)[2]/fY; // Y
}
depth /= 1000.f; //milli-meter to meter
* Второй метод
cv::Mat disparity16S(m_input.m_leftImg.size(), CV_16S);
sgbm->compute(m_input.m_leftImg, m_input.m_rightImg, disparity16S);
cv::Mat xyz;
cv::Matx44d Q = cv::Matx44d(
1.0, 0.0, 0.0, -cX,
0.0, 1.0, 0.0, -cY,
0.0, 0.0, 0.0, fX,
0.0, 0.0, -1.0/baseLine, 0/*(CX - CX)/baseLine*/
);
cv::reprojectImageTo3D(disparity16S, xyz, Q, true);
cv::Mat pointXYZ(xyz.size(), xyz.type(), cv::Scalar::all(0));
for (int i = 0; i < size; i++)
{
cv::Point pt = cv::Point((int)(feOutput.m_leftKp.at(i).pt.x + 0.5f), (int)(feOutput.m_leftKp.at(i).pt.y + 0.5f));
pointXYZ.at<cv::Vec3f>(pt) = xyz.at<cv::Vec3f>(pt)/1000.f;
}
Add + Розовый - это размер метода recjectImageTo3D, масштабированный до 1/100, а желтый - это размер 1/1000 (мм 2 метра) в первом методе. Если оба метода одинаковы, почему существует разница в масштабе?
Благодарим вас за ответ. Итак, [X Y Z 1] = inv (K) * [Z * x Z * y Z] то же самое, что и первое уравнение, и нет ли разницы между низкой формулой и reprojectImageTo3D? – user6445248
И я добавил некоторые подробности. Почему эти два метода отличаются по масштабу? – user6445248
@ user6445248 они должны быть эквивалентными (по моему предположению 2). [Это документация оператора stereoSGBM в openCV 2.4] (http://docs.opencv.org/2.4/modules/calib3d/doc/camera_calibration_and_3d_reconstruction.html#stereobm-operator). Вы разделили значение оператора sgbm на 16 (вы используете CV_16S)? – marcoresk