Use when designing, adding, or reviewing public API for the Newton physics engine — class names, method signatures, type hints, docstrings, or parameter conventions. Also use when unsure if new API conforms to project conventions.
Detailed patterns that supplement AGENTS.md. Read AGENTS.md first for the basics (prefix-first naming, PEP 604, Google-style docstrings, SI units, Sphinx cross-refs).
All ModelBuilder.add_shape_* methods follow this parameter order:
def add_shape_cone(
self,
body: int,
xform: Transform | None = None,
# shape-specific params here (radius, height, etc.)
radius: float = 0.5,
height: float = 1.0,
cfg: ShapeConfig | None = None,
as_site: bool = False,
label: str | None = None,
custom_attributes: dict[str, Any] | None = None,
) -> int:
"""Adds a cone collision shape to a body.
Args:
body: Index of the parent body. Use -1 for static shapes.
xform: Transform in parent body's local frame. If ``None``,
identity transform is used.
radius: Cone base radius [m].
height: Cone height [m].
cfg: Shape configuration. If ``None``, uses
:attr:`default_shape_cfg`.
as_site: If ``True``, creates a site instead of a collision shape.
label: Optional label for identifying the shape.
custom_attributes: Dictionary of custom attribute names to values.
Returns:
Index of the newly added shape.
"""
Key conventions:
xform (not tf, transform, or pose) — always Transform | None = Nonecfg (not config, shape_config) — always ShapeConfig | None = Nonebody, label, custom_attributes — standard params on all builder methodsNone, not constructed objects like wp.transform()Use IntEnum (not Enum with strings) for enumerations:
class Model:
class AttributeAssignment(IntEnum):
MODEL = 0
STATE = 1
When an IntEnum includes a NONE member, define it first at 0:
class GeoType(IntEnum):
NONE = 0
PLANE = 1
HFIELD = 2
This keeps the sentinel value stable and leaves room to append future real
members at the end instead of inserting them before a trailing NONE.
Dataclass field docstrings go on the line immediately below the field:
@dataclass
class ShapeConfig:
density: float = 1000.0
"""The density of the shape material."""
ke: float = 2.5e3
"""The contact elastic stiffness."""
Document shape, dtype, and units in attribute docstrings:
"""Rigid body velocities [m/s, rad/s], shape (body_count,), dtype :class:`spatial_vector`."""
"""Joint forces [N or N·m], shape (joint_dof_count,), dtype float."""
"""Contact points [m], shape [count, 3], float."""
For compound arrays, list per-component units:
"""[0] k_mu [Pa], [1] k_lambda [Pa], ..."""
For public API attributes and method signatures, use bare wp.array | None and document the concrete dtype in the docstring (e.g., dtype :class:\vec3`). Warp kernel parameters require concrete dtypes inline (wp.array(dtype=wp.vec3)`) per AGENTS.md.
When reviewing new API, verify:
xform, cfg, body, label)None, not constructed objectsIntEnum with int valuesNONE define NONE = 0 firstas_site, label, custom_attributes