官方格式
建立 Runway 角色表演
使用 CometAPI 搭配 Runway Control a character API,從參考影片啟動角色表演任務,驅動臉部表情與身體動作。
POST
/
runwayml
/
v1
/
character_performance
cURL
curl https://api.cometapi.com/runwayml/v1/character_performance \
-H "Authorization: Bearer $COMETAPI_KEY" \
-H "Content-Type: application/json" \
-d '{
"character": {
"type": "video",
"uri": "https://your-video-host/character.mp4"
},
"reference": {
"type": "video",
"uri": "https://your-video-host/performance.mp4"
},
"model": "act_two",
"ratio": "1280:720"
}'import os
import requests
response = requests.post(
"https://api.cometapi.com/runwayml/v1/character_performance",
headers={"Authorization": "Bearer " + os.environ["COMETAPI_KEY"]},
json={
"character": {
"type": "video",
"uri": "https://your-video-host/character.mp4"
},
"reference": {
"type": "video",
"uri": "https://your-video-host/performance.mp4"
},
"model": "act_two",
"ratio": "1280:720"
},
)
task = response.json()
print(task["id"]) # poll GET /runwayml/v1/tasks/{id} until the output array appearsconst response = await fetch("https://api.cometapi.com/runwayml/v1/character_performance", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.COMETAPI_KEY}`,
"Content-Type": "application/json",
},
body: JSON.stringify({
"character": {
"type": "video",
"uri": "https://your-video-host/character.mp4"
},
"reference": {
"type": "video",
"uri": "https://your-video-host/performance.mp4"
},
"model": "act_two",
"ratio": "1280:720"
}),
});
const task = await response.json();
console.log(task.id); // poll GET /runwayml/v1/tasks/{id} until the output array appears<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.cometapi.com/runwayml/v1/character_performance",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'character' => [
'type' => 'video',
'uri' => 'https://your-video-host/source.mp4'
],
'reference' => [
'type' => 'video',
'uri' => 'https://your-video-host/source.mp4'
],
'bodyControl' => true,
'expressionIntensity' => 3,
'seed' => 4294967295,
'model' => 'act_two',
'ratio' => '1280:720',
'contentModeration' => [
'publicFigureThreshold' => 'auto'
]
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json",
"X-Runway-Version: <x-runway-version>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.cometapi.com/runwayml/v1/character_performance"
payload := strings.NewReader("{\n \"character\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"reference\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"bodyControl\": true,\n \"expressionIntensity\": 3,\n \"seed\": 4294967295,\n \"model\": \"act_two\",\n \"ratio\": \"1280:720\",\n \"contentModeration\": {\n \"publicFigureThreshold\": \"auto\"\n }\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("X-Runway-Version", "<x-runway-version>")
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api.cometapi.com/runwayml/v1/character_performance")
.header("X-Runway-Version", "<x-runway-version>")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"character\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"reference\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"bodyControl\": true,\n \"expressionIntensity\": 3,\n \"seed\": 4294967295,\n \"model\": \"act_two\",\n \"ratio\": \"1280:720\",\n \"contentModeration\": {\n \"publicFigureThreshold\": \"auto\"\n }\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.cometapi.com/runwayml/v1/character_performance")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["X-Runway-Version"] = '<x-runway-version>'
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"character\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"reference\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"bodyControl\": true,\n \"expressionIntensity\": 3,\n \"seed\": 4294967295,\n \"model\": \"act_two\",\n \"ratio\": \"1280:720\",\n \"contentModeration\": {\n \"publicFigureThreshold\": \"auto\"\n }\n}"
response = http.request(request)
puts response.read_body{
"id": "5b91e444-c232-deaf-a4d7-8aef3e57336b"
}使用這個端點可將參考片段中的表演轉移到角色圖片或角色影片上。
呼叫前準備
- 傳送必要的
X-Runway-Version標頭,例如2024-11-06 - 使用
model: act_two - 提供一個
character資產與一個reference資產,且都必須是可存取的 HTTPS URL - 在調整風格前,先以
bodyControl: true和適中的expressionIntensity開始
輸出比例
| 設定 | 支援的值 | 預設起始值 | 邊界行為 |
|---|---|---|---|
ratio | 1280:720、720:1280,或所選 Runway model/version 接受的其他比例 | 1280:720 | 讓角色與參考資產盡量接近所要求的畫面比例。 |
任務流程
1
提交角色表演請求
使用你的角色資產、參考資產與動作設定建立任務。
2
儲存回傳的 task id
保留回傳的
id,因為後續輪詢會用到它。3
輪詢任務狀態
持續使用取得 Runway 任務,直到任務進入終態,且提供者中繼資料包含完成的輸出。
輸入角色
character是你想要製作動畫的主體reference是提供臉部表演或身體動作的來源片段bodyControl決定動作轉移是否除了表情轉移外,也包含身體動作contentModeration會將提供者的審核門檻套用到此請求
授權
Bearer token authentication. Use your CometAPI key.
標頭
Runway version header, for example 2024-11-06.
主體
application/json
The character to control. You can either provide a video or an image.
Show child attributes
Show child attributes
Reference performance clip. Provide type (video) and uri (HTTPS URL).
Show child attributes
Show child attributes
Enable body control.
Intensity of the expression transfer. Higher values produce more exaggerated expressions.
Random seed for reproducible results.
The model variant to use. Must be act_two.
Requested output frame shape, for example 1280:720 or 720:1280. Keep the character and reference assets close to the requested frame shape.
Show child attributes
Show child attributes
回應
200 - application/json
Task accepted.
⌘I
cURL
curl https://api.cometapi.com/runwayml/v1/character_performance \
-H "Authorization: Bearer $COMETAPI_KEY" \
-H "Content-Type: application/json" \
-d '{
"character": {
"type": "video",
"uri": "https://your-video-host/character.mp4"
},
"reference": {
"type": "video",
"uri": "https://your-video-host/performance.mp4"
},
"model": "act_two",
"ratio": "1280:720"
}'import os
import requests
response = requests.post(
"https://api.cometapi.com/runwayml/v1/character_performance",
headers={"Authorization": "Bearer " + os.environ["COMETAPI_KEY"]},
json={
"character": {
"type": "video",
"uri": "https://your-video-host/character.mp4"
},
"reference": {
"type": "video",
"uri": "https://your-video-host/performance.mp4"
},
"model": "act_two",
"ratio": "1280:720"
},
)
task = response.json()
print(task["id"]) # poll GET /runwayml/v1/tasks/{id} until the output array appearsconst response = await fetch("https://api.cometapi.com/runwayml/v1/character_performance", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.COMETAPI_KEY}`,
"Content-Type": "application/json",
},
body: JSON.stringify({
"character": {
"type": "video",
"uri": "https://your-video-host/character.mp4"
},
"reference": {
"type": "video",
"uri": "https://your-video-host/performance.mp4"
},
"model": "act_two",
"ratio": "1280:720"
}),
});
const task = await response.json();
console.log(task.id); // poll GET /runwayml/v1/tasks/{id} until the output array appears<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.cometapi.com/runwayml/v1/character_performance",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'character' => [
'type' => 'video',
'uri' => 'https://your-video-host/source.mp4'
],
'reference' => [
'type' => 'video',
'uri' => 'https://your-video-host/source.mp4'
],
'bodyControl' => true,
'expressionIntensity' => 3,
'seed' => 4294967295,
'model' => 'act_two',
'ratio' => '1280:720',
'contentModeration' => [
'publicFigureThreshold' => 'auto'
]
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json",
"X-Runway-Version: <x-runway-version>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.cometapi.com/runwayml/v1/character_performance"
payload := strings.NewReader("{\n \"character\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"reference\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"bodyControl\": true,\n \"expressionIntensity\": 3,\n \"seed\": 4294967295,\n \"model\": \"act_two\",\n \"ratio\": \"1280:720\",\n \"contentModeration\": {\n \"publicFigureThreshold\": \"auto\"\n }\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("X-Runway-Version", "<x-runway-version>")
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api.cometapi.com/runwayml/v1/character_performance")
.header("X-Runway-Version", "<x-runway-version>")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"character\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"reference\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"bodyControl\": true,\n \"expressionIntensity\": 3,\n \"seed\": 4294967295,\n \"model\": \"act_two\",\n \"ratio\": \"1280:720\",\n \"contentModeration\": {\n \"publicFigureThreshold\": \"auto\"\n }\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.cometapi.com/runwayml/v1/character_performance")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["X-Runway-Version"] = '<x-runway-version>'
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"character\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"reference\": {\n \"type\": \"video\",\n \"uri\": \"https://your-video-host/source.mp4\"\n },\n \"bodyControl\": true,\n \"expressionIntensity\": 3,\n \"seed\": 4294967295,\n \"model\": \"act_two\",\n \"ratio\": \"1280:720\",\n \"contentModeration\": {\n \"publicFigureThreshold\": \"auto\"\n }\n}"
response = http.request(request)
puts response.read_body{
"id": "5b91e444-c232-deaf-a4d7-8aef3e57336b"
}