2009-01-02 28 views
26

Estoy buscando un algoritmo o biblioteca (mejor) para descomponer un polígono en triángulos. Usaré estos triángulos en una aplicación Direct3D. ¿Cuáles son las mejores opciones disponibles?Triangulación de polígono con orificios

Aquí es lo que he encontrado hasta ahora:

  1. Ben Discoe's notes
  2. FIST: Fast Industrial-Strength Triangulation of Polygons
  3. sé que CGAL proporciona triangulación, pero no estoy seguro de si es compatible con agujeros.

Realmente agradecería algunas opiniones de personas con experiencia previa en esta área.

Editar: Este es un polígono 2D.

+0

¿Necesita 2D (triángulos) o 3D (tetraedros)? –

+0

Este es un polígono 2D –

Respuesta

18

Jonathan Shewchuk's Triangle library es fenomenal; Lo he usado para automatizar la triangulación en el pasado. Puedes pedirle que intente evitar triángulos pequeños/estrechos, etc., así que obtienes triangulaciones "buenas" en lugar de cualquier triangulación.

+0

Puedo afirmar que Triangle es de hecho una gran herramienta. También ganó el prestigioso "Premio J. H. Wilkinson para Software Numérico", otorgado solo una vez cada 4 años. – batty

+0

Cambiando la respuesta seleccionada a esta ya que de hecho tengo esto para trabajar. –

+0

Una de las mayores ventajas aquí es que Triangle hace que sea muy fácil construir buffers separados de vértices e índices de la triangulación. ¡Quiéralo! –

2

Puede agregar los orificios con relativa facilidad usted mismo. Básicamente triangular al casco convexo de los puntos de entrada, según CGAL, y luego eliminar cualquier triángulo cuyo incentivo se encuentre dentro de cualquiera de los polígonos de agujero (o fuera de cualquiera de los límites externos). Al tratar con muchos agujeros en un gran conjunto de datos, las técnicas de enmascaramiento se pueden utilizar para acelerar significativamente este proceso.

editar: Una extensión común de esta técnica es eliminar los triángulos débiles en el casco, donde el borde más largo o el ángulo interno más pequeño excede un valor dado. Esto formará un mejor casco cóncavo.

+1

Este enfoque no funcionaría: necesita utilizar una triangulación restringida, de lo contrario, puede encontrar triángulos que están parcialmente dentro y parcialmente fuera de un agujero. – Camille

+0

@camille: un polígono triangulado con agujeros siempre está restringido. Los bordes y agujeros del polígono son, por definición, contracciones.Si un borde triangular cruza un agujero, el agujero estaría parcialmente cubierto. Si cruza un borde de polígono, el TIN no sería una triangulación de ese polígono. –

11

CGAL tiene la herramienta que necesita: Constrained Triangulations

Simplemente puede proporcionar límites de su polígono (incuding los límites de los agujeros) como restricciones (lo mejor sería que se inserta todos los vértices, y luego especificar el restricciones como pares de Vertex_handles).

Puede etiquetar los triángulos de la triangulación mediante cualquier algoritmo transversal: comience con un triángulo incidente al vértice infinito y márquelo como fuera, y cada vez que cruce una restricción, cambie a la etiqueta opuesta (dentro si anteriormente etiquetó los triángulos como externos, afuera si estaba etiquetando triángulos como información privilegiada anteriormente).

+0

Es una solución lo suficientemente buena para casos simples. Donde tienes agujeros superpuestos, y agujeros dentro de agujeros, se cae. Prefiero tener límites internos y externos explícitos. –

+1

En caso de que tenga agujeros superpuestos, debe conservar la lista de agujeros que ya ha ingresado (en lugar de solo una etiqueta interior/exterior). Aparte de eso, es exactamente lo mismo. – Camille

+0

"cada vez que cruzas una restricción"? ¿Cómo lo averiguo? –

17

para darle un poco más opciones de bibliotecas por ahí:

Polyboolean. Nunca intenté este, pero parece prometedor: http://www.complex-a5.ru/polyboolean/index.html

General Polygon Clipper. Este funciona muy bien en la práctica y hace triangulación, así como los agujeros de recorte y agujeros: http://www.cs.man.ac.uk/~toby/alan/software/

Mi recomendación personal: Utilice la tesselación de la GLU (OpenGL Utility Library). El código es sólido como una roca, más rápido que GPC y genera menos triángulos. No necesita un OpenGL-Handle inicializado ni nada de esto para usar la lib.

Si no le gusta la idea de incluir las librerías OpenGL en una aplicación DirectX, también existe una solución: simplemente descargue el código de implementación de referencia SGGL de OpenGL y levante el triangulador. Solo usa los nombres OpenGL-Typedef y una mano llena de enumeraciones. Eso es. Puede extraer el código y crear una lib propia en una o dos horas.


En general, mi consejo sería utilizar algo que ya funciona y no comenzar a escribir su propia triangulación.

Es tentador rodar el suyo si ha leído sobre el algoritmo de corte de oreja o línea de barrido, pero el hecho es que los algoritmos de geometría computacional son increíblemente difíciles de escribir de manera que funcionen estable, nunca se cuelguen y siempre devolver un resultado significativo. Los errores numéricos de redondeo se acumularán y te matarán al final.

Escribí un algoritmo de triangulación en C para la empresa con la que trabajo. Lograr que el algoritmo central funcionara tomó dos días. Conseguir que funcionara con todo tipo de entradas degeneradas tomó otros dos años (no trabajaba a tiempo completo, pero créanme, pasé más tiempo de lo que debería).

+0

Escribí todas mis propias cosas TIN, y estoy de acuerdo 100% sobre los muchos casos degenerados. Nunca se movería de mis propias bibliotecas por este motivo, aunque algunos de los libros CG más nuevos son excelentes. –

1

Este es un problema común en el análisis de elementos finitos. Se llama "generación automática de malla". Google encontró this site con enlaces a software comercial y de código abierto. Suelen presuponer algún tipo de representación CAD de la geometría para comenzar.

0

Otra opción (con una licencia muy flexible) es el algoritmo puerto de VTK:

vtkDelaunay2D

Este algoritmo funciona bastante bien. Usarlo directamente es posible, pero requiere enlaces a VTK, que pueden tener más sobrecarga de lo que usted desea (aunque también tiene muchas otras características interesantes).

Admite restricciones (agujeros/límites/etc.), así como la triangulación de una superficie que no está necesariamente en el plano XY. También es compatible con algunas características que no he visto en otros lugares (ver las notas sobre los valores Alpha).

5

He encontrado que la biblioteca poly2tri es exactamente lo que necesitaba para la triangulación. Produce una malla mucho más limpia que otras bibliotecas que he probado (incluida libtess), y admite orificios también. Se ha convertido a varios idiomas. La licencia es New BSD, por lo que puede usarla en cualquier proyecto.

Poly2tri library on Google Code

+2

Encontré por mi cuenta que se bloquea mucho. – SAKrisT

0

he implementado un polígono 3D triangulator en C# usando el método de recorte de oreja. Es fácil de usar, admite orificios, es numéricamente robusto y admite polígonos convexos/no convexos aribtrary (no autointersecables).

Cuestiones relacionadas