1 // Boost.Geometry (aka GGL, Generic Geometry Library)
3 // Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
4 // Copyright (c) 2008-2012 Bruno Lalande, Paris, France.
5 // Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
6 // Copyright (c) 2014 Adam Wulkiewicz, Lodz, Poland.
8 // This file was modified by Oracle on 2020.
9 // Modifications copyright (c) 2020 Oracle and/or its affiliates.
10 // Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
12 // Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
13 // (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
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)
19 #ifndef BOOST_GEOMETRY_ALGORITHMS_REVERSE_HPP
20 #define BOOST_GEOMETRY_ALGORITHMS_REVERSE_HPP
24 #include <boost/range/begin.hpp>
25 #include <boost/range/end.hpp>
27 #include <boost/variant/apply_visitor.hpp>
28 #include <boost/variant/static_visitor.hpp>
29 #include <boost/variant/variant_fwd.hpp>
31 #include <boost/geometry/algorithms/detail/interior_iterator.hpp>
32 #include <boost/geometry/algorithms/detail/multi_modify.hpp>
33 #include <boost/geometry/core/interior_rings.hpp>
34 #include <boost/geometry/core/tags.hpp>
35 #include <boost/geometry/geometries/concepts/check.hpp>
38 namespace boost { namespace geometry
42 #ifndef DOXYGEN_NO_DETAIL
43 namespace detail { namespace reverse
49 template <typename Range>
50 static inline void apply(Range& range)
52 std::reverse(boost::begin(range), boost::end(range));
57 struct polygon_reverse: private range_reverse
59 template <typename Polygon>
60 static inline void apply(Polygon& polygon)
62 range_reverse::apply(exterior_ring(polygon));
64 typename interior_return_type<Polygon>::type
65 rings = interior_rings(polygon);
67 for (typename detail::interior_iterator<Polygon>::type
68 it = boost::begin(rings); it != boost::end(rings); ++it)
70 range_reverse::apply(*it);
76 }} // namespace detail::reverse
77 #endif // DOXYGEN_NO_DETAIL
80 #ifndef DOXYGEN_NO_DISPATCH
85 template <typename Geometry, typename Tag = typename tag<Geometry>::type>
88 static inline void apply(Geometry&)
93 template <typename Ring>
94 struct reverse<Ring, ring_tag>
95 : detail::reverse::range_reverse
99 template <typename LineString>
100 struct reverse<LineString, linestring_tag>
101 : detail::reverse::range_reverse
105 template <typename Polygon>
106 struct reverse<Polygon, polygon_tag>
107 : detail::reverse::polygon_reverse
111 template <typename Geometry>
112 struct reverse<Geometry, multi_linestring_tag>
113 : detail::multi_modify
116 detail::reverse::range_reverse
121 template <typename Geometry>
122 struct reverse<Geometry, multi_polygon_tag>
123 : detail::multi_modify
126 detail::reverse::polygon_reverse
132 } // namespace dispatch
136 namespace resolve_variant
139 template <typename Geometry>
142 static void apply(Geometry& geometry)
144 concepts::check<Geometry>();
145 dispatch::reverse<Geometry>::apply(geometry);
149 template <BOOST_VARIANT_ENUM_PARAMS(typename T)>
150 struct reverse<boost::variant<BOOST_VARIANT_ENUM_PARAMS(T)> >
152 struct visitor: boost::static_visitor<void>
154 template <typename Geometry>
155 void operator()(Geometry& geometry) const
157 reverse<Geometry>::apply(geometry);
161 static inline void apply(boost::variant<BOOST_VARIANT_ENUM_PARAMS(T)>& geometry)
163 boost::apply_visitor(visitor(), geometry);
167 } // namespace resolve_variant
171 \brief Reverses the points within a geometry
172 \details Generic function to reverse a geometry. It resembles the std::reverse
173 functionality, but it takes the geometry type into account. Only for a ring
174 or for a linestring it is the same as the std::reverse.
176 \tparam Geometry \tparam_geometry
177 \param geometry \param_geometry which will be reversed
179 \qbk{[include reference/algorithms/reverse.qbk]}
181 template <typename Geometry>
182 inline void reverse(Geometry& geometry)
184 resolve_variant::reverse<Geometry>::apply(geometry);
187 }} // namespace boost::geometry
190 #endif // BOOST_GEOMETRY_ALGORITHMS_REVERSE_HPP