API Reference
Complete WebSocket API command reference
Client Commands
get_clients
Get list of all managed clients (windows).
// Request
{"command": "get_clients"}
// Response
{
"status": "ok",
"clients": [
{
"window": 12345678,
"title": "Window Title",
"class": "window-class",
"workspace": 0,
"x": 0,
"y": 32,
"width": 960,
"height": 540,
"focused": true,
"floating": false,
"fullscreen": false,
"maximized": false,
"minimized": false
}
]
}
find_clients
Search for clients by title, class, or workspace.
// Request - find by title (substring match)
{"command": "find_clients", "title": "Firefox"}
// Request - find by class
{"command": "find_clients", "class": "terminal"}
// Request - find by workspace
{"command": "find_clients", "workspace": 2}
// Request - combine filters
{"command": "find_clients", "class": "code", "workspace": 0}
// Response
{
"status": "ok",
"clients": [...]
}
get_focused_client
Get the currently focused client.
// Request
{"command": "get_focused_client"}
// Response
{
"status": "ok",
"client": {
"window": 12345678,
"title": "...",
"class": "...",
...
}
}
focus_client
Focus a client by window ID. Switches workspace if needed.
// Request
{"command": "focus_client", "window": 12345678}
// Response (returns current status)
{
"status": "ok",
"version": "2.0.0",
"current_workspace": 0,
"client_count": 5
}
close_client
Close a client gracefully (sends WM_DELETE_WINDOW).
// Request
{"command": "close_client", "window": 12345678}
// Response
{"status": "ok"}
kill_client
Force kill a client (XKillClient). Use when close_client fails.
// Request
{"command": "kill_client", "window": 12345678}
// Response
{"status": "ok"}
move_client
Move a client to specified position.
// Request
{
"command": "move_client",
"window": 12345678,
"x": 100,
"y": 100
}
// Response
{"status": "ok"}
resize_client
Resize a client to specified dimensions.
// Request
{
"command": "resize_client",
"window": 12345678,
"width": 800,
"height": 600
}
// Response
{"status": "ok"}
minimize_client
Minimize a client.
{"command": "minimize_client", "window": 12345678}
restore_client
Restore a minimized client.
{"command": "restore_client", "window": 12345678}
maximize_client
Maximize or unmaximize a client. Toggles if state not specified.
// Toggle maximize
{"command": "maximize_client", "window": 12345678}
// Set explicit state
{"command": "maximize_client", "window": 12345678, "state": true}
fullscreen_client
Set client fullscreen state. Toggles if state not specified.
// Toggle fullscreen
{"command": "fullscreen_client", "window": 12345678}
// Set explicit state
{"command": "fullscreen_client", "window": 12345678, "state": true}
float_client
Set client floating state. Toggles if state not specified.
// Toggle floating
{"command": "float_client", "window": 12345678}
// Set explicit state
{"command": "float_client", "window": 12345678, "state": true}
raise_client
Raise client to top of stack.
{"command": "raise_client", "window": 12345678}
lower_client
Lower client to bottom of stack.
{"command": "lower_client", "window": 12345678}
Workspace Commands
get_workspaces
Get list of all workspaces.
// Request
{"command": "get_workspaces"}
// Response
{
"status": "ok",
"workspaces": [
{
"id": 0,
"name": "1",
"layout": 0,
"client_count": 3
},
{
"id": 1,
"name": "2",
"layout": 0,
"client_count": 0
}
// ... workspaces 2-8
]
}
switch_workspace
Switch to specified workspace (0-8). Returns current status.
// Request
{"command": "switch_workspace", "workspace": 2}
// Response
{
"status": "ok",
"version": "2.0.0",
"current_workspace": 2,
"client_count": 5
}
move_client_to_workspace
Move specific client to workspace.
{
"command": "move_client_to_workspace",
"window": 12345678,
"workspace": 3
}
switch_workspace_next
Switch to the next workspace (wraps around).
{"command": "switch_workspace_next"}
// Response
{
"status": "ok",
"workspace": 1,
"workspace_name": "2"
}
switch_workspace_prev
Switch to the previous workspace (wraps around).
{"command": "switch_workspace_prev"}
Layout Commands
set_layout
Set workspace layout mode. Can use string names or numeric values.
// Set layout by name ("tiling", "floating", or "monocle")
{"command": "set_layout", "layout": "floating"}
// Set layout by number (0=tiling, 1=floating, 2=monocle)
{"command": "set_layout", "layout": 1}
// Optionally specify workspace (defaults to current)
{"command": "set_layout", "layout": "monocle", "workspace": 2}
cycle_layout
Cycle to next layout mode (tiling → floating → monocle → tiling).
// Cycle current workspace
{"command": "cycle_layout"}
// Cycle specific workspace
{"command": "cycle_layout", "workspace": 3}
set_master_ratio
Set the master area ratio (0.1-0.9) for tiling layout.
// Set on current workspace
{"command": "set_master_ratio", "ratio": 0.6}
// Set on specific workspace
{"command": "set_master_ratio", "ratio": 0.55, "workspace": 2}
// Response
{
"status": "ok",
"workspace": 0,
"master_ratio": 0.6
}
adjust_master_ratio
Adjust the master area ratio by a delta value.
// Increase master area by 5%
{"command": "adjust_master_ratio", "delta": 0.05}
// Decrease master area by 5%
{"command": "adjust_master_ratio", "delta": -0.05}
set_master_count
Set the number of windows in the master area (1-10).
{"command": "set_master_count", "count": 2}
// Response
{
"status": "ok",
"workspace": 0,
"master_count": 2
}
adjust_master_count
Adjust the master count by a delta value.
// Add one window to master
{"command": "adjust_master_count", "delta": 1}
// Remove one window from master
{"command": "adjust_master_count", "delta": -1}
focus_next
Focus the next window in the current workspace.
{"command": "focus_next"}
// Response
{
"status": "ok",
"focused_window": 12345678,
"focused_title": "Firefox"
}
focus_prev
Focus the previous window in the current workspace.
{"command": "focus_prev"}
focus_master
Focus the first window in the master area.
{"command": "focus_master"}
snap_client
Snap a window to screen edge or corner.
// Snap focused window left
{"command": "snap_client", "direction": "left"}
// Snap specific window
{"command": "snap_client", "window": 12345678, "direction": "right"}
// Directions: left, right, up, down
// Snapping is composable: left then up = top-left corner
// Response
{
"status": "ok",
"window": 12345678,
"snap": {
"horizontal": 1,
"vertical": 0
}
}
Keyboard Commands
key_press
Simulate key press (key down only). Use keysym (X11 keysym name) or keycode.
// By keysym name (X11 keysym names)
{"command": "key_press", "keysym": "a"}
{"command": "key_press", "keysym": "Return"}
{"command": "key_press", "keysym": "Tab"}
{"command": "key_press", "keysym": "Escape"}
{"command": "key_press", "keysym": "F1"}
{"command": "key_press", "keysym": "Control_L"}
// By keycode (hardware keycode)
{"command": "key_press", "keycode": 38}
key_release
Simulate key release (key up only).
{"command": "key_release", "keysym": "a"}
{"command": "key_release", "keycode": 38}
key_tap
Simulate a complete keypress (press + release) with optional modifiers.
// Simple key tap
{"command": "key_tap", "keysym": "a"}
// With modifiers (modifier keysym names)
{"command": "key_tap", "keysym": "c", "modifiers": ["Control_L"]}
{"command": "key_tap", "keysym": "t", "modifiers": ["Control_L", "Alt_L"]}
{"command": "key_tap", "keysym": "s", "modifiers": ["Control_L", "Shift_L"]}
// Special keys
{"command": "key_tap", "keysym": "Return"}
{"command": "key_tap", "keysym": "Tab"}
{"command": "key_tap", "keysym": "Escape"}
{"command": "key_tap", "keysym": "F1"}
Common modifier keysyms: Control_L, Control_R, Shift_L, Shift_R, Alt_L, Alt_R, Super_L, Super_R
key_type
Type a string of text. Automatically handles shift for uppercase and special characters.
{"command": "key_type", "text": "Hello, World!"}
Mouse Commands
mouse_move
Move mouse to absolute position.
{"command": "mouse_move", "x": 500, "y": 300}
mouse_move_relative
Move mouse relative to current position.
{"command": "mouse_move_relative", "dx": 10, "dy": -5}
mouse_click
Click mouse button (press + release).
// Left click at current position
{"command": "mouse_click", "button": 1}
// Right click at specific position (moves mouse first)
{"command": "mouse_click", "button": 3, "x": 100, "y": 200}
Buttons: 1=left, 2=middle, 3=right, 4=scroll up, 5=scroll down
mouse_press
Press mouse button without releasing (for drag operations).
{"command": "mouse_press", "button": 1}
mouse_release
Release mouse button.
{"command": "mouse_release", "button": 1}
mouse_scroll
Scroll mouse wheel.
// Scroll up (amount 1-100, default 1)
{"command": "mouse_scroll", "direction": "up", "amount": 3}
// Scroll down
{"command": "mouse_scroll", "direction": "down", "amount": 3}
get_mouse_position
Get current mouse position and window under cursor.
// Request
{"command": "get_mouse_position"}
// Response
{
"status": "ok",
"x": 500,
"y": 300,
"window_x": 100,
"window_y": 50,
"window": 12345678
}
Screenshot Commands
screenshot
Capture screenshot. Returns base64-encoded PNG.
Async Mode (Default)
By default, screenshot operations run asynchronously to avoid blocking the API. Set "async": false for synchronous behavior.
// Async (default) - returns when capture completes
{"command": "screenshot", "mode": "fullscreen"}
// Synchronous - blocks until complete
{"command": "screenshot", "mode": "fullscreen", "async": false}
Fullscreen Mode
// Request
{"command": "screenshot", "mode": "fullscreen"}
// Response
{
"status": "ok",
"format": "png",
"encoding": "base64",
"width": 1920,
"height": 1080,
"data": "iVBORw0KGgoAAAANSUhEUg..."
}
Active Window Mode
{"command": "screenshot", "mode": "active"}
Specific Window Mode
{"command": "screenshot", "mode": "window", "window": 12345678}
Area Mode
{
"command": "screenshot",
"mode": "area",
"x": 100,
"y": 100,
"width": 400,
"height": 300
}
OCR Commands
ocr
Extract text from image using OCR.
Async Mode (Default)
OCR operations run asynchronously by default since text extraction can take 1-10 seconds. Set "async": false for synchronous behavior.
// Async (default)
{"command": "ocr", "image": "...", "language": "eng"}
// Synchronous
{"command": "ocr", "image": "...", "language": "eng", "async": false}
Request/Response
// Request
{
"command": "ocr",
"image": "iVBORw0KGgoAAAANSUhEUg...", // base64 PNG
"language": "eng" // optional, default "eng"
}
// Response
{
"status": "ok",
"text": "Extracted text from image...",
"confidence": 0.95
}
Common language codes: eng (English), deu (German), fra (French), spa (Spanish)
Notification Commands
notify
Show a desktop notification.
// Request
{
"command": "notify",
"summary": "Hello!",
"body": "This is a notification message",
"app_name": "My App",
"timeout": 5000
}
// Response
{
"status": "ok",
"notification_id": 1
}
close_notification
Close a notification by ID.
{"command": "close_notification", "id": 1}
get_notifications
Get list of active notifications.
{"command": "get_notifications"}
// Response
{
"status": "ok",
"notifications": [
{
"id": 1,
"app_name": "My App",
"summary": "Hello!",
"body": "This is a notification",
"timeout": 5000,
"urgency": 1
}
]
}
System Tray Commands
get_battery_state
Get battery status information.
{"command": "get_battery_state"}
// Response
{
"status": "ok",
"battery": {
"present": true,
"charging": false,
"percentage": 75,
"time_remaining": 180
}
}
get_audio_state
Get audio volume and mute status.
{"command": "get_audio_state"}
// Response
{
"status": "ok",
"volume": 50,
"muted": false
}
set_audio_volume
Set audio volume (0-100).
{"command": "set_audio_volume", "volume": 75}
// Response
{
"status": "ok",
"volume": 75,
"muted": false
}
toggle_audio_mute
Toggle audio mute state.
{"command": "toggle_audio_mute"}
// Response
{
"status": "ok",
"muted": true,
"volume": 75
}
get_wifi_state
Get WiFi connection status.
{"command": "get_wifi_state"}
// Response
{
"status": "ok",
"enabled": true,
"connected": true,
"ssid": "MyNetwork",
"signal_strength": 80
}
Panel Commands
get_panel_state
Get state of top and bottom panels.
{"command": "get_panel_state"}
// Response
{
"status": "ok",
"top_panel": {
"enabled": true,
"visible": true,
"x": 0,
"y": 0,
"width": 1920,
"height": 32
},
"bottom_panel": {
"enabled": true,
"visible": true,
"x": 0,
"y": 1048,
"width": 1920,
"height": 32
}
}
show_panel
Show a panel.
{"command": "show_panel", "panel": "top"}
{"command": "show_panel", "panel": "bottom"}
hide_panel
Hide a panel.
{"command": "hide_panel", "panel": "top"}
toggle_panel
Toggle panel visibility.
{"command": "toggle_panel", "panel": "bottom"}
AI Commands
ai_is_available
Check if AI features are available (API key configured).
{"command": "ai_is_available"}
// Response
{
"status": "ok",
"available": true,
"model": "google/gemini-2.0-flash-exp:free"
}
ai_command
Send a command to the AI assistant. Async by default.
// Request
{
"command": "ai_command",
"prompt": "What windows are open?",
"async": true
}
// Response (when complete)
{
"status": "ok",
"response": "You have 3 windows open: Firefox, Terminal, and VS Code..."
}
exa_is_available
Check if Exa semantic search is available.
{"command": "exa_is_available"}
// Response
{
"status": "ok",
"available": true
}
exa_search
Perform semantic web search using Exa. Async by default.
// Request
{
"command": "exa_search",
"query": "how to configure nginx reverse proxy",
"async": true
}
// Response
{
"status": "ok",
"results": [
{
"title": "NGINX Reverse Proxy Configuration",
"url": "https://example.com/nginx-guide",
"snippet": "Learn how to configure NGINX as a reverse proxy...",
"score": 0.95
}
]
}
News Commands
get_news
Get news articles from the news ticker.
{"command": "get_news"}
// Response
{
"status": "ok",
"current_article": 0,
"article_count": 10,
"fetching": false,
"has_error": false,
"articles": [
{
"title": "Breaking News...",
"content": "Article content...",
"link": "https://example.com/news/1",
"author": "John Doe",
"sentiment": 0,
"sentiment_score": 0.5
}
]
}
news_next
Navigate to next news article.
{"command": "news_next"}
// Response
{
"status": "ok",
"current_article": 1,
"title": "Next article title..."
}
news_prev
Navigate to previous news article.
{"command": "news_prev"}
news_open
Open current news article in browser.
{"command": "news_open"}
// Response
{
"status": "ok",
"link": "https://example.com/news/1"
}
Demo/Tutorial Commands
start_demo
Start the automated demo mode.
{"command": "start_demo"}
stop_demo
Stop the demo mode.
{"command": "stop_demo"}
get_demo_state
Get current demo mode state.
{"command": "get_demo_state"}
// Response
{
"status": "ok",
"active": true,
"phase": 2,
"phase_name": "DEMO_WORKSPACES",
"step": 3
}
start_tutorial
Start the interactive tutorial.
{"command": "start_tutorial"}
stop_tutorial
Stop the tutorial.
{"command": "stop_tutorial"}
get_tutorial_state
Get current tutorial state.
{"command": "get_tutorial_state"}
// Response
{
"status": "ok",
"active": true
}
Configuration Commands
get_config
Get configuration values. Get a specific key or all config.
// Get specific key
{"command": "get_config", "key": "terminal"}
// Response
{
"status": "ok",
"value": "xfce4-terminal"
}
// Get all config
{"command": "get_config"}
// Response
{
"status": "ok",
"config": {
"terminal": "xfce4-terminal",
"launcher": "dmenu_run",
"focus_mode": "click",
"border_width": 0,
"panel_height": 32,
"gap": 0,
"ai_enabled": true,
"fade_speed": 0.5,
"fade_intensity": 1.0
...
}
}
reload_config
Reload configuration from file.
{"command": "reload_config"}
// Response
{
"status": "ok"
}
get_keybindings
Get list of all keyboard shortcuts.
{"command": "get_keybindings"}
// Response
{
"status": "ok",
"keybindings": [
{
"key": "t",
"modifiers": "ctrl+alt",
"description": "Open terminal"
},
{
"key": "F4",
"modifiers": "alt",
"description": "Close focused window"
}
...
]
}
Event Subscription
DWN supports real-time event streaming over WebSocket. Subscribe to events to receive notifications about window actions, workspace changes, input events, and more.
list_events
Get list of all available event types.
// Request
{"command": "list_events"}
// Response
{
"status": "ok",
"events": [
"window_created",
"window_destroyed",
"window_focused",
"window_unfocused",
"window_moved",
"window_resized",
"window_minimized",
"window_restored",
"window_maximized",
"window_unmaximized",
"window_fullscreen",
"window_unfullscreen",
"window_floating",
"window_unfloating",
"window_title_changed",
"window_raised",
"window_lowered",
"workspace_switched",
"workspace_window_added",
"workspace_window_removed",
"workspace_layout_changed",
"workspace_master_ratio_changed",
"workspace_master_count_changed",
"workspace_arranged",
"layout_changed",
"key_pressed",
"key_released",
"shortcut_triggered",
"mouse_moved",
"mouse_button_pressed",
"mouse_button_released",
"drag_started",
"drag_ended",
"show_desktop_toggled",
"notification_shown",
"notification_closed"
]
}
subscribe
Subscribe to specific events or all events.
// Subscribe to specific events
{"command": "subscribe", "events": ["window_focused", "window_created"]}
// Subscribe to all events
{"command": "subscribe", "all": true}
// Response
{
"status": "ok",
"subscribed": ["window_focused", "window_created"]
}
unsubscribe
Unsubscribe from specific events or all events.
// Unsubscribe from specific events
{"command": "unsubscribe", "events": ["window_focused"]}
// Unsubscribe from all events
{"command": "unsubscribe", "all": true}
// Response
{"status": "ok"}
Event Message Format
When subscribed, events are pushed to the client as JSON messages:
// Window focus event
{
"type": "event",
"event": "window_focused",
"data": {
"window": 12345678,
"title": "Firefox",
"previous_window": 87654321
}
}
// Window moved event
{
"type": "event",
"event": "window_moved",
"data": {
"window": 12345678,
"old_x": 0,
"old_y": 32,
"new_x": 100,
"new_y": 100
}
}
// Workspace switched event
{
"type": "event",
"event": "workspace_switched",
"data": {
"old_workspace": 0,
"new_workspace": 2
}
}
// Keyboard shortcut triggered
{
"type": "event",
"event": "shortcut_triggered",
"data": {
"name": "Return",
"description": "Open terminal"
}
}
// Notification shown
{
"type": "event",
"event": "notification_shown",
"data": {
"id": 1,
"summary": "New Message",
"body": "You have a new message"
}
}
// Fade speed changed
{
"type": "event",
"event": "fade_speed_changed",
"data": {
"old_speed": 0.5,
"new_speed": 1.0
}
}
// Fade intensity changed
{
"type": "event",
"event": "fade_intensity_changed",
"data": {
"old_intensity": 1.0,
"new_intensity": 0.8
}
}
Event Types Reference
| Event | Description | Data Fields |
|---|---|---|
window_created |
New window managed | window, title, class, workspace |
window_destroyed |
Window closed | window, title, workspace |
window_focused |
Window received focus | window, title, previous_window |
window_unfocused |
Window lost focus | window, title |
window_moved |
Window position changed | window, old_x, old_y, new_x, new_y |
window_resized |
Window size changed | window, old_width, old_height, new_width, new_height |
window_minimized |
Window minimized | window |
window_restored |
Window restored from minimized | window |
window_maximized |
Window maximized/unmaximized | window, maximized |
window_fullscreen |
Fullscreen toggled | window, fullscreen |
window_floating |
Floating mode toggled | window, floating |
window_title_changed |
Window title updated | window, old_title, new_title |
workspace_switched |
Active workspace changed | old_workspace, new_workspace |
workspace_layout_changed |
Workspace layout changed | workspace, old_layout, new_layout |
key_pressed |
Key pressed | keycode, keysym, modifiers |
shortcut_triggered |
Keyboard shortcut executed | name, description |
mouse_button_pressed |
Mouse button pressed | button, x, y |
drag_started |
Window drag/resize started | window, is_resize |
drag_ended |
Window drag/resize ended | window, is_resize |
show_desktop_toggled |
Show desktop mode toggled | shown |
notification_shown |
Notification displayed | id, summary, body |
notification_closed |
Notification closed | id |
fade_speed_changed |
Fade animation speed changed | old_speed, new_speed |
fade_intensity_changed |
Fade glow intensity changed | old_intensity, new_intensity |
window_snapped |
Window snapped to position | window, horizontal, vertical |
audio_volume_changed |
System audio volume changed | old_volume, new_volume |
audio_mute_toggled |
System audio mute toggled | muted |
panel_visibility_changed |
Panel shown or hidden | panel, visible |
config_reloaded |
Configuration reloaded | (none) |
ai_response_received |
AI command completed | prompt, response, success |
exa_search_completed |
Exa search completed | query, result_count, success |
news_article_changed |
News ticker article changed | old_index, new_index, title |
demo_started |
Demo mode started | (none) |
demo_stopped |
Demo mode stopped | (none) |
demo_phase_changed |
Demo phase changed | phase, phase_name |
tutorial_started |
Tutorial mode started | (none) |
tutorial_stopped |
Tutorial mode stopped | (none) |
System Commands
get_status
Get DWN status information.
// Request
{"command": "get_status"}
// Response
{
"status": "ok",
"version": "2.0.0",
"current_workspace": 0,
"client_count": 5
}
get_screen_info
Get screen and monitor information.
// Request
{"command": "get_screen_info"}
// Response
{
"status": "ok",
"screen_width": 1920,
"screen_height": 1080,
"screen": 0,
"monitor_count": 1,
"monitors": [
{
"index": 0,
"x": 0,
"y": 0,
"width": 1920,
"height": 1080,
"primary": true
}
],
"usable_area": {
"x": 0,
"y": 32,
"width": 1920,
"height": 1048
}
}
run_command
Spawn a process asynchronously.
// Request
{"command": "run_command", "exec": "firefox"}
// Response
{"status": "launched"}
show_desktop
Toggle show desktop mode. Optionally set explicit state.
// Toggle
{"command": "show_desktop"}
// Set explicit state
{"command": "show_desktop", "state": true}
// Response
{
"status": "ok",
"desktop_shown": true
}
get_fade_settings
Get current fade effect settings (speed and intensity).
// Request
{"command": "get_fade_settings"}
// Response
{
"status": "ok",
"fade_speed": 0.5,
"fade_intensity": 1.0
}
set_fade_speed
Set fade animation speed (0.1 - 3.0, where 1.0 is normal speed).
// Request
{"command": "set_fade_speed", "speed": 1.5}
// Response
{
"status": "ok",
"fade_speed": 1.5
}
set_fade_intensity
Set fade glow intensity (0.0 - 1.0, where 1.0 is full intensity).
// Request
{"command": "set_fade_intensity", "intensity": 0.8}
// Response
{
"status": "ok",
"fade_intensity": 0.8
}
Error Responses
All commands may return errors:
{
"status": "error",
"message": "Window not found"
}
{
"status": "error",
"message": "Invalid parameter: workspace must be 0-8"
}
{
"status": "error",
"message": "Unknown command: invalid_command"
}