Go to the documentation of this file.00001 #include <spatial_world_model/RecognizedObjectsListener.h>
00002
00003 #include <interactive_world_msgs/StoreObservation.h>
00004 #include <interactive_world_msgs/FindSurface.h>
00005 #include <interactive_world_msgs/FindObservations.h>
00006 #include <interactive_world_msgs/SetObservationsRemoved.h>
00007 #include <interactive_world_msgs/TransformToSurfaceFrame.h>
00008
00009 using namespace std;
00010 using namespace rail::interactive_world;
00011
00012 RecognizedObjectsListener::RecognizedObjectsListener()
00013 {
00014 incoming_cleared_objects_ = false;
00015 store_observation_srv_ = node_.serviceClient<interactive_world_msgs::StoreObservation>(
00016 "/spatial_world_model_server/store_observation"
00017 );
00018 find_surface_srv_ = node_.serviceClient<interactive_world_msgs::FindSurface>(
00019 "/high_level_action_server/find_surface"
00020 );
00021 transform_to_surface_frame_srv_ = node_.serviceClient<interactive_world_msgs::TransformToSurfaceFrame>(
00022 "/high_level_action_server/transform_to_surface_frame"
00023 );
00024 find_observations_srv_ = node_.serviceClient<interactive_world_msgs::FindObservations>(
00025 "/spatial_world_model_server/find_observations"
00026 );
00027 recognized_objects_sub_ = node_.subscribe("/object_recognition_listener/recognized_objects", 1,
00028 &RecognizedObjectsListener::recognizedObjectsCallback, this);
00029 set_observations_removed_srv_ = node_.serviceClient<interactive_world_msgs::SetObservationsRemoved>(
00030 "/spatial_world_model_server/set_observations_removed"
00031 );
00032 ROS_INFO("Recognized Objects Listener Initialized");
00033 }
00034
00035 void RecognizedObjectsListener::recognizedObjectsCallback(const rail_manipulation_msgs::SegmentedObjectList &objects)
00036 {
00037
00038 incoming_cleared_objects_ = !incoming_cleared_objects_;
00039 if (objects.objects.empty() && incoming_cleared_objects_)
00040 {
00041 return;
00042 }
00043
00044 ROS_INFO("Attmpting to store %ld objects in the spatial world model...", objects.objects.size());
00045
00046
00047 vector<string> seen_objects;
00048
00049 map<string, vector<string> > seen_surfaces;
00050
00051
00052 uint32_t count = 0;
00053 for (size_t i = 0; i < objects.objects.size(); i++)
00054 {
00055 const rail_manipulation_msgs::SegmentedObject &object = objects.objects[i];
00056 if (object.recognized)
00057 {
00058
00059 interactive_world_msgs::FindSurface surface;
00060 surface.request.pose.header.frame_id = object.point_cloud.header.frame_id;
00061 surface.request.pose.pose.position.x = object.centroid.x;
00062 surface.request.pose.pose.position.y = object.centroid.y;
00063 surface.request.pose.pose.position.z = object.centroid.z - (object.height / 2.0);
00064 surface.request.pose.pose.orientation = object.orientation;
00065
00066 if (find_surface_srv_.call(surface))
00067 {
00068
00069 if (!surface.response.surface.empty())
00070 {
00071 seen_objects.push_back(object.name);
00072
00073
00074 interactive_world_msgs::StoreObservation store;
00075 store.request.surface = surface.response.surface;
00076 store.request.surface_frame_id = surface.response.surface_frame_id;
00077 store.request.placement_surface_frame_id = surface.response.placement_surface_frame_id;
00078 store.request.item = object.name;
00079 store.request.item_conf = object.confidence;
00080
00081
00082 seen_surfaces[surface.response.surface_frame_id].push_back(surface.response.placement_surface_frame_id);
00083
00084
00085 interactive_world_msgs::TransformToSurfaceFrame transform_to_surface_frame;
00086 transform_to_surface_frame.request.pose = surface.request.pose;
00087 transform_to_surface_frame.request.surface = surface.response.surface;
00088 if (transform_to_surface_frame_srv_.call(transform_to_surface_frame))
00089 {
00090 store.request.x = transform_to_surface_frame.response.pose.pose.position.x;
00091 store.request.y = transform_to_surface_frame.response.pose.pose.position.y;
00092 store.request.z = transform_to_surface_frame.response.pose.pose.position.z;
00093 tf2::Quaternion q(transform_to_surface_frame.response.pose.pose.orientation.x,
00094 transform_to_surface_frame.response.pose.pose.orientation.y,
00095 transform_to_surface_frame.response.pose.pose.orientation.z,
00096 transform_to_surface_frame.response.pose.pose.orientation.w);
00097 store.request.theta = q.getAngle();
00098
00099
00100 if (store_observation_srv_.call(store))
00101 {
00102 count++;
00103 } else
00104 {
00105 ROS_WARN("Failed to store current observation of object '%s'.", object.name.c_str());
00106 }
00107 } else
00108 {
00109 ROS_WARN("Failed to transform pose to surface frame for '%s'.", object.name.c_str());
00110 }
00111 } else
00112 {
00113 ROS_WARN("Failed to find surface for object '%s'.", object.name.c_str());
00114 }
00115 } else
00116 {
00117 ROS_WARN("Failed to call surface finder.");
00118 }
00119 }
00120 }
00121
00122 ROS_INFO("Stored %d item observations.", count);
00123
00124
00125 interactive_world_msgs::SetObservationsRemoved remove;
00126 for (map<string, vector<string> >::iterator iter = seen_surfaces.begin(); iter != seen_surfaces.end(); ++iter)
00127 {
00128
00129 vector<string> &placement_surfaces = iter->second;
00130 sort(placement_surfaces.begin(), placement_surfaces.end());
00131 vector<string>::iterator last = unique(iter->second.begin(), iter->second.end());
00132 placement_surfaces.erase(last, placement_surfaces.end());
00133 for (size_t i = 0; i < placement_surfaces.size(); i++)
00134 {
00135
00136 interactive_world_msgs::FindObservations find;
00137 find.request.surface_frame_id = iter->first;
00138 find.request.placement_surface_frame_id = placement_surfaces[i];
00139 find.request.removed = false;
00140 find_observations_srv_.call(find);
00141
00142 for (size_t j = 0; j < find.response.items.size(); j++)
00143 {
00144 if (std::find(seen_objects.begin(), seen_objects.end(), find.response.items[j]) == seen_objects.end())
00145 {
00146 remove.request.ids.push_back(find.response.ids[j]);
00147 }
00148 }
00149 }
00150 }
00151
00152 if (!remove.request.ids.empty())
00153 {
00154 ROS_INFO("Setting %ld old observations as removed.", remove.request.ids.size());
00155 set_observations_removed_srv_.call(remove);
00156 }
00157 }