> ## Documentation Index
> Fetch the complete documentation index at: https://docs.viggle.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Create Motion

> Create a reusable Motion from a driving video.

Creates an asynchronous Motion asset. Poll the returned ID until it is `ready` before using it as `motion_id` in a Render.

## Request parameters

Send `multipart/form-data`.

| Parameter          | Type   | Required | Default | Description                                       |
| ------------------ | ------ | :------: | ------- | ------------------------------------------------- |
| `motion_video`     | file   |  One of  | —       | Driving video uploaded from the client.           |
| `motion_video_url` | string |  One of  | —       | Publicly reachable URL for the driving video.     |
| `name`             | string |    No    | `""`    | Optional label displayed when listing the Motion. |

Provide exactly one of `motion_video` or `motion_video_url`.

## Response parameters

Returns `200 OK` with a Motion object.

| Field          | Type            | Always present | Description                                                           |
| -------------- | --------------- | :------------: | --------------------------------------------------------------------- |
| `id`           | string          |       Yes      | Public Motion ID beginning with `mot_`. Store it exactly as returned. |
| `status`       | string          |       Yes      | Normally `queued`; terminal values are `ready` and `failed`.          |
| `name`         | string          |       Yes      | Supplied label, or an empty string.                                   |
| `progress`     | integer or null |       Yes      | Progress from 0 to 100 when available.                                |
| `capabilities` | string\[]       |       Yes      | Empty until ready; ready Motions include `video_render`.              |
| `created_at`   | string or null  |       Yes      | ISO 8601 creation timestamp when available.                           |
| `completed_at` | string or null  |       Yes      | ISO 8601 completion timestamp; `null` before completion.              |
| `error`        | object or null  |       Yes      | Structured failure details when status is `failed`.                   |

```json theme={null}
{"id":"mot_550e8400-e29b-41d4-a716-446655440000","status":"queued","name":"Dance loop","progress":0,"capabilities":[],"created_at":"2026-07-21T10:00:00Z","completed_at":null,"error":null}
```

## Examples

<CodeGroup>
  ```go Go theme={null}
  file, _ := os.Open("dance.mp4"); defer file.Close()
  body := &bytes.Buffer{}; writer := multipart.NewWriter(body)
  part, _ := writer.CreateFormFile("motion_video", "dance.mp4"); io.Copy(part, file)
  writer.WriteField("name", "Dance loop"); writer.Close()
  req, _ := http.NewRequest("POST", "https://apis.viggle.ai/v1/motions", body)
  req.Header.Set("Authorization", "Bearer "+os.Getenv("VIGGLE_API_KEY")); req.Header.Set("Content-Type", writer.FormDataContentType())
  resp, err := http.DefaultClient.Do(req); if err != nil { panic(err) }; defer resp.Body.Close()
  ```

  ```javascript JavaScript theme={null}
  const form = new FormData(); form.append("motion_video", videoFile); form.append("name", "Dance loop");
  const response = await fetch("https://apis.viggle.ai/v1/motions", {method:"POST", headers:{Authorization:`Bearer ${process.env.VIGGLE_API_KEY}`}, body:form});
  const motion = await response.json();
  ```

  ```python Python theme={null}
  import os, requests
  with open("dance.mp4", "rb") as video:
      response = requests.post("https://apis.viggle.ai/v1/motions", headers={"Authorization": f"Bearer {os.environ['VIGGLE_API_KEY']}"}, files={"motion_video": video}, data={"name": "Dance loop"})
  response.raise_for_status(); motion = response.json()
  ```

  ```bash cURL theme={null}
  curl -X POST "https://apis.viggle.ai/v1/motions" -H "Authorization: Bearer $VIGGLE_API_KEY" -F "motion_video=@dance.mp4" -F "name=Dance loop"
  ```
</CodeGroup>

## Next step

Use [Get Motion](/v1/api-reference/motions/get) to poll the ID.


## OpenAPI

````yaml POST /v1/motions
openapi: 3.0.3
info:
  title: Viggle API
  description: Generate AI-powered character animation videos
  version: 2.0.0
  contact:
    name: Viggle Support
    url: https://viggle.ai
servers:
  - url: https://apis.viggle.ai
    description: Production server
security: []
paths:
  /v1/motions:
    post:
      summary: Create Motion
      operationId: v1CreateMotion
      responses:
        '200':
          description: Motion

````