Skip to main content

Utilities to programatically create MuJoCo XML configuration files

Project description

mjxml

Programmatic, type-checked helpers for composing MuJoCo XML. Define assets and worldbody elements in Python (with Pydantic validation), serialize to XML, and write files you can load in MuJoCo.

Highlights

  • Strong typing and validation via Pydantic v2.
  • Easy XML serialization: to_xml(), to_xml_str(), write().
  • Assets: TextureAsset, MeshAsset, HFieldAsset, ModelAsset.
  • Bodies: Geom (with many MuJoCo attributes), WorldBody base.
  • Utilities: Defaults blocks, rotation helpers, and runtime type protocols.

Requirements

  • Python >= 3.13
  • Runtime deps: numpy, pydantic

Install

From PyPI:

pip install mjxml

Development

This project relies on uv. To setup a virtual environment, just do:

uv sync --dev
export PYTHONPATH=src

Quickstart

The snippets below sketch a typical flow: create assets, place them in the worldbody, and export a MuJoCo XML file.

1. Define assets with validation

from mjxml.asset.texture import TextureAsset
from mjxml.asset.mesh import MeshAsset

texture = TextureAsset(
    name="tex_grid",
    file="albedo.png",
    type="2d",
    colorspace="srgb",
    content_type="image/png",
    nchannel=3,
)

mesh = MeshAsset(
    name="m_cube",
    file="cube.obj",
    content_type="model/obj",
    scale=[1.0, 1.0, 1.0],
    inertia="exact",
)

Each asset only emits the attributes you set; Pydantic validators ensure parameters such as nchannel or scale stay within MuJoCo’s requirements.

2. Create bodies and geoms

from mjxml.body import Body, Geom

body = Body(name="torso")
body.add(
    Geom(
        name="box1",
        type="box",
        size=[0.5, 0.5, 0.5],
        material=None,
        rgba=[0.8, 0.2, 0.2, 1.0],
        friction=[0.5, 0.1, 0.01],
    )
)

Geoms automatically infer fields such as condim from the friction vector length and warn when MuJoCo would ignore an attribute.

3. Assemble a complete MujocoModel

from mjxml.model import MujocoModel

model = MujocoModel(name="demo")
model.add_asset(texture)
model.add_asset(mesh)
model.add_body(body)

root = model.to_xml()
print(model.to_xml_str())
model.write("scene.xml")

MujocoModel deduplicates identical assets, appends worldbody, actuator, and contact sections, and returns a ready-to-save ElementTree root.

Testing

Run the unit tests with pytest.

pytest -q -s

Status

This repository is under active development; expect minor API adjustments. A high-level MujocoModel aggregator is planned but not yet included.

Roadmap

  • [✅] High-level Wrapper: MujocoModel class to aggregate assets, worldbody, and other sections.
  • [✅] Body Elements: Support for joint, site, camera.
  • [=] Sections: Support for actuator, sensor, equality, contact, tendon.
  • [❌] IO: Parsing existing XML files for round-trip editing.
  • [❌] Docs: Comprehensive API documentation and more examples.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

mjxml-0.2.0.tar.gz (22.5 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

mjxml-0.2.0-py3-none-any.whl (32.4 kB view details)

Uploaded Python 3

File details

Details for the file mjxml-0.2.0.tar.gz.

File metadata

  • Download URL: mjxml-0.2.0.tar.gz
  • Upload date:
  • Size: 22.5 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for mjxml-0.2.0.tar.gz
Algorithm Hash digest
SHA256 e264701f90d69d34063f31fe25cae041ad3d7ec4d3c4dd9fb18a2d4afba234f1
MD5 5dd9ad16de04c3664aeee8306bfa4aea
BLAKE2b-256 f414240665793df08f4c74557bf10edbfb8ebad891b28155ba63cebcbc2260fb

See more details on using hashes here.

File details

Details for the file mjxml-0.2.0-py3-none-any.whl.

File metadata

  • Download URL: mjxml-0.2.0-py3-none-any.whl
  • Upload date:
  • Size: 32.4 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for mjxml-0.2.0-py3-none-any.whl
Algorithm Hash digest
SHA256 da567c5a85c889507417acdf590b625f9899b5673f942fc014a394cfdc93fcea
MD5 b2e5465af3543b41cf98aca2c731c545
BLAKE2b-256 41d8e227aa41b068c16df54d320f31b1bb483e8a806f83b4e59ba9fc7e800ced

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page