Optimization: Get the colorpixels when loading configuration, make use of the new config struct
Instead of building arrays of colorpixels we can simply use a pointer to a struct Colortriple. Furthermore, by getting the colorpixels when loading the configuration, we save a lot of function calls in the main code.
This commit is contained in:
parent
1fcad44f66
commit
2a67630aa6
|
@ -19,9 +19,9 @@ typedef struct Config Config;
|
||||||
extern Config config;
|
extern Config config;
|
||||||
|
|
||||||
struct Colortriple {
|
struct Colortriple {
|
||||||
char border[8];
|
uint32_t border;
|
||||||
char background[8];
|
uint32_t background;
|
||||||
char text[8];
|
uint32_t text;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct Config {
|
struct Config {
|
||||||
|
@ -47,6 +47,6 @@ struct Config {
|
||||||
* configuration file.
|
* configuration file.
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void load_configuration(const char *override_configfile);
|
void load_configuration(xcb_connection_t *conn, const char *override_configfile);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
53
src/config.c
53
src/config.c
|
@ -17,6 +17,7 @@
|
||||||
#include "i3.h"
|
#include "i3.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
|
#include "xcb.h"
|
||||||
|
|
||||||
Config config;
|
Config config;
|
||||||
|
|
||||||
|
@ -41,7 +42,7 @@ static char *glob_path(const char *path) {
|
||||||
* configuration file.
|
* configuration file.
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void load_configuration(const char *override_configpath) {
|
void load_configuration(xcb_connection_t *conn, const char *override_configpath) {
|
||||||
#define OPTION_STRING(name) \
|
#define OPTION_STRING(name) \
|
||||||
if (strcasecmp(key, #name) == 0) { \
|
if (strcasecmp(key, #name) == 0) { \
|
||||||
config.name = sstrdup(value); \
|
config.name = sstrdup(value); \
|
||||||
|
@ -54,16 +55,20 @@ void load_configuration(const char *override_configpath) {
|
||||||
|
|
||||||
#define OPTION_COLORTRIPLE(opt, name) \
|
#define OPTION_COLORTRIPLE(opt, name) \
|
||||||
if (strcasecmp(key, opt) == 0) { \
|
if (strcasecmp(key, opt) == 0) { \
|
||||||
struct Colortriple buffer; \
|
char border[8], background[8], text[8]; \
|
||||||
memset(&buffer, 0, sizeof(struct Colortriple)); \
|
memset(border, 0, sizeof(border)); \
|
||||||
buffer.border[0] = buffer.background[0] = buffer.text[0] = '#'; \
|
memset(background, 0, sizeof(background)); \
|
||||||
|
memset(text, 0, sizeof(text)); \
|
||||||
|
border[0] = background[0] = text[0] = '#'; \
|
||||||
if (sscanf(value, "#%06[0-9a-fA-F] #%06[0-9a-fA-F] #%06[0-9a-fA-F]", \
|
if (sscanf(value, "#%06[0-9a-fA-F] #%06[0-9a-fA-F] #%06[0-9a-fA-F]", \
|
||||||
buffer.border + 1, buffer.background + 1, buffer.text + 1) != 3 || \
|
border + 1, background + 1, text + 1) != 3 || \
|
||||||
strlen(buffer.border) != 7 || \
|
strlen(border) != 7 || \
|
||||||
strlen(buffer.background) != 7 || \
|
strlen(background) != 7 || \
|
||||||
strlen(buffer.text) != 7) \
|
strlen(text) != 7) \
|
||||||
die("invalid color code line: %s\n", value); \
|
die("invalid color code line: %s\n", value); \
|
||||||
memcpy(&config.name, &buffer, sizeof(struct Colortriple)); \
|
config.name.border = get_colorpixel(conn, border); \
|
||||||
|
config.name.background = get_colorpixel(conn, background); \
|
||||||
|
config.name.text = get_colorpixel(conn, text); \
|
||||||
continue; \
|
continue; \
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -71,25 +76,25 @@ void load_configuration(const char *override_configpath) {
|
||||||
memset(&config, 0, sizeof(config));
|
memset(&config, 0, sizeof(config));
|
||||||
|
|
||||||
/* Initialize default colors */
|
/* Initialize default colors */
|
||||||
strcpy(config.client.focused.border, "#4c7899");
|
config.client.focused.border = get_colorpixel(conn, "#4c7899");
|
||||||
strcpy(config.client.focused.background, "#285577");
|
config.client.focused.background = get_colorpixel(conn, "#285577");
|
||||||
strcpy(config.client.focused.text, "#ffffff");
|
config.client.focused.text = get_colorpixel(conn, "#ffffff");
|
||||||
|
|
||||||
strcpy(config.client.focused_inactive.border, "#4c7899");
|
config.client.focused_inactive.border = get_colorpixel(conn, "#4c7899");
|
||||||
strcpy(config.client.focused_inactive.background, "#555555");
|
config.client.focused_inactive.background = get_colorpixel(conn, "#555555");
|
||||||
strcpy(config.client.focused_inactive.text, "#ffffff");
|
config.client.focused_inactive.text = get_colorpixel(conn, "#ffffff");
|
||||||
|
|
||||||
strcpy(config.client.unfocused.border, "#333333");
|
config.client.unfocused.border = get_colorpixel(conn, "#333333");
|
||||||
strcpy(config.client.unfocused.background, "#222222");
|
config.client.unfocused.background = get_colorpixel(conn, "#222222");
|
||||||
strcpy(config.client.unfocused.text, "#888888");
|
config.client.unfocused.text = get_colorpixel(conn, "#888888");
|
||||||
|
|
||||||
strcpy(config.bar.focused.border, "#4c7899");
|
config.bar.focused.border = get_colorpixel(conn, "#4c7899");
|
||||||
strcpy(config.bar.focused.background, "#285577");
|
config.bar.focused.background = get_colorpixel(conn, "#285577");
|
||||||
strcpy(config.bar.focused.text, "#ffffff");
|
config.bar.focused.text = get_colorpixel(conn, "#ffffff");
|
||||||
|
|
||||||
strcpy(config.bar.unfocused.border, "#333333");
|
config.bar.unfocused.border = get_colorpixel(conn, "#333333");
|
||||||
strcpy(config.bar.unfocused.background, "#222222");
|
config.bar.unfocused.background = get_colorpixel(conn, "#222222");
|
||||||
strcpy(config.bar.unfocused.text, "#888888");
|
config.bar.unfocused.text = get_colorpixel(conn, "#888888");
|
||||||
|
|
||||||
FILE *handle;
|
FILE *handle;
|
||||||
if (override_configpath != NULL) {
|
if (override_configpath != NULL) {
|
||||||
|
|
|
@ -793,9 +793,9 @@ int handle_expose_event(void *data, xcb_connection_t *conn, xcb_expose_event_t *
|
||||||
uint32_t background_color;
|
uint32_t background_color;
|
||||||
/* Distinguish if the window is currently focused… */
|
/* Distinguish if the window is currently focused… */
|
||||||
if (CUR_CELL->currently_focused == client)
|
if (CUR_CELL->currently_focused == client)
|
||||||
background_color = get_colorpixel(conn, config.client.focused.background);
|
background_color = config.client.focused.background;
|
||||||
/* …or if it is the focused window in a not focused container */
|
/* …or if it is the focused window in a not focused container */
|
||||||
else background_color = get_colorpixel(conn, config.client.focused_inactive.background);
|
else background_color = config.client.focused_inactive.background;
|
||||||
|
|
||||||
/* Set foreground color to current focused color, line width to 2 */
|
/* Set foreground color to current focused color, line width to 2 */
|
||||||
uint32_t values[] = {background_color, 2};
|
uint32_t values[] = {background_color, 2};
|
||||||
|
|
54
src/layout.c
54
src/layout.c
|
@ -100,9 +100,7 @@ void redecorate_window(xcb_connection_t *conn, Client *client) {
|
||||||
void decorate_window(xcb_connection_t *conn, Client *client, xcb_drawable_t drawable, xcb_gcontext_t gc, int offset) {
|
void decorate_window(xcb_connection_t *conn, Client *client, xcb_drawable_t drawable, xcb_gcontext_t gc, int offset) {
|
||||||
i3Font *font = load_font(conn, config.font);
|
i3Font *font = load_font(conn, config.font);
|
||||||
int decoration_height = font->height + 2 + 2;
|
int decoration_height = font->height + 2 + 2;
|
||||||
uint32_t background_color,
|
struct Colortriple *color;
|
||||||
text_color,
|
|
||||||
border_color;
|
|
||||||
|
|
||||||
/* Clients without a container (docks) won’t get decorated */
|
/* Clients without a container (docks) won’t get decorated */
|
||||||
if (client->dock)
|
if (client->dock)
|
||||||
|
@ -112,26 +110,19 @@ void decorate_window(xcb_connection_t *conn, Client *client, xcb_drawable_t draw
|
||||||
if (client->floating >= FLOATING_AUTO_ON || client->container->currently_focused == client) {
|
if (client->floating >= FLOATING_AUTO_ON || client->container->currently_focused == client) {
|
||||||
/* Distinguish if the window is currently focused… */
|
/* Distinguish if the window is currently focused… */
|
||||||
if (client->floating >= FLOATING_AUTO_ON || CUR_CELL->currently_focused == client)
|
if (client->floating >= FLOATING_AUTO_ON || CUR_CELL->currently_focused == client)
|
||||||
background_color = get_colorpixel(conn, config.client.focused.background);
|
color = &(config.client.focused);
|
||||||
/* …or if it is the focused window in a not focused container */
|
/* …or if it is the focused window in a not focused container */
|
||||||
else background_color = get_colorpixel(conn, config.client.focused_inactive.background);
|
else color = &(config.client.focused_inactive);
|
||||||
|
} else color = &(config.client.unfocused);
|
||||||
text_color = get_colorpixel(conn, config.client.focused.text);
|
|
||||||
border_color = get_colorpixel(conn, config.client.focused.border);
|
|
||||||
} else {
|
|
||||||
background_color = get_colorpixel(conn, config.client.unfocused.background);
|
|
||||||
text_color = get_colorpixel(conn, config.client.unfocused.text);
|
|
||||||
border_color = get_colorpixel(conn, config.client.unfocused.border);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Our plan is the following:
|
/* Our plan is the following:
|
||||||
- Draw a rect around the whole client in background_color
|
- Draw a rect around the whole client in color->background
|
||||||
- Draw two lines in a lighter color
|
- Draw two lines in a lighter color
|
||||||
- Draw the window’s title
|
- Draw the window’s title
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* Draw a rectangle in background color around the window */
|
/* Draw a rectangle in background color around the window */
|
||||||
xcb_change_gc_single(conn, gc, XCB_GC_FOREGROUND, background_color);
|
xcb_change_gc_single(conn, gc, XCB_GC_FOREGROUND, color->background);
|
||||||
|
|
||||||
/* In stacking mode, we only render the rect for this specific decoration */
|
/* In stacking mode, we only render the rect for this specific decoration */
|
||||||
if (client->container != NULL && client->container->mode == MODE_STACK) {
|
if (client->container != NULL && client->container->mode == MODE_STACK) {
|
||||||
|
@ -153,15 +144,15 @@ void decorate_window(xcb_connection_t *conn, Client *client, xcb_drawable_t draw
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Draw the lines */
|
/* Draw the lines */
|
||||||
xcb_draw_line(conn, drawable, gc, border_color, 0, offset, client->rect.width, offset);
|
xcb_draw_line(conn, drawable, gc, color->border, 0, offset, client->rect.width, offset);
|
||||||
xcb_draw_line(conn, drawable, gc, border_color, 2, offset + font->height + 3,
|
xcb_draw_line(conn, drawable, gc, color->border, 2, offset + font->height + 3,
|
||||||
client->rect.width - 4, offset + font->height + 3);
|
client->rect.width - 4, offset + font->height + 3);
|
||||||
|
|
||||||
/* If the client has a title, we draw it */
|
/* If the client has a title, we draw it */
|
||||||
if (client->name != NULL) {
|
if (client->name != NULL) {
|
||||||
/* Draw the font */
|
/* Draw the font */
|
||||||
uint32_t mask = XCB_GC_FOREGROUND | XCB_GC_BACKGROUND | XCB_GC_FONT;
|
uint32_t mask = XCB_GC_FOREGROUND | XCB_GC_BACKGROUND | XCB_GC_FONT;
|
||||||
uint32_t values[] = { text_color, background_color, font->id };
|
uint32_t values[] = { color->text, color->background, font->id };
|
||||||
xcb_change_gc(conn, gc, mask, values);
|
xcb_change_gc(conn, gc, mask, values);
|
||||||
|
|
||||||
/* name_len == -1 means this is a legacy application which does not specify _NET_WM_NAME,
|
/* name_len == -1 means this is a legacy application which does not specify _NET_WM_NAME,
|
||||||
|
@ -401,24 +392,10 @@ static void render_internal_bar(xcb_connection_t *conn, Workspace *r_ws, int wid
|
||||||
i3Font *font = load_font(conn, config.font);
|
i3Font *font = load_font(conn, config.font);
|
||||||
i3Screen *screen = r_ws->screen;
|
i3Screen *screen = r_ws->screen;
|
||||||
enum { SET_NORMAL = 0, SET_FOCUSED = 1 };
|
enum { SET_NORMAL = 0, SET_FOCUSED = 1 };
|
||||||
uint32_t background_color[2],
|
|
||||||
text_color[2],
|
|
||||||
border_color[2],
|
|
||||||
black;
|
|
||||||
char label[3];
|
char label[3];
|
||||||
|
|
||||||
black = get_colorpixel(conn, "#000000");
|
|
||||||
|
|
||||||
background_color[SET_NORMAL] = get_colorpixel(conn, config.bar.unfocused.background);
|
|
||||||
text_color[SET_NORMAL] = get_colorpixel(conn, config.bar.unfocused.text);
|
|
||||||
border_color[SET_NORMAL] = get_colorpixel(conn, config.bar.unfocused.border);
|
|
||||||
|
|
||||||
background_color[SET_FOCUSED] = get_colorpixel(conn, config.bar.focused.background);
|
|
||||||
text_color[SET_FOCUSED] = get_colorpixel(conn, config.bar.focused.text);
|
|
||||||
border_color[SET_FOCUSED] = get_colorpixel(conn, config.bar.focused.border);
|
|
||||||
|
|
||||||
/* Fill the whole bar in black */
|
/* Fill the whole bar in black */
|
||||||
xcb_change_gc_single(conn, screen->bargc, XCB_GC_FOREGROUND, black);
|
xcb_change_gc_single(conn, screen->bargc, XCB_GC_FOREGROUND, get_colorpixel(conn, "#000000"));
|
||||||
xcb_rectangle_t rect = {0, 0, width, height};
|
xcb_rectangle_t rect = {0, 0, width, height};
|
||||||
xcb_poly_fill_rectangle(conn, screen->bar, screen->bargc, 1, &rect);
|
xcb_poly_fill_rectangle(conn, screen->bar, screen->bargc, 1, &rect);
|
||||||
|
|
||||||
|
@ -430,16 +407,17 @@ static void render_internal_bar(xcb_connection_t *conn, Workspace *r_ws, int wid
|
||||||
if (workspaces[c].screen != screen)
|
if (workspaces[c].screen != screen)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
int set = (screen->current_workspace == c ? SET_FOCUSED : SET_NORMAL);
|
struct Colortriple *color = (screen->current_workspace == c ? &(config.bar.focused) :
|
||||||
|
&(config.bar.unfocused));
|
||||||
|
|
||||||
xcb_draw_rect(conn, screen->bar, screen->bargc, border_color[set],
|
xcb_draw_rect(conn, screen->bar, screen->bargc, color->border,
|
||||||
drawn * height, 1, height - 2, height - 2);
|
drawn * height, 1, height - 2, height - 2);
|
||||||
xcb_draw_rect(conn, screen->bar, screen->bargc, background_color[set],
|
xcb_draw_rect(conn, screen->bar, screen->bargc, color->background,
|
||||||
drawn * height + 1, 2, height - 4, height - 4);
|
drawn * height + 1, 2, height - 4, height - 4);
|
||||||
|
|
||||||
snprintf(label, sizeof(label), "%d", c+1);
|
snprintf(label, sizeof(label), "%d", c+1);
|
||||||
xcb_change_gc_single(conn, screen->bargc, XCB_GC_FOREGROUND, text_color[set]);
|
xcb_change_gc_single(conn, screen->bargc, XCB_GC_FOREGROUND, color->text);
|
||||||
xcb_change_gc_single(conn, screen->bargc, XCB_GC_BACKGROUND, background_color[set]);
|
xcb_change_gc_single(conn, screen->bargc, XCB_GC_BACKGROUND, color->background);
|
||||||
xcb_image_text_8(conn, strlen(label), screen->bar, screen->bargc, drawn * height + 5 /* X */,
|
xcb_image_text_8(conn, strlen(label), screen->bar, screen->bargc, drawn * height + 5 /* X */,
|
||||||
font->height + 1 /* Y = baseline of font */, label);
|
font->height + 1 /* Y = baseline of font */, label);
|
||||||
drawn++;
|
drawn++;
|
||||||
|
|
|
@ -112,10 +112,10 @@ int main(int argc, char *argv[], char *env[]) {
|
||||||
memset(&evenths, 0, sizeof(xcb_event_handlers_t));
|
memset(&evenths, 0, sizeof(xcb_event_handlers_t));
|
||||||
memset(&prophs, 0, sizeof(xcb_property_handlers_t));
|
memset(&prophs, 0, sizeof(xcb_property_handlers_t));
|
||||||
|
|
||||||
load_configuration(override_configpath);
|
|
||||||
|
|
||||||
conn = xcb_connect(NULL, &screens);
|
conn = xcb_connect(NULL, &screens);
|
||||||
|
|
||||||
|
load_configuration(conn, override_configpath);
|
||||||
|
|
||||||
/* Place requests for the atoms we need as soon as possible */
|
/* Place requests for the atoms we need as soon as possible */
|
||||||
#define REQUEST_ATOM(name) atom_cookies[name] = xcb_intern_atom(conn, 0, strlen(#name), #name);
|
#define REQUEST_ATOM(name) atom_cookies[name] = xcb_intern_atom(conn, 0, strlen(#name), #name);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue