00001 // ***************************************************************************** 00002 // 00003 // Copyright (c) 2016, Southwest Research Institute® (SwRI®) 00004 // All rights reserved. 00005 // 00006 // Redistribution and use in source and binary forms, with or without 00007 // modification, are permitted provided that the following conditions are met: 00008 // * Redistributions of source code must retain the above copyright 00009 // notice, this list of conditions and the following disclaimer. 00010 // * Redistributions in binary form must reproduce the above copyright 00011 // notice, this list of conditions and the following disclaimer in the 00012 // documentation and/or other materials provided with the distribution. 00013 // * Neither the name of Southwest Research Institute® (SwRI®) nor the 00014 // names of its contributors may be used to endorse or promote products 00015 // derived from this software without specific prior written permission. 00016 // 00017 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 00018 // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 00019 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 00020 // ARE DISCLAIMED. IN NO EVENT SHALL <COPYRIGHT HOLDER> BE LIABLE FOR ANY 00021 // DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 00022 // (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 00023 // LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 00024 // ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00025 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 00026 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00027 // 00028 // ***************************************************************************** 00029 #ifndef SWRI_ROUTE_UTIL_UTIL_H_ 00030 #define SWRI_ROUTE_UTIL_UTIL_H_ 00031 00032 #include <marti_nav_msgs/RoutePosition.h> 00033 #include <swri_transform_util/transform.h> 00034 00035 namespace swri_route_util 00036 { 00037 class Route; 00038 class RoutePoint; 00039 00040 // Transform a route. The route will be transformed in place using 00041 // the supplied transform. Known property types that are affected by 00042 // the transform are expceted to be transformed properly. The 00043 // frame_id of the transformed route will be set to the required 00044 // target_frame argument, because forgetting to up the frame_id has 00045 // caused difficult bugs several times. 00046 void transform(Route &route, 00047 const swri_transform_util::Transform &transform, 00048 const std::string &target_frame); 00049 00050 00051 // Project a route to the XY plane by setting the Z coordinate to zero. 00052 void projectToXY(Route &route); 00053 00054 00055 // Fill in the orientation of the route points using an estimate from 00056 // the route geometry and desired "up" direction. This function 00057 // assumes the route is in a cartesian (e.g. not WGS84) frame. 00058 void fillOrientations(Route &route, 00059 const tf::Vector3 &up=tf::Vector3(0.0, 0.0, 1.0)); 00060 00061 00062 // Find the closest point on the route (as a route position) for a 00063 // given point. If extrapolate_before_start and/or 00064 // extrapolate_past_end are true, the projection will consider the 00065 // first and last segments to extend infinitely (ONLY if the point is 00066 // nearest to either without extrapolation). This function assumes 00067 // the route is in a cartesian (e.g. not WGS84) frame. 00068 bool projectOntoRoute(marti_nav_msgs::RoutePosition &position, 00069 const Route &route, 00070 const tf::Vector3 &point, 00071 bool extrapolate_before_start, 00072 bool extrapolate_past_end); 00073 00074 00075 // Find the closest position on a route for a given point, restricted 00076 // to a subset of the route. The subset is defined by a start and end 00077 // position on the route. This function assumes the route is in a 00078 // cartesian (e.g. not WGS84) frame. 00079 bool projectOntoRouteWindow(marti_nav_msgs::RoutePosition &position, 00080 const Route &route, 00081 const tf::Vector3 &point, 00082 const marti_nav_msgs::RoutePosition &window_start, 00083 const marti_nav_msgs::RoutePosition &window_end); 00084 00085 00086 // Normalize a route position. A normalize route position is guaranteed to 00087 // have: 00088 // - A valid id for a point in the route. 00089 // 00090 // - If the position is before the start of the route, the id will be 00091 // first route point and the distance will be negative. 00092 00093 // - If the position is after the end of the route, the id will be the 00094 // last route point and the distance will be positive. 00095 // 00096 // - Otherwise, the position's id will be for the point that begins 00097 // the segment containing the position, and the distance will be 00098 // less than that length of that segment. 00099 // 00100 // This function fails if the original position's id is not found in the 00101 // route. This function assumes the route is in a cartesian (e.g. not 00102 // WGS84) frame. 00103 bool normalizeRoutePosition(marti_nav_msgs::RoutePosition &normalized_position, 00104 const Route &route, 00105 const marti_nav_msgs::RoutePosition &position); 00106 00107 00108 // Create a route point from a route position by interpolating between 00109 // the route's points as needed. This function assumes the route is 00110 // in a cartesian (e.g. not WGS84) frame. 00111 bool interpolateRoutePosition(RoutePoint &point, 00112 const Route &route, 00113 const marti_nav_msgs::RoutePosition &position, 00114 bool allow_extrapolation); 00115 00116 // Return the distance between two route positions. This function 00117 // works for routes defined in WGS84 or Euclidean spaces. 00118 bool routeDistance( 00119 double &distance, 00120 const marti_nav_msgs::RoutePosition &start, 00121 const marti_nav_msgs::RoutePosition &end, 00122 const Route &route); 00123 00124 // Return the distances between a start route position and multiple 00125 // end route positions. This function works for routes defined in 00126 // WGS84 or Euclidean spaces. This function returns false if the 00127 // start point wasn't found in the route, in which case distances is 00128 // not modified. If the function is true, the start point was found 00129 // and distances is guaranteed to be the same size as ends. If an end 00130 // point is not found in the route, its distance is set to NaN. 00131 bool routeDistances( 00132 std::vector<double> &distances, 00133 const marti_nav_msgs::RoutePosition &start, 00134 const std::vector<marti_nav_msgs::RoutePosition> &ends, 00135 const Route &route); 00136 00137 // Extracts a subroute from [start, end) 00138 bool extractSubroute( 00139 Route &sub_route, 00140 const Route &route, 00141 const marti_nav_msgs::RoutePosition &start, 00142 const marti_nav_msgs::RoutePosition &end); 00143 } // namespace swri_route_util 00144 #endif // SWRI_ROUTE_UTIL_UTIL_H_