@rebind.gg/mcp-server 0.2.3 → 0.3.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 +10 -4
- package/package.json +1 -1
- package/src/index.ts +96 -28
- package/src/prompts.ts +4 -0
- package/src/rebind.d.luau +640 -152
package/README.md
CHANGED
|
@@ -5,7 +5,9 @@ Stdio MCP server that turns [Rebind](https://rebind.gg) into a computer-use tool
|
|
|
5
5
|
**Requirements**
|
|
6
6
|
|
|
7
7
|
- [Bun](https://bun.sh) >= 1.1 (the server runs via `bunx`)
|
|
8
|
-
- The [Rebind app](https://rebind.gg/download) running the free [Remote Control](https://www.rebind.gg/marketplace/script_AAHteeDcYPGOT7GfXZ_OK) package (`rebind install @rebind/remote-control`)
|
|
8
|
+
- The [Rebind app](https://rebind.gg/download) running the free [Remote Control](https://www.rebind.gg/marketplace/script_AAHteeDcYPGOT7GfXZ_OK) package (`rebind install @rebind/remote-control --allow`)
|
|
9
|
+
|
|
10
|
+
The first time the server sends a command, Remote Control asks on that computer whether to allow **Rebind MCP server**. Allow it once; the name is remembered. Tool calls fail with `awaiting_approval` until you answer. Remote Control accepts connections from its own computer only unless **Local only** is turned off in its Options, which an agent on another computer or inside WSL needs. `run_lua`, `focus_window`, `position_window` and `read_page` also need **Allow custom Luau** turned on there; the server reads that setting at startup.
|
|
9
11
|
|
|
10
12
|
## Install
|
|
11
13
|
|
|
@@ -41,7 +43,7 @@ Any MCP client takes the stdio block directly:
|
|
|
41
43
|
bunx @rebind.gg/mcp-server --selftest
|
|
42
44
|
```
|
|
43
45
|
|
|
44
|
-
Connects, takes a capture, and reports the display
|
|
46
|
+
Connects, waits up to a minute for the approval prompt on a first run, takes a capture, and reports the display. It is the fastest way to catch the #1 first-run failure (relay not loaded).
|
|
45
47
|
|
|
46
48
|
## Tools
|
|
47
49
|
|
|
@@ -55,7 +57,7 @@ Connects, takes a capture, and reports the display — the fastest way to catch
|
|
|
55
57
|
| `type` | Type text into the focused element. |
|
|
56
58
|
| `key` | Press a key or combo, e.g. `Enter`, `LCtrl+L`, `LAlt+Tab`. |
|
|
57
59
|
| `scroll` | Scroll at the cursor. Positive scrolls down, negative up. `unit` is `wheel` (default, fine wheel clicks) or `page` (one PageDown or PageUp per unit, capped at 10). |
|
|
58
|
-
| `read_page` | Extract the focused browser's current page as structured text (URL, forms, interactive elements, plain text) via an address-bar bookmarklet; the full dump, including cleaned HTML, lands in the clipboard. The result is read back through AppleScript (`URL of active tab of front window`), so the tool is registered only when the relay host is macOS, and the front browser must answer that query. Safari is detected but blocks the bookmarklet path. |
|
|
60
|
+
| `read_page` | Extract the focused browser's current page as structured text (URL, forms, interactive elements, plain text) via an address-bar bookmarklet; the full dump, including cleaned HTML, lands in the clipboard. The result is read back through AppleScript (`URL of active tab of front window`), so the tool is registered only when the relay host is macOS and **Allow custom Luau** is on, and the front browser must answer that query. Safari is detected but blocks the bookmarklet path. |
|
|
59
61
|
| `meditate` | Research a problem page until a reasoning model has the data to solve it: fetches the URL directly, pulls the script bundles behind a JS shell so its API endpoints are visible, fetches those endpoints and assets, and reads the live page with vision. The browser steps (rendering a JS shell, same-origin fetches through the page, and the vision pass) need a macOS relay; elsewhere it reads pages over HTTP only. Returns a markdown dossier plus JSON `{error, problem, requirements, plan, submittable, form, live_captcha_hint, confidence, sources, assets, pending_fetch, notes, cost_usd}`. `error` is non-null when no problem could be identified or the page could not be read; partial data is still returned. Gated behind `REBIND_ALLOW_DELEGATION=1` (spends OpenRouter credits). See the pipeline below. |
|
|
60
62
|
| `run_lua` | Run a Luau script on the connected machine and return its `return` value as JSON — the fast path for any deterministic sequence (launch apps, place windows, shell commands, pixel search). |
|
|
61
63
|
| `lua_docs` | Full Luau SDK type definitions for `run_lua`. |
|
|
@@ -84,7 +86,11 @@ Connects, takes a capture, and reports the display — the fastest way to catch
|
|
|
84
86
|
|
|
85
87
|
**One coordinate space.** All results are reported in the pixel space of the last screenshot — the same space the model emits — so no rescaling math ever falls on the model.
|
|
86
88
|
|
|
87
|
-
**Machine-aware orientation.** At startup the server probes the connected machine through the relay (
|
|
89
|
+
**Machine-aware orientation.** At startup the server reads the OS from Remote Control's `hello` banner and, when custom Luau is allowed, probes the connected machine through the relay (available shell tools, installed apps) and serves it as the MCP `instructions` block, along with a policy: prefer `run_lua` for deterministic work, keyboard over mouse, and screenshots last. The full Luau SDK type definitions are embedded inline so the model never has to guess `run_lua` APIs (including the coroutine-safe HID path: `HID.Down`/`Up`/`MoveTo`/`Combo` work in a one-shot chunk, `HID.Press` does not). The OS is read from the relay, not `process.platform`, so the guidance is correct even when the server and the relay run on different machines.
|
|
90
|
+
|
|
91
|
+
## Save what worked
|
|
92
|
+
|
|
93
|
+
When the user wants a working sequence kept, the server's instructions tell the agent to save it as a Rebind script that runs with no agent: `rebind init <dir>`, the sequence in `main.luau` bound to a key, `[runtime] permissions` in `rebind.toml`, then `rebind check <dir>`, `rebind pack <dir>`, `rebind install <name>.rbp --allow` (`--force` to replace) and `rebind script start packages/<name>/main.luau`, on the computer running Rebind.
|
|
88
94
|
|
|
89
95
|
## Solve pipeline
|
|
90
96
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@rebind.gg/mcp-server",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.3.0",
|
|
4
4
|
"description": "MCP server exposing Rebind as computer-use tools: screenshot, verified click, type, key, scroll, and window control over the Remote Control protocol.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"bin": {
|
package/src/index.ts
CHANGED
|
@@ -10,7 +10,7 @@ import { appendFileSync } from "node:fs";
|
|
|
10
10
|
import { homedir } from "node:os";
|
|
11
11
|
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
|
|
12
12
|
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
|
|
13
|
-
import { RebindRemote } from "@rebind.gg/client-ts";
|
|
13
|
+
import { RebindRemote, ServerError } from "@rebind.gg/client-ts";
|
|
14
14
|
import { z } from "zod";
|
|
15
15
|
import pkg from "../package.json";
|
|
16
16
|
import { mapToImage } from "./coords.ts";
|
|
@@ -29,6 +29,7 @@ import {
|
|
|
29
29
|
PROBE_CLIS_CMD,
|
|
30
30
|
probeAppsCmd,
|
|
31
31
|
RUN_LUA_DESC,
|
|
32
|
+
SAVE_WORK_DOCTRINE,
|
|
32
33
|
toolPriority,
|
|
33
34
|
} from "./prompts.ts";
|
|
34
35
|
import { CLICK_EPS_PX, Session } from "./session.ts";
|
|
@@ -266,16 +267,32 @@ function assetsBlock(
|
|
|
266
267
|
.join("\n\n");
|
|
267
268
|
}
|
|
268
269
|
|
|
270
|
+
// The SDK as run_lua scripts see it: the typedef without its rb block, so the
|
|
271
|
+
// model writes the v1 names every relay version accepts (rb needs 3.9.0).
|
|
272
|
+
// src/rebind.d.luau is a byte-identical copy of packages/lua-sdk/types/
|
|
273
|
+
// rebind.d.luau shipped in the package; tests/lua-docs-sync.test.ts guards it.
|
|
274
|
+
async function v1Sdk(): Promise<string> {
|
|
275
|
+
const typedef = await Bun.file(
|
|
276
|
+
new URL("./rebind.d.luau", import.meta.url),
|
|
277
|
+
).text();
|
|
278
|
+
return typedef.replace(/^-- rb\n[\s\S]*?(?=^-- v1 names\n)/m, "");
|
|
279
|
+
}
|
|
280
|
+
|
|
269
281
|
// Server-level orientation (MCP `instructions`), built at startup. Every fact
|
|
270
282
|
// is probed THROUGH the relay connection — process.platform is the wrong
|
|
271
283
|
// signal because this process may run on a different machine than the relay.
|
|
272
284
|
// Probes are best-effort: a locked-down remote (no exec permission) just
|
|
273
285
|
// yields a shorter card. Machine facts and general technique only.
|
|
274
|
-
// The
|
|
286
|
+
// The OS comes from the hello banner when the server reports it (Remote
|
|
287
|
+
// Control 0.3.0+), so it is right even with lua.exec off; older servers fall
|
|
288
|
+
// back to a uname probe. When the banner says lua.exec is off, the probes and
|
|
289
|
+
// read_page (both built on lua.exec) are skipped.
|
|
290
|
+
// The OS is returned alongside: tools that pick a shortcut modifier
|
|
275
291
|
// (read_page) need it, and re-probing would be a second relay round-trip.
|
|
276
292
|
async function buildInstructions(
|
|
277
293
|
client: RebindRemote,
|
|
278
|
-
|
|
294
|
+
hello: Hello,
|
|
295
|
+
): Promise<{ instructions: string; os: OS; hasLua: boolean }> {
|
|
279
296
|
const sh = async (cmd: string): Promise<string> => {
|
|
280
297
|
try {
|
|
281
298
|
const r = await client.luaExec(
|
|
@@ -286,23 +303,27 @@ async function buildInstructions(
|
|
|
286
303
|
return "";
|
|
287
304
|
}
|
|
288
305
|
};
|
|
289
|
-
const
|
|
290
|
-
const os: OS =
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
? "
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
306
|
+
const hasLua = hello.gates?.lua !== false;
|
|
307
|
+
const os: OS =
|
|
308
|
+
HELLO_OS[hello.platform ?? ""] ??
|
|
309
|
+
(await (async () => {
|
|
310
|
+
const uname = hasLua ? await sh("uname") : "";
|
|
311
|
+
return /darwin/i.test(uname)
|
|
312
|
+
? "macOS"
|
|
313
|
+
: /linux/i.test(uname)
|
|
314
|
+
? "Linux"
|
|
315
|
+
: "Windows";
|
|
316
|
+
})());
|
|
317
|
+
const probe = hasLua && os !== "Windows";
|
|
318
|
+
const clis = probe ? await sh(PROBE_CLIS_CMD) : "";
|
|
319
|
+
const apps = probe ? await sh(probeAppsCmd(os)) : "";
|
|
297
320
|
// Embed the full Luau SDK inline so the model never has to guess run_lua APIs
|
|
298
321
|
// or make a lua_docs round-trip. It carries the coroutine-safety notes that
|
|
299
322
|
// matter for HID: HID.Press sleeps and is coroutine-only, but HID.Down/Up/
|
|
300
323
|
// MoveTo/Combo are synchronous and DO work in a one-shot chunk — so a mouse
|
|
301
324
|
// click (e.g. ticking a checkbox) is scriptable as
|
|
302
325
|
// `HID.MoveTo(x,y); HID.Down("Mouse1"); HID.Up("Mouse1")`.
|
|
303
|
-
const sdk = await
|
|
304
|
-
new URL("./rebind.d.luau", import.meta.url),
|
|
305
|
-
).text();
|
|
326
|
+
const sdk = await v1Sdk();
|
|
306
327
|
const instructions = [
|
|
307
328
|
`You control a real ${os} computer through Rebind. Keyboard shortcuts use ${modifierNote(os)}.`,
|
|
308
329
|
clis
|
|
@@ -311,8 +332,9 @@ async function buildInstructions(
|
|
|
311
332
|
apps
|
|
312
333
|
? `GUI applications installed (open via ${openAppHow(os)}): ${apps}`
|
|
313
334
|
: "",
|
|
314
|
-
`Work in as few steps as possible
|
|
315
|
-
|
|
335
|
+
`Work in as few steps as possible.${hasLua ? ` ${DETERMINISTIC_WORK_DOCTRINE}` : ""}`,
|
|
336
|
+
SAVE_WORK_DOCTRINE,
|
|
337
|
+
toolPriority(hasLua),
|
|
316
338
|
BATCHING_DOCTRINE,
|
|
317
339
|
"When you do need to see the screen, prefer screenshot_window over a full-display screenshot — a window shot costs roughly a quarter of the image tokens. Every screenshot stays in your context for the rest of the session, so each one you take keeps costing you on every later turn: verify with values (clipboard, file contents, run_lua reads) where possible.",
|
|
318
340
|
guiTips(os),
|
|
@@ -321,14 +343,34 @@ async function buildInstructions(
|
|
|
321
343
|
]
|
|
322
344
|
.filter(Boolean)
|
|
323
345
|
.join("\n");
|
|
324
|
-
return { instructions, os };
|
|
346
|
+
return { instructions, os, hasLua };
|
|
325
347
|
}
|
|
326
348
|
|
|
349
|
+
/** the fields of the Remote Control hello banner this server reads */
|
|
350
|
+
type Hello = { platform?: string; gates?: { lua?: boolean } };
|
|
351
|
+
|
|
352
|
+
const HELLO_OS: Record<string, OS> = {
|
|
353
|
+
macos: "macOS",
|
|
354
|
+
linux: "Linux",
|
|
355
|
+
windows: "Windows",
|
|
356
|
+
};
|
|
357
|
+
|
|
358
|
+
/** the name Remote Control shows in its approval prompt and remembers */
|
|
359
|
+
const APP_NAME = "Rebind MCP server";
|
|
360
|
+
|
|
327
361
|
async function main() {
|
|
328
362
|
const url = process.env.REBIND_URL ?? "ws://127.0.0.1:19561";
|
|
329
|
-
|
|
363
|
+
// name this client on every connect, reconnects included: Remote Control
|
|
364
|
+
// approves programs by the name they declare in hello. setState fires before
|
|
365
|
+
// connect() resolves, so the hello goes out ahead of any tool call.
|
|
366
|
+
let hello: Promise<Hello> = Promise.resolve({});
|
|
367
|
+
const client: RebindRemote = new RebindRemote(url, {
|
|
330
368
|
token: process.env.REBIND_TOKEN ?? "",
|
|
331
369
|
timeoutMs: 15000,
|
|
370
|
+
onStateChange: (s) => {
|
|
371
|
+
if (s !== "connected") return;
|
|
372
|
+
hello = client.call<Hello>("hello", { app: APP_NAME }).catch(() => ({}));
|
|
373
|
+
},
|
|
332
374
|
});
|
|
333
375
|
|
|
334
376
|
// --selftest: verify the relay is reachable and capturing, then exit. Used by
|
|
@@ -337,15 +379,41 @@ async function main() {
|
|
|
337
379
|
if (process.argv.includes("--selftest")) {
|
|
338
380
|
try {
|
|
339
381
|
await client.connect();
|
|
340
|
-
|
|
382
|
+
await hello;
|
|
383
|
+
// a first connection waits on the approval prompt in Remote Control:
|
|
384
|
+
// retry for up to a minute while the person decides.
|
|
385
|
+
const deadline = Date.now() + 60_000;
|
|
386
|
+
let cap: Awaited<ReturnType<RebindRemote["screenCapture"]>>;
|
|
387
|
+
for (;;) {
|
|
388
|
+
try {
|
|
389
|
+
cap = await client.screenCapture({});
|
|
390
|
+
break;
|
|
391
|
+
} catch (e) {
|
|
392
|
+
const waiting =
|
|
393
|
+
e instanceof ServerError && e.code === "awaiting_approval";
|
|
394
|
+
if (!waiting || Date.now() + 2000 > deadline) throw e;
|
|
395
|
+
console.error(
|
|
396
|
+
`selftest: allow "${APP_NAME}" in the Remote Control prompt on that computer...`,
|
|
397
|
+
);
|
|
398
|
+
await sleep(2000);
|
|
399
|
+
}
|
|
400
|
+
}
|
|
341
401
|
console.error(
|
|
342
402
|
`selftest OK: relay ${url}, display ${cap.display.index} ${cap.display.width}x${cap.display.height}`,
|
|
343
403
|
);
|
|
344
404
|
process.exit(0);
|
|
345
405
|
} catch (e) {
|
|
406
|
+
if (e instanceof ServerError) {
|
|
407
|
+
console.error(
|
|
408
|
+
e.code === "awaiting_approval" || e.code === "not_approved"
|
|
409
|
+
? `selftest FAILED: "${APP_NAME}" was not allowed in Remote Control's prompt on ${url}. (${e.message})`
|
|
410
|
+
: `selftest FAILED: Remote Control on ${url} refused the capture. (${e.message})`,
|
|
411
|
+
);
|
|
412
|
+
process.exit(1);
|
|
413
|
+
}
|
|
346
414
|
console.error(
|
|
347
415
|
`selftest FAILED: Rebind relay not reachable on ${url}.\n` +
|
|
348
|
-
`Start Rebind and the Remote Control package (rebind install @rebind/remote-control).\n(${e})`,
|
|
416
|
+
`Start Rebind and the Remote Control package (rebind install @rebind/remote-control --allow).\n(${e})`,
|
|
349
417
|
);
|
|
350
418
|
process.exit(1);
|
|
351
419
|
}
|
|
@@ -355,7 +423,10 @@ async function main() {
|
|
|
355
423
|
|
|
356
424
|
const session = new Session(client);
|
|
357
425
|
|
|
358
|
-
const { instructions, os } = await buildInstructions(
|
|
426
|
+
const { instructions, os, hasLua } = await buildInstructions(
|
|
427
|
+
client,
|
|
428
|
+
await hello,
|
|
429
|
+
);
|
|
359
430
|
const server = new McpServer(
|
|
360
431
|
{ name: "rebind", version: pkg.version },
|
|
361
432
|
{ instructions },
|
|
@@ -1071,9 +1142,9 @@ return { ok = Window.IsActive(h), name = name }
|
|
|
1071
1142
|
);
|
|
1072
1143
|
|
|
1073
1144
|
// read_page finds the front app through App.Front and reads its result back
|
|
1074
|
-
// through AppleScript (tabUrl)
|
|
1075
|
-
//
|
|
1076
|
-
if (os === "macOS") {
|
|
1145
|
+
// through AppleScript (tabUrl), both over lua.exec: offered only on a macOS
|
|
1146
|
+
// relay with lua.exec on, so never where it fails.
|
|
1147
|
+
if (os === "macOS" && hasLua) {
|
|
1077
1148
|
register(
|
|
1078
1149
|
"read_page",
|
|
1079
1150
|
{
|
|
@@ -1146,10 +1217,7 @@ return { ok = Window.IsActive(h), name = name }
|
|
|
1146
1217
|
{
|
|
1147
1218
|
description: LUA_DOCS_DESC,
|
|
1148
1219
|
},
|
|
1149
|
-
|
|
1150
|
-
// the package; tests/lua-docs-sync.test.ts guards against drift
|
|
1151
|
-
async () =>
|
|
1152
|
-
text(await Bun.file(new URL("./rebind.d.luau", import.meta.url)).text()),
|
|
1220
|
+
async () => text(await v1Sdk()),
|
|
1153
1221
|
);
|
|
1154
1222
|
|
|
1155
1223
|
// Server-side subagents. Gated: a stock install ships without them. They make
|
package/src/prompts.ts
CHANGED
|
@@ -69,6 +69,10 @@ export function guiTips(os: OS): string {
|
|
|
69
69
|
export const DETERMINISTIC_WORK_DOCTRINE =
|
|
70
70
|
"run_lua is your PRIMARY tool — reach for it FIRST and use it aggressively. It exposes the ENTIRE machine SDK (every namespace below), so almost anything a task needs — file operations, text processing, arithmetic, clipboard, launching and positioning apps, shell commands, reading the screen — is ONE run_lua call, never a click loop. Do not operate calculators, browsers, or file managers through the GUI when a script can do the work. Fall back to screenshot/click ONLY for state that exists purely on screen and cannot be scripted.";
|
|
71
71
|
|
|
72
|
+
/** MCP server only (the bench keeps its own prompt): keep what worked. */
|
|
73
|
+
export const SAVE_WORK_DOCTRINE =
|
|
74
|
+
"When a sequence works and the user wants to keep it, save it as a Rebind script so it runs again with no agent and no tokens. On the computer running Rebind: `rebind init <dir>` scaffolds rebind.toml and main.luau; put the sequence in main.luau bound to a key (Bind or OnDown; hooks never fire inside run_lua, they do in an installed script); add `[runtime] permissions = [...]` to rebind.toml listing only what it uses; then run `rebind check <dir>`, `rebind pack <dir>` (writes <name>.rbp in the current directory), `rebind install <name>.rbp --allow` (it prints what the package asks for; add --force to replace an earlier install) and `rebind script start packages/<name>/main.luau`. Tell the user which key runs it, and that it runs until Rebind restarts and can be started again from Rebind's scripts list.";
|
|
75
|
+
|
|
72
76
|
// --- tool descriptions (shared only where the underlying behavior is identical
|
|
73
77
|
// across both surfaces: run_lua, lua_docs, and key all hit the same relay) ---
|
|
74
78
|
|
package/src/rebind.d.luau
CHANGED
|
@@ -1,18 +1,28 @@
|
|
|
1
|
-
--
|
|
2
|
-
--
|
|
3
|
-
--
|
|
1
|
+
-- Rebind SDK type definitions for the Luau language server: autocomplete,
|
|
2
|
+
-- hover docs and type checking for every SDK function.
|
|
3
|
+
-- Reference this file in your .luaurc: { "languageMode": "strict", "paths": ["types"] }
|
|
4
|
+
--
|
|
5
|
+
-- The rb names need Rebind 3.9.0 or later; the v1 names work on every
|
|
6
|
+
-- version.
|
|
4
7
|
|
|
5
|
-
-- handle types
|
|
8
|
+
-- handle types. A handle answers to its v1 method names on every version,
|
|
9
|
+
-- and to their snake_case forms from Rebind 3.9.0.
|
|
6
10
|
|
|
7
11
|
export type TaskHandle = {
|
|
8
12
|
Cancel: (self: TaskHandle) -> (),
|
|
9
13
|
IsRunning: (self: TaskHandle) -> boolean,
|
|
14
|
+
stop: (self: TaskHandle) -> (),
|
|
15
|
+
is_running: (self: TaskHandle) -> boolean,
|
|
10
16
|
}
|
|
11
17
|
|
|
12
18
|
export type TimerHandle = {
|
|
13
19
|
Cancel: (self: TimerHandle) -> (),
|
|
14
20
|
Pause: (self: TimerHandle) -> (),
|
|
15
21
|
Resume: (self: TimerHandle) -> (),
|
|
22
|
+
stop: (self: TimerHandle) -> (),
|
|
23
|
+
pause: (self: TimerHandle) -> (),
|
|
24
|
+
resume: (self: TimerHandle) -> (),
|
|
25
|
+
is_running: (self: TimerHandle) -> boolean,
|
|
16
26
|
}
|
|
17
27
|
|
|
18
28
|
export type MacroHandle = {
|
|
@@ -21,18 +31,34 @@ export type MacroHandle = {
|
|
|
21
31
|
Resume: (self: MacroHandle) -> (),
|
|
22
32
|
IsPlaying: (self: MacroHandle) -> boolean,
|
|
23
33
|
GetProgress: (self: MacroHandle) -> number,
|
|
34
|
+
-- coroutine-only: waits until the macro finishes
|
|
35
|
+
Wait: (self: MacroHandle) -> (),
|
|
36
|
+
stop: (self: MacroHandle) -> (),
|
|
37
|
+
pause: (self: MacroHandle) -> (),
|
|
38
|
+
resume: (self: MacroHandle) -> (),
|
|
39
|
+
is_playing: (self: MacroHandle) -> boolean,
|
|
40
|
+
get_progress: (self: MacroHandle) -> number,
|
|
41
|
+
-- coroutine-only: waits until the macro finishes
|
|
42
|
+
wait: (self: MacroHandle) -> (),
|
|
24
43
|
}
|
|
25
44
|
|
|
26
45
|
export type BindHandle = {
|
|
27
46
|
unbind: (self: BindHandle) -> (),
|
|
47
|
+
stop: (self: BindHandle) -> (),
|
|
28
48
|
disable: (self: BindHandle) -> (),
|
|
29
49
|
enable: (self: BindHandle) -> (),
|
|
30
50
|
enabled: boolean,
|
|
31
51
|
}
|
|
32
52
|
|
|
53
|
+
-- returned by rb.on (Rebind 3.9.0 and later); stop removes the handler
|
|
54
|
+
export type EventHandle = {
|
|
55
|
+
stop: (self: EventHandle) -> (),
|
|
56
|
+
}
|
|
57
|
+
|
|
33
58
|
export type ServerHandle = {
|
|
34
59
|
port: number,
|
|
35
60
|
Stop: (self: ServerHandle) -> (),
|
|
61
|
+
stop: (self: ServerHandle) -> (),
|
|
36
62
|
}
|
|
37
63
|
|
|
38
64
|
-- UDP: socket handle returned by Net.UDPListen. SendTo sends from the bound
|
|
@@ -41,6 +67,8 @@ export type UdpHandle = {
|
|
|
41
67
|
port: number,
|
|
42
68
|
SendTo: (self: UdpHandle, ip: string, port: number, bytes: string) -> boolean,
|
|
43
69
|
Stop: (self: UdpHandle) -> (),
|
|
70
|
+
send_to: (self: UdpHandle, ip: string, port: number, bytes: string) -> boolean,
|
|
71
|
+
stop: (self: UdpHandle) -> (),
|
|
44
72
|
}
|
|
45
73
|
|
|
46
74
|
-- WebSocket: server-side per-connection handle passed to OnConnect/OnMessage/OnClose.
|
|
@@ -50,6 +78,9 @@ export type WsClient = {
|
|
|
50
78
|
Send: (self: WsClient, text: string) -> (),
|
|
51
79
|
SendBinary: (self: WsClient, bytes: string) -> (),
|
|
52
80
|
Close: (self: WsClient) -> (),
|
|
81
|
+
send: (self: WsClient, text: string) -> (),
|
|
82
|
+
send_binary: (self: WsClient, bytes: string) -> (),
|
|
83
|
+
close: (self: WsClient) -> (),
|
|
53
84
|
}
|
|
54
85
|
|
|
55
86
|
-- WebSocket: server handle returned by Net.WSListen.
|
|
@@ -59,6 +90,10 @@ export type WsServerHandle = {
|
|
|
59
90
|
BroadcastBinary: (self: WsServerHandle, bytes: string) -> (),
|
|
60
91
|
ClientCount: (self: WsServerHandle) -> number,
|
|
61
92
|
Stop: (self: WsServerHandle) -> (),
|
|
93
|
+
broadcast: (self: WsServerHandle, text: string) -> (),
|
|
94
|
+
broadcast_binary: (self: WsServerHandle, bytes: string) -> (),
|
|
95
|
+
client_count: (self: WsServerHandle) -> number,
|
|
96
|
+
stop: (self: WsServerHandle) -> (),
|
|
62
97
|
}
|
|
63
98
|
|
|
64
99
|
-- WebSocket: outbound-connection handle returned by Net.WSConnect.
|
|
@@ -66,21 +101,32 @@ export type WsConnectHandle = {
|
|
|
66
101
|
Send: (self: WsConnectHandle, text: string) -> (),
|
|
67
102
|
SendBinary: (self: WsConnectHandle, bytes: string) -> (),
|
|
68
103
|
Close: (self: WsConnectHandle) -> (),
|
|
104
|
+
send: (self: WsConnectHandle, text: string) -> (),
|
|
105
|
+
send_binary: (self: WsConnectHandle, bytes: string) -> (),
|
|
106
|
+
close: (self: WsConnectHandle) -> (),
|
|
69
107
|
}
|
|
70
108
|
|
|
71
109
|
-- WebSocket: server event-handler table passed to Net.WSListen.
|
|
72
110
|
-- All fields are optional; handlers that are absent are never called.
|
|
111
|
+
-- From Rebind 3.9.0 each handler is also read under its snake_case name.
|
|
73
112
|
export type WsListenHandlers = {
|
|
74
113
|
OnConnect: ((client: WsClient) -> ())?,
|
|
75
114
|
OnMessage: ((client: WsClient, payload: string, isBinary: boolean) -> ())?,
|
|
76
115
|
OnClose: ((client: WsClient) -> ())?,
|
|
116
|
+
on_connect: ((client: WsClient) -> ())?,
|
|
117
|
+
on_message: ((client: WsClient, payload: string, is_binary: boolean) -> ())?,
|
|
118
|
+
on_close: ((client: WsClient) -> ())?,
|
|
77
119
|
}
|
|
78
120
|
|
|
79
121
|
-- WebSocket: client event-handler table passed to Net.WSConnect.
|
|
122
|
+
-- From Rebind 3.9.0 each handler is also read under its snake_case name.
|
|
80
123
|
export type WsConnectHandlers = {
|
|
81
124
|
OnOpen: (() -> ())?,
|
|
82
125
|
OnMessage: ((payload: string, isBinary: boolean) -> ())?,
|
|
83
126
|
OnClose: (() -> ())?,
|
|
127
|
+
on_open: (() -> ())?,
|
|
128
|
+
on_message: ((payload: string, is_binary: boolean) -> ())?,
|
|
129
|
+
on_close: (() -> ())?,
|
|
84
130
|
}
|
|
85
131
|
|
|
86
132
|
export type PipeHandle = {
|
|
@@ -90,6 +136,24 @@ export type PipeHandle = {
|
|
|
90
136
|
Read: (self: PipeHandle) -> string?,
|
|
91
137
|
Write: (self: PipeHandle, data: string) -> (),
|
|
92
138
|
Close: (self: PipeHandle) -> (),
|
|
139
|
+
read: (self: PipeHandle) -> string?,
|
|
140
|
+
write: (self: PipeHandle, data: string) -> (),
|
|
141
|
+
close: (self: PipeHandle) -> (),
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
export type SoundHandle = {
|
|
145
|
+
Stop: (self: SoundHandle) -> (),
|
|
146
|
+
Pause: (self: SoundHandle) -> (),
|
|
147
|
+
Resume: (self: SoundHandle) -> (),
|
|
148
|
+
IsPlaying: (self: SoundHandle) -> boolean,
|
|
149
|
+
SetVolume: (self: SoundHandle, vol: number) -> (),
|
|
150
|
+
GetVolume: (self: SoundHandle) -> number,
|
|
151
|
+
stop: (self: SoundHandle) -> (),
|
|
152
|
+
pause: (self: SoundHandle) -> (),
|
|
153
|
+
resume: (self: SoundHandle) -> (),
|
|
154
|
+
is_playing: (self: SoundHandle) -> boolean,
|
|
155
|
+
set_volume: (self: SoundHandle, vol: number) -> (),
|
|
156
|
+
get_volume: (self: SoundHandle) -> number,
|
|
93
157
|
}
|
|
94
158
|
|
|
95
159
|
-- data types
|
|
@@ -178,6 +242,122 @@ export type HttpRequestOptions = {
|
|
|
178
242
|
timeout: number?,
|
|
179
243
|
}
|
|
180
244
|
|
|
245
|
+
export type ExecOptions = {
|
|
246
|
+
-- milliseconds; default 5000. The process is killed on expiry and Exec errors.
|
|
247
|
+
timeout: number?,
|
|
248
|
+
-- working directory for the command; default: the host process's cwd.
|
|
249
|
+
cwd: string?,
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
export type ExecResult = {
|
|
253
|
+
exit: number,
|
|
254
|
+
stdout: string,
|
|
255
|
+
stderr: string,
|
|
256
|
+
}
|
|
257
|
+
|
|
258
|
+
export type ExecDetachedOptions = {
|
|
259
|
+
cwd: string?,
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
-- a joypad state; every field is optional and defaults to neutral. buttons
|
|
263
|
+
-- lists pressed buttons 1-32, hat is 0 (up) to 7 clockwise (nil = centered),
|
|
264
|
+
-- x/y/z/rz are -1..1 (0 = center), slider and dial are 0..1.
|
|
265
|
+
export type JoypadState = {
|
|
266
|
+
buttons: { number }?,
|
|
267
|
+
hat: number?,
|
|
268
|
+
x: number?,
|
|
269
|
+
y: number?,
|
|
270
|
+
z: number?,
|
|
271
|
+
rz: number?,
|
|
272
|
+
slider: number?,
|
|
273
|
+
dial: number?,
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
export type ProcessEntry = {
|
|
277
|
+
pid: number,
|
|
278
|
+
name: string,
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
export type PixelMatch = {
|
|
282
|
+
x: number,
|
|
283
|
+
y: number,
|
|
284
|
+
}
|
|
285
|
+
|
|
286
|
+
export type MonitorEntry = {
|
|
287
|
+
index: number,
|
|
288
|
+
x: number,
|
|
289
|
+
y: number,
|
|
290
|
+
width: number,
|
|
291
|
+
height: number,
|
|
292
|
+
primary: boolean,
|
|
293
|
+
}
|
|
294
|
+
|
|
295
|
+
export type CaptureOptions = {
|
|
296
|
+
-- 1-based display index; default: the display under the cursor.
|
|
297
|
+
display: number?,
|
|
298
|
+
-- display-local logical coords; default: the whole display.
|
|
299
|
+
region: { x: number, y: number, w: number, h: number }?,
|
|
300
|
+
-- downscale so the long edge is at most this; default and 0: native.
|
|
301
|
+
max_edge: number?,
|
|
302
|
+
}
|
|
303
|
+
|
|
304
|
+
export type CaptureResult = {
|
|
305
|
+
image: string, -- base64 PNG
|
|
306
|
+
width: number,
|
|
307
|
+
height: number,
|
|
308
|
+
display: MonitorEntry,
|
|
309
|
+
cursor: { x: number, y: number },
|
|
310
|
+
}
|
|
311
|
+
|
|
312
|
+
export type FindImageOptions = {
|
|
313
|
+
display: number?,
|
|
314
|
+
region: { x: number, y: number, w: number, h: number }?,
|
|
315
|
+
-- 0.0 exact .. 1.0, per-channel fraction of 255 (same scale as SearchForColor).
|
|
316
|
+
tolerance: number?,
|
|
317
|
+
-- ratios to resample the needle by before scanning, tried in order; default { 1 }.
|
|
318
|
+
scales: { number }?,
|
|
319
|
+
}
|
|
320
|
+
|
|
321
|
+
export type ImageMatch = {
|
|
322
|
+
x: number,
|
|
323
|
+
y: number,
|
|
324
|
+
width: number,
|
|
325
|
+
height: number,
|
|
326
|
+
}
|
|
327
|
+
|
|
328
|
+
export type AppInfo = {
|
|
329
|
+
name: string,
|
|
330
|
+
pid: number,
|
|
331
|
+
}
|
|
332
|
+
|
|
333
|
+
export type PlayOptions = {
|
|
334
|
+
volume: number?,
|
|
335
|
+
loop: boolean?,
|
|
336
|
+
}
|
|
337
|
+
|
|
338
|
+
export type DialogMessageOptions = {
|
|
339
|
+
title: string?,
|
|
340
|
+
level: string?,
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
export type DialogFileFilter = {
|
|
344
|
+
name: string,
|
|
345
|
+
extensions: { string },
|
|
346
|
+
}
|
|
347
|
+
|
|
348
|
+
export type DialogFileOptions = {
|
|
349
|
+
title: string?,
|
|
350
|
+
location: string?,
|
|
351
|
+
filters: { DialogFileFilter }?,
|
|
352
|
+
}
|
|
353
|
+
|
|
354
|
+
export type RegexMatch = {
|
|
355
|
+
match: string,
|
|
356
|
+
captures: { string },
|
|
357
|
+
start: number,
|
|
358
|
+
finish: number,
|
|
359
|
+
}
|
|
360
|
+
|
|
181
361
|
-- macro action types
|
|
182
362
|
|
|
183
363
|
export type MacroMoveAction = {
|
|
@@ -186,6 +366,8 @@ export type MacroMoveAction = {
|
|
|
186
366
|
delay: number,
|
|
187
367
|
}
|
|
188
368
|
|
|
369
|
+
-- from Rebind 3.9.0, holdMs and charDelay are also read as hold_ms and
|
|
370
|
+
-- char_delay
|
|
189
371
|
export type MacroExplicitAction = {
|
|
190
372
|
action: string,
|
|
191
373
|
code: string?,
|
|
@@ -197,12 +379,15 @@ export type MacroExplicitAction = {
|
|
|
197
379
|
amount: number?,
|
|
198
380
|
holdMs: number?,
|
|
199
381
|
charDelay: number?,
|
|
382
|
+
hold_ms: number?,
|
|
383
|
+
char_delay: number?,
|
|
200
384
|
delay: number,
|
|
201
385
|
}
|
|
202
386
|
|
|
203
387
|
export type MacroAction = MacroMoveAction | MacroExplicitAction
|
|
204
388
|
|
|
205
|
-
-- ui widget option types
|
|
389
|
+
-- ui widget option types; from Rebind 3.9.0, showIf and maxLength are also
|
|
390
|
+
-- read as show_if and max_length
|
|
206
391
|
|
|
207
392
|
export type WidgetOpts = {
|
|
208
393
|
label: string?,
|
|
@@ -210,6 +395,7 @@ export type WidgetOpts = {
|
|
|
210
395
|
group: string?,
|
|
211
396
|
tab: string?,
|
|
212
397
|
showIf: string?,
|
|
398
|
+
show_if: string?,
|
|
213
399
|
}
|
|
214
400
|
|
|
215
401
|
export type ToggleOpts = WidgetOpts
|
|
@@ -228,6 +414,7 @@ export type SelectOpts = WidgetOpts
|
|
|
228
414
|
export type TextOpts = WidgetOpts & {
|
|
229
415
|
placeholder: string?,
|
|
230
416
|
maxLength: number?,
|
|
417
|
+
max_length: number?,
|
|
231
418
|
}
|
|
232
419
|
|
|
233
420
|
export type ColorOpts = WidgetOpts
|
|
@@ -264,6 +451,453 @@ export type RebindInfo = {
|
|
|
264
451
|
platform: string,
|
|
265
452
|
}
|
|
266
453
|
|
|
454
|
+
-- options of the rb calls that take one options table (Rebind 3.9.0 and later)
|
|
455
|
+
|
|
456
|
+
export type RbHttpOptions = {
|
|
457
|
+
headers: { [string]: string }?,
|
|
458
|
+
timeout: number?,
|
|
459
|
+
}
|
|
460
|
+
|
|
461
|
+
export type RbPlayOptions = {
|
|
462
|
+
-- playback speed multiplier
|
|
463
|
+
speed: number?,
|
|
464
|
+
-- "parallel" (default, plays alongside running macros) | "replace"
|
|
465
|
+
-- (stops all running macros first)
|
|
466
|
+
mode: string?,
|
|
467
|
+
}
|
|
468
|
+
|
|
469
|
+
export type RbExecDetachedOptions = {
|
|
470
|
+
args: { string }?,
|
|
471
|
+
cwd: string?,
|
|
472
|
+
}
|
|
473
|
+
|
|
474
|
+
-- fields left out keep their current value
|
|
475
|
+
export type RbWindowRect = {
|
|
476
|
+
x: number?,
|
|
477
|
+
y: number?,
|
|
478
|
+
width: number?,
|
|
479
|
+
height: number?,
|
|
480
|
+
}
|
|
481
|
+
|
|
482
|
+
export type RbBindOptions = {
|
|
483
|
+
-- false lets the key through to the system; default: the key is taken
|
|
484
|
+
swallow: boolean?,
|
|
485
|
+
-- checked on each press; false skips the bind for that press
|
|
486
|
+
when: ((device: InputDevice?) -> boolean)?,
|
|
487
|
+
-- runs when the key is released
|
|
488
|
+
release: ((device: InputDevice?) -> ())?,
|
|
489
|
+
-- nickname or id: the bind answers only to that device
|
|
490
|
+
device: string?,
|
|
491
|
+
}
|
|
492
|
+
|
|
493
|
+
-- rb.ai and rb.phone are Rebind Pro (a 7-day trial starts on first use).
|
|
494
|
+
-- Each rb.ai call waits for the model, so call it inside rb.run; its cost
|
|
495
|
+
-- counts against the monthly AI allowance. A script that declares
|
|
496
|
+
-- permissions needs ai, or ai:decide, ai:find or ai:read. A window option
|
|
497
|
+
-- names a window by title (or app name on macOS); the call reads the screen
|
|
498
|
+
-- pixels inside that window's rectangle, through the screen: permission.
|
|
499
|
+
|
|
500
|
+
export type AiDecideOptions = {
|
|
501
|
+
choices: { string },
|
|
502
|
+
-- send the display under the cursor (the target window under screen:target)
|
|
503
|
+
screen: boolean?,
|
|
504
|
+
-- send this window instead
|
|
505
|
+
window: string?,
|
|
506
|
+
}
|
|
507
|
+
|
|
508
|
+
export type AiFindOptions = {
|
|
509
|
+
-- look in this window; default: the display under the cursor
|
|
510
|
+
window: string?,
|
|
511
|
+
}
|
|
512
|
+
|
|
513
|
+
export type AiReadOptions = {
|
|
514
|
+
window: string?,
|
|
515
|
+
-- read only around this point (screen coordinates, such as rb.ai.find's)
|
|
516
|
+
at: AiPoint?,
|
|
517
|
+
}
|
|
518
|
+
|
|
519
|
+
-- screen coordinates, for rb.hid.move_to
|
|
520
|
+
export type AiPoint = {
|
|
521
|
+
x: number,
|
|
522
|
+
y: number,
|
|
523
|
+
}
|
|
524
|
+
|
|
525
|
+
export type RbAi = {
|
|
526
|
+
-- picks one of opts.choices; returns it and the model's confidence (0 to 1)
|
|
527
|
+
decide: (question: string, opts: AiDecideOptions) -> (string, number),
|
|
528
|
+
-- the centre of what is described, or nil when it is not visible
|
|
529
|
+
find: (what: string, opts: AiFindOptions?) -> AiPoint?,
|
|
530
|
+
-- the text described, as it appears on screen
|
|
531
|
+
read: (what: string, opts: AiReadOptions?) -> string,
|
|
532
|
+
}
|
|
533
|
+
|
|
534
|
+
export type PhoneResult = {
|
|
535
|
+
delivered: boolean,
|
|
536
|
+
reason: string?,
|
|
537
|
+
}
|
|
538
|
+
|
|
539
|
+
export type RbPhone = {
|
|
540
|
+
-- no phone app yet: returns { delivered = false, reason = "no phone connected" }
|
|
541
|
+
notify: (text: string, title: string?) -> PhoneResult,
|
|
542
|
+
}
|
|
543
|
+
|
|
544
|
+
-- events for rb.on (Rebind 3.9.0 and later), with the arguments each
|
|
545
|
+
-- handler receives. For down, up, move and scroll, a handler that returns
|
|
546
|
+
-- false swallows the input.
|
|
547
|
+
export type Event =
|
|
548
|
+
| "start" -- ()
|
|
549
|
+
| "stop" -- ()
|
|
550
|
+
| "focus" -- (window: WindowInfo)
|
|
551
|
+
| "blur" -- (window: WindowInfo)
|
|
552
|
+
| "tick" -- (dt_ms: number)
|
|
553
|
+
| "error" -- (message: string)
|
|
554
|
+
| "reload" -- ()
|
|
555
|
+
| "down" -- (key: string, device: InputDevice?)
|
|
556
|
+
| "up" -- (key: string, duration_ms: number, device: InputDevice?)
|
|
557
|
+
| "move" -- (dx: number, dy: number, device: InputDevice?) hardware mode only
|
|
558
|
+
| "scroll" -- (delta: number, device: InputDevice?)
|
|
559
|
+
| "scroll_h" -- (delta: number)
|
|
560
|
+
| "input_down" -- (key: string, device: InputDevice?)
|
|
561
|
+
| "input_up" -- (key: string, duration_ms: number, device: InputDevice?)
|
|
562
|
+
| "input_move" -- (dx: number, dy: number, device: InputDevice?)
|
|
563
|
+
| "input_scroll" -- (delta: number, device: InputDevice?)
|
|
564
|
+
|
|
565
|
+
-- valid key names for input events and binds:
|
|
566
|
+
--
|
|
567
|
+
-- letters: A-Z
|
|
568
|
+
-- numbers: 0-9
|
|
569
|
+
-- function: F1-F12
|
|
570
|
+
-- mouse: Mouse1 (left), Mouse2 (right), Mouse3 (middle), Mouse4, Mouse5
|
|
571
|
+
-- modifiers: LCtrl, RCtrl, LShift, RShift, LAlt, RAlt, LWin, RWin
|
|
572
|
+
-- navigation: Up, Down, Left, Right, Home, End, PageUp, PageDown, Insert, Delete
|
|
573
|
+
-- editing: Backspace, Tab, Enter, Space, Escape
|
|
574
|
+
-- punctuation: Minus, Equal, LeftBrace, RightBrace, Backslash, Semicolon,
|
|
575
|
+
-- Apostrophe, Grave, Comma, Period, Slash
|
|
576
|
+
-- locks: CapsLock, ScrollLock, NumLock
|
|
577
|
+
-- system: PrintScreen, Pause, Menu
|
|
578
|
+
-- numpad: Kp0-Kp9, KpPlus, KpMinus, KpMultiply, KpDivide, KpEnter, KpDot
|
|
579
|
+
--
|
|
580
|
+
-- HID output only:
|
|
581
|
+
-- function: F13-F24
|
|
582
|
+
-- media: MediaNext, MediaPrev, MediaStop, MediaPlay, VolumeUp, VolumeDown, Mute
|
|
583
|
+
-- aliases: Numpad0-9, NP0-9, NPAdd, NPSubtract, NPMultiply, NPDivide, NPEnter,
|
|
584
|
+
-- NPDecimal, Ctrl, Shift, Alt, Win, Meta, Del, PgUp, PgDn, etc.
|
|
585
|
+
|
|
586
|
+
-- rb
|
|
587
|
+
-- The scripting surface, for scripts that declare min_sdk=3.9.0 or later.
|
|
588
|
+
-- Every name is the snake_case of a v1 name (HID.MoveTo is rb.hid.move_to).
|
|
589
|
+
-- Hooks are rb.on(event, fn) and key names passed to rb ignore case.
|
|
590
|
+
|
|
591
|
+
declare rb: {
|
|
592
|
+
-- runtime identity: script name, versions, platform
|
|
593
|
+
info: RebindInfo,
|
|
594
|
+
-- runs fn as a coroutine, where rb.sleep and other coroutine-only calls work
|
|
595
|
+
run: (fn: () -> ()) -> TaskHandle,
|
|
596
|
+
-- coroutine-only: call inside rb.run
|
|
597
|
+
sleep: (ms: number) -> (),
|
|
598
|
+
after: (ms: number, fn: () -> ()) -> TaskHandle,
|
|
599
|
+
-- wraps fn so it runs on the coroutine scheduler; when auto-spawned the call
|
|
600
|
+
-- returns false instead of fn's results.
|
|
601
|
+
async: (fn: (...any) -> ...any) -> (...any) -> ...any,
|
|
602
|
+
-- adds a handler for an event; handlers run in the order they were added.
|
|
603
|
+
-- returns a handle whose stop removes the handler.
|
|
604
|
+
on: (event: Event, fn: (...any) -> boolean?) -> EventHandle,
|
|
605
|
+
-- rb.bind(key, fn, options) takes the key unless options.swallow is false.
|
|
606
|
+
-- the callback's return value is ignored.
|
|
607
|
+
bind: typeof(setmetatable({} :: {
|
|
608
|
+
toggle: (key: string, ui_id: string) -> BindHandle,
|
|
609
|
+
remap: (from: string, to: string) -> BindHandle,
|
|
610
|
+
}, {} :: {
|
|
611
|
+
__call: (self: any, key: string, fn: ((device: InputDevice?) -> ...any)?, options: RbBindOptions?) -> BindHandle,
|
|
612
|
+
})),
|
|
613
|
+
-- each level takes any number of values, joined like print
|
|
614
|
+
log: {
|
|
615
|
+
info: (...any) -> (),
|
|
616
|
+
warn: (...any) -> (),
|
|
617
|
+
error: (...any) -> (),
|
|
618
|
+
debug: (...any) -> (),
|
|
619
|
+
},
|
|
620
|
+
system: {
|
|
621
|
+
time: () -> number,
|
|
622
|
+
mouse: () -> (number, number),
|
|
623
|
+
screen: () -> (number, number),
|
|
624
|
+
window: () -> WindowInfo,
|
|
625
|
+
-- runs cmd through the shell (sh -c / cmd.exe), output capped at 64KB per
|
|
626
|
+
-- stream. Requires the 'exec' permission. Inside rb.run it runs off the
|
|
627
|
+
-- tick thread; elsewhere it blocks the tick thread and warns once.
|
|
628
|
+
exec: (cmd: string, options: ExecOptions?) -> ExecResult,
|
|
629
|
+
-- fire-and-forget spawn (no shell, argv array); returns the pid.
|
|
630
|
+
exec_detached: (cmd: string, options: RbExecDetachedOptions?) -> number,
|
|
631
|
+
-- types text through the host OS (Unicode aware), never through the HID
|
|
632
|
+
-- transport. raises when the OS refuses the injection.
|
|
633
|
+
type_text: (text: string) -> (),
|
|
634
|
+
},
|
|
635
|
+
hid: {
|
|
636
|
+
down: (code: string) -> (),
|
|
637
|
+
up: (code: string) -> (),
|
|
638
|
+
-- coroutine-only (sleeps for hold_ms): call inside rb.run. From a plain
|
|
639
|
+
-- chunk use down and up, or combo.
|
|
640
|
+
press: (code: string, hold_ms: number?) -> (),
|
|
641
|
+
-- fires a chord in one synchronous call (press left to right, release
|
|
642
|
+
-- right to left). modifier tokens accept macOS aliases: "cmd",
|
|
643
|
+
-- "opt"/"option", plus "ctrl"/"shift"/"alt"/"win".
|
|
644
|
+
combo: (code: string) -> (),
|
|
645
|
+
-- instant whole-string insertion; typewriter types one character at a
|
|
646
|
+
-- time and is coroutine-only.
|
|
647
|
+
type: (text: string) -> (),
|
|
648
|
+
typewriter: (text: string, delay_ms: number?) -> (),
|
|
649
|
+
move: (dx: number, dy: number) -> (),
|
|
650
|
+
move_to: (x: number, y: number) -> (),
|
|
651
|
+
scroll: (amount: number) -> (),
|
|
652
|
+
set_mouse_mode: (mode: string) -> (),
|
|
653
|
+
get_mouse_mode: () -> string,
|
|
654
|
+
-- keyboard HID usage for a key name, or nil (media keys return nil). down,
|
|
655
|
+
-- up, press and combo also accept "usage:N" (decimal or 0x hex, 0x04-0xE7).
|
|
656
|
+
usage: (name: string) -> number?,
|
|
657
|
+
-- sets the whole joypad state (last write wins across scripts). Needs a
|
|
658
|
+
-- Rebind Link whose USB profile has a joypad; raises otherwise.
|
|
659
|
+
joypad: (state: JoypadState?) -> (),
|
|
660
|
+
-- back to neutral; the relay also does this when a script stops or errors
|
|
661
|
+
joypad_reset: () -> (),
|
|
662
|
+
},
|
|
663
|
+
input: {
|
|
664
|
+
is_down: (code: string) -> boolean,
|
|
665
|
+
duration: (code: string) -> number,
|
|
666
|
+
keys: () -> { string },
|
|
667
|
+
mouse_pos: () -> MousePos,
|
|
668
|
+
modifiers: () -> ModifierState,
|
|
669
|
+
},
|
|
670
|
+
ui: {
|
|
671
|
+
schema: (descriptors: { [string]: any }) -> UiProxy,
|
|
672
|
+
toggle: (default: boolean, opts: ToggleOpts?) -> any,
|
|
673
|
+
slider: (default: number, opts: SliderOpts?) -> any,
|
|
674
|
+
keybind: (default: string, opts: KeybindOpts?) -> any,
|
|
675
|
+
select: (default: string, choices: { string }, opts: SelectOpts?) -> any,
|
|
676
|
+
text: (default: string, opts: TextOpts?) -> any,
|
|
677
|
+
color: (default: string, opts: ColorOpts?) -> any,
|
|
678
|
+
get: (id: string) -> any,
|
|
679
|
+
set: (id: string, value: any) -> (),
|
|
680
|
+
get_all: () -> { [string]: any },
|
|
681
|
+
get_schema: () -> { any },
|
|
682
|
+
notify: (text: string, variant: string?) -> (),
|
|
683
|
+
},
|
|
684
|
+
timer: {
|
|
685
|
+
after: (ms: number, callback: () -> ()) -> TimerHandle,
|
|
686
|
+
every: (ms: number, callback: () -> ()) -> TimerHandle,
|
|
687
|
+
stop_all: () -> (),
|
|
688
|
+
},
|
|
689
|
+
macro: {
|
|
690
|
+
play: (macro: { MacroAction }, options: RbPlayOptions?) -> MacroHandle,
|
|
691
|
+
stop_all: () -> (),
|
|
692
|
+
record: (options: RecordOpts?) -> (),
|
|
693
|
+
finish: () -> { MacroAction },
|
|
694
|
+
-- the saved-macro format: a `macro=true` modeline, then `return` of the
|
|
695
|
+
-- actions. require() of a saved macro returns the actions.
|
|
696
|
+
to_script: (macro: { MacroAction }, name: string) -> string,
|
|
697
|
+
stream: (macro: { MacroAction }) -> (),
|
|
698
|
+
abort: () -> (),
|
|
699
|
+
},
|
|
700
|
+
math: {
|
|
701
|
+
random: (min: number, max: number) -> number,
|
|
702
|
+
gaussian: (mean: number, std_dev: number) -> number,
|
|
703
|
+
scale: (macro: { MacroAction }, x_factor: number, y_factor: number) -> { MacroAction },
|
|
704
|
+
spline: (macro: { MacroAction }, tension: number) -> { MacroAction },
|
|
705
|
+
resample: (macro: { MacroAction }, interval_ms: number) -> { MacroAction },
|
|
706
|
+
time_comp: (macro: { MacroAction }, target_ms: number) -> { MacroAction },
|
|
707
|
+
-- mode: "linear" | anything else = positional curve (default).
|
|
708
|
+
interpolate: (macro: { MacroAction }, interval_ms: number, mode: string?) -> { MacroAction },
|
|
709
|
+
},
|
|
710
|
+
json: {
|
|
711
|
+
parse: (s: string) -> any,
|
|
712
|
+
stringify: (value: any) -> string,
|
|
713
|
+
},
|
|
714
|
+
process: {
|
|
715
|
+
exists: (name: string) -> number?,
|
|
716
|
+
list: (name: string?) -> { ProcessEntry },
|
|
717
|
+
kill: (pid: number) -> boolean,
|
|
718
|
+
},
|
|
719
|
+
-- pixel reads are limited by a screen:target or screen:none permission entry
|
|
720
|
+
screen: {
|
|
721
|
+
pixel_hex: (x: number?, y: number?) -> string,
|
|
722
|
+
-- reads the published frame. regions up to 200k physical pixels answer on
|
|
723
|
+
-- the calling thread; larger ones yield inside rb.run and are refused
|
|
724
|
+
-- outside it.
|
|
725
|
+
search_color: (region: { number }, color: string, tolerance: number?) -> PixelMatch?,
|
|
726
|
+
list: () -> { MonitorEntry },
|
|
727
|
+
-- yields inside rb.run; refused outside a coroutine.
|
|
728
|
+
capture: (options: CaptureOptions?) -> CaptureResult,
|
|
729
|
+
-- needle is a PNG path relative to the script directory. yields inside
|
|
730
|
+
-- rb.run; refused outside a coroutine.
|
|
731
|
+
find_image: (needle: string, options: FindImageOptions?) -> ImageMatch?,
|
|
732
|
+
-- usable desktop of the display containing the point (cursor when omitted).
|
|
733
|
+
-- Windows only; raises elsewhere.
|
|
734
|
+
work_area: (x: number?, y: number?) -> WindowPos,
|
|
735
|
+
},
|
|
736
|
+
window: {
|
|
737
|
+
find: (title: string) -> number?,
|
|
738
|
+
list: (title: string?) -> { WindowEntry },
|
|
739
|
+
get_title: (handle: number?) -> string,
|
|
740
|
+
get_class: (handle: number?) -> string,
|
|
741
|
+
get_pos: (handle: number?) -> WindowPos,
|
|
742
|
+
get_pid: (handle: number?) -> number,
|
|
743
|
+
activate: (handle: number) -> (),
|
|
744
|
+
move: (handle: number?, rect: RbWindowRect?) -> (),
|
|
745
|
+
set_always_on_top: (handle: number, enabled: boolean) -> (),
|
|
746
|
+
set_transparency: (handle: number, alpha: number) -> (),
|
|
747
|
+
set_title: (handle: number, title: string) -> (),
|
|
748
|
+
minimize: (handle: number?) -> (),
|
|
749
|
+
maximize: (handle: number?) -> (),
|
|
750
|
+
restore: (handle: number?) -> (),
|
|
751
|
+
hide: (handle: number?) -> (),
|
|
752
|
+
show: (handle: number?) -> (),
|
|
753
|
+
close: (handle: number?) -> (),
|
|
754
|
+
kill: (handle: number?) -> (),
|
|
755
|
+
is_visible: (handle: number) -> boolean,
|
|
756
|
+
is_active: (handle: number?) -> boolean,
|
|
757
|
+
get_foreground: () -> number?,
|
|
758
|
+
from_point: (x: number, y: number) -> number?,
|
|
759
|
+
-- "minimized" | "maximized" | "normal". Windows only; raises elsewhere.
|
|
760
|
+
get_state: (handle: number?) -> string,
|
|
761
|
+
wait: (title: string, timeout: number?) -> number?,
|
|
762
|
+
wait_active: (title: string, timeout: number?) -> boolean,
|
|
763
|
+
wait_close: (title: string, timeout: number?) -> boolean,
|
|
764
|
+
},
|
|
765
|
+
-- application control. macOS matches app display names ignoring case;
|
|
766
|
+
-- Windows matches executable names (".exe" optional) and cannot hide;
|
|
767
|
+
-- Linux raises on every call.
|
|
768
|
+
app: {
|
|
769
|
+
front: () -> AppInfo?,
|
|
770
|
+
is_front: (name: string) -> boolean,
|
|
771
|
+
is_running: (name: string) -> boolean,
|
|
772
|
+
is_hidden: (name: string) -> boolean,
|
|
773
|
+
activate: (name: string) -> (),
|
|
774
|
+
hide: (name: string) -> (),
|
|
775
|
+
quit: (name: string) -> (),
|
|
776
|
+
},
|
|
777
|
+
-- permission: net, or net:<host> for the client calls and ws_connect
|
|
778
|
+
net: {
|
|
779
|
+
get: (url: string, options: RbHttpOptions?) -> HttpResponse,
|
|
780
|
+
post: (url: string, body: string, options: RbHttpOptions?) -> HttpResponse,
|
|
781
|
+
put: (url: string, body: string, options: RbHttpOptions?) -> HttpResponse,
|
|
782
|
+
patch: (url: string, body: string, options: RbHttpOptions?) -> HttpResponse,
|
|
783
|
+
delete: (url: string, options: RbHttpOptions?) -> HttpResponse,
|
|
784
|
+
head: (url: string, options: RbHttpOptions?) -> HttpResponse,
|
|
785
|
+
request: (options: HttpRequestOptions) -> HttpResponse,
|
|
786
|
+
listen: (port: number, handler: (request: HttpRequest) -> HttpResponseSpec | string) -> ServerHandle,
|
|
787
|
+
ws_listen: (port: number, handlers: WsListenHandlers) -> WsServerHandle,
|
|
788
|
+
ws_connect: (url: string, handlers: WsConnectHandlers) -> WsConnectHandle,
|
|
789
|
+
-- binds a UDP socket; handler receives each datagram's raw bytes and sender.
|
|
790
|
+
udp_listen: (bind_ip: string, port: number, handler: (data: string, ip: string, port: number) -> ()) -> UdpHandle,
|
|
791
|
+
-- this computer's IPv4 address on its default route, or nil when there is none.
|
|
792
|
+
local_ip: () -> string?,
|
|
793
|
+
},
|
|
794
|
+
pipe: {
|
|
795
|
+
open: (name: string, options: { size: number? }?) -> PipeHandle,
|
|
796
|
+
},
|
|
797
|
+
-- paths are relative to the script directory; absolute paths are rejected
|
|
798
|
+
file: {
|
|
799
|
+
read: (path: string) -> string,
|
|
800
|
+
read_bytes: (path: string) -> string,
|
|
801
|
+
write: (path: string, content: string) -> (),
|
|
802
|
+
append: (path: string, content: string) -> (),
|
|
803
|
+
exists: (path: string) -> boolean,
|
|
804
|
+
delete: (path: string) -> boolean,
|
|
805
|
+
-- nil path lists the script's own directory
|
|
806
|
+
list: (path: string?) -> { string },
|
|
807
|
+
mkdir: (path: string) -> boolean,
|
|
808
|
+
-- recursive; returns true even when the directory did not exist.
|
|
809
|
+
rmdir: (path: string) -> boolean,
|
|
810
|
+
copy: (src: string, dst: string) -> (),
|
|
811
|
+
move: (src: string, dst: string) -> (),
|
|
812
|
+
read_json: (path: string) -> any,
|
|
813
|
+
write_json: (path: string, value: any) -> (),
|
|
814
|
+
script_dir: () -> string,
|
|
815
|
+
size: (path: string) -> number,
|
|
816
|
+
time: (path: string) -> number,
|
|
817
|
+
is_dir: (path: string) -> boolean,
|
|
818
|
+
is_file: (path: string) -> boolean,
|
|
819
|
+
},
|
|
820
|
+
audio: {
|
|
821
|
+
beep: () -> (),
|
|
822
|
+
play: (path: string, options: PlayOptions?) -> SoundHandle,
|
|
823
|
+
stop_all: () -> (),
|
|
824
|
+
set_master_volume: (vol: number) -> (),
|
|
825
|
+
get_master_volume: () -> number,
|
|
826
|
+
},
|
|
827
|
+
-- every dialog call is coroutine-only: it yields until the dialog closes
|
|
828
|
+
-- and errors outside rb.run. the pickers return nil on cancel.
|
|
829
|
+
dialog: {
|
|
830
|
+
message: (text: string, options: DialogMessageOptions?) -> (),
|
|
831
|
+
confirm: (text: string, options: DialogMessageOptions?) -> boolean,
|
|
832
|
+
open_file: (options: DialogFileOptions?) -> string?,
|
|
833
|
+
open_dir: (options: DialogFileOptions?) -> string?,
|
|
834
|
+
save_file: (options: DialogFileOptions?) -> string?,
|
|
835
|
+
},
|
|
836
|
+
-- limited by clipboard:read, clipboard:write, clipboard:none
|
|
837
|
+
clipboard: {
|
|
838
|
+
get: () -> string?,
|
|
839
|
+
set: (text: string) -> (),
|
|
840
|
+
},
|
|
841
|
+
script: {
|
|
842
|
+
exit: (reason: string?) -> (),
|
|
843
|
+
reload: () -> (),
|
|
844
|
+
},
|
|
845
|
+
regex: {
|
|
846
|
+
is_match: (text: string, pattern: string) -> boolean,
|
|
847
|
+
find: (text: string, pattern: string) -> RegexMatch?,
|
|
848
|
+
find_all: (text: string, pattern: string) -> { RegexMatch },
|
|
849
|
+
replace: (text: string, pattern: string, replacement: string) -> string,
|
|
850
|
+
replace_all: (text: string, pattern: string, replacement: string) -> string,
|
|
851
|
+
split: (text: string, pattern: string) -> { string },
|
|
852
|
+
},
|
|
853
|
+
config: {
|
|
854
|
+
parse_toml: (text: string) -> { [string]: any },
|
|
855
|
+
to_toml: (value: { [string]: any }) -> string,
|
|
856
|
+
read_toml: (path: string) -> { [string]: any },
|
|
857
|
+
write_toml: (path: string, value: { [string]: any }) -> (),
|
|
858
|
+
},
|
|
859
|
+
hash: {
|
|
860
|
+
md5: (data: string) -> string,
|
|
861
|
+
sha1: (data: string) -> string,
|
|
862
|
+
sha256: (data: string) -> string,
|
|
863
|
+
sha512: (data: string) -> string,
|
|
864
|
+
crc32: (data: string) -> number,
|
|
865
|
+
hmac: (algo: string, key: string, data: string) -> string,
|
|
866
|
+
},
|
|
867
|
+
codec: {
|
|
868
|
+
base64: (data: string) -> string,
|
|
869
|
+
base64_decode: (str: string) -> string,
|
|
870
|
+
hex: (data: string) -> string,
|
|
871
|
+
hex_decode: (str: string) -> string,
|
|
872
|
+
},
|
|
873
|
+
env: {
|
|
874
|
+
get: (name: string) -> string?,
|
|
875
|
+
set: (name: string, value: string) -> (),
|
|
876
|
+
home: () -> string?,
|
|
877
|
+
config: () -> string?,
|
|
878
|
+
data: () -> string?,
|
|
879
|
+
desktop: () -> string?,
|
|
880
|
+
documents: () -> string?,
|
|
881
|
+
downloads: () -> string?,
|
|
882
|
+
appdata: () -> string?,
|
|
883
|
+
temp: () -> string?,
|
|
884
|
+
},
|
|
885
|
+
-- Windows only
|
|
886
|
+
registry: {
|
|
887
|
+
read: (key_path: string, value_name: string) -> string | number,
|
|
888
|
+
write: (key_path: string, type: string, value_name: string, value: any) -> (),
|
|
889
|
+
delete_value: (key_path: string, value_name: string) -> (),
|
|
890
|
+
delete_key: (key_path: string) -> (),
|
|
891
|
+
create_key: (key_path: string) -> (),
|
|
892
|
+
},
|
|
893
|
+
-- Rebind Pro; require("@rebind/pro") returns rb
|
|
894
|
+
ai: RbAi,
|
|
895
|
+
phone: RbPhone,
|
|
896
|
+
}
|
|
897
|
+
|
|
898
|
+
-- v1 names
|
|
899
|
+
-- The names every Rebind version accepts. They keep working.
|
|
900
|
+
|
|
267
901
|
-- global functions
|
|
268
902
|
|
|
269
903
|
declare function Run(fn: () -> ()): TaskHandle
|
|
@@ -284,23 +918,6 @@ declare _REBIND: RebindInfo
|
|
|
284
918
|
|
|
285
919
|
-- system namespace
|
|
286
920
|
|
|
287
|
-
export type ExecOptions = {
|
|
288
|
-
-- milliseconds; default 5000. The process is killed on expiry and Exec errors.
|
|
289
|
-
timeout: number?,
|
|
290
|
-
-- working directory for the command; default: the host process's cwd.
|
|
291
|
-
cwd: string?,
|
|
292
|
-
}
|
|
293
|
-
|
|
294
|
-
export type ExecResult = {
|
|
295
|
-
exit: number,
|
|
296
|
-
stdout: string,
|
|
297
|
-
stderr: string,
|
|
298
|
-
}
|
|
299
|
-
|
|
300
|
-
export type ExecDetachedOptions = {
|
|
301
|
-
cwd: string?,
|
|
302
|
-
}
|
|
303
|
-
|
|
304
921
|
declare System: {
|
|
305
922
|
Time: () -> number,
|
|
306
923
|
Mouse: () -> (number, number),
|
|
@@ -322,20 +939,6 @@ declare System: {
|
|
|
322
939
|
|
|
323
940
|
-- hid namespace
|
|
324
941
|
|
|
325
|
-
-- a joypad state; every field is optional and defaults to neutral. buttons
|
|
326
|
-
-- lists pressed buttons 1-32, hat is 0 (up) to 7 clockwise (nil = centered),
|
|
327
|
-
-- x/y/z/rz are -1..1 (0 = center), slider and dial are 0..1.
|
|
328
|
-
export type JoypadState = {
|
|
329
|
-
buttons: { number }?,
|
|
330
|
-
hat: number?,
|
|
331
|
-
x: number?,
|
|
332
|
-
y: number?,
|
|
333
|
-
z: number?,
|
|
334
|
-
rz: number?,
|
|
335
|
-
slider: number?,
|
|
336
|
-
dial: number?,
|
|
337
|
-
}
|
|
338
|
-
|
|
339
942
|
declare HID: {
|
|
340
943
|
Down: (code: string) -> (),
|
|
341
944
|
Up: (code: string) -> (),
|
|
@@ -457,11 +1060,6 @@ declare JSON: {
|
|
|
457
1060
|
|
|
458
1061
|
-- process namespace
|
|
459
1062
|
|
|
460
|
-
export type ProcessEntry = {
|
|
461
|
-
pid: number,
|
|
462
|
-
name: string,
|
|
463
|
-
}
|
|
464
|
-
|
|
465
1063
|
declare Process: {
|
|
466
1064
|
Exists: (name: string) -> number?,
|
|
467
1065
|
List: (name: string?) -> { ProcessEntry },
|
|
@@ -470,53 +1068,6 @@ declare Process: {
|
|
|
470
1068
|
|
|
471
1069
|
-- screen namespace
|
|
472
1070
|
|
|
473
|
-
export type PixelMatch = {
|
|
474
|
-
x: number,
|
|
475
|
-
y: number,
|
|
476
|
-
}
|
|
477
|
-
|
|
478
|
-
export type MonitorEntry = {
|
|
479
|
-
index: number,
|
|
480
|
-
x: number,
|
|
481
|
-
y: number,
|
|
482
|
-
width: number,
|
|
483
|
-
height: number,
|
|
484
|
-
primary: boolean,
|
|
485
|
-
}
|
|
486
|
-
|
|
487
|
-
export type CaptureOptions = {
|
|
488
|
-
-- 1-based display index; default: the display under the cursor.
|
|
489
|
-
display: number?,
|
|
490
|
-
-- display-local logical coords; default: the whole display.
|
|
491
|
-
region: { x: number, y: number, w: number, h: number }?,
|
|
492
|
-
-- downscale so the long edge is at most this; default and 0: native.
|
|
493
|
-
max_edge: number?,
|
|
494
|
-
}
|
|
495
|
-
|
|
496
|
-
export type CaptureResult = {
|
|
497
|
-
image: string, -- base64 PNG
|
|
498
|
-
width: number,
|
|
499
|
-
height: number,
|
|
500
|
-
display: MonitorEntry,
|
|
501
|
-
cursor: { x: number, y: number },
|
|
502
|
-
}
|
|
503
|
-
|
|
504
|
-
export type FindImageOptions = {
|
|
505
|
-
display: number?,
|
|
506
|
-
region: { x: number, y: number, w: number, h: number }?,
|
|
507
|
-
-- 0.0 exact .. 1.0, per-channel fraction of 255 (same scale as SearchForColor).
|
|
508
|
-
tolerance: number?,
|
|
509
|
-
-- ratios to resample the needle by before scanning, tried in order; default { 1 }.
|
|
510
|
-
scales: { number }?,
|
|
511
|
-
}
|
|
512
|
-
|
|
513
|
-
export type ImageMatch = {
|
|
514
|
-
x: number,
|
|
515
|
-
y: number,
|
|
516
|
-
width: number,
|
|
517
|
-
height: number,
|
|
518
|
-
}
|
|
519
|
-
|
|
520
1071
|
-- pixel reads are limited by a screen:target or screen:none permission entry
|
|
521
1072
|
|
|
522
1073
|
declare Screen: {
|
|
@@ -544,7 +1095,7 @@ declare Window: {
|
|
|
544
1095
|
GetPos: (handle: number?) -> WindowPos,
|
|
545
1096
|
GetPID: (handle: number?) -> number,
|
|
546
1097
|
Activate: (handle: number) -> (),
|
|
547
|
-
Move: (handle: number
|
|
1098
|
+
Move: (handle: number?, x: number?, y: number?, width: number?, height: number?) -> (),
|
|
548
1099
|
SetAlwaysOnTop: (handle: number, enabled: boolean) -> (),
|
|
549
1100
|
SetTransparency: (handle: number, alpha: number) -> (),
|
|
550
1101
|
SetTitle: (handle: number, title: string) -> (),
|
|
@@ -574,11 +1125,6 @@ declare Window: {
|
|
|
574
1125
|
-- Activate focuses a running app and does not launch one; Quit closes its
|
|
575
1126
|
-- windows; Hide/IsHidden raise. Linux: every call raises.
|
|
576
1127
|
|
|
577
|
-
export type AppInfo = {
|
|
578
|
-
name: string,
|
|
579
|
-
pid: number,
|
|
580
|
-
}
|
|
581
|
-
|
|
582
1128
|
declare App: {
|
|
583
1129
|
Front: () -> AppInfo?,
|
|
584
1130
|
IsFront: (name: string) -> boolean,
|
|
@@ -642,20 +1188,6 @@ declare File: {
|
|
|
642
1188
|
|
|
643
1189
|
-- audio namespace
|
|
644
1190
|
|
|
645
|
-
export type PlayOptions = {
|
|
646
|
-
volume: number?,
|
|
647
|
-
loop: boolean?,
|
|
648
|
-
}
|
|
649
|
-
|
|
650
|
-
export type SoundHandle = {
|
|
651
|
-
Stop: (self: SoundHandle) -> (),
|
|
652
|
-
Pause: (self: SoundHandle) -> (),
|
|
653
|
-
Resume: (self: SoundHandle) -> (),
|
|
654
|
-
IsPlaying: (self: SoundHandle) -> boolean,
|
|
655
|
-
SetVolume: (self: SoundHandle, vol: number) -> (),
|
|
656
|
-
GetVolume: (self: SoundHandle) -> number,
|
|
657
|
-
}
|
|
658
|
-
|
|
659
1191
|
declare Audio: {
|
|
660
1192
|
Beep: () -> (),
|
|
661
1193
|
Play: (path: string, options: PlayOptions?) -> SoundHandle,
|
|
@@ -666,22 +1198,6 @@ declare Audio: {
|
|
|
666
1198
|
|
|
667
1199
|
-- dialog namespace
|
|
668
1200
|
|
|
669
|
-
export type DialogMessageOptions = {
|
|
670
|
-
title: string?,
|
|
671
|
-
level: string?,
|
|
672
|
-
}
|
|
673
|
-
|
|
674
|
-
export type DialogFileFilter = {
|
|
675
|
-
name: string,
|
|
676
|
-
extensions: { string },
|
|
677
|
-
}
|
|
678
|
-
|
|
679
|
-
export type DialogFileOptions = {
|
|
680
|
-
title: string?,
|
|
681
|
-
location: string?,
|
|
682
|
-
filters: { DialogFileFilter }?,
|
|
683
|
-
}
|
|
684
|
-
|
|
685
1201
|
-- every Dialog call is coroutine-only: it yields until the dialog closes and
|
|
686
1202
|
-- errors outside Run(). the file and folder pickers return nil on cancel.
|
|
687
1203
|
declare Dialog: {
|
|
@@ -708,13 +1224,6 @@ declare Script: {
|
|
|
708
1224
|
|
|
709
1225
|
-- regex namespace
|
|
710
1226
|
|
|
711
|
-
export type RegexMatch = {
|
|
712
|
-
match: string,
|
|
713
|
-
captures: { string },
|
|
714
|
-
start: number,
|
|
715
|
-
finish: number,
|
|
716
|
-
}
|
|
717
|
-
|
|
718
1227
|
declare Regex: {
|
|
719
1228
|
IsMatch: (text: string, pattern: string) -> boolean,
|
|
720
1229
|
Find: (text: string, pattern: string) -> RegexMatch?,
|
|
@@ -778,27 +1287,6 @@ declare Registry: {
|
|
|
778
1287
|
CreateKey: (keyPath: string) -> (),
|
|
779
1288
|
}
|
|
780
1289
|
|
|
781
|
-
-- valid key names for input hooks (OnDown, OnUp):
|
|
782
|
-
--
|
|
783
|
-
-- letters: A-Z
|
|
784
|
-
-- numbers: 0-9
|
|
785
|
-
-- function: F1-F12
|
|
786
|
-
-- mouse: Mouse1 (left), Mouse2 (right), Mouse3 (middle), Mouse4, Mouse5
|
|
787
|
-
-- modifiers: LCtrl, RCtrl, LShift, RShift, LAlt, RAlt, LWin, RWin
|
|
788
|
-
-- navigation: Up, Down, Left, Right, Home, End, PageUp, PageDown, Insert, Delete
|
|
789
|
-
-- editing: Backspace, Tab, Enter, Space, Escape
|
|
790
|
-
-- punctuation: Minus, Equal, LeftBrace, RightBrace, Backslash, Semicolon,
|
|
791
|
-
-- Apostrophe, Grave, Comma, Period, Slash
|
|
792
|
-
-- locks: CapsLock, ScrollLock, NumLock
|
|
793
|
-
-- system: PrintScreen, Pause, Menu
|
|
794
|
-
-- numpad: Kp0-Kp9, KpPlus, KpMinus, KpMultiply, KpDivide, KpEnter, KpDot
|
|
795
|
-
--
|
|
796
|
-
-- HID output only (HID.Down, HID.Press, etc.):
|
|
797
|
-
-- function: F13-F24
|
|
798
|
-
-- media: MediaNext, MediaPrev, MediaStop, MediaPlay, VolumeUp, VolumeDown, Mute
|
|
799
|
-
-- aliases: Numpad0-9, NP0-9, NPAdd, NPSubtract, NPMultiply, NPDivide, NPEnter,
|
|
800
|
-
-- NPDecimal, Ctrl, Shift, Alt, Win, Meta, Del, PgUp, PgDn, etc.
|
|
801
|
-
|
|
802
1290
|
-- hooks: declare these as global functions in your script.
|
|
803
1291
|
-- uncomment the ones you use; the runtime calls them when events occur.
|
|
804
1292
|
|