Ответ 1
Ответ, который вы хотите, будет зависеть от точности результата, который вам нужен. Как отметил Данаид, нелинейность в датчике изображения и другие факторы, такие как атмосферные искажения, могут вызывать ошибки, но будут трудные проблемы для решения с разных камер и т.д. На разных устройствах. Поэтому давайте начнем с получения разумного приближения, которое может быть изменено, так как требуется больше точности.
Во-первых, вы можете игнорировать информацию направления с устройства, если вы выберете. Если у вас есть пять местоположений (POS1 - POS4 и камера, в согласованном наборе координат, у вас есть все, что вам нужно. На самом деле вам даже не нужны все эти точки.
Замечание о согласованных координатах. В своем масштабе, как только вы используете преобразование lat и long to meters, используя cos (lat) для вашего масштабирующего коэффициента, вы должны уметь рассматривать всех с точки зрения "плоской земли". Вам просто нужно помнить, что плоскость x-y камеры является примерно глобальной плоскостью x-z.
Концептуальный фон На приведенной ниже диаграмме показана проекция точек на плоскость изображения. Dz, используемый для перспективы, может быть получен непосредственно с использованием доли расстояния между дальними точками и близкими точками по сравнению с их физическим расстоянием. В простом случае, где линия POS1-POS2 параллельна линии POS3-POS4, фактор перспективы - это просто соотношение масштабирования двух линий:
Scale (POS1, POS2) = pixel distance (pos1, pos2) / Physical distance (POS1, POS2)
Scale (POS3, POS4) = pixel distance (pos3, pos4) / Physical distance (POS3, POS4)
Perspective factor = Scale (POS3, POS4) / Scale (POS1, POS2)
Таким образом, фактор перспективы, применяемый к вершине вашего прямоугольника, будет равен расстоянию от вершины между линиями. Упрощая:
Factor(rect) ~= [(Rect.z - (POS3, POS4).z / ((POS1, POS2).z - (POS3, POS4).z)] * Perspective factor.
Ответ
Перспективное преобразование линейно относительно расстояния от фокальной точки в направлении обзора. Диаграмма ниже рисуется с осью X, параллельной плоскости изображения, и осью Y, направленной в направлении обзора. В этой системе координат для любой точки P и плоскости изображения на любом расстоянии от начала координат проецируемая точка p имеет координату X p.x, которая пропорциональна P.x/P.y. Эти значения могут быть линейно интерполированы.
На диаграмме tp - желаемая проекция целевой точки. для получения tp.x, интерполировать между, например, pos1.x и pos3.x, используя настройки для расстояния, следующим образом:
tp.x = pos1.x + ((pos3.x-pos1.x)*((TP.x/TP.y)-(POS1.x/POS1.y))/((POS3.x/POS3.y)-(POS1.x/POS1.y))
Преимущество такого подхода заключается в том, что он не требует предварительного знания угла, просматриваемого каждым пикселем, и он будет относительно устойчив к разумным ошибкам в местоположении и ориентации камеры.
Дальнейшее уточнение
Использование большего количества данных означает возможность компенсации большего количества ошибок. С учетом нескольких точек местоположение камеры и ориентация можно откалибровать с помощью метода Tienstra. Кратким доказательством этого подхода (с использованием барицентрических координат) можно найти здесь.
Поскольку требуемое преобразование линейно основано на однородных координатах, вы можете применить барицентрические координаты для интерполяции на основе любых трех или более точек, учитывая их X, Y, Z, W в однородном 3-пространстве и их координатах (x, y) в пространстве изображений. Чем ближе точки к точке назначения, тем менее значительными могут быть нелинейности, поэтому в вашем примере вы будете использовать POS 1 и POS3, так как прямоугольник слева и POS2 или POS4 в зависимости от относительного расстояния.
(Барицентрические координаты, скорее всего, наиболее известны как метод, используемый для интерполяции цветов в треугольнике (фрагменте) в 3D-графике.)
Изменить: Барицентрические координаты по-прежнему требуют однородного координатного коэффициента W, что является еще одним способом выражения коррекции перспективы для расстояния от фокальной точки. Подробнее см. в этой статье на GameDev.
Два взаимосвязанных вопроса SO: перспективная коррекция координат текстур в 3d и Barycentric maps mapping mapping.