MoveIt Task Constructor
What is MoveIt Task Constructor?
MTC Stages
There are three possible stages relating to the result flow:
Generators
Propagators
Connectors
Generator Stage
CurrentState
, which gets the current robot state as the starting point for a planning pipeline.GeneratePose
. It usually monitors a CurrentState
or ModifyPlanningScene
stage. By monitoring the solutions of CurrentState
, the GeneratePose
stage can find the object or frame around which it should generate poses.Propagating Stage
Move Relative
to a pose. This stage is commonly used to approach close to an object to pick.Connecting Stage
Wrapper
Compute IK
for Generate Grasp Pose
stage. A Generate Grasp Pose
stage will produce cartesian pose solutions. By wrapping an Compute IK
stage around Generate Pose
stage, the cartesian pose solutions from Generate Pose
stage can be used to produce IK solutions (i.e) produce joint state configuration of robot to reach the poses.MTC Containers
Currently available containers:
Serial
Parallel
Serial Container
Parallel Container
Parallel containers combine a set of stages to allow planning alternate solutions.
Initializing a MTC Task
The top-level planning problem is specified as a MTC Task and the subproblems which are specified by Stages are added to the MTC task object.
auto node = std::make_shared<rclcpp::Node>();
auto task = std::make_unique<moveit::task_constructor::Task>();
task->loadRobotModel(node);
// Set controllers used to execute robot motion. If not set, MoveIt has controller discovery logic.
task->setProperty("trajectory_execution_info", "joint_trajectory_controller gripper_controller");
Adding containers and stages to a MTC Task
Adding a stage to MTC task
auto current_state = std::make_unique<moveit::task_constructor::stages::CurrentState>("current_state");
task->add(std::move(current_state));
Containers derive from Stage and hence containers can be added to MTC task similarly
auto container = std::make_unique<moveit::task_constructor::SerialContainer>("Pick Object");
// TODO: Add stages to the container before adding the container to MTC task
task->add(std::move(container));
Setting planning solvers
Stages that do motion planning need solver information.
Solvers available in MTC
PipelinePlanner
- Uses MoveIt’s planning pipelineJointInterpolation
- Interpolates between the start and goal joint states. It does not support complex motions.CartesianPath
- Moves the end effector in a straight line in Cartesian space.
Code Example on how to initialize the solver
const auto mtc_pipeline_planner = std::make_shared<moveit::task_constructor::solvers::PipelinePlanner>(
node, "ompl", "RRTConnectkConfigDefault");
const auto mtc_joint_interpolation_planner =
std::make_shared<moveit::task_constructor::solvers::JointInterpolationPlanner>();
const auto mtc_cartesian_planner = std::make_shared<moveit::task_constructor::solvers::CartesianPath>();
These solvers will be passed into stages like MoveTo
, MoveRelative
, and Connect
.
Setting Properties
void setProperty(const std::string& name, const boost::any& value);
Cost calculator for Stages
CostTerm is the basic interface to compute costs for solutions for MTC stages.
CostTerm implementations available in MTC
Constant
- Adds a constant cost to each solutionPathLength
- Cost depends on trajectory length with optional weight for different jointsTrajectoryDuration
- Cost depends on execution duration of the whole trajectoryTrajectoryCostTerm
- Cost terms that only work on SubTrajectory solutionsLambdaCostTerm
- Pass in a lambda expression to calculate costDistanceToReference
- Cost depends on weighted joint space distance to a reference pointLinkMotion
- Cost depends on length of Cartesian trajectory of a linkClearance
- Cost is inverse of distance to collision
Example code on how to set CostTerm using LambdaCostTerm
stage->setCostTerm(moveit::task_constructor::LambdaCostTerm(
[](const moveit::task_constructor::SubTrajectory& traj) { return 100 * traj.cost(); }));
All stages provided by MTC have default cost terms. Stages which produce trajectories as solutions usually use path length to calculate cost.
Planning and Executing a MTC Task
Planning an MTC task will return a MoveItErrorCode
.
Refer here to identity the different error types.
If planning succeeds, you can expect the plan function to return moveit_msgs::msg::MoveItErrorCodes::SUCCESS
.
auto error_code = task.plan()
After planning, extract the first successful solution and pass it to the execute function. This will create an execute_task_solution
action client.
The action server resides in the execute_task_solution_capability
plugin provided by MTC.
The plugin extends MoveGroupCapability
. It constructs a MotionPlanRequest
from the MTC solution and uses MoveIt’s PlanExecution
to actuate the robot.
auto result = task.execute(*task.solutions().front());
Links to Additional Information
Here is a tutorial on how to create a Pick and Place pipeline using MTC.
The links listed below contain more information on stages and containers provided by MTC