fixed edge avent AFront update

This commit is contained in:
zzzzrrr 2009-08-08 20:50:41 -04:00
parent 99f6af554c
commit 6757b713a0
3 changed files with 95 additions and 36 deletions

View File

@ -53,7 +53,7 @@ class AFront(iTriangle: Triangle) {
return node return node
node = node.next node = node.next
} }
throw new Exception("Advancing front error: point not found") null
} }
def insert(tuple: Tuple3[Point, Triangle, Node]) = { def insert(tuple: Tuple3[Point, Triangle, Node]) = {

View File

@ -157,7 +157,7 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
private def pointEvent(point: Point): Triangle = { private def pointEvent(point: Point): Triangle = {
val node = aFront.locate(point) val node = aFront.locate(point)
/*
// Projected point coincides with existing point; create two triangles // Projected point coincides with existing point; create two triangles
if(point.x == node.point.x && node.prev != null) { if(point.x == node.point.x && node.prev != null) {
@ -190,7 +190,7 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
newNode.triangle newNode.triangle
} else { } else {
*/
// Projected point hits advancing front; create new triangle // Projected point hits advancing front; create new triangle
val cwPoint = node.next.point val cwPoint = node.next.point
val ccwPoint = node.point val ccwPoint = node.point
@ -222,7 +222,7 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
// Fill in adjacent triangles if required // Fill in adjacent triangles if required
scanAFront(newNode) scanAFront(newNode)
newNode.triangle newNode.triangle
} //}
} }
// EdgeEvent // EdgeEvent
@ -245,11 +245,17 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
// TODO: fix tList.last == null bug! // TODO: fix tList.last == null bug!
// Not sure why this happens in bird & nazca monkey demo... // Not sure why this happens in bird & nazca monkey demo...
if(tList.last == null) if(tList.last == null) tList -= tList.last
tList -= tList.last
// Remove old triangles // Neighbor triangles
tList.foreach(t => mesh.map -= t) val nTriangles = new ArrayBuffer[Triangle]
// Remove old triangles; collect neighbor triangles
tList.foreach(t => {
t.neighbors.foreach(n => if(n != null) nTriangles += n)
mesh.map -= t
//mesh.debug += t
})
val lPoints = new ArrayBuffer[Point] val lPoints = new ArrayBuffer[Point]
val rPoints = new ArrayBuffer[Point] val rPoints = new ArrayBuffer[Point]
@ -282,16 +288,60 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
val T2 = new ArrayBuffer[Triangle] val T2 = new ArrayBuffer[Triangle]
triangulate(rPoints.toArray, List(point1, point2), T2) triangulate(rPoints.toArray, List(point1, point2), T2)
// Update advancing front
val qNode = aFront.locate(edge.q)
val pNode = aFront.locate(edge.p)
println(tList.size)
for(t <- tList) {
if(qNode.triangle == t) {
println("node")
val p1 = qNode.point
val p2 = qNode.next.point
T1.foreach(tri => if(tri.contains(p1, p2)) qNode.triangle = tri)
T2.foreach(tri => if(tri.contains(p1, p2)) qNode.triangle = tri)
} else if(qNode.prev.triangle == t) {
println("prev node")
val p1 = qNode.prev.point
val p2 = qNode.point
T1.foreach(tri => if(tri.contains(p1, p2)) qNode.prev.triangle = tri)
T2.foreach(tri => if(tri.contains(p1, p2)) qNode.prev.triangle = tri)
} else if(qNode.next.triangle == t) {
println("next node")
} else
if(pNode.triangle == t) {
println("Pnode")
val p1 = pNode.point
val p2 = pNode.next.point
T1.foreach(tri => if(tri.contains(p1, p2)) pNode.triangle = tri)
T2.foreach(tri => if(tri.contains(p1, p2)) pNode.triangle = tri)
} else if(pNode.prev.triangle == t) {
println("prev Pnode")
val p1 = pNode.point
val p2 = pNode.prev.point
T1.foreach(tri => if(tri.contains(p1, p2)) pNode.prev.triangle = tri)
T2.foreach(tri => if(tri.contains(p1, p2)) pNode.prev.triangle = tri)
} else if(pNode.next.triangle == t) {
println("next Pnode")
}
}
// Update neighbors
//updateNeighbors(nTriangles, T1)
updateNeighbors(nTriangles, T2)
//nTriangles.foreach(n => n.printDebug)
// Mark constrained edges // Mark constrained edges
val dEdge = new Segment(point1, point2) T1.first.mark(point1, point2)
T1.first mark(point1, point2) T2.first.mark(point1, point2)
T2.first mark(point1, point2)
//TODO update neighbor pointers //TODO update neighbor pointers
} else if(firstTriangle == null) { } else if(firstTriangle == null) {
// NOTE: So far this only works for single triangles
// No triangles are intersected by the edge; edge must lie outside the mesh // No triangles are intersected by the edge; edge must lie outside the mesh
// Apply constraint; traverse the AFront, and build triangles // Apply constraint; traverse the AFront, and build triangles
@ -300,17 +350,18 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
val point2 = if(ahead) edge.p else edge.q val point2 = if(ahead) edge.p else edge.q
val points = new ArrayBuffer[Point] val points = new ArrayBuffer[Point]
val triangles = new ArrayBuffer[Triangle] // Neighbor triangles
val nTriangles = new ArrayBuffer[Triangle]
var node = aFront.locate(point1) var node = aFront.locate(point1)
val first = node val first = node
triangles += first.triangle nTriangles += first.triangle
node = node.next node = node.next
while(node.point != point2) { while(node.point != point2) {
points += node.point points += node.point
triangles += node.triangle nTriangles += node.triangle
node = node.next node = node.next
} }
@ -323,15 +374,8 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
// Update advancing front // Update advancing front
aFront -= (first, node.prev, T.first) aFront -= (first, node.prev, T.first)
// Update neigbor pointers // Update neighbors
// Inneficient, but it works well... updateNeighbors(nTriangles, T)
for(i <- triangles)
for(j <- T)
i.markNeighbor(j)
for(i <- 0 until T.size)
for(j <- i+1 until T.size)
T(i).markNeighbor(T(j))
// Mark constrained edge // Mark constrained edge
T.first mark(edge.p, edge.q) T.first mark(edge.p, edge.q)
@ -342,6 +386,20 @@ class CDT(val points: List[Point], val segments: List[Segment], iTriangle: Trian
} }
} }
// Update neigbor pointers for edge event
// Inneficient, but it works well...
def updateNeighbors(nTriangles: ArrayBuffer[Triangle], T: ArrayBuffer[Triangle]) {
for(t1 <- nTriangles)
for(t2 <- T)
t1.markNeighbor(t2)
for(i <- 0 until T.size)
for(j <- i+1 until T.size)
T(i).markNeighbor(T(j))
}
// Marc Vigo Anglada's triangulate pseudo-polygon algo // Marc Vigo Anglada's triangulate pseudo-polygon algo
private def triangulate(P: Array[Point], ab: List[Point], T: ArrayBuffer[Triangle]) { private def triangulate(P: Array[Point], ab: List[Point], T: ArrayBuffer[Triangle]) {

View File

@ -48,25 +48,26 @@ class Triangle(val points: Array[Point], val neighbors: Array[Triangle]) {
// Update neighbor pointers // Update neighbor pointers
// Debug version // Debug version
def markNeighbor(ccwPoint: Point, cwPoint: Point, triangle: Triangle, debug: HashSet[Triangle]) { def markNeighbor(p1: Point, p2: Point, triangle: Triangle, debug: HashSet[Triangle]) {
if((ccwPoint == points(2) && cwPoint == points(1)) || (ccwPoint == points(1) && cwPoint == points(2))) if((p1 == points(2) && p2 == points(1)) || (p1 == points(1) && p2 == points(2)))
neighbors(0) = triangle neighbors(0) = triangle
else if((ccwPoint == points(0) && cwPoint == points(2)) || (ccwPoint == points(2) && cwPoint == points(0))) else if((p1 == points(0) && p2 == points(2)) || (p1 == points(2) && p2 == points(0)))
neighbors(1) = triangle neighbors(1) = triangle
else if((ccwPoint == points(0) && cwPoint == points(1)) || (ccwPoint == points(1) && cwPoint == points(0))) else if((p1 == points(0) && p2 == points(1)) || (p1 == points(1) && p2 == points(0)))
neighbors(2) = triangle neighbors(2) = triangle
else { else {
debug += triangle debug += triangle
println("Neighbor pointer ERROR!")
} }
} }
// Update neighbor pointers // Update neighbor pointers
def markNeighbor(ccwPoint: Point, cwPoint: Point, triangle: Triangle) { def markNeighbor(p1: Point, p2: Point, triangle: Triangle) {
if((ccwPoint == points(2) && cwPoint == points(1)) || (ccwPoint == points(1) && cwPoint == points(2))) if((p1 == points(2) && p2 == points(1)) || (p1 == points(1) && p2 == points(2)))
neighbors(0) = triangle neighbors(0) = triangle
else if((ccwPoint == points(0) && cwPoint == points(2)) || (ccwPoint == points(2) && cwPoint == points(0))) else if((p1 == points(0) && p2 == points(2)) || (p1 == points(2) && p2 == points(0)))
neighbors(1) = triangle neighbors(1) = triangle
else if((ccwPoint == points(0) && cwPoint == points(1)) || (ccwPoint == points(1) && cwPoint == points(0))) else if((p1 == points(0) && p2 == points(1)) || (p1 == points(1) && p2 == points(0)))
neighbors(2) = triangle neighbors(2) = triangle
else { else {
throw new Exception("Neighbor pointer error, please report!") throw new Exception("Neighbor pointer error, please report!")