Мне нужно перевести 3d точки относительно треугольника, как если бы треугольник был где-то еще - PullRequest
1 голос
/ 01 февраля 2012

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

Я описал свою проблему в следующем pdf документе, содержащем изображение того, что я 'м пытаюсь достичь.

Чтобы дать более подробную информацию, я разделил пятиугольники додекаэдра (12 пятиугольников) на треугольники (5 / пятиугольник, всего 60 треугольников), а затем собрал набор точек данных относительнокаждый из этих треугольников.

Идея состоит в том, чтобы генерировать сетки ландшафта для каждого отдельного треугольника.Для этого данные должны быть представлены плоско, в квадрате 32K x 32K (idTech4 Megatexture)

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

Я посмотрел на этот исходный код здесь , но я не понимаю, как я должен получить очки и /или оттуда, не говоря уже о том, как выполнить настройку, чтобы я мог представлять каждую точку по очереди и возвращать точку результата.

Я получил такой же быстрый результат, как и определение точки, которая принадлежит правому заднему углу.Все мои 3D точки изначально хранятся в парах широта / долгота.Я извлекаю трехмерные векторы следующим образом:

coord getcoord(point* p) 
{
    coord c;
    c.x=cos(p->lat*pi/180.l) * cos(p->lon*pi/180.l);
    c.y=cos(p->lat*pi/180.l) * sin(p->lon*pi/180.l);
    c.z=sin(p->lat*pi/180.l);
    return c;
};

Я думаю, что если я смогу найти центр моего треугольника и выяснить, как сместить мои углы, чтобы вектор переместился из центра моей сферы в серединуиз треугольника движется к 90N, то мои точки уже были бы в правильной плоскости, если бы я повернул их все на одинаковые углы.Если я затем преобразую их все в 3d и вычту радиус из y, они также будут в правильном положении y.

Тогда все, что мне нужно сделать, это вращение, масштабирование иперемещение в конечную позицию.

Есть несколько видов «центров» для треугольника, я думаю, что мне нужен тот, который равноудален от углов треугольника (Circumcenter?)

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

Кажется, что некоторые данные образца находятся впорядок, вот несколько из этих треугольников в формате файла obj:

v 0.000000 0.000000 3396.000000
v 2061.582356 0.000000 2698.646733
v 637.063983 1960.681333 2698.646733
f 1 2 3

И еще:

v -938.631230 2888.810129 1518.737455
v 637.063983 1960.681333 2698.646733
v 1030.791271 3172.449325 637.064076
f 1 2 3

Вы заметите, что каждая точка находится на расстоянии 3396 от 0,0,0 Я упомянул «на сфере», что означает, что лицо, удаленное от центра сферы, является лицом, которое должно стать «вершиной» при переводе в квадрат.

Теоретически все эти треугольники sна самом деле он должен иметь одинаковые размеры, но из-за ошибок округления в генерирующей их математике это может быть не совсем верно.

Если я не ошибаюсь, я уже принял меры, чтобы убедиться, что первое, что вы видитездесь всегда находится та, которая находится напротив самой длинной границы, поэтому она должна идти в крайнем левом углу (тестирование 2 приведенных выше примеров подтверждает это, но я все равно измеряю, чтобы быть уверенным) Обе ноги, отводящие от этой точки, должнытеоретически также имеют одинаковую длину, но опять же ошибки округления могут немного компенсировать это.

Если я сделал это правильно, то более длинная сторона в 1,113587 раз длиннее, чем две более короткие стороны.Если предположить, что они идентичны, а затем выполнить поиск цели в Excel, я могу вывести, что конечные точки, предполагая, что я просто переводил этот треугольник, должны выглядеть следующим образом:

v 16384.000000 0.000000 16384.000000
v -16384.000000 0.000000 9916.165306
v 9916.165306 0.000000 -16384.000000
f 1 2 3

Поэтому мне нужно настроить матрицу так, чтобывыполните это преобразование, предпочтительно используя матрицу 4x4, как описано ниже.

1 Ответ

1 голос
/ 01 февраля 2012

Я бы рекомендовал использовать матрицы преобразования. Матрица трехмерного преобразования представляет собой структуру данных 4x4, которая описывает перемещение и вращение (и, возможно, масштаб). Если у вас есть матрица, вы можете преобразовать точку следующим образом:

 result.x = (tmp->pt.x * m->element[0][0]) + 
            (tmp->pt.y * m->element[1][0]) + 
            (tmp->pt.z * m->element[2][0]) + 
            m->element[3][0];

 result.y = (tmp->pt.x * m->element[0][1]) + 
            (tmp->pt.y * m->element[1][1]) + 
            (tmp->pt.z * m->element[2][1]) + 
            m->element[3][1];
 result.z = (tmp->pt.x * m->element[0][2]) + 
            (tmp->pt.y * m->element[1][2]) + 
            (tmp->pt.z * m->element[2][2]) + 
            m->element[3][2];
 int w = (tmp->pt.x * m->element[0][3]) + (tmp->pt.y * m->element[1][3])
      + (tmp->pt.z * m->element[2][3]) + m->element[3][3];
 if (w!=0 || w!=1)
 result.x/=w; result.y/=w; result.z/=w;

Это преобразует трехмерную точку pt на матрицу m. Если у вас теперь есть небольшая математическая математика, вы увидите, что я просто умножаю свою исходную точку как вектор на матрицу (и выполняю небольшую нормализацию, если это косая матрица). Матрицы можно умножать вместе для формирования сложных преобразований, чтобы они очень полезны.

Для получения подробной информации о создании матриц предлагаем прочитать эту ссылку. http://en.wikipedia.org/wiki/Transformation_matrix

...