Skip to content

Commit 3bd2735

Browse files
committed
Add examples for lecture 05
1 parent f5f3421 commit 3bd2735

15 files changed

+4020
-0
lines changed

Diff for: lecture_05/01_plan_cartesian_motion_ros_loader.py

+25
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
from compas.geometry import Frame
2+
from compas_fab.backends import RosClient
3+
from compas_fab.robots import Configuration
4+
5+
with RosClient('localhost') as client:
6+
robot = client.load_robot()
7+
group = robot.main_group_name
8+
9+
frames = []
10+
frames.append(Frame([0.3, 0.1, 0.5], [1, 0, 0], [0, 1, 0]))
11+
frames.append(Frame([0.5, 0.1, 0.6], [1, 0, 0], [0, 1, 0]))
12+
13+
start_configuration = Configuration.from_revolute_values([-0.042, 0.033, -2.174, 5.282, -1.528, 0.000])
14+
15+
trajectory = robot.plan_cartesian_motion(frames,
16+
start_configuration,
17+
group=group,
18+
options=dict(
19+
max_step=0.01,
20+
avoid_collisions=True,
21+
))
22+
23+
print("Computed cartesian path with %d configurations, " % len(trajectory.points))
24+
print("following %d%% of requested trajectory." % (trajectory.fraction * 100))
25+
print("Executing this path at full speed would take approx. %.3f seconds." % trajectory.time_from_start)
+28
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
from compas.geometry import Frame
2+
from compas_fab.backends import RosClient
3+
from compas_fab.robots import Configuration
4+
from helpers import show_trajectory
5+
6+
with RosClient('localhost') as client:
7+
robot = client.load_robot()
8+
group = robot.main_group_name
9+
10+
frames = []
11+
frames.append(Frame([0.3, 0.1, 0.5], [1, 0, 0], [0, 1, 0]))
12+
frames.append(Frame([0.5, 0.1, 0.6], [1, 0, 0], [0, 1, 0]))
13+
14+
start_configuration = Configuration.from_revolute_values([-0.042, 0.033, -2.174, 5.282, -1.528, 0.000])
15+
16+
trajectory = robot.plan_cartesian_motion(frames,
17+
start_configuration,
18+
group=group,
19+
options=dict(
20+
max_step=0.01,
21+
avoid_collisions=True,
22+
))
23+
24+
print("Computed cartesian path with %d configurations, " % len(trajectory.points))
25+
print("following %d%% of requested trajectory." % (trajectory.fraction * 100))
26+
print("Executing this path at full speed would take approx. %.3f seconds." % trajectory.time_from_start)
27+
28+
show_trajectory(trajectory)

Diff for: lecture_05/03_plan_motion_ros_loader.py

+28
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
import math
2+
from compas.geometry import Frame
3+
from compas_fab.backends import RosClient
4+
from compas_fab.robots import Configuration
5+
6+
with RosClient('localhost') as client:
7+
robot = client.load_robot()
8+
group = robot.main_group_name
9+
10+
frame = Frame([0.4, 0.3, 0.4], [0, 1, 0], [0, 0, 1])
11+
tolerance_position = 0.001
12+
tolerance_axes = [math.radians(1)] * 3
13+
14+
start_configuration = Configuration.from_revolute_values([-0.042, 4.295, 0, -3.327, 4.755, 0.])
15+
16+
# create goal constraints from frame
17+
goal_constraints = robot.constraints_from_frame(frame,
18+
tolerance_position,
19+
tolerance_axes,
20+
group)
21+
22+
trajectory = robot.plan_motion(goal_constraints,
23+
start_configuration,
24+
group,
25+
options=dict(planner_id='RRT'))
26+
27+
print("Computed kinematic path with %d configurations." % len(trajectory.points))
28+
print("Executing this path at full speed would take approx. %.3f seconds." % trajectory.time_from_start)

Diff for: lecture_05/04_plan_motion_ros_loader_viz.py

+31
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
import math
2+
from compas.geometry import Frame
3+
from compas_fab.backends import RosClient
4+
from compas_fab.robots import Configuration
5+
from helpers import show_trajectory
6+
7+
with RosClient('localhost') as client:
8+
robot = client.load_robot()
9+
group = robot.main_group_name
10+
11+
frame = Frame([0.4, 0.3, 0.4], [0, 1, 0], [0, 0, 1])
12+
tolerance_position = 0.001
13+
tolerance_axes = [math.radians(1)] * 3
14+
15+
start_configuration = Configuration.from_revolute_values([-0.042, 4.295, 0, -3.327, 4.755, 0.])
16+
17+
# create goal constraints from frame
18+
goal_constraints = robot.constraints_from_frame(frame,
19+
tolerance_position,
20+
tolerance_axes,
21+
group)
22+
23+
trajectory = robot.plan_motion(goal_constraints,
24+
start_configuration,
25+
group,
26+
options=dict(planner_id='RRT'))
27+
28+
print("Computed kinematic path with %d configurations." % len(trajectory.points))
29+
print("Executing this path at full speed would take approx. %.3f seconds." % trajectory.time_from_start)
30+
31+
show_trajectory(trajectory)

