1 #ifndef OSMIUM_GEOM_GEOS_HPP
2 #define OSMIUM_GEOM_GEOS_HPP
48 #include <geos/geom/Coordinate.h>
49 #include <geos/geom/CoordinateSequence.h>
50 #include <geos/geom/CoordinateSequenceFactory.h>
51 #include <geos/geom/GeometryFactory.h>
52 #include <geos/geom/LinearRing.h>
53 #include <geos/geom/MultiPolygon.h>
54 #include <geos/geom/Point.h>
55 #include <geos/geom/Polygon.h>
56 #include <geos/geom/PrecisionModel.h>
57 #include <geos/util/GEOSException.h>
66 # define THROW std::throw_with_nested
74 geometry_error(
std::string(
"geometry creation failed in GEOS library: ") + message) {
83 class GEOSFactoryImpl {
85 geos::geom::PrecisionModel m_precision_model;
86 geos::geom::GeometryFactory m_geos_factory;
88 std::unique_ptr<geos::geom::CoordinateSequence> m_coordinate_sequence;
89 std::vector<std::unique_ptr<geos::geom::LinearRing>> m_rings;
90 std::vector<std::unique_ptr<geos::geom::Polygon>> m_polygons;
94 typedef std::unique_ptr<geos::geom::Point> point_type;
95 typedef std::unique_ptr<geos::geom::LineString> linestring_type;
96 typedef std::unique_ptr<geos::geom::Polygon> polygon_type;
97 typedef std::unique_ptr<geos::geom::MultiPolygon> multipolygon_type;
98 typedef std::unique_ptr<geos::geom::LinearRing> ring_type;
100 explicit GEOSFactoryImpl(
int srid = -1) :
102 m_geos_factory(&m_precision_model, srid) {
109 return point_type(m_geos_factory.createPoint(geos::geom::Coordinate(xy.
x, xy.
y)));
110 }
catch (geos::util::GEOSException& e) {
117 void linestring_start() {
119 m_coordinate_sequence.reset(m_geos_factory.getCoordinateSequenceFactory()->create(static_cast<size_t>(0), 2));
120 }
catch (geos::util::GEOSException& e) {
127 m_coordinate_sequence->add(geos::geom::Coordinate(xy.
x, xy.
y));
128 }
catch (geos::util::GEOSException& e) {
133 linestring_type linestring_finish(
size_t ) {
135 return linestring_type(m_geos_factory.createLineString(m_coordinate_sequence.release()));
136 }
catch (geos::util::GEOSException& e) {
143 void multipolygon_start() {
147 void multipolygon_polygon_start() {
151 void multipolygon_polygon_finish() {
153 assert(!m_rings.empty());
154 auto inner_rings =
new std::vector<geos::geom::Geometry*>;
155 std::transform(std::next(m_rings.begin(), 1), m_rings.end(), std::back_inserter(*inner_rings), [](std::unique_ptr<geos::geom::LinearRing>& r) {
158 m_polygons.emplace_back(m_geos_factory.createPolygon(m_rings[0].release(), inner_rings));
160 }
catch (geos::util::GEOSException& e) {
165 void multipolygon_outer_ring_start() {
167 m_coordinate_sequence.reset(m_geos_factory.getCoordinateSequenceFactory()->create(static_cast<size_t>(0), 2));
168 }
catch (geos::util::GEOSException& e) {
173 void multipolygon_outer_ring_finish() {
175 m_rings.emplace_back(m_geos_factory.createLinearRing(m_coordinate_sequence.release()));
176 }
catch (geos::util::GEOSException& e) {
181 void multipolygon_inner_ring_start() {
183 m_coordinate_sequence.reset(m_geos_factory.getCoordinateSequenceFactory()->create(static_cast<size_t>(0), 2));
184 }
catch (geos::util::GEOSException& e) {
189 void multipolygon_inner_ring_finish() {
191 m_rings.emplace_back(m_geos_factory.createLinearRing(m_coordinate_sequence.release()));
192 }
catch (geos::util::GEOSException& e) {
199 m_coordinate_sequence->add(geos::geom::Coordinate(xy.
x, xy.
y));
200 }
catch (geos::util::GEOSException& e) {
205 multipolygon_type multipolygon_finish() {
207 auto polygons =
new std::vector<geos::geom::Geometry*>;
208 std::transform(m_polygons.begin(), m_polygons.end(), std::back_inserter(*polygons), [](std::unique_ptr<geos::geom::Polygon>& p) {
212 return multipolygon_type(m_geos_factory.createMultiPolygon(polygons));
213 }
catch (geos::util::GEOSException& e) {
222 template <
class TProjection = IdentityProjection>
231 #endif // OSMIUM_GEOM_GEOS_HPP
double y
Definition: coordinates.hpp:50
Definition: factory.hpp:146
#define THROW
Definition: geos.hpp:66
Definition: reader_iterator.hpp:39
Definition: factory.hpp:57
Namespace for everything in the Osmium library.
Definition: assembler.hpp:55
geos_geometry_error(const char *message)
Definition: geos.hpp:73
Definition: coordinates.hpp:47
double x
Definition: coordinates.hpp:49