sume-virtual-try-on Format: first frame, then Seedance 2.5
The sume-virtual-try-on Format builds a first frame with ChatGPT Image 2, then animates it with Seedance 2.5. What goes in, what comes back.

The sume-virtual-try-on Format makes a short video of a person wearing a garment. In the first-party Format code, it builds the first frame with ChatGPT Image 2 and then animates it with Seedance 2.5 reference-to-video. You give it a person photo and a garment photo as attachments and call it on POST /v1/formats/sume/sume-virtual-try-on/runs.
That is a different product from the try-on button OpenAI launched in ChatGPT on October 1, 2026, which produces an image inside the chat. The Sume Format is meant for the next step a store usually wants: a clip it can post. For a still-only path, see the try-on screenshot post.
Inputs the run accepts
A Format run needs at least one of instruction, input, previous_run_id or attachments. Attachments can be up to 30 images in JPEG, PNG, WebP, GIF or AVIF, with 30 MB per file and 500 MB per run. For a try-on you need two: the person and the garment. Say in the instruction which is which, because the model sees only the pixels and the text.
The instruction is read up to 8000 characters, but only about the first 4000 are carried, so put the important parts first: aspect ratio, framing, what must not change.
| Input | Limit | Tip |
|---|---|---|
attachments | Up to 30 images, 30 MB each, 500 MB per run | Send person first, then garment |
instruction | 8000 chars, about 4000 carried | Put framing and constraints first |
generation_spend_cap_usd | Format default $400, max $500, 0 rejected | Set a lower cap per run |
Idempotency-Key | Up to 255 chars, scoped per Format | Derive from shopper and SKU |
communication.webhook_url | Public HTTPS | Receive one signed format.run.terminal |
Calling it
The create call returns 202 Accepted with a run object whose status starts at queued. Poll the run or arm a webhook and read the receipt when it is terminal. The receipt carries usage.billable_amount_usd_micros, and on a failed run primary_output_url is null, so branch on that before you show anything.
curl -sS -X POST "https://api.sume.com/v1/formats/sume/sume-virtual-try-on/runs" \
-H "Authorization: Bearer $SUME_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: tryon-shopper-77-sku-1042-v1" \
-d '{
"instruction": "Image 1 is the person, image 2 is the linen shirt. Vertical 9:16, full body, natural light.",
"attachments": [
{"type": "input_image", "image_url": "https://cdn.example.com/people/77.jpg"},
{"type": "input_image", "image_url": "https://cdn.example.com/sku/1042.jpg"}
],
"generation_spend_cap_usd": 20
}'Try-on or fitting
If your goal is a fashion ad rather than a personal preview, compare it with the sibling Format. The virtual fitting versus virtual try-on post sets them side by side. Whichever you pick, the catalog lists the slug and the owner handle sume, so a run is always addressed as /v1/formats/sume/<slug>/runs.
Treat the first output as a draft. Garment print, sleeve length and hands are where renders slip, and the QC checklist covers frame checks you can run before you ship.
Reading the result and the bill
When the run is terminal, read primary_output_url for the clip and usage.billable_amount_usd_micros for what the run cost. A failed run has a null primary_output_url and a failure code such as unattended_blocked, deliverable_missing or primary_output_missing, which the errors doc explains. Do not post a result whose primary_output_url is null.
If a draft is close but wrong, for example the shirt is the right colour but the wrong length, continue the same conversation with previous_run_id and a short corrective instruction rather than starting over with new attachments. That keeps the thread's context and usually costs less than a full re-run.
To get a typed response with the video URL in a named key, bind an output_schema with a SumeMediaFile# reference and set primary_output_key; the structured output doc shows the strict subset that is accepted.
Keep your own identifiers outside the run. On the projection path, input identifiers do not round-trip into the typed output, so key your SKU id by the run id or by your Idempotency-Key and look it up when the webhook arrives. For a catalog, see the bulk try-on post. A webhook receipt larger than 1 MiB arrives with a null payload, so fetch the run by id instead of trusting the body.
Sources
Related posts
More in Formats
- Sume webhook retry schedule: 30s doubling, 10 tries, 1h cap
Sume Format run webhooks retry up to 10 times with min(max(30s x 2^(attempt-1), Retry-After), 1h). The arithmetic of that schedule and what to do when it ends.
- TikTok's Next Episode: a brand series as one Format and one queue
TikTok's The Next Episode funds creator-led series. Here is how to produce a season with Sume: one Format recipe, one bulk queue of up to 100 runs.
- Shop Creative Hub limits: 50 per upload, 10k a month, batch math
Creative Hub for GMV Max takes 50 videos per upload and 10k a month. What that means for Sume bulk queues of 100, and where the 200-video link cap bites.
- Video-hook Format for Cyber Week: cold opens, no overlapping runs
Call Sume's video-hook Format for cold-open variants of a Cyber Week ad, and use on_active_run to stop overlapping runs of the same Format.
Written by Sume