Fix cursor warp

This commit is contained in:
2023-09-18 23:25:36 +02:00
parent 47aac3a361
commit 52570d4b57
5 changed files with 15 additions and 232 deletions
@@ -1,16 +1,16 @@
diff --git a/dwl.c b/dwl.c
index 93f66ef..5562c0d 100644
index 0841bef..426ec14 100644
--- a/dwl.c
+++ b/dwl.c
@@ -314,6 +314,7 @@ static void updatetitle(struct wl_listener *listener, void *data);
@@ -322,6 +322,7 @@ static void updatetitle(struct wl_listener *listener, void *data);
static void urgent(struct wl_listener *listener, void *data);
static void view(const Arg *arg);
static void virtualkeyboard(struct wl_listener *listener, void *data);
+static void warpcursor(const Client *c);
static Monitor *xytomon(double x, double y);
static struct wlr_scene_node *xytonode(double x, double y, struct wlr_surface **psurface,
static void xytonode(double x, double y, struct wlr_surface **psurface,
Client **pc, LayerSurface **pl, double *nx, double *ny);
@@ -486,6 +487,9 @@ arrange(Monitor *m)
@@ -503,6 +504,9 @@ arrange(Monitor *m)
if (m->lt[m->sellt]->arrange)
m->lt[m->sellt]->arrange(m);
@@ -20,17 +20,18 @@ index 93f66ef..5562c0d 100644
motionnotify(0);
checkidleinhibitor(NULL);
}
@@ -1210,6 +1214,9 @@ focusclient(Client *c, int lift)
if (locked)
@@ -1304,6 +1308,10 @@ focusclient(Client *c, int lift)
if (c && client_surface(c) == old)
return;
+ /* Warp cursor to center of client if it is outside */
+ if (cursor_warp && c)
+ warpcursor(c);
/* Raise client in stacking order if requested */
if (c && lift)
@@ -2616,6 +2623,18 @@ virtualkeyboard(struct wl_listener *listener, void *data)
+
if ((old_client_type = toplevel_from_wlr_surface(old, &old_c, &old_l)) == XDGShell) {
struct wlr_xdg_popup *popup, *tmp;
wl_list_for_each_safe(popup, tmp, &old_c->surface.xdg->popups, link)
@@ -2736,6 +2744,18 @@ virtualkeyboard(struct wl_listener *listener, void *data)
createkeyboard(&keyboard->keyboard);
}
-215
View File
@@ -1,215 +0,0 @@
From 701cc94e7db68d7d943561be47f8a9d8663f30be Mon Sep 17 00:00:00 2001
From: Palanix <palanixyt@gmail.com>
Date: Sun, 3 Jul 2022 18:46:18 +0200
Subject: [PATCH] Fix pointerconstraints
---
Makefile | 5 +++-
config.def.h | 3 ++
dwl.c | 84 +++++++++++++++++++++++++++++++++++++++++++++++++++-
3 files changed, 90 insertions(+), 2 deletions(-)
diff --git a/Makefile b/Makefile
index ccca07948..ee1316146 100644
--- a/Makefile
+++ b/Makefile
@@ -16,7 +16,7 @@ LDLIBS = `$(PKG_CONFIG) --libs $(PKGS)` $(LIBS)
all: dwl
dwl: dwl.o util.o
$(CC) dwl.o util.o $(LDLIBS) $(LDFLAGS) $(DWLCFLAGS) -o $@
-dwl.o: dwl.c config.mk config.h client.h xdg-shell-protocol.h wlr-layer-shell-unstable-v1-protocol.h
+dwl.o: dwl.c config.mk config.h client.h xdg-shell-protocol.h wlr-layer-shell-unstable-v1-protocol.h pointer-constraints-unstable-v1-protocol.h
util.o: util.c util.h
# wayland-scanner is a tool which generates C headers and rigging for Wayland
@@ -28,6 +28,9 @@ WAYLAND_PROTOCOLS = `$(PKG_CONFIG) --variable=pkgdatadir wayland-protocols`
xdg-shell-protocol.h:
$(WAYLAND_SCANNER) server-header \
$(WAYLAND_PROTOCOLS)/stable/xdg-shell/xdg-shell.xml $@
+pointer-constraints-unstable-v1-protocol.h:
+ $(WAYLAND_SCANNER) server-header \
+ $(WAYLAND_PROTOCOLS)/unstable/pointer-constraints/pointer-constraints-unstable-v1.xml $@
wlr-layer-shell-unstable-v1-protocol.h:
$(WAYLAND_SCANNER) server-header \
protocols/wlr-layer-shell-unstable-v1.xml $@
diff --git a/dwl.c b/dwl.c
index 93f66efe6..d3b5cdac1 100644
--- a/dwl.c
+++ b/dwl.c
@@ -1,6 +1,7 @@
/*
* See LICENSE file for copyright and license details.
*/
+#include <assert.h>
#include <getopt.h>
#include <libinput.h>
#include <limits.h>
@@ -34,8 +35,10 @@
#include <wlr/types/wlr_output_management_v1.h>
#include <wlr/types/wlr_pointer.h>
#include <wlr/types/wlr_presentation_time.h>
+#include <wlr/types/wlr_pointer_constraints_v1.h>
#include <wlr/types/wlr_primary_selection.h>
#include <wlr/types/wlr_primary_selection_v1.h>
+#include <wlr/types/wlr_relative_pointer_v1.h>
#include <wlr/types/wlr_scene.h>
#include <wlr/types/wlr_screencopy_v1.h>
#include <wlr/types/wlr_seat.h>
@@ -203,6 +206,14 @@ typedef struct {
int x, y;
} MonitorRule;
+struct pointer_constraint {
+ struct wlr_pointer_constraint_v1 *constraint;
+
+ struct wl_listener set_region;
+ struct wl_listener destroy;
+};
+
+
typedef struct {
const char *id;
const char *title;
@@ -245,7 +256,8 @@ static void createlocksurface(struct wl_listener *listener, void *data);
static void createmon(struct wl_listener *listener, void *data);
static void createnotify(struct wl_listener *listener, void *data);
static void createpointer(struct wlr_pointer *pointer);
+static void createpointerconstraint(struct wl_listener *listener, void *data);
static void cursorframe(struct wl_listener *listener, void *data);
static void deck(Monitor *m);
static void destroydragicon(struct wl_listener *listener, void *data);
static void destroyidleinhibitor(struct wl_listener *listener, void *data);
@@ -254,12 +266,14 @@ static void destroylocksurface(struct wl_listener *listener, void *data);
static void destroynotify(struct wl_listener *listener, void *data);
static void destroysessionlock(struct wl_listener *listener, void *data);
static void destroysessionmgr(struct wl_listener *listener, void *data);
+static void destroypointerconstraint(struct wl_listener *listener, void *data);
static Monitor *dirtomon(enum wlr_direction dir);
static void focusclient(Client *c, int lift);
static void focusmon(const Arg *arg);
static void focusstack(const Arg *arg);
static Client *focustop(Monitor *m);
static void fullscreennotify(struct wl_listener *listener, void *data);
+static void handleconstraintcommit(struct wl_listener *listener, void *data);
static void handlesig(int signo);
static void incnmaster(const Arg *arg);
static void inputdevice(struct wl_listener *listener, void *data);
@@ -367,6 +381,11 @@ static struct wlr_box sgeom;
static struct wl_list mons;
static Monitor *selmon;
+struct wlr_pointer_constraints_v1 *pointer_constraints;
+struct wlr_pointer_constraint_v1 *active_constraint;
+static struct wl_listener constraint_commit;
+struct wlr_relative_pointer_manager_v1 *relative_pointer_manager;
+
/* global event handlers */
static struct wl_listener cursor_axis = {.notify = axisnotify};
static struct wl_listener cursor_button = {.notify = buttonpress};
@@ -382,6 +401,7 @@ static struct wl_listener new_virtual_keyboard = {.notify = virtualkeyboard};
static struct wl_listener new_output = {.notify = createmon};
static struct wl_listener new_xdg_surface = {.notify = createnotify};
static struct wl_listener new_xdg_decoration = {.notify = createdecoration};
+static struct wl_listener pointer_constraint_create = {.notify = createpointerconstraint};
static struct wl_listener new_layer_shell_surface = {.notify = createlayersurface};
static struct wl_listener output_mgr_apply = {.notify = outputmgrapply};
static struct wl_listener output_mgr_test = {.notify = outputmgrtest};
@@ -976,6 +996,30 @@ createmon(struct wl_listener *listener, void *data)
strncpy(m->ltsymbol, m->lt[m->sellt]->symbol, LENGTH(m->ltsymbol));
}
+void
+createpointerconstraint(struct wl_listener *listener, void *data)
+{
+ if (focustop(selmon)) {
+ struct wlr_pointer_constraint_v1 *constraint = data;
+ struct pointer_constraint *pointer_constraint = calloc(1, sizeof(struct pointer_constraint));
+ pointer_constraint->constraint = constraint;
+
+ pointer_constraint->destroy.notify = destroypointerconstraint;
+ wl_signal_add(&constraint->events.destroy, &pointer_constraint->destroy);
+
+ if (client_surface(focustop(selmon)) == constraint->surface) {
+ if (allow_constrain == 0 || active_constraint == constraint)
+ return;
+
+ active_constraint = constraint;
+ wlr_pointer_constraint_v1_send_activated(constraint);
+
+ constraint_commit.notify = handleconstraintcommit;
+ wl_signal_add(&constraint->surface->events.commit, &constraint_commit);
+ }
+ }
+}
+
void
createnotify(struct wl_listener *listener, void *data)
{
@@ -1064,6 +1108,25 @@ createpointer(struct wlr_pointer *pointer)
wlr_cursor_attach_input_device(cursor, &pointer->base);
}
+void
+destroypointerconstraint(struct wl_listener *listener, void *data)
+{
+ struct wlr_pointer_constraint_v1 *constraint = data;
+ struct pointer_constraint *pointer_constraint = wl_container_of(listener, pointer_constraint, destroy);
+
+ wl_list_remove(&pointer_constraint->destroy.link);
+
+ if (active_constraint == constraint) {
+ if (constraint_commit.link.next != NULL) {
+ wl_list_remove(&constraint_commit.link);
+ }
+ wl_list_init(&constraint_commit.link);
+ active_constraint = NULL;
+ }
+
+ free(pointer_constraint);
+}
+
void
cursorframe(struct wl_listener *listener, void *data)
{
@@ -1355,6 +1418,12 @@ handlesig(int signo)
}
}
+void
+handleconstraintcommit(struct wl_listener *listener, void *data)
+{
+ assert(active_constraint->surface == data);
+}
+
void
incnmaster(const Arg *arg)
{
@@ -1717,7 +1786,15 @@ motionrelative(struct wl_listener *listener, void *data)
* special configuration applied for the specific input device which
* generated the event. You can pass NULL for the device if you want to move
* the cursor around without any input. */
- wlr_cursor_move(cursor, &event->pointer->base, event->delta_x, event->delta_y);
+ wlr_relative_pointer_manager_v1_send_relative_motion(
+ relative_pointer_manager,
+ seat, (uint64_t)event->time_msec * 1000,
+ event->delta_x, event->delta_y, event->unaccel_dx, event->unaccel_dy);
+
+ if (!active_constraint) {
+ wlr_cursor_move(cursor, &event->pointer->base,
+ event->delta_x, event->delta_y);
+ }
motionnotify(event->time_msec);
}
@@ -2243,6 +2320,11 @@ setup(void)
xdg_decoration_mgr = wlr_xdg_decoration_manager_v1_create(dpy);
wl_signal_add(&xdg_decoration_mgr->events.new_toplevel_decoration, &new_xdg_decoration);
+ pointer_constraints = wlr_pointer_constraints_v1_create(dpy);
+ wl_signal_add(&pointer_constraints->events.new_constraint, &pointer_constraint_create);
+
+ relative_pointer_manager = wlr_relative_pointer_manager_v1_create(dpy);
+
/*
* Creates a cursor, which is a wlroots utility for tracking the cursor
* image shown on screen.
+1 -1
View File
@@ -37,7 +37,7 @@ export const Indicator = ({ ...props }) =>
rev._current = id;
const notif = Notifications.getNotification(id);
rev.child.label = `${notif.summary?.substring(0, 18)?.trim()}: ${notif.body?.substring(0, 45)?.trim()}`.replace("\n", " ");
rev.child.label = `${notif.summary?.substring(0, 18)?.trim()}: ${notif.body?.substring(0, 45)?.trim()}`.replaceAll("\n", " ");
rev.reveal_child = true;
},
],
+1 -4
View File
@@ -13,11 +13,11 @@ static const float bordercolor[] = {0.5, 0.5, 0.5, 1.0};
static const float focuscolor[] = {1.0, 0.0, 0.0, 1.0};
/* To conform the xdg-protocol, set the alpha to zero to restore the old behavior */
static const float fullscreen_bg[] = {0.1, 0.1, 0.1, 1.0};
static bool cursor_warp = true;
/* tagging - tagcount must be no greater than 31 */
#define TAGCOUNT 9
static const int tagcount = 9;
static const bool cursor_warp = true;
/* Autostart */
static const char *const autostart[] = {
@@ -30,9 +30,6 @@ static const char *const autostart[] = {
NULL /* terminate */
};
/* pointer constraints */
static const int allow_constrain = 1;
static const Rule rules[] = {
/* app_id title tags mask isfloating monitor */
/* examples:
+1 -1
View File
@@ -24,7 +24,7 @@ in {
../dwl_patches/deck.patch
../dwl_patches/output-power-managment.patch
../dwl_patches/keyboard-shortcut-inhibit.patch
../dwl_patches/cursor_wrap.patch
../dwl_patches/cursor_warp.patch
../dwl_patches/vanitygaps.patch
../dwl_patches/vanity_deck.patch
../dwl_patches/smartborders.patch