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

# Message Bubbles

> A text conversation floating in the room next to you, one bubble popping in after another, each pinned in 3D space so it foreshortens and parallaxes as the camera moves.

A text conversation floating in the room next to you, one bubble popping in after another, each pinned in 3D space so it foreshortens and parallaxes as the camera moves. Real iMessage geometry: blue sent bubbles right-aligned with the flick tail, grey replies on the left, sender and time above each, frosted-glass finish by default. Turn the sound on: every message lands with a soft chime. Ask for the Android look and your sent bubbles turn Apple's SMS green.

## See it

<Tabs>
  <Tab title="Output">
    <video controls muted loop playsinline preload="metadata" width="100%" poster="https://d7qhwxmzzmnbz.cloudfront.net/builtin-skills/message-bubbles/example-imessage-v1-poster.jpg" src="https://d7qhwxmzzmnbz.cloudfront.net/builtin-skills/message-bubbles/example-imessage-v1.mp4" />

    One phone recording in (placed on the desk, then the camera settles); the default conversation out, in the iMessage style. The first bubble pops while the camera is still moving, so you can see the thread hold its place in the room.
  </Tab>

  <Tab title="Your input video">
    <video controls muted loop playsinline preload="metadata" width="100%" poster="https://d7qhwxmzzmnbz.cloudfront.net/builtin-skills/message-bubbles/material-poster-v1.jpg" src="https://d7qhwxmzzmnbz.cloudfront.net/builtin-skills/message-bubbles/material-v1.mp4" />
  </Tab>

  <Tab title="Android style">
    <video controls muted loop playsinline preload="metadata" width="100%" src="https://d7qhwxmzzmnbz.cloudfront.net/builtin-skills/message-bubbles/example-android-v1.mp4" />

    The same clip and the same camera solve, rendered in the Android bubble style — green sent bubbles instead of blue. Ask for it with `style`.
  </Tab>

  <Tab title="Side by side">
    <Columns cols={2}>
      <Frame caption="Your input video">
        <video controls muted loop playsinline preload="metadata" style={{width:"100%",aspectRatio:"16 / 9",objectFit:"contain",background:"rgba(127,127,127,0.10)",borderRadius:"6px"}} poster="https://d7qhwxmzzmnbz.cloudfront.net/builtin-skills/message-bubbles/material-poster-v1.jpg" src="https://d7qhwxmzzmnbz.cloudfront.net/builtin-skills/message-bubbles/material-v1.mp4" />
      </Frame>

      <Frame caption="Output">
        <video controls muted loop playsinline preload="metadata" style={{width:"100%",aspectRatio:"16 / 9",objectFit:"contain",background:"rgba(127,127,127,0.10)",borderRadius:"6px"}} poster="https://d7qhwxmzzmnbz.cloudfront.net/builtin-skills/message-bubbles/example-imessage-v1-poster.jpg" src="https://d7qhwxmzzmnbz.cloudfront.net/builtin-skills/message-bubbles/example-imessage-v1.mp4" />
      </Frame>
    </Columns>
  </Tab>
</Tabs>

## Material

One person in a room with texture around them (desk, window, shelves), up to 30 seconds. The camera should move: a slow orbit, a walk-in, or even the settling pull-back after you place the phone is enough, and it is what makes the thread feel like it is hanging in the air. A locked-off tripod shot still works (the bubbles simply hold their place) but shows the effect at its least. Your body is masked out of the tracking, so you can move freely.

## Spec

