aboutsummaryrefslogtreecommitdiff
path: root/swaybar
diff options
context:
space:
mode:
authorScott Anderson <scott@anderso.nz>2018-04-22 17:13:52 +1200
committerScott Anderson <scott@anderso.nz>2018-04-22 17:25:15 +1200
commit4dfbc3160c937b4fcee2b27d78d7e46a48cd68e9 (patch)
treeb4444f49bb92cc257d529dae692958873c9736b0 /swaybar
parent72149111a5743febf4c538220478eb0f1d696ed0 (diff)
Fix swaybar axis event logic
Uses 'visible' instead of 'focused', since we may scroll on a bar which isn't the focused output. We can't use "next_on_output" or "prev_on_output" to implement this, because it only modify the focused output. So scrolling on an unfocused output will affect the incorrect one. We just use the "workspace name" command instead.
Diffstat (limited to 'swaybar')
-rw-r--r--swaybar/bar.c61
1 files changed, 43 insertions, 18 deletions
diff --git a/swaybar/bar.c b/swaybar/bar.c
index 669cb11a..d407db4f 100644
--- a/swaybar/bar.c
+++ b/swaybar/bar.c
@@ -156,31 +156,56 @@ static void wl_pointer_axis(void *data, struct wl_pointer *wl_pointer,
if (!sway_assert(output, "axis with no active output")) {
return;
}
+
double amt = wl_fixed_to_double(value);
- if (!bar->config->wrap_scroll) {
- int i = 0;
- struct swaybar_workspace *ws = NULL;
- wl_list_for_each(ws, &output->workspaces, link) {
- if (ws->focused) {
- break;
- }
- ++i;
+ if (amt == 0.0) {
+ return;
+ }
+
+ struct swaybar_workspace *first = NULL;
+ struct swaybar_workspace *active = NULL;
+ struct swaybar_workspace *last;
+
+ struct swaybar_workspace *iter;
+ wl_list_for_each(iter, &output->workspaces, link) {
+ if (!first) {
+ first = iter;
}
- int len = wl_list_length(&output->workspaces);
- if (!sway_assert(i != len, "axis with null workspace")) {
- return;
+
+ if (iter->visible) {
+ active = iter;
}
- if (i == 0 && amt > 0) {
- return; // Do not wrap
+
+ last = iter;
+ }
+
+ if (!sway_assert(active, "axis with null workspace")) {
+ return;
+ }
+
+ struct swaybar_workspace *new;
+
+ if (amt > 0.0) {
+ if (active == first) {
+ if (!bar->config->wrap_scroll) {
+ return;
+ }
+ new = last;
}
- if (i == len - 1 && amt < 0) {
- return; // Do not wrap
+
+ new = wl_container_of(active->link.prev, new, link);
+ } else {
+ if (active == last) {
+ if (!bar->config->wrap_scroll) {
+ return;
+ }
+ new = first;
}
+
+ new = wl_container_of(active->link.next, new, link);
}
- const char *workspace_name =
- amt < 0 ? "prev_on_output" : "next_on_output";
- ipc_send_workspace_command(bar, workspace_name);
+ ipc_send_workspace_command(bar, new->name);
}
static void wl_pointer_frame(void *data, struct wl_pointer *wl_pointer) {