Skip to content

compas_fab.ghpython ¤

Grasshopper (GHPython) scene objects and component helpers for compas_fab.

Scene objects (RobotCellObject, RigidBodyObject, etc.) expose compas_fab data structures to Grasshopper while keeping the data layer separated from CAD-specific code and leveraging native Rhino/Grasshopper performance.

Alongside them are the helpers the Cf_* components call to register models into a cell (register_models_into_cell), auto-build per-joint sliders (ensure_joint_sliders), cache scene objects across solves (cache_scene_object), and auto-create dropdowns (ensure_value_list) or boolean toggles (ensure_boolean_toggle) on component inputs.

Value-list dropdowns come in two flavours:

  • ensure_value_list — fire-and-forget, for static option sets (e.g. the fixed list of robots in RobotCellLibrary). Creates the value list when nothing is wired, then never touches it again.

  • ensure_dynamic_value_list — for options that depend on upstream data (e.g. the keys of cell.tool_models). Tracks the value list it created via scriptcontext.sticky and refreshes its items whenever the option set changes. Defers the canvas mutation to a ScheduleSolution(delay, callback) callback so the rebuild happens between solves rather than expiring downstream consumers mid-solve.

Classes¤

MoveItPlannerOptions ¤

MoveItPlannerOptions(
    urdf_param_name: str | None = None,
    srdf_param_name: str | None = None,
    http_file_server_base_url: str | None = None,
)

Advanced load options for the MoveIt Planner Grasshopper component.

Produced by the MoveIt Planner Options component and consumed by the MoveIt Planner component. Bundling the rarely-changed parameters into one object keeps them off the planner component in the common case, where no options need to be set at all.

This is a plain (non-iterable) class on purpose: a dict or namedtuple would be exploded into its keys/items as it travels over a Grasshopper wire, whereas a class instance crosses the wire as a single opaque object.

Every field is optional; an unset field falls back to the backend default in RosClient.load_robot_cell.

Parameters:

  • urdf_param_name (str | None, default: None ) –

    ROS parameter / topic name for the URDF. Defaults to /robot_description.

  • srdf_param_name (str | None, default: None ) –

    ROS parameter / topic name for the SRDF. Defaults to /robot_description_semantic.

  • http_file_server_base_url (str | None, default: None ) –

    ROS 2 only: base URL of the HTTP file server hosting package:// meshes.

Methods:¤

to_load_kwargs ¤
to_load_kwargs() -> dict

Return only the set fields as kwargs for RosClient.load_robot_cell.

ReachabilityMapObject ¤

ReachabilityMapObject(reachability_map, **kwargs)

Scene object for drawing a reachability map.

Parameters:

  • reachability_map (:class:`compas_robots.ReachabilityMap`) –

    Robot model.

  • **kwargs (dict, default: {} ) –

    Additional keyword arguments.

Methods:¤

draw_cloud ¤
draw_cloud(colormap='viridis', points=None)

Returns the points and colors to create a point cloud.

The colors are calculated on the score at the respective frame. If the frames are a 2D list, the point of the first frame of the list is used.

Parameters:

  • colormap (str, default: 'viridis' ) –

    The colormap for the point cloud.

  • points (list of :class:`compas.geometry.Points`, default: None ) –

    Points to override the points from the reachability map.

draw_frames ¤
draw_frames(ik_index=None)

Returns the frames of the reachability map.

Parameters:

  • ik_index (int, default: None ) –

    If passed, returns only the reachable frames at a given IK index. For a 6-axis industrial robot this index reaches from 0 to 7 (8 solutions).

RigidBodyObject ¤

RigidBodyObject(
    draw_visual=True, draw_collision=False, native_scale=1.0, *args, **kwargs
)

Scene object for drawing a RigidBody in GHPython.

RobotCellObject ¤

RobotCellObject(
    draw_visual=True, draw_collision=False, native_scale=1.0, *args, **kwargs
)

Scene object for drawing a RobotCell in GHPython.

RobotModelObject ¤

RobotModelObject(
    draw_visual: bool = True,
    draw_collision: bool = False,
    native_scale: float = 1.0,
    *args,
    **kwargs,
)

