Go to the documentation of this file.00001 #include <vigir_pattern_generator/pattern_generator.h>
00002
00003 namespace vigir_footstep_planning
00004 {
00005 PatternGenerator::PatternGenerator(ros::NodeHandle& nh)
00006 {
00007 joystick_handler.reset(new JoystickHandler(nh));
00008
00009 nh.param("world_frame_id", world_frame_id, std::string("/world"));
00010 nh.param("pattern_generator/number_of_steps", (int&)number_of_steps_needed, 5);
00011
00012 ros::service::waitForService("step_plan_request");
00013
00014
00015 generate_feet_pose_client = nh.serviceClient<msgs::GenerateFeetPoseService>("generate_feet_pose");
00016 step_plan_request_client = nh.serviceClient<vigir_footstep_planning_msgs::StepPlanRequestService>("step_plan_request");
00017
00018
00019 execute_step_plan_ac.reset(new actionlib::SimpleActionClient<msgs::ExecuteStepPlanAction>("execute_step_plan", true));
00020
00021 reset();
00022 }
00023
00024 PatternGenerator::~PatternGenerator()
00025 {}
00026
00027 msgs::ErrorStatus PatternGenerator::generatePattern(const msgs::StepPlanRequest& step_plan_request, msgs::StepPlan& step_plan)
00028 {
00029
00030 msgs::StepPlanRequestService step_plan_request_srv;
00031 step_plan_request_srv.request.plan_request = step_plan_request;
00032
00033
00034 if (!step_plan_request_client.call(step_plan_request_srv.request, step_plan_request_srv.response))
00035 return ErrorStatusError(msgs::ErrorStatus::ERR_UNKNOWN, "[PatternGenerator]", "Can't call footstep planner!");
00036
00037
00038 if (step_plan_request_srv.response.status.error == msgs::ErrorStatus::NO_ERROR)
00039 step_plan = step_plan_request_srv.response.step_plan;
00040
00041 return step_plan_request_srv.response.status;
00042 }
00043
00044 void PatternGenerator::reset()
00045 {
00046 joy_d_step = geometry_msgs::Pose();
00047 joy_d_step.orientation = tf::createQuaternionMsgFromYaw(0.0);
00048
00049 last_performed_step_index = 0;
00050 first_changeable_step_index = 0;
00051 next_step_index_needed = 0;
00052
00053 start_feet_pose.reset();
00054 foot_start_step_index_left = 0;
00055 foot_start_step_index_right = 0;
00056 has_new_steps = false;
00057
00058 clearStepPlan();
00059
00060 params.enable = false;
00061 }
00062
00063 void PatternGenerator::setParams(const msgs::PatternGeneratorParameters& params)
00064 {
00065 if (isEnabled() && params.enable)
00066 {
00067
00068 bool result = true;
00069 if (isSimulationMode())
00070 result = setNextStartStepIndex(last_performed_step_index+1);
00071 else
00072 result = setNextStartStepIndex(first_changeable_step_index-1);
00073
00074 if (!result)
00075 {
00076 ROS_ERROR("[PatternGenerator] setParams: Replanning failed due to unknown start step.");
00077 reset();
00078 }
00079 }
00080 else
00081 {
00082
00083 setEnabled(params.enable);
00084 }
00085
00086 this->params = params;
00087 }
00088
00089 void PatternGenerator::setEnabled(bool enable)
00090 {
00091
00092 if (!isEnabled() && enable)
00093 {
00094 reset();
00095 }
00096
00097 else if (isEnabled() && !enable)
00098 {
00099 bool result = true;
00100 if (isSimulationMode())
00101 result = setNextStartStepIndex(last_performed_step_index+1);
00102 else
00103 result = setNextStartStepIndex(first_changeable_step_index-1);
00104
00105 if (result)
00106 generateSteps(0, true);
00107 }
00108
00109 params.enable = enable;
00110 }
00111
00112 bool PatternGenerator::isEnabled() const
00113 {
00114 return params.enable;
00115 }
00116
00117 bool PatternGenerator::isSimulationMode() const
00118 {
00119 return params.simulation_mode;
00120 }
00121
00122 bool PatternGenerator::hasSteps() const
00123 {
00124 return !newest_step_plan.steps.empty();
00125 }
00126
00127 bool PatternGenerator::hasNewSteps() const
00128 {
00129 return !newest_step_plan.steps.empty() && has_new_steps;
00130 }
00131
00132 void PatternGenerator::getCompleteStepPlan(msgs::StepPlan& step_plan) const
00133 {
00134 step_plan = complete_step_plan;
00135 }
00136
00137 void PatternGenerator::getNewestStepPlan(msgs::StepPlan& step_plan) const
00138 {
00139 has_new_steps = false;
00140 step_plan = newest_step_plan;
00141 }
00142
00143 bool PatternGenerator::setNextStartStepIndex(int step_index)
00144 {
00145 if (step_index < 0)
00146 return false;
00147 else if (!updateFeetStartPoseByStepMap(step_map, step_index-1) || !updateFeetStartPoseByStepMap(step_map, step_index))
00148 return false;
00149
00150 return true;
00151 }
00152
00153 int PatternGenerator::getNextStartStepIndex() const
00154 {
00155 return std::max(foot_start_step_index_left, foot_start_step_index_right);
00156 }
00157
00158 void PatternGenerator::clearStepPlan()
00159 {
00160 complete_step_plan = msgs::StepPlan();
00161 newest_step_plan = msgs::StepPlan();
00162 step_map.clear();
00163 }
00164
00165 void PatternGenerator::update(const ros::TimerEvent& timer)
00166 {
00167
00168 if (joystick_handler && params.joystick_mode)
00169 {
00170 double yaw = tf::getYaw(joy_d_step.orientation);
00171
00172 bool enable;
00173 joystick_handler->updateJoystickCommands((timer.current_real - timer.last_real).toSec(), enable, joy_d_step.position.x, joy_d_step.position.y, yaw);
00174 joy_d_step.orientation = tf::createQuaternionMsgFromYaw(yaw);
00175
00176 setEnabled(enable);
00177 }
00178
00179
00180 if (!isEnabled())
00181 return;
00182
00183
00184 int queued_steps = getNextStartStepIndex() - last_performed_step_index;
00185 if (queued_steps < static_cast<int>(number_of_steps_needed))
00186 generateSteps(number_of_steps_needed-queued_steps);
00187
00188 if (isSimulationMode())
00189 last_performed_step_index++;
00190 }
00191
00192 void PatternGenerator::updateLastPerformedStepIndex(int last_performed_step_index)
00193 {
00194 if (!isSimulationMode())
00195 {
00196 if (last_performed_step_index < 0)
00197 {
00198 ROS_ERROR("[PatternGenerator] updateLastPerformedStepIndex: Stopping due to invalid step indx %i", last_performed_step_index);
00199 reset();
00200 }
00201
00202 this->last_performed_step_index = last_performed_step_index;
00203 }
00204 }
00205
00206 void PatternGenerator::updateFirstChangeableStepIndex(int first_changeable_step_index)
00207 {
00208 if (!isSimulationMode())
00209 {
00210 if (first_changeable_step_index < 0)
00211 {
00212 ROS_ERROR("[PatternGenerator] updateFirstChangeableStepIndex: Stopping due to invalid step indx %i", first_changeable_step_index);
00213 setEnabled(false);
00214 }
00215
00216 this->first_changeable_step_index = first_changeable_step_index;
00217 }
00218 }
00219
00220 void PatternGenerator::updateFeetStartPose(uint8_t foot_index, const geometry_msgs::Pose& pose)
00221 {
00222 msgs::Foot foot;
00223 foot.header.frame_id = world_frame_id;
00224 foot.header.stamp = ros::Time::now();
00225 foot.foot_index = foot_index;
00226 foot.pose = pose;
00227 updateFeetStartPose(foot);
00228 }
00229
00230 void PatternGenerator::updateFeetStartPose(const msgs::Foot& foot)
00231 {
00232 if (!start_feet_pose)
00233 {
00234 start_feet_pose.reset(new msgs::Feet());
00235 start_feet_pose->header = foot.header;
00236 start_feet_pose->left.header = foot.header;
00237 start_feet_pose->left.foot_index = msgs::Foot::LEFT;
00238 start_feet_pose->right.header = foot.header;
00239 start_feet_pose->right.foot_index = msgs::Foot::RIGHT;
00240 }
00241
00242 if (foot.foot_index == msgs::Foot::LEFT)
00243 {
00244 start_feet_pose->left.header = foot.header;
00245 start_feet_pose->left = foot;
00246 }
00247 if (foot.foot_index == msgs::Foot::RIGHT)
00248 {
00249 start_feet_pose->right.header = foot.header;
00250 start_feet_pose->right = foot;
00251 }
00252 }
00253
00254 void PatternGenerator::updateFeetStartPose(const msgs::Feet& feet)
00255 {
00256 updateFeetStartPose(feet.left);
00257 updateFeetStartPose(feet.right);
00258
00259 start_feet_pose->header = feet.header;
00260 }
00261
00262 void PatternGenerator::updateFeetStartPose(const msgs::Step& step)
00263 {
00264 updateFeetStartPose(step.foot);
00265
00266 start_feet_pose->header = step.header;
00267 if (step.foot.foot_index == msgs::Foot::LEFT)
00268 foot_start_step_index_left = step.step_index;
00269 if (step.foot.foot_index == msgs::Foot::RIGHT)
00270 foot_start_step_index_right = step.step_index;
00271 }
00272
00273 bool PatternGenerator::updateFeetStartPoseByStepMap(const std::map<unsigned int, msgs::Step>& map, unsigned int step_index)
00274 {
00275 std::map<unsigned int, msgs::Step>::const_iterator itr = map.find(step_index);
00276 if (itr != map.end())
00277 {
00278 updateFeetStartPose(itr->second);
00279 return true;
00280 }
00281 return false;
00282 }
00283
00284 void PatternGenerator::updateFootstepMap(std::map<unsigned int, msgs::Step>& map, const std::vector<msgs::Step>& vec) const
00285 {
00286 std::vector<msgs::Step>::const_iterator itr = vec.begin();
00287
00288 if (!map.empty())
00289 itr++;
00290
00291 for (; itr != vec.end(); itr++)
00292 map[itr->step_index] = *itr;
00293 }
00294
00295 void PatternGenerator::mapToVectorIndexed(const std::map<unsigned int, msgs::Step>& map, std::vector<msgs::Step>& vec, unsigned int start_index, unsigned int end_index) const
00296 {
00297 double foot_z = 0.0;
00298
00299 vec.clear();
00300 for (unsigned int step_index = start_index; step_index <= end_index; step_index++)
00301 {
00302 std::map<unsigned int, msgs::Step>::const_iterator itr = map.find(step_index);
00303
00304
00305 if (itr == map.end())
00306 break;
00307
00308 msgs::Step step = itr->second;
00309
00311 if (step_index == start_index)
00312 foot_z = step.foot.pose.position.z;
00313 else
00314 step.foot.pose.position.z = foot_z;
00315 vec.push_back(step);
00316 }
00317 }
00318
00319 void PatternGenerator::generateSteps(unsigned int n, bool close_step)
00320 {
00321 msgs::StepPlanRequestService step_plan_request_srv;
00322 msgs::StepPlanRequest& req = step_plan_request_srv.request.plan_request;
00323
00324 if (!start_feet_pose)
00325 {
00326 std_msgs::Header header;
00327 header.frame_id = world_frame_id;
00328 header.stamp = ros::Time::now();
00329 msgs::Feet start_feet;
00330 determineStartFeetPose(start_feet, generate_feet_pose_client, header);
00331 updateFeetStartPose(start_feet);
00332 }
00333
00334
00335 geometry_msgs::Pose d_step = params.d_step;
00336 if (params.joystick_mode)
00337 d_step = joy_d_step;
00338
00339 tf::Quaternion q_tf;
00340 tf::quaternionMsgToTF(d_step.orientation, q_tf);
00341
00342 double roll, pitch, yaw;
00343 tf::Matrix3x3(q_tf).getRPY(roll, pitch, yaw);
00344
00345
00346 unsigned int next_moving_foot_index = msgs::Foot::LEFT;
00347 if (getNextStartStepIndex() == 0)
00348 {
00349 if (d_step.position.y < 0.0)
00350 next_moving_foot_index = msgs::Foot::LEFT;
00351 else if (d_step.position.y == 0.0 && yaw < 0.0)
00352 next_moving_foot_index = msgs::Foot::RIGHT;
00353 }
00354 else
00355 {
00356 if (foot_start_step_index_left > foot_start_step_index_right)
00357 next_moving_foot_index = msgs::Foot::RIGHT;
00358 else
00359 next_moving_foot_index = msgs::Foot::LEFT;
00360 }
00361
00362
00363 req.header = start_feet_pose->header;
00364 req.start = *start_feet_pose;
00365 switch (next_moving_foot_index)
00366 {
00367 case msgs::Foot::LEFT:
00368 req.start_step_index = foot_start_step_index_right;
00369 req.start_foot_selection = msgs::StepPlanRequest::LEFT;
00370 break;
00371 case msgs::Foot::RIGHT:
00372 req.start_step_index = foot_start_step_index_left;
00373 req.start_foot_selection = msgs::StepPlanRequest::RIGHT;
00374 break;
00375 default:
00376 ROS_ERROR("[PatternGenerator] Unknown foot index '%u'", next_moving_foot_index);
00377 return;
00378 }
00379
00380
00381 if (n == 0)
00382 {
00383 if (next_moving_foot_index == msgs::Foot::LEFT)
00384 req.pattern_parameters.mode = msgs::PatternParameters::FEET_REALIGN_ON_RIGHT;
00385 else
00386 req.pattern_parameters.mode = msgs::PatternParameters::FEET_REALIGN_ON_LEFT;
00387 }
00388 else
00389 {
00390 req.pattern_parameters.steps = n;
00391 req.pattern_parameters.step_distance_forward = d_step.position.x;
00392 req.pattern_parameters.step_distance_sideward = d_step.position.y;
00393 req.pattern_parameters.turn_angle = yaw;
00394 req.pattern_parameters.close_step = close_step;
00395 req.pattern_parameters.extra_seperation = false;
00396 req.pattern_parameters.override = false;
00397 req.pattern_parameters.roll = roll;
00398 req.pattern_parameters.pitch = pitch;
00399 req.pattern_parameters.mode = msgs::PatternParameters::SAMPLING;
00400 }
00401
00402 req.planning_mode = msgs::StepPlanRequest::PLANNING_MODE_PATTERN;
00403 req.parameter_set_name = params.parameter_set_name;
00404
00405
00406 if (!step_plan_request_client.call(step_plan_request_srv.request, step_plan_request_srv.response))
00407 {
00408 ROS_ERROR("[PatternGenerator] Can't call footstep planner!");
00409 return;
00410 }
00411
00412
00413 if (!step_plan_request_srv.response.step_plan.steps.size())
00414 return;
00415
00416 updateFootstepMap(step_map, step_plan_request_srv.response.step_plan.steps);
00417
00418 if (complete_step_plan.steps.empty())
00419 complete_step_plan = step_plan_request_srv.response.step_plan;
00420 else
00421 mapToVectorIndexed(step_map, complete_step_plan.steps, 0, step_plan_request_srv.response.step_plan.steps.back().step_index);
00422
00423 newest_step_plan = step_plan_request_srv.response.step_plan;
00424 newest_step_plan.header.stamp = ros::Time::now();
00425 newest_step_plan.header.seq++;
00426 has_new_steps = true;
00427
00428 if (!setNextStartStepIndex(newest_step_plan.steps.back().step_index))
00429 {
00430 ROS_ERROR("[PatternGenerator] generateSteps: Last step index of recent pattern was wrong. Resetting now!");
00431 reset();
00432 }
00433 }
00434 }