mirror of
https://codeberg.org/dwl/dwl-patches.git
synced 2026-06-20 23:12:44 +00:00
Compare commits
6 Commits
33acb045a8
..
main
| Author | SHA1 | Date | |
|---|---|---|---|
| 41fdaddfb0 | |||
| ee22414b44 | |||
| d8046ab6ec | |||
| 0935f95e01 | |||
| e2ba7017ea | |||
| 493dc4c408 |
@@ -13,8 +13,8 @@ This allows the user to change size and placement of floating windows using only
|
|||||||
| <kbd>MODKEY</kbd> + <kbd>Shift</kbd> + <kbd>Right</kbd> | grow width 40px |
|
| <kbd>MODKEY</kbd> + <kbd>Shift</kbd> + <kbd>Right</kbd> | grow width 40px |
|
||||||
|
|
||||||
### Download
|
### Download
|
||||||
- [git branch](https://codeberg.org/wochap/dwl/src/branch/v0.5/moveresizekb)
|
- [v0.8](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/moveresizekb/moveresizekb.patch)
|
||||||
- [v0.5](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/moveresizekb/moveresizekb.patch)
|
|
||||||
|
|
||||||
### Authors
|
### Authors
|
||||||
|
- [cana](https://codeberg.org/cana)
|
||||||
- [wochap](https://codeberg.org/wochap)
|
- [wochap](https://codeberg.org/wochap)
|
||||||
|
|||||||
@@ -1,38 +1,38 @@
|
|||||||
From c8af428f964679089599e4ffbe7d28d08a4e875f Mon Sep 17 00:00:00 2001
|
From f19c162ba64c2c4860e5d16e48e08cebd7a7e46c Mon Sep 17 00:00:00 2001
|
||||||
From: wochap <gean.marroquin@gmail.com>
|
From: C4FE1 <heitorcdesousa13@gmail.com>
|
||||||
Date: Tue, 5 Mar 2024 23:42:55 -0500
|
Date: Wed, 10 Jun 2026 19:50:26 -0300
|
||||||
Subject: [PATCH] implement keybindings to move and resize focused floating
|
Subject: [PATCH] Change moveresizekb logic to allow it's use in floating
|
||||||
window
|
(NULL) Layout
|
||||||
|
|
||||||
---
|
---
|
||||||
config.def.h | 8 ++++++++
|
config.def.h | 8 ++++++++
|
||||||
dwl.c | 19 +++++++++++++++++++
|
dwl.c | 23 +++++++++++++++++++++++
|
||||||
2 files changed, 27 insertions(+)
|
2 files changed, 31 insertions(+)
|
||||||
|
|
||||||
diff --git a/config.def.h b/config.def.h
|
diff --git a/config.def.h b/config.def.h
|
||||||
index db0babc..d0570b8 100644
|
index 8a6eda0..b8398f9 100644
|
||||||
--- a/config.def.h
|
--- a/config.def.h
|
||||||
+++ b/config.def.h
|
+++ b/config.def.h
|
||||||
@@ -135,6 +135,14 @@ static const Key keys[] = {
|
@@ -138,6 +138,14 @@ static const Key keys[] = {
|
||||||
{ MODKEY, XKB_KEY_space, setlayout, {0} },
|
{ MODKEY, XKB_KEY_space, setlayout, {0} },
|
||||||
{ MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_space, togglefloating, {0} },
|
{ MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_space, togglefloating, {0} },
|
||||||
{ MODKEY, XKB_KEY_e, togglefullscreen, {0} },
|
{ MODKEY, XKB_KEY_e, togglefullscreen, {0} },
|
||||||
+ { MODKEY, XKB_KEY_Down, moveresizekb, {.v = (int []){ 0, 40, 0, 0 }}},
|
+ { MODKEY, XKB_KEY_Down, moveresizekb, {.v = (int []){ 0, 40, 0, 0 }}},
|
||||||
+ { MODKEY, XKB_KEY_Up, moveresizekb, {.v = (int []){ 0, -40, 0, 0 }}},
|
+ { MODKEY, XKB_KEY_Up, moveresizekb, {.v = (int []){ 0, -40, 0, 0 }}},
|
||||||
+ { MODKEY, XKB_KEY_Right, moveresizekb, {.v = (int []){ 40, 0, 0, 0 }}},
|
+ { MODKEY, XKB_KEY_Right, moveresizekb, {.v = (int []){ 40, 0, 0, 0 }}},
|
||||||
+ { MODKEY, XKB_KEY_Left, moveresizekb, {.v = (int []){ -40, 0, 0, 0 }}},
|
+ { MODKEY, XKB_KEY_Left, moveresizekb, {.v = (int []){ -40, 0, 0, 0 }}},
|
||||||
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Down, moveresizekb, {.v = (int []){ 0, 0, 0, 40 }}},
|
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Down, moveresizekb, {.v = (int []){ 0, 0, 0, 40 }}},
|
||||||
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Up, moveresizekb, {.v = (int []){ 0, 0, 0, -40 }}},
|
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Up, moveresizekb, {.v = (int []){ 0, 0, 0, -40 }}},
|
||||||
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Right, moveresizekb, {.v = (int []){ 0, 0, 40, 0 }}},
|
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Right, moveresizekb, {.v = (int []){ 0, 0, 40, 0 }}},
|
||||||
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Left, moveresizekb, {.v = (int []){ 0, 0, -40, 0 }}},
|
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Left, moveresizekb, {.v = (int []){ 0, 0, -40, 0 }}},
|
||||||
{ MODKEY, XKB_KEY_0, view, {.ui = ~0} },
|
{ MODKEY, XKB_KEY_0, view, {.ui = ~0} },
|
||||||
{ MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_parenright, tag, {.ui = ~0} },
|
{ MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_parenright, tag, {.ui = ~0} },
|
||||||
{ MODKEY, XKB_KEY_comma, focusmon, {.i = WLR_DIRECTION_LEFT} },
|
{ MODKEY, XKB_KEY_comma, focusmon, {.i = WLR_DIRECTION_LEFT} },
|
||||||
diff --git a/dwl.c b/dwl.c
|
diff --git a/dwl.c b/dwl.c
|
||||||
index ef27a1d..251472b 100644
|
index 44f3ad9..a6450f5 100644
|
||||||
--- a/dwl.c
|
--- a/dwl.c
|
||||||
+++ b/dwl.c
|
+++ b/dwl.c
|
||||||
@@ -313,6 +313,7 @@ static void tagmon(const Arg *arg);
|
@@ -336,6 +336,7 @@ static void tagmon(const Arg *arg);
|
||||||
static void tile(Monitor *m);
|
static void tile(Monitor *m);
|
||||||
static void togglefloating(const Arg *arg);
|
static void togglefloating(const Arg *arg);
|
||||||
static void togglefullscreen(const Arg *arg);
|
static void togglefullscreen(const Arg *arg);
|
||||||
@@ -40,7 +40,7 @@ index ef27a1d..251472b 100644
|
|||||||
static void toggletag(const Arg *arg);
|
static void toggletag(const Arg *arg);
|
||||||
static void toggleview(const Arg *arg);
|
static void toggleview(const Arg *arg);
|
||||||
static void unlocksession(struct wl_listener *listener, void *data);
|
static void unlocksession(struct wl_listener *listener, void *data);
|
||||||
@@ -2454,6 +2455,24 @@ togglefullscreen(const Arg *arg)
|
@@ -2760,6 +2761,28 @@ togglefullscreen(const Arg *arg)
|
||||||
setfullscreen(sel, !sel->isfullscreen);
|
setfullscreen(sel, !sel->isfullscreen);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -50,7 +50,11 @@ index ef27a1d..251472b 100644
|
|||||||
+ Client *c = focustop(selmon);
|
+ Client *c = focustop(selmon);
|
||||||
+ Monitor *m = selmon;
|
+ Monitor *m = selmon;
|
||||||
+
|
+
|
||||||
+ if(!(m && arg && arg->v && c && c->isfloating)) {
|
+ if(!(m && arg && arg->v && c)){
|
||||||
|
+ return;
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ if(!(c->isfloating || m->lt[m->sellt]->arrange == NULL)){
|
||||||
+ return;
|
+ return;
|
||||||
+ }
|
+ }
|
||||||
+
|
+
|
||||||
@@ -66,5 +70,5 @@ index ef27a1d..251472b 100644
|
|||||||
toggletag(const Arg *arg)
|
toggletag(const Arg *arg)
|
||||||
{
|
{
|
||||||
--
|
--
|
||||||
2.42.0
|
2.54.0
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,18 @@
|
|||||||
|
### Description
|
||||||
|
Adds per-window screen sharing aka toplevel capture via `ext-foreign-toplevel-image-capture-source-v1` based on the sway implementation <br>
|
||||||
|
XWayland clients work in basic testing but it should be considered rather experimental. There is some possible restacking edge-cases but I was not able to reproduce them yet <br>
|
||||||
|
Note that the captured surface is rendered a second time into its own scene, so there's a small GPU cost while a capture is active
|
||||||
|
|
||||||
|
Targets the dwl **`wlroots-next`** branch (base commit `d41ecb745c`).
|
||||||
|
|
||||||
|
### Requirements
|
||||||
|
| Requirement | Notes |
|
||||||
|
| --- | --- |
|
||||||
|
| `wlroots` ≥ 0.20 | mandatory |
|
||||||
|
| `xdg-desktop-portal-wlr` ≥ 0.8 | `chooser_type` has to be configured as `dmenu` |
|
||||||
|
|
||||||
|
### Download
|
||||||
|
- [per-app-share-wlroots-next-d41ecb745c](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/per-app-cast/per-app-share-wlroots-next-d41ecb745c.patch)
|
||||||
|
|
||||||
|
### Authors
|
||||||
|
- [skeetamine](https://codeberg.org/skeetamine)
|
||||||
@@ -0,0 +1,194 @@
|
|||||||
|
From e0fe17a27625440a1a4ac8cfe91639a938589925 Mon Sep 17 00:00:00 2001
|
||||||
|
From: skeetamine <lesrallidenud@gmail.com>
|
||||||
|
Date: Fri, 19 Jun 2026 18:37:41 +0300
|
||||||
|
Subject: [PATCH] per-app-cast: capture individual toplevels
|
||||||
|
|
||||||
|
Implement ext-foreign-toplevel-image-capture-source-v1 so portals can
|
||||||
|
offer per-window screen sharing alongside per-output. Each toplevel is
|
||||||
|
rendered into a dedicated offscreen scene so capture isolates the window
|
||||||
|
regardless of tag/position.
|
||||||
|
---
|
||||||
|
dwl.c | 83 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
|
||||||
|
1 file changed, 83 insertions(+)
|
||||||
|
|
||||||
|
diff --git a/dwl.c b/dwl.c
|
||||||
|
index 8101ffa..7f4d059 100644
|
||||||
|
--- a/dwl.c
|
||||||
|
+++ b/dwl.c
|
||||||
|
@@ -25,6 +25,7 @@
|
||||||
|
#include <wlr/types/wlr_drm.h>
|
||||||
|
#include <wlr/types/wlr_export_dmabuf_v1.h>
|
||||||
|
#include <wlr/types/wlr_ext_data_control_v1.h>
|
||||||
|
+#include <wlr/types/wlr_ext_foreign_toplevel_list_v1.h>
|
||||||
|
#include <wlr/types/wlr_ext_image_capture_source_v1.h>
|
||||||
|
#include <wlr/types/wlr_ext_image_copy_capture_v1.h>
|
||||||
|
#include <wlr/types/wlr_fractional_scale_v1.h>
|
||||||
|
@@ -123,6 +124,7 @@ typedef struct {
|
||||||
|
struct wlr_xwayland_surface *xwayland;
|
||||||
|
} surface;
|
||||||
|
struct wlr_xdg_toplevel_decoration_v1 *decoration;
|
||||||
|
+ struct wlr_ext_foreign_toplevel_handle_v1 *foreign_toplevel;
|
||||||
|
struct wl_listener commit;
|
||||||
|
struct wl_listener map;
|
||||||
|
struct wl_listener maximize;
|
||||||
|
@@ -243,6 +245,11 @@ typedef struct {
|
||||||
|
struct wl_listener destroy;
|
||||||
|
} SessionLock;
|
||||||
|
|
||||||
|
+typedef struct {
|
||||||
|
+ struct wlr_scene *scene;
|
||||||
|
+ struct wl_listener source_destroy;
|
||||||
|
+} CaptureScene;
|
||||||
|
+
|
||||||
|
/* function declarations */
|
||||||
|
static void applybounds(Client *c, struct wlr_box *bbox);
|
||||||
|
static void applyrules(Client *c);
|
||||||
|
@@ -252,6 +259,7 @@ static void arrangelayer(Monitor *m, struct wl_list *list,
|
||||||
|
static void arrangelayers(Monitor *m);
|
||||||
|
static void axisnotify(struct wl_listener *listener, void *data);
|
||||||
|
static void buttonpress(struct wl_listener *listener, void *data);
|
||||||
|
+static void capturescenedestroy(struct wl_listener *listener, void *data);
|
||||||
|
static void chvt(const Arg *arg);
|
||||||
|
static void checkidleinhibitor(struct wlr_surface *exclude);
|
||||||
|
static void cleanup(void);
|
||||||
|
@@ -292,6 +300,7 @@ static void focusstack(const Arg *arg);
|
||||||
|
static Client *focustop(Monitor *m);
|
||||||
|
static void fullscreennotify(struct wl_listener *listener, void *data);
|
||||||
|
static void gpureset(struct wl_listener *listener, void *data);
|
||||||
|
+static void handlecapturerequest(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);
|
||||||
|
@@ -399,6 +408,10 @@ static struct wlr_session_lock_manager_v1 *session_lock_mgr;
|
||||||
|
static struct wlr_scene_rect *locked_bg;
|
||||||
|
static struct wlr_session_lock_v1 *cur_lock;
|
||||||
|
|
||||||
|
+static struct wlr_ext_foreign_toplevel_list_v1 *foreign_toplevel_list;
|
||||||
|
+static struct wlr_ext_foreign_toplevel_image_capture_source_manager_v1 *toplevel_capture_mgr;
|
||||||
|
+static struct wl_listener foreign_toplevel_capture_request = {.notify = handlecapturerequest};
|
||||||
|
+
|
||||||
|
static struct wlr_seat *seat;
|
||||||
|
static KeyboardGroup *kb_group;
|
||||||
|
static unsigned int cursor_mode;
|
||||||
|
@@ -676,6 +689,15 @@ buttonpress(struct wl_listener *listener, void *data)
|
||||||
|
event->time_msec, event->button, event->state);
|
||||||
|
}
|
||||||
|
|
||||||
|
+void
|
||||||
|
+capturescenedestroy(struct wl_listener *listener, void *data)
|
||||||
|
+{
|
||||||
|
+ CaptureScene *cs = wl_container_of(listener, cs, source_destroy);
|
||||||
|
+ wl_list_remove(&cs->source_destroy.link);
|
||||||
|
+ wlr_scene_node_destroy(&cs->scene->tree.node);
|
||||||
|
+ free(cs);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void
|
||||||
|
chvt(const Arg *arg)
|
||||||
|
{
|
||||||
|
@@ -786,6 +808,7 @@ cleanuplisteners(void)
|
||||||
|
wl_list_remove(&request_start_drag.link);
|
||||||
|
wl_list_remove(&start_drag.link);
|
||||||
|
wl_list_remove(&new_session_lock.link);
|
||||||
|
+ wl_list_remove(&foreign_toplevel_capture_request.link);
|
||||||
|
#ifdef XWAYLAND
|
||||||
|
wl_list_remove(&new_xwayland_surface.link);
|
||||||
|
wl_list_remove(&xwayland_ready.link);
|
||||||
|
@@ -1561,6 +1584,41 @@ gpureset(struct wl_listener *listener, void *data)
|
||||||
|
wlr_renderer_destroy(old_drw);
|
||||||
|
}
|
||||||
|
|
||||||
|
+void
|
||||||
|
+handlecapturerequest(struct wl_listener *listener, void *data)
|
||||||
|
+{
|
||||||
|
+ struct wlr_ext_foreign_toplevel_image_capture_source_manager_v1_request *req = data;
|
||||||
|
+ Client *c;
|
||||||
|
+ CaptureScene *cs;
|
||||||
|
+ struct wlr_ext_image_capture_source_v1 *source;
|
||||||
|
+
|
||||||
|
+ wl_list_for_each(c, &clients, link) {
|
||||||
|
+ if (c->foreign_toplevel != req->toplevel_handle)
|
||||||
|
+ continue;
|
||||||
|
+
|
||||||
|
+ cs = ecalloc(1, sizeof(*cs));
|
||||||
|
+ cs->scene = wlr_scene_create();
|
||||||
|
+ if (c->type == XDGShell)
|
||||||
|
+ wlr_scene_xdg_surface_create(&cs->scene->tree, c->surface.xdg);
|
||||||
|
+ else
|
||||||
|
+ wlr_scene_subsurface_tree_create(&cs->scene->tree, client_surface(c));
|
||||||
|
+
|
||||||
|
+ source =
|
||||||
|
+ wlr_ext_image_capture_source_v1_create_with_scene_node(
|
||||||
|
+ &cs->scene->tree.node, event_loop, alloc, drw);
|
||||||
|
+
|
||||||
|
+ if (source) {
|
||||||
|
+ cs->source_destroy.notify = capturescenedestroy;
|
||||||
|
+ wl_signal_add(&source->events.destroy, &cs->source_destroy);
|
||||||
|
+ wlr_ext_foreign_toplevel_image_capture_source_manager_v1_request_accept(req, source);
|
||||||
|
+ } else {
|
||||||
|
+ wlr_scene_node_destroy(&cs->scene->tree.node);
|
||||||
|
+ free(cs);
|
||||||
|
+ }
|
||||||
|
+ return;
|
||||||
|
+ }
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void
|
||||||
|
handlesig(int signo)
|
||||||
|
{
|
||||||
|
@@ -1786,6 +1844,14 @@ mapnotify(struct wl_listener *listener, void *data)
|
||||||
|
wl_list_insert(&clients, &c->link);
|
||||||
|
wl_list_insert(&fstack, &c->flink);
|
||||||
|
|
||||||
|
+ {
|
||||||
|
+ struct wlr_ext_foreign_toplevel_handle_v1_state ft_state = {
|
||||||
|
+ .title = client_get_title(c),
|
||||||
|
+ .app_id = client_get_appid(c),
|
||||||
|
+ };
|
||||||
|
+ c->foreign_toplevel = wlr_ext_foreign_toplevel_handle_v1_create(foreign_toplevel_list, &ft_state);
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
/* Set initial monitor, tags, floating status, and focus:
|
||||||
|
* we always consider floating, clients that have parent and thus
|
||||||
|
* we set the same tags and monitor as its parent.
|
||||||
|
@@ -2532,6 +2598,10 @@ setup(void)
|
||||||
|
wlr_presentation_create(dpy, backend, 2);
|
||||||
|
wlr_alpha_modifier_v1_create(dpy);
|
||||||
|
|
||||||
|
+ foreign_toplevel_list = wlr_ext_foreign_toplevel_list_v1_create(dpy, 1);
|
||||||
|
+ toplevel_capture_mgr = wlr_ext_foreign_toplevel_image_capture_source_manager_v1_create(dpy, 1);
|
||||||
|
+ wl_signal_add(&toplevel_capture_mgr->events.new_request, &foreign_toplevel_capture_request);
|
||||||
|
+
|
||||||
|
/* Initializes the interface used to implement urgency hints */
|
||||||
|
activation = wlr_xdg_activation_v1_create(dpy);
|
||||||
|
wl_signal_add(&activation->events.request_activate, &request_activate);
|
||||||
|
@@ -2838,6 +2908,11 @@ unmapnotify(struct wl_listener *listener, void *data)
|
||||||
|
wl_list_remove(&c->flink);
|
||||||
|
}
|
||||||
|
|
||||||
|
+ if (c->foreign_toplevel) {
|
||||||
|
+ wlr_ext_foreign_toplevel_handle_v1_destroy(c->foreign_toplevel);
|
||||||
|
+ c->foreign_toplevel = NULL;
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
wlr_scene_node_destroy(&c->scene->node);
|
||||||
|
printstatus();
|
||||||
|
motionnotify(0, NULL, 0, 0, 0, 0);
|
||||||
|
@@ -2955,6 +3030,14 @@ updatetitle(struct wl_listener *listener, void *data)
|
||||||
|
Client *c = wl_container_of(listener, c, set_title);
|
||||||
|
if (c == focustop(c->mon))
|
||||||
|
printstatus();
|
||||||
|
+
|
||||||
|
+ if (c->foreign_toplevel) {
|
||||||
|
+ struct wlr_ext_foreign_toplevel_handle_v1_state ft_state = {
|
||||||
|
+ .title = client_get_title(c),
|
||||||
|
+ .app_id = client_get_appid(c),
|
||||||
|
+ };
|
||||||
|
+ wlr_ext_foreign_toplevel_handle_v1_update_state(c->foreign_toplevel, &ft_state);
|
||||||
|
+ }
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
--
|
||||||
|
2.54.0
|
||||||
|
|
||||||
@@ -2,7 +2,11 @@
|
|||||||
Moves clients to their old output when it is reattached.
|
Moves clients to their old output when it is reattached.
|
||||||
|
|
||||||
### Download
|
### Download
|
||||||
- [git branch](https://codeberg.org/eyusupov/dwl/src/branch/restore-monitor)
|
- [git branch](https://codeberg.org/6z7y/dwl-patches/src/branch/restore-monitor)
|
||||||
- [2024-04-07](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/restore-monitor/restore-monitor.patch)
|
- [2026-06-20](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/restore-monitor/restore-monitor.patch)
|
||||||
### Authors
|
### Authors
|
||||||
- [eyusupov](https://codeberg.org/eyusupov)
|
#### Current
|
||||||
|
- [6z7y](https://codeberg.org/6z7y)
|
||||||
|
#### Historic
|
||||||
|
- [eyusupov](https://codeberg.org/eyusupov)
|
||||||
|
|
||||||
|
|||||||
@@ -1,79 +1,95 @@
|
|||||||
From e42ca1c539437d3098d80983cfe2ad6f938d7a08 Mon Sep 17 00:00:00 2001
|
From e42ca1c539437d3098d80983cfe2ad6f938d7a08 Mon Sep 17 00:00:00 2001
|
||||||
From: Eldar Yusupov <eyusupov@gmail.com>
|
From: Eldar Yusupov <eyusupov@gmail.com>
|
||||||
Date: Sun, 17 Mar 2024 19:12:29 +0300
|
Date: Sun, 17 Mar 2024 19:12:29 +0300
|
||||||
Subject: [PATCH] Restore correct monitor for client when it is reattached
|
Subject: [PATCH] Restore correct monitor and floating position when reattached
|
||||||
|
|
||||||
---
|
---
|
||||||
dwl.c | 24 ++++++++++++++++++++++--
|
dwl.c | 33 ++++++++++++++++++++++++++++++---
|
||||||
1 file changed, 22 insertions(+), 2 deletions(-)
|
1 file changed, 30 insertions(+), 3 deletions(-)
|
||||||
|
|
||||||
diff --git a/dwl.c b/dwl.c
|
diff --git a/dwl.c b/dwl.c
|
||||||
index bf763df..d8d8139 100644
|
index 44f3ad9..41548cd 100644
|
||||||
--- a/dwl.c
|
--- a/dwl.c
|
||||||
+++ b/dwl.c
|
+++ b/dwl.c
|
||||||
@@ -107,6 +107,7 @@ typedef struct {
|
@@ -106,6 +106,8 @@ typedef struct {
|
||||||
unsigned int type; /* XDGShell or X11* */
|
unsigned int type; /* XDGShell or X11* */
|
||||||
struct wlr_box geom; /* layout-relative, includes border */
|
|
||||||
Monitor *mon;
|
Monitor *mon;
|
||||||
+ char *output;
|
+ char *output;
|
||||||
|
+ struct wlr_box floatgeom; /* saved geom for floating restore after monitor reconnect */
|
||||||
struct wlr_scene_tree *scene;
|
struct wlr_scene_tree *scene;
|
||||||
struct wlr_scene_rect *border[4]; /* top, bottom, left, right */
|
struct wlr_scene_rect *border[4]; /* top, bottom, left, right */
|
||||||
struct wlr_scene_tree *scene_surface;
|
struct wlr_scene_tree *scene_surface;
|
||||||
@@ -869,6 +870,7 @@ createmon(struct wl_listener *listener, void *data)
|
@@ -807,6 +809,13 @@ closemon(Monitor *m)
|
||||||
|
}
|
||||||
|
|
||||||
|
wl_list_for_each(c, &clients, link) {
|
||||||
|
+
|
||||||
|
+ /* Save floating geom now, before destroymon modifies it below.
|
||||||
|
+ * destroymon subtracts m->w.width from c->geom.x for floating
|
||||||
|
+ * windows, which corrupts the layout-absolute position we need
|
||||||
|
+ * to restore on reconnect. */
|
||||||
|
+ if (c->isfloating && c->mon == m) c->floatgeom = c->geom;
|
||||||
|
+
|
||||||
|
if (c->isfloating && c->geom.x > m->m.width)
|
||||||
|
resize(c, (struct wlr_box){.x = c->geom.x - m->w.width, .y = c->geom.y,
|
||||||
|
.width = c->geom.width, .height = c->geom.height}, 0);
|
||||||
|
@@ -1045,6 +1054,7 @@ createmon(struct wl_listener *listener, void *data)
|
||||||
size_t i;
|
size_t i;
|
||||||
struct wlr_output_state state;
|
struct wlr_output_state state;
|
||||||
Monitor *m;
|
Monitor *m;
|
||||||
+ Client *c;
|
+ Client *c;
|
||||||
|
|
||||||
if (!wlr_output_init_render(wlr_output, alloc, drw))
|
if (!wlr_output_init_render(wlr_output, alloc, drw))
|
||||||
return;
|
return;
|
||||||
@@ -938,6 +940,13 @@ createmon(struct wl_listener *listener, void *data)
|
@@ -1114,6 +1124,15 @@ createmon(struct wl_listener *listener, void *data)
|
||||||
wlr_output_layout_add_auto(output_layout, wlr_output);
|
wlr_output_layout_add_auto(output_layout, wlr_output);
|
||||||
else
|
else
|
||||||
wlr_output_layout_add(output_layout, wlr_output, m->m.x, m->m.y);
|
wlr_output_layout_add(output_layout, wlr_output, m->m.x, m->m.y);
|
||||||
+
|
+
|
||||||
+ wl_list_for_each(c, &clients, link) {
|
+ wl_list_for_each(c, &clients, link) {
|
||||||
+ if (strcmp(wlr_output->name, c->output) == 0) {
|
+ if (!c->output || strcmp(wlr_output->name, c->output) != 0)
|
||||||
+ c->mon = m;
|
+ continue;
|
||||||
+ }
|
+ c->mon = m;
|
||||||
+ }
|
+ if (c->isfloating)
|
||||||
+ updatemons(NULL, NULL);
|
+ resize(c, c->floatgeom, 0);
|
||||||
|
+ }
|
||||||
|
+ updatemons(NULL, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@@ -1186,6 +1195,7 @@ destroynotify(struct wl_listener *listener, void *data)
|
@@ -1347,7 +1366,8 @@ destroynotify(struct wl_listener *listener, void *data)
|
||||||
wl_list_remove(&c->map.link);
|
|
||||||
wl_list_remove(&c->unmap.link);
|
wl_list_remove(&c->unmap.link);
|
||||||
|
wl_list_remove(&c->maximize.link);
|
||||||
}
|
}
|
||||||
+ free(c->output);
|
- free(c);
|
||||||
free(c);
|
+ free(c->output);
|
||||||
|
+ free(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1618,6 +1628,10 @@ mapnotify(struct wl_listener *listener, void *data)
|
void
|
||||||
|
@@ -1792,6 +1812,9 @@ mapnotify(struct wl_listener *listener, void *data)
|
||||||
} else {
|
} else {
|
||||||
applyrules(c);
|
applyrules(c);
|
||||||
}
|
}
|
||||||
+ c->output = strdup(c->mon->wlr_output->name);
|
+ c->output = strdup(c->mon->wlr_output->name);
|
||||||
+ if (c->output == NULL) {
|
+ if (c->output == NULL) die("oom");
|
||||||
+ die("oom");
|
+
|
||||||
+ }
|
|
||||||
printstatus();
|
printstatus();
|
||||||
|
|
||||||
unset_fullscreen:
|
unset_fullscreen:
|
||||||
@@ -2565,8 +2579,14 @@ void
|
@@ -2705,8 +2728,12 @@ void
|
||||||
tagmon(const Arg *arg)
|
tagmon(const Arg *arg)
|
||||||
{
|
{
|
||||||
Client *sel = focustop(selmon);
|
Client *sel = focustop(selmon);
|
||||||
- if (sel)
|
- if (sel)
|
||||||
- setmon(sel, dirtomon(arg->i), 0);
|
- setmon(sel, dirtomon(arg->i), 0);
|
||||||
+ if (!sel)
|
+ if (!sel) return;
|
||||||
+ return;
|
+
|
||||||
+ setmon(sel, dirtomon(arg->i), 0);
|
+ setmon(sel, dirtomon(arg->i), 0);
|
||||||
+ free(sel->output);
|
+ free(sel->output);
|
||||||
+ sel->output = strdup(sel->mon->wlr_output->name);
|
+ sel->output = strdup(sel->mon->wlr_output->name);
|
||||||
+ if (sel->output == NULL) {
|
+ if (sel->output == NULL) die("oom");
|
||||||
+ die("oom");
|
|
||||||
+ }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
|||||||
@@ -1,22 +1,28 @@
|
|||||||
### Description
|
### Description
|
||||||
Adds touchscreen functionality.
|
Adds touchscreen functionality.
|
||||||
|
|
||||||
KNOWN BUGS:
|
KNOWN BUGS:
|
||||||
- Sometimes, the pointer moves to where the screen is pressed, but the button press doesn't occur until the screen is touched AGAIN. This means that if you touch to click button 'Q' on the screen (for instance), nothing happens; then you touch elsewhere on the screen and THEN button 'Q' registers a click. This is annoying, doesn't always happen, and I don't yet know how to fix it.
|
- Sometimes, the pointer moves to where the screen is pressed, but the button press doesn't occur until the screen is touched AGAIN. This means that if you touch to click button 'Q' on the screen (for instance), nothing happens; then you touch elsewhere on the screen and THEN button 'Q' registers a click. This is annoying, doesn't always happen, and I don't yet know how to fix it.
|
||||||
|
|
||||||
### Download
|
### Download
|
||||||
- [git branch](https://codeberg.org/fauxmight/dwl/src/branch/touch-input)
|
- [git branch](https://codeberg.org/fauxmight/dwl/src/branch/touch-input)
|
||||||
- [touch-input-wlroots-next-f4249db.patch](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/touch-input/touch-input-wlroots-next-f4249db.patch)
|
- [touch-input-wlroots-next-f4249db.patch](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/touch-input/touch-input-wlroots-next-f4249db.patch)
|
||||||
- [touch-input-0.8.patch](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/touch-input/touch-input-0.8.patch)
|
- [touch-input-0.8.patch](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/touch-input/touch-input-0.8.patch)
|
||||||
|
- [touch-input-0.8-osu-ver.patch](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/touch-input/touch-input-0.8-osu-ver.patch)
|
||||||
### Authors
|
|
||||||
- [fauxmight](https://codeberg.org/fauxmight)
|
### Authors
|
||||||
- [minego](https://codeberg.org/minego)
|
#### Current
|
||||||
- [Unprex](https://github.com/Unprex)
|
- [fauxmight](https://codeberg.org/fauxmight)
|
||||||
|
- [6z7y](https://codeberg.org/6z7y) -- maintaining `osu!` version of the `touch-input` patch
|
||||||
### Changelog
|
#### Historic
|
||||||
- 2026-02-26 Update patch for dwl v0.8 and dwl wlroots-next branch commit f4249db
|
- [minego](https://codeberg.org/minego)
|
||||||
- 2025-01-01 @fauxmight took over maintenance. Previous maintainer @minego notes [lack of available time](https://codeberg.org/dwl/dwl-patches/pulls/102#issuecomment-2557944)
|
- [Unprex](https://github.com/Unprex)
|
||||||
- 2024-02-11 Corrected issue where motion events where not sending notifications for unfocused clients such as an on screen keyboard
|
|
||||||
- 2024-03-26 Rebased, and removed #ifdef's for the pointer constraints patch which has been merged into upstream
|
|
||||||
- 2024-03-28 Removed debug
|
### Changelog
|
||||||
|
- 2026-06-15 Add support for osu! fullscreen touch input (fix cursor stuck issue)
|
||||||
|
- 2026-02-26 Update patch for dwl v0.8 and dwl wlroots-next branch commit f4249db
|
||||||
|
- 2025-01-01 @fauxmight took over maintenance. Previous maintainer @minego notes [lack of available time](https://codeberg.org/dwl/dwl-patches/pulls/102#issuecomment-2557944)
|
||||||
|
- 2024-02-11 Corrected issue where motion events where not sending notifications for unfocused clients such as an on screen keyboard
|
||||||
|
- 2024-03-26 Rebased, and removed #ifdef's for the pointer constraints patch which has been merged into upstream
|
||||||
|
- 2024-03-28 Removed debug
|
||||||
|
|||||||
+279
@@ -0,0 +1,279 @@
|
|||||||
|
diff --git a/dwl.c b/dwl.c
|
||||||
|
index 44f3ad9..977f2c8 100644
|
||||||
|
--- a/dwl.c
|
||||||
|
+++ b/dwl.c
|
||||||
|
@@ -24,6 +24,7 @@
|
||||||
|
#include <wlr/types/wlr_data_device.h>
|
||||||
|
#include <wlr/types/wlr_drm.h>
|
||||||
|
#include <wlr/types/wlr_export_dmabuf_v1.h>
|
||||||
|
+#include <wlr/types/wlr_ext_data_control_v1.h>
|
||||||
|
#include <wlr/types/wlr_fractional_scale_v1.h>
|
||||||
|
#include <wlr/types/wlr_gamma_control_v1.h>
|
||||||
|
#include <wlr/types/wlr_idle_inhibit_v1.h>
|
||||||
|
@@ -51,6 +52,7 @@
|
||||||
|
#include <wlr/types/wlr_session_lock_v1.h>
|
||||||
|
#include <wlr/types/wlr_single_pixel_buffer_v1.h>
|
||||||
|
#include <wlr/types/wlr_subcompositor.h>
|
||||||
|
+#include <wlr/types/wlr_touch.h>
|
||||||
|
#include <wlr/types/wlr_viewporter.h>
|
||||||
|
#include <wlr/types/wlr_virtual_keyboard_v1.h>
|
||||||
|
#include <wlr/types/wlr_virtual_pointer_v1.h>
|
||||||
|
@@ -161,6 +163,12 @@ typedef struct {
|
||||||
|
struct wl_listener destroy;
|
||||||
|
} KeyboardGroup;
|
||||||
|
|
||||||
|
+typedef struct TouchGroup {
|
||||||
|
+ struct wl_list link;
|
||||||
|
+ struct wlr_touch *touch;
|
||||||
|
+ Monitor *m;
|
||||||
|
+} TouchGroup;
|
||||||
|
+
|
||||||
|
typedef struct {
|
||||||
|
/* Must keep this field first */
|
||||||
|
unsigned int type; /* LayerShell */
|
||||||
|
@@ -269,6 +277,7 @@ static void createpointer(struct wlr_pointer *pointer);
|
||||||
|
static void createpointerconstraint(struct wl_listener *listener, void *data);
|
||||||
|
static void createpopup(struct wl_listener *listener, void *data);
|
||||||
|
static void cursorconstrain(struct wlr_pointer_constraint_v1 *constraint);
|
||||||
|
+static void createtouch(struct wlr_touch *touch);
|
||||||
|
static void cursorframe(struct wl_listener *listener, void *data);
|
||||||
|
static void cursorwarptohint(void);
|
||||||
|
static void destroydecoration(struct wl_listener *listener, void *data);
|
||||||
|
@@ -338,6 +347,10 @@ static void togglefloating(const Arg *arg);
|
||||||
|
static void togglefullscreen(const Arg *arg);
|
||||||
|
static void toggletag(const Arg *arg);
|
||||||
|
static void toggleview(const Arg *arg);
|
||||||
|
+static void touchdown(struct wl_listener *listener, void *data);
|
||||||
|
+static void touchup(struct wl_listener *listener, void *data);
|
||||||
|
+static void touchframe(struct wl_listener *listener, void *data);
|
||||||
|
+static void touchmotion(struct wl_listener *listener, void *data);
|
||||||
|
static void unlocksession(struct wl_listener *listener, void *data);
|
||||||
|
static void unmaplayersurfacenotify(struct wl_listener *listener, void *data);
|
||||||
|
static void unmapnotify(struct wl_listener *listener, void *data);
|
||||||
|
@@ -405,6 +418,7 @@ static struct wlr_output_layout *output_layout;
|
||||||
|
static struct wlr_box sgeom;
|
||||||
|
static struct wl_list mons;
|
||||||
|
static Monitor *selmon;
|
||||||
|
+static struct wl_list touches;
|
||||||
|
|
||||||
|
/* global event handlers */
|
||||||
|
static struct wl_listener cursor_axis = {.notify = axisnotify};
|
||||||
|
@@ -434,6 +448,10 @@ static struct wl_listener request_set_sel = {.notify = setsel};
|
||||||
|
static struct wl_listener request_set_cursor_shape = {.notify = setcursorshape};
|
||||||
|
static struct wl_listener request_start_drag = {.notify = requeststartdrag};
|
||||||
|
static struct wl_listener start_drag = {.notify = startdrag};
|
||||||
|
+static struct wl_listener touch_down = {.notify = touchdown};
|
||||||
|
+static struct wl_listener touch_frame = {.notify = touchframe};
|
||||||
|
+static struct wl_listener touch_motion = {.notify = touchmotion};
|
||||||
|
+static struct wl_listener touch_up = {.notify = touchup};
|
||||||
|
static struct wl_listener new_session_lock = {.notify = locksession};
|
||||||
|
|
||||||
|
#ifdef XWAYLAND
|
||||||
|
@@ -585,7 +603,7 @@ arrangelayers(Monitor *m)
|
||||||
|
arrange(m);
|
||||||
|
}
|
||||||
|
|
||||||
|
- /* Arrange non-exlusive surfaces from top->bottom */
|
||||||
|
+ /* Arrange non-exclusive surfaces from top->bottom */
|
||||||
|
for (i = 3; i >= 0; i--)
|
||||||
|
arrangelayer(m, &m->layers[i], &usable_area, 0);
|
||||||
|
|
||||||
|
@@ -781,6 +799,10 @@ cleanuplisteners(void)
|
||||||
|
wl_list_remove(&request_set_cursor_shape.link);
|
||||||
|
wl_list_remove(&request_start_drag.link);
|
||||||
|
wl_list_remove(&start_drag.link);
|
||||||
|
+ wl_list_remove(&touch_down.link);
|
||||||
|
+ wl_list_remove(&touch_frame.link);
|
||||||
|
+ wl_list_remove(&touch_motion.link);
|
||||||
|
+ wl_list_remove(&touch_up.link);
|
||||||
|
wl_list_remove(&new_session_lock.link);
|
||||||
|
#ifdef XWAYLAND
|
||||||
|
wl_list_remove(&new_xwayland_surface.link);
|
||||||
|
@@ -1199,6 +1221,16 @@ createpopup(struct wl_listener *listener, void *data)
|
||||||
|
LISTEN_STATIC(&popup->base->surface->events.commit, commitpopup);
|
||||||
|
}
|
||||||
|
|
||||||
|
+void
|
||||||
|
+createtouch(struct wlr_touch *wlr_touch)
|
||||||
|
+{
|
||||||
|
+ TouchGroup *touch = ecalloc(1, sizeof(TouchGroup));
|
||||||
|
+
|
||||||
|
+ touch->touch = wlr_touch;
|
||||||
|
+ wl_list_insert(&touches, &touch->link);
|
||||||
|
+ wlr_cursor_attach_input_device(cursor, &wlr_touch->base);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void
|
||||||
|
cursorconstrain(struct wlr_pointer_constraint_v1 *constraint)
|
||||||
|
{
|
||||||
|
@@ -1590,6 +1622,9 @@ inputdevice(struct wl_listener *listener, void *data)
|
||||||
|
case WLR_INPUT_DEVICE_POINTER:
|
||||||
|
createpointer(wlr_pointer_from_input_device(device));
|
||||||
|
break;
|
||||||
|
+ case WLR_INPUT_DEVICE_TOUCH:
|
||||||
|
+ createtouch(wlr_touch_from_input_device(device));
|
||||||
|
+ break;
|
||||||
|
default:
|
||||||
|
/* TODO handle other input device types */
|
||||||
|
break;
|
||||||
|
@@ -1602,6 +1637,8 @@ inputdevice(struct wl_listener *listener, void *data)
|
||||||
|
caps = WL_SEAT_CAPABILITY_POINTER;
|
||||||
|
if (!wl_list_empty(&kb_group->wlr_group->devices))
|
||||||
|
caps |= WL_SEAT_CAPABILITY_KEYBOARD;
|
||||||
|
+ if (!wl_list_empty(&touches))
|
||||||
|
+ caps |= WL_SEAT_CAPABILITY_TOUCH;
|
||||||
|
wlr_seat_set_capabilities(seat, caps);
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -2133,7 +2170,7 @@ powermgrsetmode(struct wl_listener *listener, void *data)
|
||||||
|
if (!m)
|
||||||
|
return;
|
||||||
|
|
||||||
|
- m->gamma_lut_changed = 1; /* Reapply gamma LUT when re-enabling the ouput */
|
||||||
|
+ m->gamma_lut_changed = 1; /* Reapply gamma LUT when re-enabling the output */
|
||||||
|
wlr_output_state_set_enabled(&state, event->mode);
|
||||||
|
wlr_output_commit_state(m->wlr_output, &state);
|
||||||
|
|
||||||
|
@@ -2455,7 +2492,7 @@ setup(void)
|
||||||
|
wlr_log_init(log_level, NULL);
|
||||||
|
|
||||||
|
/* The Wayland display is managed by libwayland. It handles accepting
|
||||||
|
- * clients from the Unix socket, manging Wayland globals, and so on. */
|
||||||
|
+ * clients from the Unix socket, managing Wayland globals, and so on. */
|
||||||
|
dpy = wl_display_create();
|
||||||
|
event_loop = wl_display_get_event_loop(dpy);
|
||||||
|
|
||||||
|
@@ -2518,6 +2555,7 @@ setup(void)
|
||||||
|
wlr_export_dmabuf_manager_v1_create(dpy);
|
||||||
|
wlr_screencopy_manager_v1_create(dpy);
|
||||||
|
wlr_data_control_manager_v1_create(dpy);
|
||||||
|
+ wlr_ext_data_control_manager_v1_create(dpy, 1);
|
||||||
|
wlr_primary_selection_v1_device_manager_create(dpy);
|
||||||
|
wlr_viewporter_create(dpy);
|
||||||
|
wlr_single_pixel_buffer_manager_v1_create(dpy);
|
||||||
|
@@ -2615,6 +2653,13 @@ setup(void)
|
||||||
|
wl_signal_add(&cursor->events.axis, &cursor_axis);
|
||||||
|
wl_signal_add(&cursor->events.frame, &cursor_frame);
|
||||||
|
|
||||||
|
+ wl_list_init(&touches);
|
||||||
|
+
|
||||||
|
+ wl_signal_add(&cursor->events.touch_down, &touch_down);
|
||||||
|
+ wl_signal_add(&cursor->events.touch_frame, &touch_frame);
|
||||||
|
+ wl_signal_add(&cursor->events.touch_motion, &touch_motion);
|
||||||
|
+ wl_signal_add(&cursor->events.touch_up, &touch_up);
|
||||||
|
+
|
||||||
|
cursor_shape_mgr = wlr_cursor_shape_manager_v1_create(dpy, 1);
|
||||||
|
wl_signal_add(&cursor_shape_mgr->events.request_set_shape, &request_set_cursor_shape);
|
||||||
|
|
||||||
|
@@ -2787,6 +2832,111 @@ toggleview(const Arg *arg)
|
||||||
|
printstatus();
|
||||||
|
}
|
||||||
|
|
||||||
|
+void
|
||||||
|
+touchdown(struct wl_listener *listener, void *data)
|
||||||
|
+{
|
||||||
|
+ struct wlr_touch_down_event *event = data;
|
||||||
|
+ double lx, ly;
|
||||||
|
+ double sx, sy;
|
||||||
|
+ struct wlr_surface *surface;
|
||||||
|
+ Client *c = NULL;
|
||||||
|
+ Monitor *m;
|
||||||
|
+
|
||||||
|
+ wlr_idle_notifier_v1_notify_activity(idle_notifier, seat);
|
||||||
|
+
|
||||||
|
+ // Map the input to the appropriate output
|
||||||
|
+ wl_list_for_each(m, &mons, link) {
|
||||||
|
+ if (m == NULL || m->wlr_output == NULL)
|
||||||
|
+ continue;
|
||||||
|
+ if (event->touch->output_name != NULL &&
|
||||||
|
+ 0 != strcmp(event->touch->output_name, m->wlr_output->name))
|
||||||
|
+ continue;
|
||||||
|
+ wlr_cursor_map_input_to_output(cursor, &event->touch->base, m->wlr_output);
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ wlr_cursor_absolute_to_layout_coords(cursor, &event->touch->base,
|
||||||
|
+ event->x, event->y, &lx, &ly);
|
||||||
|
+
|
||||||
|
+ /* Find the client under the touch point */
|
||||||
|
+ xytonode(lx, ly, &surface, &c, NULL, &sx, &sy);
|
||||||
|
+ if (sloppyfocus && c)
|
||||||
|
+ focusclient(c, 0);
|
||||||
|
+
|
||||||
|
+ // Send touch event to client (if any)
|
||||||
|
+ if (surface != NULL) {
|
||||||
|
+ wlr_seat_touch_notify_down(seat, surface, event->time_msec,
|
||||||
|
+ event->touch_id, sx, sy);
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ // ALWAYS move cursor and send click - no conditions!
|
||||||
|
+ wlr_cursor_warp_closest(cursor, NULL, lx, ly);
|
||||||
|
+ motionnotify(0, NULL, 0, 0, 0, 0);
|
||||||
|
+
|
||||||
|
+ wlr_seat_pointer_notify_button(seat, event->time_msec,
|
||||||
|
+ BTN_LEFT, WL_POINTER_BUTTON_STATE_PRESSED);
|
||||||
|
+ wlr_seat_pointer_notify_frame(seat);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void
|
||||||
|
+touchup(struct wl_listener *listener, void *data)
|
||||||
|
+{
|
||||||
|
+ struct wlr_touch_up_event *event = data;
|
||||||
|
+
|
||||||
|
+ if (!wlr_seat_touch_get_point(seat, event->touch_id))
|
||||||
|
+ return;
|
||||||
|
+
|
||||||
|
+ wlr_seat_touch_notify_up(seat, event->time_msec, event->touch_id);
|
||||||
|
+
|
||||||
|
+ // Always send click release
|
||||||
|
+ wlr_seat_pointer_notify_button(seat, event->time_msec,
|
||||||
|
+ BTN_LEFT, WL_POINTER_BUTTON_STATE_RELEASED);
|
||||||
|
+ wlr_seat_pointer_notify_frame(seat);
|
||||||
|
+
|
||||||
|
+ wlr_idle_notifier_v1_notify_activity(idle_notifier, seat);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void
|
||||||
|
+touchframe(struct wl_listener *listener, void *data)
|
||||||
|
+{
|
||||||
|
+ wlr_seat_touch_notify_frame(seat);
|
||||||
|
+ wlr_idle_notifier_v1_notify_activity(idle_notifier, seat);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void
|
||||||
|
+touchmotion(struct wl_listener *listener, void *data)
|
||||||
|
+{
|
||||||
|
+ struct wlr_touch_motion_event *event = data;
|
||||||
|
+ double lx, ly;
|
||||||
|
+ double sx, sy;
|
||||||
|
+ struct wlr_surface *surface;
|
||||||
|
+ Client *c = NULL;
|
||||||
|
+
|
||||||
|
+ if (!wlr_seat_touch_get_point(seat, event->touch_id)) {
|
||||||
|
+ return;
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
+ wlr_cursor_absolute_to_layout_coords(cursor, &event->touch->base, event->x, event->y, &lx, &ly);
|
||||||
|
+ wlr_cursor_warp_closest(cursor, NULL, lx, ly);
|
||||||
|
+ motionnotify(0, NULL, 0, 0, 0, 0);
|
||||||
|
+ wlr_seat_pointer_notify_frame(seat);
|
||||||
|
+
|
||||||
|
+ xytonode(lx, ly, &surface, &c, NULL, &sx, &sy);
|
||||||
|
+
|
||||||
|
+ if (c != NULL && surface != NULL) {
|
||||||
|
+ if (sloppyfocus)
|
||||||
|
+ focusclient(c, 0);
|
||||||
|
+ wlr_seat_touch_point_focus(seat, surface, event->time_msec, event->touch_id, sx, sy);
|
||||||
|
+ } else {
|
||||||
|
+ if (sloppyfocus)
|
||||||
|
+ focusclient(NULL, 0);
|
||||||
|
+ wlr_seat_touch_point_clear_focus(seat, event->time_msec, event->touch_id);
|
||||||
|
+ }
|
||||||
|
+ wlr_seat_touch_notify_motion(seat, event->time_msec, event->touch_id, sx, sy);
|
||||||
|
+
|
||||||
|
+ wlr_idle_notifier_v1_notify_activity(idle_notifier, seat);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+
|
||||||
|
void
|
||||||
|
unlocksession(struct wl_listener *listener, void *data)
|
||||||
|
{
|
||||||
@@ -3,10 +3,11 @@ Adds (inner) gaps between client windows and (outer) gaps between windows and
|
|||||||
the screen edge in a flexible manner.
|
the screen edge in a flexible manner.
|
||||||
|
|
||||||
### Download
|
### Download
|
||||||
- [git branch](https://codeberg.org/sevz/dwl/src/branch/vanitygaps)
|
|
||||||
- [main 2025-01-20](/dwl/dwl-patches/raw/branch/main/patches/vanitygaps/vanitygaps.patch)
|
- [main 2025-01-20](/dwl/dwl-patches/raw/branch/main/patches/vanitygaps/vanitygaps.patch)
|
||||||
- [vanitygaps-0.7.patch](/dwl/dwl-patches/raw/branch/main/patches/vanitygaps/vanitygaps-0.7.patch)
|
- [vanitygaps-0.7.patch](/dwl/dwl-patches/raw/branch/main/patches/vanitygaps/vanitygaps-0.7.patch)
|
||||||
|
- [vanitygaps-0.8.patch](/dwl/dwl-patches/raw/branch/main/patches/vanitygaps/vanitygaps-0.8.patch)
|
||||||
|
|
||||||
### Authors
|
### Authors
|
||||||
|
- [nshan651](https://codeberg.org/nshan651)
|
||||||
- [sevz](https://codeberg.org/sevz)
|
- [sevz](https://codeberg.org/sevz)
|
||||||
- [Bonicgamer](https://github.com/Bonicgamer)
|
- [Bonicgamer](https://github.com/Bonicgamer)
|
||||||
|
|||||||
@@ -0,0 +1,354 @@
|
|||||||
|
From 826adff70b94a402847d6d374a3c4ddca74d7175 Mon Sep 17 00:00:00 2001
|
||||||
|
From: nshan651 <nshan651@proton.me>
|
||||||
|
Date: Thu, 18 Jun 2026 22:17:54 -0500
|
||||||
|
Subject: [PATCH 1/2] vanitygaps v0.8 patch
|
||||||
|
|
||||||
|
---
|
||||||
|
config.def.h | 21 ++++++++
|
||||||
|
dwl.c | 150 +++++++++++++++++++++++++++++++++++++++++++++++----
|
||||||
|
2 files changed, 161 insertions(+), 10 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/config.def.h b/config.def.h
|
||||||
|
index 8a6eda0..980c147 100644
|
||||||
|
--- a/config.def.h
|
||||||
|
+++ b/config.def.h
|
||||||
|
@@ -6,7 +6,12 @@
|
||||||
|
/* appearance */
|
||||||
|
static const int sloppyfocus = 1; /* focus follows mouse */
|
||||||
|
static const int bypass_surface_visibility = 0; /* 1 means idle inhibitors will disable idle tracking even if it's surface isn't visible */
|
||||||
|
+static const int smartgaps = 0; /* 1 means no outer gap when there is only one window */
|
||||||
|
static const unsigned int borderpx = 1; /* border pixel of windows */
|
||||||
|
+static const unsigned int gappih = 10; /* horiz inner gap between windows */
|
||||||
|
+static const unsigned int gappiv = 10; /* vert inner gap between windows */
|
||||||
|
+static const unsigned int gappoh = 10; /* horiz outer gap between windows and screen edge */
|
||||||
|
+static const unsigned int gappov = 10; /* vert outer gap between windows and screen edge */
|
||||||
|
static const float rootcolor[] = COLOR(0x222222ff);
|
||||||
|
static const float bordercolor[] = COLOR(0x444444ff);
|
||||||
|
static const float focuscolor[] = COLOR(0x005577ff);
|
||||||
|
@@ -129,6 +134,22 @@ static const Key keys[] = {
|
||||||
|
{ MODKEY, XKB_KEY_d, incnmaster, {.i = -1} },
|
||||||
|
{ MODKEY, XKB_KEY_h, setmfact, {.f = -0.05f} },
|
||||||
|
{ MODKEY, XKB_KEY_l, setmfact, {.f = +0.05f} },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO, XKB_KEY_h, incgaps, {.i = +1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO, XKB_KEY_l, incgaps, {.i = -1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO|WLR_MODIFIER_SHIFT, XKB_KEY_H, incogaps, {.i = +1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO|WLR_MODIFIER_SHIFT, XKB_KEY_L, incogaps, {.i = -1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO|WLR_MODIFIER_CTRL, XKB_KEY_h, incigaps, {.i = +1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO|WLR_MODIFIER_CTRL, XKB_KEY_l, incigaps, {.i = -1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO, XKB_KEY_0, togglegaps, {0} },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO|WLR_MODIFIER_SHIFT, XKB_KEY_parenright,defaultgaps, {0} },
|
||||||
|
+ { MODKEY, XKB_KEY_y, incihgaps, {.i = +1 } },
|
||||||
|
+ { MODKEY, XKB_KEY_o, incihgaps, {.i = -1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_CTRL, XKB_KEY_y, incivgaps, {.i = +1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_CTRL, XKB_KEY_o, incivgaps, {.i = -1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO, XKB_KEY_y, incohgaps, {.i = +1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_LOGO, XKB_KEY_o, incohgaps, {.i = -1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Y, incovgaps, {.i = +1 } },
|
||||||
|
+ { MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_O, incovgaps, {.i = -1 } },
|
||||||
|
{ MODKEY, XKB_KEY_Return, zoom, {0} },
|
||||||
|
{ MODKEY, XKB_KEY_Tab, view, {0} },
|
||||||
|
{ MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_c, killclient, {0} },
|
||||||
|
diff --git a/dwl.c b/dwl.c
|
||||||
|
index 44f3ad9..6af921a 100644
|
||||||
|
--- a/dwl.c
|
||||||
|
+++ b/dwl.c
|
||||||
|
@@ -197,6 +197,10 @@ struct Monitor {
|
||||||
|
struct wlr_box w; /* window area, layout-relative */
|
||||||
|
struct wl_list layers[4]; /* LayerSurface.link */
|
||||||
|
const Layout *lt[2];
|
||||||
|
+ int gappih; /* horizontal gap between windows */
|
||||||
|
+ int gappiv; /* vertical gap between windows */
|
||||||
|
+ int gappoh; /* horizontal outer gaps */
|
||||||
|
+ int gappov; /* vertical outer gaps */
|
||||||
|
unsigned int seltags;
|
||||||
|
unsigned int sellt;
|
||||||
|
uint32_t tagset[2];
|
||||||
|
@@ -271,6 +275,7 @@ static void createpopup(struct wl_listener *listener, void *data);
|
||||||
|
static void cursorconstrain(struct wlr_pointer_constraint_v1 *constraint);
|
||||||
|
static void cursorframe(struct wl_listener *listener, void *data);
|
||||||
|
static void cursorwarptohint(void);
|
||||||
|
+static void defaultgaps(const Arg *arg);
|
||||||
|
static void destroydecoration(struct wl_listener *listener, void *data);
|
||||||
|
static void destroydragicon(struct wl_listener *listener, void *data);
|
||||||
|
static void destroyidleinhibitor(struct wl_listener *listener, void *data);
|
||||||
|
@@ -290,6 +295,13 @@ static void fullscreennotify(struct wl_listener *listener, void *data);
|
||||||
|
static void gpureset(struct wl_listener *listener, void *data);
|
||||||
|
static void handlesig(int signo);
|
||||||
|
static void incnmaster(const Arg *arg);
|
||||||
|
+static void incgaps(const Arg *arg);
|
||||||
|
+static void incigaps(const Arg *arg);
|
||||||
|
+static void incihgaps(const Arg *arg);
|
||||||
|
+static void incivgaps(const Arg *arg);
|
||||||
|
+static void incogaps(const Arg *arg);
|
||||||
|
+static void incohgaps(const Arg *arg);
|
||||||
|
+static void incovgaps(const Arg *arg);
|
||||||
|
static void inputdevice(struct wl_listener *listener, void *data);
|
||||||
|
static int keybinding(uint32_t mods, xkb_keysym_t sym);
|
||||||
|
static void keypress(struct wl_listener *listener, void *data);
|
||||||
|
@@ -323,6 +335,7 @@ static void setcursor(struct wl_listener *listener, void *data);
|
||||||
|
static void setcursorshape(struct wl_listener *listener, void *data);
|
||||||
|
static void setfloating(Client *c, int floating);
|
||||||
|
static void setfullscreen(Client *c, int fullscreen);
|
||||||
|
+static void setgaps(int oh, int ov, int ih, int iv);
|
||||||
|
static void setlayout(const Arg *arg);
|
||||||
|
static void setmfact(const Arg *arg);
|
||||||
|
static void setmon(Client *c, Monitor *m, uint32_t newtags);
|
||||||
|
@@ -336,6 +349,7 @@ static void tagmon(const Arg *arg);
|
||||||
|
static void tile(Monitor *m);
|
||||||
|
static void togglefloating(const Arg *arg);
|
||||||
|
static void togglefullscreen(const Arg *arg);
|
||||||
|
+static void togglegaps(const Arg *arg);
|
||||||
|
static void toggletag(const Arg *arg);
|
||||||
|
static void toggleview(const Arg *arg);
|
||||||
|
static void unlocksession(struct wl_listener *listener, void *data);
|
||||||
|
@@ -406,6 +420,8 @@ static struct wlr_box sgeom;
|
||||||
|
static struct wl_list mons;
|
||||||
|
static Monitor *selmon;
|
||||||
|
|
||||||
|
+static int enablegaps = 1; /* enables gaps, used by togglegaps */
|
||||||
|
+
|
||||||
|
/* global event handlers */
|
||||||
|
static struct wl_listener cursor_axis = {.notify = axisnotify};
|
||||||
|
static struct wl_listener cursor_button = {.notify = buttonpress};
|
||||||
|
@@ -1055,6 +1071,11 @@ createmon(struct wl_listener *listener, void *data)
|
||||||
|
for (i = 0; i < LENGTH(m->layers); i++)
|
||||||
|
wl_list_init(&m->layers[i]);
|
||||||
|
|
||||||
|
+ m->gappih = gappih;
|
||||||
|
+ m->gappiv = gappiv;
|
||||||
|
+ m->gappoh = gappoh;
|
||||||
|
+ m->gappov = gappov;
|
||||||
|
+
|
||||||
|
wlr_output_state_init(&state);
|
||||||
|
/* Initialize monitor state using configured rules */
|
||||||
|
m->tagset[0] = m->tagset[1] = 1;
|
||||||
|
@@ -1237,6 +1258,12 @@ cursorwarptohint(void)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
+void
|
||||||
|
+defaultgaps(const Arg *arg)
|
||||||
|
+{
|
||||||
|
+ setgaps(gappoh, gappov, gappih, gappiv);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void
|
||||||
|
destroydecoration(struct wl_listener *listener, void *data)
|
||||||
|
{
|
||||||
|
@@ -1575,6 +1602,83 @@ incnmaster(const Arg *arg)
|
||||||
|
arrange(selmon);
|
||||||
|
}
|
||||||
|
|
||||||
|
+void
|
||||||
|
+incgaps(const Arg *arg)
|
||||||
|
+{
|
||||||
|
+ setgaps(
|
||||||
|
+ selmon->gappoh + arg->i,
|
||||||
|
+ selmon->gappov + arg->i,
|
||||||
|
+ selmon->gappih + arg->i,
|
||||||
|
+ selmon->gappiv + arg->i
|
||||||
|
+ );
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void
|
||||||
|
+incigaps(const Arg *arg)
|
||||||
|
+{
|
||||||
|
+ setgaps(
|
||||||
|
+ selmon->gappoh,
|
||||||
|
+ selmon->gappov,
|
||||||
|
+ selmon->gappih + arg->i,
|
||||||
|
+ selmon->gappiv + arg->i
|
||||||
|
+ );
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void
|
||||||
|
+incihgaps(const Arg *arg)
|
||||||
|
+{
|
||||||
|
+ setgaps(
|
||||||
|
+ selmon->gappoh,
|
||||||
|
+ selmon->gappov,
|
||||||
|
+ selmon->gappih + arg->i,
|
||||||
|
+ selmon->gappiv
|
||||||
|
+ );
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void
|
||||||
|
+incivgaps(const Arg *arg)
|
||||||
|
+{
|
||||||
|
+ setgaps(
|
||||||
|
+ selmon->gappoh,
|
||||||
|
+ selmon->gappov,
|
||||||
|
+ selmon->gappih,
|
||||||
|
+ selmon->gappiv + arg->i
|
||||||
|
+ );
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void
|
||||||
|
+incogaps(const Arg *arg)
|
||||||
|
+{
|
||||||
|
+ setgaps(
|
||||||
|
+ selmon->gappoh + arg->i,
|
||||||
|
+ selmon->gappov + arg->i,
|
||||||
|
+ selmon->gappih,
|
||||||
|
+ selmon->gappiv
|
||||||
|
+ );
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void
|
||||||
|
+incohgaps(const Arg *arg)
|
||||||
|
+{
|
||||||
|
+ setgaps(
|
||||||
|
+ selmon->gappoh + arg->i,
|
||||||
|
+ selmon->gappov,
|
||||||
|
+ selmon->gappih,
|
||||||
|
+ selmon->gappiv
|
||||||
|
+ );
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+void
|
||||||
|
+incovgaps(const Arg *arg)
|
||||||
|
+{
|
||||||
|
+ setgaps(
|
||||||
|
+ selmon->gappoh,
|
||||||
|
+ selmon->gappov + arg->i,
|
||||||
|
+ selmon->gappih,
|
||||||
|
+ selmon->gappiv
|
||||||
|
+ );
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void
|
||||||
|
inputdevice(struct wl_listener *listener, void *data)
|
||||||
|
{
|
||||||
|
@@ -2368,6 +2472,16 @@ setfullscreen(Client *c, int fullscreen)
|
||||||
|
printstatus();
|
||||||
|
}
|
||||||
|
|
||||||
|
+void
|
||||||
|
+setgaps(int oh, int ov, int ih, int iv)
|
||||||
|
+{
|
||||||
|
+ selmon->gappoh = MAX(oh, 0);
|
||||||
|
+ selmon->gappov = MAX(ov, 0);
|
||||||
|
+ selmon->gappih = MAX(ih, 0);
|
||||||
|
+ selmon->gappiv = MAX(iv, 0);
|
||||||
|
+ arrange(selmon);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void
|
||||||
|
setlayout(const Arg *arg)
|
||||||
|
{
|
||||||
|
@@ -2712,7 +2826,7 @@ tagmon(const Arg *arg)
|
||||||
|
void
|
||||||
|
tile(Monitor *m)
|
||||||
|
{
|
||||||
|
- unsigned int mw, my, ty;
|
||||||
|
+ unsigned int mw, my, ty, h, r, oe = enablegaps, ie = enablegaps;
|
||||||
|
int i, n = 0;
|
||||||
|
Client *c;
|
||||||
|
|
||||||
|
@@ -2722,22 +2836,31 @@ tile(Monitor *m)
|
||||||
|
if (n == 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
+ if (smartgaps == n) {
|
||||||
|
+ oe = 0; // outer gaps disabled
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
if (n > m->nmaster)
|
||||||
|
- mw = m->nmaster ? (int)roundf(m->w.width * m->mfact) : 0;
|
||||||
|
+ mw = m->nmaster ? (int)roundf((m->w.width + m->gappiv*ie) * m->mfact) : 0;
|
||||||
|
else
|
||||||
|
- mw = m->w.width;
|
||||||
|
- i = my = ty = 0;
|
||||||
|
+ mw = m->w.width - 2*m->gappov*oe + m->gappiv*ie;
|
||||||
|
+ i = 0;
|
||||||
|
+ my = ty = m->gappoh*oe;
|
||||||
|
wl_list_for_each(c, &clients, link) {
|
||||||
|
if (!VISIBLEON(c, m) || c->isfloating || c->isfullscreen)
|
||||||
|
continue;
|
||||||
|
if (i < m->nmaster) {
|
||||||
|
- resize(c, (struct wlr_box){.x = m->w.x, .y = m->w.y + my, .width = mw,
|
||||||
|
- .height = (m->w.height - my) / (MIN(n, m->nmaster) - i)}, 0);
|
||||||
|
- my += c->geom.height;
|
||||||
|
+ r = MIN(n, m->nmaster) - i;
|
||||||
|
+ h = (m->w.height - my - m->gappoh*oe - m->gappih*ie * (r - 1)) / r;
|
||||||
|
+ resize(c, (struct wlr_box){.x = m->w.x + m->gappov*oe, .y = m->w.y + my,
|
||||||
|
+ .width = mw - m->gappiv*ie, .height = h}, 0);
|
||||||
|
+ my += c->geom.height + m->gappih*ie;
|
||||||
|
} else {
|
||||||
|
- resize(c, (struct wlr_box){.x = m->w.x + mw, .y = m->w.y + ty,
|
||||||
|
- .width = m->w.width - mw, .height = (m->w.height - ty) / (n - i)}, 0);
|
||||||
|
- ty += c->geom.height;
|
||||||
|
+ r = n - i;
|
||||||
|
+ h = (m->w.height - ty - m->gappoh*oe - m->gappih*ie * (r - 1)) / r;
|
||||||
|
+ resize(c, (struct wlr_box){.x = m->w.x + mw + m->gappov*oe, .y = m->w.y + ty,
|
||||||
|
+ .width = m->w.width - mw - 2*m->gappov*oe, .height = h}, 0);
|
||||||
|
+ ty += c->geom.height + m->gappih*ie;
|
||||||
|
}
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
@@ -2760,6 +2883,13 @@ togglefullscreen(const Arg *arg)
|
||||||
|
setfullscreen(sel, !sel->isfullscreen);
|
||||||
|
}
|
||||||
|
|
||||||
|
+void
|
||||||
|
+togglegaps(const Arg *arg)
|
||||||
|
+{
|
||||||
|
+ enablegaps = !enablegaps;
|
||||||
|
+ arrange(selmon);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
void
|
||||||
|
toggletag(const Arg *arg)
|
||||||
|
{
|
||||||
|
--
|
||||||
|
2.52.0
|
||||||
|
|
||||||
|
|
||||||
|
From 8b9db986eddeade22d92fb15a8c836912869be29 Mon Sep 17 00:00:00 2001
|
||||||
|
From: =?UTF-8?q?Leonardo=20Hern=C3=A1ndez=20Hern=C3=A1ndez?=
|
||||||
|
<leohdz172@protonmail.com>
|
||||||
|
Date: Wed, 20 Jul 2022 00:15:32 -0500
|
||||||
|
Subject: [PATCH 2/2] allow gaps in monocle layout if requested
|
||||||
|
MIME-Version: 1.0
|
||||||
|
Content-Type: text/plain; charset=UTF-8
|
||||||
|
Content-Transfer-Encoding: 8bit
|
||||||
|
|
||||||
|
Signed-off-by: Leonardo Hernández Hernández <leohdz172@proton.me>
|
||||||
|
---
|
||||||
|
config.def.h | 1 +
|
||||||
|
dwl.c | 6 +++++-
|
||||||
|
2 files changed, 6 insertions(+), 1 deletion(-)
|
||||||
|
|
||||||
|
diff --git a/config.def.h b/config.def.h
|
||||||
|
index 980c147..10b9054 100644
|
||||||
|
--- a/config.def.h
|
||||||
|
+++ b/config.def.h
|
||||||
|
@@ -7,6 +7,7 @@
|
||||||
|
static const int sloppyfocus = 1; /* focus follows mouse */
|
||||||
|
static const int bypass_surface_visibility = 0; /* 1 means idle inhibitors will disable idle tracking even if it's surface isn't visible */
|
||||||
|
static const int smartgaps = 0; /* 1 means no outer gap when there is only one window */
|
||||||
|
+static const int monoclegaps = 0; /* 1 means outer gaps in monocle layout */
|
||||||
|
static const unsigned int borderpx = 1; /* border pixel of windows */
|
||||||
|
static const unsigned int gappih = 10; /* horiz inner gap between windows */
|
||||||
|
static const unsigned int gappiv = 10; /* vert inner gap between windows */
|
||||||
|
diff --git a/dwl.c b/dwl.c
|
||||||
|
index 6af921a..144dd78 100644
|
||||||
|
--- a/dwl.c
|
||||||
|
+++ b/dwl.c
|
||||||
|
@@ -1933,8 +1933,12 @@ monocle(Monitor *m)
|
||||||
|
wl_list_for_each(c, &clients, link) {
|
||||||
|
if (!VISIBLEON(c, m) || c->isfloating || c->isfullscreen)
|
||||||
|
continue;
|
||||||
|
- resize(c, m->w, 0);
|
||||||
|
n++;
|
||||||
|
+ if (!monoclegaps)
|
||||||
|
+ resize(c, m->w, 0);
|
||||||
|
+ else
|
||||||
|
+ resize(c, (struct wlr_box){.x = m->w.x + gappoh, .y = m->w.y + gappov,
|
||||||
|
+ .width = m->w.width - 2 * gappoh, .height = m->w.height - 2 * gappov}, 0);
|
||||||
|
}
|
||||||
|
if (n)
|
||||||
|
snprintf(m->ltsymbol, LENGTH(m->ltsymbol), "[%d]", n);
|
||||||
|
--
|
||||||
|
2.52.0
|
||||||
|
|
||||||
@@ -9,8 +9,9 @@ This patch comes in **two versions**:
|
|||||||
- **`zerotag.patch`** - No dependencies.
|
- **`zerotag.patch`** - No dependencies.
|
||||||
|
|
||||||
### Download
|
### Download
|
||||||
- [git branch](https://codeberg.org/6z7y/dwl-patches/raw/branch/main/patches/zerotag/zerotag.patch)
|
- [git branch](https://codeberg.org/6z7y/dwl-patches/raw/branch/zerotag/patches/zerotag/zerotag.patch)
|
||||||
- [main 2026-02-25](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/zerotag/zerotag.patch)
|
- [main 2026-02-25](https://codeberg.org/dwl/dwl-patches/raw/branch/main/patches/zerotag/zerotag.patch)
|
||||||
|
|
||||||
### Authors
|
### Authors
|
||||||
- [6z7y](https://codeberg.org/6z7y)
|
- [6z7y](https://codeberg.org/6z7y)
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user