rgeo 2.3.1 → 3.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.yardopts +6 -0
- data/README.md +23 -14
- data/ext/geos_c_impl/analysis.c +30 -25
- data/ext/geos_c_impl/analysis.h +8 -7
- data/ext/geos_c_impl/coordinates.c +27 -21
- data/ext/geos_c_impl/coordinates.h +5 -2
- data/ext/geos_c_impl/errors.c +19 -10
- data/ext/geos_c_impl/errors.h +11 -4
- data/ext/geos_c_impl/extconf.rb +42 -28
- data/ext/geos_c_impl/factory.c +540 -451
- data/ext/geos_c_impl/factory.h +105 -95
- data/ext/geos_c_impl/geometry.c +593 -387
- data/ext/geos_c_impl/geometry.h +10 -5
- data/ext/geos_c_impl/geometry_collection.c +306 -339
- data/ext/geos_c_impl/geometry_collection.h +6 -20
- data/ext/geos_c_impl/globals.c +169 -0
- data/ext/geos_c_impl/globals.h +46 -0
- data/ext/geos_c_impl/line_string.c +271 -231
- data/ext/geos_c_impl/line_string.h +5 -8
- data/ext/geos_c_impl/main.c +16 -16
- data/ext/geos_c_impl/point.c +65 -67
- data/ext/geos_c_impl/point.h +4 -7
- data/ext/geos_c_impl/polygon.c +137 -135
- data/ext/geos_c_impl/polygon.h +11 -11
- data/ext/geos_c_impl/preface.h +16 -10
- data/ext/geos_c_impl/ruby_more.c +67 -0
- data/ext/geos_c_impl/ruby_more.h +25 -0
- data/lib/rgeo/cartesian/analysis.rb +5 -3
- data/lib/rgeo/cartesian/bounding_box.rb +74 -79
- data/lib/rgeo/cartesian/calculations.rb +64 -33
- data/lib/rgeo/cartesian/factory.rb +57 -102
- data/lib/rgeo/cartesian/feature_classes.rb +68 -46
- data/lib/rgeo/cartesian/feature_methods.rb +67 -25
- data/lib/rgeo/cartesian/interface.rb +6 -41
- data/lib/rgeo/cartesian/planar_graph.rb +373 -0
- data/lib/rgeo/cartesian/sweepline_intersector.rb +147 -0
- data/lib/rgeo/cartesian/valid_op.rb +69 -0
- data/lib/rgeo/cartesian.rb +3 -0
- data/lib/rgeo/coord_sys/cs/entities.rb +303 -99
- data/lib/rgeo/coord_sys/cs/factories.rb +0 -2
- data/lib/rgeo/coord_sys/cs/wkt_parser.rb +90 -42
- data/lib/rgeo/coord_sys.rb +1 -20
- data/lib/rgeo/error.rb +15 -0
- data/lib/rgeo/feature/curve.rb +0 -11
- data/lib/rgeo/feature/factory.rb +26 -36
- data/lib/rgeo/feature/factory_generator.rb +6 -14
- data/lib/rgeo/feature/geometry.rb +146 -66
- data/lib/rgeo/feature/geometry_collection.rb +16 -9
- data/lib/rgeo/feature/line_string.rb +4 -5
- data/lib/rgeo/feature/linear_ring.rb +0 -1
- data/lib/rgeo/feature/multi_curve.rb +0 -6
- data/lib/rgeo/feature/multi_surface.rb +3 -4
- data/lib/rgeo/feature/point.rb +4 -5
- data/lib/rgeo/feature/polygon.rb +1 -2
- data/lib/rgeo/feature/surface.rb +3 -4
- data/lib/rgeo/feature/types.rb +69 -85
- data/lib/rgeo/geographic/factory.rb +98 -125
- data/lib/rgeo/geographic/interface.rb +69 -166
- data/lib/rgeo/geographic/projected_feature_classes.rb +21 -9
- data/lib/rgeo/geographic/projected_feature_methods.rb +67 -42
- data/lib/rgeo/geographic/projected_window.rb +36 -22
- data/lib/rgeo/geographic/{proj4_projector.rb → projector.rb} +3 -5
- data/lib/rgeo/geographic/simple_mercator_projector.rb +26 -25
- data/lib/rgeo/geographic/spherical_feature_classes.rb +29 -9
- data/lib/rgeo/geographic/spherical_feature_methods.rb +86 -9
- data/lib/rgeo/geographic/spherical_math.rb +17 -20
- data/lib/rgeo/geographic.rb +1 -1
- data/lib/rgeo/geos/capi_factory.rb +87 -158
- data/lib/rgeo/geos/capi_feature_classes.rb +50 -36
- data/lib/rgeo/geos/ffi_factory.rb +105 -173
- data/lib/rgeo/geos/ffi_feature_classes.rb +34 -10
- data/lib/rgeo/geos/ffi_feature_methods.rb +105 -127
- data/lib/rgeo/geos/interface.rb +20 -59
- data/lib/rgeo/geos/utils.rb +5 -5
- data/lib/rgeo/geos/zm_factory.rb +53 -95
- data/lib/rgeo/geos/zm_feature_methods.rb +30 -33
- data/lib/rgeo/geos.rb +8 -8
- data/lib/rgeo/impl_helper/basic_geometry_collection_methods.rb +9 -22
- data/lib/rgeo/impl_helper/basic_geometry_methods.rb +1 -2
- data/lib/rgeo/impl_helper/basic_line_string_methods.rb +28 -56
- data/lib/rgeo/impl_helper/basic_point_methods.rb +2 -14
- data/lib/rgeo/impl_helper/basic_polygon_methods.rb +17 -26
- data/lib/rgeo/impl_helper/utils.rb +21 -0
- data/lib/rgeo/impl_helper/valid_op.rb +350 -0
- data/lib/rgeo/impl_helper/validity_check.rb +139 -0
- data/lib/rgeo/impl_helper.rb +1 -0
- data/lib/rgeo/version.rb +1 -1
- data/lib/rgeo/wkrep/wkb_generator.rb +73 -63
- data/lib/rgeo/wkrep/wkb_parser.rb +33 -31
- data/lib/rgeo/wkrep/wkt_generator.rb +52 -45
- data/lib/rgeo/wkrep/wkt_parser.rb +48 -35
- data/lib/rgeo.rb +1 -3
- metadata +50 -13
- data/lib/rgeo/coord_sys/srs_database/entry.rb +0 -107
- data/lib/rgeo/coord_sys/srs_database/sr_org.rb +0 -64
- data/lib/rgeo/coord_sys/srs_database/url_reader.rb +0 -65
@@ -19,8 +19,40 @@ module RGeo
|
|
19
19
|
# adding the geometries to it. You may then query it for the bounds,
|
20
20
|
# or use it to determine whether it encloses other geometries or
|
21
21
|
# bounding boxes.
|
22
|
-
|
23
22
|
class BoundingBox
|
23
|
+
# Returns the bounding box's factory.
|
24
|
+
attr_reader :factory
|
25
|
+
|
26
|
+
# Returns true if this bounding box tracks Z coordinates.
|
27
|
+
attr_reader :has_z
|
28
|
+
|
29
|
+
# Returns true if this bounding box tracks M coordinates.
|
30
|
+
attr_reader :has_m
|
31
|
+
|
32
|
+
# Returns the minimum X, or nil if this bounding box is empty.
|
33
|
+
attr_reader :min_x
|
34
|
+
|
35
|
+
# Returns the maximum X, or nil if this bounding box is empty.
|
36
|
+
attr_reader :max_x
|
37
|
+
|
38
|
+
# Returns the minimum Y, or nil if this bounding box is empty.
|
39
|
+
attr_reader :min_y
|
40
|
+
|
41
|
+
# Returns the maximum Y, or nil if this bounding box is empty.
|
42
|
+
attr_reader :max_y
|
43
|
+
|
44
|
+
# Returns the minimum Z, or nil if this bounding box is empty.
|
45
|
+
attr_reader :min_z
|
46
|
+
|
47
|
+
# Returns the maximum Z, or nil if this bounding box is empty.
|
48
|
+
attr_reader :max_z
|
49
|
+
|
50
|
+
# Returns the minimum M, or nil if this bounding box is empty.
|
51
|
+
attr_reader :min_m
|
52
|
+
|
53
|
+
# Returns the maximum M, or nil if this bounding box is empty.
|
54
|
+
attr_reader :max_m
|
55
|
+
|
24
56
|
# Create a bounding box given two corner points.
|
25
57
|
# The bounding box will be given the factory of the first point.
|
26
58
|
# You may also provide the same options available to
|
@@ -69,19 +101,15 @@ module RGeo
|
|
69
101
|
end
|
70
102
|
end
|
71
103
|
|
72
|
-
def eql?(
|
73
|
-
|
74
|
-
@min_x ==
|
75
|
-
@min_y ==
|
76
|
-
@min_z ==
|
77
|
-
@min_m ==
|
104
|
+
def eql?(other) # :nodoc:
|
105
|
+
other.is_a?(BoundingBox) && @factory == other.factory &&
|
106
|
+
@min_x == other.min_x && @max_x == other.max_x &&
|
107
|
+
@min_y == other.min_y && @max_y == other.max_y &&
|
108
|
+
@min_z == other.min_z && @max_z == other.max_z &&
|
109
|
+
@min_m == other.min_m && @max_m == other.max_m
|
78
110
|
end
|
79
111
|
alias == eql?
|
80
112
|
|
81
|
-
# Returns the bounding box's factory.
|
82
|
-
|
83
|
-
attr_reader :factory
|
84
|
-
|
85
113
|
# Returns true if this bounding box is still empty.
|
86
114
|
|
87
115
|
def empty?
|
@@ -105,22 +133,6 @@ module RGeo
|
|
105
133
|
@min_x && (@min_x == @max_x || @min_y == @max_y)
|
106
134
|
end
|
107
135
|
|
108
|
-
# Returns true if this bounding box tracks Z coordinates.
|
109
|
-
|
110
|
-
attr_reader :has_z
|
111
|
-
|
112
|
-
# Returns true if this bounding box tracks M coordinates.
|
113
|
-
|
114
|
-
attr_reader :has_m
|
115
|
-
|
116
|
-
# Returns the minimum X, or nil if this bounding box is empty.
|
117
|
-
|
118
|
-
attr_reader :min_x
|
119
|
-
|
120
|
-
# Returns the maximum X, or nil if this bounding box is empty.
|
121
|
-
|
122
|
-
attr_reader :max_x
|
123
|
-
|
124
136
|
# Returns the midpoint X, or nil if this bounding box is empty.
|
125
137
|
|
126
138
|
def center_x
|
@@ -133,14 +145,6 @@ module RGeo
|
|
133
145
|
@max_x ? @max_x - @min_x : 0
|
134
146
|
end
|
135
147
|
|
136
|
-
# Returns the minimum Y, or nil if this bounding box is empty.
|
137
|
-
|
138
|
-
attr_reader :min_y
|
139
|
-
|
140
|
-
# Returns the maximum Y, or nil if this bounding box is empty.
|
141
|
-
|
142
|
-
attr_reader :max_y
|
143
|
-
|
144
148
|
# Returns the midpoint Y, or nil if this bounding box is empty.
|
145
149
|
|
146
150
|
def center_y
|
@@ -153,14 +157,6 @@ module RGeo
|
|
153
157
|
@max_y ? @max_y - @min_y : 0
|
154
158
|
end
|
155
159
|
|
156
|
-
# Returns the minimum Z, or nil if this bounding box is empty.
|
157
|
-
|
158
|
-
attr_reader :min_z
|
159
|
-
|
160
|
-
# Returns the maximum Z, or nil if this bounding box is empty.
|
161
|
-
|
162
|
-
attr_reader :max_z
|
163
|
-
|
164
160
|
# Returns the midpoint Z, or nil if this bounding box is empty or has no Z.
|
165
161
|
|
166
162
|
def center_z
|
@@ -170,16 +166,12 @@ module RGeo
|
|
170
166
|
# Returns the Z span, 0 if this bounding box is empty, or nil if it has no Z.
|
171
167
|
|
172
168
|
def z_span
|
173
|
-
|
174
|
-
end
|
169
|
+
return unless @has_z
|
175
170
|
|
176
|
-
|
177
|
-
|
178
|
-
attr_reader :min_m
|
171
|
+
return 0 unless @max_z
|
179
172
|
|
180
|
-
|
181
|
-
|
182
|
-
attr_reader :max_m
|
173
|
+
@max_z - @min_z
|
174
|
+
end
|
183
175
|
|
184
176
|
# Returns the midpoint M, or nil if this bounding box is empty or has no M.
|
185
177
|
|
@@ -190,31 +182,37 @@ module RGeo
|
|
190
182
|
# Returns the M span, 0 if this bounding box is empty, or nil if it has no M.
|
191
183
|
|
192
184
|
def m_span
|
193
|
-
|
185
|
+
return unless @has_m
|
186
|
+
|
187
|
+
return 0 unless @max_m
|
188
|
+
|
189
|
+
@max_m - @min_m
|
194
190
|
end
|
195
191
|
|
196
192
|
# Returns a point representing the minimum extent in all dimensions,
|
197
193
|
# or nil if this bounding box is empty.
|
198
194
|
|
199
195
|
def min_point
|
200
|
-
|
201
|
-
|
202
|
-
|
203
|
-
|
204
|
-
|
205
|
-
|
196
|
+
return unless @min_x
|
197
|
+
|
198
|
+
extras = []
|
199
|
+
extras << @min_z if @has_z
|
200
|
+
extras << @min_m if @has_m
|
201
|
+
|
202
|
+
@factory.point(@min_x, @min_y, *extras)
|
206
203
|
end
|
207
204
|
|
208
205
|
# Returns a point representing the maximum extent in all dimensions,
|
209
206
|
# or nil if this bounding box is empty.
|
210
207
|
|
211
208
|
def max_point
|
212
|
-
|
213
|
-
|
214
|
-
|
215
|
-
|
216
|
-
|
217
|
-
|
209
|
+
return unless @min_x
|
210
|
+
|
211
|
+
extras = []
|
212
|
+
extras << @max_z if @has_z
|
213
|
+
extras << @max_m if @has_m
|
214
|
+
|
215
|
+
@factory.point(@max_x, @max_y, *extras)
|
218
216
|
end
|
219
217
|
|
220
218
|
# Adjusts the extents of this bounding box to encompass the given
|
@@ -280,21 +278,18 @@ module RGeo
|
|
280
278
|
# have M. Default is false.
|
281
279
|
|
282
280
|
def contains?(rhs, opts = {})
|
283
|
-
if Feature::Geometry === rhs
|
284
|
-
|
285
|
-
|
286
|
-
|
287
|
-
|
288
|
-
|
289
|
-
|
290
|
-
|
291
|
-
|
292
|
-
|
293
|
-
|
294
|
-
|
295
|
-
else
|
296
|
-
true
|
297
|
-
end
|
281
|
+
return contains?(BoundingBox.new(@factory).add(rhs)) if Feature::Geometry === rhs
|
282
|
+
|
283
|
+
return true if rhs.empty?
|
284
|
+
|
285
|
+
return false if empty?
|
286
|
+
|
287
|
+
cmp_xymz =
|
288
|
+
(@min_x > rhs.min_x || @max_x < rhs.max_x || @min_y > rhs.min_y || @max_y < rhs.max_y) ||
|
289
|
+
(@has_m && rhs.has_m && !opts[:ignore_m] && (@min_m > rhs.min_m || @max_m < rhs.max_m)) ||
|
290
|
+
(@has_z && rhs.has_z && !opts[:ignore_z] && (@min_z > rhs.min_z || @max_z < rhs.max_z))
|
291
|
+
|
292
|
+
!cmp_xymz
|
298
293
|
end
|
299
294
|
|
300
295
|
# Returns this bounding box subdivided, as an array of bounding boxes.
|
@@ -23,17 +23,14 @@ module RGeo
|
|
23
23
|
@lensq = @dx * @dx + @dy * @dy
|
24
24
|
end
|
25
25
|
|
26
|
-
attr_reader :s
|
27
|
-
attr_reader :e
|
28
|
-
attr_reader :dx
|
29
|
-
attr_reader :dy
|
26
|
+
attr_reader :s, :e, :dx, :dy
|
30
27
|
|
31
28
|
def to_s
|
32
29
|
"#{@s} - #{@e}"
|
33
30
|
end
|
34
31
|
|
35
|
-
def eql?(
|
36
|
-
|
32
|
+
def eql?(other)
|
33
|
+
other.is_a?(Segment) && @s == other.s && @e == other.e
|
37
34
|
end
|
38
35
|
alias == eql?
|
39
36
|
|
@@ -45,23 +42,23 @@ module RGeo
|
|
45
42
|
# a positive value if the point is to the right, or
|
46
43
|
# 0 if the point is collinear to the segment.
|
47
44
|
|
48
|
-
def side(
|
49
|
-
px =
|
50
|
-
py =
|
45
|
+
def side(point)
|
46
|
+
px = point.x
|
47
|
+
py = point.y
|
51
48
|
(@sx - px) * (@ey - py) - (@sy - py) * (@ex - px)
|
52
49
|
end
|
53
50
|
|
54
|
-
def tproj(
|
51
|
+
def tproj(point)
|
55
52
|
if @lensq == 0
|
56
53
|
nil
|
57
54
|
else
|
58
|
-
(@dx * (
|
55
|
+
(@dx * (point.x - @sx) + @dy * (point.y - @sy)) / @lensq
|
59
56
|
end
|
60
57
|
end
|
61
58
|
|
62
|
-
def contains_point?(
|
63
|
-
if side(
|
64
|
-
t = tproj(
|
59
|
+
def contains_point?(point)
|
60
|
+
if side(point) == 0
|
61
|
+
t = tproj(point)
|
65
62
|
t && t >= 0.0 && t <= 1.0
|
66
63
|
else
|
67
64
|
false
|
@@ -69,41 +66,75 @@ module RGeo
|
|
69
66
|
end
|
70
67
|
|
71
68
|
def intersects_segment?(seg)
|
69
|
+
!segment_intersection(seg).nil?
|
70
|
+
end
|
71
|
+
|
72
|
+
# If this and the other segment intersect, this method will return the coordinate
|
73
|
+
# at which they intersect, otherwise nil.
|
74
|
+
# In the case of a partial overlap (parallel segments), this will return
|
75
|
+
# a single point on the overlapping portion.
|
76
|
+
#
|
77
|
+
# @param seg [Segment]
|
78
|
+
#
|
79
|
+
# @return [RGeo::Feature::Point, nil]
|
80
|
+
def segment_intersection(seg)
|
72
81
|
s2 = seg.s
|
73
82
|
# Handle degenerate cases
|
74
83
|
if seg.degenerate?
|
75
|
-
if @lensq == 0
|
76
|
-
|
77
|
-
|
78
|
-
return contains_point?(s2)
|
79
|
-
end
|
84
|
+
return @s if @lensq == 0 && @s == s2
|
85
|
+
|
86
|
+
return contains_point?(s2) ? s2 : nil
|
80
87
|
elsif @lensq == 0
|
81
|
-
return seg.contains_point?(@s)
|
88
|
+
return seg.contains_point?(@s) ? @s : nil
|
82
89
|
end
|
90
|
+
|
83
91
|
# Both segments have nonzero length.
|
84
92
|
sx2 = s2.x
|
85
93
|
sy2 = s2.y
|
86
94
|
dx2 = seg.dx
|
87
95
|
dy2 = seg.dy
|
88
96
|
denom = @dx * dy2 - @dy * dx2
|
97
|
+
|
89
98
|
if denom == 0
|
90
99
|
# Segments are parallel. Make sure they are collinear.
|
91
|
-
return
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
+
return nil unless side(s2) == 0
|
101
|
+
|
102
|
+
# return the first point it finds that intersects another line.
|
103
|
+
# In many cases, the intersection is actually another line
|
104
|
+
# segment, but for now, we will just return a single point.
|
105
|
+
return s2 if contains_point?(s2)
|
106
|
+
return seg.e if contains_point?(seg.e)
|
107
|
+
return @s if seg.contains_point?(@s)
|
108
|
+
return @e if seg.contains_point?(@e)
|
109
|
+
nil
|
100
110
|
else
|
101
111
|
# Segments are not parallel. Check the intersection of their
|
102
112
|
# containing lines.
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
113
|
+
num1 = dx2 * (@sy - sy2) - (dy2 * (@sx - sx2))
|
114
|
+
num2 = @dx * (@sy - sy2) - (@dy * (@sx - sx2))
|
115
|
+
cross1 = num1 / denom
|
116
|
+
cross2 = num2 / denom
|
117
|
+
|
118
|
+
return nil if cross1 < 0.0 || cross1 > 1.0
|
119
|
+
if cross2 >= 0.0 && cross2 <= 1.0
|
120
|
+
x = @sx + (cross1 * @dx)
|
121
|
+
y = @sy + (cross1 * @dy)
|
122
|
+
|
123
|
+
# Check if this segment contains the point.
|
124
|
+
# Sometimes round-off errors occur and intersections
|
125
|
+
# are recorded as off the line segments.
|
126
|
+
#
|
127
|
+
# If this is the case, return the closest point from
|
128
|
+
# either segment.
|
129
|
+
int_pt = @s.factory.point(x, y)
|
130
|
+
|
131
|
+
return int_pt if contains_point?(int_pt)
|
132
|
+
|
133
|
+
# find closest of @s, @e, seg.s, seg.e
|
134
|
+
[@e, seg.s, seg.e].reduce(@s) do |closest, pt|
|
135
|
+
int_pt.distance(pt) < int_pt.distance(closest) ? pt : closest
|
136
|
+
end
|
137
|
+
end
|
107
138
|
end
|
108
139
|
end
|
109
140
|
|
@@ -10,11 +10,18 @@ module RGeo
|
|
10
10
|
module Cartesian
|
11
11
|
# This class implements the factory for the simple cartesian
|
12
12
|
# implementation.
|
13
|
-
|
14
13
|
class Factory
|
15
14
|
include Feature::Factory::Instance
|
16
15
|
include ImplHelper::Utils
|
17
16
|
|
17
|
+
attr_reader :coordinate_dimension, :spatial_dimension
|
18
|
+
|
19
|
+
# Returns the SRID.
|
20
|
+
attr_reader :srid
|
21
|
+
|
22
|
+
# See RGeo::Feature::Factory#coord_sys
|
23
|
+
attr_reader :coord_sys
|
24
|
+
|
18
25
|
# Create a new simple cartesian factory.
|
19
26
|
#
|
20
27
|
# See RGeo::Cartesian.simple_factory for a list of supported options.
|
@@ -22,74 +29,66 @@ module RGeo
|
|
22
29
|
def initialize(opts = {})
|
23
30
|
@has_z = opts[:has_z_coordinate] ? true : false
|
24
31
|
@has_m = opts[:has_m_coordinate] ? true : false
|
25
|
-
@
|
26
|
-
if @
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
@
|
33
|
-
|
34
|
-
@coord_sys = CoordSys::CS.create_from_wkt(@coord_sys)
|
35
|
-
end
|
36
|
-
if (!@proj4 || !@coord_sys) && srid && (db = opts[:srs_database])
|
37
|
-
entry = db.get(srid.to_i)
|
38
|
-
if entry
|
39
|
-
@proj4 ||= entry.proj4
|
40
|
-
@coord_sys ||= entry.coord_sys
|
41
|
-
end
|
42
|
-
end
|
43
|
-
srid ||= @coord_sys.authority_code if @coord_sys
|
44
|
-
@srid = srid.to_i
|
45
|
-
@lenient_assertions = opts[:uses_lenient_assertions] ? true : false
|
32
|
+
@coordinate_dimension = 2
|
33
|
+
@coordinate_dimension += 1 if @has_z
|
34
|
+
@coordinate_dimension += 1 if @has_m
|
35
|
+
@spatial_dimension = @has_z ? 3 : 2
|
36
|
+
|
37
|
+
coord_sys_info = ImplHelper::Utils.setup_coord_sys(opts[:srid], opts[:coord_sys], opts[:coord_sys_class])
|
38
|
+
@coord_sys = coord_sys_info[:coord_sys]
|
39
|
+
@srid = coord_sys_info[:srid]
|
40
|
+
|
46
41
|
@buffer_resolution = opts[:buffer_resolution].to_i
|
47
42
|
@buffer_resolution = 1 if @buffer_resolution < 1
|
48
43
|
|
49
44
|
wkt_generator = opts[:wkt_generator]
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
45
|
+
@wkt_generator =
|
46
|
+
case wkt_generator
|
47
|
+
when Hash
|
48
|
+
WKRep::WKTGenerator.new(wkt_generator)
|
49
|
+
else
|
50
|
+
WKRep::WKTGenerator.new(convert_case: :upper)
|
51
|
+
end
|
56
52
|
wkb_generator = opts[:wkb_generator]
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
53
|
+
@wkb_generator =
|
54
|
+
case wkb_generator
|
55
|
+
when Hash
|
56
|
+
WKRep::WKBGenerator.new(wkb_generator)
|
57
|
+
else
|
58
|
+
WKRep::WKBGenerator.new
|
59
|
+
end
|
63
60
|
wkt_parser = opts[:wkt_parser]
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
61
|
+
@wkt_parser =
|
62
|
+
case wkt_parser
|
63
|
+
when Hash
|
64
|
+
WKRep::WKTParser.new(self, wkt_parser)
|
65
|
+
else
|
66
|
+
WKRep::WKTParser.new(self)
|
67
|
+
end
|
70
68
|
wkb_parser = opts[:wkb_parser]
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
69
|
+
@wkb_parser =
|
70
|
+
case wkb_parser
|
71
|
+
when Hash
|
72
|
+
WKRep::WKBParser.new(self, wkb_parser)
|
73
|
+
else
|
74
|
+
WKRep::WKBParser.new(self)
|
75
|
+
end
|
77
76
|
end
|
78
77
|
|
79
78
|
# Equivalence test.
|
80
79
|
|
81
|
-
def eql?(
|
82
|
-
|
83
|
-
@has_z ==
|
84
|
-
@has_m ==
|
85
|
-
@
|
80
|
+
def eql?(other)
|
81
|
+
other.is_a?(self.class) && @srid == other.srid &&
|
82
|
+
@has_z == other.property(:has_z_coordinate) &&
|
83
|
+
@has_m == other.property(:has_m_coordinate) &&
|
84
|
+
@coord_sys == other.instance_variable_get(:@coord_sys)
|
86
85
|
end
|
87
86
|
alias == eql?
|
88
87
|
|
89
88
|
# Standard hash code
|
90
89
|
|
91
90
|
def hash
|
92
|
-
@hash ||= [@srid, @has_z, @has_m, @
|
91
|
+
@hash ||= [@srid, @has_z, @has_m, @coord_sys].hash
|
93
92
|
end
|
94
93
|
|
95
94
|
# Marshal support
|
@@ -103,26 +102,16 @@ module RGeo
|
|
103
102
|
"wkbg" => @wkb_generator.properties,
|
104
103
|
"wktp" => @wkt_parser.properties,
|
105
104
|
"wkbp" => @wkb_parser.properties,
|
106
|
-
"lena" => @lenient_assertions,
|
107
105
|
"bufr" => @buffer_resolution
|
108
106
|
}
|
109
|
-
hash_["proj4"] = @proj4.marshal_dump if @proj4
|
110
107
|
hash_["cs"] = @coord_sys.to_wkt if @coord_sys
|
111
108
|
hash_
|
112
109
|
end
|
113
110
|
|
114
111
|
def marshal_load(data) # :nodoc:
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
else
|
119
|
-
proj4 = nil
|
120
|
-
end
|
121
|
-
if (coord_sys_data = data["cs"])
|
122
|
-
coord_sys = CoordSys::CS.create_from_wkt(coord_sys_data)
|
123
|
-
else
|
124
|
-
coord_sys = nil
|
125
|
-
end
|
112
|
+
cs_class = CoordSys::CONFIG.default_coord_sys_class
|
113
|
+
coord_sys = data["cs"]&.then { |cs| cs_class.create_from_wkt(cs) }
|
114
|
+
|
126
115
|
initialize(
|
127
116
|
has_z_coordinate: data["hasz"],
|
128
117
|
has_m_coordinate: data["hasm"],
|
@@ -131,9 +120,7 @@ module RGeo
|
|
131
120
|
wkb_generator: symbolize_hash(data["wkbg"]),
|
132
121
|
wkt_parser: symbolize_hash(data["wktp"]),
|
133
122
|
wkb_parser: symbolize_hash(data["wkbp"]),
|
134
|
-
uses_lenient_assertions: data["lena"],
|
135
123
|
buffer_resolution: data["bufr"],
|
136
|
-
proj4: proj4,
|
137
124
|
coord_sys: coord_sys
|
138
125
|
)
|
139
126
|
end
|
@@ -144,34 +131,18 @@ module RGeo
|
|
144
131
|
coder["has_z_coordinate"] = @has_z
|
145
132
|
coder["has_m_coordinate"] = @has_m
|
146
133
|
coder["srid"] = @srid
|
147
|
-
coder["lenient_assertions"] = @lenient_assertions
|
148
134
|
coder["buffer_resolution"] = @buffer_resolution
|
149
135
|
coder["wkt_generator"] = @wkt_generator.properties
|
150
136
|
coder["wkb_generator"] = @wkb_generator.properties
|
151
137
|
coder["wkt_parser"] = @wkt_parser.properties
|
152
138
|
coder["wkb_parser"] = @wkb_parser.properties
|
153
|
-
if @proj4
|
154
|
-
str = @proj4.original_str || @proj4.canonical_str
|
155
|
-
coder["proj4"] = @proj4.radians? ? { "proj4" => str, "radians" => true } : str
|
156
|
-
end
|
157
139
|
coder["coord_sys"] = @coord_sys.to_wkt if @coord_sys
|
158
140
|
end
|
159
141
|
|
160
142
|
def init_with(coder) # :nodoc:
|
161
|
-
|
162
|
-
|
163
|
-
|
164
|
-
else
|
165
|
-
proj4 = CoordSys::Proj4.create(proj4_data.to_s)
|
166
|
-
end
|
167
|
-
else
|
168
|
-
proj4 = nil
|
169
|
-
end
|
170
|
-
if (coord_sys_data = coder["cs"])
|
171
|
-
coord_sys = CoordSys::CS.create_from_wkt(coord_sys_data.to_s)
|
172
|
-
else
|
173
|
-
coord_sys = nil
|
174
|
-
end
|
143
|
+
cs_class = CoordSys::CONFIG.default_coord_sys_class
|
144
|
+
coord_sys = coder["cs"]&.then { |cs| cs_class.create_from_wkt(cs) }
|
145
|
+
|
175
146
|
initialize(
|
176
147
|
has_z_coordinate: coder["has_z_coordinate"],
|
177
148
|
has_m_coordinate: coder["has_m_coordinate"],
|
@@ -180,17 +151,11 @@ module RGeo
|
|
180
151
|
wkb_generator: symbolize_hash(coder["wkb_generator"]),
|
181
152
|
wkt_parser: symbolize_hash(coder["wkt_parser"]),
|
182
153
|
wkb_parser: symbolize_hash(coder["wkb_parser"]),
|
183
|
-
uses_lenient_assertions: coder["lenient_assertions"],
|
184
154
|
buffer_resolution: coder["buffer_resolution"],
|
185
|
-
proj4: proj4,
|
186
155
|
coord_sys: coord_sys
|
187
156
|
)
|
188
157
|
end
|
189
158
|
|
190
|
-
# Returns the SRID.
|
191
|
-
|
192
|
-
attr_reader :srid
|
193
|
-
|
194
159
|
# See RGeo::Feature::Factory#property
|
195
160
|
|
196
161
|
def property(name)
|
@@ -199,8 +164,6 @@ module RGeo
|
|
199
164
|
@has_z
|
200
165
|
when :has_m_coordinate
|
201
166
|
@has_m
|
202
|
-
when :uses_lenient_assertions
|
203
|
-
@lenient_assertions
|
204
167
|
when :buffer_resolution
|
205
168
|
@buffer_resolution
|
206
169
|
when :is_cartesian
|
@@ -274,14 +237,6 @@ module RGeo
|
|
274
237
|
MultiPolygonImpl.new(self, elems)
|
275
238
|
end
|
276
239
|
|
277
|
-
# See RGeo::Feature::Factory#proj4
|
278
|
-
|
279
|
-
attr_reader :proj4
|
280
|
-
|
281
|
-
# See RGeo::Feature::Factory#coord_sys
|
282
|
-
|
283
|
-
attr_reader :coord_sys
|
284
|
-
|
285
240
|
def generate_wkt(obj)
|
286
241
|
@wkt_generator.generate(obj)
|
287
242
|
end
|