From 74016d7d3349d8600933a1e88b62caab12fc1009 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20Ekl=C3=B6f?= Date: Mon, 2 Aug 2021 19:29:52 +0200 Subject: [PATCH 1/3] =?UTF-8?q?bar:=20add=20bar->output=5Fname(),=20return?= =?UTF-8?q?s=20the=20name=20of=20the=20output=20we=E2=80=99re=20on?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bar/backend.h | 1 + bar/bar.c | 8 ++++++++ bar/bar.h | 2 ++ bar/wayland.c | 10 ++++++++++ bar/xcb.c | 8 ++++++++ 5 files changed, 29 insertions(+) diff --git a/bar/backend.h b/bar/backend.h index d365da6..47fae95 100644 --- a/bar/backend.h +++ b/bar/backend.h @@ -14,4 +14,5 @@ struct backend { void (*commit)(const struct bar *bar); void (*refresh)(const struct bar *bar); void (*set_cursor)(struct bar *bar, const char *cursor); + const char *(*output_name)(const struct bar *bar); }; diff --git a/bar/bar.c b/bar/bar.c index c7b1ea5..9d1b0cc 100644 --- a/bar/bar.c +++ b/bar/bar.c @@ -162,6 +162,13 @@ set_cursor(struct bar *bar, const char *cursor) b->backend.iface->set_cursor(bar, cursor); } +static const char * +output_name(const struct bar *bar) +{ + const struct private *b = bar->private; + return b->backend.iface->output_name(bar); +} + static void on_mouse(struct bar *_bar, enum mouse_event event, enum mouse_button btn, int x, int y) @@ -456,6 +463,7 @@ bar_new(const struct bar_config *config) bar->destroy = &destroy; bar->refresh = &refresh; bar->set_cursor = &set_cursor; + bar->output_name = &output_name; for (size_t i = 0; i < priv->left.count; i++) priv->left.mods[i]->bar = bar; diff --git a/bar/bar.h b/bar/bar.h index 5d154dd..45fb328 100644 --- a/bar/bar.h +++ b/bar/bar.h @@ -12,6 +12,8 @@ struct bar { void (*refresh)(const struct bar *bar); void (*set_cursor)(struct bar *bar, const char *cursor); + + const char *(*output_name)(const struct bar *bar); }; enum bar_location { BAR_TOP, BAR_BOTTOM }; diff --git a/bar/wayland.c b/bar/wayland.c index ef62025..cb10eae 100644 --- a/bar/wayland.c +++ b/bar/wayland.c @@ -1308,6 +1308,15 @@ set_cursor(struct bar *_bar, const char *cursor) update_cursor_surface(backend, seat); } +static const char * +output_name(const struct bar *_bar) +{ + const struct private *bar = _bar->private; + const struct wayland_backend *backend = bar->backend.data; + + return backend->monitor != NULL ? backend->monitor->name : NULL; +} + const struct backend wayland_backend_iface = { .setup = &setup, .cleanup = &cleanup, @@ -1315,4 +1324,5 @@ const struct backend wayland_backend_iface = { .commit = &commit, .refresh = &refresh, .set_cursor = &set_cursor, + .output_name = &output_name, }; diff --git a/bar/xcb.c b/bar/xcb.c index 9c452da..4b0e7c1 100644 --- a/bar/xcb.c +++ b/bar/xcb.c @@ -462,6 +462,13 @@ set_cursor(struct bar *_bar, const char *cursor) backend->conn, backend->win, XCB_CW_CURSOR, &backend->cursor); } +static const char * +output_name(const struct bar *_bar) +{ + /* Not implemented */ + return NULL; +} + const struct backend xcb_backend_iface = { .setup = &setup, .cleanup = &cleanup, @@ -469,4 +476,5 @@ const struct backend xcb_backend_iface = { .commit = &commit, .refresh = &refresh, .set_cursor = &set_cursor, + .output_name = &output_name, }; From 1c6c73928b841efa9c043045a6feee4d3cfe0955 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20Ekl=C3=B6f?= Date: Mon, 2 Aug 2021 19:30:22 +0200 Subject: [PATCH 2/3] config-verify: add conf_verify_bool() --- config-verify.c | 11 +++++++++++ config-verify.h | 1 + 2 files changed, 12 insertions(+) diff --git a/config-verify.c b/config-verify.c index 7c4f365..5d4089a 100644 --- a/config-verify.c +++ b/config-verify.c @@ -50,6 +50,17 @@ conf_verify_int(keychain_t *chain, const struct yml_node *node) return false; } +bool +conf_verify_bool(keychain_t *chain, const struct yml_node *node) +{ + if (yml_value_is_bool(node)) + return true; + + LOG_ERR("%s: value is not a boolean: '%s'", + conf_err_prefix(chain, node), yml_value_as_string(node)); + return false; +} + bool conf_verify_list(keychain_t *chain, const struct yml_node *node, bool (*verify)(keychain_t *chain, const struct yml_node *node)) diff --git a/config-verify.h b/config-verify.h index dccaf5f..5afe3f6 100644 --- a/config-verify.h +++ b/config-verify.h @@ -32,6 +32,7 @@ const char *conf_err_prefix( bool conf_verify_string(keychain_t *chain, const struct yml_node *node); bool conf_verify_int(keychain_t *chain, const struct yml_node *node); +bool conf_verify_bool(keychain_t *chain, const struct yml_node *node); bool conf_verify_enum(keychain_t *chain, const struct yml_node *node, const char *values[], size_t count); From ba7b9e6244d5f28ffc6220190fec2c7b5548234b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20Ekl=C3=B6f?= Date: Mon, 2 Aug 2021 19:31:01 +0200 Subject: [PATCH 3/3] =?UTF-8?q?module/river:=20add=20=E2=80=98per-output?= =?UTF-8?q?=E2=80=99=20attribute?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit When set, river tags and seats’ view titles apply to the output yambar is on, only. The default is disabled, which implements the old behavior, where river tags and seats’ view titles represent the union of all outputs. --- CHANGELOG.md | 1 + doc/yambar-modules-river.5.scd | 14 +++++++++---- modules/river.c | 38 +++++++++++++++++++++++++++------- 3 files changed, 41 insertions(+), 12 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 9475062..6d27aea 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -17,6 +17,7 @@ individually. `border.width` is now a short-hand for setting all four borders to the same value (https://codeberg.org/dnkl/yambar/issues/77). +* river: `per-output: false|true`. ### Changed diff --git a/doc/yambar-modules-river.5.scd b/doc/yambar-modules-river.5.scd index 46607a2..570e8a5 100644 --- a/doc/yambar-modules-river.5.scd +++ b/doc/yambar-modules-river.5.scd @@ -12,8 +12,8 @@ about the river tags. It has an interface similar to the i3/sway module. The configuration for the river module specifies one _title_ particle, -which will be instantiated with tags representing the currently active -seat and the currently focused view's title. +which will be instantiated once for each seat, with tags representing +the seats' name and the title of the seats' currently focused view. It also specifies a _content_ template particle, which is instantiated once for all 32 river tags. This means you probably want to use a @@ -41,10 +41,10 @@ once for all 32 river tags. This means you probably want to use a : Set to *focused* if _focused_ is true, *unfocused* if _visible_ is true, but _focused_ is false, or *invisible* if the river tag is not visible on any monitors. | seat : string -: The name of the currently active seat (*title* particle only, see CONFIGURATION) +: The name of the seat (*title* particle only, see CONFIGURATION) | title : string -: The focused view's title (*title* particle only, see CONFIGURATION) +: The seat's focused view's title (*title* particle only, see CONFIGURATION) # CONFIGURATION @@ -60,6 +60,12 @@ once for all 32 river tags. This means you probably want to use a : particle : yes : Template particle that will be instantiated once for all of the 32 river tags. +| per-output +: bool +: no +: When set to false (the default), tags reflect the union of all + outputs. When set to true, tags reflect river tags and seats for + the output yambar is on only. # EXAMPLES diff --git a/modules/river.c b/modules/river.c index 0cdab38..9b494f3 100644 --- a/modules/river.c +++ b/modules/river.c @@ -48,6 +48,7 @@ struct private { struct zriver_status_manager_v1 *status_manager; struct particle *template; struct particle *title; + bool per_output; bool is_starting_up; tll(struct output) outputs; @@ -76,6 +77,8 @@ content(struct module *mod) { const struct private *m = mod->private; + const char *output_bar_is_on = mod->bar->output_name(mod->bar); + mtx_lock(&m->mod->lock); uint32_t output_focused = 0; @@ -85,6 +88,13 @@ content(struct module *mod) tll_foreach(m->outputs, it) { const struct output *output = &it->item; + if (m->per_output && + output_bar_is_on != NULL && output->name != NULL && + strcmp(output->name, output_bar_is_on) != 0) + { + continue; + } + output_focused |= output->focused; occupied |= output->occupied; @@ -348,7 +358,6 @@ unfocused_output(void *data, struct zriver_seat_status_v1 *zriver_seat_status_v1 mtx_lock(&mod->lock); { - struct output *output = NULL; tll_foreach(m->outputs, it) { if (it->item.wl_output == wl_output) { @@ -382,13 +391,21 @@ focused_view(void *data, struct zriver_seat_status_v1 *zriver_seat_status_v1, LOG_DBG("seat: %s: focused view: %s", seat->name, title); - mtx_lock(&mod->lock); + const char *output_bar_is_on = mod->bar->output_name(mod->bar); + + if (!seat->m->per_output || + (output_bar_is_on != NULL && + seat->output != NULL && seat->output->name != NULL && + strcmp(output_bar_is_on, seat->output->name) == 0)) { - free(seat->title); - seat->title = title != NULL ? strdup(title) : NULL; + mtx_lock(&mod->lock); + { + free(seat->title); + seat->title = title != NULL ? strdup(title) : NULL; + } + mtx_unlock(&mod->lock); + mod->bar->refresh(mod->bar); } - mtx_unlock(&mod->lock); - mod->bar->refresh(mod->bar); } static const struct zriver_seat_status_v1_listener river_seat_status_listener = { @@ -646,11 +663,12 @@ out: } static struct module * -river_new(struct particle *template, struct particle *title) +river_new(struct particle *template, struct particle *title, bool per_output) { struct private *m = calloc(1, sizeof(*m)); m->template = template; m->title = title; + m->per_output = per_output; m->is_starting_up = true; struct module *mod = module_common_new(); @@ -668,9 +686,12 @@ from_conf(const struct yml_node *node, struct conf_inherit inherited) { const struct yml_node *c = yml_get_value(node, "content"); const struct yml_node *title = yml_get_value(node, "title"); + const struct yml_node *per_output = yml_get_value(node, "per-output"); + return river_new( conf_to_particle(c, inherited), - title != NULL ? conf_to_particle(title, inherited) : NULL); + title != NULL ? conf_to_particle(title, inherited) : NULL, + per_output != NULL ? yml_value_as_bool(per_output) : false); } static bool @@ -678,6 +699,7 @@ verify_conf(keychain_t *chain, const struct yml_node *node) { static const struct attr_info attrs[] = { {"title", false, &conf_verify_particle}, + {"per-output", false, &conf_verify_bool}, MODULE_COMMON_ATTRS, };