obsbot-mcp 0.7.0 → 0.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +111 -20
- package/dist/build-info.json +5 -0
- package/dist/device/manager.d.ts +8 -0
- package/dist/device/manager.js +37 -4
- package/dist/device/manager.js.map +1 -1
- package/dist/geometry/aim.d.ts +24 -13
- package/dist/geometry/aim.js +26 -13
- package/dist/geometry/aim.js.map +1 -1
- package/dist/ipc/build-id.d.ts +25 -0
- package/dist/ipc/build-id.js +60 -0
- package/dist/ipc/build-id.js.map +1 -0
- package/dist/ipc/client.d.ts +36 -0
- package/dist/ipc/client.js +106 -4
- package/dist/ipc/client.js.map +1 -1
- package/dist/ipc/coordinator.d.ts +91 -12
- package/dist/ipc/coordinator.js +293 -57
- package/dist/ipc/coordinator.js.map +1 -1
- package/dist/ipc/gate.d.ts +14 -0
- package/dist/ipc/gate.js +45 -0
- package/dist/ipc/gate.js.map +1 -0
- package/dist/ipc/owner.d.ts +27 -1
- package/dist/ipc/owner.js +67 -4
- package/dist/ipc/owner.js.map +1 -1
- package/dist/ipc/protocol.d.ts +30 -0
- package/dist/ipc/protocol.js +40 -0
- package/dist/ipc/protocol.js.map +1 -1
- package/dist/ipc/rendezvous.d.ts +37 -11
- package/dist/ipc/rendezvous.js +143 -30
- package/dist/ipc/rendezvous.js.map +1 -1
- package/dist/mcp/server.js +40 -12
- package/dist/mcp/server.js.map +1 -1
- package/dist/tail2/api.d.ts +381 -0
- package/dist/tail2/api.js +547 -0
- package/dist/tail2/api.js.map +1 -0
- package/dist/tail2/mdns.d.ts +48 -0
- package/dist/tail2/mdns.js +216 -0
- package/dist/tail2/mdns.js.map +1 -0
- package/dist/tail2/move.d.ts +41 -0
- package/dist/tail2/move.js +79 -0
- package/dist/tail2/move.js.map +1 -0
- package/dist/tail2/registry.d.ts +100 -0
- package/dist/tail2/registry.js +200 -0
- package/dist/tail2/registry.js.map +1 -0
- package/dist/tail2/snapshot.d.ts +54 -0
- package/dist/tail2/snapshot.js +157 -0
- package/dist/tail2/snapshot.js.map +1 -0
- package/dist/tail2/tools.d.ts +7 -0
- package/dist/tail2/tools.js +772 -0
- package/dist/tail2/tools.js.map +1 -0
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/native/prebuilt/darwin-arm64/obsbot-helper +0 -0
- package/native/prebuilt/darwin-x64/obsbot-helper +0 -0
- package/native/prebuilt/linux-x64/obsbot-helper +0 -0
- package/native/prebuilt/win32-x64/obsbot-helper.exe +0 -0
- package/package.json +4 -1
|
@@ -0,0 +1,381 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* HTTP/WS client for the OBSBOT Tail 2 control API.
|
|
3
|
+
*
|
|
4
|
+
* The Tail 2's network control plane is a lighttpd REST API plus a WebSocket
|
|
5
|
+
* status push (see TAIL2-PROTOCOL.md). Its USB-C UVC mode has a control
|
|
6
|
+
* surface of its own (§11) that this client does not use.
|
|
7
|
+
* Everything here is plain HTTP and therefore platform-independent: the same
|
|
8
|
+
* code runs on Windows, Linux and macOS with no native helper, which is the
|
|
9
|
+
* whole reason this module exists as a separate family from the Tiny 2's
|
|
10
|
+
* helper-process transports.
|
|
11
|
+
*
|
|
12
|
+
* Identity is the camera's MAC (what OBSBOT Center keys on); device_name and
|
|
13
|
+
* any of its IPs are accepted as selectors one level up, in the registry.
|
|
14
|
+
*/
|
|
15
|
+
/** `GET /camera/sdk/device_info` — the probe target and identity source. */
|
|
16
|
+
export interface Tail2DeviceInfo {
|
|
17
|
+
device_name: string;
|
|
18
|
+
wired_ip: string;
|
|
19
|
+
wireless_ip: string;
|
|
20
|
+
mac: string;
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* One push from `ws://<host>/ws/`. The camera sends the FULL status block
|
|
24
|
+
* ~1 Hz with no subscription message. Fields the tools rely on are typed;
|
|
25
|
+
* the block carries more (and firmware may add some) — unknown fields pass
|
|
26
|
+
* through untouched via the index signature.
|
|
27
|
+
*
|
|
28
|
+
* MEASURED 2026-09-26 against firmware 7.2.13.1; see TAIL2-PROTOCOL.md §4.
|
|
29
|
+
*/
|
|
30
|
+
export interface Tail2Status {
|
|
31
|
+
[key: string]: unknown;
|
|
32
|
+
power_on?: boolean;
|
|
33
|
+
usb_mode?: number;
|
|
34
|
+
rec?: boolean;
|
|
35
|
+
rec_time?: number;
|
|
36
|
+
switch_portrait?: boolean;
|
|
37
|
+
ai_mode?: string;
|
|
38
|
+
zoom_ratio?: number;
|
|
39
|
+
roll_bias?: number;
|
|
40
|
+
focus_mode?: string;
|
|
41
|
+
auto_focus_mode?: string;
|
|
42
|
+
ndi?: {
|
|
43
|
+
enable?: boolean;
|
|
44
|
+
};
|
|
45
|
+
rtsp?: {
|
|
46
|
+
enable?: boolean;
|
|
47
|
+
};
|
|
48
|
+
srt?: {
|
|
49
|
+
enable?: boolean;
|
|
50
|
+
};
|
|
51
|
+
rtmp?: {
|
|
52
|
+
enable?: boolean;
|
|
53
|
+
};
|
|
54
|
+
preset_info?: Array<{
|
|
55
|
+
id: number;
|
|
56
|
+
pitch: number;
|
|
57
|
+
yaw: number;
|
|
58
|
+
roll: number;
|
|
59
|
+
ratio: number;
|
|
60
|
+
name: string;
|
|
61
|
+
}>;
|
|
62
|
+
device_status?: Record<string, unknown>;
|
|
63
|
+
}
|
|
64
|
+
/** A saved gimbal pose: degrees + zoom ratio. Names are base64 on the wire only. */
|
|
65
|
+
export interface Preset {
|
|
66
|
+
id: number;
|
|
67
|
+
pitch: number;
|
|
68
|
+
yaw: number;
|
|
69
|
+
roll: number;
|
|
70
|
+
ratio: number;
|
|
71
|
+
name: string;
|
|
72
|
+
}
|
|
73
|
+
/** A live gimbal pose in degrees, plus the zoom ratio the pose read carries. */
|
|
74
|
+
export interface Pose {
|
|
75
|
+
yaw: number;
|
|
76
|
+
pitch: number;
|
|
77
|
+
roll: number;
|
|
78
|
+
ratio: number;
|
|
79
|
+
}
|
|
80
|
+
export declare class Tail2HttpError extends Error {
|
|
81
|
+
readonly status: number;
|
|
82
|
+
readonly path: string;
|
|
83
|
+
readonly body: string;
|
|
84
|
+
constructor(status: number, path: string, body: string);
|
|
85
|
+
}
|
|
86
|
+
/**
|
|
87
|
+
* `{"code":200,"err_idx":0}` means ACKNOWLEDGED, not applied — MEASURED
|
|
88
|
+
* 2026-09-26: a rollbias write returned 200 while the portrait motor was in
|
|
89
|
+
* motion and never landed (TAIL2-PROTOCOL.md §8.1). This is the same failure
|
|
90
|
+
* class as the Tiny 2's post-replug vendor mailbox, so every setter here
|
|
91
|
+
* verifies by readback before reporting success, with a bounded retry ladder
|
|
92
|
+
* sized for the actuator involved (the zoom motor and the portrait rotation
|
|
93
|
+
* take seconds, not milliseconds).
|
|
94
|
+
*/
|
|
95
|
+
export interface VerifyOpts {
|
|
96
|
+
attempts?: number;
|
|
97
|
+
delayMs?: number;
|
|
98
|
+
}
|
|
99
|
+
export declare class Tail2Api {
|
|
100
|
+
readonly baseUrl: string;
|
|
101
|
+
private readonly timeoutMs;
|
|
102
|
+
private readonly wsUrl;
|
|
103
|
+
constructor(opts: {
|
|
104
|
+
baseUrl: string;
|
|
105
|
+
timeoutMs?: number;
|
|
106
|
+
});
|
|
107
|
+
private req;
|
|
108
|
+
/**
|
|
109
|
+
* PUT/POST with ack checking. `body` may be an object (JSON.stringify'd)
|
|
110
|
+
* or a pre-built JSON string — evbias needs a float literal like `0.0`
|
|
111
|
+
* that stringifying a number cannot produce (measured 2026-09-30: JSON
|
|
112
|
+
* integers 0 and -1 get 400 "Invalid value type"; 0.0 and -1.0 apply).
|
|
113
|
+
*/
|
|
114
|
+
private send;
|
|
115
|
+
/**
|
|
116
|
+
* Read `read()` until `match()` holds, on a bounded ladder. Returns
|
|
117
|
+
* `settled:false` (NOT a throw) when the ladder runs out — the command was
|
|
118
|
+
* sent and acknowledged, so the caller decides whether that is failure.
|
|
119
|
+
* Mirrors `obsbot_zoom_uvc`'s `settled` contract.
|
|
120
|
+
*/
|
|
121
|
+
verified<T>(read: () => Promise<T>, match: (v: T) => boolean, opts?: VerifyOpts): Promise<{
|
|
122
|
+
settled: boolean;
|
|
123
|
+
value: T;
|
|
124
|
+
}>;
|
|
125
|
+
info(): Promise<Tail2DeviceInfo>;
|
|
126
|
+
/** One-shot status: connect, take the first push, close. No persistent socket. */
|
|
127
|
+
status(): Promise<Tail2Status>;
|
|
128
|
+
ranges(): Promise<Record<string, unknown>>;
|
|
129
|
+
networkConfig(): Promise<Record<string, unknown>>;
|
|
130
|
+
imageState(): Promise<Record<string, unknown>>;
|
|
131
|
+
zoomGet(): Promise<{
|
|
132
|
+
ratio: number;
|
|
133
|
+
}>;
|
|
134
|
+
/**
|
|
135
|
+
* Absolute zoom ratio on the Tail 2's own 1.0–12.0 scale (`GET range`).
|
|
136
|
+
* `speed` is REQUIRED by the firmware (a ratio-only PUT is a 400) — both
|
|
137
|
+
* fields MEASURED 2026-09-26.
|
|
138
|
+
*/
|
|
139
|
+
zoomSet(ratio: number, speed: number, verify?: VerifyOpts): Promise<{
|
|
140
|
+
settled: boolean;
|
|
141
|
+
ratio: number;
|
|
142
|
+
}>;
|
|
143
|
+
/** Gimbal recenter (`POST ptz/reset`). Open-loop: the Tail 2 reports no live pose. */
|
|
144
|
+
recenter(): Promise<void>;
|
|
145
|
+
gimbalSpeed(yaw: number, pitch: number, roll: number): Promise<void>;
|
|
146
|
+
gimbalStop(): Promise<void>;
|
|
147
|
+
gimbalInvertGet(): Promise<{
|
|
148
|
+
enable: boolean;
|
|
149
|
+
}>;
|
|
150
|
+
/** Reverse (invert) control directions. Readback-verified like every write. */
|
|
151
|
+
gimbalInvertSet(enable: boolean, verify?: VerifyOpts): Promise<{
|
|
152
|
+
settled: boolean;
|
|
153
|
+
enable: boolean;
|
|
154
|
+
}>;
|
|
155
|
+
/** Marker name for pose-probe scratch slots, so crashed probes are reusable. */
|
|
156
|
+
static readonly POSE_PROBE_NAME = "pose-probe";
|
|
157
|
+
readPose(verify?: VerifyOpts): Promise<Pose>;
|
|
158
|
+
/**
|
|
159
|
+
* Motorized 90° barrel rotation. Verified against the WS push rather than a
|
|
160
|
+
* REST readback (none exists) — and the readback MUST be tolerant of the
|
|
161
|
+
* motor taking ~1.5s, plus the swallowed-write hazard during motion.
|
|
162
|
+
*/
|
|
163
|
+
portraitSet(enable: boolean, verify?: VerifyOpts): Promise<{
|
|
164
|
+
settled: boolean;
|
|
165
|
+
switch_portrait: boolean;
|
|
166
|
+
}>;
|
|
167
|
+
rollBiasGet(): Promise<{
|
|
168
|
+
angle: number;
|
|
169
|
+
}>;
|
|
170
|
+
/** Roll trim in degrees. MEASURED write + readback 2026-09-26. */
|
|
171
|
+
rollBiasSet(angle: number, verify?: VerifyOpts): Promise<{
|
|
172
|
+
settled: boolean;
|
|
173
|
+
angle: number;
|
|
174
|
+
}>;
|
|
175
|
+
aiModeGet(): Promise<{
|
|
176
|
+
mode: string;
|
|
177
|
+
}>;
|
|
178
|
+
/**
|
|
179
|
+
* `mode` strings are the camera's own enum (bundle-verified, TAIL2-PROTOCOL
|
|
180
|
+
* §3): none | humanTrackingSingleMode | humanTrackingGroupMode |
|
|
181
|
+
* animalTrackingNormal | animalTrackingCloseUp | objectTracking |
|
|
182
|
+
* objectTrackingNormal | objectTrackingCloseUp.
|
|
183
|
+
*/
|
|
184
|
+
aiModeSet(mode: string, verify?: VerifyOpts): Promise<{
|
|
185
|
+
settled: boolean;
|
|
186
|
+
mode: string;
|
|
187
|
+
}>;
|
|
188
|
+
trackSpeedGet(): Promise<{
|
|
189
|
+
speed: string;
|
|
190
|
+
}>;
|
|
191
|
+
/**
|
|
192
|
+
* The Tail 2's own six-speed enum (bundle-verified): superLazy | lazy |
|
|
193
|
+
* slow | fast | crazy | customized. NOT the Tiny 2's standard/sport pair.
|
|
194
|
+
*/
|
|
195
|
+
trackSpeedSet(speed: string, verify?: VerifyOpts): Promise<{
|
|
196
|
+
settled: boolean;
|
|
197
|
+
speed: string;
|
|
198
|
+
}>;
|
|
199
|
+
recordGet(): Promise<{
|
|
200
|
+
recording: "on" | "off";
|
|
201
|
+
}>;
|
|
202
|
+
recordSet(on: boolean, verify?: VerifyOpts): Promise<{
|
|
203
|
+
settled: boolean;
|
|
204
|
+
recording: "on" | "off";
|
|
205
|
+
}>;
|
|
206
|
+
/** Still-photo trigger. Needs storage; the ack says the camera accepted it. */
|
|
207
|
+
captureTrigger(): Promise<void>;
|
|
208
|
+
focusModeGet(): Promise<{
|
|
209
|
+
mode: "afc" | "afs" | "mf";
|
|
210
|
+
}>;
|
|
211
|
+
focusModeSet(mode: "afc" | "afs" | "mf", verify?: VerifyOpts): Promise<{
|
|
212
|
+
settled: boolean;
|
|
213
|
+
mode: "afc" | "afs" | "mf";
|
|
214
|
+
}>;
|
|
215
|
+
focusPositionGet(): Promise<{
|
|
216
|
+
position: number;
|
|
217
|
+
}>;
|
|
218
|
+
focusPositionSet(position: number, verify?: VerifyOpts): Promise<{
|
|
219
|
+
settled: boolean;
|
|
220
|
+
position: number;
|
|
221
|
+
}>;
|
|
222
|
+
focusWindowGet(): Promise<{
|
|
223
|
+
x: number;
|
|
224
|
+
y: number;
|
|
225
|
+
}>;
|
|
226
|
+
/** Move the focus window AND start a point focus (per the vendor doc). AFC/AFS only. */
|
|
227
|
+
focusWindowSet(x: number, y: number, verify?: VerifyOpts): Promise<{
|
|
228
|
+
settled: boolean;
|
|
229
|
+
x: number;
|
|
230
|
+
y: number;
|
|
231
|
+
}>;
|
|
232
|
+
/**
|
|
233
|
+
* Tap-to-track (MEASURED 2026-09-30, undocumented in the Tail 2's own doc):
|
|
234
|
+
* POST a normalized coordinate and the camera engages tracking on the
|
|
235
|
+
* subject there — from mode none it armed humanTrackingSingleMode on its
|
|
236
|
+
* own. Fire-and-ack; which mode engages depends on what (if anything) is
|
|
237
|
+
* at the coordinate, so the caller reads ai mode back when it matters.
|
|
238
|
+
*/
|
|
239
|
+
targetSelect(x: number, y: number): Promise<void>;
|
|
240
|
+
exposureModeGet(): Promise<{
|
|
241
|
+
mode: "manual" | "auto";
|
|
242
|
+
}>;
|
|
243
|
+
exposureModeSet(mode: "manual" | "auto", verify?: VerifyOpts): Promise<{
|
|
244
|
+
settled: boolean;
|
|
245
|
+
mode: "manual" | "auto";
|
|
246
|
+
}>;
|
|
247
|
+
exposureAutoModeGet(): Promise<{
|
|
248
|
+
mode: "global" | "face";
|
|
249
|
+
}>;
|
|
250
|
+
exposureAutoModeSet(mode: "global" | "face", verify?: VerifyOpts): Promise<{
|
|
251
|
+
settled: boolean;
|
|
252
|
+
mode: "global" | "face";
|
|
253
|
+
}>;
|
|
254
|
+
exposureEvbiasGet(): Promise<{
|
|
255
|
+
evbias: number;
|
|
256
|
+
}>;
|
|
257
|
+
exposureEvbiasSet(evbias: number, verify?: VerifyOpts): Promise<{
|
|
258
|
+
settled: boolean;
|
|
259
|
+
evbias: number;
|
|
260
|
+
}>;
|
|
261
|
+
exposureIsoGet(): Promise<{
|
|
262
|
+
iso: number;
|
|
263
|
+
}>;
|
|
264
|
+
exposureIsoSet(iso: number, verify?: VerifyOpts): Promise<{
|
|
265
|
+
settled: boolean;
|
|
266
|
+
iso: number;
|
|
267
|
+
}>;
|
|
268
|
+
exposureShutterGet(): Promise<{
|
|
269
|
+
shutter: string;
|
|
270
|
+
}>;
|
|
271
|
+
exposureShutterSet(shutter: string, verify?: VerifyOpts): Promise<{
|
|
272
|
+
settled: boolean;
|
|
273
|
+
shutter: string;
|
|
274
|
+
}>;
|
|
275
|
+
styleGet(): Promise<{
|
|
276
|
+
mode: string;
|
|
277
|
+
brightness: number;
|
|
278
|
+
contrast: number;
|
|
279
|
+
hue: number;
|
|
280
|
+
saturation: number;
|
|
281
|
+
sharpness: number;
|
|
282
|
+
}>;
|
|
283
|
+
styleSet(control: "brightness" | "contrast" | "hue" | "saturation" | "sharpness", value: number, verify?: VerifyOpts): Promise<{
|
|
284
|
+
settled: boolean;
|
|
285
|
+
value: number;
|
|
286
|
+
mode: string;
|
|
287
|
+
}>;
|
|
288
|
+
styleModeSet(mode: "standard" | "outdoor" | "pastel" | "manual", verify?: VerifyOpts): Promise<{
|
|
289
|
+
settled: boolean;
|
|
290
|
+
mode: string;
|
|
291
|
+
}>;
|
|
292
|
+
hdrGet(): Promise<{
|
|
293
|
+
control: "on" | "off";
|
|
294
|
+
}>;
|
|
295
|
+
hdrSet(on: boolean, verify?: VerifyOpts): Promise<{
|
|
296
|
+
settled: boolean;
|
|
297
|
+
control: "on" | "off";
|
|
298
|
+
}>;
|
|
299
|
+
wbConfigGet(): Promise<{
|
|
300
|
+
mode: string;
|
|
301
|
+
temperature: number;
|
|
302
|
+
}>;
|
|
303
|
+
wbConfigSet(mode: "auto" | "daylight" | "fluorescent" | "tungsten" | "cloudy" | "manual", temperature: number | undefined, verify?: VerifyOpts): Promise<{
|
|
304
|
+
settled: boolean;
|
|
305
|
+
mode: string;
|
|
306
|
+
temperature: number;
|
|
307
|
+
}>;
|
|
308
|
+
streamControlGet(): Promise<{
|
|
309
|
+
control: "ndi" | "rtsp" | "srt" | "off";
|
|
310
|
+
}>;
|
|
311
|
+
streamControlSet(control: "ndi" | "rtsp" | "srt" | "off", verify?: VerifyOpts): Promise<{
|
|
312
|
+
settled: boolean;
|
|
313
|
+
control: "ndi" | "rtsp" | "srt" | "off";
|
|
314
|
+
}>;
|
|
315
|
+
onlyMeGet(): Promise<{
|
|
316
|
+
enable: boolean;
|
|
317
|
+
}>;
|
|
318
|
+
onlyMeSet(enable: boolean, verify?: VerifyOpts): Promise<{
|
|
319
|
+
settled: boolean;
|
|
320
|
+
enable: boolean;
|
|
321
|
+
}>;
|
|
322
|
+
audioVolumeGet(): Promise<{
|
|
323
|
+
volume: number;
|
|
324
|
+
}>;
|
|
325
|
+
audioVolumeSet(volume: number, verify?: VerifyOpts): Promise<{
|
|
326
|
+
settled: boolean;
|
|
327
|
+
volume: number;
|
|
328
|
+
}>;
|
|
329
|
+
audioMuteGet(): Promise<{
|
|
330
|
+
enable: boolean;
|
|
331
|
+
}>;
|
|
332
|
+
audioMuteSet(enable: boolean, verify?: VerifyOpts): Promise<{
|
|
333
|
+
settled: boolean;
|
|
334
|
+
enable: boolean;
|
|
335
|
+
}>;
|
|
336
|
+
/**
|
|
337
|
+
* A saved pose: angles in DEGREES plus zoom ratio — the same units the
|
|
338
|
+
* tools speak. `name` is base64 on the wire; encode/decode lives here so
|
|
339
|
+
* callers never see it raw.
|
|
340
|
+
*/
|
|
341
|
+
presetsGet(): Promise<Preset[]>;
|
|
342
|
+
/**
|
|
343
|
+
* `PUT ptz/preset {"operation": ..., "id": ..., "name": base64}` — one
|
|
344
|
+
* endpoint, four operations (grammar decoded from the camera's own web
|
|
345
|
+
* bundle and hardware-verified 2026-09-26; see TAIL2-PROTOCOL.md §3).
|
|
346
|
+
* IDs are 0-based (0–2); the tools expose 1-based slots for consistency
|
|
347
|
+
* with the Tiny 2's preset tools.
|
|
348
|
+
*
|
|
349
|
+
* `set` saves the CURRENT live pose — there is NO explicit-pose write
|
|
350
|
+
* anywhere in this API (measured), and `set` on an occupied slot
|
|
351
|
+
* OVERWRITES it (unlike the Tiny 2's create-once slots).
|
|
352
|
+
*/
|
|
353
|
+
private presetOp;
|
|
354
|
+
/**
|
|
355
|
+
* Save the current live pose into slot `id`. The preset LIST lags the
|
|
356
|
+
* write by up to ~1s (measured), so verification is a ladder, and the
|
|
357
|
+
* pose itself can't be verified at all — the camera reports no live pose,
|
|
358
|
+
* so "the slot exists afterwards" is the honest success criterion.
|
|
359
|
+
*/
|
|
360
|
+
presetSave(id: number, name: string, verify?: VerifyOpts): Promise<{
|
|
361
|
+
settled: boolean;
|
|
362
|
+
presets: Preset[];
|
|
363
|
+
}>;
|
|
364
|
+
/**
|
|
365
|
+
* Recall slot `id`. Physical arrival is verifiable through exactly one
|
|
366
|
+
* observable: the preset's zoom ratio landing in the live zoom_ratio (the
|
|
367
|
+
* WS push carries it). The gimbal axes themselves are open-loop.
|
|
368
|
+
*/
|
|
369
|
+
presetRecall(id: number, verify?: VerifyOpts): Promise<{
|
|
370
|
+
settled: boolean;
|
|
371
|
+
zoom: number;
|
|
372
|
+
}>;
|
|
373
|
+
presetDelete(id: number, verify?: VerifyOpts): Promise<{
|
|
374
|
+
settled: boolean;
|
|
375
|
+
presets: Preset[];
|
|
376
|
+
}>;
|
|
377
|
+
presetRename(id: number, name: string, verify?: VerifyOpts): Promise<{
|
|
378
|
+
settled: boolean;
|
|
379
|
+
presets: Preset[];
|
|
380
|
+
}>;
|
|
381
|
+
}
|