00:00 / 00:00

Persona

SDK

@laplace.live/persona-sdk 是 Persona 插件 API 的官方 TypeScript/JavaScript 客户端,同时提供通信传输 Schema 的类型定义。本页面为完整的类型与 API 参考;有关服务端配置、密钥生成以及可用 RPC 方法的详细说明,请参阅 插件 API。

该 SDK 兼容 Node.js 22+、Bun、现代 Web 浏览器以及 OBS 浏览器源等运行环境。其唯一的运行时依赖为 zod,用于定义并校验传输 Schema。

npm install @laplace.live/persona-sdk

你能用它做什么

Persona Console 是基于该 SDK 构建的官方参考实现。它提供了一个全功能的 Web 控制台,可在单一浏览器标签页内集中管理场景、图层、素材库、表情、动作、参数映射、快捷键、捕捉源以及全局系统设置,其界面针对直播演播期间的移动端与触控操作进行了专门优化。

该控制台完全基于插件 API 构建,未引用任何桌面端专有代码,开发者可使用相同的 SDK 实现同等深度的控制能力。

开发客户端时建议遵循以下设计原则:

  • 基于功能能力判断,而非格式或版本号:各实例控件应在读取 InstanceRuntime.capabilities 后按需启用或禁用,避免盲目调用导致 unsupported-for-format 错误;
  • 断线重连视为状态重置:WebSocket 连接断开期间错过的广播事件不会重放,本地缓存可能与服务端最新状态脱节,重连建立后应清空本地缓存并重新拉取完整状态快照;
  • 妥善处理终止性连接关闭码:状态码 4001(密钥失效/吊销)与 4002(服务端强制踢出)属于终止性关闭,应停止自动重连重试;其他异常关闭则建议执行指数退避重连;
  • 事件订阅由 SDK 托管:通过 persona.on(…) 注册的事件监听器将在重连成功后自动重新订阅,业务代码无需手动维护重连后的监听生命周期。

LLM 提示词

可将以下 Prompt 提供给 LLM 或加入项目的 CLAUDE.md / AGENTS.md 规则文件中,作为插件开发的完整上下文指引:

