From 4ce0d6f014fb89c17af8493357b61f0cf75e7946 Mon Sep 17 00:00:00 2001 From: Michael Stapelberg Date: Fri, 19 Mar 2010 22:24:52 +0100 Subject: [PATCH] ipc: implement GET_OUTPUTS --- docs/ipc | 49 ++++++++++++++++++++++++++++++++++++++++ include/data.h | 4 ++-- include/i3/ipc.h | 6 +++++ src/ipc.c | 58 ++++++++++++++++++++++++++++++++++++++++++++++-- 4 files changed, 113 insertions(+), 4 deletions(-) diff --git a/docs/ipc b/docs/ipc index 383bde50..35a5fa03 100644 --- a/docs/ipc +++ b/docs/ipc @@ -49,6 +49,9 @@ GET_WORKSPACES (1):: SUBSCRIBE (2):: Subscribes your connection to certain events. See <> for a description of this message and the concept of events. +GET_OUTPUTS (3):: + Gets the current outputs. The reply will be a JSON-encoded list of outputs + (see the reply section). So, a typical message could look like this: -------------------------------------------------- @@ -96,6 +99,8 @@ GET_WORKSPACES (1):: Reply to the GET_WORKSPACES message. SUBSCRIBE (2):: Confirmation/Error code for the SUBSCRIBE message. +GET_OUTPUTS (3):: + Reply to the GET_OUTPUTS message. === COMMAND reply @@ -177,6 +182,50 @@ default) or whether a JSON parse error occurred. { "success": true } ------------------- +=== GET_OUTPUTS reply + +The reply consists of a serialized list of outputs. Each output has the +following properties: + +name (string):: + The name of this output (as seen in +xrandr(1)+). Encoded in UTF-8. +active (boolean):: + Whether this output is currently active (has a valid mode). +current_workspace (integer):: + The current workspace which is visible on this output. +null+ if the + output is not active. +rect (map):: + The rectangle of this output (equals the rect of the output it + is on), consists of x, y, width, height. + +*Example:* +------------------- +[ + { + "name": "LVDS1", + "active": true, + "current_workspace": 4, + "rect": { + "x": 0, + "y": 0, + "width": 1280, + "height": 800 + } + }, + { + "name": "VGA1", + "active": true, + "current_workspace": 1, + "rect": { + "x": 1280, + "y": 0, + "width": 1280, + "height": 1024 + }, + } +] +------------------- + == Events [[events]] diff --git a/include/data.h b/include/data.h index 6819ca95..2d8c7b1a 100644 --- a/include/data.h +++ b/include/data.h @@ -512,8 +512,8 @@ struct xoutput { /** Name of the output */ char *name; - /** Whether the output is currently (has a CRTC attached with a valid - * mode) */ + /** Whether the output is currently active (has a CRTC attached with a + * valid mode) */ bool active; /** Internal flags, necessary for querying RandR screens (happens in diff --git a/include/i3/ipc.h b/include/i3/ipc.h index 5adec378..56f22344 100644 --- a/include/i3/ipc.h +++ b/include/i3/ipc.h @@ -32,6 +32,9 @@ /** Subscribe to the specified events */ #define I3_IPC_MESSAGE_TYPE_SUBSCRIBE 2 +/** Requests the current outputs from i3 */ +#define I3_IPC_MESSAGE_TYPE_GET_OUTPUTS 3 + /* * Messages from i3 to clients * @@ -46,6 +49,9 @@ /** Subscription reply type */ #define I3_IPC_REPLY_TYPE_SUBSCRIBE 2 +/** Outputs reply type */ +#define I3_IPC_REPLY_TYPE_OUTPUTS 3 + /* * Events from i3 to clients. Events have the first bit set high. * diff --git a/src/ipc.c b/src/ipc.c index 1b9bf6e0..8ed455dd 100644 --- a/src/ipc.c +++ b/src/ipc.c @@ -32,6 +32,7 @@ #include "commands.h" #include "log.h" #include "table.h" +#include "randr.h" /* Shorter names for all those yajl_gen_* functions */ #define y(x, ...) yajl_gen_ ## x (gen, ##__VA_ARGS__) @@ -201,6 +202,56 @@ IPC_HANDLER(get_workspaces) { y(free); } +/* + * Formats the reply message for a GET_OUTPUTS request and sends it to the + * client + * + */ +IPC_HANDLER(get_outputs) { + Output *output; + + yajl_gen gen = yajl_gen_alloc(NULL, NULL); + y(array_open); + + TAILQ_FOREACH(output, &outputs, outputs) { + y(map_open); + + ystr("name"); + ystr(output->name); + + ystr("active"); + y(bool, output->active); + + ystr("rect"); + y(map_open); + ystr("x"); + y(integer, output->rect.x); + ystr("y"); + y(integer, output->rect.y); + ystr("width"); + y(integer, output->rect.width); + ystr("height"); + y(integer, output->rect.height); + y(map_close); + + ystr("current_workspace"); + if (output->current_workspace == NULL) + y(null); + else y(integer, output->current_workspace->num + 1); + + y(map_close); + } + + y(array_close); + + const unsigned char *payload; + unsigned int length; + y(get_buf, &payload, &length); + + ipc_send_message(fd, payload, I3_IPC_REPLY_TYPE_OUTPUTS, length); + y(free); +} + /* * Callback for the YAJL parser (will be called when a string is parsed). * @@ -277,10 +328,13 @@ IPC_HANDLER(subscribe) { I3_IPC_REPLY_TYPE_SUBSCRIBE, strlen(reply)); } -handler_t handlers[3] = { +/* The index of each callback function corresponds to the numeric + * value of the message type (see include/i3/ipc.h) */ +handler_t handlers[4] = { handle_command, handle_get_workspaces, - handle_subscribe + handle_subscribe, + handle_get_outputs }; /* -- 2.39.5