Skip to content

Commit

Permalink
claimchunk: fix various polygon merging issues
Browse files Browse the repository at this point in the history
- fix some claims not connecting by sorting before grouping
- fix polygons with negative space/points after SEG_CLOSE getting mangled
  • Loading branch information
jpenilla committed Oct 9, 2024
1 parent 390dcb0 commit e5887e1
Show file tree
Hide file tree
Showing 3 changed files with 31 additions and 19 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,8 @@ public final class ClaimChunkConfig extends Config<ClaimChunkConfig, WorldConfig
public double strokeOpacity = 0.75D;
public Color fillColor = Color.RED;
public double fillOpacity = 0.2D;
public String claimTooltip = "{owner}";
public boolean showChunks = true;
public String claimTooltip = "{name}";
public boolean showChunks = false;

@SuppressWarnings("unused")
private void init() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
import com.cjburkey.claimchunk.player.PlayerHandler;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
Expand Down Expand Up @@ -90,16 +91,15 @@ private List<Group> groupClaims(List<Claim> claims) {
// break groups down by owner
Map<UUID, List<Claim>> byOwner = new HashMap<>();
for (Claim claim : claims) {
List<Claim> list = byOwner.getOrDefault(claim.owner(), new ArrayList<>());
list.add(claim);
byOwner.put(claim.owner(), list);
byOwner.computeIfAbsent(claim.owner(), $ -> new ArrayList<>()).add(claim);
}

// combine touching claims
Map<UUID, List<Group>> groups = new HashMap<>();
for (Map.Entry<UUID, List<Claim>> entry : byOwner.entrySet()) {
UUID owner = entry.getKey();
List<Claim> list = entry.getValue();
list.sort(Comparator.comparing(Claim::x).thenComparing(Claim::z));
next1:
for (Claim claim : list) {
List<Group> groupList = groups.getOrDefault(owner, new ArrayList<>());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
public final class RectangleMerge {

public static Polygon getPoly(List<Claim> claims) {
List<Point> combined = new ArrayList<>();
List<Shape> shapes = new ArrayList<>();
for (Claim claim : claims) {
int x = claim.x() << 4;
int z = claim.z() << 4;
Expand All @@ -27,19 +27,23 @@ public static Polygon getPoly(List<Claim> claims) {
Point.of(x + 16, z + 16),
Point.of(x + 16, z)
);
if (combined.isEmpty()) {
combined = points;
shapes.add(toShape(points));
}

Area area = null;
for (Shape shape : shapes) {
if (area == null) {
area = new Area(shape);
} else {
combined = merge(combined, points);
area.add(new Area(shape));
}
}
return Marker.polygon(combined);
}

private static List<Point> merge(List<Point> p1, List<Point> p2) {
Area area = new Area(toShape(p1));
area.add(new Area(toShape(p2)));
return toPoints(area);
if (area == null) {
throw new IllegalStateException();
}

return toMarker(area);
}

private static Shape toShape(List<Point> points) {
Expand All @@ -56,18 +60,26 @@ private static Shape toShape(List<Point> points) {
return path;
}

private static List<Point> toPoints(Shape shape) {
List<Point> result = new ArrayList<>();
private static Polygon toMarker(Shape shape) {
List<Point> main = new ArrayList<>();
List<List<Point>> subtract = new ArrayList<>();
PathIterator iter = shape.getPathIterator(null, 0.0);
double[] coords = new double[6];
List<Point> current = main;
while (!iter.isDone()) {
int segment = iter.currentSegment(coords);
switch (segment) {
case PathIterator.SEG_MOVETO, PathIterator.SEG_LINETO -> result.add(Point.of(coords[0], coords[1]));
case PathIterator.SEG_MOVETO, PathIterator.SEG_LINETO -> current.add(Point.of(coords[0], coords[1]));
case PathIterator.SEG_CLOSE -> {
List<Point> newList = new ArrayList<>();
subtract.add(newList);
current = newList;
}
}
iter.next();
}
return result;
subtract.removeIf(List::isEmpty);
return Marker.polygon(main, subtract);
}

}
Expand Down

0 comments on commit e5887e1

Please sign in to comment.