Move an arm with motion constraints
Welding requires the torch to follow a straight line. Carrying a cup of water
requires the end effector to stay level. The motion planner’s default behavior
satisfies neither: it finds any collision-free path, which typically curves
through intermediate poses and tilts the end effector along the way.
Constraints let you bound what the planner will accept.
Prerequisites
- A running machine with an arm and frame system configured
- Familiarity with Move arm to pose
Steps
1. Welding: straight-line tool path
Use a LinearConstraint to keep the end effector within a tolerance of the
direct line between start and goal.
from viam.services.motion import MotionClient
from viam.proto.service.motion import Constraints, LinearConstraint
from viam.proto.common import PoseInFrame, Pose
motion_service = MotionClient.from_robot(machine, "builtin")
constraints = Constraints(
linear_constraint=[
LinearConstraint(line_tolerance_mm=5.0)
]
)
destination = PoseInFrame(
reference_frame="world",
pose=Pose(x=400, y=200, z=300, o_x=0, o_y=0, o_z=-1, theta=0)
)
await motion_service.move(
component_name="my-arm",
destination=destination,
constraints=constraints
)
import "go.viam.com/rdk/motionplan"
constraints := &motionplan.Constraints{
LinearConstraint: []motionplan.LinearConstraint{
{LineToleranceMm: 5.0},
},
}
_, err = motionService.Move(ctx, motion.MoveReq{
ComponentName: "my-arm",
Destination: destination,
Constraints: constraints,
})
2. Carrying a liquid: level end effector
Use an OrientationConstraint to keep the end effector level (or at any
fixed orientation) throughout the motion.
from viam.proto.service.motion import OrientationConstraint
constraints = Constraints(
orientation_constraint=[
OrientationConstraint(orientation_tolerance_degs=5.0)
]
)
await motion_service.move(
component_name="my-arm",
destination=destination,
constraints=constraints
)
constraints := &motionplan.Constraints{
OrientationConstraint: []motionplan.OrientationConstraint{
{OrientationToleranceDegs: 5.0},
},
}
3. Combine constraints
Linear and orientation constraints compose: pass both in the same Constraints
object and the planner enforces both simultaneously. This is the usual setup
for welding and other tasks that require a straight-line path plus a fixed tool
orientation.
# Straight line, level orientation
constraints = Constraints(
linear_constraint=[
LinearConstraint(line_tolerance_mm=5.0)
],
orientation_constraint=[
OrientationConstraint(orientation_tolerance_degs=3.0)
]
)
constraints := &motionplan.Constraints{
LinearConstraint: []motionplan.LinearConstraint{
{LineToleranceMm: 5.0},
},
OrientationConstraint: []motionplan.OrientationConstraint{
{OrientationToleranceDegs: 3.0},
},
}
4. Use proportional tolerances
PseudolinearConstraint scales the tolerance with the motion distance. Useful
when the same code handles both short and long moves.
from viam.proto.service.motion import PseudolinearConstraint
constraints = Constraints(
pseudolinear_constraint=[
PseudolinearConstraint(
line_tolerance_factor=0.1,
orientation_tolerance_factor=0.1
)
]
)
constraints := &motionplan.Constraints{
PseudolinearConstraint: []motionplan.PseudolinearConstraint{
{
LineToleranceFactor: 0.1,
OrientationToleranceFactor: 0.1,
},
},
}
Tips
- Constraints and obstacles compete. If an obstacle blocks the straight-line path, no path satisfies both the constraint and the collision check, so the planner returns no-path. Widen the constraint or move the obstacle.
- Orientation is checked against the nearer endpoint. The planner compares the current orientation to the start and goal, then uses whichever is closer as the reference. This lets the constraint track intent as the motion progresses rather than locking to one endpoint.
For tolerance selection guidance and more on planning cost, see the Performance considerations section in the constraints reference.
What’s next
- Configure motion constraints: full reference for all four constraint types.
- Allow frame collisions: the fourth constraint type, for letting specific frame pairs touch.
- Plan collision-free paths: combine constraints with obstacle avoidance.
Was this page helpful?
Glad to hear it! If you have any other feedback please let us know:
We're sorry about that. To help us improve, please tell us what we can do better:
Thank you!