Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-18 09:35:18

0001 // Boost.Geometry (aka GGL, Generic Geometry Library)
0002 
0003 // Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
0004 // Copyright (c) 2008-2012 Bruno Lalande, Paris, France.
0005 // Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
0006 
0007 // This file was modified by Oracle on 2017-2022.
0008 // Modifications copyright (c) 2017-2022 Oracle and/or its affiliates.
0009 // Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
0010 
0011 // Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
0012 // (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
0013 
0014 // Use, modification and distribution is subject to the Boost Software License,
0015 // Version 1.Dimension. (See accompanying file LICENSE_1_0.txt or copy at
0016 // http://www.boost.org/LICENSE_1_0.txt)
0017 
0018 #ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_POINT_ON_BORDER_HPP
0019 #define BOOST_GEOMETRY_ALGORITHMS_DETAIL_POINT_ON_BORDER_HPP
0020 
0021 
0022 #include <cstddef>
0023 
0024 #include <boost/range/begin.hpp>
0025 #include <boost/range/end.hpp>
0026 #include <boost/static_assert.hpp>
0027 
0028 #include <boost/geometry/algorithms/assign.hpp>
0029 #include <boost/geometry/algorithms/detail/convert_point_to_point.hpp>
0030 #include <boost/geometry/algorithms/detail/equals/point_point.hpp>
0031 #include <boost/geometry/core/tags.hpp>
0032 #include <boost/geometry/core/point_type.hpp>
0033 #include <boost/geometry/core/ring_type.hpp>
0034 #include <boost/geometry/geometries/concepts/check.hpp>
0035 #include <boost/geometry/util/condition.hpp>
0036 #include <boost/geometry/views/detail/indexed_point_view.hpp>
0037 
0038 
0039 namespace boost { namespace geometry
0040 {
0041 
0042 
0043 #ifndef DOXYGEN_NO_DETAIL
0044 namespace detail { namespace point_on_border
0045 {
0046 
0047 
0048 struct get_point
0049 {
0050     template <typename Destination, typename Source>
0051     static inline bool apply(Destination& destination, Source const& source)
0052     {
0053         detail::conversion::convert_point_to_point(source, destination);
0054         return true;
0055     }
0056 };
0057 
0058 
0059 struct point_on_range
0060 {
0061     // Version with iterator
0062     template<typename Point, typename Iterator>
0063     static inline bool apply(Point& point, Iterator begin, Iterator end)
0064     {
0065         if (begin == end)
0066         {
0067             return false;
0068         }
0069 
0070         detail::conversion::convert_point_to_point(*begin, point);
0071         return true;
0072     }
0073 
0074     // Version with range
0075     template<typename Point, typename Range>
0076     static inline bool apply(Point& point, Range const& range)
0077     {
0078         return apply(point, boost::begin(range), boost::end(range));
0079     }
0080 };
0081 
0082 
0083 struct point_on_polygon
0084 {
0085     template<typename Point, typename Polygon>
0086     static inline bool apply(Point& point, Polygon const& polygon)
0087     {
0088         return point_on_range::apply(point, exterior_ring(polygon));
0089     }
0090 };
0091 
0092 
0093 struct point_on_segment_or_box
0094 {
0095     template<typename Point, typename SegmentOrBox>
0096     static inline bool apply(Point& point, SegmentOrBox const& segment_or_box)
0097     {
0098         detail::indexed_point_view<SegmentOrBox const, 0> view(segment_or_box);
0099         detail::conversion::convert_point_to_point(view, point);
0100         return true;
0101     }
0102 };
0103 
0104 
0105 template <typename Policy>
0106 struct point_on_multi
0107 {
0108     template<typename Point, typename MultiGeometry>
0109     static inline bool apply(Point& point, MultiGeometry const& multi)
0110     {
0111         // Take a point on the first multi-geometry
0112         // (i.e. the first that is not empty)
0113         for (auto it = boost::begin(multi); it != boost::end(multi); ++it)
0114         {
0115             if (Policy::apply(point, *it))
0116             {
0117                 return true;
0118             }
0119         }
0120         return false;
0121     }
0122 };
0123 
0124 
0125 }} // namespace detail::point_on_border
0126 #endif // DOXYGEN_NO_DETAIL
0127 
0128 
0129 #ifndef DOXYGEN_NO_DISPATCH
0130 namespace dispatch
0131 {
0132 
0133 
0134 template <typename GeometryTag>
0135 struct point_on_border
0136 {};
0137 
0138 template <>
0139 struct point_on_border<point_tag>
0140     : detail::point_on_border::get_point
0141 {};
0142 
0143 template <>
0144 struct point_on_border<segment_tag>
0145     : detail::point_on_border::point_on_segment_or_box
0146 {};
0147 
0148 template <>
0149 struct point_on_border<linestring_tag>
0150     : detail::point_on_border::point_on_range
0151 {};
0152 
0153 template <>
0154 struct point_on_border<ring_tag>
0155     : detail::point_on_border::point_on_range
0156 {};
0157 
0158 template <>
0159 struct point_on_border<polygon_tag>
0160     : detail::point_on_border::point_on_polygon
0161 {};
0162 
0163 template <>
0164 struct point_on_border<box_tag>
0165     : detail::point_on_border::point_on_segment_or_box
0166 {};
0167 
0168 
0169 template <>
0170 struct point_on_border<multi_point_tag>
0171     : detail::point_on_border::point_on_range
0172 {};
0173 
0174 template <>
0175 struct point_on_border<multi_polygon_tag>
0176     : detail::point_on_border::point_on_multi
0177         <
0178             detail::point_on_border::point_on_polygon
0179         >
0180 {};
0181 
0182 
0183 template <>
0184 struct point_on_border<multi_linestring_tag>
0185     : detail::point_on_border::point_on_multi
0186         <
0187             detail::point_on_border::point_on_range
0188         >
0189 {};
0190 
0191 
0192 } // namespace dispatch
0193 #endif // DOXYGEN_NO_DISPATCH
0194 
0195 
0196 // TODO: We should probably rename this utility because it can return point
0197 //   which is in the interior of a geometry (for PointLike and LinearRings).
0198 
0199 /*!
0200 \brief Take point on a border
0201 \ingroup overlay
0202 \tparam Geometry geometry type. This also defines the type of the output point
0203 \param point to assign
0204 \param geometry geometry to take point from
0205 \return TRUE if successful, else false.
0206     It is only false if polygon/line have no points
0207 \note for a polygon, it is always a point on the exterior ring
0208  */
0209 template <typename Point, typename Geometry>
0210 inline bool point_on_border(Point& point, Geometry const& geometry)
0211 {
0212     concepts::check<Point>();
0213     concepts::check<Geometry const>();
0214 
0215     return dispatch::point_on_border
0216             <
0217                 typename tag<Geometry>::type
0218             >::apply(point, geometry);
0219 }
0220 
0221 
0222 }} // namespace boost::geometry
0223 
0224 
0225 #endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_POINT_ON_BORDER_HPP