Diff for: lecture_05/07_add_collision_mesh.py

+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
import time
2+
3+
from compas.datastructures import Mesh
4+
5+
import compas_fab
6+
from compas_fab.backends import RosClient
7+
from compas_fab.robots import CollisionMesh
8+
from compas_fab.robots import PlanningScene
9+
10+
with RosClient('localhost') as client:
11+
robot = client.load_robot()
12+
13+
scene = PlanningScene(robot)
14+
mesh = Mesh.from_stl(compas_fab.get('planning_scene/floor.stl'))
15+
cm = CollisionMesh(mesh, 'floor')
16+
scene.add_collision_mesh(cm)
17+
18+
# sleep a bit before terminating the client
19+
#time.sleep(1)
20+
21+
#scene.remove_collision_mesh('floor')
22+

Diff for: lecture_05/08_append_collision_meshes.py

+26
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
import time
2+
3+
from compas.datastructures import Mesh
4+
from compas.geometry import Box, Translation
5+
6+
from compas_fab.backends import RosClient
7+
from compas_fab.robots import CollisionMesh
8+
from compas_fab.robots import PlanningScene
9+
10+
with RosClient('localhost') as client:
11+
robot = client.load_robot()
12+
scene = PlanningScene(robot)
13+
14+
brick = Box.from_width_height_depth(0.016, 0.012, 0.031)
15+
brick.transform(Translation.from_vector([0, 0, brick.zsize / 2.]))
16+
17+
for i in range(5):
18+
mesh = Mesh.from_shape(brick)
19+
cm = CollisionMesh(mesh, 'brick_wall')
20+
cm.frame.point.y += 0.5
21+
cm.frame.point.z += brick.zsize * i
22+
23+
scene.append_collision_mesh(cm)
24+
25+
# sleep a bit before terminating the client
26+
time.sleep(1)

Diff for: lecture_05/09_remove_collision_mesh.py

+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
import time
2+
3+
from compas_fab.backends import RosClient
4+
from compas_fab.robots import PlanningScene
5+
6+
with RosClient('localhost') as client:
7+
robot = client.load_robot()
8+
scene = PlanningScene(robot)
9+
scene.remove_collision_mesh('brick_wall')
10+
scene.remove_collision_mesh('floor')
11+
12+
# sleep a bit before terminating the client
13+
time.sleep(1)

Diff for: lecture_05/10_attach_tool.py

+32
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
import os
2+
import time
3+
4+
from compas_fab.backends import RosClient
5+
from compas_fab.robots import PlanningScene
6+
from compas_fab.robots import Tool
7+
8+
from compas.datastructures import Mesh
9+
from compas.geometry import Frame
10+
11+
HERE = os.path.dirname(__file__)
12+
13+
# create tool from mesh and frame
14+
mesh = Mesh.from_stl(os.path.join(HERE, 'vacuum_gripper.stl'))
15+
frame = Frame([0.07, 0, 0], [0, 0, 1], [0, 1, 0])
16+
tool = Tool(mesh, frame)
17+
tool.to_json(os.path.join(HERE, 'vacuum_gripper.json'))
18+
19+
20+
with RosClient('localhost') as client:
21+
robot = client.load_robot()
22+
scene = PlanningScene(robot)
23+
robot.attach_tool(tool)
24+
25+
# add attached tool to planning scene
26+
scene.add_attached_tool()
27+
28+
# now we can convert frames at robot's tool tip and flange
29+
frames_tcf = [Frame((-0.309, -0.046, -0.266), (0.276, 0.926, -0.256), (0.879, -0.136, 0.456))]
30+
frames_tcf0 = robot.from_tcf_to_t0cf(frames_tcf)
31+
32+
time.sleep(1)

Diff for: lecture_05/11_detach_tool.py

+24
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import os
2+
import time
3+
4+
from compas_fab.backends import RosClient
5+
from compas_fab.robots import PlanningScene
6+
from compas_fab.robots import Tool
7+
8+
HERE = os.path.dirname(__file__)
9+
tool = Tool.from_json(os.path.join(HERE, 'vacuum_gripper.json'))
10+
11+
with RosClient('localhost') as client:
12+
robot = client.load_robot()
13+
scene = PlanningScene(robot)
14+
15+
# Attach the tool
16+
robot.attach_tool(tool)
17+
scene.add_attached_tool()
18+
time.sleep(1)
19+
20+
# Remove the tool
21+
scene.remove_attached_tool()
22+
scene.remove_collision_mesh(tool.name)
23+
robot.detach_tool()
24+
time.sleep(1)
+38
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
import os
2+
from compas.geometry import Frame
3+
from compas_fab.backends import RosClient
4+
from compas_fab.robots import Configuration
5+
from compas_fab.robots import Tool
6+
7+
# create tool from json
8+
HERE = os.path.dirname(__file__)
9+
filepath = os.path.join(HERE, 'vacuum_gripper.json')
10+
tool = Tool.from_json(filepath)
11+
12+
element_height = 0.014
13+
approach_distance = 0.05
14+
15+
with RosClient('localhost') as client:
16+
robot = client.load_robot()
17+
18+
# 1. Set tool
19+
robot.attach_tool(tool)
20+
21+
# 2. Define start configuration
22+
start_configuration = Configuration.from_revolute_values([-5.961, 4.407, -2.265, 5.712, 1.571, -2.820])
23+
24+
# 3. Define frames
25+
picking_frame = Frame([-0.43, 0, element_height], [1, 0, 0], [0, 1, 0])
26+
approach_picking_frame = Frame([-0.43, 0, element_height + approach_distance], [1, 0, 0], [0, 1, 0])
27+
frames = [picking_frame, approach_picking_frame]
28+
29+
# 4. Convert frames to tool0_frames
30+
frames_tool0 = robot.from_tcf_to_t0cf(frames)
31+
32+
trajectory = robot.plan_cartesian_motion(frames_tool0,
33+
start_configuration,
34+
options=dict(max_step=0.01))
35+
36+
print("Computed cartesian path with %d configurations, " % len(trajectory.points))
37+
print("following %d%% of requested trajectory." % (trajectory.fraction * 100))
38+
print("Executing this path at full speed would take approx. %.3f seconds." % trajectory.time_from_start)

