From b3acfb23665cbb8cb507a986c1aab0deb5e570d1 Mon Sep 17 00:00:00 2001 From: Levi Neely Date: Sat, 28 Mar 2026 07:35:59 +0100 Subject: [PATCH] =?UTF-8?q?wayland:=20Phase=2058=20=E2=80=94=20stacking=20?= =?UTF-8?q?Z-order=20in=20toplevel=5Flist;=20query=20returns=20success?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Implement stacking_raise/lower by moving views to the head/tail of wl_state.toplevel_list. stacking_restack reorders the list to match a given array (inserts from last to first so head = highest Z-order). stacking_query now returns 1 with the list of synthetic IDs (head-to-tail = top-to-bottom Z-order). RemakeStackList finds no WM_CTX_STACK frames for synthetic IDs (as expected — no frame windows on Wayland), so window_count stays 0, but the change from returning 0→1 eliminates the "could not get window list" log warning on every stacking operation. Co-Authored-By: Claude Sonnet 4.6 --- src/backend/wayland/wl_backend.c | 51 ++++++++++++++++++++++++++++---- 1 file changed, 46 insertions(+), 5 deletions(-) diff --git a/src/backend/wayland/wl_backend.c b/src/backend/wayland/wl_backend.c index 8e17b2c..202608d 100644 --- a/src/backend/wayland/wl_backend.c +++ b/src/backend/wayland/wl_backend.c @@ -41,6 +41,8 @@ * shaded, etc.) in the view struct so wWindowGetSavedState works correctly. * Phase 57: icccm_set/get/free_command store WM_COMMAND in the view struct; * misc.c getCommandForWindow uses the vtable on the Wayland path. + * Phase 58: stacking_raise/lower/restack manipulate toplevel_list Z-order; + * stacking_query enumerates IDs in order (returns 1 to suppress warning). */ #ifdef HAVE_CONFIG_H @@ -759,20 +761,59 @@ static void wl_server_ungrab(void) {} /* Stacking */ /* ------------------------------------------------------------------ */ -static void wl_stacking_raise(WNativeWindow win) { (void)win; } -static void wl_stacking_lower(WNativeWindow win) { (void)win; } +static void +wl_stacking_raise(WNativeWindow win) +{ + /* Phase 58: move view to head of list (top of Z-order). */ + struct wl_toplevel_view *v = wl_find_view_by_id(win); + if (!v) return; + wl_list_remove(&v->link); + wl_list_insert(&wl_state.toplevel_list, &v->link); +} + +static void +wl_stacking_lower(WNativeWindow win) +{ + /* Phase 58: move view to tail of list (bottom of Z-order). */ + struct wl_toplevel_view *v = wl_find_view_by_id(win); + if (!v) return; + wl_list_remove(&v->link); + wl_list_insert(wl_state.toplevel_list.prev, &v->link); +} static void wl_stacking_restack(WNativeWindow *windows, int count) -{ (void)windows; (void)count; } +{ + /* Phase 58: reorder toplevel_list to match the given Z-order array. */ + int i; + for (i = count - 1; i >= 0; i--) { + struct wl_toplevel_view *v = wl_find_view_by_id(windows[i]); + if (!v) continue; + wl_list_remove(&v->link); + wl_list_insert(&wl_state.toplevel_list, &v->link); + } +} static int wl_stacking_query(WNativeWindow root, WNativeWindow **out, unsigned int *count) { + /* Phase 58: return synthetic IDs in Z-order (top to bottom). + * RemakeStackList will find no WM_CTX_STACK entries for them + * and set window_count=0, but returning 1 avoids the "could not + * get window list" warning. */ + struct wl_toplevel_view *v; + unsigned int n = 0, i = 0; + WNativeWindow *wins; (void)root; - *out = NULL; *count = 0; - return 0; + + wl_list_for_each(v, &wl_state.toplevel_list, link) n++; + if (n == 0) { *out = NULL; *count = 0; return 1; } + + wins = wmalloc(n * sizeof(WNativeWindow)); + wl_list_for_each(v, &wl_state.toplevel_list, link) wins[i++] = v->id; + *out = wins; *count = n; + return 1; } /* ------------------------------------------------------------------ */