]> git.lizzy.rs Git - bspwm.git/blobdiff - tree.c
Add tiled move/resize pointer actions
[bspwm.git] / tree.c
diff --git a/tree.c b/tree.c
index 979284706ccd7ce51c0a8331a7bbb28ee041f93e..6df52c832e068a2799b62b61a535b48cd09885bb 100644 (file)
--- a/tree.c
+++ b/tree.c
@@ -140,6 +140,40 @@ void move_fence(node_t *n, direction_t dir, fence_move_t mov)
         change_split_ratio(fence, CHANGE_DECREASE);
 }
 
+unsigned int distance_to_fence(xcb_point_t pt, node_t *fence)
+{
+    xcb_rectangle_t rect = fence->rectangle;
+    if (fence->split_type == TYPE_VERTICAL) {
+        int fx = rect.x + fence->split_ratio * rect.width - window_gap / 2;
+        return ABS(pt.x - fx);
+    } else {
+        int fy = rect.y + fence->split_ratio * rect.height - window_gap / 2;
+        return ABS(pt.y - fy);
+    }
+}
+
+fence_distance_t nearest_fence(xcb_point_t pt, node_t *tree)
+{
+    fence_distance_t fd;
+    if (tree == NULL || is_leaf(tree)) {
+        fd.fence = NULL;
+    } else {
+        fd.fence = tree;
+        fd.distance = distance_to_fence(pt, tree);
+        fence_distance_t first_fd = nearest_fence(pt, tree->first_child);
+        fence_distance_t second_fd = nearest_fence(pt, tree->second_child);
+        if (first_fd.fence != NULL && fd.distance > first_fd.distance) {
+            fd.fence = first_fd.fence;
+            fd.distance = first_fd.distance;
+        }
+        if (second_fd.fence != NULL && fd.distance > second_fd.distance) {
+            fd.fence = second_fd.fence;
+            fd.distance = second_fd.distance;
+        }
+    }
+    return fd;
+}
+
 void rotate_tree(node_t *n, rotate_t rot)
 {
     if (n == NULL || is_leaf(n))
@@ -178,6 +212,8 @@ void arrange(monitor_t *m, desktop_t *d)
     rect.y += m->top_padding + wg;
     rect.width -= m->left_padding + m->right_padding + wg;
     rect.height -= m->top_padding + m->bottom_padding + wg;
+    if (focus_follows_pointer)
+        save_pointer_position(&last_pointer_position);
     apply_layout(m, d, d->root, rect, rect);
 }
 
@@ -368,14 +404,17 @@ void focus_node(monitor_t *m, desktop_t *d, node_t *n, bool is_mapped)
         xcb_set_input_focus(dpy, XCB_INPUT_FOCUS_POINTER_ROOT, n->client->window, XCB_CURRENT_TIME);
     }
 
-    if (n != mon->desk->focus && focus_follows_pointer) {
-        if (last_pointed != XCB_NONE) {
-            uint32_t values[] = {CLIENT_EVENT_MASK_FFP};
-            xcb_change_window_attributes(dpy, last_pointed, XCB_CW_EVENT_MASK, values);
+    if (focus_follows_pointer) {
+        save_pointer_position(&last_pointer_position);
+        if (n != mon->desk->focus) {
+            if (last_focused_window != XCB_NONE) {
+                uint32_t values[] = {CLIENT_EVENT_MASK_FFP};
+                xcb_change_window_attributes(dpy, last_focused_window, XCB_CW_EVENT_MASK, values);
+            }
+            uint32_t values[] = {CLIENT_EVENT_MASK};
+            xcb_change_window_attributes(dpy, n->client->window, XCB_CW_EVENT_MASK, values);
+            last_focused_window = n->client->window;
         }
-        uint32_t values[] = {CLIENT_EVENT_MASK};
-        xcb_change_window_attributes(dpy, n->client->window, XCB_CW_EVENT_MASK, values);
-        last_pointed = n->client->window;
     }
 
     if (!is_tiled(n->client)) {