Есть ли решатель pnp, представленный в ARKit, или как использовать функцию SolvePnP opencv в проекте Unity3D с помощью оболочки EmguCV C#

Контекст высокого уровня:

В проекте Unity3D AR с использованием машинного обучения система обеспечивает соответствие между набором двухмерных координат пикселей в изображении и одним и тем же набором трехмерных точек в мировой координате. Из соответствия между этими двумя наборами я хотел бы оценить позу камеры, которая привела к этому изображению.

Цель низкого уровня для достижения:

Результаты моего исследования показывают, что я использую алгоритм PnP-Ransac. Perspective-n-Points - это название этой проблемы, которую я имею: нахождение позы камеры по совпадающим 2D-3D точкам. Определение проблемы PnP: https://en.wikipedia.org/wiki/Perspective-n-Point

Что я пробовал

1) Я пытался найти PnP-решатель в ARKit, но я не смог его найти, так что, похоже, он не выставлен. 2) Я попытался использовать актив EmguCV из магазина, который должен позволить мне использовать openCV в моем проекте Unity. Документация OpenCV solvePnP: https://docs.opencv.org/3.3.0/d9/d0c/group__calib3d.html

Вопрос:

Существует ли PnP-решатель, представленный в платформе ARKit, и если нет, то как правильно использовать PnP-решатель openCV, используя оболочку EmguCV C# в рамках проекта Unity (системы координат, о которых нужно знать, корректные параметры функции, чтобы обеспечить аналогичные внутренней матрице камеры, как интерпретировать выходы, чтобы получить правильную позу камеры)?

Проблемы, с которыми я столкнулся, пытаясь ответить на вопрос:

Использование SolvePnPRansac привело к сбою самого Unity-Editor, даже если я поместил его в блок try-catch (возможно, мои входные аргументы имели неожиданные форматы). У меня был больший успех с использованием только solvePnP, но результаты не те, которые я ожидаю. В документации говорится, что выходные векторы rvec и tvec соответствуют сдвигу и повороту, переносящим объект из системы координат модели в систему координат камеры. Так что, если бы я поместил камеру в (0,0,0), смотря в направлении -z, имея объект в tvec с эйлеровыми поворотами rvec, я бы ожидал, что визуализированный объект будет похож на изображение, которое я использовал для соответствия пиксель-координат, Я неправильно понял это?

У меня есть подозрения: система координат openCV утверждает, что координата y изображения идет сверху вниз, а z и x остаются вперед-вправо. Я пытался инвертировать 2D, а также 3D-координаты по оси Y, но это не сработало

Изменить [Я удалил свой код здесь, потому что я сильно изменил его, так как я задал вопрос, чтобы заставить его работать]

(некоторые из многих) Похожие посты, которые я посмотрел, бросили остальные 41 вопрос stackru с тегом opencv-solvePnP, но ни один из них не был связан с Unity3D или C#

решить PnP с Unity3D

не получил ответов

Оценка позы камеры по гомографии или с функцией solvePnP()

Как я могу оценить позу камеры с 3D-2D-точечными соответствиями (используя opencv)

Разница: мне нужно сделать это в проекте unity3D C#

получение 2d-3d точечных соответствий для pnp или posit

Я понял, мне нужно использовать математические алгоритмы, это теория, но теперь, как мне использовать библиотеки в моем распоряжении

1 ответ

Решение

Предоставляет ли ARKIT PnP-решатель? я до сих пор не знаю

о том, как использовать openCV в проекте Unity: вот мой собственный ответ:

1) система координат: просто убедитесь, что ваши 2D-точки имеют правильное вертикальное направление координат: в зависимости от того, как вы получаете эти 2D-точки, может быть нечего менять.

2) какую внутреннюю матрицу использовать:

var pixelsPerMeter = (((float)Screen.height / 2f)) / (Mathf.Tan(_mainCamera.fieldOfView * Mathf.Deg2Rad / 2f));
var fx = pixelsPerMeter;
var cx = Screen.width * 0.5f;
var fy = pixelsPerMeter;
var cy = Screen.height * 0.5f;
var cameraMatrix = new Emgu.CV.Matrix<float>(new float[3, 3] {
        {fx,0,cx},
        {0,fy,cy},
        {0,0,1}
        });

РЕДАКТИРОВАТЬ: выше, только работал в редакторе единства для меня до сих пор. развертывание на мобильном устройстве с использованием ARKit до сих пор дает неверные результаты для меня до сих пор!

3) Как интерпретировать veg и rvec из результата:

Используйте Rodrigues для правильного преобразования rvec в матрицу вращения, просто выполнив Quaternion.Euler(rvec[0], rvec[1], rvec[2]) НЕ будет работать!

Сначала поверните ваш объект, затем переведите его с помощью tvec, и, наконец, примените матрицу localToWorld вашей камеры, чтобы разместить объект относительно камеры (если вы хотите, чтобы объект имел фиксированное положение и камера была размещена, просто инвертируйте матрицу). в результате rvec и tvec)

Другие вопросы по тегам