forked from uusense/python-devicebase
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathcomputer_control.py
More file actions
71 lines (55 loc) · 2.96 KB
/
Copy pathcomputer_control.py
File metadata and controls
71 lines (55 loc) · 2.96 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
"""Desktop control (macOS / Windows / Linux): mouse, keyboard, host shell.
Coordinates are absolute screen pixels, so ask the device for its screen size
before computing a position rather than assuming a resolution.
Run with:
DEVICEBASE_API_KEY=… python examples/computer_control.py
"""
from devicebase import DeviceBaseHttpClient, list_devices
def main() -> None:
computers = list_devices(device_type="computer", limit=1)
if not computers:
print("No computer device available on this account.")
return
serialno = computers[0].serialno
os_type = computers[0].os_type
# macOS uses Meta for the shortcuts that Windows and Linux put on Control.
modifier = "Meta" if os_type.lower() == "macos" else "Control"
print(f"Driving desktop {serialno} ({os_type})")
with DeviceBaseHttpClient() as client:
# --- Permissions first ---
# Screen recording and accessibility are granted per application on
# macOS, and a missing one shows up here rather than as a click that
# silently does nothing.
print(f"permissions: {client.computer_permissions(serialno).payload}")
size = client.computer_screen_size(serialno).payload
print(f"screen: {size}")
width = int(size.get("width", 1920))
height = int(size.get("height", 1080))
centre_x, centre_y = width // 2, height // 2
# --- Mouse ---
client.computer_move(serialno, centre_x, centre_y)
client.computer_click(serialno, centre_x, centre_y)
client.computer_click(serialno, centre_x, centre_y, button="right")
client.computer_double_click(serialno, centre_x, centre_y)
# duration is in seconds; omitted, the driver picks its own.
client.computer_long_click(serialno, centre_x, centre_y, duration=2)
client.computer_drag(serialno, 100, 100, centre_x, centre_y)
client.computer_scroll(serialno, "down", amount=3)
print(f"pointer now at {client.computer_position(serialno).payload}")
# --- Keyboard ---
client.computer_type_text(serialno, "你好, world")
client.computer_press(serialno, "Enter")
client.computer_hotkey(serialno, [modifier, "c"])
# --- Apps ---
client.computer_launch_app(serialno, "Safari") # a macOS example; name the
# equivalent application per platform in real use
# --- Blocking actions ---
# Both widen the transport deadline past the shared 30s default, so a
# long wait is not aborted client-side while the server is still working.
client.computer_wait(serialno, 2000) # milliseconds
# computer_bash runs on the host as the desktop user, unsandboxed —
# treat it as shell access. timeout_seconds is the server-side budget.
result = client.computer_bash(serialno, "uname -a", timeout_seconds=30)
print(f"exitCode={result.payload.get('exitCode')} out={result.payload.get('stdout')}")
if __name__ == "__main__":
main()