Skip to content

Commit bebbf0f

Browse files
committed
Some GH Examples
1 parent 1f541a5 commit bebbf0f

6 files changed

Lines changed: 155 additions & 5 deletions

docs/frontends/ghpython/02_modify_configuration_interactively.rst

Lines changed: 109 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,23 +4,127 @@
44
Interactively modify Robot Configuration and Visualization
55
==============================================================
66

7-
The following example shows how to visualize a robot from the COMPAS FAB library in Grasshopper.
8-
All the code is placed in a single Python Script component for simplicity.
7+
The following example shows how to interactively modify the robot configuration
8+
and visualize it in Grasshopper.
9+
10+
Because loading the robot cell and the initial draw by the visualization
11+
function can take some time, this example splits the process into three
12+
Custom Python components:
13+
14+
1. **Load Robot Cell**: This component loads the robot cell and its initial state.
15+
2. **Modify Robot Configuration**: This component allows you to modify the robot's configuration interactively from slider inputs.
16+
3. **Visualize Robot**: This component visualizes the robot with the modified robot_cell_state.
17+
18+
By splitting the workflow into these three components, the user can avoid
19+
reloading the robot cell when changing the robot configuration.
20+
21+
22+
.. figure:: files/02_modify_configuration_interactively.jpg
23+
:figclass: figure
24+
:class: figure-img img-fluid
25+
26+
Three Custom Python components in Grasshopper to modify and visualize a robot configuration.
27+
28+
29+
Load Robot Cell
30+
==========================
31+
The first component loads the robot cell from the `RobotCellLibrary`.
932

1033
.. code-block:: python
1134
1235
# r: compas_fab
1336
# venv: compas_fab
14-
1537
from compas_fab.robots import RobotCellLibrary
16-
from compas.scene import Scene
1738
1839
# Load the robot model
1940
robot_cell, robot_cell_state = RobotCellLibrary.ur5()
2041
42+
43+
Modify Robot Configuration
44+
==========================
45+
46+
The second component modifies the joint values of the default
47+
robot configuration.
48+
Note that we make a copy of the `robot_cell_state` before modifying it.
49+
This avoid modifying the original state object that maybe connected to
50+
other components in Grasshopper.
51+
52+
.. code-block:: python
53+
54+
# venv: compas_fab
55+
56+
robot_cell_state_out = robot_cell_state.copy()
57+
robot_cell_state_out.robot_configuration.joint_values[0] = j0
58+
robot_cell_state_out.robot_configuration.joint_values[1] = j1
59+
robot_cell_state_out.robot_configuration.joint_values[2] = j2
60+
robot_cell_state_out.robot_configuration.joint_values[3] = j3
61+
robot_cell_state_out.robot_configuration.joint_values[4] = j4
62+
robot_cell_state_out.robot_configuration.joint_values[5] = j5
63+
64+
65+
Visualization with Cached Scene Object in Grasshopper
66+
============================================================
67+
68+
The visualization component can be as simple as before by using the
69+
`Scene` class from COMPAS and calling the `draw` method on the
70+
`SceneObject`. A simple example consist of the following code:
71+
72+
.. code-block:: python
73+
74+
# venv: compas_fab
75+
from compas.scene import Scene
76+
2177
# Create a scene object for visualization
2278
scene = Scene()
2379
scene_object = scene.add(robot_cell)
2480
2581
# Visualize the robot in the COMPAS Viewer or other CAD environment
26-
native_geometry = scene_object.draw(robot_cell_state)
82+
native_geometry = scene_object.draw(robot_cell_state)
83+
84+
However, this approach can be inefficient because the draw function
85+
rebuilds the native geometry when it called the first time.
86+
To improve performance, especially when the robot configuration changes frequently,
87+
it is recommended to cache the scene object in the Grasshopper component
88+
using the `scriptcontext.sticky` dictionary.
89+
The subsequent modifications to the robot configuration can then reuse the cached
90+
`SceneObject` without needing to redraw the entire robot model.
91+
The code for the third component with caching looks like this:
92+
93+
.. code-block:: python
94+
95+
# venv: compas_fab
96+
97+
from scriptcontext import sticky
98+
from compas_ghpython import create_id
99+
from compas.scene import Scene
100+
101+
# Create hash (scope limited to this component) for caching SceneObject
102+
object_hash = str(id(robot_cell))
103+
gh_component = ghenv.Component
104+
cache_id = create_id(gh_component, object_hash)
105+
106+
# If scene object exist in sticky, retrieve it
107+
scene_object = None
108+
if sticky.has_key(cache_id):
109+
scene_object = sticky[cache_id]
110+
# Double check if the item is the same
111+
if scene_object.item is robot_cell:
112+
print("SceneObject '{}' reused for '{}'".format(type(scene_object).__name__, type(robot_cell).__name__))
113+
else:
114+
scene_object = None
115+
116+
# Create Scene Object and cache it
117+
if scene_object is None:
118+
scene = Scene()
119+
scene_object = scene.add(robot_cell)
120+
print("SceneObject {} newly created for {}".format(type(scene_object).__name__, type(robot_cell).__name__))
121+
sticky[cache_id] = scene_object
122+
123+
# The draw method is the same as before
124+
native_geometry = scene_object.draw(robot_cell_state)
125+
126+
127+
Example Files
128+
=================
129+
You can download the example file:
130+
* :download:`Interactive Configuration (Grasshopper) (.GH) <files/02_modify_configuration_interactively.gh>`
Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
.. _gh_modify_configuration_interactively:
2+
3+
==============================================================
4+
Plan Motion and Visualize Trajectory
5+
==============================================================
6+
7+
The following example shows how to interactively modify the robot configuration
8+
and visualize it in Grasshopper.
9+
10+
11+
Plan Motion
12+
===========
13+
14+
.. code-block:: python
15+
16+
# venv: compas_fab
17+
from compas_fab.robots import ConfigurationTarget
18+
19+
# Create Configuration Target
20+
configuration_target = ConfigurationTarget(target_configuration)
21+
22+
# Plan motion to the target configuration
23+
trajectory = planner.plan_motion(configuration_target, start_state)
24+
25+
Convert Trajectory to Configuration to Robot Cell State
26+
==============================================================
27+
28+
The returned trajectory from the planner is a list of points,
29+
the following code allows you to retrieve one of the points
30+
and merge it with the robot cell state for visualization.
31+
32+
.. code-block:: python
33+
34+
from compas_robots import Configuration
35+
36+
# Convert fraction number to index of trajectory point
37+
config_index = round(fraction * (len(trajectory.points)-1))
38+
print(config_index)
39+
40+
# The start_configuration of the trajectory has names and joint type info
41+
configuration = trajectory.start_configuration.copy()
42+
configuration.joint_values = trajectory.points[config_index].joint_values
43+
44+
# Merge configuration with a copy of the state
45+
robot_cell_state_out = start_state.copy()
46+
robot_cell_state_out.robot_configuration.merge(configuration)
Binary file not shown.
102 KB
Loading
15.9 KB
Binary file not shown.
-1.86 KB
Binary file not shown.

0 commit comments

Comments
 (0)