Diff for: lecture_05/README.md

+38
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
# COMPAS II: Path planning
2+
3+
Cartesian and kinematic path planning using MoveIt.
4+
5+
Planning scene operations.
6+
7+
End effectors.
8+
9+
Pick and Place processes with discrete building elements.
10+
11+
👉 [Slides](lecture_05.pdf)
12+
📜 [Assignment 04](assignment_04/README.md)
13+
14+
## Examples
15+
16+
Make sure you start (`compose up`) the container with a UR5 planner for these examples. You can use
17+
either [the one with browser-based UI](..\docker\moveit\docker-compose.yml) or
18+
the [lightweight version of it without UI]((..\docker\ur5-planner\docker-compose.yml)).
19+
20+
* Path planning with MoveIt
21+
* [Cartesian motion planning](01_plan_cartesian_motion_ros_loader.py)
22+
* [Cartesian motion planning + graphs](02_plan_cartesian_motion_ros_loader_viz.py)
23+
* [Free space motion planning](03_plan_motion_ros_loader.py)
24+
* [Free space motion planning + graphs](04_plan_motion_ros_loader_viz.py)
25+
* [Constraints](05_constraints.py)
26+
27+
* Planning scene in MoveIt
28+
* [Add objects to the scene](07_add_collision_mesh.py)
29+
* [Append nested objects to the scene](08_append_collision_meshes.py)
30+
* [Remove objects from the scene](09_remove_collision_mesh.py)
31+
32+
* Pick and place process
33+
* [Attach tool][10_attach_tool.py]
34+
* [Detach tool][11_detach_tool.py]
35+
* [Plan cartesian motion with tool][12_plan_cartesian_motion_with_attached_tool.py]
36+
37+
* MoveIt & Grasshopper
38+
* [Planning playground](16_robot_example.ghx)

Diff for: lecture_05/assignment_04/README.md

+52
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
# Assignment 04
2+
3+
4+
## How to start
5+
6+
Use the following code as a starting point for your assignment:
7+
8+
```python
9+
```
10+
11+
## Expected result
12+
13+
14+
## How to submit your assignment
15+
16+
1. Make sure you have forked this repository already, if not, check [assignment submission instructions in lecture 02](../../lecture_02/assignment_01#how-to-submit-your-assignment).
17+
2. Make sure your local clone is up to date on the `main` branch
18+
19+
(compas-fs2021) git checkout main
20+
(compas-fs2021) git pull origin
21+
22+
3. Use a branch called `assignment-04` for this week's assignment
23+
24+
(compas-fs2021) git checkout -b assignment-04
25+
(compas-fs2021) git push -u assignments assignment-04
26+
27+
4. Create a folder with your name and last name, eg. `elvis_presley` (make sure it is inside the current assignment folder)
28+
5. Create a Python file named `assignment_04.py` and paste the starting point code.
29+
6. For visual inspection, **copy** the file `solution_viewer.ghx` in the same folder of your `assignment_04.py`.
30+
6. Solve the coding assignment and commit
31+
<details><summary><small>(How do I commit?)</small></summary>
32+
<p>
33+
34+
Usually, commits are done from a visual client or VS code,
35+
but you can also commit your changes from the command line:
36+
37+
(compas-fs2021) git add lecture_05/assignment_04/elvis_presley/\* && git commit -m "hello world"
38+
39+
40+
</p>
41+
</details>
42+
43+
8. Once you're ready to submit, push the changes:
44+
45+
(compas-fs2021) git push assignments
46+
47+
9. And create a pull request (<small>[What's a pull request?](https://docs.github.com/en/github/collaborating-with-issues-and-pull-requests/about-pull-requests)</small>)
48+
49+
1. Open your browser and go to your fork
50+
2. Create the pull request clicking `Compare & pull request` and follow the instructions
51+
52+
![Start a pull request](../../.github/pull-request.png)

0 commit comments

Comments
 (0)