You are helping me build a plugin for LAPLACE Persona, a desktop VTuber app
(https://laplace.live/persona). Persona exposes a local WebSocket server called the
Plugin API, and `@laplace.live/persona-sdk` is its typed client.

Before writing any code, fetch the reference documents listed at the end — they are
the single source of truth for method names, events, error codes and types. Do not
rely on memory and do not invent names.

## Setup

- Install `@laplace.live/persona-sdk`. Isomorphic: Node 22+, Bun, browsers and OBS
  browser sources. Its only runtime dependency is zod.
- The user enables the server in Persona under Settings → Plugin API and creates an
  API key there. Tokens look like `sk-lp-v1-…`. Default endpoint: `ws://127.0.0.1:25034`.
- Everything — values and types — is exported from the package root; there is no
  other entry point.

## Client

```ts
import { PersonaClient } from "@laplace.live/persona-sdk";

const persona = new PersonaClient({
  token: "sk-lp-v1-…", // required; everything else is optional
  clientInfo: { name: "My Plugin", version: "1.0.0" }, // display-only identity
});
await persona.connect();

const { scenes, activeSceneId } = await persona.call("scene.list");
await persona.call("scene.patch", {
  background: { mode: "color", color: "#00ff00", imageAssetId: null },
});
persona.on("motion.started", (m) => console.log("playing", m.group));

const mouth = persona.driveParameter("MouthOpen", 0.8); // parameter lease
mouth.set(0.3);
mouth.release();
```

`call(method, params?)` is fully typed — the method name determines the request and
response shapes.

Methods cover scenes, model instances, stage objects, expressions, motions, speech,
hotkeys, automations, model and asset registration, settings, tracking and pose
input, per-key storage and parameter injection. Events notify you of scene,
selection, expression, motion, speech, tracking and registry changes.

The exact method and event names, parameter shapes, error codes and limits live in
the reference below — look them up instead of guessing. Gate features on the
capabilities reported by `app.info` and `instance.list`, never on version strings.

## Reference

Fetch these before writing code. The documentation is served as raw Markdown —
append `.mdx` to any page URL (`.en.mdx` for English):

- https://laplace.live/persona/plugin-api.en.mdx — server setup, API keys, and every
  method, event, error code and limit
- https://laplace.live/persona/sdk.en.mdx — the SDK client: options, auth modes and
  every exported type

客户端

import { PersonaClient } from "@laplace.live/persona-sdk";

const persona = new PersonaClient({ token: "sk-lp-v1-…" });
await persona.connect();

const { scenes, activeSceneId } = await persona.call("scene.list");
await persona.call("scene.patch", {
  background: { mode: "color", color: "#00ff00", imageAssetId: null },
});
persona.on("motion.started", (m) => console.log("playing", m.group));

PersonaClient 支持通过配置选项创建实例,其中仅 token 为必填项:

Prop

Type

ClientInfo

clientInfo 用于向 Persona 声明客户端的身份标识,该标识将显示在客户端设置界面的已连接的客户端列表中。此字段为可选的声明性元数据,仅用于界面呈现,不参与鉴权逻辑。SDK 在每次断线重连时均会自动重新上报该信息。

const persona = new PersonaClient({
  token,
  clientInfo: { name: "My Overlay", version: "1.2.0", developer: "You" },
});

Prop

Type

认证配置

在浏览器环境中,API Token 统一通过 ?token= URL 查询参数传递(受限于浏览器 WebSocket API 的实现)。在 Node.js 或 Bun 等服务端环境中,可通过自定义 createWebSocket 钩子注入 Authorization: Bearer 请求头(配合 ws 等客户端库):

import WebSocket from "ws";

const persona = new PersonaClient({
  token,
  auth: "header",
  createWebSocket: (url, headers) => new WebSocket(url, { headers }),
});

WebSocketLike 定义了 createWebSocket 必须返回的 Socket 抽象接口。全局 WebSocket 实例与 ws 客户端均在结构上完全满足该类型约束,无需额外的类型断言。

Prop

Type

在 Node.js 22+ 中,全局 WebSocket 可以通过 WebSocketInit 扩展发送握手请求头。SDK 提供的 createNodeClient 辅助函数基于它创建客户端:

  • 设置 auth: 'header'
  • 使用 Node 的全局 WebSocket
  • 将连接超时设为 5 秒
  • 将 SDK 警告与终止性关闭(如 API Key 被吊销或被服务端强制断开)输出到传入的 log 函数
import { createNodeClient } from "@laplace.live/persona-sdk";

const persona = createNodeClient({
  token: "sk-lp-v1-…",
  log: console.warn,
});
await persona.connect();

Prop

Type

参数租约驱动

driveParameter 用于持续向模型参数写入目标值,并返回一个 InjectionHandle 控制句柄。SDK 在后台自动维系租约心跳,参数租约在最后一次写入约 1 秒后自动过期并平滑恢复默认值,从而避免客户端进程异常退出时导致参数僵死。

const mouth = persona.driveParameter("MouthOpen", 0.8);
mouth.set(0.3);
mouth.release();

同一模型参数在同一时间段内仅允许由单个会话独占租借;其他会话尝试重复租借将触发 conflict 错误。

该方法还支持传入可选的 weight(权重)以及 onError 异常回调函数。当后台心跳续租失败时将通过回调通知,无需在每次更新参数时调用 await。

Prop

Type

连接关闭处理

onClose 在服务端或网络导致连接关闭时触发。回调参数包含原始 Socket 关闭码、关闭原因,以及表示是否已停止重连的 terminal 标志。

  • 回调在客户端重置内部状态并清理待决请求之后才触发,因此可以在回调中安全地调用 close()。
  • 客户端主动调用 close() 不会触发 onClose。
  • 配置 onClose 后,终止性关闭改由它上报,不再经过 onWarning。

Prop

Type

PersonaClientState 与客户端错误

type PersonaClientState = "closed" | "connecting" | "open" | "reconnecting";
type ClientErrorReason =
  | "connect-timeout"
  | "connection-closed"
  | "client-closed"
  | "not-connected"
  | "request-timeout";

当客户端自身或底层传输层无法完成 connect() 或 call() 时,Promise 会以 PersonaClientError 拒绝(带有 reason: ClientErrorReason,取值见 CLIENT_ERROR_REASONS);服务端返回的错误帧则以 PersonaApiError(带有 code: ApiErrorCode)拒绝 call()。详见 插件 API:错误代码。

Prop

Type

常量定义

导出常量取值语义说明
PROTOCOL_VERSION4通信传输格式发生破坏性升级时递增;服务端在 hello 握手中上报自身版本
DEFAULT_API_HOST127.0.0.1服务端默认绑定的本地回环地址(除非用户手动开启局域网访问)
DEFAULT_API_PORT25034服务端默认监听的 WebSocket 端口
SCENE_ACTIVATION_TIMEOUT_MS120000未指定 requestTimeoutMs 时,SDK 等待 scene.activate 的默认超时时间
ASSET_IMPORT_PROMPT_MS45000asset.import 导入插件目录外的文件时,桌面端等待用户确认的超时时间(未指定 requestTimeoutMs 时,SDK 对 asset.import 默认等待 55000 毫秒)
CLOSE_KEY_REVOKED4001终止性关闭状态码:API Key 已被服务端吊销
CLOSE_FORCE_DISCONNECTED4002终止性关闭状态码:用户在控制面板中断开了当前客户端会话
CLOSE_SERVER_STOPPING1001非终止性状态码:服务端进程正在退出,客户端可等待重启后自动重连
INJECT_LEASE_TTL_MS1000注入参数在最后一次写入后的租约存活时间(TTL)
INJECT_HEARTBEAT_MS100SDK 后台重发租约心跳包的时间间隔
STORAGE_KEY_MAX_LENGTH128插件存储键名的最大允许字符长度
STORAGE_VALUE_MAX_LENGTH65536单个存储值序列化后的最大字节长度限制
STORAGE_KEYS_MAX256每个 API Key 最多可保存的键数量
SPEECH_URL_MAX_LENGTH8000000speech.play 接口支持的 url 最大长度(可容纳约 40 秒的 Base64 编码 WAV 音频)

SDK 还导出了以下取值列表与辅助函数:

  • API_ERROR_CODES、CLIENT_ERROR_REASONS、EVENT_NAMES、INPUT_NAMES、TIME_INPUT_NAMES、RANDOM_PULSE_INPUT_NAMES、MODIFIER_TOKENS、APP_CAPABILITIES、FPS_LIMIT_PRESETS、EFFECTS_QUALITY_LEVELS:as const 数组,便于在 UI 选择器中列出全部合法取值
  • isApiErrorCode、isEventName、isAppCapability、isTimeInputName、isRandomPulseInputName:对应的 TypeScript 类型守卫
  • injectTargetKey:生成标准化的注入目标标识符
  • personaWsUrl:根据 { host, port, secure }(PersonaAddress,其中 host 须为纯主机名或 IP 地址)或用户输入的地址字符串(支持纯主机名、host:port、IPv4/IPv6 地址以及完整的 ws:// / wss:// URL)生成 WebSocket URL;API Token 由 PersonaClient 在连接时自动附加
  • parseHost、parsePort、isValidPort:校验纯主机名/IP 地址(支持带或不带方括号的 IPv6,含协议、端口、路径或区域 ID 时返回 null)与端口号
  • requestTimeoutMs(method, fallbackMs):按方法名计算请求超时时间(scene.activate 与 asset.import 自动采用各自的长超时)

模型与素材

模型与通用素材共享统一的元数据定义。kind 用于标识条目的资源类型,origin 用于标识其来源:bundled 表示应用内置资源或桌面端从 Persona 目录按需下载的资源,user 表示用户本地注册的文件,同时包含清单中声明的创作者署名信息。

Prop

Type

type ModelFormat = "live2d" | "vrm";
type ContentOrigin = "bundled" | "user";
type AssetKind =
  | "image"
  | "video"
  | "audio"
  | "prop"
  | "ibl"
  | "lut"
  | "animation"
  | "cameraMotion"
  | "lyrics";
type InventoryKind = ModelFormat | AssetKind | "effect" | "addon";

effect 属于特殊的虚拟资产类型,不对应实际磁盘文件,素材库通过它枚举系统支持的 内置特效;addon 则代表扩展应用程序本身的可选附加组件(如 摄像头追踪附加组件),不会作为图层进入场景。

model.list 返回 ModelRef 数组,asset.list 返回 AssetRef 数组。二者都是 ContentRef,kind 分别收窄为 ModelFormat 与 AssetKind。

二者还带有布尔字段 exists:AssetRef 的文件在磁盘上被移动或删除后,该字段为 false;ModelRef 在模型入口文件丢失时同样为 false。

Prop

Type

Prop

Type

Prop

Type

CatalogItem

CatalogItem 提供了脱离具体传输协议的内容元数据抽象模型,本地注册表条目与远程资源目录均转换为此统一结构。它在 ContentRef 基础上移除了未安装状态下的 origin 字段,并扩展了多语言简介 description(LocalizedText)与目录检索属性。download(CatalogDownload)描述未安装条目的下载源信息;若该字段为空,表示该资产已存在于本地环境。

Prop

Type

Prop

Type

Prop

Type

目录与多语言辅助项:

  • CATALOG_FORMAT、MARKETPLACE_ITEMS_PATH、CATALOG_KINDS:目录清单格式版本号、公开目录 API 路径(/api/items)与目录支持的条目类型列表
  • isCatalogId、healCatalog、healCatalogItem、healCatalogRows、healSha256:校验并规范化远程或本地目录清单数据
  • payloadEntryPath、payloadEntryKey、catalogMediaFile(参数为 CatalogMediaRole):计算解压后的目录资源入口路径,以及源目录下预渲染缩略图与预览视频的文件名(.thumbnail.avif 与 .preview.webm)
  • pickLocalized(text, locale)、healLocalizedText:按当前界面语言从 LocalizedText 中选取匹配的展示文案并规范化多语言对象

空间排版与放置

2D 屏幕空间以像素为单位,以舞台视窗中心为坐标原点(+y 轴向下);3D 世界空间以米为单位。传输协议中所有旋转分量均严格采用弧度制表示(控制面板上为便于直观理解以角度呈现)。

Prop

Type

Prop

Type

Place2D 与 Place3D 为物体道具对应的排版类型,字段结构相同并额外包含 opacity 不透明度属性。

场景条目

场景配置中的 items 数组依据渲染深度(Z-order)混合管理模型与物体图层:

type SceneItem = SceneModelItem | SceneObjectItem;

Prop

Type

Prop

Type

Prop

Type

ObjectContent

物体图层承载的实际内容结构依据 kind 字段区分。除 capture(屏幕采集)外,其余类型均可在桌面端界面中直接创建,详见 图层管理。

type ObjectContent =
  | { kind: "image"; assetId: string }
  | {
      kind: "video";
      assetId: string;
      loop: boolean;
      muted: boolean;
      volume: number;
    }
  | { kind: "prop"; assetId: string }
  | {
      kind: "web";
      url: string;
      width: number;
      height: number;
      fps: number;
      transparent: boolean;
      css: string;
      layer: WebLayer;
      shutdownWhenHidden: boolean;
    }
  | { kind: "capture"; source: CaptureKind; sourceId: string; label: string };

type ObjectSpace = "2d" | "3d";
type WebLayer = "behind" | "front";
type CaptureKind = "display" | "window";

Prop

Type

钉附系统

Prop

Type

AttachAnchor

type AttachAnchor =
  | { kind: "root" }
  | { kind: "bone"; bone: string }
  | {
      kind: "artMesh";
      id: string;
      verts: [number, number, number];
      weights: [number, number, number];
    };

object.anchors 返回父级对象可供绑定的挂载锚点列表(以 AnchorOption 结构呈现,包含锚点 ID 及对应的可读名称)。VRM 模型提供根节点及人形骨骼节点;Live2D 模型提供根节点及各 ArtMesh 部件,并带有 order 绘制层级序号。

AttachDepth

type AttachDepth =
  { kind: "front" } | { kind: "behind" } | { kind: "artMesh"; id: string };

depth 用于控制 Live2D 道具 在父模型内部的渲染层深,可置于模型后方、前方,或指定 ArtMesh 的正上方。该属性仅适用于附着到 Live2D 父模型的 Live2D 实例,通过 instance.attach 配置。

Prop

Type

钉附相关的辅助函数:

  • depthStops(meshes):由后到前列出可选的深度挡位(模型后方、按绘制顺序排列的各 ArtMesh 上方、模型前方)
  • depthStopIndex(meshes, depth):计算某个深度位于哪个挡位;关联的 ArtMesh 已不存在时按最顶层处理
  • pinRiders(items, instanceId):递归找出直接或间接附着在 instanceId 上的所有实例,用于防止循环附着
  • pinnableParents(models, items, instanceId):生成父级候选列表,并用 ridesThis 标记须禁用的非法项
  • defaultAttach(parentInstanceId, screenSpace?):生成默认附着配置(绑定根节点、位于模型最前方、不切分部件、无动态物理参数);设置 screenSpace(Live2D 模型或 2D 物体)时,还会以默认响应跟随父模型头部转动

Prop

Type

Prop

Type

场景配置

Prop

Type

Prop

Type

Prop

Type

背景设置

Prop

Type

type BackgroundMode = "color" | "image";

相机设置

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

cameraDistanceLimits(environment, radius) 计算轨道相机在鼠标导航时允许的距离范围。默认最小、最大距离分别为 DISTANCE_MIN(0.35 米)与 DISTANCE_MAX(20 米);3D 环境的包围尺寸明显大于或小于标准空间(约 10 米跨度)时,限制会按比例缩放。radius 是 3D 场景的包围球半径,即 scene.inspect 返回的 environment.radius;场景加载完成前为 null,此时返回默认限制。

灯光系统

Prop

Type

type SceneLightType = "directional" | "point" | "ambient" | "area" | "spot";
type ShadowQuality = "off" | "low" | "medium" | "high" | "ultra";
type ShadowFilter = "pcf" | "pcss";

SCENE_LIGHT_TYPES、SHADOW_QUALITY_LEVELS 和 SHADOW_FILTERS 以 as const 数组提供光源类型、阴影档位和过滤方式,顺序与面板中的一致。

SceneLight 的以下三个字段让灯光跟随相机:

  • followCamera:将光源的位置与旋转绑定到相机坐标系
  • followCameraOptions:选择哪些运动自由度跟随相机;DEFAULT_LIGHT_FOLLOW_CAMERA_OPTIONS 启用全部
  • followCameraReference:不跟随的维度所使用的固定参考变换

若要在不改变灯光实际照射角度的前提下切换跟随状态,请调用 scene.setLightFollowCamera,不要直接修改这些字段,详见 灯光系统。

Prop

Type

Prop

Type

iblAssetId 与 modelAssetId 分别指定环境贴图(IBL)与 3D 场景模型;具备 environment-map-model 能力的应用版本可以同时使用二者。

  • 更新环境时建议使用 environmentWithAsset():它设置新的资源、保留另一项现有资源,并清理与旧场景绑定的灯光覆盖项。
  • 选中环境贴图会自动关闭 bakeFromModel;只有此前两项均为空时,加载新 3D 场景才会默认开启烘焙。
  • environmentClearPatch(environment, slot) 生成清除 'model' 或 'map' 的补丁;slot 为 null 时两者都清除。
  • applyEnvironmentLighting() 与 applyEnvironmentLook() 对应面板中的快捷操作,分别用于启用环境灯光与整体应用 EnvironmentLook 视觉风格。

Prop

Type

Prop

Type

Prop

Type

Prop

Type

体积光照按光源单独开启,通过 SceneLight.volumetric 配置。相关辅助项:

  • SCENE_VOLUMETRIC_LIGHTING_SPECS:体积雾各滑块的取值范围
  • defaultSceneVolumetricLighting():默认的体积雾配置
  • healSceneVolumetricLighting():将越界参数钳制到合法范围
  • sceneLightCanHaze(type):判断某种光源类型能否产生体积光
  • sceneLightHazes(light):判断某个光源当前是否正在产生体积光

特效系统

SceneEffects 采用扁平化的数据结构设计:每个具备开关及参数的后处理特效均直接挂载于顶层,便于开发工具进行通用的遍历与反射处理。具体特效在用户界面中的呈现分组属于视图层设计,不影响底层协议结构。

Prop

Type

特效在 图层列表 中的呈现顺序由 environment.effectLayers 独立维护(为 ToggleEffectKey 数组)。该列表与特效自身的 enabled 状态相互独立:enabled 控制特效管线的运算开关,effectLayers 决定其在 UI 面板中是否作为图层列出。当通过 Patch 启用某个特效时,系统会自动补齐对应的图层条目,因此插件开发时通常只需修改 enabled 属性。

type SceneToneMapping = "none" | "neutral" | "aces" | "agx";

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

渐变特效提供 24 种混合模式 EffectBlendMode,EFFECT_BLEND_MODES 按面板中的顺序列出它们。

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

rain(降雨)与 snow(降雪)在数据结构上与其他特效保持一致,但在管线行为上具有本质区别:它们在场景中以实际的 3D 粒子几何体形式存在并参与渲染,而非传统的屏幕空间后处理通道,详见 雨景特效 与 雪景特效。

虚拟形象与物体图层也有各自的特效管线。SceneModelItem 与 SceneObjectItem 上的 effects 与 effectLayers 先于全屏场景特效执行,通过 instance.setEffects 修改。

  • 图层特效支持 LayerEffectKey 定义的子集:color、levels、colorWheels、colorShift、selectColors、gradient、blur、bloom、diffusion、sketch、rim、outline 与 dropShadow。
  • 辉光特效的颜色过滤仅在图层级别生效,详见 图层特效。

转场过渡

transition 用于配置场景激活时的视觉过渡效果,详见 场景转场(未声明 scene-transitions 能力的版本不提供该特性)。SCENE_TRANSITION_TYPES 列出所有合法转场类型,defaultSceneTransition() 返回默认的硬切过渡,healSceneTransition() 用于将参数纠偏至合法范围。

Prop

Type

environment.itemTransition 控制场景内模型、道具及动态生成物体的出现与消失动效,详见 显示与隐藏。ITEM_TRANSITION_STYLES 列出全部支持的过渡风格,defaultItemTransition() 默认采用 300 ms 的 glitch 故障效果,ITEM_TRANSITION_MAX_MS 限制最长过渡时间为 5000 ms。

Prop

Type

场景预设

presets 按显示顺序列出场景已保存的 场景预设;未声明 scene-presets 能力的版本不提供该字段。可通过 preset.create、preset.update、preset.rename、preset.setTransition、preset.delete 与 preset.apply 管理当前场景的预设,详见 插件 API:场景预设。

  • SCENE_PRESET_TRANSITIONS:全部转场方式
  • scenePresetIsCurrent():判断舞台当前布局是否与某个预设吻合,桌面端与网页控制台据此高亮对应预设
  • capturePresetItems():采集图层布局
  • presetStep():计算应用预设时各图层的变化

Prop

Type

Prop

Type

运行时状态

instance.list 动态返回当前舞台上每个活动实例支持的实际能力集,客户端可据此在 UI 层面精确禁用非支持的操作控件,而无需依赖被动捕获 RPC 异常:

Prop

Type

type InstanceCapability =
  | "motions"
  | "expressions"
  | "placement-2d"
  | "placement-3d"
  | "mtoon"
  | "idle-clips"
  | "idle-motions"
  | "pose"
  | "breath"
  | "expression-weights"
  | "live2d-params"
  | "speech"
  | "post-fx";

speech 语音合成能力仅对已加载的 Live2D 模型有效,因此仅在运行时实例能力清单中动态返回,无法单从静态文件格式推断。应用程序自身的功能特性则通过 hello 握手及 app.info 统一上报。客户端应始终通过能力枚举(Capability Flags)判断功能是否可用,不要比对应用版本号字符串:

type AppCapability =
  | "storage"
  | "speech"
  | "automations"
  | "controllers"
  | "model-editing"
  | "asset-inspection"
  | "layer-effects"
  | "scene-transitions"
  | "light-area"
  | "light-spot"
  | "light-camera-follow"
  | "light-shadow-filter"
  | "environment-map-model"
  | "stage-spawn"
  | "idle-tracking-lost"
  | "motion-stop"
  | "stage-capture"
  | "object-pin-depth"
  | "object-text"
  | "camera-follow"
  | "camera-aim"
  | "camera-focus"
  | "camera-handheld"
  | "object-video-sound"
  | "object-chroma-key"
  | "model-movement"
  | "model-movement-pivot"
  | "layer-effects-2d"
  | "scene-presets"
  | "background-alpha"
  | "binding-calibration"
  | "binding-random-pulses"
  | "expression-groups"
  | "expression-groups-hide-first"
  | "model-history"
  | "automation-editing"
  | "automation-transport"
  | "asset-import";

canonicalAppCapability 将旧版能力名称映射为当前的标准名称。旧版名称包括 area-lights、spot-lights、camera-follow-lights、shadow-filters、spawn、tracking-lost、text-objects 与 video-sound 等。PersonaClient 收到服务端上报的能力清单时已自动完成这一转换。

stage.capture(依赖 stage-capture 能力)返回 { dataUrl, width, height },包含舞台渲染窗口带透明通道的 PNG 图像,最长边不超过 maxEdge(有效范围 64 – 2048,默认 1024)。无图形界面的自动化客户端或 AI 助手主要通过此接口验证渲染结果,协议规范详见 插件 API:功能能力。

Prop

Type

files 保持了模型定义文件中各动作的原始索引顺序:文件缺失的动作项使用空字符串占位,以确保后续动作的绝对索引不发生偏移。motionSlots(files) 返回实际可播放的动作项及其对应索引;若尝试向空位调用 motion.play 将返回 not-found 错误。Live2D 模型还会自动扫描并列出同目录下未在 model3.json 中声明的所有 .motion3.json 动作文件,并以文件名分别建立独立的分组。

motion.stop(依赖 motion-stop 能力)用于结束当前播放中的单次动作,并让模型平滑回到待机状态;若当前仅处于待机状态,则返回 { stopped: false }。motion.playing 及 motion.started 中的 oneShot 标志表明该动作是否属于可通过 stop 中断的单次播放动作。

Prop

Type

Prop

Type

Prop

Type

表情组

expression.getGroups 与 expression.setGroups(依赖 expression-groups 能力)读写模型的表情组,返回 ExpressionGroups;规则详见 插件 API:表情组。

Prop

Type

Prop

Type

Prop

Type

EXPRESSION_GROUP_FADE_SECONDS_MAX(2)为成员淡入淡出时长的上限,EXPRESSION_GROUP_FADE_SECONDS_DEFAULT(0.2)为新成员的默认值;foldExpressionKey 按 VTS 的规则(不区分大小写)折叠表情键,用于判断两个键是否指向同一表情,firstByExpressionKey(items, keyOf) 则按折叠后的键建立映射并保留每个非空键下首次出现的项(与 VTS 解析表情键的顺序一致);newVtsId 生成 VTS 格式的 ID(32 位小写十六进制),可用于新建的组。

快捷键系统

Prop

Type

Prop

Type

HotkeyConfig 是剥离了 registered 状态后的配置结构,用于 hotkey.set 接口传参。registered 列出当前在 Persona 处于后台时仍会响应的快捷键;桌面端直接读取按键状态而非向系统注册全局热键,因此任意组合键(包括单个按键)均可在后台触发,hotkeyRunsInBackground 用于判断某条快捷键是否设置为后台生效。组合键按同时按住的按键集合触发,comboKey(accelerator) 返回与顺序无关的组合标识,duplicateAccelerators 据此找出被多条快捷键占用的组合。acceleratorLabel(accelerator, platform, mouseLabels?) 按标准修饰键顺序(MODIFIER_TOKENS:Control、Alt、Shift、Super)将组合键格式化为适合键帽显示的标签数组,并根据 hello 上报的桌面端 app.platform 选择符号('darwin' 下为 ⌃、⌥、⇧、⌘,其他平台为 Ctrl、Alt、Shift、Win;鼠标按键默认使用 MOUSE_TRIGGER_LABELS,也可传入本地化标签)。

舞台上的每个虚拟形象都有一套独立的快捷键:

  • hotkey.list、hotkey.set 与 hotkey.trigger 均接受可选的 modelId 参数,省略时指向主模型。
  • hotkey.state 事件按模型分别推送更新。
  • hold、fadeSeconds、deactivateAfterSeconds 与 stopsOnLastFrame 为新版协议新增的字段;调用 hotkey.set 时省略的字段保持现有配置不变。

SDK 提供了快速枚举当前场景快捷键的辅助函数:listSceneHotkeys(client) 查询当前活动场景中所有模型的快捷键配置(主模型排在首位);listModelHotkeys(client, scene) 为舞台上的每个模型分别返回一个 Promise<ModelHotkeys>,便于调用方并发独立结算。

Prop

Type

自动化系统

自动化工作流是应用级的自动化系统,独立于单个模型实例。每条自动化包含一组操作指令,可由快捷键、系统事件或 API 调用触发。automation.list 用于查询列表,automation.run 按 ID 执行指定自动化,automation.state 在工作流发生变更时广播推送完整列表。该特性需要应用声明 automations 能力,详见 插件 API:自动化。

Prop

Type

type AutomationActionKind =
  | "effect-toggle"
  | "effect-params"
  | "effect-clip"
  | "camera-pose"
  | "camera-reset"
  | "camera-motion-play"
  | "camera-motion-stop"
  | "camera-follow"
  | "camera-aim"
  | "camera-focus"
  | "camera-handheld"
  | "layer-visibility"
  | "preset-apply"
  | "text-set"
  | "lyrics-play"
  | "stream-mode"
  | "scene-switch"
  | "expression-toggle"
  | "motion-play"
  | "audio-play"
  | "audio-control"
  | "expression-clear"
  | "model-load"
  | "model-position";

actionKinds 与 triggerKinds 的类型是开放的 string[] 而非固定的联合类型,以便兼容更高版本服务端新增的类型。操作类型统一以类别开头命名,客户端会自动规范化旧版主机发来的历史名称。

  • automationActionLabel:操作类型的英文显示标签
  • automationLabel:整条自动化的摘要标签,优先使用 title,未设置时以 · 连接各项操作的标签
  • AUTOMATION_SETUP_KINDS、isAutomationSetup(以及 isAutomationSetupAction):识别在时间线开始前先行执行的准备操作(scene-switch 与 model-load);AUTOMATION_BOUNDARY_KINDS 与 isAutomationBoundary 为已废弃的别名
  • isAutomationMediaAction、isAutomationSourcedAction、isAutomationSampledClip、isAutomationContentAction:按时间线行为对动作分类(媒体片段、带 sourceInMs 入点偏移的片段、支持拖动定位预览的片段、普通时间线动作)

时间线编辑与传输控制

具备 automation-editing 能力时,automation.get、automation.create、automation.update 与 automation.delete 可读写完整的 AppAutomation 时间线定义;具备 automation-transport 能力时,automation.control 与 automation.status 可驱动时间线传输并读取 AutomationRunStatus,详见 插件 API:自动化。

Prop

Type

Prop

Type

Prop

Type

Prop

Type

  • AutomationDefinitionSchema、AppAutomationSchema、automationTimelineActionSchemas、automationTriggerSchemas:时间线定义、各动作类型与各事件触发器类型的 Zod Schema
  • validateAutomationTimeline、automationTimelineLimit:校验时间线时长与各片段的时间范围,并计算时间线的结束时间
  • AUTOMATION_TRANSPORT_COMMANDS、AUTOMATION_RUN_PHASES、AUTOMATION_STEP_STATES:传输控制命令(play、pause、stop、seek、prepare)、运行阶段与步骤状态的 as const 数组
  • MAX_AUTOMATION_DURATION_MS、MAX_AUTOMATION_EFFECT_FADE_MS、MAX_AUTOMATION_HOLD_MS、MAX_AUTOMATION_COOLDOWN_MS:时间线时长、画面效果片段淡入淡出、保持时长与触发器冷却时间的上限常量
  • AUDIO_RETRIGGER_MODES、PLAYBACK_COMMANDS、MAX_AUDIO_FADE_MS、MAX_AUDIO_REPEAT_COUNT:audio-play 与 audio-control 动作使用的重触发模式、播放控制指令与音频参数上限

系统设置

Prop

Type

SettingsPatch 是设置中可写入的部分,所有字段均为可选:lipSync、controller(仅 enabled 开关)、window、ui 与 performance。面部与姿态捕捉参数则通过 tracking.* 与 pose.* 接口单独配置。

Settings 与 SettingsPatch 均由 SDK 导出的运行时 Zod Schema(SettingsSchema 与 SettingsPatchSchema)推导而来:

  • 校验补丁时会剥离未知字段与只读字段。
  • 解析服务端响应时会放行扩展字段。
  • PersonaClient 本身不在客户端做前置校验。
type TrackingSourceId = "persona-ios" | "ifacialmocap" | "vts-ios";
type PoseSourceId = "vmc" | "mocopi";
type TrackingSourceKind = TrackingSourceId | PoseSourceId | "mediapipe";
type TrackingStatus = "off" | "waiting" | "tracking" | "no-face";
type PoseStatus = "off" | "waiting" | "tracking";
type EffectsQuality = "low" | "medium" | "high";

捕捉源配置

tracking.sources 列出了当前配置的所有输入源,包括网络面部源、动作姿态源以及本地摄像头。系统支持多源同时运行,模型实例通过 SceneModelItem 上的 faceSourceId、poseSourceId 与 handSourceId 按 ID 绑定对应的捕捉源。

Prop

Type

tracking.source、pose.source 及 pose.port 属于多源架构引入前的旧字段,目前镜像映射至对应通道的首个网络源,仅供旧版客户端兼容使用。新开发的插件应统一使用 sources 字段。

mediapipe 摄像头捕捉 源包含独立的配置属性,默认参数定义于 DEFAULT_MEDIAPIPE_CONFIG。

Prop

Type

type HandTrackingMode = "arms" | "fingers";

单个输入源可以同时驱动多个数据通道,例如一台摄像头可同时输出面部、手部与身体姿态。sourceSupportsChannel(source, channel) 用于判断特定源在当前算法模式下是否支持 face、hands 或 pose 输出通道;sourceChannelEnabled(source, channel, masters) 则在此基础上综合计算该源自身的分通道开关以及全局总开关的启用状态。

口型同步配置

settings.lipSync 与 lipSync.configure 接口共享相同的 LipSyncConfig 结构,对应桌面端的麦克风音频驱动。对于不支持音频口型同步的环境构建,Settings 中将剔除该配置项。

Prop

Type

lipSync.state 与 lipSync.calibrate 返回 LipSyncState。校准交互流程详见 麦克风口型同步。

Prop

Type

SceneModelItem 中的 lipSyncMode 用于按模型配置麦克风口型同步的驱动策略:

type LipSyncMode = "off" | "always" | "when-untracked";

模型整体移动配置

model.getMovement 与 model.setMovement 接口使用 ModelMovementConfig 配置结构,对应 Live2D 模型在面部捕捉驱动下的整体位移与缩放(即 VTube Studio 的 Movement Config)。水平、垂直与深度位移滑块范围为 −50 – 50;pivot(前后缩放中心,需 model-movement-pivot 能力)以 Live2D 画布归一化坐标记录缩放中心。

Prop

Type

版本历史

model.*Version* 方法与 model.restoreFiles(依赖 model-history 能力)读取与管理模型的已保存版本,对应桌面端的 版本历史;各方法的参数与错误语义详见 插件 API:版本历史。

Prop

Type

Prop

Type

Prop

Type

type ModelVersionKind = "first" | "saved" | "backup";
type ModelVersionUnsavedAction = "save" | "discard";
type ModelVersionChangeStatus = "added" | "modified" | "deleted" | "unchanged";
  • MODEL_VERSION_KINDS、MODEL_VERSION_UNSAVED_ACTIONS、MODEL_VERSION_CHANGE_STATUSES:上述类型对应的 as const 数组
  • MODEL_VERSION_CURRENT('current'):可在任何接受版本 ID 的位置代表磁盘上的当前文件,如 model.compareVersions 的 from 或 to
  • MODEL_VERSION_NAME_MAX_LENGTH(80)、MODEL_VERSION_NOTES_MAX_LENGTH(2000):版本名称与备注的最大字符数
  • MODEL_VERSIONS_LIST_MAX(500)、MODEL_VERSIONS_LIST_DEFAULT(50):单次 model.listVersions 返回版本数的上限与默认值

插件存储

storage.* 接口支持保存任意合法的 JSON 值。具体键值限制详见 常量定义,使用规范详见 插件存储。

type JsonValue =
  string | number | boolean | null | JsonValue[] | { [key: string]: JsonValue };

参数注入

Prop

Type

type InjectTargetType = "input" | "live2d-param" | "vrm-expression";

InjectTarget 是去掉 value 与 weight 后的注入目标。

输入名称

input 目标的 id 取自下表中的输入名称。INPUT_NAMES 包含下表中的全部名称,其中 VTube Studio 与 ARKit 名称与模型 .vtube.json 中的命名一致。注入的 input 值仅对 Live2D 模型生效。

类别输入
VTube StudioVTS 经典 21 项输入命名:FaceAngleX FaceAngleY FaceAngleZ FacePositionX FacePositionY FacePositionZ EyeOpenLeft EyeOpenRight EyeLeftX EyeLeftY EyeRightX EyeRightY Brows BrowLeftY BrowRightY MouthSmile MouthOpen MouthX CheekPuff JawOpen TongueOut
ARKit其余 52 个通道,以 ARKit 为前缀,后接 ARKit Blendshape 的 PascalCase 名称,如 ARKitJawOpen、ARKitMouthSmileLeft、ARKitEyeBlinkRight
手柄BASE_CONTROLLER_INPUT_NAMES,即首个手柄沿用 VTS 规范的键位名:左右摇杆(ControllerStickLeftX/Y、ControllerStickRightX/Y)与摇杆下压、十字键轴向与四个独立方向键(ControllerDPadUp/Down/Left/Right)、动作键、肩键、扳机键、Options、Home、PlayStation 触控板按下(ControllerTouchPadPress)、VTS 派生的拇指与食指位置(ControllerThumbPosLeft/Right、ControllerFingerPosLeft/Right)、左右侧按钮状态与计数(ControllerButtonsAnyLeft/Right、ControllerButtonCountLeft/Right)以及手柄倾斜(ControllerLean)
手部HAND_INPUT_NAMES:VTS 规范的 26 个手部通道,外加 HandLeftAngleY 与 HandRightAngleY,涵盖双手检测标志、三维坐标、空间旋转角、手掌开合度、各手指独立开合(如 HandLeftFinger_1_Thumb),以及 BothHandsFound 与 HandDistance
语音VOICE_INPUT_NAMES:VTS 的 VoiceVolume、VoiceFrequency、VoiceVolumePlusMouthOpen、VoiceFrequencyPlusMouthSmile、VoiceA 至 VoiceO 以及 VoiceSilence,外加 VoiceMouthOpen 与带符号的 VoiceMouthSpread
鼠标MOUSE_INPUT_NAMES:MousePositionX 与 MousePositionY,即鼠标指针在屏幕上的位置,归一化为 −1..1(向右为正、向上为正,与 FacePositionY 一致)
时间TIME_INPUT_NAMES:Time24h 与 Time12h,取值范围为 0..1(TIME_INPUT_RANGES)
随机RANDOM_PULSE_INPUT_NAMES:RandomPulse1 至 RandomPulse8,取值范围为 0..1(RANDOM_PULSE_INPUT_RANGES)
  • 添加 ARKit 前缀是为了与 VTS 已占用的 JawOpen、CheekPuff、TongueOut 区分,因为 .vtube.json 的参数匹配不区分大小写。这三个同名通道即 ARKIT_TWINS:它们与对应的 ARKit 通道共享同一个浮点值,两个名称均可写入,内部统一映射到 ARKit 通道。
  • INPUT_RANGES 定义了各输入的标准取值范围:头部与手部旋转以角度(Degrees)为单位,ARKit 通道为 0..1,其余为无量纲的归一化数值。
  • CONTROLLER_THUMB_POSITIONS、CONTROLLER_FINGER_POSITIONS 与 isControllerPositionInput 对应拇指与食指位置。次级手柄在 Controller 后追加索引数字(如 Controller2StickLeftX、Controller12Cross),支持任意数量的手柄。controllerInputName 生成指定序号的键位名,getInputRange 返回对应量程(摇杆与十字键的 Y 轴向上为正)。
  • 鼠标输入独立于面部捕捉,不受面部捕捉总开关影响。
  • 时间输入每帧采样桌面主机的本地时钟,独立于面部捕捉状态,同时支持 Live2D 与 VRM 参数绑定,详见 时间参数绑定。isTimeInputName 是对应的类型守卫。
  • 随机脉冲输入各自按独立的触发设置自动在 0(静止)与 1(完全触发)之间起伏,独立于面部捕捉状态(详见 参数绑定 与 插件 API:参数绑定)。RandomPulseSchedules 按输入名称记录模型的自定义触发设置,未单独配置的脉冲使用 DEFAULT_RANDOM_PULSE_SCHEDULE(间隔 0.5–4.5 秒、持续 0.58 秒、淡入与淡出各 0.29 秒,与 VTube Studio 自动眨眼一致);RANDOM_PULSE_MIN_SECONDS(0.1)与 RANDOM_PULSE_MAX_SECONDS(3600)定义时间范围上下限,sanitizeRandomPulse 与 sanitizeRandomPulses 负责校验与规范化配置,isPulseBinding、pulseRest、pulseHoldsRest、firePulseBinding 与 bindingOutputRange 则用于计算脉冲绑定的叠加输出。

Prop

Type

有关 Live2D 模型中各输入通道如何映射至具体内部参数,详见 参数绑定。

底层消息信封

若直接使用 SDK 客户端开发,无需手动处理此类底层消息信封;本节规范供直接对接原始 WebSocket 协议的开发者参考:

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

Prop

Type

ApiErrorCode 为 ErrorMessage 中 code 属性的封闭枚举集合,各错误码的具体语义详见 错误码参考。客户端在执行 call 发生异常时抛出的 PersonaApiError 实例将封装该错误码。

最后更新于 2026年11月7日

Tech otakus destroy the world