segment.hpp 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203
  1. // Boost.Geometry (aka GGL, Generic Geometry Library)
  2. // Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
  3. // Copyright (c) 2008-2012 Bruno Lalande, Paris, France.
  4. // Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
  5. // Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
  6. // (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
  7. // Use, modification and distribution is subject to the Boost Software License,
  8. // Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
  9. // http://www.boost.org/LICENSE_1_0.txt)
  10. #ifndef BOOST_GEOMETRY_GEOMETRIES_SEGMENT_HPP
  11. #define BOOST_GEOMETRY_GEOMETRIES_SEGMENT_HPP
  12. #include <cstddef>
  13. #include <boost/concept/assert.hpp>
  14. #include <boost/mpl/if.hpp>
  15. #include <boost/type_traits/is_const.hpp>
  16. #include <boost/geometry/geometries/concepts/point_concept.hpp>
  17. namespace boost { namespace geometry
  18. {
  19. namespace model
  20. {
  21. /*!
  22. \brief Class segment: small class containing two points
  23. \ingroup geometries
  24. \details From Wikipedia: In geometry, a line segment is a part of a line that is bounded
  25. by two distinct end points, and contains every point on the line between its end points.
  26. \note There is also a point-referring-segment, class referring_segment,
  27. containing point references, where points are NOT copied
  28. */
  29. template<typename Point>
  30. class segment : public std::pair<Point, Point>
  31. {
  32. public :
  33. inline segment()
  34. {}
  35. inline segment(Point const& p1, Point const& p2)
  36. {
  37. this->first = p1;
  38. this->second = p2;
  39. }
  40. };
  41. /*!
  42. \brief Class segment: small class containing two (templatized) point references
  43. \ingroup geometries
  44. \details From Wikipedia: In geometry, a line segment is a part of a line that is bounded
  45. by two distinct end points, and contains every point on the line between its end points.
  46. \note The structure is like std::pair, and can often be used interchangeable.
  47. Difference is that it refers to points, does not have points.
  48. \note Like std::pair, points are public available.
  49. \note type is const or non const, so geometry::segment<P> or geometry::segment<P const>
  50. \note We cannot derive from std::pair<P&, P&> because of
  51. reference assignments.
  52. \tparam ConstOrNonConstPoint point type of the segment, maybe a point or a const point
  53. */
  54. template<typename ConstOrNonConstPoint>
  55. class referring_segment
  56. {
  57. BOOST_CONCEPT_ASSERT( (
  58. typename boost::mpl::if_
  59. <
  60. boost::is_const<ConstOrNonConstPoint>,
  61. concept::Point<ConstOrNonConstPoint>,
  62. concept::ConstPoint<ConstOrNonConstPoint>
  63. >
  64. ) );
  65. typedef ConstOrNonConstPoint point_type;
  66. public:
  67. point_type& first;
  68. point_type& second;
  69. inline referring_segment(point_type& p1, point_type& p2)
  70. : first(p1)
  71. , second(p2)
  72. {}
  73. };
  74. } // namespace model
  75. // Traits specializations for segment above
  76. #ifndef DOXYGEN_NO_TRAITS_SPECIALIZATIONS
  77. namespace traits
  78. {
  79. template <typename Point>
  80. struct tag<model::segment<Point> >
  81. {
  82. typedef segment_tag type;
  83. };
  84. template <typename Point>
  85. struct point_type<model::segment<Point> >
  86. {
  87. typedef Point type;
  88. };
  89. template <typename Point, std::size_t Dimension>
  90. struct indexed_access<model::segment<Point>, 0, Dimension>
  91. {
  92. typedef model::segment<Point> segment_type;
  93. typedef typename geometry::coordinate_type<segment_type>::type coordinate_type;
  94. static inline coordinate_type get(segment_type const& s)
  95. {
  96. return geometry::get<Dimension>(s.first);
  97. }
  98. static inline void set(segment_type& s, coordinate_type const& value)
  99. {
  100. geometry::set<Dimension>(s.first, value);
  101. }
  102. };
  103. template <typename Point, std::size_t Dimension>
  104. struct indexed_access<model::segment<Point>, 1, Dimension>
  105. {
  106. typedef model::segment<Point> segment_type;
  107. typedef typename geometry::coordinate_type<segment_type>::type coordinate_type;
  108. static inline coordinate_type get(segment_type const& s)
  109. {
  110. return geometry::get<Dimension>(s.second);
  111. }
  112. static inline void set(segment_type& s, coordinate_type const& value)
  113. {
  114. geometry::set<Dimension>(s.second, value);
  115. }
  116. };
  117. template <typename ConstOrNonConstPoint>
  118. struct tag<model::referring_segment<ConstOrNonConstPoint> >
  119. {
  120. typedef segment_tag type;
  121. };
  122. template <typename ConstOrNonConstPoint>
  123. struct point_type<model::referring_segment<ConstOrNonConstPoint> >
  124. {
  125. typedef ConstOrNonConstPoint type;
  126. };
  127. template <typename ConstOrNonConstPoint, std::size_t Dimension>
  128. struct indexed_access<model::referring_segment<ConstOrNonConstPoint>, 0, Dimension>
  129. {
  130. typedef model::referring_segment<ConstOrNonConstPoint> segment_type;
  131. typedef typename geometry::coordinate_type<segment_type>::type coordinate_type;
  132. static inline coordinate_type get(segment_type const& s)
  133. {
  134. return geometry::get<Dimension>(s.first);
  135. }
  136. static inline void set(segment_type& s, coordinate_type const& value)
  137. {
  138. geometry::set<Dimension>(s.first, value);
  139. }
  140. };
  141. template <typename ConstOrNonConstPoint, std::size_t Dimension>
  142. struct indexed_access<model::referring_segment<ConstOrNonConstPoint>, 1, Dimension>
  143. {
  144. typedef model::referring_segment<ConstOrNonConstPoint> segment_type;
  145. typedef typename geometry::coordinate_type<segment_type>::type coordinate_type;
  146. static inline coordinate_type get(segment_type const& s)
  147. {
  148. return geometry::get<Dimension>(s.second);
  149. }
  150. static inline void set(segment_type& s, coordinate_type const& value)
  151. {
  152. geometry::set<Dimension>(s.second, value);
  153. }
  154. };
  155. } // namespace traits
  156. #endif // DOXYGEN_NO_TRAITS_SPECIALIZATIONS
  157. }} // namespace boost::geometry
  158. #endif // BOOST_GEOMETRY_GEOMETRIES_SEGMENT_HPP