Add MUTTER_WM_CLASS_FILTER environment variable
In a performance or regression testing environment, we may want to only manage windows from a particular test program, and ignore all other windows. The MUTTER_WM_CLASS_FILTER environment variable is a list of WM_CLASS values that should be managed; other windows will be unmapped and ignored. https://bugzilla.gnome.org/show_bug.cgi?id=644252
This commit is contained in:
parent
6e6ed81c19
commit
9043191927
@ -64,6 +64,9 @@ static void recalc_window_type (MetaWindow *window);
|
||||
static void recalc_window_features (MetaWindow *window);
|
||||
static void invalidate_work_areas (MetaWindow *window);
|
||||
static void recalc_window_type (MetaWindow *window);
|
||||
static void set_wm_state_on_xwindow (MetaDisplay *display,
|
||||
Window xwindow,
|
||||
int state);
|
||||
static void set_wm_state (MetaWindow *window,
|
||||
int state);
|
||||
static void set_net_wm_state (MetaWindow *window);
|
||||
@ -517,6 +520,90 @@ meta_window_new (MetaDisplay *display,
|
||||
return window;
|
||||
}
|
||||
|
||||
/* The MUTTER_WM_CLASS_FILTER environment variable is designed for
|
||||
* performance and regression testing environments where we want to do
|
||||
* tests with only a limited set of windows and ignore all other windows
|
||||
*
|
||||
* When it is set to a comma separated list of WM_CLASS class names, all
|
||||
* windows not matching the list will be ignored.
|
||||
*
|
||||
* Returns TRUE if window has been filtered out and should be ignored.
|
||||
*/
|
||||
static gboolean
|
||||
maybe_filter_window (MetaDisplay *display,
|
||||
Window xwindow,
|
||||
gboolean must_be_viewable,
|
||||
XWindowAttributes *attrs)
|
||||
{
|
||||
static char **filter_wm_classes = NULL;
|
||||
static gboolean initialized = FALSE;
|
||||
XClassHint class_hint;
|
||||
gboolean filtered;
|
||||
Status success;
|
||||
int i;
|
||||
|
||||
if (!initialized)
|
||||
{
|
||||
const char *filter_string = g_getenv ("MUTTER_WM_CLASS_FILTER");
|
||||
if (filter_string)
|
||||
filter_wm_classes = g_strsplit (filter_string, ",", -1);
|
||||
initialized = TRUE;
|
||||
}
|
||||
|
||||
if (!filter_wm_classes || !filter_wm_classes[0])
|
||||
return FALSE;
|
||||
|
||||
filtered = TRUE;
|
||||
|
||||
meta_error_trap_push (display);
|
||||
success = XGetClassHint (display->xdisplay, xwindow, &class_hint);
|
||||
|
||||
if (success)
|
||||
{
|
||||
for (i = 0; filter_wm_classes[i]; i++)
|
||||
{
|
||||
if (strcmp (class_hint.res_class, filter_wm_classes[i]) == 0)
|
||||
{
|
||||
filtered = FALSE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
XFree (class_hint.res_name);
|
||||
XFree (class_hint.res_class);
|
||||
}
|
||||
|
||||
if (filtered)
|
||||
{
|
||||
/* We want to try and get the window managed by the next WM that come along,
|
||||
* so we need to make sure that windows that are requested to be mapped while
|
||||
* Mutter is running (!must_be_viewable), or windows already viewable at startup
|
||||
* get a non-withdrawn WM_STATE property. Previously unmapped windows are left
|
||||
* with whatever WM_STATE property they had.
|
||||
*/
|
||||
if (!must_be_viewable || attrs->map_state == IsViewable)
|
||||
{
|
||||
gulong old_state;
|
||||
|
||||
if (!meta_prop_get_cardinal_with_atom_type (display, xwindow,
|
||||
display->atom_WM_STATE,
|
||||
display->atom_WM_STATE,
|
||||
&old_state))
|
||||
old_state = WithdrawnState;
|
||||
|
||||
if (old_state == WithdrawnState)
|
||||
set_wm_state_on_xwindow (display, xwindow, NormalState);
|
||||
}
|
||||
|
||||
/* Make sure filtered windows are hidden from view */
|
||||
XUnmapWindow (display->xdisplay, xwindow);
|
||||
}
|
||||
|
||||
meta_error_trap_pop (display);
|
||||
|
||||
return filtered;
|
||||
}
|
||||
|
||||
MetaWindow*
|
||||
meta_window_new_with_attrs (MetaDisplay *display,
|
||||
Window xwindow,
|
||||
@ -579,6 +666,12 @@ meta_window_new_with_attrs (MetaDisplay *display,
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (maybe_filter_window (display, xwindow, must_be_viewable, attrs))
|
||||
{
|
||||
meta_verbose ("Not managing filtered window\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Grab server */
|
||||
meta_display_grab (display);
|
||||
meta_error_trap_push (display); /* Push a trap over all of window
|
||||
@ -1632,26 +1725,34 @@ meta_window_update_on_all_workspaces (MetaWindow *window)
|
||||
}
|
||||
|
||||
static void
|
||||
set_wm_state (MetaWindow *window,
|
||||
int state)
|
||||
set_wm_state_on_xwindow (MetaDisplay *display,
|
||||
Window xwindow,
|
||||
int state)
|
||||
{
|
||||
unsigned long data[2];
|
||||
|
||||
meta_verbose ("Setting wm state %s on %s\n",
|
||||
wm_state_to_string (state), window->desc);
|
||||
|
||||
/* Mutter doesn't use icon windows, so data[1] should be None
|
||||
* according to the ICCCM 2.0 Section 4.1.3.1.
|
||||
*/
|
||||
data[0] = state;
|
||||
data[1] = None;
|
||||
|
||||
meta_error_trap_push (window->display);
|
||||
XChangeProperty (window->display->xdisplay, window->xwindow,
|
||||
window->display->atom_WM_STATE,
|
||||
window->display->atom_WM_STATE,
|
||||
meta_error_trap_push (display);
|
||||
XChangeProperty (display->xdisplay, xwindow,
|
||||
display->atom_WM_STATE,
|
||||
display->atom_WM_STATE,
|
||||
32, PropModeReplace, (guchar*) data, 2);
|
||||
meta_error_trap_pop (window->display);
|
||||
meta_error_trap_pop (display);
|
||||
}
|
||||
|
||||
static void
|
||||
set_wm_state (MetaWindow *window,
|
||||
int state)
|
||||
{
|
||||
meta_verbose ("Setting wm state %s on %s\n",
|
||||
wm_state_to_string (state), window->desc);
|
||||
|
||||
set_wm_state_on_xwindow (window->display, window->xwindow, state);
|
||||
}
|
||||
|
||||
static void
|
||||
|
Loading…
Reference in New Issue
Block a user