rgeo 2.3.1 → 3.0.0.pre.rc.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (75) hide show
  1. checksums.yaml +4 -4
  2. data/.yardopts +6 -0
  3. data/README.md +11 -10
  4. data/ext/geos_c_impl/analysis.c +8 -6
  5. data/ext/geos_c_impl/analysis.h +1 -3
  6. data/ext/geos_c_impl/errors.c +10 -8
  7. data/ext/geos_c_impl/errors.h +7 -3
  8. data/ext/geos_c_impl/extconf.rb +3 -0
  9. data/ext/geos_c_impl/factory.c +273 -202
  10. data/ext/geos_c_impl/factory.h +51 -63
  11. data/ext/geos_c_impl/geometry.c +124 -22
  12. data/ext/geos_c_impl/geometry.h +8 -3
  13. data/ext/geos_c_impl/geometry_collection.c +81 -185
  14. data/ext/geos_c_impl/geometry_collection.h +1 -14
  15. data/ext/geos_c_impl/globals.c +91 -0
  16. data/ext/geos_c_impl/globals.h +45 -0
  17. data/ext/geos_c_impl/line_string.c +28 -29
  18. data/ext/geos_c_impl/line_string.h +1 -3
  19. data/ext/geos_c_impl/main.c +10 -9
  20. data/ext/geos_c_impl/point.c +9 -8
  21. data/ext/geos_c_impl/point.h +1 -3
  22. data/ext/geos_c_impl/polygon.c +43 -72
  23. data/ext/geos_c_impl/polygon.h +1 -3
  24. data/ext/geos_c_impl/preface.h +12 -0
  25. data/ext/geos_c_impl/ruby_more.c +65 -0
  26. data/ext/geos_c_impl/ruby_more.h +16 -0
  27. data/lib/rgeo/cartesian/calculations.rb +54 -17
  28. data/lib/rgeo/cartesian/factory.rb +6 -14
  29. data/lib/rgeo/cartesian/feature_classes.rb +68 -46
  30. data/lib/rgeo/cartesian/feature_methods.rb +67 -20
  31. data/lib/rgeo/cartesian/interface.rb +0 -36
  32. data/lib/rgeo/cartesian/planar_graph.rb +379 -0
  33. data/lib/rgeo/cartesian/sweepline_intersector.rb +149 -0
  34. data/lib/rgeo/cartesian/valid_op.rb +71 -0
  35. data/lib/rgeo/cartesian.rb +3 -0
  36. data/lib/rgeo/coord_sys/cs/wkt_parser.rb +6 -6
  37. data/lib/rgeo/coord_sys.rb +0 -11
  38. data/lib/rgeo/error.rb +15 -0
  39. data/lib/rgeo/feature/factory_generator.rb +0 -3
  40. data/lib/rgeo/feature/geometry.rb +107 -28
  41. data/lib/rgeo/feature/geometry_collection.rb +13 -5
  42. data/lib/rgeo/feature/line_string.rb +3 -3
  43. data/lib/rgeo/feature/multi_surface.rb +3 -3
  44. data/lib/rgeo/feature/point.rb +4 -4
  45. data/lib/rgeo/feature/surface.rb +3 -3
  46. data/lib/rgeo/geographic/factory.rb +6 -7
  47. data/lib/rgeo/geographic/interface.rb +6 -49
  48. data/lib/rgeo/geographic/proj4_projector.rb +0 -2
  49. data/lib/rgeo/geographic/projected_feature_classes.rb +21 -9
  50. data/lib/rgeo/geographic/projected_feature_methods.rb +67 -28
  51. data/lib/rgeo/geographic/simple_mercator_projector.rb +0 -2
  52. data/lib/rgeo/geographic/spherical_feature_classes.rb +29 -9
  53. data/lib/rgeo/geographic/spherical_feature_methods.rb +79 -2
  54. data/lib/rgeo/geos/capi_factory.rb +21 -38
  55. data/lib/rgeo/geos/capi_feature_classes.rb +54 -11
  56. data/lib/rgeo/geos/ffi_factory.rb +6 -35
  57. data/lib/rgeo/geos/ffi_feature_classes.rb +34 -10
  58. data/lib/rgeo/geos/ffi_feature_methods.rb +39 -5
  59. data/lib/rgeo/geos/interface.rb +0 -24
  60. data/lib/rgeo/geos/zm_factory.rb +0 -19
  61. data/lib/rgeo/geos/zm_feature_methods.rb +16 -0
  62. data/lib/rgeo/geos.rb +6 -3
  63. data/lib/rgeo/impl_helper/basic_geometry_collection_methods.rb +4 -4
  64. data/lib/rgeo/impl_helper/basic_geometry_methods.rb +1 -1
  65. data/lib/rgeo/impl_helper/basic_line_string_methods.rb +15 -19
  66. data/lib/rgeo/impl_helper/basic_point_methods.rb +1 -1
  67. data/lib/rgeo/impl_helper/basic_polygon_methods.rb +1 -1
  68. data/lib/rgeo/impl_helper/valid_op.rb +354 -0
  69. data/lib/rgeo/impl_helper/validity_check.rb +139 -0
  70. data/lib/rgeo/impl_helper.rb +1 -0
  71. data/lib/rgeo/version.rb +1 -1
  72. metadata +45 -9
  73. data/lib/rgeo/coord_sys/srs_database/entry.rb +0 -107
  74. data/lib/rgeo/coord_sys/srs_database/sr_org.rb +0 -64
  75. data/lib/rgeo/coord_sys/srs_database/url_reader.rb +0 -65
@@ -10,58 +10,13 @@
10
10
 
11
11
  RGEO_BEGIN_C
12
12
 
13
- /*
14
- Per-interpreter globals.
15
- Most of these are cached references to commonly used classes, modules,
16
- and symbols so we don't have to do a lot of constant lookups and calls
17
- to rb_intern.
18
- */
19
- typedef struct {
20
- VALUE feature_module;
21
- VALUE feature_geometry;
22
- VALUE feature_point;
23
- VALUE feature_line_string;
24
- VALUE feature_linear_ring;
25
- VALUE feature_line;
26
- VALUE feature_polygon;
27
- VALUE feature_geometry_collection;
28
- VALUE feature_multi_point;
29
- VALUE feature_multi_line_string;
30
- VALUE feature_multi_polygon;
31
- VALUE geos_module;
32
- VALUE geos_geometry;
33
- VALUE geos_point;
34
- VALUE geos_line_string;
35
- VALUE geos_linear_ring;
36
- VALUE geos_line;
37
- VALUE geos_polygon;
38
- VALUE geos_geometry_collection;
39
- VALUE geos_multi_point;
40
- VALUE geos_multi_line_string;
41
- VALUE geos_multi_polygon;
42
- ID id_cast;
43
- ID id_eql;
44
- ID id_generate;
45
- ID id_enum_for;
46
- ID id_hash;
47
- VALUE sym_force_new;
48
- VALUE sym_keep_subtype;
49
- #ifndef RGEO_GEOS_SUPPORTS_SETOUTPUTDIMENSION
50
- VALUE psych_wkt_generator;
51
- VALUE marshal_wkb_generator;
52
- #endif
53
- } RGeo_Globals;
54
-
55
-
56
13
  /*
57
14
  Wrapped structure for Factory objects.
58
15
  A factory encapsulates the GEOS context, and GEOS serializer settings.
59
16
  It also stores the SRID for all geometries created by this factory,
60
17
  and the resolution for buffers created for this factory's geometries.
61
- Finally, it provides easy access to the globals.
62
18
  */
