Skip to content

Commit 1847f05

Browse files
committed
sort of works
1 parent de54b22 commit 1847f05

File tree

6 files changed

+346
-313
lines changed

6 files changed

+346
-313
lines changed

.idea/workspace.xml

Lines changed: 195 additions & 245 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/main/java/convex_dt/ConvexDT.java

Lines changed: 38 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -45,16 +45,16 @@ public void setScene(J2DScene scene) {
4545
public HalfEdge computeSmallDelaunay(ArrayList<KDSPoint> points) throws Exception {
4646
if (points.size() == 2) {
4747
// sort them
48-
sort(points);
48+
//sort(points);
4949
KDSPoint a = points.get(0);
5050
KDSPoint b = points.get(1);
5151
HalfEdge e1 = dcel.createEdge(a, b);
5252
if (e1.getOrigin().getPoint(0).y() < e1.getDestination().getPoint(0).y())
5353
return e1;
5454
return e1.getTwin();
5555
} else if (points.size() == 3) {
56-
// sort them
57-
sort(points);
56+
// sort them, is it really needed though?
57+
// sort(points);
5858
KDSPoint a = points.get(0);
5959
KDSPoint b = points.get(1);
6060
KDSPoint c = points.get(2);
@@ -67,23 +67,23 @@ public HalfEdge computeSmallDelaunay(ArrayList<KDSPoint> points) throws Exceptio
6767
e2.setPrev(e1);
6868
e2.getTwin().setNext(e1.getTwin());
6969

70+
// don't create a triangle if they are collinear
7071
if (leftOf(a, b, c) || rightOf(a, b, c)) {
7172
// connect and create a triangle
7273
System.out.println("Creating triangle!");
7374
connect(e2, e1);
7475
}
75-
HalfEdge lowest = e1;
76-
while (true) {
77-
if (lowest.getNext() != null && lowerThan(lowest.getNext(), lowest)) {
78-
lowest = lowest.getNext();
79-
} else {
80-
break;
81-
}
82-
if (lowest == e1) break;
83-
}
84-
if (lowest.getOrigin().getPoint(0).y() < lowest.getDestination().getPoint(0).y())
85-
return lowest;
86-
return lowest.getTwin();
76+
// find the lowest point (y-coordinate only)
77+
KDSPoint lowestPoint;
78+
if (a.getY() < b.getY()) lowestPoint = a;
79+
else lowestPoint = b;
80+
if (lowestPoint.getY() > c.getY()) lowestPoint = c;
81+
82+
// find the ccw edge incident to lowest point
83+
HalfEdge candidateEdge = lowestPoint.getIncidentEdge();
84+
if (!isCCW(candidateEdge.getPrev().getOrigin(), candidateEdge.getOrigin(), candidateEdge.getDestination()))
85+
candidateEdge = candidateEdge.getTwin();
86+
return candidateEdge;
8787
} else {
8888
throw new Exception();
8989
}
@@ -111,20 +111,19 @@ infCircleEnum.INSIDE && lessThan(rNext(right).getOrigin(), right.getOrigin())) {
111111
} else {
112112
// TODO I think it should move CW around left as the 'candidate' for lower support can't be on the right
113113
// side of left when the lowest point in right is lower
114-
while (rPrev(left) != null && rNext(right) != null &&
115-
shape.inInfCircle(rPrev(left).getOrigin(), left.getOrigin(), right.getOrigin()) ==
116-
infCircleEnum.INSIDE && lessThan(rNext(right).getOrigin(), right.getOrigin())) {
114+
while (lPrev(left) != null && shape.inInfCircle(lPrev(left).getOrigin(), left.getOrigin(), right.getOrigin()) ==
115+
infCircleEnum.INSIDE && lessThan(lPrev(left).getOrigin(), left.getOrigin())) {
117116
if (rPrev(left) == null) break;
118-
left = rPrev(left);
117+
left = lPrev(left);
119118
}
120119
while (true) {
121120
if (shape.inInfCircle(left.getDestination(), left.getOrigin(), right.getOrigin()) == infCircleEnum.INSIDE) {
122-
left = rNext(left);
121+
left = rPrev(left);
123122
} else if (shape.inInfCircle(right.getDestination(), left.getOrigin(), right.getOrigin()) == infCircleEnum.INSIDE) {
124-
right = rNext(right);
123+
right = rPrev(right);
125124
} else {
126-
if (oNext(right) == null) return connect(left.getTwin(), right).getTwin();
127-
return connect(left.getTwin(), oNext(right)).getTwin();
125+
if (oNext(left) == null) return connect(left, right.getTwin()).getTwin();
126+
return connect(oNext(left), right.getTwin()).getTwin();
128127
}
129128
System.out.println("Am I stuck in lowersupport2?");
130129
}
@@ -183,10 +182,10 @@ public HalfEdge produceONext(HalfEdge edge) {
183182
}
184183

185184
public HalfEdge produceOPrev(HalfEdge edge) {
186-
if (lPrev(edge).isBridge()) {
185+
if (lPrev(edge) != null && lPrev(edge).isBridge()) {
187186
delete(lPrev(edge));
188187
makeBundle(connect(lPrev(edge), edge).getTwin());
189-
} else if (oPrev(edge).isBridge()) {
188+
} else if (oPrev(edge) != null && oPrev(edge).isBridge()) {
190189
delete(oPrev(edge));
191190
makeBundle(oNext(connect(edge, lNext(edge))));
192191
}
@@ -326,18 +325,17 @@ public HalfEdge computeRcand() {
326325
HalfEdge current = null, top = null, t = null;
327326
boolean foundRcand = false;
328327
// base must be directed from left to right for this
329-
base = base.getTwin();
330-
rcand = lNext(base);
328+
rcand = lNext(base.getTwin());
331329

332330
if (rcand != null && shape.inInfCircle(rcand.getDestination(), base.getOrigin(), base.getDestination()) == infCircleEnum.BEFORE) {
333331
rcand = produceOPrev(rcand);
334332
while (shape.inInfCircle(rcand.getDestination(), base.getDestination(), base.getOrigin()) == infCircleEnum.BEFORE) {
335-
delete(oNext(rcand));
333+
delete(rNext(rcand).getTwin());
336334
if (produceOPrev(rcand) == null) break;
337335
rcand = produceOPrev(rcand);
338336
}
339-
if (isValid(rcand)) delete(oNext(rcand));
340-
else rcand = oNext(rcand);
337+
if (isValid(rcand)) delete(rNext(rcand).getTwin());
338+
else rcand = rNext(rcand).getTwin();
341339
}
342340

343341
if (isValid(rcand)) {
@@ -353,18 +351,19 @@ public HalfEdge computeRcand() {
353351
current.draw(scene, 0, Color.ORANGE);
354352
top = rcand;
355353
while (true) {
354+
assert rcand != null;
356355
if (foundRcand) break;
357-
switch (shape.inCircle(rcand.getOrigin(), rcand.getDestination(), base.getOrigin(), current.getDestination())) {
356+
switch (shape.inCircle(rcand.getDestination(), rcand.getOrigin(), base.getDestination(), current.getDestination())) {
358357
case INSIDE:
359358
if (current.isBridge() || lNext(current).isBridge()) {
360-
current = produceOPrev(lNext(current));
359+
current = produceOPrev(oNext(current));
361360
}
362361
if (rightOf(rcand.getOrigin(), rcand.getDestination(), current.getDestination())) {
363362
if (lNext(current) != dNext(rcand)) {
364363
makeBundle(connect(rcand, current.getTwin()).getTwin());
365364
}
366365
if (current != oPrev(rcand)) {
367-
makeBundle(connect(lNext(rcand), current.getTwin()));
366+
makeBundle(rPrev(connect(rNext(rcand), current.getTwin())));
368367
}
369368
t = produceOPrev(rcand);
370369
delete(rcand);
@@ -377,7 +376,7 @@ public HalfEdge computeRcand() {
377376
break;
378377
case ONBEFORE:
379378
if (rightOf(current.getOrigin(), rcand.getDestination(), current.getDestination())) {
380-
current = lNext(current);
379+
current = rNext(current);
381380
} else {
382381
foundRcand = true;
383382
}
@@ -399,15 +398,13 @@ public HalfEdge computeRcand() {
399398
}
400399

401400
if (top != null && rcand != null && top != rcand) {
402-
makeBundle(connect(top, rcand));
401+
makeBundle(rPrev(connect(top, rcand)));
403402
top = oPrev(rcand);
404403
}
405404
if (current != null && top != null && oNext(current) != top) {
406-
makeBundle(connect(top, oNext(current)));
405+
makeBundle(oNext(connect(top, oNext(current))));
407406
}
408407

409-
// revert direction
410-
base = base.getTwin();
411408
return rcand;
412409
}
413410

@@ -430,7 +427,7 @@ public HalfEdge delaunay(ArrayList<KDSPoint> points) throws Exception {
430427
sleep(1000);
431428
base = findLowerSupport(lleft, lright);
432429
base.draw(scene, 0, Color.black);
433-
sleep(5000);
430+
sleep(1000);
434431
boolean leftLower = lowerThan(lleft.getOrigin(), lright.getOrigin());
435432
HalfEdge lower;
436433
if (leftLower) {
@@ -447,6 +444,8 @@ public HalfEdge delaunay(ArrayList<KDSPoint> points) throws Exception {
447444
System.out.println("ROUND TWO");
448445
}
449446
++iteration;
447+
base.draw(scene, 0, Color.BLACK);
448+
sleep(1000);
450449
lcand = computeLcand();
451450
rcand = computeRcand();
452451
System.out.println(lcand.getTwin() == rcand || lcand == rcand);

src/main/java/convex_dt/run.java

Lines changed: 38 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
11
package convex_dt;
22

33
import ProGAL.geom2d.viewer.J2DScene;
4-
import dcel.DCEL;
54
import dcel.HalfEdge;
65
import kds.KDSPoint;
76

87
import java.util.ArrayList;
98
import java.util.Random;
109

1110
import static java.util.Collections.sort;
11+
import static java.lang.Thread.sleep;
1212

1313
/**
1414
* Created by cvium on 11-12-2016.
@@ -18,23 +18,42 @@ public static void main(String[] args) throws Exception {
1818
ArrayList<KDSPoint> points = new ArrayList<>();
1919
ConvexShape circle = new Circle();
2020

21-
points.add(new KDSPoint(new double[]{0}, new double[]{0}));
22-
points.add(new KDSPoint(new double[]{-0.5}, new double[]{1}));
23-
points.add(new KDSPoint(new double[]{0.5}, new double[]{1.5}));
24-
points.add(new KDSPoint(new double[]{2}, new double[]{0.5}));
25-
points.add(new KDSPoint(new double[]{3}, new double[]{2.5}));
26-
points.add(new KDSPoint(new double[]{2.5}, new double[]{3}));
27-
// Random rand = new Random();
28-
//
29-
// for (int i = 0; i < 6; ++i) {
30-
// double[] coeffsX = new double[1];
31-
// double[] coeffsY = new double[1];
32-
// for (int j = 0; j < 1; ++j) {
33-
// coeffsX[j] = -1 + (1 + 1) * rand.nextDouble();//
34-
// coeffsY[j] = -1 + (1 + 1) * rand.nextDouble();
35-
// }
36-
// points.add(new KDSPoint(coeffsX, coeffsY));
37-
// }
21+
if (false) {
22+
points.add(new KDSPoint(new double[]{0}, new double[]{0}));
23+
points.add(new KDSPoint(new double[]{-0.5}, new double[]{1}));
24+
points.add(new KDSPoint(new double[]{0.5}, new double[]{1.5}));
25+
points.add(new KDSPoint(new double[]{2}, new double[]{0.5}));
26+
points.add(new KDSPoint(new double[]{3}, new double[]{2.5}));
27+
points.add(new KDSPoint(new double[]{2.5}, new double[]{3}));
28+
} else if (false) {
29+
points.add(new KDSPoint(new double[]{-0.5}, new double[]{1}));
30+
points.add(new KDSPoint(new double[]{0}, new double[]{0}));
31+
points.add(new KDSPoint(new double[]{0.5}, new double[]{1.2}));
32+
points.add(new KDSPoint(new double[]{2}, new double[]{0.5}));
33+
points.add(new KDSPoint(new double[]{2.5}, new double[]{0.8}));
34+
points.add(new KDSPoint(new double[]{2.6}, new double[]{0.3}));
35+
} else if (true){
36+
points.add(new KDSPoint(new double[]{0}, new double[]{1}));
37+
points.add(new KDSPoint(new double[]{0.3}, new double[]{0.7}));
38+
points.add(new KDSPoint(new double[]{0.5}, new double[]{1.1}));
39+
points.add(new KDSPoint(new double[]{1}, new double[]{0.2}));
40+
points.add(new KDSPoint(new double[]{1.2}, new double[]{0.5}));
41+
points.add(new KDSPoint(new double[]{1.4}, new double[]{0.22}));
42+
}
43+
44+
else{
45+
Random rand = new Random();
46+
47+
for (int i = 0; i < 20; ++i) {
48+
double[] coeffsX = new double[1];
49+
double[] coeffsY = new double[1];
50+
for (int j = 0; j < 1; ++j) {
51+
coeffsX[j] = -1 + (1 + 1) * rand.nextDouble();//
52+
coeffsY[j] = -1 + (1 + 1) * rand.nextDouble();
53+
}
54+
points.add(new KDSPoint(coeffsX, coeffsY));
55+
}
56+
}
3857

3958
sort(points);
4059

@@ -54,6 +73,7 @@ public static void main(String[] args) throws Exception {
5473
System.out.println("Printing DCEL!");
5574
scene.removeAllShapes();
5675
scene.repaint();
76+
sleep(1000);
5777
for (KDSPoint p : points) {
5878
p.draw(scene, 0);
5979
}

src/main/java/dcel/DCEL.java

Lines changed: 30 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -145,6 +145,7 @@ else if (b.getPrev() != null) {
145145
while (tmp != null && tmp != c_twin) {
146146
tmp.draw(scene, 0, Color.CYAN);
147147
scene.repaint();
148+
try {sleep(1000);} catch (InterruptedException e){}
148149
tmp.setFace(c_twin_face);
149150
tmp = tmp.getNext();
150151
}
@@ -171,7 +172,7 @@ else if (b.getPrev() != null) {
171172
}
172173

173174
public void deleteEdge(HalfEdge e) {
174-
// remove e from its prev and next edges, TODO: IS THAT ENOUGH?
175+
// remove e from its face if it's the outercomponent of said face. if e has no next and no prev, delete face
175176
if (e.getFace().getOuterComponent() == e) {
176177
if (e.getNext() != null)
177178
e.getFace().setOuterComponent(e.getNext());
@@ -181,13 +182,36 @@ else if (e.getPrev() != null)
181182
faces.remove(e.getFace());
182183
}
183184

184-
if (e.getPrev() != null) e.getPrev().setNext(null);
185-
if (e.getNext() != null) e.getNext().setPrev(null);
186-
// have to remove the twin as well
187-
if (e.getTwin().getPrev() != null) e.getTwin().getPrev().setNext(null);
188-
if (e.getTwin().getNext() != null) e.getTwin().getNext().setPrev(null);
185+
// update incident edges for e and e.twin
186+
updateIncidentEdges(e);
187+
updateIncidentEdges(e.getTwin());
188+
189189
edges.remove(e);
190190
edges.remove(e.getTwin());
191+
192+
e.undraw(scene);
193+
e.getTwin().undraw(scene);
194+
scene.repaint();
195+
}
196+
197+
private void updateIncidentEdges(HalfEdge e) {
198+
// remove e from its prev and next edges, TODO: IS THAT ENOUGH? NO, gotta fix them
199+
if (e.getPrev() != null) {
200+
// might need a new next, it will always be e.oPrev if it exists
201+
if (oPrev(e) != null) {
202+
e.getPrev().setNext(oPrev(e));
203+
oPrev(e).setPrev(e.getPrev());
204+
}
205+
else e.getPrev().setNext(null);
206+
}
207+
if (e.getNext() != null) {
208+
// its next might need a new prev, it will always be e.dNext if it exists
209+
if (dNext(e) != null) {
210+
e.getNext().setPrev(dNext(e));
211+
dNext(e).setNext(e.getNext());
212+
}
213+
else e.getNext().setNext(null);
214+
}
191215
}
192216

193217
private Face createFace(HalfEdge e) {

src/main/java/dcel/HalfEdge.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -160,4 +160,12 @@ public void draw(J2DScene scene, double t, boolean next) {
160160
Color color = java.awt.Color.GREEN;
161161
scene.addShape(lineSegment, color);
162162
}
163+
164+
public void undraw(J2DScene scene) {
165+
if (lineSegment != null) {
166+
try {
167+
scene.removeShape(lineSegment);
168+
} catch (IllegalStateException e) {}
169+
}
170+
}
163171
}

0 commit comments

Comments
 (0)