Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -49,4 +49,16 @@ public static Geometry transform(Geometry geometry, double zValue) {
GeometryForce3DTransformer transformer = new GeometryForce3DTransformer(zValue);
return transformer.transform(geometry);
}

protected Geometry transformMultiPolygon(MultiPolygon geom, Geometry parent) {
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is simply an override of this method in JTS's GeometryTransformer class to handle MultiPolygons separately.

// Transform each polygon individually to avoid recursion
Polygon[] transformedPolygons = new Polygon[geom.getNumGeometries()];
for (int i = 0; i < geom.getNumGeometries(); i++) {
Polygon polygon = (Polygon) geom.getGeometryN(i);
Geometry transformed = super.transform(polygon);
transformedPolygons[i] = (Polygon) transformed;
}
// Always return as MultiPolygon, even if there's only one polygon
return geom.getFactory().createMultiPolygon(transformedPolygons);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2460,6 +2460,24 @@ public void force3DHybridGeomCollectionDefaultValue() {
wktWriter3D.write(actualGeometryCollection.getGeometryN(0).getGeometryN(2)));
}

@Test
public void force3DMultiPolygonWithSinglePolygon() {
// Test that a MultiPolygon with a single polygon remains a MultiPolygon after force3D
Polygon polygon = GEOMETRY_FACTORY.createPolygon(coordArray(0, 0, 10, 0, 10, 10, 0, 10, 0, 0));
MultiPolygon multiPolygon = GEOMETRY_FACTORY.createMultiPolygon(new Polygon[] {polygon});

Geometry forced = Functions.force3D(multiPolygon, 5.0);

assertTrue(forced instanceof MultiPolygon);
assertEquals(1, ((MultiPolygon) forced).getNumGeometries());

Polygon forcedPolygon = (Polygon) ((MultiPolygon) forced).getGeometryN(0);
Coordinate[] coords = forcedPolygon.getCoordinates();
for (Coordinate coord : coords) {
assertEquals(5.0, coord.getZ(), 0.0001);
}
}

@Test
public void makeLine() {
Point point1 = GEOMETRY_FACTORY.createPoint(new Coordinate(0, 0));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3033,6 +3033,17 @@ class functionTestScala
}
}

it("should pass ST_Force3D with MultiPolygon containing single polygon") {
// Test that a MultiPolygon with a single polygon remains a MultiPolygon after force3D
val df = sparkSession.sql(
"SELECT ST_AsText(ST_Force3D(ST_GeomFromWKT('MULTIPOLYGON (((0 0, 10 0, 10 10, 0 10, 0 0)))'), 5.0)) AS geom")
val actual = df.take(1)(0).get(0).asInstanceOf[String]
// Should still be MULTIPOLYGON, not POLYGON
assertTrue(actual.startsWith("MULTIPOLYGON"))
assertTrue(actual.contains("Z"))
assertTrue(actual.contains("5"))
}

it("Should pass ST_Force3DZ") {
val geomTestCases = Map(
("'LINESTRING (0 1, 1 0, 2 0)'") -> ("'LINESTRING Z(0 1 1, 1 0 1, 2 0 1)'", "'LINESTRING Z(0 1 0, 1 0 0, 2 0 0)'"),
Expand Down
Loading