From e914d76acd7e9fc38bbbff83f4c1405d7bf5fed4 Mon Sep 17 00:00:00 2001 From: DreamMaoMao <2523610504@qq.com> Date: Mon, 29 Jun 2026 12:07:45 +0800 Subject: [PATCH] opt: optimize swallow in ipc action --- docs/window-management/rules.md | 2 +- src/action/client.h | 2 +- src/animation/client.h | 6 ++-- src/dispatch/bind_define.h | 7 ++++ src/ext-protocol/foreign-toplevel.h | 6 ++-- src/fetch/client.h | 8 ++--- src/ipc/ipc.h | 4 +++ src/mango.c | 56 ++++++++++++++++------------- 8 files changed, 55 insertions(+), 36 deletions(-) diff --git a/docs/window-management/rules.md b/docs/window-management/rules.md index 27ff8ab0..27216942 100644 --- a/docs/window-management/rules.md +++ b/docs/window-management/rules.md @@ -141,7 +141,7 @@ windowrule=offsetx:20,offsety:-30,width:800,height:600,appid:alacritty # Send to specific tag and monitor windowrule=tags:9,monitor:HDMI-A-1,appid:discord -# Terminal swallowing setup +# Terminal swallowdby setup windowrule=isterm:1,appid:st windowrule=noswallow:1,appid:foot diff --git a/src/action/client.h b/src/action/client.h index 6a180c8c..dce78d1e 100644 --- a/src/action/client.h +++ b/src/action/client.h @@ -84,7 +84,7 @@ void client_active(Client *c) { return; } - if (c->swallowing || !c->mon) + if (c->swallowdby || !c->mon) return; if (c->isminimized) { diff --git a/src/animation/client.h b/src/animation/client.h index 555bbf51..937ce3b6 100644 --- a/src/animation/client.h +++ b/src/animation/client.h @@ -1555,11 +1555,11 @@ void resize(Client *c, struct wlr_box geo, int32_t interact) { c->pending = c->geom; } - if (c->swallowedby && c->animation.action == OPEN) { - c->animainit_geom = c->swallowedby->animation.current; + if (c->swallowing && c->animation.action == OPEN) { + c->animainit_geom = c->swallowing->animation.current; } - if (c->swallowing) { + if (c->swallowdby) { c->animainit_geom = c->geom; } diff --git a/src/dispatch/bind_define.h b/src/dispatch/bind_define.h index 6215b962..4899808d 100644 --- a/src/dispatch/bind_define.h +++ b/src/dispatch/bind_define.h @@ -2196,6 +2196,13 @@ int32_t focusid(const Arg *arg) { return 0; Client *c = arg->tc; + + if (c->swallowdby) + return 0; + + if (c->group_next || c->group_prev) + client_focus_group_member(c); + client_active(c); return 0; } \ No newline at end of file diff --git a/src/ext-protocol/foreign-toplevel.h b/src/ext-protocol/foreign-toplevel.h index a8c49c77..eb5e7f0b 100644 --- a/src/ext-protocol/foreign-toplevel.h +++ b/src/ext-protocol/foreign-toplevel.h @@ -12,7 +12,7 @@ void handle_foreign_maximize_request(struct wl_listener *listener, void *data) { Client *c = wl_container_of(listener, c, foreign_maximize_request); struct wlr_foreign_toplevel_handle_v1_maximized_event *event = data; - if (c->swallowing || !c->mon) + if (c->swallowdby || !c->mon) return; if (c->ismaximizescreen && !event->maximized) { @@ -30,7 +30,7 @@ void handle_foreign_minimize_request(struct wl_listener *listener, void *data) { Client *c = wl_container_of(listener, c, foreign_minimize_request); struct wlr_foreign_toplevel_handle_v1_minimized_event *event = data; - if (c->swallowing || !c->mon) + if (c->swallowdby || !c->mon) return; if (!c->isminimized && event->minimized) { @@ -55,7 +55,7 @@ void handle_foreign_fullscreen_request(struct wl_listener *listener, Client *c = wl_container_of(listener, c, foreign_fullscreen_request); struct wlr_foreign_toplevel_handle_v1_fullscreen_event *event = data; - if (c->swallowing || !c->mon) + if (c->swallowdby || !c->mon) return; if (c->isfullscreen && !event->fullscreen) { diff --git a/src/fetch/client.h b/src/fetch/client.h index c67b9022..869f3da3 100644 --- a/src/fetch/client.h +++ b/src/fetch/client.h @@ -31,7 +31,7 @@ Client *termforwin(Client *w) { return NULL; wl_list_for_each(c, &fstack, flink) { - if (c->isterm && !c->swallowing && c->pid && + if (c->isterm && !c->swallowdby && c->pid && isdescprocess(c->pid, w->pid)) { return c; } @@ -48,9 +48,9 @@ Client *get_client_by_id_or_title(const char *arg_id, const char *arg_title) { continue; } - if (c->swallowedby) { - appid = client_get_appid(c->swallowedby); - title = client_get_title(c->swallowedby); + if (c->swallowing) { + appid = client_get_appid(c->swallowing); + title = client_get_title(c->swallowing); } else { appid = client_get_appid(c); title = client_get_title(c); diff --git a/src/ipc/ipc.h b/src/ipc/ipc.h index 9ac1a7b2..ee93ed23 100644 --- a/src/ipc/ipc.h +++ b/src/ipc/ipc.h @@ -148,6 +148,10 @@ static cJSON *build_client_json(Client *c) { cJSON_AddStringToObject(obj, "monitor", c->mon ? c->mon->wlr_output->name : ""); cJSON_AddItemToObject(obj, "tags", tags_mask_to_array(c->tags)); + cJSON_AddBoolToObject(obj, "is_swallowing", c->swallowing ? true : false); + cJSON_AddBoolToObject(obj, "is_swallowedby", c->swallowdby ? true : false); + cJSON_AddBoolToObject(obj, "is_group", c->group_prev || c->group_next); + cJSON_AddBoolToObject(obj, "is_visible", c->mon && VISIBLEON(c, c->mon)); cJSON_AddBoolToObject(obj, "is_focused", c->isfocusing); cJSON_AddBoolToObject(obj, "is_fullscreen", c->isfullscreen); cJSON_AddBoolToObject(obj, "is_floating", c->isfloating); diff --git a/src/mango.c b/src/mango.c index 47aa9497..12511672 100644 --- a/src/mango.c +++ b/src/mango.c @@ -432,7 +432,7 @@ struct Client { int32_t force_fakemaximize; int32_t force_tiled_state; pid_t pid; - Client *swallowing, *swallowedby; + Client *swallowdby, *swallowing; bool is_clip_to_hide; bool drag_to_tile; bool scratchpad_switching_mon; @@ -1719,7 +1719,7 @@ void client_reset_mon_tags(Client *c, Monitor *mon, uint32_t newtags) { } void check_match_tag_floating_rule(Client *c, Monitor *mon) { - if (c->tags && !c->isfloating && mon && !c->swallowedby && + if (c->tags && !c->isfloating && mon && !c->swallowing && mon->pertag->open_as_floating[get_tags_first_tag_num(c->tags)]) { c->isfloating = 1; } @@ -1849,8 +1849,8 @@ void applyrules(Client *c) { !c->surface.xdg->initial_commit) { Client *p = termforwin(c); if (p && !p->isminimized) { - c->swallowedby = p; - p->swallowing = c; + c->swallowing = p; + p->swallowdby = c; client_replace(c, p, false); @@ -4568,8 +4568,8 @@ void init_client_properties(Client *c) { c->overview_ismaximizescreenbak = 0; c->overview_isfloatingbak = 0; c->pid = 0; + c->swallowdby = NULL; c->swallowing = NULL; - c->swallowedby = NULL; c->ismaster = 0; c->old_ismaster = 0; c->isleftstack = 0; @@ -6798,16 +6798,11 @@ void unmapnotify(struct wl_listener *listener, void *data) { (!c->mon || VISIBLEON(c, c->mon))) init_fadeout_client(c); - if (c->ext_foreign_toplevel) { - wlr_ext_foreign_toplevel_handle_v1_destroy(c->ext_foreign_toplevel); - c->ext_foreign_toplevel = NULL; - } - // If the client is in a stack, remove it from the stack - if (c->swallowedby) { - c->swallowedby->mon = c->mon; - client_replace(c->swallowedby, c, false); + if (c->swallowing) { + c->swallowing->mon = c->mon; + client_replace(c->swallowing, c, false); } else if ((c->group_next || c->group_prev) && c->isgroupfocusing) { Client *group_replacement = c->group_next ? c->group_next : c->group_prev; @@ -6840,9 +6835,9 @@ void unmapnotify(struct wl_listener *listener, void *data) { } if (c->mon && c->mon == selmon) { - if (next_node && !c->swallowedby) { + if (next_node && !c->swallowing) { nextfocus = next_node->client; - } else if (prev_node && !c->swallowedby) { + } else if (prev_node && !c->swallowing) { nextfocus = prev_node->client; } else { nextfocus = focustop(selmon); @@ -6895,30 +6890,43 @@ void unmapnotify(struct wl_listener *listener, void *data) { c->foreign_toplevel = NULL; } - if (c->swallowedby) { - setmaximizescreen(c->swallowedby, c->ismaximizescreen, true); - setfullscreen(c->swallowedby, c->isfullscreen, true); - c->swallowedby->swallowing = NULL; - c->swallowedby = NULL; + if (c->ext_foreign_toplevel) { + wlr_ext_foreign_toplevel_handle_v1_destroy(c->ext_foreign_toplevel); + c->ext_foreign_toplevel = NULL; } if (c->swallowing) { - c->swallowing->swallowedby = NULL; + setmaximizescreen(c->swallowing, c->ismaximizescreen, true); + setfullscreen(c->swallowing, c->isfullscreen, true); + c->swallowing->swallowdby = NULL; c->swallowing = NULL; } + if (c->swallowdby) { + c->swallowdby->swallowing = NULL; + c->swallowdby = NULL; + } + if (c->jump_label_node) { mango_jump_label_node_destroy(c->jump_label_node); c->jump_label_node = NULL; } + if (c->group_bar) { mango_group_bar_destroy(c->group_bar); c->group_bar = NULL; } - wlr_scene_node_destroy(&c->image_capture_scene_surface->buffer->node); - wlr_scene_node_destroy(&c->image_capture_scene->tree.node); + if (c->image_capture_tree) { + wlr_scene_node_destroy(&c->image_capture_tree->node); + c->image_capture_tree = NULL; + } + if (c->image_capture_scene) { + wlr_scene_node_destroy(&c->image_capture_scene->tree.node); + c->image_capture_scene = NULL; + } + c->image_capture_source = NULL; init_client_properties(c); wlr_scene_node_destroy(&c->scene->node); @@ -7310,7 +7318,7 @@ void activatex11(struct wl_listener *listener, void *data) { if (!c || c->iskilling || !c->foreign_toplevel || client_is_unmanaged(c)) return; - if (c && c->swallowing) + if (c && c->swallowdby) return; if (c->isminimized) {