00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030 #ifndef FILTERS_SELF_SEE_H_
00031 #define FILTERS_SELF_SEE_H_
00032
00033 #include <filters/filter_base.h>
00034 #include <robot_self_filter/self_mask.h>
00035 #include <ros/console.h>
00036
00037 #include <pcl/point_types.h>
00038 #include <pcl/point_cloud.h>
00039
00040 namespace filters
00041 {
00043 template <typename T>
00044 class SelfFilter: public FilterBase <T>
00045 {
00046 public:
00048 SelfFilter (ros::NodeHandle nh) : nh_(nh)
00049 {
00050 nh_.param<double> ("min_sensor_dist", min_sensor_dist_, 0.01);
00051 double default_padding, default_scale;
00052 nh_.param<double> ("self_see_default_padding", default_padding, .01);
00053 nh_.param<double> ("self_see_default_scale", default_scale, 1.0);
00054
00055 std::vector<robot_self_filter::LinkInfo> links;
00056 std::string link_names;
00057
00058 if (!nh_.hasParam ("self_see_links"))
00059 {
00060 ROS_WARN ("No links specified for self filtering.");
00061 }
00062 else
00063 {
00064 XmlRpc::XmlRpcValue ssl_vals;;
00065
00066 nh_.getParam ("self_see_links", ssl_vals);
00067 if (ssl_vals.getType () != XmlRpc::XmlRpcValue::TypeArray)
00068 {
00069 ROS_WARN ("Self see links need to be an array");
00070 }
00071 else
00072 {
00073 if (ssl_vals.size () == 0)
00074 {
00075 ROS_WARN ("No values in self see links array");
00076 }
00077 else
00078 {
00079 for (int i = 0; i < ssl_vals.size (); ++i)
00080 {
00081 robot_self_filter::LinkInfo li;
00082
00083 if (ssl_vals[i].getType() != XmlRpc::XmlRpcValue::TypeStruct)
00084 {
00085 ROS_WARN ("Self see links entry %d is not a structure. Stopping processing of self see links", i);
00086 break;
00087 }
00088 if (!ssl_vals[i].hasMember ("name"))
00089 {
00090 ROS_WARN ("Self see links entry %d has no name. Stopping processing of self see links", i);
00091 break;
00092 }
00093 li.name = std::string (ssl_vals[i]["name"]);
00094 if (!ssl_vals[i].hasMember ("padding"))
00095 {
00096 ROS_DEBUG ("Self see links entry %d has no padding. Assuming default padding of %g", i, default_padding);
00097 li.padding = default_padding;
00098 }
00099 else
00100 {
00101 li.padding = ssl_vals[i]["padding"];
00102 }
00103 if (!ssl_vals[i].hasMember ("scale"))
00104 {
00105 ROS_DEBUG ("Self see links entry %d has no scale. Assuming default scale of %g", i, default_scale);
00106 li.scale = default_scale;
00107 }
00108 else
00109 {
00110 li.scale = ssl_vals[i]["scale"];
00111 }
00112 links.push_back (li);
00113 }
00114 }
00115 }
00116 }
00117 sm_ = new robot_self_filter::SelfMask (tf_, links);
00118
00119
00120
00121 if (!sensor_frame_.empty ())
00122 ROS_INFO("Self filter is removing shadow points for sensor in frame '%s'. Minimum distance to sensor is %f.", sensor_frame_.c_str (), min_sensor_dist_);
00123 }
00124
00127 virtual ~SelfFilter (void)
00128 {
00129 delete sm_;
00130 }
00131
00132 virtual bool
00133 configure (void)
00134 {
00135
00136
00137 nh_.param ("invert", invert_, false);
00138
00139 if (invert_)
00140 ROS_INFO ("Inverting filter output");
00141
00142 return (true);
00143 }
00144
00145 bool updateWithSensorFrame
00146 (const pcl::PointCloud<pcl::PointXYZ>& data_in, pcl::PointCloud<pcl::PointXYZ>& data_out, const std::string& sensor_frame)
00147 {
00148 sensor_frame_ = sensor_frame;
00149 return (update (data_in, data_out));
00150 }
00151
00156 virtual bool
00157 update (const pcl::PointCloud<pcl::PointXYZ>& data_in, pcl::PointCloud<pcl::PointXYZ>& data_out)
00158 {
00159 std::vector<int> keep (data_in.points.size ());
00160 if (sensor_frame_.empty ())
00161 {
00162 sm_->maskContainment (data_in, keep);
00163 }
00164 else
00165 {
00166 sm_->maskIntersection (data_in, sensor_frame_, min_sensor_dist_, keep);
00167 }
00168 fillResult (data_in, keep, data_out);
00169 return (true);
00170 }
00171
00172 bool updateWithSensorFrame (const pcl::PointCloud<pcl::PointXYZ>& data_in, pcl::PointCloud<pcl::PointXYZ>& data_out, pcl::PointCloud<pcl::PointXYZ>& data_diff, const std::string& sensor_frame)
00173 {
00174 sensor_frame_ = sensor_frame;
00175 return (update (data_in, data_out, data_diff));
00176 }
00177
00182 virtual bool update (const pcl::PointCloud<pcl::PointXYZ>& data_in, pcl::PointCloud<pcl::PointXYZ>& data_out, pcl::PointCloud<pcl::PointXYZ>& data_diff)
00183 {
00184 std::vector<int> keep (data_in.points.size ());
00185 if (sensor_frame_.empty ())
00186 {
00187 sm_->maskContainment (data_in, keep);
00188 }
00189 else
00190 {
00191 sm_->maskIntersection (data_in, sensor_frame_, min_sensor_dist_, keep);
00192 }
00193 fillResult (data_in, keep, data_out);
00194 fillDiff (data_in,keep,data_diff);
00195 return (true);
00196 }
00197
00198 void fillDiff (const pcl::PointCloud<pcl::PointXYZ>& data_in, const std::vector<int> &keep, pcl::PointCloud<pcl::PointXYZ>& data_out)
00199 {
00200 const unsigned int np = data_in.points.size ();
00201
00202
00203 data_out.header = data_in.header;
00204
00205 data_out.points.resize (0);
00206 data_out.points.reserve (np);
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216 for (unsigned int i = 0 ; i < np ; ++i)
00217 {
00218 if ((keep[i] && invert_) || (!keep[i] && !invert_))
00219 {
00220 data_out.points.push_back(data_in.points[i]);
00221
00222
00223 }
00224 }
00225 }
00226
00227 void fillResult (const pcl::PointCloud<pcl::PointXYZ>& data_in, const std::vector<int> &keep, pcl::PointCloud<pcl::PointXYZ>& data_out)
00228 {
00229 const unsigned int np = data_in.points.size ();
00230
00231
00232 data_out.header = data_in.header;
00233
00234 data_out.points.resize (0);
00235 data_out.points.reserve (np);
00236
00237
00238
00239
00240
00241
00242
00243
00244
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00255
00256
00257
00258
00259
00260
00261
00262
00263
00264 for (unsigned int i = 0 ; i < np ; ++i)
00265
00266 {
00267 if (keep[i] == robot_self_filter::OUTSIDE)
00268 {
00269 data_out.points.push_back (data_in.points[i]);
00270
00271
00272 }
00273 }
00274
00275
00276
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286
00287
00288
00289
00290 }
00291
00292
00293
00294
00295
00296
00297
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308 robot_self_filter::SelfMask* getSelfMask ()
00309 {
00310 return (sm_);
00311 }
00312
00313 void setSensorFrame (const std::string& frame)
00314 {
00315 sensor_frame_ = frame;
00316 }
00317
00318 protected:
00319
00320 tf::TransformListener tf_;
00321 robot_self_filter::SelfMask* sm_;
00322
00323 ros::NodeHandle nh_;
00324 bool invert_;
00325 std::string sensor_frame_;
00326 std::string annotate_;
00327 double min_sensor_dist_;
00328 };
00329 }
00330
00331 #endif //#ifndef FILTERS_SELF_SEE_H_