]> git.proxmox.com Git - ceph.git/blame - ceph/src/boost/libs/geometry/include/boost/geometry/strategies/cartesian/point_in_box.hpp
add subtree-ish sources for 12.0.3
[ceph.git] / ceph / src / boost / libs / geometry / include / boost / geometry / strategies / cartesian / point_in_box.hpp
CommitLineData
7c673cae
FG
1// Boost.Geometry (aka GGL, Generic Geometry Library)
2
3// Copyright (c) 2007-2015 Barend Gehrels, Amsterdam, the Netherlands.
4// Copyright (c) 2008-2015 Bruno Lalande, Paris, France.
5// Copyright (c) 2009-2015 Mateusz Loskot, London, UK.
6
7// This file was modified by Oracle on 2015-2016.
8// Modifications copyright (c) 2015-2016, Oracle and/or its affiliates.
9
10// Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
11
12// Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
13// (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
14
15// Use, modification and distribution is subject to the Boost Software License,
16// Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
17// http://www.boost.org/LICENSE_1_0.txt)
18
19#ifndef BOOST_GEOMETRY_STRATEGIES_CARTESIAN_POINT_IN_BOX_HPP
20#define BOOST_GEOMETRY_STRATEGIES_CARTESIAN_POINT_IN_BOX_HPP
21
22
23#include <boost/geometry/core/access.hpp>
24#include <boost/geometry/core/coordinate_dimension.hpp>
25#include <boost/geometry/strategies/covered_by.hpp>
26#include <boost/geometry/strategies/within.hpp>
27#include <boost/geometry/util/normalize_spheroidal_coordinates.hpp>
28
29
30namespace boost { namespace geometry { namespace strategy
31{
32
33namespace within
34{
35
36
37template <typename Geometry, std::size_t Dimension, typename CSTag>
38struct within_range
39{
40 template <typename Value1, typename Value2>
41 static inline bool apply(Value1 const& value, Value2 const& min_value, Value2 const& max_value)
42 {
43 return value > min_value && value < max_value;
44 }
45};
46
47
48template <typename Geometry, std::size_t Dimension, typename CSTag>
49struct covered_by_range
50{
51 template <typename Value1, typename Value2>
52 static inline bool apply(Value1 const& value, Value2 const& min_value, Value2 const& max_value)
53 {
54 return value >= min_value && value <= max_value;
55 }
56};
57
58
59// NOTE: the result would be the same if instead of structs defined below
60// the above xxx_range were used with the following arguments:
61// (min_value + diff_min, min_value, max_value)
62struct within_longitude_range
63{
64 template <typename CalcT>
65 static inline bool apply(CalcT const& diff_min, CalcT const& min_value, CalcT const& max_value)
66 {
67 CalcT const c0 = 0;
68 return diff_min > c0 && min_value + diff_min < max_value;
69 }
70};
71
72struct covered_by_longitude_range
73{
74 template <typename CalcT>
75 static inline bool apply(CalcT const& diff_min, CalcT const& min_value, CalcT const& max_value)
76 {
77 return min_value + diff_min <= max_value;
78 }
79};
80
81
82template <typename Geometry,
83 typename ResultCheck>
84struct longitude_range
85{
86 template <typename Value1, typename Value2>
87 static inline bool apply(Value1 const& value, Value2 const& min_value, Value2 const& max_value)
88 {
89 typedef typename select_most_precise
90 <
91 Value1, Value2
92 >::type calc_t;
93 typedef typename coordinate_system<Geometry>::type::units units_t;
94 typedef math::detail::constants_on_spheroid<calc_t, units_t> constants;
95
96 // min <= max <=> diff >= 0
97 calc_t const diff_ing = max_value - min_value;
98
99 // if containing covers the whole globe it contains all
100 if (diff_ing >= constants::period())
101 {
102 return true;
103 }
104
105 // calculate positive longitude translation with min_value as origin
106 calc_t const diff_min = math::longitude_distance_unsigned<units_t, calc_t>(min_value, value);
107
108 return ResultCheck::template apply<calc_t>(diff_min, min_value, max_value);
109 }
110};
111
112
113// spherical_equatorial_tag, spherical_polar_tag and geographic_cat are casted to spherical_tag
114template <typename Geometry>
115struct within_range<Geometry, 0, spherical_tag>
116 : longitude_range<Geometry, within_longitude_range>
117{};
118
119
120template <typename Geometry>
121struct covered_by_range<Geometry, 0, spherical_tag>
122 : longitude_range<Geometry, covered_by_longitude_range>
123{};
124
125
126template
127<
128 template <typename, std::size_t, typename> class SubStrategy,
129 typename Point,
130 typename Box,
131 std::size_t Dimension,
132 std::size_t DimensionCount
133>
134struct relate_point_box_loop
135{
136 static inline bool apply(Point const& point, Box const& box)
137 {
138 typedef typename tag_cast<typename cs_tag<Point>::type, spherical_tag>::type cs_tag_t;
139
140 if (! SubStrategy<Point, Dimension, cs_tag_t>::apply(get<Dimension>(point),
141 get<min_corner, Dimension>(box),
142 get<max_corner, Dimension>(box))
143 )
144 {
145 return false;
146 }
147
148 return relate_point_box_loop
149 <
150 SubStrategy,
151 Point, Box,
152 Dimension + 1, DimensionCount
153 >::apply(point, box);
154 }
155};
156
157
158template
159<
160 template <typename, std::size_t, typename> class SubStrategy,
161 typename Point,
162 typename Box,
163 std::size_t DimensionCount
164>
165struct relate_point_box_loop<SubStrategy, Point, Box, DimensionCount, DimensionCount>
166{
167 static inline bool apply(Point const& , Box const& )
168 {
169 return true;
170 }
171};
172
173
174template
175<
176 typename Point,
177 typename Box,
178 template <typename, std::size_t, typename> class SubStrategy = within_range
179>
180struct point_in_box
181{
182 static inline bool apply(Point const& point, Box const& box)
183 {
184 return relate_point_box_loop
185 <
186 SubStrategy,
187 Point, Box,
188 0, dimension<Point>::type::value
189 >::apply(point, box);
190 }
191};
192
193
194} // namespace within
195
196
197#ifndef DOXYGEN_NO_STRATEGY_SPECIALIZATIONS
198
199
200namespace within { namespace services
201{
202
203template <typename Point, typename Box>
204struct default_strategy
205 <
206 point_tag, box_tag,
207 point_tag, areal_tag,
208 cartesian_tag, cartesian_tag,
209 Point, Box
210 >
211{
212 typedef within::point_in_box<Point, Box> type;
213};
214
215// spherical_equatorial_tag, spherical_polar_tag and geographic_cat are casted to spherical_tag
216template <typename Point, typename Box>
217struct default_strategy
218 <
219 point_tag, box_tag,
220 point_tag, areal_tag,
221 spherical_tag, spherical_tag,
222 Point, Box
223 >
224{
225 typedef within::point_in_box<Point, Box> type;
226};
227
228
229}} // namespace within::services
230
231
232namespace covered_by { namespace services
233{
234
235
236template <typename Point, typename Box>
237struct default_strategy
238 <
239 point_tag, box_tag,
240 point_tag, areal_tag,
241 cartesian_tag, cartesian_tag,
242 Point, Box
243 >
244{
245 typedef within::point_in_box
246 <
247 Point, Box,
248 within::covered_by_range
249 > type;
250};
251
252// spherical_equatorial_tag, spherical_polar_tag and geographic_cat are casted to spherical_tag
253template <typename Point, typename Box>
254struct default_strategy
255 <
256 point_tag, box_tag,
257 point_tag, areal_tag,
258 spherical_tag, spherical_tag,
259 Point, Box
260 >
261{
262 typedef within::point_in_box
263 <
264 Point, Box,
265 within::covered_by_range
266 > type;
267};
268
269
270}} // namespace covered_by::services
271
272
273#endif // DOXYGEN_NO_STRATEGY_SPECIALIZATIONS
274
275
276}}} // namespace boost::geometry::strategy
277
278
279#endif // BOOST_GEOMETRY_STRATEGIES_CARTESIAN_POINT_IN_BOX_HPP