| Field        | Type                           | Required | Description                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| ------------ | ------------------------------ | -------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `messages`   | array                          | **yes**  | 2 to 6 messages in order. Each: `from` (sender name for the label), `text` (one or two lines; emoji welcome), `dir` (`out` = sent by the person on camera, blue, tail bottom-right; `in` = a reply, grey, tail bottom-left). The default conversation is the person texting AskEditor and AskEditor making the very bubbles you are watching. Message cadence follows the reference (about 1.2 to 1.5 s apart) unless you pass `at` seconds per message. |
| `style`      | enum (`imessage` \| `android`) | no       | `imessage` (default): sent bubbles in Apple's iMessage blue. `android`: sent bubbles in Apple's SMS green, the way an Android contact's thread looks on an iPhone. Replies are grey in both.                                                                                                                                                                                                                                                             |
| `finish`     | enum (`glass` \| `flat`)       | no       | `glass` (default): frosted backdrop blur, translucent tint, hairline and soft shadow, one continuous silhouette including the tail. `flat`: opaque, exactly like the phone.                                                                                                                                                                                                                                                                              |
| `stabilizer` | number                         | no       | Gimbal cutoff in Hz, default 2. The bubbles follow camera motion slower than this and have inertia against anything faster, with no lag. 1.5 for slow cinematic orbits; do not go below 1 (the thread starts gliding away from the room).                                                                                                                                                                                                                |

## Pricing & timing

|              |                                                                                 |
| ------------ | ------------------------------------------------------------------------------- |
| **Delivery** | **File** — an mp4 at `outputUrl`, plus an editable canvas                       |
| Price        | 100 credits: [estimate](/docs/setting-up/jobs-and-polling) is free and authoritative |
| Typical run  | \~300s                                                                          |
| Review gate  | No: runs straight through                                                       |

## Refusals this template can return

* `NO_SUBJECT`
* `NO_TRACKABLE_BACKGROUND`
* `MATERIAL_TOO_LONG`
* `UNREADABLE`
* `BAD_SPEC`

Refusals are free and typed: see [Refusals](/docs/setting-up/refusals).

## Run it

<Tabs>
  <Tab title="curl (REST)">
    ```bash theme={null}
    # 1. mint an upload ticket, then put the file against it
    curl -X POST https://api.askeditor.com/v1/uploads \
      -H "Authorization: Bearer $ASKEDITOR_API_KEY" \
      -H "Content-Type: application/json" -d '{"purpose":"message-bubbles"}'
    # → { "ticket": "upl_…", "uploadUrl": "…" }

    curl -X POST https://api.askeditor.com/v1/uploads/{ticket}/file \
      -F "file=@./recording.mp4"
    # → { "material": "mat_…" }

    # 2. submit the run
    curl -X POST https://api.askeditor.com/api/message-bubbles/jobs \
      -H "Authorization: Bearer $ASKEDITOR_API_KEY" \
      -H "Content-Type: application/json" \
      -d '{ "material": "mat_…", "clientRequestId": "your-own-id", "messages": … }'
    # → { "jobId": "…", "envelopeId": "message-bubbles:…", "credits": { "quoted": 100, "charged": 0 } }

    # 3. poll until it resolves
    curl https://api.askeditor.com/v1/jobs/{envelopeId} \
      -H "Authorization: Bearer $ASKEDITOR_API_KEY"
    ```

    `clientRequestId` is **required**: reuse the same value on a retry and you
    cannot be charged twice for the same run.
  </Tab>

  <Tab title="Agent (MCP)">
    Connected via the [MCP connector](/docs/mcp/connect)? It is one sentence:

    > "Run the **Message Bubbles** template on \~/Desktop/recording.mp4"

    The agent lists the menu, estimates (free), asks your consent, uploads, runs,
    and polls [`GET /v1/jobs/{id}`](/docs/setting-up/jobs-and-polling) to the finished
    envelope.
  </Tab>
</Tabs>

**Editable delivery:** Delivers the finished mp4 with the chimes mixed under your audio. The editable form (each bubble as a live element carrying its 3D track, plus the solved camera so you can add messages later) ships with the bubble element; until then the copy is baked.

<Note>
  The tracking is a real camera solve, not a 2D sticker track: the bubbles are planes fixed in the room, so they foreshorten and drift against the background exactly like objects would. Validated against a professional After Effects reference over a 60-degree orbit, and against the real scene at about a fifth of a pixel of reprojection error on the clip shown here.
</Note>

<Note>
  Width shapes copy: a bubble is its longest line plus padding, and sent bubbles stop short of your face. Long sentences wrap to two lines; if a message will not fit beside you, the run tells you rather than covering you.
</Note>
