diff --git a/include/types.h b/include/types.h index 5f96eec..99eb14b 100644 --- a/include/types.h +++ b/include/types.h @@ -22,7 +22,7 @@ #define ABSINTHE_CURSOR_MOVE_BUTTON BTN_LEFT #define ABSINTHE_CURSOR_RESIZE_BUTTON BTN_RIGHT -#define ABSINTHE_BORDER_WIDTH 2 +#define ABSINTHE_BORDER_WIDTH 1 static const float bordercolor[4] = {0.88, 0.18, 0.18, 1.0}; @@ -69,7 +69,6 @@ struct absinthe_server { struct wl_listener pointer_focus_change; struct wl_listener request_set_selection; struct wl_list keyboards; - uint32_t last_pointer_motion_time_msec; enum absinthe_cursor_mode cursor_mode; struct absinthe_toplevel *grabbed_toplevel; struct wlr_box grabbed_geometry; @@ -98,6 +97,7 @@ struct absinthe_toplevel { struct wl_list link; struct absinthe_server *server; struct wlr_scene_tree *scene_tree; + struct wlr_scene_tree *scene_surface; struct wlr_scene_rect *border[4]; struct wlr_box geometry; struct wlr_xdg_toplevel *xdg_toplevel; diff --git a/src/absinthe-toplevel.c b/src/absinthe-toplevel.c index dc4deaf..471fc10 100644 --- a/src/absinthe-toplevel.c +++ b/src/absinthe-toplevel.c @@ -1,6 +1,7 @@ #include #include "types.h" +#include "xdg-toplevel.h" struct absinthe_toplevel *absinthe_toplevel_at(struct absinthe_server *server, double lx, double ly, struct wlr_surface **surface, double *sx, double *sy) { @@ -30,6 +31,10 @@ void absinthe_toplevel_set_position(struct absinthe_toplevel *toplevel, int32_t void absinthe_toplevel_set_size(struct absinthe_toplevel *toplevel, int32_t width, int32_t height) { + if (width < 0 || height < 0) { + return; + } + if (width == toplevel->xdg_toplevel->current.width && height == toplevel->xdg_toplevel->current.height) { return; } @@ -37,24 +42,31 @@ void absinthe_toplevel_set_size(struct absinthe_toplevel *toplevel, int32_t widt toplevel->geometry.width = width; toplevel->geometry.height = height; + int bw = ABSINTHE_BORDER_WIDTH; + wlr_xdg_toplevel_set_size(toplevel->xdg_toplevel, width, height); + wlr_xdg_surface_schedule_configure(toplevel->xdg_toplevel->base); } void absinthe_toplevel_update_border_geometry(struct absinthe_toplevel *toplevel) { int bw = ABSINTHE_BORDER_WIDTH; + if (toplevel->geometry.width - 2 * bw < 0 || toplevel->geometry.height - 2 * bw < 0) { + return; + } + + wlr_scene_node_set_position(&toplevel->scene_surface->node, bw, bw); + wlr_scene_rect_set_size(toplevel->border[0], toplevel->geometry.width - 2 * bw, bw); wlr_scene_rect_set_size(toplevel->border[1], toplevel->geometry.width - 2 * bw, bw); wlr_scene_rect_set_size(toplevel->border[2], bw, toplevel->geometry.height); wlr_scene_rect_set_size(toplevel->border[3], bw, toplevel->geometry.height); - wlr_scene_node_set_position(&toplevel->border[0]->node, 0, -bw); - wlr_scene_node_set_position(&toplevel->border[1]->node, 0, toplevel->geometry.height - 2 * bw); - wlr_scene_node_set_position(&toplevel->border[2]->node, -bw, -bw); - wlr_scene_node_set_position(&toplevel->border[3]->node, toplevel->geometry.width - 2 * bw, -bw); - - absinthe_toplevel_set_size(toplevel, toplevel->geometry.width - 2 * bw, toplevel->geometry.height - 2 * bw); + wlr_scene_node_set_position(&toplevel->border[0]->node, bw, 0); + wlr_scene_node_set_position(&toplevel->border[1]->node, bw, toplevel->geometry.height - bw); + wlr_scene_node_set_position(&toplevel->border[2]->node, 0, 0); + wlr_scene_node_set_position(&toplevel->border[3]->node, toplevel->geometry.width - bw, 0); } void absinthe_toplevel_set_border_color(struct absinthe_toplevel *toplevel, const float color[4]) diff --git a/src/cursor.c b/src/cursor.c index 21acc89..6b4c94d 100644 --- a/src/cursor.c +++ b/src/cursor.c @@ -58,10 +58,10 @@ static void process_cursor_resize(struct absinthe_server *server) { } if (new_width > 0 && new_height > 0) { - wlr_scene_node_set_position(&toplevel->scene_tree->node, new_x, new_y); - absinthe_toplevel_set_size(toplevel, new_width, new_height); + toplevel->geometry.x = new_x; + toplevel->geometry.y = new_y; - absinthe_toplevel_update_border_geometry(toplevel); + absinthe_toplevel_set_size(toplevel, new_width, new_height); } } diff --git a/src/main.c b/src/main.c index d0a605c..8d01226 100644 --- a/src/main.c +++ b/src/main.c @@ -98,7 +98,6 @@ int main(int argc, char **argv) server.cursor_mgr = wlr_xcursor_manager_create(NULL, 24); - server.last_pointer_motion_time_msec = 0; server.cursor_mode = ABSINTHE_CURSOR_PASSTHROUGH; server.cursor_motion.notify = server_cursor_motion; wl_signal_add(&server.cursor->events.motion, &server.cursor_motion); diff --git a/src/server.c b/src/server.c index afc5615..9551a39 100644 --- a/src/server.c +++ b/src/server.c @@ -58,8 +58,9 @@ void server_new_xdg_toplevel(struct wl_listener *listener, void *data) struct absinthe_toplevel *toplevel = calloc(1, sizeof(*toplevel)); toplevel->server = server; toplevel->xdg_toplevel = xdg_toplevel; - toplevel->scene_tree = wlr_scene_xdg_surface_create(&toplevel->server->scene->tree, xdg_toplevel->base); + toplevel->scene_tree = wlr_scene_tree_create(&toplevel->server->scene->tree); toplevel->scene_tree->node.data = toplevel; + toplevel->scene_surface = wlr_scene_xdg_surface_create(toplevel->scene_tree, xdg_toplevel->base); toplevel->geometry.x = 0; toplevel->geometry.y = 0; toplevel->geometry.width = 100; @@ -124,22 +125,16 @@ void server_cursor_motion(struct wl_listener *listener, void *data) { struct absinthe_server *server = wl_container_of(listener, server, cursor_motion); struct wlr_pointer_motion_event *event = data; - if (event->time_msec - server->last_pointer_motion_time_msec > 5) { - wlr_cursor_move(server->cursor, &event->pointer->base, event->delta_x, event->delta_y); - process_cursor_motion(server, event->time_msec); - server->last_pointer_motion_time_msec = event->time_msec; - } + wlr_cursor_move(server->cursor, &event->pointer->base, event->delta_x, event->delta_y); + process_cursor_motion(server, event->time_msec); } void server_cursor_motion_absolute(struct wl_listener *listener, void *data) { struct absinthe_server *server = wl_container_of(listener, server, cursor_motion_absolute); struct wlr_pointer_motion_absolute_event *event = data; - if (event->time_msec - server->last_pointer_motion_time_msec > 5) { - wlr_cursor_warp_absolute(server->cursor, &event->pointer->base, event->x, event->y); - process_cursor_motion(server, event->time_msec); - server->last_pointer_motion_time_msec = event->time_msec; - } + wlr_cursor_warp_absolute(server->cursor, &event->pointer->base, event->x, event->y); + process_cursor_motion(server, event->time_msec); } void server_cursor_button(struct wl_listener *listener, void *data) diff --git a/src/xdg-decoration.c b/src/xdg-decoration.c index eb59fe1..577ead6 100644 --- a/src/xdg-decoration.c +++ b/src/xdg-decoration.c @@ -14,6 +14,10 @@ void xdg_decoration_destroy(struct wl_listener *listener, void *data) { struct absinthe_toplevel *toplevel = wl_container_of(listener, toplevel, decoration_destroy); + for (int i = 0; i < 4; ++i) { + wlr_scene_node_destroy(&toplevel->border[i]->node); + } + wl_list_remove(&toplevel->decoration_request_mode.link); wl_list_remove(&toplevel->decoration_destroy.link); } diff --git a/src/xdg-toplevel.c b/src/xdg-toplevel.c index 7dd04d3..be7a1ec 100644 --- a/src/xdg-toplevel.c +++ b/src/xdg-toplevel.c @@ -11,11 +11,16 @@ void xdg_toplevel_commit(struct wl_listener *listener, void *data) struct absinthe_toplevel *toplevel = wl_container_of(listener, toplevel, commit); if (toplevel->xdg_toplevel->base->initial_commit) { - wlr_xdg_toplevel_set_size(toplevel->xdg_toplevel, 0, 0); + int bw = ABSINTHE_BORDER_WIDTH; + + wlr_xdg_toplevel_set_size(toplevel->xdg_toplevel, toplevel->geometry.width - 2 * bw, toplevel->geometry.height - 2 * bw); if (toplevel->decoration) { xdg_decoration_request_mode(&toplevel->decoration_request_mode, toplevel->decoration); } + } else { + absinthe_toplevel_update_border_geometry(toplevel); + absinthe_toplevel_set_position(toplevel, toplevel->geometry.x, toplevel->geometry.y); } } @@ -32,7 +37,6 @@ void xdg_toplevel_map(struct wl_listener *listener, void *data) absinthe_toplevel_set_border_color(toplevel, bordercolor); - wl_list_insert(&toplevel->server->toplevels, &toplevel->link); } @@ -59,8 +63,21 @@ void xdg_toplevel_destroy(struct wl_listener *listener, void *data) free(toplevel); } -void xdg_toplevel_request_move(struct wl_listener *listener, void *data) {} -void xdg_toplevel_request_resize(struct wl_listener *listener, void *data) {} +void xdg_toplevel_request_move(struct wl_listener *listener, void *data) +{ + struct absinthe_toplevel *toplevel = wl_container_of(listener, toplevel, request_maximize); + if (toplevel->xdg_toplevel->base->initialized) { + wlr_xdg_surface_schedule_configure(toplevel->xdg_toplevel->base); + } +} + +void xdg_toplevel_request_resize(struct wl_listener *listener, void *data) +{ + struct absinthe_toplevel *toplevel = wl_container_of(listener, toplevel, request_maximize); + if (toplevel->xdg_toplevel->base->initialized) { + wlr_xdg_surface_schedule_configure(toplevel->xdg_toplevel->base); + } +} void xdg_toplevel_request_maximize(struct wl_listener *listener, void *data) {