aboutsummaryrefslogtreecommitdiff
path: root/sway
diff options
context:
space:
mode:
authorDrew DeVault <sir@cmpwn.com>2015-08-09 09:23:10 -0400
committerDrew DeVault <sir@cmpwn.com>2015-08-09 09:23:10 -0400
commitf97a48d5b75fd80a578af14f19d0b1d954f82fdd (patch)
treec99dcdd46754915d18445281d2778ea61be05f3b /sway
parent086691016e7cbe9794b73c174eaefa77e2d56498 (diff)
Implement focus_follows_mouse
Diffstat (limited to 'sway')
-rw-r--r--sway/commands.c60
-rw-r--r--sway/config.c11
-rw-r--r--sway/config.h4
-rw-r--r--sway/handlers.c40
-rw-r--r--sway/handlers.h4
-rw-r--r--sway/layout.c19
-rw-r--r--sway/layout.h2
-rw-r--r--sway/main.c4
8 files changed, 118 insertions, 26 deletions
diff --git a/sway/commands.c b/sway/commands.c
index 6e2a79f6..8e6d19ec 100644
--- a/sway/commands.c
+++ b/sway/commands.c
@@ -9,30 +9,6 @@
#include "log.h"
#include "commands.h"
-int cmd_set(struct sway_config *config, int argc, char **argv) {
- if (argc != 2) {
- sway_log(L_ERROR, "Invalid set command (expected 2 arguments, got %d)", argc);
- return 1;
- }
- struct sway_variable *var = malloc(sizeof(struct sway_variable));
- var->name = malloc(strlen(argv[0]) + 1);
- strcpy(var->name, argv[0]);
- var->value = malloc(strlen(argv[1]) + 1);
- strcpy(var->value, argv[1]);
- list_add(config->symbols, var);
- return 0;
-}
-
-int cmd_exit(struct sway_config *config, int argc, char **argv) {
- if (argc != 0) {
- sway_log(L_ERROR, "Invalid exit command (expected 1 arguments, got %d)", argc);
- return 1;
- }
- // TODO: Some kind of clean up is probably in order
- exit(0);
- return 0;
-}
-
struct modifier_key {
char *name;
uint32_t mod;
@@ -94,10 +70,46 @@ int cmd_bindsym(struct sway_config *config, int argc, char **argv) {
return 0;
}
+int cmd_exit(struct sway_config *config, int argc, char **argv) {
+ if (argc != 0) {
+ sway_log(L_ERROR, "Invalid exit command (expected 1 arguments, got %d)", argc);
+ return 1;
+ }
+ // TODO: Some kind of clean up is probably in order
+ exit(0);
+ return 0;
+}
+
+
+int cmd_focus_follows_mouse(struct sway_config *config, int argc, char **argv) {
+ if (argc != 1) {
+ sway_log(L_ERROR, "Invalid focus_follows_mouse command (expected 1 arguments, got %d)", argc);
+ return 1;
+ }
+
+ config->focus_follows_mouse = !strcasecmp(argv[0], "yes");
+ return 0;
+}
+
+int cmd_set(struct sway_config *config, int argc, char **argv) {
+ if (argc != 2) {
+ sway_log(L_ERROR, "Invalid set command (expected 2 arguments, got %d)", argc);
+ return 1;
+ }
+ struct sway_variable *var = malloc(sizeof(struct sway_variable));
+ var->name = malloc(strlen(argv[0]) + 1);
+ strcpy(var->name, argv[0]);
+ var->value = malloc(strlen(argv[1]) + 1);
+ strcpy(var->value, argv[1]);
+ list_add(config->symbols, var);
+ return 0;
+}
+
/* Keep alphabetized */
struct cmd_handler handlers[] = {
{ "bindsym", cmd_bindsym },
{ "exit", cmd_exit },
+ { "focus_follows_mouse", cmd_focus_follows_mouse },
{ "set", cmd_set },
};
diff --git a/sway/config.c b/sway/config.c
index 7c610755..26dc88cb 100644
--- a/sway/config.c
+++ b/sway/config.c
@@ -8,14 +8,21 @@
#include "commands.h"
#include "config.h"
-struct sway_config *read_config(FILE *file) {
- struct sway_config *config = malloc(sizeof(struct sway_config));
+void config_defaults(struct sway_config *config) {
config->symbols = create_list();
config->modes = create_list();
config->current_mode = malloc(sizeof(struct sway_mode));
config->current_mode->name = NULL;
config->current_mode->bindings = create_list();
list_add(config->modes, config->current_mode);
+ // Flags
+ config->focus_follows_mouse = true;
+ config->mouse_warping = true;
+}
+
+struct sway_config *read_config(FILE *file) {
+ struct sway_config *config = malloc(sizeof(struct sway_config));
+ config_defaults(config);
bool success = true;
diff --git a/sway/config.h b/sway/config.h
index 88225800..6802a341 100644
--- a/sway/config.h
+++ b/sway/config.h
@@ -25,6 +25,10 @@ struct sway_config {
list_t *symbols;
list_t *modes;
struct sway_mode *current_mode;
+
+ // Flags
+ bool focus_follows_mouse;
+ bool mouse_warping;
};
struct sway_config *read_config(FILE *file);
diff --git a/sway/handlers.c b/sway/handlers.c
index f1098835..0c0fb85f 100644
--- a/sway/handlers.c
+++ b/sway/handlers.c
@@ -83,3 +83,43 @@ bool handle_key(wlc_handle view, uint32_t time, const struct wlc_modifiers
}
return ret;
}
+
+bool pointer_test(swayc_t *view, void *_origin) {
+ const struct wlc_origin *origin = _origin;
+ if (view->type == C_VIEW && origin->x >= view->x && origin->y >= view->y
+ && origin->x < view->x + view->width && origin->y < view->y + view->height) {
+ return true;
+ }
+ return false;
+}
+
+struct wlc_origin mouse_origin;
+
+bool handle_pointer_motion(wlc_handle view, uint32_t time, const struct wlc_origin *origin) {
+ mouse_origin = *origin;
+ if (!config->focus_follows_mouse) {
+ return true;
+ }
+ swayc_t *c = find_container(&root_container, pointer_test, (void *)origin);
+ swayc_t *focused = get_focused_container(&root_container);
+ if (c && c != focused) {
+ sway_log(L_DEBUG, "Switching focus to %p", c);
+ focus_view(c);
+ }
+ return true;
+}
+
+bool handle_pointer_button(wlc_handle view, uint32_t time, const struct wlc_modifiers *modifiers,
+ uint32_t button, enum wlc_button_state state) {
+ if (state == WLC_BUTTON_STATE_PRESSED) {
+ swayc_t *c = find_container(&root_container, pointer_test, &mouse_origin);
+ swayc_t *focused = get_focused_container(&root_container);
+ if (c && c != focused) {
+ sway_log(L_DEBUG, "Switching focus to %p", c);
+ focus_view(c);
+ return false;
+ }
+ return true;
+ }
+ return true;
+}
diff --git a/sway/handlers.h b/sway/handlers.h
index d0cc67c8..331be725 100644
--- a/sway/handlers.h
+++ b/sway/handlers.h
@@ -16,4 +16,8 @@ void handle_view_geometry_request(wlc_handle view, const struct wlc_geometry* ge
bool handle_key(wlc_handle view, uint32_t time, const struct wlc_modifiers
*modifiers, uint32_t key, uint32_t sym, enum wlc_key_state state);
+bool handle_pointer_motion(wlc_handle view, uint32_t time, const struct wlc_origin *origin);
+bool handle_pointer_button(wlc_handle view, uint32_t time, const struct wlc_modifiers *modifiers,
+ uint32_t button, enum wlc_button_state state);
+
#endif
diff --git a/sway/layout.c b/sway/layout.c
index 2a57ccce..996be387 100644
--- a/sway/layout.c
+++ b/sway/layout.c
@@ -7,6 +7,25 @@
swayc_t root_container;
+swayc_t *find_container(swayc_t *container, bool (*test)(swayc_t *view, void *data), void *data) {
+ if (!container->children) {
+ return NULL;
+ }
+ int i;
+ for (i = 0; i < container->children->length; ++i) {
+ swayc_t *child = container->children->items[i];
+ if (test(child, data)) {
+ return child;
+ } else {
+ swayc_t *_ = find_container(child, test, data);
+ if (_) {
+ return _;
+ }
+ }
+ }
+ return NULL;
+}
+
void arrange_windows(swayc_t *container, int width, int height) {
int i;
if (width == -1 || height == -1) {
diff --git a/sway/layout.h b/sway/layout.h
index 801faf90..0e34cb5c 100644
--- a/sway/layout.h
+++ b/sway/layout.h
@@ -51,6 +51,8 @@ void destroy_view(swayc_t *view);
void add_view(wlc_handle view);
void focus_view(swayc_t *view);
void arrange_windows(swayc_t *container, int width, int height);
+swayc_t *find_container(swayc_t *container, bool (*test)(swayc_t *view, void *data), void *data);
+swayc_t *get_focused_container(swayc_t *parent);
swayc_t *get_swayc_for_handle(wlc_handle handle, swayc_t *parent);
diff --git a/sway/main.c b/sway/main.c
index e547ef4a..2f69506c 100644
--- a/sway/main.c
+++ b/sway/main.c
@@ -48,6 +48,10 @@ int main(int argc, char **argv) {
},
.keyboard = {
.key = handle_key
+ },
+ .pointer = {
+ .motion = handle_pointer_motion,
+ .button = handle_pointer_button
}
};