surface-actor-x11: Move window related unredirect logic to MetaWindowX11

Better to have the relevant object figure out whether it is a good
position to be unredirectable other than the actor, which should be
responsible for being composited.

https://gitlab.gnome.org/GNOME/mutter/merge_requests/798
This commit is contained in:
Jonas Ådahl 2019-08-20 21:46:50 +02:00
parent 0f8f607e4c
commit 5dad87cfb9
9 changed files with 100 additions and 70 deletions

View File

@ -260,33 +260,14 @@ meta_surface_actor_x11_is_opaque (MetaSurfaceActor *actor)
gboolean gboolean
meta_surface_actor_x11_should_unredirect (MetaSurfaceActorX11 *self) meta_surface_actor_x11_should_unredirect (MetaSurfaceActorX11 *self)
{ {
MetaWindow *window = self->window;
if (meta_window_requested_dont_bypass_compositor (window))
return FALSE;
if (window->opacity != 0xFF)
return FALSE;
if (window->shape_region != NULL)
return FALSE;
if (!meta_window_is_monitor_sized (window))
return FALSE;
if (meta_window_requested_bypass_compositor (window))
return TRUE;
if (!meta_surface_actor_x11_is_opaque (META_SURFACE_ACTOR (self))) if (!meta_surface_actor_x11_is_opaque (META_SURFACE_ACTOR (self)))
return FALSE; return FALSE;
if (meta_window_is_override_redirect (window)) if (!self->does_full_damage &&
return TRUE; !meta_window_is_override_redirect (self->window))
if (self->does_full_damage)
return TRUE;
return FALSE; return FALSE;
return TRUE;
} }
static void static void

View File

