Алгоритм 2D-контура для проецируемой 3D-сетки

Дано: 3D-сетка, определенная набором вершин и треугольников, составляющих сетку с этими точками.

Задача: найти 2d контур спроецированной произвольно повернутой сетки на произвольной плоскости.

Проекция проста. Задача состоит в том, чтобы найти «оболочку» спроецированных ребер треугольника на плоскость. Мне нужна помощь с вводом / указателями при исследовании этого алгоритма. Для простоты мы можем предположить, что 3D-края проецируются прямо вниз на плоскость xy.


person ralphtheninja    schedule 18.06.2009    source источник
comment
Синяя линия здесь не выглядит выпуклой.   -  person Svante    schedule 19.06.2009
comment
Да, ты прав. Я быстро украл это изображение с сайта и нарисовал на нем несколько красных линий для иллюстрации. Я все еще надеюсь, что идея пришла в голову :)   -  person ralphtheninja    schedule 19.06.2009
comment
@MagnusSkog: Мне нужно сделать именно это. Какой метод в итоге подошел вам больше всего?   -  person PeteUK    schedule 10.03.2013
comment
@PeteUK Это сработало очень хорошо, выбрав, например, самый восточный узел, измерьте углы и выберите ближайший. Предупреждение: будьте осторожны с точностью до чисел с плавающей запятой! Я помню, что у меня были проблемы с этим, и алгоритм выбрал неправильный путь в сетке.   -  person ralphtheninja    schedule 12.03.2013
comment
@MagnusSkog Спасибо за ваш ответ и предупреждение о проблемах с FP. Я чувствую себя увереннее в этом сейчас :)   -  person PeteUK    schedule 12.03.2013


Ответы (6)


  • Начните с самой правой точки (точки с наибольшей координатой x)
  • Получить все края с этой точки
  • Следуйте за кромкой с наименьшим углом к ​​положительной оси x, а также добавьте ее в набор решений.
  • От достигнутой точки следуйте и добавьте кромку с наименьшим углом к ​​кромке, с которой вы пришли.
  • Повторяйте, пока не дойдете до исходной точки
person Svante    schedule 18.06.2009
comment
Что произойдет, если вы спроецируете тор на плоскость x-y? Так не получится внутреннее отверстие. - person nsanders; 19.06.2009
comment
Что, если есть два ребра, равных наименьшему углу? - person Richard Inglis; 21.06.2009
comment
Хм ... Возьми короче из двух. - person Richard Inglis; 21.06.2009
comment
Нет, измеряйте угол только в одном направлении, например против часовой стрелки. - person Svante; 22.06.2009
comment
спасибо за красивое решение @Svante. Не могли бы вы посоветовать, как это будет работать для других направлений проекции? - person flatronka; 19.06.2018
comment
Это решение только в 2D. То, как вы придете к 2D-входу, полностью не зависит. Вы можете сопоставить любую плоскость с плоскостью xy. - person Svante; 19.06.2018

Я вижу ответы только для выпуклых решений, поэтому вот мой для невыпуклых. (Было немного непонятно, каковы были намерения.)

Возьмите все ребра из ваших 2D-треугольников и сгруппируйте их. Если два ребра имеют обе конечные точки, они находятся в одной группе. Все группы, имеющие только одно ребро, тогда являются частью оболочки.

Наконец, вы можете объединить края раковины в одно кольцо, соединив их вместе.

person LaZe    schedule 21.06.2009

Техника альфа-форм, упомянутая в этом вопросе, обрабатывает общий набор точек, в которых соединения вершин неизвестны:

Есть ли эффективный алгоритм для создать двухмерный вогнутый корпус?

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

Алгоритм грубой силы может быть осуществим, особенно если используются структуры пространственной сортировки. например, для каждого аспекта:

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

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

person nsanders    schedule 18.06.2009

Двумерный контур проекции сетки - это подмножество проекции ее краев.

Используя это наблюдение, можно определить двухмерный контур, используя следующий метод:

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

Обратите внимание, что этот метод сообщит о всех кромках, ортогональных плоскости проекции, даже тех, которые не видны с точки зрения плоскости проекции. Например, с тором он найдет внутренние и внешние очертания, даже если тор повернут таким образом, что его внутреннее отверстие не будет видно с точки зрения плоскости проекции. Чтобы определить, какие края видны, вам понадобится какой-то тест на видимость. Если предполагаемое использование предназначено для отображения пользователем, вы можете использовать буфер глубины, вычисленный с помощью ортогональной матрицы проекции, для визуализации геометрии с точки зрения плоскости проекции и выполнения некоторого z-тестирования, чтобы определить, какие края видны с плоскости. Если вам нужна точность, вам нужно будет выполнить пересечение луча / треугольника, чтобы определить видимость.

person Sebastien Pellizzari    schedule 23.03.2014
comment
Я бы порекомендовал сделать проекцию пост-ориентировочного теста. Я пытаюсь вспомнить, почему предварительное проецирование не работает. Однако не могу придумать вескую математическую причину. Я просто неправильно преобразовал нормали, вероятно, когда я это сделал. - person starmole; 20.04.2015

Просто добавлю: очень интуитивно понятный способ найти края в проекции - это отбраковка задней грани! Любая грань между забитой и неотрубленной гранью должна быть очертанием. Если вы хотите скрыть внутренние края, просто используйте z-буфер. Отбор задней грани - это просто порядок вершин после проекции, и его очень дешево вычислить.

person starmole    schedule 20.04.2015

  1. Найдите точку, x которой min
  2. Найдите все ребра для этой точки
  3. начните с этого момента, представьте, что у вас есть палка (зеленая), она катится по часовой стрелке, чтобы найти первый край, с которым она встречается. Назовем это Edge-A. edge-A
  4. Ищите пересечения на этом ребре-A. Найдите ребро-B, которое вызывает пересечение, назовем его inter-A, это inter-A - ваша вторая точка контура. edge-B
  5. Затем давайте подумаем, кто будет следующей точкой контура между двумя точками ребра-B. Связывание интер-А и начальной точки. Затем мы можем вращать палку, чтобы найти следующую точку контура. (кандидат точка 1 - тот) введите здесь описание изображения
  6. повторяйте вышеуказанные шаги, пока не найдете точки, которые уже существуют в вашей коллекции.

см. демонстрацию поиска схемы для кролика Вот реализация описанного выше алгоритма.

person tt h    schedule 17.04.2021