Scene object for drawing a Robot Model in GHPython.

Functions:¤

cache_scene_object ¤

cache_scene_object(model, kwargs, components, sceneobject_type=None, debug=False)

Creates or retrieves a SceneObject from the sticky cache.

This is intended for caching RobotCellObjects and their constituent SceneObjects.

If the SceneObject is not in the cache, it will be created and stored in the cache. The SceneObject is created using compas.scene.Scene.add(model, **kwargs).

The cache scope is limited to the current component instance, such as a Grasshopper component. Meaning that it is possible to have multiple cached SceneObjects in the same GH document, allowing multiple visualizations of the same model.

Parameters:

  • model (object) –

    The model for which the SceneObject is created.

  • kwargs (dict) –

    The keyword arguments to be passed to the SceneObject creation.

  • components (`ghpythonlib.componentbase.executingcomponent`) –

    The components instance. Use self in advanced (SDK) mode and ghenv.Components otherwise.

  • debug (bool, default: False ) –

    If True, debug messages will be printed. Default is False.

Returns:

  • SceneObject

    The SceneObject created or retrieved from the cache.

collision_diagnostic ¤

collision_diagnostic(planner, state, group=None)

A concise one-line hint about why planning/IK failed, via a collision check.

Runs planner.check_collision(state) and summarises the result:

  • in collision -> "start state in collision: a<->b, c<->d, +N more"
  • collision-free -> "start state collision-free (likely unreachable)"
  • planner has no collision check -> None (caller reports the bare error)

Never raises: a diagnostic must not mask the real failure.

Parameters:

  • planner

    The planner to query (any backend).

  • state

    The robot cell state to check (typically the planning start_state).

  • group

    Optional planning group to check. Defaults to the planner's main group.

Returns:

  • str or None

ensure_boolean_toggle ¤

ensure_boolean_toggle(
    component: IGH_Component,
    input_name: str,
    default: bool = True,
    x_offset: float = 30,
    y_offset: float = 0,
) -> None

Create and wire a Boolean Toggle to a component input if nothing is connected.

No-op if the input already has a source connected. Safe to call on every RunScript invocation (creation is deferred and de-duplicated, so repeated recomputes do not stack up toggles). Gives a boolean input a one-click on/off widget on the canvas instead of forcing the user to wire a separate toggle.

Parameters:

  • component (IGH_Component) –

    The hosting component. Pass ghenv.Component.

  • input_name (str) –

    The Name of the input parameter to attach to.

  • default (bool, default: True ) –

    The toggle's initial value. Defaults to True.

  • x_offset (float, default: 30 ) –

    x_offset is the gap (px) between the toggle's right edge and the input; y_offset nudges it vertically. Placed just to the left of the input, vertically centred on it.

  • y_offset (float, default: 30 ) –

    x_offset is the gap (px) between the toggle's right edge and the input; y_offset nudges it vertically. Placed just to the left of the input, vertically centred on it.

ensure_dynamic_value_list ¤

ensure_dynamic_value_list(
    component: IGH_Component,
    input_name: str,
    options: Iterable[str],
    signature_key: str | None = None,
    x_offset: float = 30,
    y_offset: float = 0,
) -> None

Maintain a Value List on input_name whose items reflect options.