@ -39,6 +39,7 @@
#include "meta/meta-window-actor.h" #include "meta/meta-window-actor.h"
#include "meta/meta-x11-errors.h" #include "meta/meta-x11-errors.h"
#include "meta/window.h" #include "meta/window.h"
#include "x11/window-x11.h"
#include "x11/meta-x11-display-private.h" #include "x11/meta-x11-display-private.h"
#include "x11/window-x11.h" #include "x11/window-x11.h"
@ -540,12 +541,18 @@ has_shadow (MetaWindowActorX11 *actor_x11)
gboolean gboolean
meta_window_actor_x11_should_unredirect (MetaWindowActorX11 *actor_x11) meta_window_actor_x11_should_unredirect (MetaWindowActorX11 *actor_x11)
{ {
MetaWindow *window =
meta_window_actor_get_meta_window (META_WINDOW_ACTOR (actor_x11));
MetaWindowX11 *window_x11 = META_WINDOW_X11 (window);
MetaSurfaceActor *surface; MetaSurfaceActor *surface;
MetaSurfaceActorX11 *surface_x11; MetaSurfaceActorX11 *surface_x11;
if (meta_window_actor_is_destroyed (META_WINDOW_ACTOR (actor_x11))) if (meta_window_actor_is_destroyed (META_WINDOW_ACTOR (actor_x11)))
return FALSE; return FALSE;
if (!meta_window_x11_can_unredirect (window_x11))
return FALSE;
surface = meta_window_actor_get_surface (META_WINDOW_ACTOR (actor_x11)); surface = meta_window_actor_get_surface (META_WINDOW_ACTOR (actor_x11));
if (!surface) if (!surface)
return FALSE; return FALSE;

View File

@ -65,13 +65,6 @@ typedef enum
#define NUMBER_OF_QUEUES 3 #define NUMBER_OF_QUEUES 3
typedef enum
{
_NET_WM_BYPASS_COMPOSITOR_HINT_AUTO = 0,
_NET_WM_BYPASS_COMPOSITOR_HINT_ON = 1,
_NET_WM_BYPASS_COMPOSITOR_HINT_OFF = 2,
} MetaBypassCompositorHintValue;
typedef enum typedef enum
{ {
META_MOVE_RESIZE_CONFIGURE_REQUEST = 1 << 0, META_MOVE_RESIZE_CONFIGURE_REQUEST = 1 << 0,
@ -539,9 +532,6 @@ struct _MetaWindow
/* The currently complementary tiled window, if any */ /* The currently complementary tiled window, if any */
MetaWindow *tile_match; MetaWindow *tile_match;
/* Bypass compositor hints */
guint bypass_compositor;
struct { struct {
MetaPlacementRule *rule; MetaPlacementRule *rule;
MetaPlacementState state; MetaPlacementState state;

View File

@ -3018,30 +3018,6 @@ meta_window_is_on_primary_monitor (MetaWindow *window)
return window->monitor->is_primary; return window->monitor->is_primary;
} }
/**
* meta_window_requested_bypass_compositor:
* @window: a #MetaWindow
*
* Return value: %TRUE if the window requested to bypass the compositor
*/
gboolean
meta_window_requested_bypass_compositor (MetaWindow *window)
{
return window->bypass_compositor == _NET_WM_BYPASS_COMPOSITOR_HINT_ON;
}
/**
* meta_window_requested_dont_bypass_compositor:
* @window: a #MetaWindow
*
* Return value: %TRUE if the window requested to opt out of unredirecting
*/
gboolean
meta_window_requested_dont_bypass_compositor (MetaWindow *window)
{
return window->bypass_compositor == _NET_WM_BYPASS_COMPOSITOR_HINT_OFF;
}
static void static void
meta_window_get_tile_fraction (MetaWindow *window, meta_window_get_tile_fraction (MetaWindow *window,
MetaTileMode tile_mode, MetaTileMode tile_mode,

View File

@ -283,12 +283,6 @@ gboolean meta_window_is_monitor_sized (MetaWindow *window);
META_EXPORT META_EXPORT
gboolean meta_window_is_on_primary_monitor (MetaWindow *window); gboolean meta_window_is_on_primary_monitor (MetaWindow *window);
META_EXPORT
gboolean meta_window_requested_bypass_compositor (MetaWindow *window);
META_EXPORT
gboolean meta_window_requested_dont_bypass_compositor (MetaWindow *window);
META_EXPORT META_EXPORT
gboolean meta_window_get_icon_geometry (MetaWindow *window, gboolean meta_window_get_icon_geometry (MetaWindow *window,
MetaRectangle *rect); MetaRectangle *rect);

View File

@ -1755,23 +1755,28 @@ reload_bypass_compositor (MetaWindow *window,
MetaPropValue *value, MetaPropValue *value,
gboolean initial) gboolean initial)
{ {
int requested_value = 0; MetaWindowX11 *window_x11 = META_WINDOW_X11 (window);
int current_value = window->bypass_compositor; MetaWindowX11Private *priv = meta_window_x11_get_private (window_x11);
MetaBypassCompositorHint requested_value;
MetaBypassCompositorHint current_value;
if (value->type != META_PROP_VALUE_INVALID) if (value->type != META_PROP_VALUE_INVALID)
requested_value = (int) value->v.cardinal; requested_value = (MetaBypassCompositorHint) value->v.cardinal;
else
requested_value = META_BYPASS_COMPOSITOR_HINT_AUTO;
current_value = priv->bypass_compositor;
if (requested_value == current_value) if (requested_value == current_value)
return; return;
if (requested_value == _NET_WM_BYPASS_COMPOSITOR_HINT_ON) if (requested_value == META_BYPASS_COMPOSITOR_HINT_ON)
meta_verbose ("Request to bypass compositor for window %s.\n", window->desc); meta_verbose ("Request to bypass compositor for window %s.\n", window->desc);
else if (requested_value == _NET_WM_BYPASS_COMPOSITOR_HINT_OFF) else if (requested_value == META_BYPASS_COMPOSITOR_HINT_OFF)
meta_verbose ("Request to don't bypass compositor for window %s.\n", window->desc); meta_verbose ("Request to don't bypass compositor for window %s.\n", window->desc);
else if (requested_value != _NET_WM_BYPASS_COMPOSITOR_HINT_AUTO) else if (requested_value != META_BYPASS_COMPOSITOR_HINT_AUTO)
return; return;
window->bypass_compositor = requested_value; priv->bypass_compositor = requested_value;
} }
static void static void

View File

@ -29,6 +29,16 @@
G_BEGIN_DECLS G_BEGIN_DECLS
/*
* Mirrors _NET_WM_BYPASS_COMPOSITOR preference values.
*/
typedef enum _MetaBypassCompositorHint
{
META_BYPASS_COMPOSITOR_HINT_AUTO = 0,
META_BYPASS_COMPOSITOR_HINT_ON = 1,
META_BYPASS_COMPOSITOR_HINT_OFF = 2,
} MetaBypassCompositorHint;
typedef struct _MetaWindowX11Private MetaWindowX11Private; typedef struct _MetaWindowX11Private MetaWindowX11Private;
struct _MetaWindowX11Private struct _MetaWindowX11Private
@ -64,10 +74,16 @@ struct _MetaWindowX11Private
/* Freeze/thaw on resize (for Xwayland) */ /* Freeze/thaw on resize (for Xwayland) */
gboolean thaw_after_paint; gboolean thaw_after_paint;
/* Bypass compositor hints */
MetaBypassCompositorHint bypass_compositor;
}; };
MetaWindowX11Private * meta_window_x11_get_private (MetaWindowX11 *window_x11); MetaWindowX11Private * meta_window_x11_get_private (MetaWindowX11 *window_x11);
void meta_window_x11_set_bypass_compositor_hint (MetaWindowX11 *window_x11,
MetaBypassCompositorHint requested_value);
G_END_DECLS G_END_DECLS
#endif #endif

View File

@ -4121,3 +4121,62 @@ meta_window_x11_get_client_rect (MetaWindowX11 *window_x11)
return priv->client_rect; return priv->client_rect;
} }
static gboolean
has_requested_bypass_compositor (MetaWindowX11 *window_x11)
{
MetaWindowX11Private *priv = meta_window_x11_get_instance_private (window_x11);
return priv->bypass_compositor == META_BYPASS_COMPOSITOR_HINT_ON;
}
static gboolean
has_requested_dont_bypass_compositor (MetaWindowX11 *window_x11)
{
MetaWindowX11Private *priv = meta_window_x11_get_instance_private (window_x11);
return priv->bypass_compositor == META_BYPASS_COMPOSITOR_HINT_OFF;
}
gboolean
meta_window_x11_can_unredirect (MetaWindowX11 *window_x11)
{
MetaWindow *window = META_WINDOW (window_x11);
if (has_requested_dont_bypass_compositor (window_x11))
return FALSE;
if (window->opacity != 0xFF)
return FALSE;
if (window->shape_region != NULL)
return FALSE;
if (!window->monitor)
return FALSE;
if (window->fullscreen)
return TRUE;
if (meta_window_is_screen_sized (window))
return TRUE;
if (has_requested_bypass_compositor (window_x11))
return TRUE;
if (window->override_redirect)
{
MetaRectangle window_rect;
MetaRectangle logical_monitor_layout;
MetaLogicalMonitor *logical_monitor = window->monitor;
meta_window_get_frame_rect (window, &window_rect);
logical_monitor_layout =
meta_logical_monitor_get_layout (logical_monitor);
if (meta_rectangle_equal (&window_rect, &logical_monitor_layout))
return TRUE;
}
return FALSE;
}

View File

@ -98,4 +98,6 @@ void meta_window_x11_surface_rect_to_client_rect (MetaWindow *window,
MetaRectangle meta_window_x11_get_client_rect (MetaWindowX11 *window_x11); MetaRectangle meta_window_x11_get_client_rect (MetaWindowX11 *window_x11);
gboolean meta_window_x11_can_unredirect (MetaWindowX11 *window_x11);
#endif #endif