disjoint_box_box.hpp 4.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134
  1. // Boost.Geometry (aka GGL, Generic Geometry Library)
  2. // Copyright (c) 2007-2015 Barend Gehrels, Amsterdam, the Netherlands.
  3. // Copyright (c) 2008-2015 Bruno Lalande, Paris, France.
  4. // Copyright (c) 2009-2015 Mateusz Loskot, London, UK.
  5. // Copyright (c) 2013-2015 Adam Wulkiewicz, Lodz, Poland.
  6. // This file was modified by Oracle on 2013-2018.
  7. // Modifications copyright (c) 2013-2018, Oracle and/or its affiliates.
  8. // Contributed and/or modified by Adam Wulkiewicz, on behalf of Oracle
  9. // Contributed and/or modified by Menelaos Karavelas, on behalf of Oracle
  10. // Parts of Boost.Geometry are redesigned from Geodan's Geographic Library
  11. // (geolib/GGL), copyright (c) 1995-2010 Geodan, Amsterdam, the Netherlands.
  12. // Use, modification and distribution is subject to the Boost Software License,
  13. // Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
  14. // http://www.boost.org/LICENSE_1_0.txt)
  15. #ifndef BOOST_GEOMETRY_STRATEGIES_SPHERICAL_DISJOINT_BOX_BOX_HPP
  16. #define BOOST_GEOMETRY_STRATEGIES_SPHERICAL_DISJOINT_BOX_BOX_HPP
  17. #include <cstddef>
  18. #include <boost/geometry/core/cs.hpp>
  19. #include <boost/geometry/strategies/cartesian/disjoint_box_box.hpp>
  20. #include <boost/geometry/strategies/disjoint.hpp>
  21. #include <boost/geometry/util/normalize_spheroidal_coordinates.hpp>
  22. #include <boost/geometry/util/select_most_precise.hpp>
  23. namespace boost { namespace geometry { namespace strategy { namespace disjoint
  24. {
  25. #ifndef DOXYGEN_NO_DETAIL
  26. namespace detail
  27. {
  28. struct box_box_on_spheroid
  29. {
  30. template <typename Box1, typename Box2>
  31. static inline bool apply(Box1 const& box1, Box2 const& box2)
  32. {
  33. typedef typename geometry::select_most_precise
  34. <
  35. typename coordinate_type<Box1>::type,
  36. typename coordinate_type<Box2>::type
  37. >::type calc_t;
  38. typedef typename geometry::detail::cs_angular_units<Box1>::type units_t;
  39. typedef math::detail::constants_on_spheroid<calc_t, units_t> constants;
  40. calc_t const b1_min = get<min_corner, 0>(box1);
  41. calc_t const b1_max = get<max_corner, 0>(box1);
  42. calc_t const b2_min = get<min_corner, 0>(box2);
  43. calc_t const b2_max = get<max_corner, 0>(box2);
  44. // min <= max <=> diff >= 0
  45. calc_t const diff1 = b1_max - b1_min;
  46. calc_t const diff2 = b2_max - b2_min;
  47. // check the intersection if neither box cover the whole globe
  48. if (diff1 < constants::period() && diff2 < constants::period())
  49. {
  50. // calculate positive longitude translation with b1_min as origin
  51. calc_t const diff_min = math::longitude_distance_unsigned<units_t>(b1_min, b2_min);
  52. calc_t const b2_min_transl = b1_min + diff_min; // always right of b1_min
  53. calc_t b2_max_transl = b2_min_transl - constants::period() + diff2;
  54. // if the translation is too close then use the original point
  55. // note that math::abs(b2_max_transl - b2_max) takes values very
  56. // close to k*2*constants::period() for k=0,1,2,...
  57. if (math::abs(b2_max_transl - b2_max) < constants::period() / 2)
  58. {
  59. b2_max_transl = b2_max;
  60. }
  61. if (b2_min_transl > b1_max // b2_min right of b1_max
  62. && b2_max_transl < b1_min) // b2_max left of b1_min
  63. {
  64. return true;
  65. }
  66. }
  67. return box_box
  68. <
  69. Box1, Box2, 1
  70. >::apply(box1, box2);
  71. }
  72. };
  73. } // namespace detail
  74. #endif // DOXYGEN_NO_DETAIL
  75. struct spherical_box_box
  76. {
  77. template <typename Box1, typename Box2>
  78. static inline bool apply(Box1 const& box1, Box2 const& box2)
  79. {
  80. return detail::box_box_on_spheroid::apply(box1, box2);
  81. }
  82. };
  83. namespace services
  84. {
  85. template <typename Box1, typename Box2, int TopDim1, int TopDim2>
  86. struct default_strategy<Box1, Box2, box_tag, box_tag, TopDim1, TopDim2, spherical_equatorial_tag, spherical_equatorial_tag>
  87. {
  88. typedef disjoint::spherical_box_box type;
  89. };
  90. template <typename Box1, typename Box2, int TopDim1, int TopDim2>
  91. struct default_strategy<Box1, Box2, box_tag, box_tag, TopDim1, TopDim2, spherical_polar_tag, spherical_polar_tag>
  92. {
  93. typedef disjoint::spherical_box_box type;
  94. };
  95. template <typename Box1, typename Box2, int TopDim1, int TopDim2>
  96. struct default_strategy<Box1, Box2, box_tag, box_tag, TopDim1, TopDim2, geographic_tag, geographic_tag>
  97. {
  98. typedef disjoint::spherical_box_box type;
  99. };
  100. } // namespace services
  101. }}}} // namespace boost::geometry::strategy::disjoint
  102. #endif // BOOST_GEOMETRY_STRATEGIES_SPHERICAL_DISJOINT_BOX_BOX_HPP