From 11ab11d59ef4b2b1616943b980bb90e972d7be72 Mon Sep 17 00:00:00 2001 From: Charlie Root Date: Tue, 23 Apr 2024 10:59:57 +0200 Subject: [PATCH] fixed fonts, added newsboat --- hosts/vali/mars/configuration.nix | 19 +- hosts/vali/mars/dwm/default.nix | 0 hosts/vali/mars/dwm/dmenu-5.3/config.h | 2 +- hosts/vali/mars/dwm/dmenu-5.3/dmenu | Bin 42560 -> 42560 bytes hosts/vali/mars/dwm/dmenu-5.3/dmenu.o | Bin 32384 -> 32384 bytes hosts/vali/mars/dwm/dwm-6.5/config.def.h | 7 + hosts/vali/mars/dwm/dwm-6.5/config.h | 36 +- hosts/vali/mars/dwm/dwm-6.5/dwm | Bin 62656 -> 62920 bytes .../dwm-multiple-dynamic-scratchpads.diff | 207 ++ .../dwm-scratchpad-20240321-061e9fe.diff | 105 + hosts/vali/mars/dwm/dwm-6.5/dwm.c | 150 +- hosts/vali/mars/dwm/dwm-6.5/dwm.c.orig | 2207 +++++++++++++++++ hosts/vali/mars/dwm/dwm-6.5/dwm.c.rej | 23 + hosts/vali/mars/dwm/dwm-6.5/dwm.o | Bin 57904 -> 59856 bytes hosts/vali/mars/dwm/dwm.nix | 13 +- hosts/vali/mars/dwm/eww/eww.scss | 0 hosts/vali/mars/dwm/eww/eww.yuck | 0 hosts/vali/mars/programs.nix | 4 +- modules/gui/default.nix | 1 + modules/gui/kitty.nix | 78 + modules/tui/default.nix | 2 +- modules/tui/newsboat.nix | 73 + options/desktop/fonts.nix | 2 +- 23 files changed, 2892 insertions(+), 37 deletions(-) delete mode 100644 hosts/vali/mars/dwm/default.nix create mode 100644 hosts/vali/mars/dwm/dwm-6.5/dwm-multiple-dynamic-scratchpads.diff create mode 100644 hosts/vali/mars/dwm/dwm-6.5/dwm-scratchpad-20240321-061e9fe.diff create mode 100644 hosts/vali/mars/dwm/dwm-6.5/dwm.c.orig create mode 100644 hosts/vali/mars/dwm/dwm-6.5/dwm.c.rej delete mode 100644 hosts/vali/mars/dwm/eww/eww.scss delete mode 100644 hosts/vali/mars/dwm/eww/eww.yuck create mode 100644 modules/gui/kitty.nix create mode 100644 modules/tui/newsboat.nix diff --git a/hosts/vali/mars/configuration.nix b/hosts/vali/mars/configuration.nix index 5bea2c4..0031be2 100644 --- a/hosts/vali/mars/configuration.nix +++ b/hosts/vali/mars/configuration.nix @@ -1,4 +1,4 @@ -{ config, inputs, pkgs, ... }: +{ config, inputs, pkgs, lib, ... }: { nixpkgs.config.allowUnfree = true; # Time Zone @@ -23,7 +23,6 @@ security.sudo.package = pkgs.sudo.override { withInsults = true; }; security.polkit.enable = true; programs.kdeconnect.enable = true; - services.picom.enable = true; services.mpd = { enable = true; musicDirectory = "/home/vali/Nextcloud/Media/Music/"; @@ -35,6 +34,12 @@ } ''; }; +/* options.ui.darkTheme = { + type = lib.types.bool; + default = true; + example = false; + description = "If ui programs should use a dark or light theme"; + };*/ modules = { other = { system = { @@ -49,10 +54,10 @@ }; programs = { vesktop.enable = true; - ncmpcpp.enable = true; ssh.enable = true; btop.enable = true; mpv.enable = true; + kitty.enable = true; dwm.enable = true; schizofox.enable = true; #git = { @@ -66,13 +71,6 @@ enable = true; profiling = false; }; - alacritty = { - enable = true; - catppuccin = true; - opacity = 0.8; - blur = true; - # GrĂ¼sse - }; }; services = { pipewire.enable = true; @@ -106,3 +104,4 @@ }; system.stateVersion = "23.11"; } + diff --git a/hosts/vali/mars/dwm/default.nix b/hosts/vali/mars/dwm/default.nix deleted file mode 100644 index e69de29..0000000 diff --git a/hosts/vali/mars/dwm/dmenu-5.3/config.h b/hosts/vali/mars/dwm/dmenu-5.3/config.h index 687b07c..1edb647 100644 --- a/hosts/vali/mars/dwm/dmenu-5.3/config.h +++ b/hosts/vali/mars/dwm/dmenu-5.3/config.h @@ -4,7 +4,7 @@ static int topbar = 1; /* -b option; if 0, dmenu appears at bottom */ /* -fn option overrides fonts[0]; default X11 font or font set */ static const char *fonts[] = { - "monospace:size=18" + "monospace:size=10" }; static const char *prompt = NULL; /* -p option; prompt to the left of input field */ static const char *colors[SchemeLast][2] = { diff --git a/hosts/vali/mars/dwm/dmenu-5.3/dmenu b/hosts/vali/mars/dwm/dmenu-5.3/dmenu index e47d6461d622e7c3e46a853b9c513ee498f9f3f6..8906fbffc1fddc3401e9a2b3ca90ab0537e36dad 100755 GIT binary patch delta 15 WcmX?bhUvf=rVaKl3V~du?8>z diff --git a/hosts/vali/mars/dwm/dmenu-5.3/dmenu.o b/hosts/vali/mars/dwm/dmenu-5.3/dmenu.o index 693870d44626714aca6da283a423c9b815a3c06b..75e7e0be9078e3e3c70141fc419ae6da5255619b 100644 GIT binary patch delta 16 XcmZqp%h>RjaYGG1qrv7{e&&1tJV*u_ delta 16 XcmZqp%h>RjaYGG1qs8W0e&&1tJa`5o diff --git a/hosts/vali/mars/dwm/dwm-6.5/config.def.h b/hosts/vali/mars/dwm/dwm-6.5/config.def.h index 9efa774..aabd622 100644 --- a/hosts/vali/mars/dwm/dwm-6.5/config.def.h +++ b/hosts/vali/mars/dwm/dwm-6.5/config.def.h @@ -95,6 +95,13 @@ static const Key keys[] = { TAGKEYS( XK_8, 7) TAGKEYS( XK_9, 8) { MODKEY|ShiftMask, XK_q, quit, {0} }, + { MODKEY, XK_s, scratchpad_show, {.i = 1} }, + { MODKEY, XK_y, scratchpad_show, {.i = 2} }, + { MODKEY, XK_u, scratchpad_show, {.i = 3} }, + { MODKEY|ShiftMask, XK_s, scratchpad_hide, {.i = 1} }, + { MODKEY|ShiftMask, XK_y, scratchpad_hide, {.i = 2} }, + { MODKEY|ShiftMask, XK_u, scratchpad_hide, {.i = 3} }, + { MODKEY|ShiftMask, XK_r, scratchpad_remove, {0} }, }; /* button definitions */ diff --git a/hosts/vali/mars/dwm/dwm-6.5/config.h b/hosts/vali/mars/dwm/dwm-6.5/config.h index 647ebed..1e4f2b6 100644 --- a/hosts/vali/mars/dwm/dwm-6.5/config.h +++ b/hosts/vali/mars/dwm/dwm-6.5/config.h @@ -1,21 +1,22 @@ -/* See LICENSE file for copyright and license details. */ + /* appearance */ -static const unsigned int borderpx = 1; /* border pixel of windows */ +static const unsigned int borderpx = 4; /* border pixel of windows */ static const unsigned int snap = 32; /* snap pixel */ -static const int showbar = 1; /* 0 means no bar */ +static const int showbar = 0; /* 0 means no bar */ static const int topbar = 1; /* 0 means bottom bar */ static const char *fonts[] = { "monospace:size=10" }; static const char dmenufont[] = "monospace:size=10"; -static const char col_gray1[] = "#222222"; -static const char col_gray2[] = "#444444"; +static const char col_gray1[] = "#282828"; +static const char col_gray2[] = "#98971a"; static const char col_gray3[] = "#bbbbbb"; -static const char col_gray4[] = "#eeeeee"; -static const char col_cyan[] = "#005577"; +static const char col_gray4[] = "#928374"; +static const char col_cyan[] = "#BD93BD"; +static const char col_sel[] = "#d79921"; static const char *colors[][3] = { /* fg bg border */ - [SchemeNorm] = { col_gray3, col_gray1, col_gray2 }, - [SchemeSel] = { col_gray4, col_cyan, col_cyan }, + [SchemeNorm] = { col_gray2, col_gray1, col_gray4 }, + [SchemeSel] = { col_gray2, col_gray1, col_sel }, }; /* tagging */ @@ -57,14 +58,18 @@ static const Layout layouts[] = { /* commands */ static char dmenumon[2] = "0"; /* component of dmenucmd, manipulated in spawn() */ -static const char *dmenucmd[] = { "dmenu_run", "-m", dmenumon, "-fn", dmenufont, "-nb", col_gray1, "-nf", col_gray3, "-sb", col_cyan, "-sf", col_gray4, NULL }; +static const char *dmenucmd[] = { "rofi", "-show", "drun", NULL }; static const char *termcmd[] = { "kitty", NULL }; +static const char *browsercmd[] = { "tor-browser", NULL }; +static const char *filebrowsercmd[] = { "pcmanfm", NULL }; +static const char *spkeepassxc[] = { "keepassxc", NULL }; static const Key keys[] = { - /* modifier key function argument */ +/* modifier key function argument */ { MODKEY, XK_d, spawn, {.v = dmenucmd } }, { MODKEY, XK_Return, spawn, {.v = termcmd } }, - { MODKEY, XK_b, togglebar, {0} }, + { MODKEY, XK_b, spawn, {.v = browsercmd } }, + { MODKEY, XK_e, spawn, {.v = filebrowsercmd } }, { MODKEY, XK_j, focusstack, {.i = +1 } }, { MODKEY, XK_k, focusstack, {.i = -1 } }, { MODKEY, XK_i, incnmaster, {.i = +1 } }, @@ -85,6 +90,13 @@ static const Key keys[] = { { MODKEY, XK_space, togglefullscr, {0} }, { MODKEY, XK_0, view, {.ui = ~0 } }, { MODKEY|ShiftMask, XK_0, tag, {.ui = ~0 } }, + { MODKEY, XK_s, scratchpad_show, {.i = 1} }, + { MODKEY, XK_y, scratchpad_show, {.i = 2} }, + { MODKEY, XK_p, scratchpad_show, {.i = 3} }, + { MODKEY|ShiftMask, XK_s, scratchpad_hide, {.i = 1} }, + { MODKEY|ShiftMask, XK_y, scratchpad_hide, {.i = 2} }, + { MODKEY|ShiftMask, XK_p, scratchpad_hide, {.i = 3} }, + { MODKEY|ShiftMask, XK_r, scratchpad_remove, {0} }, TAGKEYS( XK_1, 0) TAGKEYS( XK_2, 1) TAGKEYS( XK_3, 2) diff --git a/hosts/vali/mars/dwm/dwm-6.5/dwm b/hosts/vali/mars/dwm/dwm-6.5/dwm index 3952e1f89fa70658d5e11aaa2c07e62b069d2c1a..382a15dc453a6090162ab2d5a8141dd99db6729d 100755 GIT binary patch delta 19772 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 Xt`m15x+?i6Cw(zva(p{^))zGZ7RCQw delta 18326 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 diff --git a/hosts/vali/mars/dwm/dwm-6.5/dwm-multiple-dynamic-scratchpads.diff b/hosts/vali/mars/dwm/dwm-6.5/dwm-multiple-dynamic-scratchpads.diff new file mode 100644 index 0000000..22d0000 --- /dev/null +++ b/hosts/vali/mars/dwm/dwm-6.5/dwm-multiple-dynamic-scratchpads.diff @@ -0,0 +1,207 @@ +diff --git a/config.def.h b/config.def.h +index a2ac963..1c82453 100644 +--- a/config.def.h ++++ b/config.def.h +@@ -95,6 +95,13 @@ static Key keys[] = { + TAGKEYS( XK_8, 7) + TAGKEYS( XK_9, 8) + { MODKEY|ShiftMask, XK_q, quit, {0} }, ++ { MODKEY, XK_s, scratchpad_show, {.i = 1} }, ++ { MODKEY, XK_y, scratchpad_show, {.i = 2} }, ++ { MODKEY, XK_u, scratchpad_show, {.i = 3} }, ++ { MODKEY|ShiftMask, XK_s, scratchpad_hide, {.i = 1} }, ++ { MODKEY|ShiftMask, XK_y, scratchpad_hide, {.i = 2} }, ++ { MODKEY|ShiftMask, XK_u, scratchpad_hide, {.i = 3} }, ++ { MODKEY|ShiftMask, XK_r, scratchpad_remove, {0} }, + }; + + /* button definitions */ +diff --git a/dwm.c b/dwm.c +index 5f16260..202038f 100644 +--- a/dwm.c ++++ b/dwm.c +@@ -195,6 +195,11 @@ static void resizemouse(const Arg *arg); + static void restack(Monitor *m); + static void run(void); + static void scan(void); ++static void scratchpad_hide(); ++static void scratchpad_remove(); ++static void scratchpad_show(); ++static void scratchpad_show_client(Client *c); ++static void scratchpad_show_first(int scratchNum); + static int sendevent(Client *c, Atom proto); + static void sendmon(Client *c, Monitor *m); + static void setclientstate(Client *c, long state); +@@ -269,11 +274,19 @@ static Drw *drw; + static Monitor *mons, *selmon; + static Window root, wmcheckwin; + ++/* scratchpad */ ++#define SCRATCHPAD_MASK_1 (1u << sizeof tags / sizeof * tags) ++#define SCRATCHPAD_MASK_2 (1u << (sizeof tags / sizeof * tags + 1)) ++#define SCRATCHPAD_MASK_3 (1u << (sizeof tags / sizeof * tags + 2)) ++static int scratchpad_hide_flag = 0; ++static Client *scratchpad_last_showed_1 = NULL; ++static Client *scratchpad_last_showed_2 = NULL; ++static Client *scratchpad_last_showed_3 = NULL; + /* configuration, allows nested code to access above variables */ + #include "config.h" + + /* compile-time check if all tags fit into an unsigned int bit array. */ +-struct NumTags { char limitexceeded[LENGTH(tags) > 31 ? -1 : 1]; }; ++struct NumTags { char limitexceeded[LENGTH(tags) > 28 ? -1 : 1]; }; + + /* function implementations */ + void +@@ -309,7 +322,9 @@ applyrules(Client *c) + XFree(ch.res_class); + if (ch.res_name) + XFree(ch.res_name); ++ if(c->tags != SCRATCHPAD_MASK_1 && c->tags != SCRATCHPAD_MASK_2 && c->tags != SCRATCHPAD_MASK_3) { + c->tags = c->tags & TAGMASK ? c->tags & TAGMASK : c->mon->tagset[c->mon->seltags]; ++ } + } + + int +@@ -1412,6 +1427,124 @@ scan(void) + } + } + ++static void scratchpad_hide(const Arg *arg) { ++ if(scratchpad_hide_flag < 4) { ++ if(arg->i == 1) { ++ if(selmon->sel) { ++ selmon->sel->tags = SCRATCHPAD_MASK_1; ++ selmon->sel->isfloating = 1; ++ focus(NULL); ++ arrange(selmon); ++ scratchpad_hide_flag++; ++ } ++ } ++ else if(arg->i == 2) { ++ if(selmon->sel) { ++ selmon->sel->tags = SCRATCHPAD_MASK_2; ++ selmon->sel->isfloating = 1; ++ focus(NULL); ++ arrange(selmon); ++ scratchpad_hide_flag++; ++ } ++ } ++ else if(arg->i == 3) { ++ if(selmon->sel) { ++ selmon->sel->tags = SCRATCHPAD_MASK_3; ++ selmon->sel->isfloating = 1; ++ focus(NULL); ++ arrange(selmon); ++ scratchpad_hide_flag++; ++ } ++ } ++ } ++} ++ ++static void scratchpad_remove() { ++ if(selmon->sel && (scratchpad_last_showed_1 != NULL || scratchpad_last_showed_2 != NULL ||scratchpad_last_showed_3 != NULL) && (selmon->sel == scratchpad_last_showed_1 || selmon->sel == scratchpad_last_showed_2 || selmon->sel == scratchpad_last_showed_3)) { ++ if(scratchpad_last_showed_1 == selmon->sel) { ++ scratchpad_last_showed_1 = NULL; ++ scratchpad_hide_flag--; ++ } ++ else if(scratchpad_last_showed_2 == selmon->sel) { ++ scratchpad_last_showed_2 = NULL; ++ scratchpad_hide_flag--; ++ } ++ else if(scratchpad_last_showed_3 == selmon->sel) { ++ scratchpad_last_showed_3 = NULL; ++ scratchpad_hide_flag--; ++ } ++ } ++} ++ ++static void scratchpad_show(const Arg *arg) { ++ if(arg->i == 1) { ++ if(scratchpad_last_showed_1 == NULL) { ++ scratchpad_show_first(arg->i); ++ } ++ else { ++ if(scratchpad_last_showed_1->tags != SCRATCHPAD_MASK_1) { ++ scratchpad_last_showed_1->tags = SCRATCHPAD_MASK_1; ++ focus(NULL); ++ arrange(selmon); ++ } ++ else { ++ scratchpad_show_first(arg->i); ++ } ++ } ++ } ++ else if(arg->i == 2) { ++ if(scratchpad_last_showed_2 == NULL) { ++ scratchpad_show_first(arg->i); ++ } ++ else { ++ if(scratchpad_last_showed_2->tags != SCRATCHPAD_MASK_2) { ++ scratchpad_last_showed_2->tags = SCRATCHPAD_MASK_2; ++ focus(NULL); ++ arrange(selmon); ++ } ++ else { ++ scratchpad_show_first(arg->i); ++ } ++ } ++ } ++ else if(arg->i == 3) { ++ if(scratchpad_last_showed_3 == NULL) { ++ scratchpad_show_first(arg->i); ++ } ++ else { ++ if(scratchpad_last_showed_3->tags != SCRATCHPAD_MASK_3) { ++ scratchpad_last_showed_3->tags = SCRATCHPAD_MASK_3; ++ focus(NULL); ++ arrange(selmon); ++ } ++ else { ++ scratchpad_show_first(arg->i); ++ } ++ } ++ } ++} ++ ++static void scratchpad_show_client(Client *c) { ++ c->tags = selmon->tagset[selmon->seltags]; ++ focus(c); ++ arrange(selmon); ++} ++ ++static void scratchpad_show_first(int scratchNum) { ++ for(Client *c = selmon->clients; c !=NULL; c = c->next) { ++ if(c->tags == SCRATCHPAD_MASK_1 && scratchNum == 1) { ++ scratchpad_last_showed_1 = c; ++ scratchpad_show_client(c); ++ } else if(c->tags == SCRATCHPAD_MASK_2 && scratchNum == 2) { ++ scratchpad_last_showed_2 = c; ++ scratchpad_show_client(c); ++ } else if(c->tags == SCRATCHPAD_MASK_3 && scratchNum == 3) { ++ scratchpad_last_showed_3 = c; ++ scratchpad_show_client(c); ++ } ++ } ++} ++ + void + sendmon(Client *c, Monitor *m) + { +@@ -1785,6 +1918,16 @@ unmanage(Client *c, int destroyed) + XSetErrorHandler(xerror); + XUngrabServer(dpy); + } ++ if(scratchpad_last_showed_1 == c) { ++ scratchpad_last_showed_1 = NULL; ++ } ++ if(scratchpad_last_showed_2 == c) { ++ scratchpad_last_showed_2 = NULL; ++ } ++ if(scratchpad_last_showed_3 == c) { ++ scratchpad_last_showed_3 = NULL; ++ } ++ + free(c); + focus(NULL); + updateclientlist(); diff --git a/hosts/vali/mars/dwm/dwm-6.5/dwm-scratchpad-20240321-061e9fe.diff b/hosts/vali/mars/dwm/dwm-6.5/dwm-scratchpad-20240321-061e9fe.diff new file mode 100644 index 0000000..cb218b6 --- /dev/null +++ b/hosts/vali/mars/dwm/dwm-6.5/dwm-scratchpad-20240321-061e9fe.diff @@ -0,0 +1,105 @@ +From b9f3c11c3150f0b5d5b297a4eeeb2012764c98f5 Mon Sep 17 00:00:00 2001 +From: visil +Date: Thu, 21 Mar 2024 15:16:39 +0300 +Subject: [PATCH] Patch updated to 6.5 + +--- + config.def.h | 3 +++ + dwm.c | 34 ++++++++++++++++++++++++++++++++++ + 2 files changed, 37 insertions(+) + +diff --git a/config.def.h b/config.def.h +index 9efa774..0b8b310 100644 +--- a/config.def.h ++++ b/config.def.h +@@ -59,11 +59,14 @@ static const Layout layouts[] = { + static char dmenumon[2] = "0"; /* component of dmenucmd, manipulated in spawn() */ + static const char *dmenucmd[] = { "dmenu_run", "-m", dmenumon, "-fn", dmenufont, "-nb", col_gray1, "-nf", col_gray3, "-sb", col_cyan, "-sf", col_gray4, NULL }; + static const char *termcmd[] = { "st", NULL }; ++static const char scratchpadname[] = "scratchpad"; ++static const char *scratchpadcmd[] = { "st", "-t", scratchpadname, "-g", "120x34", NULL }; + + static const Key keys[] = { + /* modifier key function argument */ + { MODKEY, XK_p, spawn, {.v = dmenucmd } }, + { MODKEY|ShiftMask, XK_Return, spawn, {.v = termcmd } }, ++ { MODKEY, XK_grave, togglescratch, {.v = scratchpadcmd } }, + { MODKEY, XK_b, togglebar, {0} }, + { MODKEY, XK_j, focusstack, {.i = +1 } }, + { MODKEY, XK_k, focusstack, {.i = -1 } }, +diff --git a/dwm.c b/dwm.c +index f1d86b2..a8db21a 100644 +--- a/dwm.c ++++ b/dwm.c +@@ -211,6 +211,7 @@ static void tagmon(const Arg *arg); + static void tile(Monitor *m); + static void togglebar(const Arg *arg); + static void togglefloating(const Arg *arg); ++static void togglescratch(const Arg *arg); + static void toggletag(const Arg *arg); + static void toggleview(const Arg *arg); + static void unfocus(Client *c, int setfocus); +@@ -271,6 +272,8 @@ static Window root, wmcheckwin; + /* configuration, allows nested code to access above variables */ + #include "config.h" + ++static unsigned int scratchtag = 1 << LENGTH(tags); ++ + /* compile-time check if all tags fit into an unsigned int bit array. */ + struct NumTags { char limitexceeded[LENGTH(tags) > 31 ? -1 : 1]; }; + +@@ -1061,6 +1064,14 @@ manage(Window w, XWindowAttributes *wa) + c->y = MAX(c->y, c->mon->wy); + c->bw = borderpx; + ++ selmon->tagset[selmon->seltags] &= ~scratchtag; ++ if (!strcmp(c->name, scratchpadname)) { ++ c->mon->tagset[c->mon->seltags] |= c->tags = scratchtag; ++ c->isfloating = True; ++ c->x = c->mon->wx + (c->mon->ww / 2 - WIDTH(c) / 2); ++ c->y = c->mon->wy + (c->mon->wh / 2 - HEIGHT(c) / 2); ++ } ++ + wc.border_width = c->bw; + XConfigureWindow(dpy, w, CWBorderWidth, &wc); + XSetWindowBorder(dpy, w, scheme[SchemeNorm][ColBorder].pixel); +@@ -1651,6 +1662,7 @@ spawn(const Arg *arg) + + if (arg->v == dmenucmd) + dmenumon[0] = '0' + selmon->num; ++ selmon->tagset[selmon->seltags] &= ~scratchtag; + if (fork() == 0) { + if (dpy) + close(ConnectionNumber(dpy)); +@@ -1735,6 +1747,28 @@ togglefloating(const Arg *arg) + arrange(selmon); + } + ++void ++togglescratch(const Arg *arg) ++{ ++ Client *c; ++ unsigned int found = 0; ++ ++ for (c = selmon->clients; c && !(found = c->tags & scratchtag); c = c->next); ++ if (found) { ++ unsigned int newtagset = selmon->tagset[selmon->seltags] ^ scratchtag; ++ if (newtagset) { ++ selmon->tagset[selmon->seltags] = newtagset; ++ focus(NULL); ++ arrange(selmon); ++ } ++ if (ISVISIBLE(c)) { ++ focus(c); ++ restack(selmon); ++ } ++ } else ++ spawn(arg); ++} ++ + void + toggletag(const Arg *arg) + { +-- +2.44.0 + diff --git a/hosts/vali/mars/dwm/dwm-6.5/dwm.c b/hosts/vali/mars/dwm/dwm-6.5/dwm.c index e940130..f7e94b6 100644 --- a/hosts/vali/mars/dwm/dwm-6.5/dwm.c +++ b/hosts/vali/mars/dwm/dwm-6.5/dwm.c @@ -195,6 +195,11 @@ static void resizemouse(const Arg *arg); static void restack(Monitor *m); static void run(void); static void scan(void); +static void scratchpad_hide(); +static void scratchpad_remove(); +static void scratchpad_show(); +static void scratchpad_show_client(Client *c); +static void scratchpad_show_first(int scratchNum); static int sendevent(Client *c, Atom proto); static void sendmon(Client *c, Monitor *m); static void setclientstate(Client *c, long state); @@ -269,11 +274,20 @@ static Drw *drw; static Monitor *mons, *selmon; static Window root, wmcheckwin; +/* scratchpad */ +#define SCRATCHPAD_MASK_1 (1u << sizeof tags / sizeof * tags) +#define SCRATCHPAD_MASK_2 (1u << (sizeof tags / sizeof * tags + 1)) +#define SCRATCHPAD_MASK_3 (1u << (sizeof tags / sizeof * tags + 2)) +static int scratchpad_hide_flag = 0; +static Client *scratchpad_last_showed_1 = NULL; +static Client *scratchpad_last_showed_2 = NULL; +static Client *scratchpad_last_showed_3 = NULL; + /* configuration, allows nested code to access above variables */ #include "config.h" /* compile-time check if all tags fit into an unsigned int bit array. */ -struct NumTags { char limitexceeded[LENGTH(tags) > 31 ? -1 : 1]; }; +struct NumTags { char limitexceeded[LENGTH(tags) > 28 ? -1 : 1]; }; /* function implementations */ void @@ -309,7 +323,9 @@ applyrules(Client *c) XFree(ch.res_class); if (ch.res_name) XFree(ch.res_name); + if(c->tags != SCRATCHPAD_MASK_1 && c->tags != SCRATCHPAD_MASK_2 && c->tags != SCRATCHPAD_MASK_3) { c->tags = c->tags & TAGMASK ? c->tags & TAGMASK : c->mon->tagset[c->mon->seltags]; + } } int @@ -1062,13 +1078,15 @@ manage(Window w, XWindowAttributes *wa) c->y = MAX(c->y, c->mon->wy); c->bw = borderpx; - wc.border_width = c->bw; + wc.border_width = c->bw; XConfigureWindow(dpy, w, CWBorderWidth, &wc); XSetWindowBorder(dpy, w, scheme[SchemeNorm][ColBorder].pixel); configure(c); /* propagates border_width, if size doesn't change */ updatewindowtype(c); updatesizehints(c); updatewmhints(c); + c->x = c->mon->mx + (c->mon->mw - WIDTH(c)) / 2; + c->y = c->mon->my + (c->mon->mh - HEIGHT(c)) / 2; XSelectInput(dpy, w, EnterWindowMask|FocusChangeMask|PropertyChangeMask|StructureNotifyMask); grabbuttons(c, 0); if (!c->isfloating) @@ -1418,6 +1436,124 @@ scan(void) } } +static void scratchpad_hide(const Arg *arg) { + if(scratchpad_hide_flag < 4) { + if(arg->i == 1) { + if(selmon->sel) { + selmon->sel->tags = SCRATCHPAD_MASK_1; + selmon->sel->isfloating = 1; + focus(NULL); + arrange(selmon); + scratchpad_hide_flag++; + } + } + else if(arg->i == 2) { + if(selmon->sel) { + selmon->sel->tags = SCRATCHPAD_MASK_2; + selmon->sel->isfloating = 1; + focus(NULL); + arrange(selmon); + scratchpad_hide_flag++; + } + } + else if(arg->i == 3) { + if(selmon->sel) { + selmon->sel->tags = SCRATCHPAD_MASK_3; + selmon->sel->isfloating = 1; + focus(NULL); + arrange(selmon); + scratchpad_hide_flag++; + } + } + } +} + +static void scratchpad_remove() { + if(selmon->sel && (scratchpad_last_showed_1 != NULL || scratchpad_last_showed_2 != NULL ||scratchpad_last_showed_3 != NULL) && (selmon->sel == scratchpad_last_showed_1 || selmon->sel == scratchpad_last_showed_2 || selmon->sel == scratchpad_last_showed_3)) { + if(scratchpad_last_showed_1 == selmon->sel) { + scratchpad_last_showed_1 = NULL; + scratchpad_hide_flag--; + } + else if(scratchpad_last_showed_2 == selmon->sel) { + scratchpad_last_showed_2 = NULL; + scratchpad_hide_flag--; + } + else if(scratchpad_last_showed_3 == selmon->sel) { + scratchpad_last_showed_3 = NULL; + scratchpad_hide_flag--; + } + } +} + +static void scratchpad_show(const Arg *arg) { + if(arg->i == 1) { + if(scratchpad_last_showed_1 == NULL) { + scratchpad_show_first(arg->i); + } + else { + if(scratchpad_last_showed_1->tags != SCRATCHPAD_MASK_1) { + scratchpad_last_showed_1->tags = SCRATCHPAD_MASK_1; + focus(NULL); + arrange(selmon); + } + else { + scratchpad_show_first(arg->i); + } + } + } + else if(arg->i == 2) { + if(scratchpad_last_showed_2 == NULL) { + scratchpad_show_first(arg->i); + } + else { + if(scratchpad_last_showed_2->tags != SCRATCHPAD_MASK_2) { + scratchpad_last_showed_2->tags = SCRATCHPAD_MASK_2; + focus(NULL); + arrange(selmon); + } + else { + scratchpad_show_first(arg->i); + } + } + } + else if(arg->i == 3) { + if(scratchpad_last_showed_3 == NULL) { + scratchpad_show_first(arg->i); + } + else { + if(scratchpad_last_showed_3->tags != SCRATCHPAD_MASK_3) { + scratchpad_last_showed_3->tags = SCRATCHPAD_MASK_3; + focus(NULL); + arrange(selmon); + } + else { + scratchpad_show_first(arg->i); + } + } + } +} + +static void scratchpad_show_client(Client *c) { + c->tags = selmon->tagset[selmon->seltags]; + focus(c); + arrange(selmon); +} + +static void scratchpad_show_first(int scratchNum) { + for(Client *c = selmon->clients; c !=NULL; c = c->next) { + if(c->tags == SCRATCHPAD_MASK_1 && scratchNum == 1) { + scratchpad_last_showed_1 = c; + scratchpad_show_client(c); + } else if(c->tags == SCRATCHPAD_MASK_2 && scratchNum == 2) { + scratchpad_last_showed_2 = c; + scratchpad_show_client(c); + } else if(c->tags == SCRATCHPAD_MASK_3 && scratchNum == 3) { + scratchpad_last_showed_3 = c; + scratchpad_show_client(c); + } + } +} + void sendmon(Client *c, Monitor *m) { @@ -1803,6 +1939,16 @@ unmanage(Client *c, int destroyed) XSetErrorHandler(xerror); XUngrabServer(dpy); } + if(scratchpad_last_showed_1 == c) { + scratchpad_last_showed_1 = NULL; + } + if(scratchpad_last_showed_2 == c) { + scratchpad_last_showed_2 = NULL; + } + if(scratchpad_last_showed_3 == c) { + scratchpad_last_showed_3 = NULL; + } + free(c); focus(NULL); updateclientlist(); diff --git a/hosts/vali/mars/dwm/dwm-6.5/dwm.c.orig b/hosts/vali/mars/dwm/dwm-6.5/dwm.c.orig new file mode 100644 index 0000000..7ab1910 --- /dev/null +++ b/hosts/vali/mars/dwm/dwm-6.5/dwm.c.orig @@ -0,0 +1,2207 @@ +/* See LICENSE file for copyright and license details. + * + * dynamic window manager is designed like any other X client as well. It is + * driven through handling X events. In contrast to other X clients, a window + * manager selects for SubstructureRedirectMask on the root window, to receive + * events about window (dis-)appearance. Only one X connection at a time is + * allowed to select for this event mask. + * + * The event handlers of dwm are organized in an array which is accessed + * whenever a new event has been fetched. This allows event dispatching + * in O(1) time. + * + * Each child of the root window is called a client, except windows which have + * set the override_redirect flag. Clients are organized in a linked client + * list on each monitor, the focus history is remembered through a stack list + * on each monitor. Each client contains a bit array to indicate the tags of a + * client. + * + * Keys and tagging rules are organized as arrays and defined in config.h. + * + * To understand everything else, start reading main(). + */ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#ifdef XINERAMA +#include +#endif /* XINERAMA */ +#include + +#include "drw.h" +#include "util.h" + +/* macros */ +#define BUTTONMASK (ButtonPressMask|ButtonReleaseMask) +#define CLEANMASK(mask) (mask & ~(numlockmask|LockMask) & (ShiftMask|ControlMask|Mod1Mask|Mod2Mask|Mod3Mask|Mod4Mask|Mod5Mask)) +#define INTERSECT(x,y,w,h,m) (MAX(0, MIN((x)+(w),(m)->wx+(m)->ww) - MAX((x),(m)->wx)) \ + * MAX(0, MIN((y)+(h),(m)->wy+(m)->wh) - MAX((y),(m)->wy))) +#define ISVISIBLE(C) ((C->tags & C->mon->tagset[C->mon->seltags])) +#define LENGTH(X) (sizeof X / sizeof X[0]) +#define MOUSEMASK (BUTTONMASK|PointerMotionMask) +#define WIDTH(X) ((X)->w + 2 * (X)->bw) +#define HEIGHT(X) ((X)->h + 2 * (X)->bw) +#define TAGMASK ((1 << LENGTH(tags)) - 1) +#define TEXTW(X) (drw_fontset_getwidth(drw, (X)) + lrpad) + +/* enums */ +enum { CurNormal, CurResize, CurMove, CurLast }; /* cursor */ +enum { SchemeNorm, SchemeSel }; /* color schemes */ +enum { NetSupported, NetWMName, NetWMState, NetWMCheck, + NetWMFullscreen, NetActiveWindow, NetWMWindowType, + NetWMWindowTypeDialog, NetClientList, NetLast }; /* EWMH atoms */ +enum { WMProtocols, WMDelete, WMState, WMTakeFocus, WMLast }; /* default atoms */ +enum { ClkTagBar, ClkLtSymbol, ClkStatusText, ClkWinTitle, + ClkClientWin, ClkRootWin, ClkLast }; /* clicks */ + +typedef union { + int i; + unsigned int ui; + float f; + const void *v; +} Arg; + +typedef struct { + unsigned int click; + unsigned int mask; + unsigned int button; + void (*func)(const Arg *arg); + const Arg arg; +} Button; + +typedef struct Monitor Monitor; +typedef struct Client Client; +struct Client { + char name[256]; + float mina, maxa; + int x, y, w, h; + int oldx, oldy, oldw, oldh; + int basew, baseh, incw, inch, maxw, maxh, minw, minh, hintsvalid; + int bw, oldbw; + unsigned int tags; + int isfixed, isfloating, isurgent, neverfocus, oldstate, isfullscreen; + Client *next; + Client *snext; + Monitor *mon; + Window win; +}; + +typedef struct { + unsigned int mod; + KeySym keysym; + void (*func)(const Arg *); + const Arg arg; +} Key; + +typedef struct { + const char *symbol; + 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; + const char *title; + unsigned int tags; + int isfloating; + int monitor; +} Rule; + +/* function declarations */ +static void applyrules(Client *c); +static int applysizehints(Client *c, int *x, int *y, int *w, int *h, int interact); +static void arrange(Monitor *m); +static void arrangemon(Monitor *m); +static void attach(Client *c); +static void attachstack(Client *c); +static void buttonpress(XEvent *e); +static void checkotherwm(void); +static void cleanup(void); +static void cleanupmon(Monitor *mon); +static void clientmessage(XEvent *e); +static void configure(Client *c); +static void configurenotify(XEvent *e); +static void configurerequest(XEvent *e); +static Monitor *createmon(void); +static void destroynotify(XEvent *e); +static void detach(Client *c); +static void detachstack(Client *c); +static Monitor *dirtomon(int dir); +static void drawbar(Monitor *m); +static void drawbars(void); +static void enternotify(XEvent *e); +static void expose(XEvent *e); +static void focus(Client *c); +static void focusin(XEvent *e); +static void focusmon(const Arg *arg); +static void focusstack(const Arg *arg); +static Atom getatomprop(Client *c, Atom prop); +static int getrootptr(int *x, int *y); +static long getstate(Window w); +static int gettextprop(Window w, Atom atom, char *text, unsigned int size); +static void grabbuttons(Client *c, int focused); +static void grabkeys(void); +static void incnmaster(const Arg *arg); +static void keypress(XEvent *e); +static void killclient(const Arg *arg); +static void manage(Window w, XWindowAttributes *wa); +static void mappingnotify(XEvent *e); +static void maprequest(XEvent *e); +static void monocle(Monitor *m); +static void motionnotify(XEvent *e); +static void movemouse(const Arg *arg); +static Client *nexttiled(Client *c); +static void pop(Client *c); +static void propertynotify(XEvent *e); +static void quit(const Arg *arg); +static Monitor *recttomon(int x, int y, int w, int h); +static void resize(Client *c, int x, int y, int w, int h, int interact); +static void resizeclient(Client *c, int x, int y, int w, int h); +static void resizemouse(const Arg *arg); +static void restack(Monitor *m); +static void run(void); +static void scan(void); +static int sendevent(Client *c, Atom proto); +static void sendmon(Client *c, Monitor *m); +static void setclientstate(Client *c, long state); +static void setfocus(Client *c); +static void setfullscreen(Client *c, int fullscreen); +static void setlayout(const Arg *arg); +static void setmfact(const Arg *arg); +static void setup(void); +static void seturgent(Client *c, int urg); +static void showhide(Client *c); +static void spawn(const Arg *arg); +static void tag(const Arg *arg); +static void tagmon(const Arg *arg); +static void tile(Monitor *m); +static void togglebar(const Arg *arg); +static void togglefloating(const Arg *arg); +static void togglefullscr(const Arg *arg); +static void togglescratch(const Arg *arg); +static void toggletag(const Arg *arg); +static void toggleview(const Arg *arg); +static void unfocus(Client *c, int setfocus); +static void unmanage(Client *c, int destroyed); +static void unmapnotify(XEvent *e); +static void updatebarpos(Monitor *m); +static void updatebars(void); +static void updateclientlist(void); +static int updategeom(void); +static void updatenumlockmask(void); +static void updatesizehints(Client *c); +static void updatestatus(void); +static void updatetitle(Client *c); +static void updatewindowtype(Client *c); +static void updatewmhints(Client *c); +static void view(const Arg *arg); +static Client *wintoclient(Window w); +static Monitor *wintomon(Window w); +static int xerror(Display *dpy, XErrorEvent *ee); +static int xerrordummy(Display *dpy, XErrorEvent *ee); +static int xerrorstart(Display *dpy, XErrorEvent *ee); +static void zoom(const Arg *arg); + +/* variables */ +static const char broken[] = "broken"; +static char stext[256]; +static int screen; +static int sw, sh; /* X display screen geometry width, height */ +static int bh; /* bar height */ +static int lrpad; /* sum of left and right padding for text */ +static int (*xerrorxlib)(Display *, XErrorEvent *); +static unsigned int numlockmask = 0; +static void (*handler[LASTEvent]) (XEvent *) = { + [ButtonPress] = buttonpress, + [ClientMessage] = clientmessage, + [ConfigureRequest] = configurerequest, + [ConfigureNotify] = configurenotify, + [DestroyNotify] = destroynotify, + [EnterNotify] = enternotify, + [Expose] = expose, + [FocusIn] = focusin, + [KeyPress] = keypress, + [MappingNotify] = mappingnotify, + [MapRequest] = maprequest, + [MotionNotify] = motionnotify, + [PropertyNotify] = propertynotify, + [UnmapNotify] = unmapnotify +}; +static Atom wmatom[WMLast], netatom[NetLast]; +static int running = 1; +static Cur *cursor[CurLast]; +static Clr **scheme; +static Display *dpy; +static Drw *drw; +static Monitor *mons, *selmon; +static Window root, wmcheckwin; + +/* configuration, allows nested code to access above variables */ +#include "config.h" + +static unsigned int scratchtag = 1 << LENGTH(tags); +/* compile-time check if all tags fit into an unsigned int bit array. */ +struct NumTags { char limitexceeded[LENGTH(tags) > 31 ? -1 : 1]; }; + +/* function implementations */ +void +applyrules(Client *c) +{ + const char *class, *instance; + unsigned int i; + const Rule *r; + Monitor *m; + XClassHint ch = { NULL, NULL }; + + /* rule matching */ + c->isfloating = 0; + c->tags = 0; + XGetClassHint(dpy, c->win, &ch); + class = ch.res_class ? ch.res_class : broken; + instance = ch.res_name ? ch.res_name : broken; + + for (i = 0; i < LENGTH(rules); i++) { + r = &rules[i]; + if ((!r->title || strstr(c->name, r->title)) + && (!r->class || strstr(class, r->class)) + && (!r->instance || strstr(instance, r->instance))) + { + c->isfloating = r->isfloating; + c->tags |= r->tags; + for (m = mons; m && m->num != r->monitor; m = m->next); + if (m) + c->mon = m; + } + } + if (ch.res_class) + XFree(ch.res_class); + if (ch.res_name) + XFree(ch.res_name); + c->tags = c->tags & TAGMASK ? c->tags & TAGMASK : c->mon->tagset[c->mon->seltags]; +} + +int +applysizehints(Client *c, int *x, int *y, int *w, int *h, int interact) +{ + int baseismin; + Monitor *m = c->mon; + + /* set minimum possible */ + *w = MAX(1, *w); + *h = MAX(1, *h); + if (interact) { + if (*x > sw) + *x = sw - WIDTH(c); + if (*y > sh) + *y = sh - HEIGHT(c); + if (*x + *w + 2 * c->bw < 0) + *x = 0; + if (*y + *h + 2 * c->bw < 0) + *y = 0; + } else { + if (*x >= m->wx + m->ww) + *x = m->wx + m->ww - WIDTH(c); + if (*y >= m->wy + m->wh) + *y = m->wy + m->wh - HEIGHT(c); + if (*x + *w + 2 * c->bw <= m->wx) + *x = m->wx; + if (*y + *h + 2 * c->bw <= m->wy) + *y = m->wy; + } + if (*h < bh) + *h = bh; + if (*w < bh) + *w = bh; + if (resizehints || c->isfloating || !c->mon->lt[c->mon->sellt]->arrange) { + if (!c->hintsvalid) + updatesizehints(c); + /* see last two sentences in ICCCM 4.1.2.3 */ + baseismin = c->basew == c->minw && c->baseh == c->minh; + if (!baseismin) { /* temporarily remove base dimensions */ + *w -= c->basew; + *h -= c->baseh; + } + /* adjust for aspect limits */ + if (c->mina > 0 && c->maxa > 0) { + if (c->maxa < (float)*w / *h) + *w = *h * c->maxa + 0.5; + else if (c->mina < (float)*h / *w) + *h = *w * c->mina + 0.5; + } + if (baseismin) { /* increment calculation requires this */ + *w -= c->basew; + *h -= c->baseh; + } + /* adjust for increment value */ + if (c->incw) + *w -= *w % c->incw; + if (c->inch) + *h -= *h % c->inch; + /* restore base dimensions */ + *w = MAX(*w + c->basew, c->minw); + *h = MAX(*h + c->baseh, c->minh); + if (c->maxw) + *w = MIN(*w, c->maxw); + if (c->maxh) + *h = MIN(*h, c->maxh); + } + return *x != c->x || *y != c->y || *w != c->w || *h != c->h; +} + +void +arrange(Monitor *m) +{ + if (m) + showhide(m->stack); + else for (m = mons; m; m = m->next) + showhide(m->stack); + if (m) { + arrangemon(m); + restack(m); + } else for (m = mons; m; m = m->next) + arrangemon(m); +} + +void +arrangemon(Monitor *m) +{ + strncpy(m->ltsymbol, m->lt[m->sellt]->symbol, sizeof m->ltsymbol); + if (m->lt[m->sellt]->arrange) + m->lt[m->sellt]->arrange(m); +} + +void +attach(Client *c) +{ + c->next = c->mon->clients; + c->mon->clients = c; +} + +void +attachstack(Client *c) +{ + c->snext = c->mon->stack; + c->mon->stack = c; +} + +void +buttonpress(XEvent *e) +{ + unsigned int i, x, click; + Arg arg = {0}; + Client *c; + Monitor *m; + XButtonPressedEvent *ev = &e->xbutton; + + click = ClkRootWin; + /* focus monitor if necessary */ + if ((m = wintomon(ev->window)) && m != selmon) { + unfocus(selmon->sel, 1); + selmon = m; + focus(NULL); + } + if (ev->window == selmon->barwin) { + i = x = 0; + do + x += TEXTW(tags[i]); + while (ev->x >= x && ++i < LENGTH(tags)); + if (i < LENGTH(tags)) { + click = ClkTagBar; + arg.ui = 1 << i; + } else if (ev->x < x + TEXTW(selmon->ltsymbol)) + click = ClkLtSymbol; + else if (ev->x > selmon->ww - (int)TEXTW(stext)) + click = ClkStatusText; + else + click = ClkWinTitle; + } else if ((c = wintoclient(ev->window))) { + focus(c); + restack(selmon); + XAllowEvents(dpy, ReplayPointer, CurrentTime); + click = ClkClientWin; + } + for (i = 0; i < LENGTH(buttons); i++) + if (click == buttons[i].click && buttons[i].func && buttons[i].button == ev->button + && CLEANMASK(buttons[i].mask) == CLEANMASK(ev->state)) + buttons[i].func(click == ClkTagBar && buttons[i].arg.i == 0 ? &arg : &buttons[i].arg); +} + +void +checkotherwm(void) +{ + xerrorxlib = XSetErrorHandler(xerrorstart); + /* this causes an error if some other window manager is running */ + XSelectInput(dpy, DefaultRootWindow(dpy), SubstructureRedirectMask); + XSync(dpy, False); + XSetErrorHandler(xerror); + XSync(dpy, False); +} + +void +cleanup(void) +{ + Arg a = {.ui = ~0}; + Layout foo = { "", NULL }; + Monitor *m; + size_t i; + + view(&a); + selmon->lt[selmon->sellt] = &foo; + for (m = mons; m; m = m->next) + while (m->stack) + unmanage(m->stack, 0); + XUngrabKey(dpy, AnyKey, AnyModifier, root); + while (mons) + cleanupmon(mons); + for (i = 0; i < CurLast; i++) + drw_cur_free(drw, cursor[i]); + for (i = 0; i < LENGTH(colors); i++) + free(scheme[i]); + free(scheme); + XDestroyWindow(dpy, wmcheckwin); + drw_free(drw); + XSync(dpy, False); + XSetInputFocus(dpy, PointerRoot, RevertToPointerRoot, CurrentTime); + XDeleteProperty(dpy, root, netatom[NetActiveWindow]); +} + +void +cleanupmon(Monitor *mon) +{ + Monitor *m; + + if (mon == mons) + mons = mons->next; + else { + for (m = mons; m && m->next != mon; m = m->next); + m->next = mon->next; + } + XUnmapWindow(dpy, mon->barwin); + XDestroyWindow(dpy, mon->barwin); + free(mon); +} + +void +clientmessage(XEvent *e) +{ + XClientMessageEvent *cme = &e->xclient; + Client *c = wintoclient(cme->window); + + if (!c) + return; + if (cme->message_type == netatom[NetWMState]) { + if (cme->data.l[1] == netatom[NetWMFullscreen] + || cme->data.l[2] == netatom[NetWMFullscreen]) + setfullscreen(c, (cme->data.l[0] == 1 /* _NET_WM_STATE_ADD */ + || (cme->data.l[0] == 2 /* _NET_WM_STATE_TOGGLE */ && !c->isfullscreen))); + } else if (cme->message_type == netatom[NetActiveWindow]) { + if (c != selmon->sel && !c->isurgent) + seturgent(c, 1); + } +} + +void +configure(Client *c) +{ + XConfigureEvent ce; + + ce.type = ConfigureNotify; + ce.display = dpy; + ce.event = c->win; + ce.window = c->win; + ce.x = c->x; + ce.y = c->y; + ce.width = c->w; + ce.height = c->h; + ce.border_width = c->bw; + ce.above = None; + ce.override_redirect = False; + XSendEvent(dpy, c->win, False, StructureNotifyMask, (XEvent *)&ce); +} + +void +configurenotify(XEvent *e) +{ + Monitor *m; + Client *c; + XConfigureEvent *ev = &e->xconfigure; + int dirty; + + /* TODO: updategeom handling sucks, needs to be simplified */ + if (ev->window == root) { + dirty = (sw != ev->width || sh != ev->height); + sw = ev->width; + sh = ev->height; + if (updategeom() || dirty) { + drw_resize(drw, sw, bh); + updatebars(); + for (m = mons; m; m = m->next) { + for (c = m->clients; c; c = c->next) + if (c->isfullscreen) + resizeclient(c, m->mx, m->my, m->mw, m->mh); + XMoveResizeWindow(dpy, m->barwin, m->wx, m->by, m->ww, bh); + } + focus(NULL); + arrange(NULL); + } + } +} + +void +configurerequest(XEvent *e) +{ + Client *c; + Monitor *m; + XConfigureRequestEvent *ev = &e->xconfigurerequest; + XWindowChanges wc; + + if ((c = wintoclient(ev->window))) { + if (ev->value_mask & CWBorderWidth) + c->bw = ev->border_width; + else if (c->isfloating || !selmon->lt[selmon->sellt]->arrange) { + m = c->mon; + if (ev->value_mask & CWX) { + c->oldx = c->x; + c->x = m->mx + ev->x; + } + if (ev->value_mask & CWY) { + c->oldy = c->y; + c->y = m->my + ev->y; + } + if (ev->value_mask & CWWidth) { + c->oldw = c->w; + c->w = ev->width; + } + if (ev->value_mask & CWHeight) { + c->oldh = c->h; + c->h = ev->height; + } + if ((c->x + c->w) > m->mx + m->mw && c->isfloating) + c->x = m->mx + (m->mw / 2 - WIDTH(c) / 2); /* center in x direction */ + if ((c->y + c->h) > m->my + m->mh && c->isfloating) + c->y = m->my + (m->mh / 2 - HEIGHT(c) / 2); /* center in y direction */ + if ((ev->value_mask & (CWX|CWY)) && !(ev->value_mask & (CWWidth|CWHeight))) + configure(c); + if (ISVISIBLE(c)) + XMoveResizeWindow(dpy, c->win, c->x, c->y, c->w, c->h); + } else + configure(c); + } else { + wc.x = ev->x; + wc.y = ev->y; + wc.width = ev->width; + wc.height = ev->height; + wc.border_width = ev->border_width; + wc.sibling = ev->above; + wc.stack_mode = ev->detail; + XConfigureWindow(dpy, ev->window, ev->value_mask, &wc); + } + XSync(dpy, False); +} + +Monitor * +createmon(void) +{ + Monitor *m; + + m = ecalloc(1, sizeof(Monitor)); + m->tagset[0] = m->tagset[1] = 1; + m->mfact = mfact; + m->nmaster = nmaster; + m->showbar = showbar; + m->topbar = topbar; + m->lt[0] = &layouts[0]; + m->lt[1] = &layouts[1 % LENGTH(layouts)]; + strncpy(m->ltsymbol, layouts[0].symbol, sizeof m->ltsymbol); + return m; +} + +void +destroynotify(XEvent *e) +{ + Client *c; + XDestroyWindowEvent *ev = &e->xdestroywindow; + + if ((c = wintoclient(ev->window))) + unmanage(c, 1); +} + +void +detach(Client *c) +{ + Client **tc; + + for (tc = &c->mon->clients; *tc && *tc != c; tc = &(*tc)->next); + *tc = c->next; +} + +void +detachstack(Client *c) +{ + Client **tc, *t; + + for (tc = &c->mon->stack; *tc && *tc != c; tc = &(*tc)->snext); + *tc = c->snext; + + if (c == c->mon->sel) { + for (t = c->mon->stack; t && !ISVISIBLE(t); t = t->snext); + c->mon->sel = t; + } +} + +Monitor * +dirtomon(int dir) +{ + Monitor *m = NULL; + + if (dir > 0) { + if (!(m = selmon->next)) + m = mons; + } else if (selmon == mons) + for (m = mons; m->next; m = m->next); + else + for (m = mons; m->next != selmon; m = m->next); + return m; +} + +void +drawbar(Monitor *m) +{ + int x, w, tw = 0; + int boxs = drw->fonts->h / 9; + int boxw = drw->fonts->h / 6 + 2; + unsigned int i, occ = 0, urg = 0; + Client *c; + + if (!m->showbar) + return; + + /* draw status first so it can be overdrawn by tags later */ + if (m == selmon) { /* status is only drawn on selected monitor */ + drw_setscheme(drw, scheme[SchemeNorm]); + tw = TEXTW(stext) - lrpad + 2; /* 2px right padding */ + drw_text(drw, m->ww - tw, 0, tw, bh, 0, stext, 0); + } + + for (c = m->clients; c; c = c->next) { + occ |= c->tags; + if (c->isurgent) + urg |= c->tags; + } + x = 0; + for (i = 0; i < LENGTH(tags); i++) { + w = TEXTW(tags[i]); + drw_setscheme(drw, scheme[m->tagset[m->seltags] & 1 << i ? SchemeSel : SchemeNorm]); + drw_text(drw, x, 0, w, bh, lrpad / 2, tags[i], urg & 1 << i); + if (occ & 1 << i) + drw_rect(drw, x + boxs, boxs, boxw, boxw, + m == selmon && selmon->sel && selmon->sel->tags & 1 << i, + urg & 1 << i); + x += w; + } + w = TEXTW(m->ltsymbol); + drw_setscheme(drw, scheme[SchemeNorm]); + x = drw_text(drw, x, 0, w, bh, lrpad / 2, m->ltsymbol, 0); + + if ((w = m->ww - tw - x) > bh) { + if (m->sel) { + drw_setscheme(drw, scheme[m == selmon ? SchemeSel : SchemeNorm]); + drw_text(drw, x, 0, w, bh, lrpad / 2, m->sel->name, 0); + if (m->sel->isfloating) + drw_rect(drw, x + boxs, boxs, boxw, boxw, m->sel->isfixed, 0); + } else { + drw_setscheme(drw, scheme[SchemeNorm]); + drw_rect(drw, x, 0, w, bh, 1, 1); + } + } + drw_map(drw, m->barwin, 0, 0, m->ww, bh); +} + +void +drawbars(void) +{ + Monitor *m; + + for (m = mons; m; m = m->next) + drawbar(m); +} + +void +enternotify(XEvent *e) +{ + Client *c; + Monitor *m; + XCrossingEvent *ev = &e->xcrossing; + + if ((ev->mode != NotifyNormal || ev->detail == NotifyInferior) && ev->window != root) + return; + c = wintoclient(ev->window); + m = c ? c->mon : wintomon(ev->window); + if (m != selmon) { + unfocus(selmon->sel, 1); + selmon = m; + } else if (!c || c == selmon->sel) + return; + focus(c); +} + +void +expose(XEvent *e) +{ + Monitor *m; + XExposeEvent *ev = &e->xexpose; + + if (ev->count == 0 && (m = wintomon(ev->window))) + drawbar(m); +} + +void +focus(Client *c) +{ + if (!c || !ISVISIBLE(c)) + for (c = selmon->stack; c && !ISVISIBLE(c); c = c->snext); + if (selmon->sel && selmon->sel != c) + unfocus(selmon->sel, 0); + if (c) { + if (c->mon != selmon) + selmon = c->mon; + if (c->isurgent) + seturgent(c, 0); + detachstack(c); + attachstack(c); + grabbuttons(c, 1); + XSetWindowBorder(dpy, c->win, scheme[SchemeSel][ColBorder].pixel); + setfocus(c); + } else { + XSetInputFocus(dpy, root, RevertToPointerRoot, CurrentTime); + XDeleteProperty(dpy, root, netatom[NetActiveWindow]); + } + selmon->sel = c; + drawbars(); +} + +/* there are some broken focus acquiring clients needing extra handling */ +void +focusin(XEvent *e) +{ + XFocusChangeEvent *ev = &e->xfocus; + + if (selmon->sel && ev->window != selmon->sel->win) + setfocus(selmon->sel); +} + +void +focusmon(const Arg *arg) +{ + Monitor *m; + + if (!mons->next) + return; + if ((m = dirtomon(arg->i)) == selmon) + return; + unfocus(selmon->sel, 0); + selmon = m; + focus(NULL); +} + +void +focusstack(const Arg *arg) +{ + Client *c = NULL, *i; + + if (!selmon->sel || (selmon->sel->isfullscreen && lockfullscreen)) + return; + if (arg->i > 0) { + for (c = selmon->sel->next; c && !ISVISIBLE(c); c = c->next); + if (!c) + for (c = selmon->clients; c && !ISVISIBLE(c); c = c->next); + } else { + for (i = selmon->clients; i != selmon->sel; i = i->next) + if (ISVISIBLE(i)) + c = i; + if (!c) + for (; i; i = i->next) + if (ISVISIBLE(i)) + c = i; + } + if (c) { + focus(c); + restack(selmon); + } +} + +Atom +getatomprop(Client *c, Atom prop) +{ + int di; + unsigned long dl; + unsigned char *p = NULL; + Atom da, atom = None; + + if (XGetWindowProperty(dpy, c->win, prop, 0L, sizeof atom, False, XA_ATOM, + &da, &di, &dl, &dl, &p) == Success && p) { + atom = *(Atom *)p; + XFree(p); + } + return atom; +} + +int +getrootptr(int *x, int *y) +{ + int di; + unsigned int dui; + Window dummy; + + return XQueryPointer(dpy, root, &dummy, &dummy, x, y, &di, &di, &dui); +} + +long +getstate(Window w) +{ + int format; + long result = -1; + unsigned char *p = NULL; + unsigned long n, extra; + Atom real; + + if (XGetWindowProperty(dpy, w, wmatom[WMState], 0L, 2L, False, wmatom[WMState], + &real, &format, &n, &extra, (unsigned char **)&p) != Success) + return -1; + if (n != 0) + result = *p; + XFree(p); + return result; +} + +int +gettextprop(Window w, Atom atom, char *text, unsigned int size) +{ + char **list = NULL; + int n; + XTextProperty name; + + if (!text || size == 0) + return 0; + text[0] = '\0'; + if (!XGetTextProperty(dpy, w, &name, atom) || !name.nitems) + return 0; + if (name.encoding == XA_STRING) { + strncpy(text, (char *)name.value, size - 1); + } else if (XmbTextPropertyToTextList(dpy, &name, &list, &n) >= Success && n > 0 && *list) { + strncpy(text, *list, size - 1); + XFreeStringList(list); + } + text[size - 1] = '\0'; + XFree(name.value); + return 1; +} + +void +grabbuttons(Client *c, int focused) +{ + updatenumlockmask(); + { + unsigned int i, j; + unsigned int modifiers[] = { 0, LockMask, numlockmask, numlockmask|LockMask }; + XUngrabButton(dpy, AnyButton, AnyModifier, c->win); + if (!focused) + XGrabButton(dpy, AnyButton, AnyModifier, c->win, False, + BUTTONMASK, GrabModeSync, GrabModeSync, None, None); + for (i = 0; i < LENGTH(buttons); i++) + if (buttons[i].click == ClkClientWin) + for (j = 0; j < LENGTH(modifiers); j++) + XGrabButton(dpy, buttons[i].button, + buttons[i].mask | modifiers[j], + c->win, False, BUTTONMASK, + GrabModeAsync, GrabModeSync, None, None); + } +} + +void +grabkeys(void) +{ + updatenumlockmask(); + { + unsigned int i, j, k; + unsigned int modifiers[] = { 0, LockMask, numlockmask, numlockmask|LockMask }; + int start, end, skip; + KeySym *syms; + + XUngrabKey(dpy, AnyKey, AnyModifier, root); + XDisplayKeycodes(dpy, &start, &end); + syms = XGetKeyboardMapping(dpy, start, end - start + 1, &skip); + if (!syms) + return; + for (k = start; k <= end; k++) + for (i = 0; i < LENGTH(keys); i++) + /* skip modifier codes, we do that ourselves */ + if (keys[i].keysym == syms[(k - start) * skip]) + for (j = 0; j < LENGTH(modifiers); j++) + XGrabKey(dpy, k, + keys[i].mod | modifiers[j], + root, True, + GrabModeAsync, GrabModeAsync); + XFree(syms); + } +} + +void +incnmaster(const Arg *arg) +{ + selmon->nmaster = MAX(selmon->nmaster + arg->i, 0); + arrange(selmon); +} + +#ifdef XINERAMA +static int +isuniquegeom(XineramaScreenInfo *unique, size_t n, XineramaScreenInfo *info) +{ + while (n--) + if (unique[n].x_org == info->x_org && unique[n].y_org == info->y_org + && unique[n].width == info->width && unique[n].height == info->height) + return 0; + return 1; +} +#endif /* XINERAMA */ + +void +keypress(XEvent *e) +{ + unsigned int i; + KeySym keysym; + XKeyEvent *ev; + + ev = &e->xkey; + keysym = XKeycodeToKeysym(dpy, (KeyCode)ev->keycode, 0); + for (i = 0; i < LENGTH(keys); i++) + if (keysym == keys[i].keysym + && CLEANMASK(keys[i].mod) == CLEANMASK(ev->state) + && keys[i].func) + keys[i].func(&(keys[i].arg)); +} + +void +killclient(const Arg *arg) +{ + if (!selmon->sel) + return; + if (!sendevent(selmon->sel, wmatom[WMDelete])) { + XGrabServer(dpy); + XSetErrorHandler(xerrordummy); + XSetCloseDownMode(dpy, DestroyAll); + XKillClient(dpy, selmon->sel->win); + XSync(dpy, False); + XSetErrorHandler(xerror); + XUngrabServer(dpy); + } +} + +void +manage(Window w, XWindowAttributes *wa) +{ + Client *c, *t = NULL; + Window trans = None; + XWindowChanges wc; + + c = ecalloc(1, sizeof(Client)); + c->win = w; + /* geometry */ + c->x = c->oldx = wa->x; + c->y = c->oldy = wa->y; + c->w = c->oldw = wa->width; + c->h = c->oldh = wa->height; + c->oldbw = wa->border_width; + + updatetitle(c); + if (XGetTransientForHint(dpy, w, &trans) && (t = wintoclient(trans))) { + c->mon = t->mon; + c->tags = t->tags; + } else { + c->mon = selmon; + applyrules(c); + } + + if (c->x + WIDTH(c) > c->mon->wx + c->mon->ww) + c->x = c->mon->wx + c->mon->ww - WIDTH(c); + if (c->y + HEIGHT(c) > c->mon->wy + c->mon->wh) + c->y = c->mon->wy + c->mon->wh - HEIGHT(c); + c->x = MAX(c->x, c->mon->wx); + c->y = MAX(c->y, c->mon->wy); + c->bw = borderpx; + + selmon->tagset[selmon->seltags] &= ~scratchtag; + if (!strcmp(c->name, scratchpadname)) { + c->mon->tagset[c->mon->seltags] |= c->tags = scratchtag; + c->isfloating = True; + c->x = c->mon->wx + (c->mon->ww / 2 - WIDTH(c) / 2); + c->y = c->mon->wy + (c->mon->wh / 2 - HEIGHT(c) / 2); + } + + wc.border_width = c->bw; + XConfigureWindow(dpy, w, CWBorderWidth, &wc); + XSetWindowBorder(dpy, w, scheme[SchemeNorm][ColBorder].pixel); + configure(c); /* propagates border_width, if size doesn't change */ + updatewindowtype(c); + updatesizehints(c); + updatewmhints(c); + c->x = c->mon->mx + (c->mon->mw - WIDTH(c)) / 2; + c->y = c->mon->my + (c->mon->mh - HEIGHT(c)) / 2; + XSelectInput(dpy, w, EnterWindowMask|FocusChangeMask|PropertyChangeMask|StructureNotifyMask); + grabbuttons(c, 0); + if (!c->isfloating) + c->isfloating = c->oldstate = trans != None || c->isfixed; + if (c->isfloating) + XRaiseWindow(dpy, c->win); + attach(c); + attachstack(c); + XChangeProperty(dpy, root, netatom[NetClientList], XA_WINDOW, 32, PropModeAppend, + (unsigned char *) &(c->win), 1); + XMoveResizeWindow(dpy, c->win, c->x + 2 * sw, c->y, c->w, c->h); /* some windows require this */ + setclientstate(c, NormalState); + if (c->mon == selmon) + unfocus(selmon->sel, 0); + c->mon->sel = c; + arrange(c->mon); + XMapWindow(dpy, c->win); + focus(NULL); +} + +void +mappingnotify(XEvent *e) +{ + XMappingEvent *ev = &e->xmapping; + + XRefreshKeyboardMapping(ev); + if (ev->request == MappingKeyboard) + grabkeys(); +} + +void +maprequest(XEvent *e) +{ + static XWindowAttributes wa; + XMapRequestEvent *ev = &e->xmaprequest; + + if (!XGetWindowAttributes(dpy, ev->window, &wa) || wa.override_redirect) + return; + if (!wintoclient(ev->window)) + manage(ev->window, &wa); +} + +void +monocle(Monitor *m) +{ + unsigned int n = 0; + Client *c; + + for (c = m->clients; c; c = c->next) + if (ISVISIBLE(c)) + n++; + if (n > 0) /* override layout symbol */ + snprintf(m->ltsymbol, sizeof m->ltsymbol, "[%d]", n); + for (c = nexttiled(m->clients); c; c = nexttiled(c->next)) + resize(c, m->wx, m->wy, m->ww - 2 * c->bw, m->wh - 2 * c->bw, 0); +} + +void +motionnotify(XEvent *e) +{ + static Monitor *mon = NULL; + Monitor *m; + XMotionEvent *ev = &e->xmotion; + + if (ev->window != root) + return; + if ((m = recttomon(ev->x_root, ev->y_root, 1, 1)) != mon && mon) { + unfocus(selmon->sel, 1); + selmon = m; + focus(NULL); + } + mon = m; +} + +void +movemouse(const Arg *arg) +{ + int x, y, ocx, ocy, nx, ny; + Client *c; + Monitor *m; + XEvent ev; + Time lasttime = 0; + + if (!(c = selmon->sel)) + return; + if (c->isfullscreen) /* no support moving fullscreen windows by mouse */ + return; + restack(selmon); + ocx = c->x; + ocy = c->y; + if (XGrabPointer(dpy, root, False, MOUSEMASK, GrabModeAsync, GrabModeAsync, + None, cursor[CurMove]->cursor, CurrentTime) != GrabSuccess) + return; + if (!getrootptr(&x, &y)) + return; + do { + XMaskEvent(dpy, MOUSEMASK|ExposureMask|SubstructureRedirectMask, &ev); + switch(ev.type) { + case ConfigureRequest: + case Expose: + case MapRequest: + handler[ev.type](&ev); + break; + case MotionNotify: + if ((ev.xmotion.time - lasttime) <= (1000 / 60)) + continue; + lasttime = ev.xmotion.time; + + nx = ocx + (ev.xmotion.x - x); + ny = ocy + (ev.xmotion.y - y); + if (abs(selmon->wx - nx) < snap) + nx = selmon->wx; + else if (abs((selmon->wx + selmon->ww) - (nx + WIDTH(c))) < snap) + nx = selmon->wx + selmon->ww - WIDTH(c); + if (abs(selmon->wy - ny) < snap) + ny = selmon->wy; + else if (abs((selmon->wy + selmon->wh) - (ny + HEIGHT(c))) < snap) + ny = selmon->wy + selmon->wh - HEIGHT(c); + if (!c->isfloating && selmon->lt[selmon->sellt]->arrange + && (abs(nx - c->x) > snap || abs(ny - c->y) > snap)) + togglefloating(NULL); + if (!selmon->lt[selmon->sellt]->arrange || c->isfloating) + resize(c, nx, ny, c->w, c->h, 1); + break; + } + } while (ev.type != ButtonRelease); + XUngrabPointer(dpy, CurrentTime); + if ((m = recttomon(c->x, c->y, c->w, c->h)) != selmon) { + sendmon(c, m); + selmon = m; + focus(NULL); + } +} + +Client * +nexttiled(Client *c) +{ + for (; c && (c->isfloating || !ISVISIBLE(c)); c = c->next); + return c; +} + +void +pop(Client *c) +{ + detach(c); + attach(c); + focus(c); + arrange(c->mon); +} + +void +propertynotify(XEvent *e) +{ + Client *c; + Window trans; + XPropertyEvent *ev = &e->xproperty; + + if ((ev->window == root) && (ev->atom == XA_WM_NAME)) + updatestatus(); + else if (ev->state == PropertyDelete) + return; /* ignore */ + else if ((c = wintoclient(ev->window))) { + switch(ev->atom) { + default: break; + case XA_WM_TRANSIENT_FOR: + if (!c->isfloating && (XGetTransientForHint(dpy, c->win, &trans)) && + (c->isfloating = (wintoclient(trans)) != NULL)) + arrange(c->mon); + break; + case XA_WM_NORMAL_HINTS: + c->hintsvalid = 0; + break; + case XA_WM_HINTS: + updatewmhints(c); + drawbars(); + break; + } + if (ev->atom == XA_WM_NAME || ev->atom == netatom[NetWMName]) { + updatetitle(c); + if (c == c->mon->sel) + drawbar(c->mon); + } + if (ev->atom == netatom[NetWMWindowType]) + updatewindowtype(c); + } +} + +void +quit(const Arg *arg) +{ + running = 0; +} + +Monitor * +recttomon(int x, int y, int w, int h) +{ + Monitor *m, *r = selmon; + int a, area = 0; + + for (m = mons; m; m = m->next) + if ((a = INTERSECT(x, y, w, h, m)) > area) { + area = a; + r = m; + } + return r; +} + +void +resize(Client *c, int x, int y, int w, int h, int interact) +{ + if (applysizehints(c, &x, &y, &w, &h, interact)) + resizeclient(c, x, y, w, h); +} + +void +resizeclient(Client *c, int x, int y, int w, int h) +{ + XWindowChanges wc; + + c->oldx = c->x; c->x = wc.x = x; + c->oldy = c->y; c->y = wc.y = y; + c->oldw = c->w; c->w = wc.width = w; + c->oldh = c->h; c->h = wc.height = h; + wc.border_width = c->bw; + XConfigureWindow(dpy, c->win, CWX|CWY|CWWidth|CWHeight|CWBorderWidth, &wc); + configure(c); + XSync(dpy, False); +} + +void +resizemouse(const Arg *arg) +{ + int ocx, ocy, nw, nh; + Client *c; + Monitor *m; + XEvent ev; + Time lasttime = 0; + + if (!(c = selmon->sel)) + return; + if (c->isfullscreen) /* no support resizing fullscreen windows by mouse */ + return; + restack(selmon); + ocx = c->x; + ocy = c->y; + if (XGrabPointer(dpy, root, False, MOUSEMASK, GrabModeAsync, GrabModeAsync, + None, cursor[CurResize]->cursor, CurrentTime) != GrabSuccess) + return; + XWarpPointer(dpy, None, c->win, 0, 0, 0, 0, c->w + c->bw - 1, c->h + c->bw - 1); + do { + XMaskEvent(dpy, MOUSEMASK|ExposureMask|SubstructureRedirectMask, &ev); + switch(ev.type) { + case ConfigureRequest: + case Expose: + case MapRequest: + handler[ev.type](&ev); + break; + case MotionNotify: + if ((ev.xmotion.time - lasttime) <= (1000 / 60)) + continue; + lasttime = ev.xmotion.time; + + nw = MAX(ev.xmotion.x - ocx - 2 * c->bw + 1, 1); + nh = MAX(ev.xmotion.y - ocy - 2 * c->bw + 1, 1); + if (c->mon->wx + nw >= selmon->wx && c->mon->wx + nw <= selmon->wx + selmon->ww + && c->mon->wy + nh >= selmon->wy && c->mon->wy + nh <= selmon->wy + selmon->wh) + { + if (!c->isfloating && selmon->lt[selmon->sellt]->arrange + && (abs(nw - c->w) > snap || abs(nh - c->h) > snap)) + togglefloating(NULL); + } + if (!selmon->lt[selmon->sellt]->arrange || c->isfloating) + resize(c, c->x, c->y, nw, nh, 1); + break; + } + } while (ev.type != ButtonRelease); + XWarpPointer(dpy, None, c->win, 0, 0, 0, 0, c->w + c->bw - 1, c->h + c->bw - 1); + XUngrabPointer(dpy, CurrentTime); + while (XCheckMaskEvent(dpy, EnterWindowMask, &ev)); + if ((m = recttomon(c->x, c->y, c->w, c->h)) != selmon) { + sendmon(c, m); + selmon = m; + focus(NULL); + } +} + +void +restack(Monitor *m) +{ + Client *c; + XEvent ev; + XWindowChanges wc; + + drawbar(m); + if (!m->sel) + return; + if (m->sel->isfloating || !m->lt[m->sellt]->arrange) + XRaiseWindow(dpy, m->sel->win); + if (m->lt[m->sellt]->arrange) { + wc.stack_mode = Below; + wc.sibling = m->barwin; + for (c = m->stack; c; c = c->snext) + if (!c->isfloating && ISVISIBLE(c)) { + XConfigureWindow(dpy, c->win, CWSibling|CWStackMode, &wc); + wc.sibling = c->win; + } + } + XSync(dpy, False); + while (XCheckMaskEvent(dpy, EnterWindowMask, &ev)); +} + +void +run(void) +{ + XEvent ev; + /* main event loop */ + XSync(dpy, False); + while (running && !XNextEvent(dpy, &ev)) + if (handler[ev.type]) + handler[ev.type](&ev); /* call handler */ +} + +void +scan(void) +{ + unsigned int i, num; + Window d1, d2, *wins = NULL; + XWindowAttributes wa; + + if (XQueryTree(dpy, root, &d1, &d2, &wins, &num)) { + for (i = 0; i < num; i++) { + if (!XGetWindowAttributes(dpy, wins[i], &wa) + || wa.override_redirect || XGetTransientForHint(dpy, wins[i], &d1)) + continue; + if (wa.map_state == IsViewable || getstate(wins[i]) == IconicState) + manage(wins[i], &wa); + } + for (i = 0; i < num; i++) { /* now the transients */ + if (!XGetWindowAttributes(dpy, wins[i], &wa)) + continue; + if (XGetTransientForHint(dpy, wins[i], &d1) + && (wa.map_state == IsViewable || getstate(wins[i]) == IconicState)) + manage(wins[i], &wa); + } + if (wins) + XFree(wins); + } +} + +void +sendmon(Client *c, Monitor *m) +{ + if (c->mon == m) + return; + unfocus(c, 1); + detach(c); + detachstack(c); + c->mon = m; + c->tags = m->tagset[m->seltags]; /* assign tags of target monitor */ + attach(c); + attachstack(c); + focus(NULL); + arrange(NULL); +} + +void +setclientstate(Client *c, long state) +{ + long data[] = { state, None }; + + XChangeProperty(dpy, c->win, wmatom[WMState], wmatom[WMState], 32, + PropModeReplace, (unsigned char *)data, 2); +} + +int +sendevent(Client *c, Atom proto) +{ + int n; + Atom *protocols; + int exists = 0; + XEvent ev; + + if (XGetWMProtocols(dpy, c->win, &protocols, &n)) { + while (!exists && n--) + exists = protocols[n] == proto; + XFree(protocols); + } + if (exists) { + ev.type = ClientMessage; + ev.xclient.window = c->win; + ev.xclient.message_type = wmatom[WMProtocols]; + ev.xclient.format = 32; + ev.xclient.data.l[0] = proto; + ev.xclient.data.l[1] = CurrentTime; + XSendEvent(dpy, c->win, False, NoEventMask, &ev); + } + return exists; +} + +void +setfocus(Client *c) +{ + if (!c->neverfocus) { + XSetInputFocus(dpy, c->win, RevertToPointerRoot, CurrentTime); + XChangeProperty(dpy, root, netatom[NetActiveWindow], + XA_WINDOW, 32, PropModeReplace, + (unsigned char *) &(c->win), 1); + } + sendevent(c, wmatom[WMTakeFocus]); +} + +void +setfullscreen(Client *c, int fullscreen) +{ + if (fullscreen && !c->isfullscreen) { + XChangeProperty(dpy, c->win, netatom[NetWMState], XA_ATOM, 32, + PropModeReplace, (unsigned char*)&netatom[NetWMFullscreen], 1); + c->isfullscreen = 1; + c->oldstate = c->isfloating; + c->oldbw = c->bw; + c->bw = 0; + c->isfloating = 1; + resizeclient(c, c->mon->mx, c->mon->my, c->mon->mw, c->mon->mh); + XRaiseWindow(dpy, c->win); + } else if (!fullscreen && c->isfullscreen){ + XChangeProperty(dpy, c->win, netatom[NetWMState], XA_ATOM, 32, + PropModeReplace, (unsigned char*)0, 0); + c->isfullscreen = 0; + c->isfloating = c->oldstate; + c->bw = c->oldbw; + c->x = c->oldx; + c->y = c->oldy; + c->w = c->oldw; + c->h = c->oldh; + resizeclient(c, c->x, c->y, c->w, c->h); + arrange(c->mon); + } +} + +void +setlayout(const Arg *arg) +{ + if (!arg || !arg->v || arg->v != selmon->lt[selmon->sellt]) + selmon->sellt ^= 1; + if (arg && arg->v) + selmon->lt[selmon->sellt] = (Layout *)arg->v; + strncpy(selmon->ltsymbol, selmon->lt[selmon->sellt]->symbol, sizeof selmon->ltsymbol); + if (selmon->sel) + arrange(selmon); + else + drawbar(selmon); +} + +/* arg > 1.0 will set mfact absolutely */ +void +setmfact(const Arg *arg) +{ + float f; + + if (!arg || !selmon->lt[selmon->sellt]->arrange) + return; + f = arg->f < 1.0 ? arg->f + selmon->mfact : arg->f - 1.0; + if (f < 0.05 || f > 0.95) + return; + selmon->mfact = f; + arrange(selmon); +} + +void +setup(void) +{ + int i; + XSetWindowAttributes wa; + Atom utf8string; + struct sigaction sa; + + /* do not transform children into zombies when they terminate */ + sigemptyset(&sa.sa_mask); + sa.sa_flags = SA_NOCLDSTOP | SA_NOCLDWAIT | SA_RESTART; + sa.sa_handler = SIG_IGN; + sigaction(SIGCHLD, &sa, NULL); + + /* clean up any zombies (inherited from .xinitrc etc) immediately */ + while (waitpid(-1, NULL, WNOHANG) > 0); + + /* init screen */ + screen = DefaultScreen(dpy); + sw = DisplayWidth(dpy, screen); + sh = DisplayHeight(dpy, screen); + root = RootWindow(dpy, screen); + drw = drw_create(dpy, screen, root, sw, sh); + if (!drw_fontset_create(drw, fonts, LENGTH(fonts))) + die("no fonts could be loaded."); + lrpad = drw->fonts->h; + bh = drw->fonts->h + 2; + updategeom(); + /* init atoms */ + utf8string = XInternAtom(dpy, "UTF8_STRING", False); + wmatom[WMProtocols] = XInternAtom(dpy, "WM_PROTOCOLS", False); + wmatom[WMDelete] = XInternAtom(dpy, "WM_DELETE_WINDOW", False); + wmatom[WMState] = XInternAtom(dpy, "WM_STATE", False); + wmatom[WMTakeFocus] = XInternAtom(dpy, "WM_TAKE_FOCUS", False); + netatom[NetActiveWindow] = XInternAtom(dpy, "_NET_ACTIVE_WINDOW", False); + netatom[NetSupported] = XInternAtom(dpy, "_NET_SUPPORTED", False); + netatom[NetWMName] = XInternAtom(dpy, "_NET_WM_NAME", False); + netatom[NetWMState] = XInternAtom(dpy, "_NET_WM_STATE", False); + netatom[NetWMCheck] = XInternAtom(dpy, "_NET_SUPPORTING_WM_CHECK", False); + netatom[NetWMFullscreen] = XInternAtom(dpy, "_NET_WM_STATE_FULLSCREEN", False); + netatom[NetWMWindowType] = XInternAtom(dpy, "_NET_WM_WINDOW_TYPE", False); + netatom[NetWMWindowTypeDialog] = XInternAtom(dpy, "_NET_WM_WINDOW_TYPE_DIALOG", False); + netatom[NetClientList] = XInternAtom(dpy, "_NET_CLIENT_LIST", False); + /* init cursors */ + cursor[CurNormal] = drw_cur_create(drw, XC_left_ptr); + cursor[CurResize] = drw_cur_create(drw, XC_sizing); + cursor[CurMove] = drw_cur_create(drw, XC_fleur); + /* init appearance */ + scheme = ecalloc(LENGTH(colors), sizeof(Clr *)); + for (i = 0; i < LENGTH(colors); i++) + scheme[i] = drw_scm_create(drw, colors[i], 3); + /* init bars */ + updatebars(); + updatestatus(); + /* supporting window for NetWMCheck */ + wmcheckwin = XCreateSimpleWindow(dpy, root, 0, 0, 1, 1, 0, 0, 0); + XChangeProperty(dpy, wmcheckwin, netatom[NetWMCheck], XA_WINDOW, 32, + PropModeReplace, (unsigned char *) &wmcheckwin, 1); + XChangeProperty(dpy, wmcheckwin, netatom[NetWMName], utf8string, 8, + PropModeReplace, (unsigned char *) "dwm", 3); + XChangeProperty(dpy, root, netatom[NetWMCheck], XA_WINDOW, 32, + PropModeReplace, (unsigned char *) &wmcheckwin, 1); + /* EWMH support per view */ + XChangeProperty(dpy, root, netatom[NetSupported], XA_ATOM, 32, + PropModeReplace, (unsigned char *) netatom, NetLast); + XDeleteProperty(dpy, root, netatom[NetClientList]); + /* select events */ + wa.cursor = cursor[CurNormal]->cursor; + wa.event_mask = SubstructureRedirectMask|SubstructureNotifyMask + |ButtonPressMask|PointerMotionMask|EnterWindowMask + |LeaveWindowMask|StructureNotifyMask|PropertyChangeMask; + XChangeWindowAttributes(dpy, root, CWEventMask|CWCursor, &wa); + XSelectInput(dpy, root, wa.event_mask); + grabkeys(); + focus(NULL); +} + +void +seturgent(Client *c, int urg) +{ + XWMHints *wmh; + + c->isurgent = urg; + if (!(wmh = XGetWMHints(dpy, c->win))) + return; + wmh->flags = urg ? (wmh->flags | XUrgencyHint) : (wmh->flags & ~XUrgencyHint); + XSetWMHints(dpy, c->win, wmh); + XFree(wmh); +} + +void +showhide(Client *c) +{ + if (!c) + return; + if (ISVISIBLE(c)) { + /* show clients top down */ + XMoveWindow(dpy, c->win, c->x, c->y); + if ((!c->mon->lt[c->mon->sellt]->arrange || c->isfloating) && !c->isfullscreen) + resize(c, c->x, c->y, c->w, c->h, 0); + showhide(c->snext); + } else { + /* hide clients bottom up */ + showhide(c->snext); + XMoveWindow(dpy, c->win, WIDTH(c) * -2, c->y); + } +} + +void +spawn(const Arg *arg) +{ + struct sigaction sa; + + if (arg->v == dmenucmd) + dmenumon[0] = '0' + selmon->num; + selmon->tagset[selmon->seltags] &= ~scratchtag; + if (fork() == 0) { + if (dpy) + close(ConnectionNumber(dpy)); + setsid(); + + sigemptyset(&sa.sa_mask); + sa.sa_flags = 0; + sa.sa_handler = SIG_DFL; + sigaction(SIGCHLD, &sa, NULL); + + execvp(((char **)arg->v)[0], (char **)arg->v); + die("dwm: execvp '%s' failed:", ((char **)arg->v)[0]); + } +} + +void +tag(const Arg *arg) +{ + if (selmon->sel && arg->ui & TAGMASK) { + selmon->sel->tags = arg->ui & TAGMASK; + focus(NULL); + arrange(selmon); + } +} + +void +tagmon(const Arg *arg) +{ + if (!selmon->sel || !mons->next) + return; + sendmon(selmon->sel, dirtomon(arg->i)); +} + +void +tile(Monitor *m) +{ + unsigned int i, n, h, mw, my, ty; + Client *c; + + for (n = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), n++); + if (n == 0) + return; + + if (n > m->nmaster) + mw = m->nmaster ? m->ww * m->mfact : 0; + else + mw = m->ww; + for (i = my = ty = 0, c = nexttiled(m->clients); c; c = nexttiled(c->next), i++) + if (i < m->nmaster) { + h = (m->wh - my) / (MIN(n, m->nmaster) - i); + resize(c, m->wx, m->wy + my, mw - (2*c->bw), h - (2*c->bw), 0); + if (my + HEIGHT(c) < m->wh) + my += HEIGHT(c); + } else { + h = (m->wh - ty) / (n - i); + resize(c, m->wx + mw, m->wy + ty, m->ww - mw - (2*c->bw), h - (2*c->bw), 0); + if (ty + HEIGHT(c) < m->wh) + ty += HEIGHT(c); + } +} + +void +togglebar(const Arg *arg) +{ + selmon->showbar = !selmon->showbar; + updatebarpos(selmon); + XMoveResizeWindow(dpy, selmon->barwin, selmon->wx, selmon->by, selmon->ww, bh); + arrange(selmon); +} + +void +togglefloating(const Arg *arg) +{ + if (!selmon->sel) + return; + if (selmon->sel->isfullscreen) /* no support for fullscreen windows */ + return; + selmon->sel->isfloating = !selmon->sel->isfloating || selmon->sel->isfixed; + if (selmon->sel->isfloating) + resize(selmon->sel, selmon->sel->x, selmon->sel->y, + selmon->sel->w, selmon->sel->h, 0); + arrange(selmon); +} + +void +togglescratch(const Arg *arg) +{ + Client *c; + unsigned int found = 0; + + for (c = selmon->clients; c && !(found = c->tags & scratchtag); c = c->next); + if (found) { + unsigned int newtagset = selmon->tagset[selmon->seltags] ^ scratchtag; + if (newtagset) { + selmon->tagset[selmon->seltags] = newtagset; + focus(NULL); + arrange(selmon); + } + if (ISVISIBLE(c)) { + focus(c); + restack(selmon); + } + } else + spawn(arg); +} +void +togglefullscr(const Arg *arg) +{ + if(selmon->sel) + setfullscreen(selmon->sel, !selmon->sel->isfullscreen); +} + +void +toggletag(const Arg *arg) +{ + unsigned int newtags; + + if (!selmon->sel) + return; + newtags = selmon->sel->tags ^ (arg->ui & TAGMASK); + if (newtags) { + selmon->sel->tags = newtags; + focus(NULL); + arrange(selmon); + } +} + +void +toggleview(const Arg *arg) +{ + unsigned int newtagset = selmon->tagset[selmon->seltags] ^ (arg->ui & TAGMASK); + + if (newtagset) { + selmon->tagset[selmon->seltags] = newtagset; + focus(NULL); + arrange(selmon); + } +} + +void +unfocus(Client *c, int setfocus) +{ + if (!c) + return; + grabbuttons(c, 0); + XSetWindowBorder(dpy, c->win, scheme[SchemeNorm][ColBorder].pixel); + if (setfocus) { + XSetInputFocus(dpy, root, RevertToPointerRoot, CurrentTime); + XDeleteProperty(dpy, root, netatom[NetActiveWindow]); + } +} + +void +unmanage(Client *c, int destroyed) +{ + Monitor *m = c->mon; + XWindowChanges wc; + + detach(c); + detachstack(c); + if (!destroyed) { + wc.border_width = c->oldbw; + XGrabServer(dpy); /* avoid race conditions */ + XSetErrorHandler(xerrordummy); + XSelectInput(dpy, c->win, NoEventMask); + XConfigureWindow(dpy, c->win, CWBorderWidth, &wc); /* restore border */ + XUngrabButton(dpy, AnyButton, AnyModifier, c->win); + setclientstate(c, WithdrawnState); + XSync(dpy, False); + XSetErrorHandler(xerror); + XUngrabServer(dpy); + } + free(c); + focus(NULL); + updateclientlist(); + arrange(m); +} + +void +unmapnotify(XEvent *e) +{ + Client *c; + XUnmapEvent *ev = &e->xunmap; + + if ((c = wintoclient(ev->window))) { + if (ev->send_event) + setclientstate(c, WithdrawnState); + else + unmanage(c, 0); + } +} + +void +updatebars(void) +{ + Monitor *m; + XSetWindowAttributes wa = { + .override_redirect = True, + .background_pixmap = ParentRelative, + .event_mask = ButtonPressMask|ExposureMask + }; + XClassHint ch = {"dwm", "dwm"}; + for (m = mons; m; m = m->next) { + if (m->barwin) + continue; + m->barwin = XCreateWindow(dpy, root, m->wx, m->by, m->ww, bh, 0, DefaultDepth(dpy, screen), + CopyFromParent, DefaultVisual(dpy, screen), + CWOverrideRedirect|CWBackPixmap|CWEventMask, &wa); + XDefineCursor(dpy, m->barwin, cursor[CurNormal]->cursor); + XMapRaised(dpy, m->barwin); + XSetClassHint(dpy, m->barwin, &ch); + } +} + +void +updatebarpos(Monitor *m) +{ + m->wy = m->my; + m->wh = m->mh; + if (m->showbar) { + m->wh -= bh; + m->by = m->topbar ? m->wy : m->wy + m->wh; + m->wy = m->topbar ? m->wy + bh : m->wy; + } else + m->by = -bh; +} + +void +updateclientlist() +{ + Client *c; + Monitor *m; + + XDeleteProperty(dpy, root, netatom[NetClientList]); + for (m = mons; m; m = m->next) + for (c = m->clients; c; c = c->next) + XChangeProperty(dpy, root, netatom[NetClientList], + XA_WINDOW, 32, PropModeAppend, + (unsigned char *) &(c->win), 1); +} + +int +updategeom(void) +{ + int dirty = 0; + +#ifdef XINERAMA + if (XineramaIsActive(dpy)) { + int i, j, n, nn; + Client *c; + Monitor *m; + XineramaScreenInfo *info = XineramaQueryScreens(dpy, &nn); + XineramaScreenInfo *unique = NULL; + + for (n = 0, m = mons; m; m = m->next, n++); + /* only consider unique geometries as separate screens */ + unique = ecalloc(nn, sizeof(XineramaScreenInfo)); + for (i = 0, j = 0; i < nn; i++) + if (isuniquegeom(unique, j, &info[i])) + memcpy(&unique[j++], &info[i], sizeof(XineramaScreenInfo)); + XFree(info); + nn = j; + + /* new monitors if nn > n */ + for (i = n; i < nn; i++) { + for (m = mons; m && m->next; m = m->next); + if (m) + m->next = createmon(); + else + mons = createmon(); + } + for (i = 0, m = mons; i < nn && m; m = m->next, i++) + if (i >= n + || unique[i].x_org != m->mx || unique[i].y_org != m->my + || unique[i].width != m->mw || unique[i].height != m->mh) + { + dirty = 1; + m->num = i; + m->mx = m->wx = unique[i].x_org; + m->my = m->wy = unique[i].y_org; + m->mw = m->ww = unique[i].width; + m->mh = m->wh = unique[i].height; + updatebarpos(m); + } + /* removed monitors if n > nn */ + for (i = nn; i < n; i++) { + for (m = mons; m && m->next; m = m->next); + while ((c = m->clients)) { + dirty = 1; + m->clients = c->next; + detachstack(c); + c->mon = mons; + attach(c); + attachstack(c); + } + if (m == selmon) + selmon = mons; + cleanupmon(m); + } + free(unique); + } else +#endif /* XINERAMA */ + { /* default monitor setup */ + if (!mons) + mons = createmon(); + if (mons->mw != sw || mons->mh != sh) { + dirty = 1; + mons->mw = mons->ww = sw; + mons->mh = mons->wh = sh; + updatebarpos(mons); + } + } + if (dirty) { + selmon = mons; + selmon = wintomon(root); + } + return dirty; +} + +void +updatenumlockmask(void) +{ + unsigned int i, j; + XModifierKeymap *modmap; + + numlockmask = 0; + modmap = XGetModifierMapping(dpy); + for (i = 0; i < 8; i++) + for (j = 0; j < modmap->max_keypermod; j++) + if (modmap->modifiermap[i * modmap->max_keypermod + j] + == XKeysymToKeycode(dpy, XK_Num_Lock)) + numlockmask = (1 << i); + XFreeModifiermap(modmap); +} + +void +updatesizehints(Client *c) +{ + long msize; + XSizeHints size; + + if (!XGetWMNormalHints(dpy, c->win, &size, &msize)) + /* size is uninitialized, ensure that size.flags aren't used */ + size.flags = PSize; + if (size.flags & PBaseSize) { + c->basew = size.base_width; + c->baseh = size.base_height; + } else if (size.flags & PMinSize) { + c->basew = size.min_width; + c->baseh = size.min_height; + } else + c->basew = c->baseh = 0; + if (size.flags & PResizeInc) { + c->incw = size.width_inc; + c->inch = size.height_inc; + } else + c->incw = c->inch = 0; + if (size.flags & PMaxSize) { + c->maxw = size.max_width; + c->maxh = size.max_height; + } else + c->maxw = c->maxh = 0; + if (size.flags & PMinSize) { + c->minw = size.min_width; + c->minh = size.min_height; + } else if (size.flags & PBaseSize) { + c->minw = size.base_width; + c->minh = size.base_height; + } else + c->minw = c->minh = 0; + if (size.flags & PAspect) { + c->mina = (float)size.min_aspect.y / size.min_aspect.x; + c->maxa = (float)size.max_aspect.x / size.max_aspect.y; + } else + c->maxa = c->mina = 0.0; + c->isfixed = (c->maxw && c->maxh && c->maxw == c->minw && c->maxh == c->minh); + c->hintsvalid = 1; +} + +void +updatestatus(void) +{ + if (!gettextprop(root, XA_WM_NAME, stext, sizeof(stext))) + strcpy(stext, "dwm-"VERSION); + drawbar(selmon); +} + +void +updatetitle(Client *c) +{ + if (!gettextprop(c->win, netatom[NetWMName], c->name, sizeof c->name)) + gettextprop(c->win, XA_WM_NAME, c->name, sizeof c->name); + if (c->name[0] == '\0') /* hack to mark broken clients */ + strcpy(c->name, broken); +} + +void +updatewindowtype(Client *c) +{ + Atom state = getatomprop(c, netatom[NetWMState]); + Atom wtype = getatomprop(c, netatom[NetWMWindowType]); + + if (state == netatom[NetWMFullscreen]) + setfullscreen(c, 1); + if (wtype == netatom[NetWMWindowTypeDialog]) + c->isfloating = 1; +} + +void +updatewmhints(Client *c) +{ + XWMHints *wmh; + + if ((wmh = XGetWMHints(dpy, c->win))) { + if (c == selmon->sel && wmh->flags & XUrgencyHint) { + wmh->flags &= ~XUrgencyHint; + XSetWMHints(dpy, c->win, wmh); + } else + c->isurgent = (wmh->flags & XUrgencyHint) ? 1 : 0; + if (wmh->flags & InputHint) + c->neverfocus = !wmh->input; + else + c->neverfocus = 0; + XFree(wmh); + } +} + +void +view(const Arg *arg) +{ + if ((arg->ui & TAGMASK) == selmon->tagset[selmon->seltags]) + return; + selmon->seltags ^= 1; /* toggle sel tagset */ + if (arg->ui & TAGMASK) + selmon->tagset[selmon->seltags] = arg->ui & TAGMASK; + focus(NULL); + arrange(selmon); +} + +Client * +wintoclient(Window w) +{ + Client *c; + Monitor *m; + + for (m = mons; m; m = m->next) + for (c = m->clients; c; c = c->next) + if (c->win == w) + return c; + return NULL; +} + +Monitor * +wintomon(Window w) +{ + int x, y; + Client *c; + Monitor *m; + + if (w == root && getrootptr(&x, &y)) + return recttomon(x, y, 1, 1); + for (m = mons; m; m = m->next) + if (w == m->barwin) + return m; + if ((c = wintoclient(w))) + return c->mon; + return selmon; +} + +/* There's no way to check accesses to destroyed windows, thus those cases are + * ignored (especially on UnmapNotify's). Other types of errors call Xlibs + * default error handler, which may call exit. */ +int +xerror(Display *dpy, XErrorEvent *ee) +{ + if (ee->error_code == BadWindow + || (ee->request_code == X_SetInputFocus && ee->error_code == BadMatch) + || (ee->request_code == X_PolyText8 && ee->error_code == BadDrawable) + || (ee->request_code == X_PolyFillRectangle && ee->error_code == BadDrawable) + || (ee->request_code == X_PolySegment && ee->error_code == BadDrawable) + || (ee->request_code == X_ConfigureWindow && ee->error_code == BadMatch) + || (ee->request_code == X_GrabButton && ee->error_code == BadAccess) + || (ee->request_code == X_GrabKey && ee->error_code == BadAccess) + || (ee->request_code == X_CopyArea && ee->error_code == BadDrawable)) + return 0; + fprintf(stderr, "dwm: fatal error: request code=%d, error code=%d\n", + ee->request_code, ee->error_code); + return xerrorxlib(dpy, ee); /* may call exit */ +} + +int +xerrordummy(Display *dpy, XErrorEvent *ee) +{ + return 0; +} + +/* Startup Error handler to check if another window manager + * is already running. */ +int +xerrorstart(Display *dpy, XErrorEvent *ee) +{ + die("dwm: another window manager is already running"); + return -1; +} + +void +zoom(const Arg *arg) +{ + Client *c = selmon->sel; + + if (!selmon->lt[selmon->sellt]->arrange || !c || c->isfloating) + return; + if (c == nexttiled(selmon->clients) && !(c = nexttiled(c->next))) + return; + pop(c); +} + +int +main(int argc, char *argv[]) +{ + if (argc == 2 && !strcmp("-v", argv[1])) + die("dwm-"VERSION); + else if (argc != 1) + die("usage: dwm [-v]"); + if (!setlocale(LC_CTYPE, "") || !XSupportsLocale()) + fputs("warning: no locale support\n", stderr); + if (!(dpy = XOpenDisplay(NULL))) + die("dwm: cannot open display"); + checkotherwm(); + setup(); +#ifdef __OpenBSD__ + if (pledge("stdio rpath proc exec", NULL) == -1) + die("pledge"); +#endif /* __OpenBSD__ */ + scan(); + run(); + cleanup(); + XCloseDisplay(dpy); + return EXIT_SUCCESS; +} diff --git a/hosts/vali/mars/dwm/dwm-6.5/dwm.c.rej b/hosts/vali/mars/dwm/dwm-6.5/dwm.c.rej new file mode 100644 index 0000000..10b98fd --- /dev/null +++ b/hosts/vali/mars/dwm/dwm-6.5/dwm.c.rej @@ -0,0 +1,23 @@ +--- dwm.c ++++ dwm.c +@@ -274,11 +279,19 @@ static Drw *drw; + static Monitor *mons, *selmon; + static Window root, wmcheckwin; + ++/* scratchpad */ ++#define SCRATCHPAD_MASK_1 (1u << sizeof tags / sizeof * tags) ++#define SCRATCHPAD_MASK_2 (1u << (sizeof tags / sizeof * tags + 1)) ++#define SCRATCHPAD_MASK_3 (1u << (sizeof tags / sizeof * tags + 2)) ++static int scratchpad_hide_flag = 0; ++static Client *scratchpad_last_showed_1 = NULL; ++static Client *scratchpad_last_showed_2 = NULL; ++static Client *scratchpad_last_showed_3 = NULL; + /* configuration, allows nested code to access above variables */ + #include "config.h" + + /* compile-time check if all tags fit into an unsigned int bit array. */ +-struct NumTags { char limitexceeded[LENGTH(tags) > 31 ? -1 : 1]; }; ++struct NumTags { char limitexceeded[LENGTH(tags) > 28 ? -1 : 1]; }; + + /* function implementations */ + void diff --git a/hosts/vali/mars/dwm/dwm-6.5/dwm.o b/hosts/vali/mars/dwm/dwm-6.5/dwm.o index e48aabbf016c630168214df4d4544eec04374458..167e75d11e0e21d9afa10ecd139c0e990adfa918 100644 GIT binary patch literal 59856 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 diff --git a/hosts/vali/mars/dwm/dwm.nix b/hosts/vali/mars/dwm/dwm.nix index 325f4f8..bc7670e 100644 --- a/hosts/vali/mars/dwm/dwm.nix +++ b/hosts/vali/mars/dwm/dwm.nix @@ -6,9 +6,11 @@ in { options.modules.programs.dwm.enable = mkEnableOption "dwm"; config = mkIf cfg.enable { - services.xserver = { + services.xserver = { enable = true; - xkb.layout = "de"; + layout = "de, de"; + xkbVariant = ",neo "; + xkbOptions = "grp:alt_space_toggle"; windowManager.dwm = { enable = true; }; @@ -24,12 +26,7 @@ in { }) ]; environment.systemPackages = with pkgs; [ - (st.overrideAttrs (oldAttrs: rec { src = ./st-0.9.2; })) - (dmenu.overrideAttrs (oldAttrs: rec { src = ./dmenu-5.3; })) + # (dmenu.overrideAttrs (oldAttrs: rec { src = ./dmenu-5.3; })) ]; - home-manager.users.${username} = { - programs.eww.enable = true; - programs.eww.configDir=./eww; - }; }; } diff --git a/hosts/vali/mars/dwm/eww/eww.scss b/hosts/vali/mars/dwm/eww/eww.scss deleted file mode 100644 index e69de29..0000000 diff --git a/hosts/vali/mars/dwm/eww/eww.yuck b/hosts/vali/mars/dwm/eww/eww.yuck deleted file mode 100644 index e69de29..0000000 diff --git a/hosts/vali/mars/programs.nix b/hosts/vali/mars/programs.nix index c0cb81c..0ce5632 100644 --- a/hosts/vali/mars/programs.nix +++ b/hosts/vali/mars/programs.nix @@ -36,7 +36,6 @@ in { httpie imagemagick keepassxc - kitty krita lazygit libreoffice-fresh @@ -48,6 +47,7 @@ in { neovim networkmanagerapplet nextcloud-client + nheko pamixer pavucontrol pcmanfm @@ -65,7 +65,6 @@ in { signal-desktop-beta smartmontools spotube - st steam strawberry telegram-desktop @@ -78,6 +77,7 @@ in { ventoy-full vesktop vlc + weechat wget xclip xfce.thunar diff --git a/modules/gui/default.nix b/modules/gui/default.nix index ff880a6..6296fc3 100644 --- a/modules/gui/default.nix +++ b/modules/gui/default.nix @@ -11,6 +11,7 @@ _: { ./foot.nix ./rofi.nix ./WM + ./kitty.nix ./vivado.nix ./alacritty.nix ./firefox.nix diff --git a/modules/gui/kitty.nix b/modules/gui/kitty.nix new file mode 100644 index 0000000..b665bc9 --- /dev/null +++ b/modules/gui/kitty.nix @@ -0,0 +1,78 @@ +{ config, lib, pkgs, ... }: +with lib; let + cfg = config.modules.programs.kitty; + username = config.modules.other.system.username; +in { + options.modules.programs.kitty.enable = mkEnableOption "kitty"; + + config = mkIf cfg.enable { + home-manager.users.${username} = { + programs.kitty = { + enable = true; + settings = { + font_size = "13.0"; + mouse_hide_wait = -1; + url_style = "curly"; + open_url_with = "default"; + background_opacity = "0.9"; + confirm_os_window_close = "0"; + font_family = "JetBrainsMono Nerd Font"; + + cursor_text_color = "background"; + + url_color = "#83a598"; + + visual_bell_color = "#8ec07c"; + bell_border_color = "#8ec07c"; + + active_border_color = "#d3869b"; + inactive_border_color = "#665c54"; + + foreground = "#ebdbb2"; + background = "#282828"; + selection_foreground = "#928374"; + selection_background = "#ebdbb2"; + + active_tab_foreground = "#fbf1c7"; + active_tab_background = "#665c54"; + inactive_tab_foreground = "#a89984"; + inactive_tab_background = "#3c3836"; + + # black (bg3/bg4) + color0 = "#665c54"; + color8 = "#7c6f64"; + + # red + color1 = "#cc241d"; + color9 = "#fb4934"; + + #: green + color2 = "#98971a"; + color10 = "#b8bb26"; + + # yellow + color3 = "#d79921"; + color11 = "#fabd2f"; + + # blue + color4 = "#458588"; + color12 = "#83a598"; + + # purple + color5 = "#b16286"; + color13 = "#d3869b"; + + # aqua + color6 = "#689d6a"; + color14 = "#8ec07c"; + + # white (fg4/fg3) + color7 = "#a89984"; + color15 = "#bdae93"; + }; + + }; + }; + }; + +} diff --git a/modules/tui/default.nix b/modules/tui/default.nix index 459fc7a..34ce59e 100644 --- a/modules/tui/default.nix +++ b/modules/tui/default.nix @@ -3,7 +3,7 @@ _: { ./btop.nix # ./helix.nix ./neovim.nix -# ./newsboat.nix + ./newsboat.nix ./ncmpcpp.nix ./yazi.nix ]; diff --git a/modules/tui/newsboat.nix b/modules/tui/newsboat.nix new file mode 100644 index 0000000..5fa69f2 --- /dev/null +++ b/modules/tui/newsboat.nix @@ -0,0 +1,73 @@ +{ + config, + lib, + ... +}: with lib; let + cfg = config.modules.programs.newsboat; + username = config.modules.other.system.username; +in { + options.modules.programs.newsboat.enable = mkEnableOption "newsboat"; + + config = mkIf cfg.enable { + home-manager.users.${username} = { + programs.newsboat = { + enable = true; + autoReload = true; + extraConfig = '' + download-full-page yes + download-retries 3 + error-log /dev/null + cookie-cache ~/.cache/newsboat/cookies.txt + bind-key j down + bind-key k up + bind-key G end + bind-key g home + bind-key d pagedown + bind-key u pageup + bind-key a toggle-article-read + + color listnormal color15 default + color listnormal_unread color2 default + color listfocus_unread color2 color0 + color listfocus default color0 + color background default default + color article default default + color end-of-text-marker color8 default + color info color4 color8 + color hint-separator default color8 + color hint-description default color8 + color title color14 color8 + + highlight article "^(Feed|Title|Author|Link|Date): .+" color4 default bold + highlight article "^(Feed|Title|Author|Link|Date):" color14 default bold + highlight article "\\((link|image|video)\\)" color8 default + highlight article "https?://[^ ]+" color4 default + highlight article "\[[0-9]+\]" color6 default bold + user-agent "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/107.0.0.0 Safari/537.36" + ''; + urls = [ + { + title = "NixOS Weekly"; + url = "https://weekly.nixos.org/feeds/all.rss.xml"; + } + { + title = "Hacker News"; + url = "https://hnrss.org/newest"; + } + { + title = "Phoronix"; + url = "https://www.phoronix.com/rss.php"; + } + { + title = "LWN"; + url = "https://lwn.net/headlines/rss"; + } + { + title = "Hyprland Commit Feed"; + url = "https://github.com/hyprwm/Hyprland/commits/main.atom"; + } + ]; + }; + }; + }; +} diff --git a/options/desktop/fonts.nix b/options/desktop/fonts.nix index 4496e88..247c40d 100644 --- a/options/desktop/fonts.nix +++ b/options/desktop/fonts.nix @@ -3,7 +3,7 @@ fonts.packages = with pkgs; [ material-design-icons (nerdfonts.override { - fonts = [ "JetBrainsMono"]; + # fonts = [ "JetBrains Mono"]; }) noto-fonts noto-fonts-cjk-sans