Unlike ensure_value_list, this variant tracks the VL it created (sticky-cached by the component's InstanceGuid and signature_key) and re-populates its items whenever the options set changes between solves. Use this when the available choices come from upstream data — e.g. the keys of cell.tool_models for a "pick a tool" dropdown.

Behaviour:

  • If a non-VL source is already wired to input_name, the helper does nothing — the user provided their own value.
  • If a VL is wired AND we tracked it AND the items don't match options, the items are refreshed.
  • If nothing is wired, a fresh VL is created and added to the canvas, then a follow-up solve is scheduled so the value flows on the next pass.

All mutation (creating the VL, updating items, expiring the component) runs inside a doc.ScheduleSolution(delay, callback) callback to avoid "X expired during a solution" warnings on downstream consumers.

Parameters:

  • component (IGH_Component) –

    Pass ghenv.Component.

  • input_name (str) –

    Name of the input parameter to attach a VL to.

  • options (Iterable[str]) –

    Current option set the VL should expose. Empty means "skip".

  • signature_key (str | None, default: None ) –

    Suffix used to identify the tracked VL in sticky. Override only when a single component manages more than one dynamic VL.

  • x_offset (float, default: 30 ) –

    x_offset is the gap (px) between the value list's right edge and the input; y_offset nudges it vertically. Placed just left of the input.

  • y_offset (float, default: 30 ) –

    x_offset is the gap (px) between the value list's right edge and the input; y_offset nudges it vertically. Placed just left of the input.

ensure_joint_sliders ¤

ensure_joint_sliders(
    component, robot_model, input_name="joints", signature_key="joint_signature"
)

Wire one Number Slider per configurable joint into the named list input.

On first call (or when the model's joint signature changes), this helper deletes any previously auto-wired sliders on the target input and creates a fresh bank — one GH_NumberSlider per configurable joint, in canonical order, with ranges set to each joint's limits. All sliders are wired to a single list-access input named input_name.

No reading of slider values is necessary: the calling script declares input_name in its RunScript signature and receives the values as a plain Python list of floats via the standard GH solve path.

Parameters:

  • component (IGH_Component) –

    Pass ghenv.Component.

  • robot_model (RobotModel) –

    The model to derive joint metadata from.

  • input_name (str, default: 'joints' ) –

    Name of the static list-access input the sliders are wired into. Must exist on the component. Defaults to "joints".

  • signature_key (str, default: 'joint_signature' ) –

    Sticky key suffix used to remember the last installed joint signature on this component. Override if the same component manages multiple slider banks.

Returns:

  • list of (joint_name, joint_type, default_value) tuples in canonical
  • joint order. Use this for the configuration's `joint_names` /
  • `joint_types`, and as a fallback when the `joints` list isn't yet
  • populated (e.g. the very first solve before the scheduled follow-up).

ensure_value_list ¤

ensure_value_list(
    component: IGH_Component,
    input_name: str,
    options: Iterable[str],
    default: str | None = None,
    x_offset: float = 30,
    y_offset: float = 0,
) -> None

Create and wire a Value List to a component input if nothing is connected.

No-op if the input already has a source connected. Safe to call on every RunScript invocation (creation is deferred and de-duplicated, so repeated recomputes do not stack up value lists).

Parameters:

  • component (IGH_Component) –

    The hosting component. Pass ghenv.Component.

  • input_name (str) –

    The Name of the input parameter to attach to.

  • options (Iterable[str]) –

    The string options to populate the Value List with.

  • default (str | None, default: None ) –

    If provided and present in options, that item is pre-selected.

  • x_offset (float, default: 30 ) –

    x_offset is the gap (px) between the value list's right edge and the input; y_offset nudges it vertically. The value list is placed just to the left of the input, vertically centred on it.

  • y_offset (float, default: 30 ) –

    x_offset is the gap (px) between the value list's right edge and the input; y_offset nudges it vertically. The value list is placed just to the left of the input, vertically centred on it.

register_models_into_cell ¤

register_models_into_cell(
    component,
    robot_cell: RobotCell,
    tools: list[ToolModel] | None = None,
    rigid_bodies: list[RigidBody] | None = None,
) -> RobotCell | None

Return a deepcopy of robot_cell with the given tools and rigid bodies registered.

Tools are keyed by tool.name; rigid bodies by body.name. The input cell is never mutated, so a sticky-cached base cell can be passed safely. Missing or duplicate ids are reported via :func:compas_ghpython.error on component and skipped.

Parameters:

  • component

    The Grasshopper component (ghenv.Component) used to surface errors.

  • robot_cell (RobotCell) –

    The base cell to copy and extend.

  • tools (list[ToolModel] | None, default: None ) –

    Tools to register. Each must have a non-empty .name.

  • rigid_bodies (list[RigidBody] | None, default: None ) –

    Rigid bodies to register. Each must have a non-empty .name.

Returns:

  • class:`compas_fab.robots.RobotCell`

    A new cell with the models registered. If robot_cell is None, returns None.