From 1129be616d58b672ff9c6c264ce19e8e5ceff22c Mon Sep 17 00:00:00 2001 From: DreamMaoMao <2523610504@qq.com> Date: Tue, 25 Mar 2025 10:15:54 +0800 Subject: [PATCH 1/7] feat: add option focus_cross_monitor --- config.conf | 1 + maomao.c | 4 ++-- parse_config.h | 5 +++++ preset_config.h | 1 + 4 files changed, 9 insertions(+), 2 deletions(-) diff --git a/config.conf b/config.conf index 4910f69d..dc01b2a6 100644 --- a/config.conf +++ b/config.conf @@ -19,6 +19,7 @@ animation_curve_close=0.08,0.92,0,1 scroller_structs=20 scroller_default_proportion=0.8 scoller_focus_center=0 +focus_cross_monitor=0 scroller_proportion_preset=0.5,0.8,1.0 # Master-Stack Layout Setting (tile,spiral,dwindle) diff --git a/maomao.c b/maomao.c index d7986c00..ccdd1490 100644 --- a/maomao.c +++ b/maomao.c @@ -1684,7 +1684,7 @@ Client *direction_select(const Arg *arg) { // 第一次遍历,计算客户端数量 wl_list_for_each(c, &clients, link) { - if (c && (c->tags & c->mon->tagset[c->mon->seltags])) { + if (c && (focus_cross_monitor || c->mon == selmon) && (c->tags & c->mon->tagset[c->mon->seltags])) { last++; } } @@ -1703,7 +1703,7 @@ Client *direction_select(const Arg *arg) { // 第二次遍历,填充 tempClients last = -1; wl_list_for_each(c, &clients, link) { - if (c && (c->tags & c->mon->tagset[c->mon->seltags])) { + if (c && (focus_cross_monitor || c->mon == selmon) && (c->tags & c->mon->tagset[c->mon->seltags])) { last++; tempClients[last] = c; } diff --git a/parse_config.h b/parse_config.h index 5706053e..7c79ca16 100644 --- a/parse_config.h +++ b/parse_config.h @@ -93,6 +93,7 @@ typedef struct { int scroller_structs; float scroller_default_proportion; int scoller_focus_center; + int focus_cross_monitor; float *scroller_proportion_preset; int scroller_proportion_preset_count; @@ -552,6 +553,8 @@ void parse_config_line(Config *config, const char *line) { config->scroller_default_proportion = atof(value); } else if (strcmp(key, "scoller_focus_center") == 0) { config->scoller_focus_center = atoi(value); + } else if (strcmp(key, "focus_cross_monitor") == 0) { + config->focus_cross_monitor = atoi(value); } else if (strcmp(key, "scroller_proportion_preset") == 0) { // 1. 统计 value 中有多少个逗号,确定需要解析的浮点数个数 int count = 0; // 初始化为 0 @@ -1130,6 +1133,7 @@ void override_config(void) { scroller_structs = config.scroller_structs; scroller_default_proportion = config.scroller_default_proportion; scoller_focus_center = config.scoller_focus_center; + focus_cross_monitor = config.focus_cross_monitor; new_is_master = config.new_is_master; default_mfact = config.default_mfact; @@ -1208,6 +1212,7 @@ void set_value_default() { config.scroller_structs = 20; config.scroller_default_proportion = 0.9; config.scoller_focus_center = 0; + config.focus_cross_monitor = 0; config.bypass_surface_visibility = 0; /* 1 means idle inhibitors will disable idle tracking even if it's diff --git a/preset_config.h b/preset_config.h index 848593fd..535655cd 100644 --- a/preset_config.h +++ b/preset_config.h @@ -46,6 +46,7 @@ unsigned int gappov = 10; /* vert outer gap between windows and screen edge */ int scroller_structs = 20; float scroller_default_proportion = 0.9; int scoller_focus_center = 0; +int focus_cross_monitor = 0; int bypass_surface_visibility = 0; /* 1 means idle inhibitors will disable idle tracking even if it's From 5d2d5f7b2ffc6fa3ab459e1dcdd7d9f274816d41 Mon Sep 17 00:00:00 2001 From: DreamMaoMao <2523610504@qq.com> Date: Tue, 25 Mar 2025 10:23:07 +0800 Subject: [PATCH 2/7] fix: only current monitor frame event to flush animaiton --- maomao.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/maomao.c b/maomao.c index ccdd1490..f336ea19 100644 --- a/maomao.c +++ b/maomao.c @@ -4253,10 +4253,12 @@ void rendermon(struct wl_listener *listener, void *data) { // Draw frames for all clients wl_list_for_each(c, &clients, link) { + if(c->mon != m) continue; need_more_frames = client_draw_frame(c) || need_more_frames; } wl_list_for_each_safe(c, tmp, &fadeout_clients, fadeout_link) { + if(c->mon != m) continue; need_more_frames = client_draw_fadeout_frame(c) || need_more_frames; } From 68e323a804300743bbfff9e0b145720fad9f9002 Mon Sep 17 00:00:00 2001 From: DreamMaoMao <2523610504@qq.com> Date: Tue, 25 Mar 2025 10:31:07 +0800 Subject: [PATCH 3/7] opt: change some value to bool type --- maomao.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/maomao.c b/maomao.c index f336ea19..78f72b92 100644 --- a/maomao.c +++ b/maomao.c @@ -1334,8 +1334,8 @@ swallow(Client *c, Client *w) if(w->foreign_toplevel) remove_foreign_topleve(w); - wlr_scene_node_set_enabled(&w->scene->node, 0); - wlr_scene_node_set_enabled(&c->scene->node, 1); + wlr_scene_node_set_enabled(&w->scene->node, false); + wlr_scene_node_set_enabled(&c->scene->node, true); if(!c->foreign_toplevel && c->mon) add_foreign_toplevel(c); @@ -2779,7 +2779,7 @@ void destroylock(SessionLock *lock, int unlock) { if ((locked = !unlock)) goto destroy; - wlr_scene_node_set_enabled(&locked_bg->node, 0); + wlr_scene_node_set_enabled(&locked_bg->node, false); focusclient(focustop(selmon), 0); motionnotify(0, NULL, 0, 0, 0, 0); @@ -3679,7 +3679,7 @@ void killclient(const Arg *arg) { void locksession(struct wl_listener *listener, void *data) { struct wlr_session_lock_v1 *session_lock = data; SessionLock *lock; - wlr_scene_node_set_enabled(&locked_bg->node, 1); + wlr_scene_node_set_enabled(&locked_bg->node, true); if (cur_lock) { wlr_session_lock_v1_destroy(session_lock); return; @@ -5195,7 +5195,7 @@ void setup(void) { locked_bg = wlr_scene_rect_create(layers[LyrBlock], sgeom.width, sgeom.height, (float[4]){0.1, 0.1, 0.1, 1.0}); - wlr_scene_node_set_enabled(&locked_bg->node, 0); + wlr_scene_node_set_enabled(&locked_bg->node, false); /* Use decoration protocols to negotiate server-side decorations */ wlr_server_decoration_manager_set_default_mode( @@ -6084,7 +6084,7 @@ void unmaplayersurfacenotify(struct wl_listener *listener, void *data) { LayerSurface *l = wl_container_of(listener, l, unmap); l->mapped = 0; - wlr_scene_node_set_enabled(&l->scene->node, 0); + wlr_scene_node_set_enabled(&l->scene->node, false); if (l == exclusive_focus) exclusive_focus = NULL; if (l->layer_surface->output && (l->mon = l->layer_surface->output->data)) From a497205d33fd64e78184643f6e6525300b85366a Mon Sep 17 00:00:00 2001 From: DreamMaoMao <2523610504@qq.com> Date: Tue, 25 Mar 2025 10:36:53 +0800 Subject: [PATCH 4/7] opt:warp cursor to new mon after foucsmon --- maomao.c | 1 + 1 file changed, 1 insertion(+) diff --git a/maomao.c b/maomao.c index 78f72b92..51dbaa45 100644 --- a/maomao.c +++ b/maomao.c @@ -3214,6 +3214,7 @@ void focusmon(const Arg *arg) { selmon = dirtomon(arg->i); while (!selmon->wlr_output->enabled && i++ < nmons); } + warp_cursor_to_selmon(selmon); focusclient(focustop(selmon), 1); } From 4e689736e608bf942b7901e9ef2bdc1c92da66cb Mon Sep 17 00:00:00 2001 From: DreamMaoMao <2523610504@qq.com> Date: Tue, 25 Mar 2025 12:12:36 +0800 Subject: [PATCH 5/7] fix: tagmon miss scan window size --- maomao.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/maomao.c b/maomao.c index 51dbaa45..4d21822c 100644 --- a/maomao.c +++ b/maomao.c @@ -5432,14 +5432,14 @@ void tagmon(const Arg *arg) { if (c) { setmon(c, dirtomon(arg->i), 0); reset_foreign_tolevel(c); - selmon = c->mon; - c->geom.width = (int)(c->geom.width * selmon->m.width / c->mon->m.width); + c->geom.width = (int)(c->geom.width * c->mon->w.width / selmon->w.width); c->geom.height = - (int)(c->geom.height * selmon->m.height / c->mon->m.height); + (int)(c->geom.height * c->mon->w.height / selmon->w.height); + selmon = c->mon; // 重新计算居中的坐标 if (c->isfloating) { c->geom = setclient_coordinate_center(c->geom); - resize(c, c->geom, 0); + resize(c, c->geom, 1); } warp_cursor_to_selmon(c->mon); focusclient(c, 1); From ea63f40935b8d60a54e1f74fe732145e0425f526 Mon Sep 17 00:00:00 2001 From: DreamMaoMao <2523610504@qq.com> Date: Tue, 25 Mar 2025 12:39:27 +0800 Subject: [PATCH 6/7] fix: miss arrange when tagmon --- maomao.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/maomao.c b/maomao.c index 4d21822c..5c7d121a 100644 --- a/maomao.c +++ b/maomao.c @@ -5432,14 +5432,17 @@ void tagmon(const Arg *arg) { if (c) { setmon(c, dirtomon(arg->i), 0); reset_foreign_tolevel(c); - c->geom.width = (int)(c->geom.width * c->mon->w.width / selmon->w.width); - c->geom.height = - (int)(c->geom.height * c->mon->w.height / selmon->w.height); - selmon = c->mon; // 重新计算居中的坐标 if (c->isfloating) { + c->geom.width = (int)(c->geom.width * c->mon->w.width / selmon->w.width); + c->geom.height = + (int)(c->geom.height * c->mon->w.height / selmon->w.height); + selmon = c->mon; c->geom = setclient_coordinate_center(c->geom); resize(c, c->geom, 1); + } else { + selmon = c->mon; + arrange(selmon,false); } warp_cursor_to_selmon(c->mon); focusclient(c, 1); From d51d57860295317257e5f26703e9d9b28ac219b8 Mon Sep 17 00:00:00 2001 From: DreamMaoMao <2523610504@qq.com> Date: Tue, 25 Mar 2025 13:24:20 +0800 Subject: [PATCH 7/7] opt: optimize nix --- flake.lock | 55 ++++++++++++++++++++++++++++++++++ flake.nix | 10 ++++++- nix/default.nix | 4 +++ nix/nixos-modules.nix | 68 +++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 136 insertions(+), 1 deletion(-) create mode 100644 nix/nixos-modules.nix diff --git a/flake.lock b/flake.lock index 620452fb..6bce6d69 100644 --- a/flake.lock +++ b/flake.lock @@ -18,6 +18,45 @@ "type": "github" } }, + "flake-parts_2": { + "inputs": { + "nixpkgs-lib": "nixpkgs-lib_2" + }, + "locked": { + "lastModified": 1741352980, + "narHash": "sha256-+u2UunDA4Cl5Fci3m7S643HzKmIDAe+fiXrLqYsR2fs=", + "owner": "hercules-ci", + "repo": "flake-parts", + "rev": "f4330d22f1c5d2ba72d3d22df5597d123fdb60a9", + "type": "github" + }, + "original": { + "owner": "hercules-ci", + "repo": "flake-parts", + "type": "github" + } + }, + "mmsg": { + "inputs": { + "flake-parts": "flake-parts_2", + "nixpkgs": [ + "nixpkgs" + ] + }, + "locked": { + "lastModified": 1742777868, + "narHash": "sha256-MdHiygQjBoM22LUJSjeW87t7eDkfRLI2F4Nd64xdLX4=", + "owner": "DreamMaoMao", + "repo": "mmsg", + "rev": "6c9dc91e86a0eb89db3ef8f8290530441cb7b658", + "type": "github" + }, + "original": { + "owner": "DreamMaoMao", + "repo": "mmsg", + "type": "github" + } + }, "nixpkgs": { "locked": { "lastModified": 1740019556, @@ -46,9 +85,25 @@ "url": "https://github.com/NixOS/nixpkgs/archive/072a6db25e947df2f31aab9eccd0ab75d5b2da11.tar.gz" } }, + "nixpkgs-lib_2": { + "locked": { + "lastModified": 1740877520, + "narHash": "sha256-oiwv/ZK/2FhGxrCkQkB83i7GnWXPPLzoqFHpDD3uYpk=", + "owner": "nix-community", + "repo": "nixpkgs.lib", + "rev": "147dee35aab2193b174e4c0868bd80ead5ce755c", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "nixpkgs.lib", + "type": "github" + } + }, "root": { "inputs": { "flake-parts": "flake-parts", + "mmsg": "mmsg", "nixpkgs": "nixpkgs", "treefmt-nix": "treefmt-nix" } diff --git a/flake.nix b/flake.nix index 866bb7fc..6b52aed6 100644 --- a/flake.nix +++ b/flake.nix @@ -6,10 +6,15 @@ url = "github:numtide/treefmt-nix"; inputs.nixpkgs.follows = "nixpkgs"; }; + mmsg = { + url = "github:DreamMaoMao/mmsg"; + inputs.nixpkgs.follows = "nixpkgs"; + }; }; outputs = { + self, flake-parts, treefmt-nix, ... @@ -19,7 +24,10 @@ inputs.flake-parts.flakeModules.easyOverlay ]; - flake.hmModules.maomaowm = import ./nix/hm-modules.nix; + flake = { + hmModules.maomaowm = import ./nix/hm-modules.nix; + nixosModules.maomaowm = import ./nix/nixos-modules.nix { inherit inputs self; }; + }; perSystem = { diff --git a/nix/default.nix b/nix/default.nix index 8cca30b1..d76f4af3 100644 --- a/nix/default.nix +++ b/nix/default.nix @@ -49,6 +49,10 @@ stdenv.mkDerivation { xwayland ]; + passthru = { + providedSessions = [ "maomao" ]; + }; + meta = { mainProgram = "maomao"; description = "A streamlined but feature-rich Wayland compositor"; diff --git a/nix/nixos-modules.nix b/nix/nixos-modules.nix new file mode 100644 index 00000000..fc570b94 --- /dev/null +++ b/nix/nixos-modules.nix @@ -0,0 +1,68 @@ +{ inputs, self }: +{ + config, + lib, + pkgs, + ... +}: +let + cfg = config.programs.maomaowm; + mmsg = lib.types.submodule { + options = { + enable = lib.mkEnableOption "Enable mmsg, the ipc for maomaowm"; + package = lib.mkOption { + type = lib.types.package; + default = inputs.mmsg.packages.${pkgs.system}.mmsg; + description = "The mmsg package to use"; + }; + }; + }; +in +{ + options = { + programs.maomaowm = { + enable = lib.mkEnableOption "maomaowm, a wayland compositor based on dwl"; + package = lib.mkOption { + type = lib.types.package; + default = self.packages.${pkgs.system}.maomaowm; + description = "The maomaowm package to use"; + }; + mmsg = lib.mkOption { + type = mmsg; + default = { + enable = true; + }; + description = "Options for mmsg, the ipc for maomaowm"; + }; + }; + }; + + config = lib.mkMerge [ + (lib.mkIf cfg.enable { + environment.systemPackages = [ cfg.package ]; + + xdg.portal = { + enable = lib.mkDefault true; + + wlr.enable = lib.mkDefault true; + + configPackages = [ cfg.package ]; + }; + + security.polkit.enable = lib.mkDefault true; + + programs.xwayland.enable = lib.mkDefault true; + + services = { + displayManager.sessionPackages = [ cfg.package ]; + + graphical-desktop.enable = lib.mkDefault true; + }; + + }) + + (lib.mkIf cfg.mmsg.enable { + environment.systemPackages = [ cfg.mmsg.package ]; + }) + ]; +}