mirror of
https://github.com/jhasse/poly2tri.git
synced 2024-11-05 13:59:53 +01:00
fixed edge bug
This commit is contained in:
parent
251e8ed8ff
commit
7f999024b9
@ -79,7 +79,7 @@ class Poly2TriDemo extends BasicGame("Poly2Tri") {
|
||||
var drawcdtMesh = false
|
||||
|
||||
val nazcaMonkey = "data/nazca_monkey.dat"
|
||||
val nazcaHeron = "data/nazca_heron.dat"
|
||||
val nazcaHeron = "data/nazca_heron_old.dat"
|
||||
val bird = "data/bird.dat"
|
||||
val snake = "data/i.snake"
|
||||
val star = "data/star.dat"
|
||||
@ -87,7 +87,7 @@ class Poly2TriDemo extends BasicGame("Poly2Tri") {
|
||||
val i18 = "data/i.18"
|
||||
val tank = "data/tank.dat"
|
||||
|
||||
var currentModel = nazcaMonkey
|
||||
var currentModel = nazcaHeron
|
||||
var doCDT = true
|
||||
|
||||
var mouseButton = 0
|
||||
@ -318,7 +318,7 @@ class Poly2TriDemo extends BasicGame("Poly2Tri") {
|
||||
doCDT = true; drawCDT = true
|
||||
CDT.clearPoint = 7
|
||||
loadModel(i18, 20f, Point(600f, 500f), 20)
|
||||
case "data/nazca_heron.dat" =>
|
||||
case "data/nazca_heron_old.dat" =>
|
||||
//doCDT = false; drawCDT = false; drawcdtMesh = false
|
||||
CDT.clearPoint = 100
|
||||
loadModel(nazcaHeron, 4.2f, Point(400f, 300f), 1500)
|
||||
|
@ -42,9 +42,9 @@ import seidel.MonotoneMountain
|
||||
* International Journal of Geographical Information Science
|
||||
*/
|
||||
|
||||
// NOTE: Still need to implement edge insertion which combines advancing front (AF)
|
||||
// NOTE: May need to implement edge insertion which combines advancing front (AF)
|
||||
// and triangle traversal respectively. See figure 14(a) from Domiter et al.
|
||||
|
||||
// Although it may not be necessary for simple polygons....
|
||||
object CDT {
|
||||
|
||||
// Inital triangle factor
|
||||
@ -83,12 +83,11 @@ object CDT {
|
||||
private def initSegments(points: ArrayBuffer[Point]): List[Segment] = {
|
||||
|
||||
var segments = List[Segment]()
|
||||
|
||||
for(i <- 0 until points.size-1) {
|
||||
|
||||
val endPoints = validatePoints(points(i), points(i+1))
|
||||
segments = new Segment(endPoints(0), endPoints(1)) :: segments
|
||||
endPoints(1).edges += segments.first
|
||||
|
||||
}
|
||||
|
||||
val endPoints = validatePoints(points.first, points.last)
|
||||
@ -199,7 +198,7 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
|
||||
|
||||
// Locate the first intersected triangle
|
||||
val firstTriangle = node.triangle.locateFirst(edge)
|
||||
//if(firstTriangle != null)mesh.debug += firstTriangle
|
||||
|
||||
// Remove intersected triangles
|
||||
if(firstTriangle != null && !firstTriangle.contains(edge)) {
|
||||
|
||||
@ -270,6 +269,9 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
|
||||
// Mark constrained edge
|
||||
T1.last markEdge(point1, point2)
|
||||
T2.last markEdge(point1, point2)
|
||||
// Copy constraied edges from old triangles
|
||||
T1.foreach(t => t.markEdge(tList))
|
||||
T2.foreach(t => t.markEdge(tList))
|
||||
|
||||
} else if(firstTriangle == null) {
|
||||
|
||||
@ -280,7 +282,7 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
|
||||
val point1 = if(ahead) edge.q else edge.p
|
||||
val point2 = if(ahead) edge.p else edge.q
|
||||
|
||||
var pNode = if(ahead) node else aFront.locatePoint(point1)
|
||||
var pNode = if(ahead) node else aFront.locate(point1)
|
||||
val first = pNode
|
||||
|
||||
val points = new ArrayBuffer[Point]
|
||||
@ -288,15 +290,14 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
|
||||
// Neighbor triangles
|
||||
val nTriangles = new ArrayBuffer[Triangle]
|
||||
nTriangles += pNode.triangle
|
||||
|
||||
pNode = pNode.next
|
||||
|
||||
while(pNode.point != point2) {
|
||||
while(pNode.point != point2 && edge > pNode.point) {
|
||||
points += pNode.point
|
||||
nTriangles += pNode.triangle
|
||||
pNode = pNode.next
|
||||
}
|
||||
|
||||
|
||||
// Triangulate empty areas.
|
||||
val T = new ArrayBuffer[Triangle]
|
||||
triangulate(points.toArray, List(point1, point2), T)
|
||||
@ -437,9 +438,13 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
|
||||
if(illegal && !t2.finalized) {
|
||||
|
||||
// Flip edge and rotate everything clockwise
|
||||
|
||||
// Legalize points
|
||||
t1.legalize(oPoint)
|
||||
t2.legalize(oPoint, point)
|
||||
|
||||
// Update neighbors
|
||||
|
||||
// Copy old neighbors
|
||||
val neighbors = List(t2.neighbors(0), t2.neighbors(1), t2.neighbors(2))
|
||||
// Clear old neighbors
|
||||
|
@ -42,16 +42,6 @@ class Mesh(initialTriangle: Triangle) {
|
||||
val debug = HashSet.empty[Triangle]
|
||||
val triangles = new ArrayBuffer[Triangle]
|
||||
|
||||
def test(triangle: Triangle) {
|
||||
if(triangle != null && !triangle.test){
|
||||
triangle.test = true
|
||||
debug += triangle
|
||||
for(i <- 0 until 3) {
|
||||
test(triangle.neighbors(i))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Recursively collect triangles
|
||||
def clean(triangle: Triangle) {
|
||||
if(triangle != null && !triangle.interior) {
|
||||
|
@ -44,13 +44,14 @@ class Triangle(val points: Array[Point]) {
|
||||
var neighbors = new Array[Triangle](3)
|
||||
// Flags to determine if an edge is the final Delauney edge
|
||||
val edges = Array(false, false, false)
|
||||
|
||||
// Finalization flag
|
||||
// Finalization flag. Set true if legalized or edge constrained
|
||||
var finalized = false
|
||||
// Has this triangle been marked as an interoir triangle?
|
||||
var interior = false
|
||||
|
||||
var finalized = false
|
||||
|
||||
var test = false
|
||||
def contains(p: Point): Boolean = (p == points(0) || p == points(1) || p == points(2))
|
||||
def contains(e: Segment): Boolean = (contains(e.p) && contains(e.q))
|
||||
def contains(p: Point, q: Point): Boolean = (contains(p) && contains(q))
|
||||
|
||||
// Update neighbor pointers
|
||||
private def markNeighbor(p1: Point, p2: Point, t: Triangle) {
|
||||
@ -102,10 +103,6 @@ class Triangle(val points: Array[Point]) {
|
||||
|
||||
}
|
||||
|
||||
def contains(p: Point): Boolean = (p == points(0) || p == points(1) || p == points(2))
|
||||
def contains(e: Segment): Boolean = (contains(e.p) && contains(e.q))
|
||||
def contains(p: Point, q: Point): Boolean = (contains(p) && contains(q))
|
||||
|
||||
// Fast point in triangle test
|
||||
def pointIn(point: Point): Boolean = {
|
||||
|
||||
@ -308,6 +305,18 @@ class Triangle(val points: Array[Point]) {
|
||||
}
|
||||
}
|
||||
|
||||
def markEdge(T: ArrayBuffer[Triangle]) {
|
||||
for(t <- T) {
|
||||
for(i <- 0 to 2)
|
||||
if(t.edges(i))
|
||||
i match {
|
||||
case 0 => markEdge(t.points(1), t.points(2))
|
||||
case 1 => markEdge(t.points(0), t.points(2))
|
||||
case 2 => markEdge(t.points(0), t.points(1))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Mark edge as constrained
|
||||
def markEdge(p: Point, q: Point) {
|
||||
if((q == points(0) && p == points(1)) || (q == points(1) && p == points(0))) {
|
||||
|
Loading…
Reference in New Issue
Block a user