]> git.proxmox.com Git - ceph.git/blame - ceph/src/boost/boost/geometry/strategies/relate/cartesian.hpp
update ceph source to reef 18.1.2
[ceph.git] / ceph / src / boost / boost / geometry / strategies / relate / cartesian.hpp
CommitLineData
1e59de90
TL
1// Boost.Geometry
2
3// Copyright (c) 2020, Oracle and/or its affiliates.
4
5// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
6
7// Licensed under the Boost Software License version 1.0.
8// http://www.boost.org/users/license.html
9
10#ifndef BOOST_GEOMETRY_STRATEGIES_RELATE_CARTESIAN_HPP
11#define BOOST_GEOMETRY_STRATEGIES_RELATE_CARTESIAN_HPP
12
13
14// TEMP - move to strategy
15#include <boost/geometry/strategies/agnostic/point_in_box_by_side.hpp>
16#include <boost/geometry/strategies/cartesian/intersection.hpp>
17#include <boost/geometry/strategies/cartesian/box_in_box.hpp>
18#include <boost/geometry/strategies/cartesian/point_in_point.hpp>
19#include <boost/geometry/strategies/cartesian/point_in_poly_crossings_multiply.hpp>
20#include <boost/geometry/strategies/cartesian/point_in_poly_franklin.hpp>
21#include <boost/geometry/strategies/cartesian/point_in_poly_winding.hpp>
22#include <boost/geometry/strategies/cartesian/disjoint_box_box.hpp>
23
24#include <boost/geometry/strategies/envelope/cartesian.hpp>
25#include <boost/geometry/strategies/relate/services.hpp>
26#include <boost/geometry/strategies/detail.hpp>
27
28#include <boost/geometry/strategy/cartesian/area.hpp>
29#include <boost/geometry/strategy/cartesian/side_robust.hpp>
30#include <boost/geometry/strategy/cartesian/side_by_triangle.hpp>
31#include <boost/geometry/strategy/cartesian/area_box.hpp>
32
33#include <boost/geometry/util/type_traits.hpp>
34
35
36namespace boost { namespace geometry
37{
38
39namespace strategies { namespace relate
40{
41
42template <typename CalculationType = void>
43class cartesian
44 : public strategies::envelope::cartesian<CalculationType>
45{
46public:
47 //area
48
49 template <typename Geometry>
50 static auto area(Geometry const&,
51 std::enable_if_t<! util::is_box<Geometry>::value> * = nullptr)
52 {
53 return strategy::area::cartesian<CalculationType>();
54 }
55
56 template <typename Geometry>
57 static auto area(Geometry const&,
58 std::enable_if_t<util::is_box<Geometry>::value> * = nullptr)
59 {
60 return strategy::area::cartesian_box<CalculationType>();
61 }
62
63 // covered_by
64
65 template <typename Geometry1, typename Geometry2>
66 static auto covered_by(Geometry1 const&, Geometry2 const&,
67 std::enable_if_t
68 <
69 util::is_pointlike<Geometry1>::value
70 && util::is_box<Geometry2>::value
71 > * = nullptr)
72 {
73 return strategy::covered_by::cartesian_point_box();
74 }
75
76 template <typename Geometry1, typename Geometry2>
77 static auto covered_by(Geometry1 const&, Geometry2 const&,
78 std::enable_if_t
79 <
80 util::is_box<Geometry1>::value
81 && util::is_box<Geometry2>::value
82 > * = nullptr)
83 {
84 return strategy::covered_by::cartesian_box_box();
85 }
86
87 // disjoint
88
89 template <typename Geometry1, typename Geometry2>
90 static auto disjoint(Geometry1 const&, Geometry2 const&,
91 std::enable_if_t
92 <
93 util::is_box<Geometry1>::value
94 && util::is_box<Geometry2>::value
95 > * = nullptr)
96 {
97 return strategy::disjoint::cartesian_box_box();
98 }
99
100 template <typename Geometry1, typename Geometry2>
101 static auto disjoint(Geometry1 const&, Geometry2 const&,
102 std::enable_if_t
103 <
104 util::is_segment<Geometry1>::value
105 && util::is_box<Geometry2>::value
106 > * = nullptr)
107 {
108 // NOTE: Inconsistent name.
109 return strategy::disjoint::segment_box();
110 }
111
112 // relate
113
114 template <typename Geometry1, typename Geometry2>
115 static auto relate(Geometry1 const&, Geometry2 const&,
116 std::enable_if_t
117 <
118 util::is_pointlike<Geometry1>::value
119 && util::is_pointlike<Geometry2>::value
120 > * = nullptr)
121 {
122 return strategy::within::cartesian_point_point();
123 }
124
125 template <typename Geometry1, typename Geometry2>
126 static auto relate(Geometry1 const&, Geometry2 const&,
127 std::enable_if_t
128 <
129 util::is_pointlike<Geometry1>::value
130 && ( util::is_linear<Geometry2>::value
131 || util::is_polygonal<Geometry2>::value )
132 > * = nullptr)
133 {
134 return strategy::within::cartesian_winding<void, void, CalculationType>();
135 }
136
137 // The problem is that this strategy is often used with non-geometry ranges.
138 // So dispatching only by geometry categories is impossible.
139 // In the past it was taking two segments, now it takes 3-point sub-ranges.
140 // So dispatching by segments is impossible.
141 // It could be dispatched by (linear || polygonal || non-geometry point range).
142 // For now implement as 0-parameter, special case relate.
143
144 //template <typename Geometry1, typename Geometry2>
145 static auto relate(/*Geometry1 const&, Geometry2 const&,
146 std::enable_if_t
147 <
148 ( util::is_linear<Geometry1>::value
149 || util::is_polygonal<Geometry1>::value )
150 && ( util::is_linear<Geometry2>::value
151 || util::is_polygonal<Geometry2>::value )
152 > * = nullptr*/)
153 {
154 return strategy::intersection::cartesian_segments<CalculationType>();
155 }
156
157 // side
158
159 static auto side()
160 {
161 using side_strategy_type
162 = typename strategy::side::services::default_strategy
163 <cartesian_tag, CalculationType>::type;
164 return side_strategy_type();
165 }
166
167 // within
168
169 template <typename Geometry1, typename Geometry2>
170 static auto within(Geometry1 const&, Geometry2 const&,
171 std::enable_if_t
172 <
173 util::is_pointlike<Geometry1>::value
174 && util::is_box<Geometry2>::value
175 > * = nullptr)
176 {
177 return strategy::within::cartesian_point_box();
178 }
179
180 template <typename Geometry1, typename Geometry2>
181 static auto within(Geometry1 const&, Geometry2 const&,
182 std::enable_if_t
183 <
184 util::is_box<Geometry1>::value
185 && util::is_box<Geometry2>::value
186 > * = nullptr)
187 {
188 return strategy::within::cartesian_box_box();
189 }
190};
191
192
193namespace services
194{
195
196template <typename Geometry1, typename Geometry2>
197struct default_strategy<Geometry1, Geometry2, cartesian_tag, cartesian_tag>
198{
199 using type = strategies::relate::cartesian<>;
200};
201
202
203template <>
204struct strategy_converter<strategy::within::cartesian_point_point>
205{
206 static auto get(strategy::within::cartesian_point_point const& )
207 {
208 return strategies::relate::cartesian<>();
209 }
210};
211
212template <>
213struct strategy_converter<strategy::within::cartesian_point_box>
214{
215 static auto get(strategy::within::cartesian_point_box const&)
216 {
217 return strategies::relate::cartesian<>();
218 }
219};
220
221template <>
222struct strategy_converter<strategy::covered_by::cartesian_point_box>
223{
224 static auto get(strategy::covered_by::cartesian_point_box const&)
225 {
226 return strategies::relate::cartesian<>();
227 }
228};
229
230template <>
231struct strategy_converter<strategy::covered_by::cartesian_box_box>
232{
233 static auto get(strategy::covered_by::cartesian_box_box const&)
234 {
235 return strategies::relate::cartesian<>();
236 }
237};
238
239template <>
240struct strategy_converter<strategy::disjoint::cartesian_box_box>
241{
242 static auto get(strategy::disjoint::cartesian_box_box const&)
243 {
244 return strategies::relate::cartesian<>();
245 }
246};
247
248template <>
249struct strategy_converter<strategy::disjoint::segment_box>
250{
251 static auto get(strategy::disjoint::segment_box const&)
252 {
253 return strategies::relate::cartesian<>();
254 }
255};
256
257template <>
258struct strategy_converter<strategy::within::cartesian_box_box>
259{
260 static auto get(strategy::within::cartesian_box_box const&)
261 {
262 return strategies::relate::cartesian<>();
263 }
264};
265
266template <typename P1, typename P2, typename CalculationType>
267struct strategy_converter<strategy::within::cartesian_winding<P1, P2, CalculationType>>
268{
269 static auto get(strategy::within::cartesian_winding<P1, P2, CalculationType> const& )
270 {
271 return strategies::relate::cartesian<CalculationType>();
272 }
273};
274
275template <typename CalculationType>
276struct strategy_converter<strategy::intersection::cartesian_segments<CalculationType>>
277{
278 static auto get(strategy::intersection::cartesian_segments<CalculationType> const& )
279 {
280 return strategies::relate::cartesian<CalculationType>();
281 }
282};
283
284template <typename CalculationType>
285struct strategy_converter<strategy::within::cartesian_point_box_by_side<CalculationType>>
286{
287 struct altered_strategy
288 : strategies::relate::cartesian<CalculationType>
289 {
290 template <typename Geometry1, typename Geometry2>
291 static auto covered_by(Geometry1 const&, Geometry2 const&,
292 std::enable_if_t
293 <
294 util::is_pointlike<Geometry1>::value
295 && util::is_box<Geometry2>::value
296 > * = nullptr)
297 {
298 return strategy::covered_by::cartesian_point_box_by_side<CalculationType>();
299 }
300
301 template <typename Geometry1, typename Geometry2>
302 static auto within(Geometry1 const&, Geometry2 const&,
303 std::enable_if_t
304 <
305 util::is_pointlike<Geometry1>::value
306 && util::is_box<Geometry2>::value
307 > * = nullptr)
308 {
309 return strategy::within::cartesian_point_box_by_side<CalculationType>();
310 }
311 };
312
313 static auto get(strategy::covered_by::cartesian_point_box_by_side<CalculationType> const&)
314 {
315 return altered_strategy();
316 }
317
318 static auto get(strategy::within::cartesian_point_box_by_side<CalculationType> const&)
319 {
320 return altered_strategy();
321 }
322};
323
324template <typename CalculationType>
325struct strategy_converter<strategy::covered_by::cartesian_point_box_by_side<CalculationType>>
326 : strategy_converter<strategy::within::cartesian_point_box_by_side<CalculationType>>
327{};
328
329template <typename P1, typename P2, typename CalculationType>
330struct strategy_converter<strategy::within::franklin<P1, P2, CalculationType>>
331{
332 struct altered_strategy
333 : strategies::relate::cartesian<CalculationType>
334 {
335 template <typename Geometry1, typename Geometry2>
336 static auto relate(Geometry1 const&, Geometry2 const&,
337 std::enable_if_t
338 <
339 util::is_pointlike<Geometry1>::value
340 && ( util::is_linear<Geometry2>::value
341 || util::is_polygonal<Geometry2>::value )
342 > * = nullptr)
343 {
344 return strategy::within::franklin<void, void, CalculationType>();
345 }
346 };
347
348 static auto get(strategy::within::franklin<P1, P2, CalculationType> const&)
349 {
350 return altered_strategy();
351 }
352};
353
354template <typename P1, typename P2, typename CalculationType>
355struct strategy_converter<strategy::within::crossings_multiply<P1, P2, CalculationType>>
356{
357 struct altered_strategy
358 : strategies::relate::cartesian<CalculationType>
359 {
360 template <typename Geometry1, typename Geometry2>
361 static auto relate(Geometry1 const&, Geometry2 const&,
362 std::enable_if_t
363 <
364 util::is_pointlike<Geometry1>::value
365 && ( util::is_linear<Geometry2>::value
366 || util::is_polygonal<Geometry2>::value )
367 > * = nullptr)
368 {
369 return strategy::within::crossings_multiply<void, void, CalculationType>();
370 }
371 };
372
373 static auto get(strategy::within::crossings_multiply<P1, P2, CalculationType> const&)
374 {
375 return altered_strategy();
376 }
377};
378
379// TEMP used in distance segment/box
380template <typename CalculationType>
381struct strategy_converter<strategy::side::side_by_triangle<CalculationType>>
382{
383 static auto get(strategy::side::side_by_triangle<CalculationType> const&)
384 {
385 return strategies::relate::cartesian<CalculationType>();
386 }
387};
388
389template <typename CalculationType>
390struct strategy_converter<strategy::side::side_robust<CalculationType>>
391{
392 static auto get(strategy::side::side_robust<CalculationType> const&)
393 {
394 return strategies::relate::cartesian<CalculationType>();
395 }
396};
397
398
399} // namespace services
400
401}} // namespace strategies::relate
402
403}} // namespace boost::geometry
404
405#endif // BOOST_GEOMETRY_STRATEGIES_RELATE_CARTESIAN_HPP