11/*
2- * Copyright 2024 elementary, Inc. (https://elementary.io)
2+ * Copyright 2024-2025 elementary, Inc. (https://elementary.io)
33 * SPDX-License-Identifier: GPL-3.0-or-later
44 *
55 * Authored by: Leonhard Kargl <[email protected] > @@ -30,8 +30,10 @@ public class Gala.PanelWindow : ShellWindow, RootTarget {
3030
3131 public bool visible_in_multitasking_view { get ; private set ; default = false ; }
3232
33- private GestureController gesture_controller ;
33+ private GestureController user_gesture_controller ;
3434 private HideTracker hide_tracker;
35+ private GestureController workspace_gesture_controller;
36+ private WorkspaceHideTracker workspace_hide_tracker;
3537
3638 public PanelWindow (WindowManager wm, Meta . Window window, Pantheon . Desktop . Anchor anchor) {
3739 Object (wm: wm, anchor: anchor, window: window, position: Position . from_anchor (anchor));
@@ -55,33 +57,100 @@ public class Gala.PanelWindow : ShellWindow, RootTarget {
5557 notify[" width" ]. connect (update_strut);
5658 notify[" height" ]. connect (update_strut);
5759
58- gesture_controller = new GestureController (CUSTOM , wm);
59- add_gesture_controller (gesture_controller);
60+ user_gesture_controller = new GestureController (CUSTOM , wm) {
61+ progress = 1.0
62+ };
63+ add_gesture_controller (user_gesture_controller);
6064
6165 hide_tracker = new HideTracker (wm. get_display (), this );
6266 hide_tracker. hide. connect (hide);
6367 hide_tracker. show. connect (show);
68+
69+ workspace_gesture_controller = new GestureController (CUSTOM , wm);
70+ add_gesture_controller (workspace_gesture_controller);
71+
72+ workspace_hide_tracker = new WorkspaceHideTracker (window. display, update_overlap);
73+ workspace_hide_tracker. switching_workspace_progress_updated. connect ((value ) = > workspace_gesture_controller. progress = value );
74+ workspace_hide_tracker. window_state_changed_progress_updated. connect (workspace_gesture_controller. goto);
6475 }
6576
6677 public void request_visible_in_multitasking_view () {
6778 visible_in_multitasking_view = true ;
6879 actor. add_action (new DragDropAction (DESTINATION , " multitaskingview-window" ));
6980 }
7081
82+ protected override void update_target () {
83+ base . update_target ();
84+ workspace_hide_tracker. recalculate_all_workspaces ();
85+ }
86+
7187 protected override double get_hidden_progress () {
7288 if (visible_in_multitasking_view) {
73- return double . min (gesture_controller . progress, 1 - base . get_hidden_progress ());
89+ return double . min (double . min (user_gesture_controller . progress, workspace_gesture_controller . progress) , 1 - base . get_hidden_progress ());
7490 } else {
75- return double . max (gesture_controller . progress, base . get_hidden_progress ());
91+ return double . max (double . min (user_gesture_controller . progress, workspace_gesture_controller . progress) , base . get_hidden_progress ());
7692 }
7793 }
7894
95+ public override void propagate (GestureTarget . UpdateType update_type, GestureAction action, double progress) {
96+ workspace_hide_tracker. update (update_type, action, progress);
97+ base . propagate (update_type, action, progress);
98+ }
99+
79100 private void hide () {
80- gesture_controller . goto (1 );
101+ user_gesture_controller . goto (1 );
81102 }
82103
83104 private void show () {
84- gesture_controller. goto (0 );
105+ user_gesture_controller. goto (0 );
106+ }
107+
108+ private bool update_overlap (Meta . Workspace workspace) {
109+ var overlap = false ;
110+ var focus_overlap = false ;
111+ var focus_maximized_overlap = false ;
112+ var fullscreen_overlap = window. display. get_monitor_in_fullscreen (window. get_monitor ());
113+
114+ Meta . Window ? normal_mru_window, any_mru_window;
115+ normal_mru_window = InternalUtils . get_mru_window (workspace, out any_mru_window);
116+
117+ foreach (var window in workspace. list_windows ()) {
118+ if (window == this . window) {
119+ continue ;
120+ }
121+
122+ if (window. minimized) {
123+ continue ;
124+ }
125+
126+ var type = window. get_window_type ();
127+ if (type == DESKTOP || type == DOCK || type == MENU || type == SPLASHSCREEN ) {
128+ continue ;
129+ }
130+
131+ if (! get_custom_window_rect (). overlap (window. get_frame_rect ())) {
132+ continue ;
133+ }
134+
135+ overlap = true ;
136+
137+ if (window != normal_mru_window && window != any_mru_window) {
138+ continue ;
139+ }
140+
141+ focus_overlap = true ;
142+ focus_maximized_overlap = window. maximized_vertically;
143+ }
144+
145+ switch (hide_mode) {
146+ case MAXIMIZED_FOCUS_WINDOW : return focus_maximized_overlap;
147+ case OVERLAPPING_FOCUS_WINDOW : return focus_overlap;
148+ case OVERLAPPING_WINDOW : return overlap;
149+ case ALWAYS : return true ;
150+ case NEVER : return fullscreen_overlap;
151+ }
152+
153+ return false ;
85154 }
86155
87156 private void make_exclusive () {
0 commit comments