[wiki] [sites] [dwm][patch][tag preview] add See the contents of a tag by hovering on it. || explosion-mental

From: <git_AT_suckless.org>
Date: Thu, 12 Aug 2021 06:14:33 +0200

commit ea1f3406af87ecd227a6e9a2ca41ed6180309c7b
Author: explosion-mental <explosion0mental_AT_gmail.com>
Date: Wed Aug 11 23:10:47 2021 -0500

    [dwm][patch][tag preview] add
    See the contents of a tag by hovering on it.

diff --git a/dwm.suckless.org/patches/tag-previews/dwm-tag-preview-6.2.diff b/dwm.suckless.org/patches/tag-previews/dwm-tag-preview-6.2.diff
new file mode 100644
index 00000000..d33084dc
--- /dev/null
+++ b/dwm.suckless.org/patches/tag-previews/dwm-tag-preview-6.2.diff
_AT_@ -0,0 +1,318 @@
+From 7381bf4e11b76ad8f51c94bd226296bf971ad430 Mon Sep 17 00:00:00 2001
+From: explosion-mental <explosion0mental_AT_gmail.com>
+Date: Wed, 11 Aug 2021 17:28:32 -0500
+Subject: [PATCH] Tag preview This is a patch extracted from
+ https://github.com/siduck76/chadwm build. First view a tag with at least a
+ client, then move to any other tag. Finally hover you mouse over the tag you
+ were previously and you got a tag preview.
+
+---
+ config.def.h | 1 +
+ config.mk | 5 +-
+ dwm.c | 157 +++++++++++++++++++++++++++++++++++++++++++--------
+ 3 files changed, 140 insertions(+), 23 deletions(-)
+
+diff --git a/config.def.h b/config.def.h
+index 1c0b587..81a3d3d 100644
+--- a/config.def.h
++++ b/config.def.h
+_AT_@ -3,6 +3,7 @@
+ /* appearance */
+ static const unsigned int borderpx = 1; /* border pixel of windows */
+ static const unsigned int snap = 32; /* snap pixel */
++static const int scalepreview = 4; /* Tag preview scaling */
+ static const int showbar = 1; /* 0 means no bar */
+ static const int topbar = 1; /* 0 means bottom bar */
+ static const char *fonts[] = { "monospace:size=10" };
+diff --git a/config.mk b/config.mk
+index 6d36cb7..70b2a3a 100644
+--- a/config.mk
++++ b/config.mk
+_AT_@ -20,9 +20,12 @@ FREETYPEINC = /usr/include/freetype2
+ # OpenBSD (uncomment)
+ #FREETYPEINC = ${X11INC}/freetype2
+
++# Tag previews are done with Imlib2
++IMLIB2LIBS = -lImlib2
++
+ # includes and libs
+ INCS = -I${X11INC} -I${FREETYPEINC}
+-LIBS = -L${X11LIB} -lX11 ${XINERAMALIBS} ${FREETYPELIBS}
++LIBS = -L${X11LIB} -lX11 ${XINERAMALIBS} ${FREETYPELIBS} ${IMLIB2LIBS}
+
+ # flags
+ CPPFLAGS = -D_DEFAULT_SOURCE -D_BSD_SOURCE -D_POSIX_C_SOURCE=2 -DVERSION=\"${VERSION}\" ${XINERAMAFLAGS}
+diff --git a/dwm.c b/dwm.c
+index 4465af1..aafdccc 100644
+--- a/dwm.c
++++ b/dwm.c
+_AT_@ -40,6 +40,7 @@
+ #include <X11/extensions/Xinerama.h>
+ #endif /* XINERAMA */
+ #include <X11/Xft/Xft.h>
++#include <Imlib2.h>
+
+ #include "drw.h"
+ #include "util.h"
+_AT_@ -111,27 +112,6 @@ typedef struct {
+ void (*arrange)(Monitor *);
+ } Layout;
+
+-struct Monitor {
+- char ltsymbol[16];
+- float mfact;
+- int nmaster;
+- int num;
+- int by; /* bar geometry */
+- int mx, my, mw, mh; /* screen size */
+- int wx, wy, ww, wh; /* window area */
+- unsigned int seltags;
+- unsigned int sellt;
+- unsigned int tagset[2];
+- int showbar;
+- int topbar;
+- Client *clients;
+- Client *sel;
+- Client *stack;
+- Monitor *next;
+- Window barwin;
+- const Layout *lt[2];
+-};
+-
+ typedef struct {
+ const char *class;
+ const char *instance;
+_AT_@ -204,8 +184,10 @@ static void setmfact(const Arg *arg);
+ static void setup(void);
+ static void seturgent(Client *c, int urg);
+ static void showhide(Client *c);
++static void showtagpreview(int tag);
+ static void sigchld(int unused);
+ static void spawn(const Arg *arg);
++static void switchtag(void);
+ static void tag(const Arg *arg);
+ static void tagmon(const Arg *arg);
+ static void tile(Monitor *);
+_AT_@ -224,6 +206,7 @@ static void updatenumlockmask(void);
+ static void updatesizehints(Client *c);
+ static void updatestatus(void);
+ static void updatetitle(Client *c);
++static void updatepreview(void);
+ static void updatewindowtype(Client *c);
+ static void updatewmhints(Client *c);
+ static void view(const Arg *arg);
+_AT_@ -271,6 +254,31 @@ static Window root, wmcheckwin;
+ /* configuration, allows nested code to access above variables */
+ #include "config.h"
+
++struct Monitor {
++ char ltsymbol[16];
++ float mfact;
++ int nmaster;
++ int num;
++ int by; /* bar geometry */
++ int mx, my, mw, mh; /* screen size */
++ int wx, wy, ww, wh; /* window area */
++ unsigned int seltags;
++ unsigned int sellt;
++ unsigned int tagset[2];
++ int showbar;
++ int topbar;
++ Client *clients;
++ Client *sel;
++ Client *stack;
++ Monitor *next;
++ Window barwin;
++ Window tagwin;
++ int previewshow;
++ Pixmap tagmap[LENGTH(tags)];
++ const Layout *lt[2];
++};
++
++
+ /* compile-time check if all tags fit into an unsigned int bit array. */
+ struct NumTags { char limitexceeded[LENGTH(tags) > 31 ? -1 : 1]; };
+
+_AT_@ -430,6 +438,10 @@ buttonpress(XEvent *e)
+ focus(NULL);
+ }
+ if (ev->window == selmon->barwin) {
++ if (selmon->previewshow) {
++ XUnmapWindow(dpy, selmon->tagwin);
++ selmon->previewshow = 0;
++ }
+ i = x = 0;
+ do
+ x += TEXTW(tags[i]);
+_AT_@ -504,8 +516,13 @@ cleanupmon(Monitor *mon)
+ for (m = mons; m && m->next != mon; m = m->next);
+ m->next = mon->next;
+ }
++ for (size_t i = 0; i < LENGTH(tags); i++)
++ if (mon->tagmap[i])
++ XFreePixmap(dpy, mon->tagmap[i]);
+ XUnmapWindow(dpy, mon->barwin);
+ XDestroyWindow(dpy, mon->barwin);
++ XUnmapWindow(dpy, mon->tagwin);
++ XDestroyWindow(dpy, mon->tagwin);
+ free(mon);
+ }
+
+_AT_@ -1121,7 +1138,31 @@ motionnotify(XEvent *e)
+ static Monitor *mon = NULL;
+ Monitor *m;
+ XMotionEvent *ev = &e->xmotion;
++ unsigned int i, x;
++
++ if (ev->window == selmon->barwin) {
++ i = x = 0;
++ do
++ x += TEXTW(tags[i]);
++ while (ev->x >= x && ++i < LENGTH(tags));
+
++ if (i < LENGTH(tags)) {
++ if ((i + 1) != selmon->previewshow && !(selmon->tagset[selmon->seltags] & 1 << i)) {
++ selmon->previewshow = i + 1;
++ showtagpreview(i);
++ }
++ else if (selmon->tagset[selmon->seltags] & 1 << i) {
++ selmon->previewshow = 0;
++ showtagpreview(0);
++ }
++ } else if (selmon->previewshow != 0) {
++ selmon->previewshow = 0;
++ showtagpreview(0);
++ }
++ } else if (selmon->previewshow != 0) {
++ selmon->previewshow = 0;
++ showtagpreview(0);
++ }
+ if (ev->window != root)
+ return;
+ if ((m = recttomon(ev->x_root, ev->y_root, 1, 1)) != mon && mon) {
+_AT_@ -1573,6 +1614,7 @@ setup(void)
+ /* init bars */
+ updatebars();
+ updatestatus();
++ updatepreview();
+ /* supporting window for NetWMCheck */
+ wmcheckwin = XCreateSimpleWindow(dpy, root, 0, 0, 1, 1, 0, 0, 0);
+ XChangeProperty(dpy, wmcheckwin, netatom[NetWMCheck], XA_WINDOW, 32,
+_AT_@ -1628,6 +1670,23 @@ showhide(Client *c)
+ }
+ }
+
++void
++showtagpreview(int tag)
++{
++ if (!selmon->previewshow) {
++ XUnmapWindow(dpy, selmon->tagwin);
++ return;
++ }
++
++ if (selmon->tagmap[tag]) {
++ XSetWindowBackgroundPixmap(dpy, selmon->tagwin, selmon->tagmap[tag]);
++ XCopyArea(dpy, selmon->tagmap[tag], selmon->tagwin, drw->gc, 0, 0, selmon->mw / scalepreview, selmon->mh / scalepreview, 0, 0);
++ XSync(dpy, False);
++ XMapWindow(dpy, selmon->tagwin);
++ } else
++ XUnmapWindow(dpy, selmon->tagwin);
++}
++
+ void
+ sigchld(int unused)
+ {
+_AT_@ -1652,6 +1711,38 @@ spawn(const Arg *arg)
+ }
+ }
+
++void
++switchtag(void)
++{
++ int i;
++ unsigned int occ = 0;
++ Client *c;
++ Imlib_Image image;
++
++ for (c = selmon->clients; c; c = c->next)
++ occ |= c->tags;
++ for (i = 0; i < LENGTH(tags); i++) {
++ if (selmon->tagset[selmon->seltags] & 1 << i) {
++ if (selmon->tagmap[i] != 0) {
++ XFreePixmap(dpy, selmon->tagmap[i]);
++ selmon->tagmap[i] = 0;
++ }
++ if (occ & 1 << i) {
++ image = imlib_create_image(sw, sh);
++ imlib_context_set_image(image);
++ imlib_context_set_display(dpy);
++ imlib_context_set_visual(DefaultVisual(dpy, screen));
++ imlib_context_set_drawable(RootWindow(dpy, screen));
++ imlib_copy_drawable_to_image(0, selmon->mx, selmon->my, selmon->mw ,selmon->mh, 0, 0, 1);
++ selmon->tagmap[i] = XCreatePixmap(dpy, selmon->tagwin, selmon->mw / scalepreview, selmon->mh / scalepreview, DefaultDepth(dpy, screen));
++ imlib_context_set_drawable(selmon->tagmap[i]);
++ imlib_render_image_part_on_drawable_at_size(0, 0, selmon->mw, selmon->mh, 0, 0, selmon->mw / scalepreview, selmon->mh / scalepreview);
++ imlib_free_image();
++ }
++ }
++ }
++}
++
+ void
+ tag(const Arg *arg)
+ {
+_AT_@ -1740,6 +1831,7 @@ toggleview(const Arg *arg)
+ unsigned int newtagset = selmon->tagset[selmon->seltags] ^ (arg->ui & TAGMASK);
+
+ if (newtagset) {
++ switchtag();
+ selmon->tagset[selmon->seltags] = newtagset;
+ focus(NULL);
+ arrange(selmon);
+_AT_@ -1805,7 +1897,7 @@ updatebars(void)
+ XSetWindowAttributes wa = {
+ .override_redirect = True,
+ .background_pixmap = ParentRelative,
+- .event_mask = ButtonPressMask|ExposureMask
++ .event_mask = ButtonPressMask|ExposureMask|PointerMotionMask
+ };
+ XClassHint ch = {"dwm", "dwm"};
+ for (m = mons; m; m = m->next) {
+_AT_@ -2001,6 +2093,26 @@ updatetitle(Client *c)
+ strcpy(c->name, broken);
+ }
+
++void
++updatepreview(void)
++{
++ Monitor *m;
++
++ XSetWindowAttributes wa = {
++ .override_redirect = True,
++ .background_pixmap = ParentRelative,
++ .event_mask = ButtonPressMask|ExposureMask
++ };
++ for (m = mons; m; m = m->next) {
++ m->tagwin = XCreateWindow(dpy, root, m->wx, m->by + bh, m->mw / 4, m->mh / 4, 0,
++ DefaultDepth(dpy, screen), CopyFromParent, DefaultVisual(dpy, screen),
++ CWOverrideRedirect|CWBackPixmap|CWEventMask, &wa);
++ XDefineCursor(dpy, m->tagwin, cursor[CurNormal]->cursor);
++ XMapRaised(dpy, m->tagwin);
++ XUnmapWindow(dpy, m->tagwin);
++ }
++}
++
+ void
+ updatewindowtype(Client *c)
+ {
+_AT_@ -2037,6 +2149,7 @@ view(const Arg *arg)
+ {
+ if ((arg->ui & TAGMASK) == selmon->tagset[selmon->seltags])
+ return;
++ switchtag();
+ selmon->seltags ^= 1; /* toggle sel tagset */
+ if (arg->ui & TAGMASK)
+ selmon->tagset[selmon->seltags] = arg->ui & TAGMASK;
+--
+2.32.0
+
diff --git a/dwm.suckless.org/patches/tag-previews/index.md b/dwm.suckless.org/patches/tag-previews/index.md
new file mode 100644
index 00000000..2e3fc7d1
--- /dev/null
+++ b/dwm.suckless.org/patches/tag-previews/index.md
_AT_@ -0,0 +1,22 @@
+tag previews
+================
+
+Description
+-----------
+Allows you to see the contents of an already viewed tag. So a more accurate
+description would be to re-view a tag. This patch is extracted from
+https://github.com/siduck76/chadwm. Keep in mind that this uses Imlib2, which
+on the diff is already put on.
+
+
+![screenshot](screenshot.png)
+
+
+Download
+--------
+* [dwm-tag-preview-6.2.diff](dwm-tag-preview-6.2.diff)
+* [Github mirror](https://github.com/explosion-mental/Dwm/blob/main/Patches/dwm-tag-preview-6.2.diff)
+
+Authors
+-------
+* explosion-mental - <explosion0mental_AT_gmail.com>
diff --git a/dwm.suckless.org/patches/tag-previews/screenshot.png b/dwm.suckless.org/patches/tag-previews/screenshot.png
new file mode 100644
index 00000000..2ffa8ef2
Binary files /dev/null and b/dwm.suckless.org/patches/tag-previews/screenshot.png differ
Received on Thu Aug 12 2021 - 06:14:33 CEST

This archive was generated by hypermail 2.3.0 : Thu Aug 12 2021 - 06:24:42 CEST