| 1 | //! IPC protocol types for garchomp compositor. |
| 2 | |
| 3 | use serde::{Deserialize, Serialize}; |
| 4 | |
| 5 | /// IPC protocol version for compatibility checks. |
| 6 | pub const PROTOCOL_VERSION: u32 = 1; |
| 7 | |
| 8 | /// Request sent to garchomp. |
| 9 | #[derive(Debug, Clone, Serialize, Deserialize)] |
| 10 | #[serde(tag = "type", rename_all = "snake_case")] |
| 11 | pub enum Request { |
| 12 | /// Reload configuration. |
| 13 | Reload, |
| 14 | /// Toggle an effect. |
| 15 | SetEffect { effect: String, enabled: bool }, |
| 16 | /// Set blur strength (0-20). |
| 17 | SetBlurStrength { strength: u32 }, |
| 18 | /// Get window information. |
| 19 | GetWindowInfo { window: u32 }, |
| 20 | /// List all managed windows. |
| 21 | ListWindows, |
| 22 | /// Ping for health check. |
| 23 | Ping, |
| 24 | /// Version negotiation. |
| 25 | Version { version: u32 }, |
| 26 | /// Get compositor status. |
| 27 | Status, |
| 28 | } |
| 29 | |
| 30 | /// Response from garchomp. |
| 31 | #[derive(Debug, Clone, Serialize, Deserialize)] |
| 32 | #[serde(tag = "type", rename_all = "snake_case")] |
| 33 | pub enum Response { |
| 34 | /// Success with no data. |
| 35 | Ok, |
| 36 | /// Error response. |
| 37 | Error { message: String }, |
| 38 | /// Pong response to ping. |
| 39 | Pong, |
| 40 | /// Version response. |
| 41 | Version { version: u32, name: String }, |
| 42 | /// Compositor status. |
| 43 | Status(CompositorStatus), |
| 44 | /// Window information. |
| 45 | WindowInfo(WindowInfo), |
| 46 | /// List of windows. |
| 47 | WindowList { windows: Vec<WindowInfo> }, |
| 48 | } |
| 49 | |
| 50 | /// Compositor status information. |
| 51 | #[derive(Debug, Clone, Serialize, Deserialize)] |
| 52 | pub struct CompositorStatus { |
| 53 | pub version: u32, |
| 54 | pub window_count: usize, |
| 55 | pub current_workspace: usize, |
| 56 | pub effects_enabled: EffectsStatus, |
| 57 | pub connected_to_gar: bool, |
| 58 | #[serde(default)] |
| 59 | pub monitors: Vec<MonitorStatus>, |
| 60 | } |
| 61 | |
| 62 | /// Information about a monitor. |
| 63 | #[derive(Debug, Clone, Serialize, Deserialize)] |
| 64 | pub struct MonitorStatus { |
| 65 | pub name: String, |
| 66 | pub x: i16, |
| 67 | pub y: i16, |
| 68 | pub width: u16, |
| 69 | pub height: u16, |
| 70 | pub primary: bool, |
| 71 | } |
| 72 | |
| 73 | /// Status of compositor effects. |
| 74 | #[derive(Debug, Clone, Serialize, Deserialize)] |
| 75 | pub struct EffectsStatus { |
| 76 | pub blur: bool, |
| 77 | pub shadows: bool, |
| 78 | pub animations: bool, |
| 79 | pub blur_strength: u32, |
| 80 | } |
| 81 | |
| 82 | /// Information about a managed window. |
| 83 | #[derive(Debug, Clone, Serialize, Deserialize)] |
| 84 | pub struct WindowInfo { |
| 85 | pub id: u32, |
| 86 | pub x: i16, |
| 87 | pub y: i16, |
| 88 | pub width: u16, |
| 89 | pub height: u16, |
| 90 | pub mapped: bool, |
| 91 | pub override_redirect: bool, |
| 92 | #[serde(default)] |
| 93 | pub workspace: Option<usize>, |
| 94 | #[serde(default)] |
| 95 | pub focused: bool, |
| 96 | #[serde(default)] |
| 97 | pub fullscreen: bool, |
| 98 | #[serde(default)] |
| 99 | pub class: Option<String>, |
| 100 | #[serde(default)] |
| 101 | pub title: Option<String>, |
| 102 | } |
| 103 | |
| 104 | /// Events sent from gar WM to garchomp. |
| 105 | #[derive(Debug, Clone, Serialize, Deserialize)] |
| 106 | #[serde(tag = "type", rename_all = "snake_case")] |
| 107 | pub enum GarEvent { |
| 108 | /// Workspace changed. |
| 109 | WorkspaceChanged { |
| 110 | from: usize, |
| 111 | to: usize, |
| 112 | direction: String, |
| 113 | }, |
| 114 | /// Focus changed. |
| 115 | FocusChanged { old: Option<u32>, new: Option<u32> }, |
| 116 | /// Window entered fullscreen. |
| 117 | WindowFullscreen { window: u32, fullscreen: bool }, |
| 118 | /// Window moved. |
| 119 | WindowMoved { window: u32, x: i32, y: i32 }, |
| 120 | /// Window resized. |
| 121 | WindowResized { window: u32, width: u32, height: u32 }, |
| 122 | /// Window workspace changed. |
| 123 | WindowWorkspace { window: u32, workspace: usize }, |
| 124 | /// Initial sync request (gar sending full state). |
| 125 | Sync { windows: Vec<WindowInfo>, current_workspace: usize }, |
| 126 | } |
| 127 | |
| 128 | /// Direction of workspace transition. |
| 129 | #[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)] |
| 130 | #[serde(rename_all = "snake_case")] |
| 131 | pub enum TransitionDirection { |
| 132 | Left, |
| 133 | Right, |
| 134 | Up, |
| 135 | Down, |
| 136 | } |
| 137 | |
| 138 | impl TransitionDirection { |
| 139 | pub fn from_str(s: &str) -> Self { |
| 140 | match s.to_lowercase().as_str() { |
| 141 | "left" => Self::Left, |
| 142 | "right" => Self::Right, |
| 143 | "up" => Self::Up, |
| 144 | "down" => Self::Down, |
| 145 | _ => Self::Right, |
| 146 | } |
| 147 | } |
| 148 | } |
| 149 |