---
title: "Generate text-driven skeletal animations for an already-rigged 3D model. Pass the rigged GLB in `model` (URL or base64) and a motion `prompt` (e.g. \"walking\", \"swinging its axe\"). The model must already have a skeleton — rig it first via the rig endpoint if not. Synchronous: returns num_variants candidate animations (default 4), each a standalone animation-only GLB (skeleton + one clip, no mesh) in `glb_url` plus an mp4 `preview_url`, so you can pick the best one and fuse it with your model in a game engine or three.js. mode selects the representation — rot_trans (default, most faithful) or rot_only (for retargeting). Animation quality is hit-or-miss, which is why multiple candidates are returned. Credits are charged once per call regardless of variant count, only on success. Requires an API key (user scope)."
method: POST
path: "/assets/3d-model/animate"
tags: ["3D Models"]
---

# Generate text-driven skeletal animations for an already-rigged 3D model. Pass the rigged GLB in `model` (URL or base64) and a motion `prompt` (e.g. "walking", "swinging its axe"). The model must already have a skeleton — rig it first via the rig endpoint if not. Synchronous: returns num_variants candidate animations (default 4), each a standalone animation-only GLB (skeleton + one clip, no mesh) in `glb_url` plus an mp4 `preview_url`, so you can pick the best one and fuse it with your model in a game engine or three.js. mode selects the representation — rot_trans (default, most faithful) or rot_only (for retargeting). Animation quality is hit-or-miss, which is why multiple candidates are returned. Credits are charged once per call regardless of variant count, only on success. Requires an API key (user scope).

`POST /assets/3d-model/animate`

## Request body

- Animate3DModelPayload
  - `model` string, required — URL or base64-encoded already-rigged GLB to animate. Rig it first via the rig endpoint if it has no skeleton.
  - `prompt` string, required — Desired motion, e.g. "walking" or "swinging its axe".
  - `mode` 'rot_trans' | 'rot_only' — Animation representation: rot_trans (per-bone rotation+translation, most faithful) or rot_only (rotation + root translation only, for retargeting).
  - `num_variants` integer — Number of candidate animations to generate; each returned as a standalone animation-only GLB with an mp4 preview.
  - `loop` boolean — Return to the initial pose: each clip plays forward then mirrors back to the rest pose for a seamless loop. Best for one-way motions (crouch, punch, wave); reads oddly for cyclic gaits like walking.
  - `augment_prompt` boolean — Rewrite the prompt into a detailed motion caption with an LLM (recommended).
  - `request_id` string — Optional client-provided id to retrieve the result later.

## Response `200`

Success

- AnimationCandidates
  - `animations` AnimationClip[]
    - `clip_name` string
    - `prompt` string
    - `preset_id` string — Set when the clip came from the preset library (retargeting) rather than a text prompt.
    - `mode` 'rot_trans' | 'rot_only'
    - `seed` integer
    - `glb_url` string
    - `preview_url` string
    - `motion` number, float
    - `fit_rmse` number, float

## Other responses

- `400` — Error

---

[API](https://skmtc.net/ludo/apis/ludo-ai-api.md) · [All operations](https://skmtc.net/ludo/apis/ludo-ai-api/llms.txt) · [OpenAPI document](https://skmtc-service-staging.skmtc.workers.dev/v1/apis/ludo/ludo-ai-api/revisions/3af866d68651/schema)