63
19
  typedef struct {
64
- RGeo_Globals* globals;
65
20
  GEOSContextHandle_t geos_context;
66
21
  GEOSWKTReader* wkt_reader;
67
22
  GEOSWKBReader* wkb_reader;
@@ -82,12 +37,35 @@ typedef struct {
82
37
  int buffer_resolution;
83
38
  } RGeo_FactoryData;
84
39
 
85
- #define RGEO_FACTORYFLAGS_LENIENT_MULTIPOLYGON 1
86
- #define RGEO_FACTORYFLAGS_SUPPORTS_Z 2
87
- #define RGEO_FACTORYFLAGS_SUPPORTS_M 4
88
- #define RGEO_FACTORYFLAGS_SUPPORTS_Z_OR_M 6
89
- #define RGEO_FACTORYFLAGS_PREPARE_HEURISTIC 8
40
+ /*
41
+ Flags that are used to pass options when creating a factory.
42
+ They are available in ruby under RGeo::Geos::CAPIFactory::FLAG_name
43
+ where name is the name below without the RGEO_FACTORYFLAGS_ prefix.
44
+ */
45
+ #define RGEO_FACTORYFLAGS_SUPPORTS_Z 0b0010
46
+ #define RGEO_FACTORYFLAGS_SUPPORTS_M 0b0100
47
+ #define RGEO_FACTORYFLAGS_SUPPORTS_Z_OR_M (RGEO_FACTORYFLAGS_SUPPORTS_Z | RGEO_FACTORYFLAGS_SUPPORTS_M)
48
+ #define RGEO_FACTORYFLAGS_PREPARE_HEURISTIC 0b1000
49
+
50
+ /* call-seq:
51
+ * RGeo::Geos::CAPIFactory.supports_z? -> true or false
52
+ */
53
+ VALUE method_factory_supports_z_p(VALUE self);
54
+
55
+ /* call-seq:
56
+ * RGeo::Geos::CAPIFactory.supports_m? -> true or false
57
+ */
58
+ VALUE method_factory_supports_m_p(VALUE self);
59
+
60
+ /* call-seq:
61
+ * RGeo::Geos::CAPIFactory.supports_z_or_m? -> true or false
62
+ */
63
+ VALUE method_factory_supports_z_or_m_p(VALUE self);
90
64
 
65
+ /* call-seq:
66
+ * RGeo::Geos::CAPIFactory.prepare_heuristic? -> true or false
67
+ */
68
+ VALUE method_factory_prepare_heuristic_p(VALUE self);
91
69
 
92
70
  /*
93
71
  Wrapped structure for Geometry objects.
@@ -119,18 +97,30 @@ typedef struct {
119
97
  } RGeo_GeometryData;
120
98
 
121
99
 
100
+ // Data types which indicate how RGeo types should be managed by Ruby.
101
+ extern const rb_data_type_t rgeo_factory_type;
102
+
103
+ extern const rb_data_type_t rgeo_geometry_type;
104
+
105
+
106
+ // Convenient macros for checking the type of data from Ruby
107
+ #define RGEO_FACTORY_TYPEDDATA_P(object) (_RGEO_TYPEDDATA_P(object, &rgeo_factory_type))
108
+ #define RGEO_GEOMETRY_TYPEDDATA_P(object) (_RGEO_TYPEDDATA_P(object, &rgeo_geometry_type))
109
+
110
+ #define _RGEO_TYPEDDATA_P(object, data_type) (TYPE(object) == T_DATA && RTYPEDDATA(object)->typed_flag == 1 && RTYPEDDATA(object)->type == data_type)
111
+
122
112
  // Returns the RGeo_FactoryData* given a ruby Factory object
123
- #define RGEO_FACTORY_DATA_PTR(factory) ((RGeo_FactoryData*)DATA_PTR(factory))
113
+ #define RGEO_FACTORY_DATA_PTR(factory) ((RGeo_FactoryData*)RTYPEDDATA_DATA(factory))
124
114
 
125
115
  // Returns the RGeo_GeometryData* given a ruby Geometry object
126
- #define RGEO_GEOMETRY_DATA_PTR(geometry) ((RGeo_GeometryData*)DATA_PTR(geometry))
116
+ #define RGEO_GEOMETRY_DATA_PTR(geometry) ((RGeo_GeometryData*)RTYPEDDATA_DATA(geometry))
127
117
 
128
118
 
129
119
  /*
130
120
  Initializes the factory module. This should be called first in the
131
121
  initialization process.
132
122
  */
133
- RGeo_Globals* rgeo_init_geos_factory();
123
+ void rgeo_init_geos_factory();
134
124
 
135
125
  /*
136
126
  Given a GEOS geometry handle, wraps it in a ruby Geometry object of the
@@ -177,8 +167,15 @@ const GEOSGeometry* rgeo_convert_to_geos_geometry(VALUE factory, VALUE obj, VALU
177
167
  result of this function to build a GEOS-backed clone of the original
178
168
  geometry, or to include the given geometry in a collection while keeping
179
169
  the klasses intact.
170
+
171
+ The state parameter is given to follow `rb_protect*` ruby methods: this
172
+ method calls `#cast`, and this call may raise. if it does raise, state
173
+ will be set to a non-zero value, and you'll have access to the error
174
+ in `rb_errinfo()`. IT IS THE CALLER'S RESPONSIBILITY TO PROPAGATE THE
175
+ ERROR. You could also discard the error with `rb_set_errinfo(Qnil)`,
176
+ this will just ignore the error altogether.
180
177
  */
181
- GEOSGeometry* rgeo_convert_to_detached_geos_geometry(VALUE obj, VALUE factory, VALUE type, VALUE* klasses);
178
+ GEOSGeometry* rgeo_convert_to_detached_geos_geometry(VALUE obj, VALUE factory, VALUE type, VALUE* klasses, int* state);
182
179
 
183
180
  /*
184
181
  Returns 1 if the given ruby object is a GEOS Geometry implementation,
@@ -197,15 +194,6 @@ void rgeo_check_geos_object(VALUE obj);
197
194
  */
198
195
  const GEOSGeometry* rgeo_get_geos_geometry_safe(VALUE obj);
199
196
 
200
- /*
201
- Compares the coordinate sequences for two given GEOS geometries.
202
- The two given geometries MUST be of types backed directly by
203
- coordinate sequences-- i.e. points or line strings.
204
- Returns Qtrue if the two coordinate sequences are equal, Qfalse
205
- if they are inequal, or Qnil if an error occurs.
206
- */
207
- VALUE rgeo_geos_coordseqs_eql(GEOSContextHandle_t context, const GEOSGeometry* geom1, const GEOSGeometry* geom2, char check_z);
208
-
209
197
  /*
210
198
  Compares the ruby classes and geometry factories of the two given ruby
211
199
  objects. Returns Qtrue if everything is equal (that is, the two objects
@@ -11,6 +11,9 @@
11
11
  #include <ruby.h>
12
12
  #include <geos_c.h>
13
13
 
14
+ #include "globals.h"
15
+
16
+ #include "errors.h"
14
17
  #include "factory.h"
15
18
  #include "geometry.h"
16
19
 
@@ -180,13 +183,11 @@ static VALUE method_geometry_geometry_type(VALUE self)
180
183
  {
181
184
  VALUE result;
182
185
  RGeo_GeometryData* self_data;
183
- const GEOSGeometry* self_geom;
184
186
 
185
187
  result = Qnil;
186
188
  self_data = RGEO_GEOMETRY_DATA_PTR(self);
187
- self_geom = self_data->geom;
188
- if (self_geom) {
189
- result = RGEO_FACTORY_DATA_PTR(self_data->factory)->globals->feature_geometry;
189
+ if (self_data->geom) {
190
+ result = rgeo_feature_geometry_module;
190
191
  }
191
192
  return result;
192
193
  }
@@ -271,7 +272,7 @@ static VALUE method_geometry_as_text(VALUE self)
271
272
  factory_data = RGEO_FACTORY_DATA_PTR(self_data->factory);
272
273
  wkt_generator = factory_data->wkrep_wkt_generator;
273
274
  if (!NIL_P(wkt_generator)) {
274
- result = rb_funcall(wkt_generator, factory_data->globals->id_generate, 1, self);
275
+ result = rb_funcall(wkt_generator, rb_intern("generate"), 1, self);
275
276
  }
276
277
  else {
277
278
  wkt_writer = factory_data->wkt_writer;
@@ -310,7 +311,7 @@ static VALUE method_geometry_as_binary(VALUE self)
310
311
  factory_data = RGEO_FACTORY_DATA_PTR(self_data->factory);
311
312
  wkb_generator = factory_data->wkrep_wkb_generator;
312
313
  if (!NIL_P(wkb_generator)) {
313
- result = rb_funcall(wkb_generator, factory_data->globals->id_generate, 1, self);
314
+ result = rb_funcall(wkb_generator, rb_intern("generate"), 1, self);
314
315
  }
315
316
  else {
316
317
  wkb_writer = factory_data->wkb_writer;
@@ -385,6 +386,11 @@ static VALUE method_geometry_equals(VALUE self, VALUE rhs)
385
386
  GEOSContextHandle_t self_context;
386
387
  char val;
387
388
 
389
+ // Shortcut when self and rhs are the same object.
390
+ if (self == rhs) {
391
+ return Qtrue;
392
+ }
393
+
388
394
  result = Qnil;
389
395
  self_data = RGEO_GEOMETRY_DATA_PTR(self);
390
396
  self_geom = self_data->geom;
@@ -863,24 +869,21 @@ static VALUE method_geometry_union(VALUE self, VALUE rhs)
863
869
 
864
870
  static VALUE method_geometry_unary_union(VALUE self)
865
871
  {
866
- VALUE result;
872
+ #ifdef RGEO_GEOS_SUPPORTS_UNARYUNION
867
873
  RGeo_GeometryData* self_data;
868
874
  const GEOSGeometry* self_geom;
869
875
 
870
- result = Qnil;
871
-
872
- #ifdef RGEO_GEOS_SUPPORTS_UNARYUNION
873
876
  self_data = RGEO_GEOMETRY_DATA_PTR(self);
874
877
  self_geom = self_data->geom;
875
878
  if (self_geom) {
876
879
  GEOSContextHandle_t self_context = self_data->geos_context;
877
- result = rgeo_wrap_geos_geometry(self_data->factory,
880
+ return rgeo_wrap_geos_geometry(self_data->factory,
878
881
  GEOSUnaryUnion_r(self_context, self_geom),
879
882
  Qnil);
880
883
  }
881
884
  #endif
882
885
 
883
- return result;
886
+ return Qnil;
884
887
  }
885
888
 
886
889
 
@@ -1044,18 +1047,65 @@ static VALUE method_geometry_invalid_reason(VALUE self)
1044
1047
  self_data = RGEO_GEOMETRY_DATA_PTR(self);
1045
1048
  self_geom = self_data->geom;
1046
1049
  if (self_geom) {
1047
- str = GEOSisValidReason_r(self_data->geos_context, self_geom);
1048
- // Per documentation, a valid geometry should give an empty string.
1049
- // However it seems not to be the case. Hence the comparison against
1050
- // the string that is really given: `"Valid Geometry"`.
1051
- // See https://github.com/libgeos/geos/issues/431.
1052
- if (str) result = (str[0] == '\0' || !strcmp(str, "Valid Geometry")) ? Qnil : rb_str_new2(str);
1053
- else result = rb_str_new2("Exception");
1054
- GEOSFree_r(self_data->geos_context, str);
1050
+ // We use NULL there to tell GEOS that we don't care about the position.
1051
+ switch(GEOSisValidDetail_r(self_data->geos_context, self_geom, 0, &str, NULL)) {
1052
+ case 0: // invalid
1053
+ result = rb_utf8_str_new_cstr(str);
1054
+ case 1: // valid
1055
+ break;
1056
+ case 2: // exception
1057
+ default:
1058
+ result = rb_utf8_str_new_cstr("Exception");
1059
+ break;
1060
+ };
1061
+ if (str) GEOSFree_r(self_data->geos_context, str);
1055
1062
  }
1056
1063
  return result;
1057
1064
  }
1058
1065
 
1066
+ static VALUE method_geometry_invalid_reason_location(VALUE self)
1067
+ {
1068
+ VALUE result;
1069
+ RGeo_GeometryData* self_data;
1070
+ const GEOSGeometry* self_geom;
1071
+ GEOSGeometry* location = NULL;
1072
+
1073
+ result = Qnil;
1074
+ self_data = RGEO_GEOMETRY_DATA_PTR(self);
1075
+ self_geom = self_data->geom;
1076
+ if (self_geom) {
1077
+ // We use NULL there to tell GEOS that we don't care about the reason.
1078
+ switch(GEOSisValidDetail_r(self_data->geos_context, self_geom, 0, NULL, &location)) {
1079
+ case 0: // invalid
1080
+ result = rgeo_wrap_geos_geometry(self_data->factory, location, Qnil);
1081
+ case 1: // valid
1082
+ break;
1083
+ case 2: // exception
1084
+ break;
1085
+ default:
1086
+ break;
1087
+ };
1088
+ }
1089
+ return result;
1090
+ }
1091
+
1092
+ static VALUE method_geometry_make_valid(VALUE self)
1093
+ {
1094
+ RGeo_GeometryData* self_data;
1095
+ const GEOSGeometry* self_geom;
1096
+ GEOSGeometry* valid_geom;
1097
+ self_data = RGEO_GEOMETRY_DATA_PTR(self);
1098
+ self_geom = self_data->geom;
1099
+ if (!self_geom) return Qnil;
1100
+
1101
+ // According to GEOS implementation, MakeValid always returns.
1102
+ valid_geom = GEOSMakeValid_r(self_data->geos_context, self_geom);
1103
+ if (!valid_geom) {
1104
+ rb_raise(rb_eRGeoInvalidGeometry, "%"PRIsVALUE, method_geometry_invalid_reason(self));
1105
+ }
1106
+ return rgeo_wrap_geos_geometry(self_data->factory, valid_geom, Qnil);
1107
+ }
1108
+
1059
1109
  static VALUE method_geometry_point_on_surface(VALUE self)
1060
1110
  {
1061
1111
  VALUE result;
@@ -1071,15 +1121,64 @@ static VALUE method_geometry_point_on_surface(VALUE self)
1071
1121
  return result;
1072
1122
  }
1073
1123
 
1124
+ /**
1125
+ * call-seq:
1126
+ * some.polygonize -> RGeo::Feature::GeometryCollection
1127
+ *
1128
+ * Polygonizes a set of Geometries which contain linework that
1129
+ * represents the edges of a planar graph.
1130
+ *
1131
+ * All types of Geometry are accepted as input;
1132
+ * the constituent linework is extracted as the edges to be polygonized.
1133
+ *
1134
+ * The edges must be correctly noded;
1135
+ * that is, they must only meet at their endpoints and not overlap anywhere.
1136
+ *
1137
+ * @see https://libgeos.org/doxygen/geos__c_8h.html#a9d98e448d3b846d591c726d1c0000d25 GEOSPolygonize
1138
+ */
1139
+ static VALUE method_geometry_polygonize(VALUE self)
1140
+ {
1141
+ VALUE result;
1142
+ RGeo_GeometryData* self_data;
1143
+ const GEOSGeometry* self_geom;
1144
+ GEOSGeometry* geos_polygon_collection;
1145
+
1146
+ result = Qnil;
1147
+ self_data = RGEO_GEOMETRY_DATA_PTR(self);
1148
+ self_geom = self_data->geom;
1149
+ if (self_geom) {
1150
+ geos_polygon_collection = GEOSPolygonize_r(self_data->geos_context, &self_geom, 1);
1151
+
1152
+ if (geos_polygon_collection == NULL) {
1153
+ rb_raise(rb_eGeosError, "GEOS can't polygonize this geometry.");
1154
+ }
1155
+
1156
+ result = rgeo_wrap_geos_geometry(self_data->factory, geos_polygon_collection, Qnil);
1157
+ }
1158
+ return result;
1159
+ }
1160
+
1161
+ VALUE rgeo_geos_geometries_strict_eql(GEOSContextHandle_t context, const GEOSGeometry* geom1, const GEOSGeometry* geom2)
1162
+ {
1163
+ switch (GEOSEqualsExact_r(context, geom1, geom2, 0.0)) {
1164
+ case 0:
1165
+ return Qfalse;
1166
+ case 1:
1167
+ return Qtrue;
1168
+ case 2:
1169
+ default:
1170
+ rb_raise(rb_eGeosError, "Cannot test equality.");
1171
+ }
1172
+ }
1074
1173
 
1075
1174
  /**** INITIALIZATION FUNCTION ****/
1076
1175
 
1077
1176
 
1078
- void rgeo_init_geos_geometry(RGeo_Globals* globals)
1177
+ void rgeo_init_geos_geometry()
1079
1178
  {
1080
1179
  VALUE geos_geometry_methods;
1081
1180
 
1082
- geos_geometry_methods = rb_define_module_under(globals->geos_module, "CAPIGeometryMethods");
1181
+ geos_geometry_methods = rb_define_module_under(rgeo_geos_module, "CAPIGeometryMethods");
1083
1182
 
1084
1183
  rb_define_method(geos_geometry_methods, "factory=", method_geometry_set_factory, 1);
1085
1184
  rb_define_method(geos_geometry_methods, "initialize_copy", method_geometry_initialize_copy, 1);
@@ -1125,7 +1224,10 @@ void rgeo_init_geos_geometry(RGeo_Globals* globals)
1125
1224
  rb_define_method(geos_geometry_methods, "sym_difference", method_geometry_sym_difference, 1);
1126
1225
  rb_define_method(geos_geometry_methods, "valid?", method_geometry_is_valid, 0);
1127
1226
  rb_define_method(geos_geometry_methods, "invalid_reason", method_geometry_invalid_reason, 0);
1227
+ rb_define_method(geos_geometry_methods, "invalid_reason_location", method_geometry_invalid_reason_location, 0);
1128
1228
  rb_define_method(geos_geometry_methods, "point_on_surface", method_geometry_point_on_surface, 0);
1229
+ rb_define_method(geos_geometry_methods, "make_valid", method_geometry_make_valid, 0);
1230
+ rb_define_method(geos_geometry_methods, "polygonize", method_geometry_polygonize, 0);
1129
1231
  }
1130
1232
 
1131
1233
 
@@ -6,8 +6,6 @@
6
6
  #ifndef RGEO_GEOS_GEOMETRY_INCLUDED
7
7
  #define RGEO_GEOS_GEOMETRY_INCLUDED
8
8
 
9
- #include "factory.h"
10
-
11
9
  RGEO_BEGIN_C
12
10
 
13
11
 
@@ -15,8 +13,15 @@ RGEO_BEGIN_C
15
13
  Initializes the geometry module. This should be called after the factory
16
14
  module is initialized, but before any of the other modules.
17
15
  */
18
- void rgeo_init_geos_geometry(RGeo_Globals* globals);
16
+ void rgeo_init_geos_geometry();
17
+
19
18
 
19
+ /*
20
+ Compares two geometries using strict GEOS comparison. return Qtrue
21
+ if they are equal, Qfalse otherwise.
22
+ May raise a `RGeo::Error::GeosError`.
23
+ */
24
+ VALUE rgeo_geos_geometries_strict_eql(GEOSContextHandle_t context, const GEOSGeometry* geom1, const GEOSGeometry* geom2);
20
25
 
21
26
  RGEO_END_C
22
27