Implement freezing of updates during resize
Replace the unused meta_compositor_set_updates() with a reversed-meaning meta_compositor_set_updates_frozen(), and use it to implement freezing application window updates during interactive resizing. This avoids drawing new areas of the window with blank content before the application has a chance to repaint. https://bugzilla.gnome.org/show_bug.cgi?id=685463
This commit is contained in:
parent
3abaf506a6
commit
c9343e3ee3
@ -721,10 +721,18 @@ meta_compositor_remove_window (MetaCompositor *compositor,
|
||||
}
|
||||
|
||||
void
|
||||
meta_compositor_set_updates (MetaCompositor *compositor,
|
||||
MetaWindow *window,
|
||||
gboolean updates)
|
||||
meta_compositor_set_updates_frozen (MetaCompositor *compositor,
|
||||
MetaWindow *window,
|
||||
gboolean updates_frozen)
|
||||
{
|
||||
MetaWindowActor *window_actor;
|
||||
|
||||
DEBUG_TRACE ("meta_compositor_set_updates_frozen\n");
|
||||
window_actor = META_WINDOW_ACTOR (meta_window_get_compositor_private (window));
|
||||
if (!window_actor)
|
||||
return;
|
||||
|
||||
meta_window_actor_set_updates_frozen (window_actor, updates_frozen);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
|
@ -45,6 +45,8 @@ void meta_window_actor_update_shape (MetaWindowActor *self);
|
||||
void meta_window_actor_update_opacity (MetaWindowActor *self);
|
||||
void meta_window_actor_mapped (MetaWindowActor *self);
|
||||
void meta_window_actor_unmapped (MetaWindowActor *self);
|
||||
void meta_window_actor_set_updates_frozen (MetaWindowActor *self,
|
||||
gboolean updates_frozen);
|
||||
|
||||
cairo_region_t *meta_window_actor_get_obscured_region (MetaWindowActor *self);
|
||||
|
||||
|
@ -111,6 +111,7 @@ struct _MetaWindowActorPrivate
|
||||
guint recompute_focused_shadow : 1;
|
||||
guint recompute_unfocused_shadow : 1;
|
||||
guint size_changed : 1;
|
||||
guint updates_frozen : 1;
|
||||
|
||||
guint needs_destroy : 1;
|
||||
|
||||
@ -925,10 +926,16 @@ meta_window_actor_thaw (MetaWindowActor *self)
|
||||
if (self->priv->freeze_count)
|
||||
return;
|
||||
|
||||
/* We ignore moves and resizes on frozen windows */
|
||||
meta_window_actor_sync_actor_position (self);
|
||||
|
||||
/* We do this now since we might be going right back into the
|
||||
* frozen state */
|
||||
meta_window_actor_pre_paint (self);
|
||||
|
||||
/* Since we ignore damage events while a window is frozen for certain effects
|
||||
* we may need to issue an update_area() covering the whole pixmap if we
|
||||
* don't know what real damage has happened. */
|
||||
|
||||
if (self->priv->needs_damage_all)
|
||||
meta_window_actor_damage_all (self);
|
||||
}
|
||||
@ -1291,6 +1298,12 @@ meta_window_actor_destroy (MetaWindowActor *self)
|
||||
clutter_actor_destroy (CLUTTER_ACTOR (self));
|
||||
}
|
||||
|
||||
static gboolean
|
||||
is_frozen (MetaWindowActor *self)
|
||||
{
|
||||
return self->priv->freeze_count ? TRUE : FALSE;
|
||||
}
|
||||
|
||||
void
|
||||
meta_window_actor_sync_actor_position (MetaWindowActor *self)
|
||||
{
|
||||
@ -1299,6 +1312,9 @@ meta_window_actor_sync_actor_position (MetaWindowActor *self)
|
||||
|
||||
meta_window_get_input_rect (priv->window, &window_rect);
|
||||
|
||||
if (is_frozen (self))
|
||||
return;
|
||||
|
||||
if (priv->last_width != window_rect.width ||
|
||||
priv->last_height != window_rect.height)
|
||||
{
|
||||
@ -1496,6 +1512,9 @@ meta_window_actor_new (MetaWindow *window)
|
||||
if (priv->mapped)
|
||||
meta_window_actor_queue_create_pixmap (self);
|
||||
|
||||
meta_window_actor_set_updates_frozen (self,
|
||||
meta_window_updates_are_frozen (priv->window));
|
||||
|
||||
meta_window_actor_sync_actor_position (self);
|
||||
|
||||
/* Hang our compositor window state off the MetaWindow for fast retrieval */
|
||||
@ -1829,12 +1848,6 @@ check_needs_shadow (MetaWindowActor *self)
|
||||
meta_shadow_unref (old_shadow);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
is_frozen (MetaWindowActor *self)
|
||||
{
|
||||
return self->priv->freeze_count ? TRUE : FALSE;
|
||||
}
|
||||
|
||||
void
|
||||
meta_window_actor_process_damage (MetaWindowActor *self,
|
||||
XDamageNotifyEvent *event)
|
||||
@ -2328,3 +2341,21 @@ meta_window_actor_update_opacity (MetaWindowActor *self)
|
||||
self->priv->opacity = opacity;
|
||||
clutter_actor_set_opacity (self->priv->actor, opacity);
|
||||
}
|
||||
|
||||
void
|
||||
meta_window_actor_set_updates_frozen (MetaWindowActor *self,
|
||||
gboolean updates_frozen)
|
||||
{
|
||||
MetaWindowActorPrivate *priv = self->priv;
|
||||
|
||||
updates_frozen = updates_frozen != FALSE;
|
||||
|
||||
if (priv->updates_frozen != updates_frozen)
|
||||
{
|
||||
priv->updates_frozen = updates_frozen;
|
||||
if (updates_frozen)
|
||||
meta_window_actor_freeze (self);
|
||||
else
|
||||
meta_window_actor_thaw (self);
|
||||
}
|
||||
}
|
||||
|
@ -343,6 +343,9 @@ struct _MetaWindow
|
||||
/* if TRUE, window is attached to its parent */
|
||||
guint attached : 1;
|
||||
|
||||
/* if TRUE, we are freezing updates during a resize */
|
||||
guint updates_frozen_for_resize : 1;
|
||||
|
||||
/* if non-NULL, the bounds of the window frame */
|
||||
cairo_region_t *frame_bounds;
|
||||
|
||||
@ -663,4 +666,6 @@ gboolean meta_window_can_tile_side_by_side (MetaWindow *window);
|
||||
|
||||
void meta_window_compute_tile_match (MetaWindow *window);
|
||||
|
||||
gboolean meta_window_updates_are_frozen (MetaWindow *window);
|
||||
|
||||
#endif
|
||||
|
@ -4472,6 +4472,37 @@ send_sync_request (MetaWindow *window)
|
||||
}
|
||||
#endif
|
||||
|
||||
/**
|
||||
* meta_window_updates_are_frozen:
|
||||
* @window: a #MetaWindow
|
||||
*
|
||||
* Gets whether the compositor should be updating the window contents;
|
||||
* window content updates may be frozen at client request by setting
|
||||
* an odd value in the extended _NET_WM_SYNC_REQUEST_COUNTER counter r
|
||||
* by the window manager during a resize operation while waiting for
|
||||
* the client to redraw.
|
||||
*
|
||||
* Return value: %TRUE if updates are currently frozen
|
||||
*/
|
||||
gboolean
|
||||
meta_window_updates_are_frozen (MetaWindow *window)
|
||||
{
|
||||
return window->updates_frozen_for_resize;
|
||||
}
|
||||
|
||||
static void
|
||||
meta_window_set_updates_frozen_for_resize (MetaWindow *window,
|
||||
gboolean updates_frozen)
|
||||
{
|
||||
if (updates_frozen != window->updates_frozen_for_resize)
|
||||
{
|
||||
window->updates_frozen_for_resize = updates_frozen;
|
||||
if (window->display->compositor)
|
||||
meta_compositor_set_updates_frozen (window->display->compositor, window,
|
||||
meta_window_updates_are_frozen (window));
|
||||
}
|
||||
}
|
||||
|
||||
static gboolean
|
||||
maybe_move_attached_dialog (MetaWindow *window,
|
||||
void *data)
|
||||
@ -4972,8 +5003,7 @@ meta_window_move_resize_internal (MetaWindow *window,
|
||||
window->sync_request_time.tv_sec == 0)
|
||||
{
|
||||
/* turn off updating */
|
||||
if (window->display->compositor)
|
||||
meta_compositor_set_updates (window->display->compositor, window, FALSE);
|
||||
meta_window_set_updates_frozen_for_resize (window, TRUE);
|
||||
|
||||
send_sync_request (window);
|
||||
}
|
||||
@ -9159,8 +9189,7 @@ update_resize (MetaWindow *window,
|
||||
}
|
||||
|
||||
/* If we get here, it means the client should have redrawn itself */
|
||||
if (window->display->compositor)
|
||||
meta_compositor_set_updates (window->display->compositor, window, TRUE);
|
||||
meta_window_set_updates_frozen_for_resize (window, FALSE);
|
||||
|
||||
/* Remove any scheduled compensation events */
|
||||
if (window->display->grab_resize_timeout_id)
|
||||
@ -9442,8 +9471,7 @@ meta_window_handle_mouse_grab_op_event (MetaWindow *window,
|
||||
xev->root_x,
|
||||
xev->root_y,
|
||||
TRUE);
|
||||
if (window->display->compositor)
|
||||
meta_compositor_set_updates (window->display->compositor, window, TRUE);
|
||||
meta_window_set_updates_frozen_for_resize (window, FALSE);
|
||||
|
||||
/* If a tiled window has been dragged free with a
|
||||
* mouse resize without snapping back to the tiled
|
||||
|
@ -153,9 +153,9 @@ void meta_compositor_window_unmapped (MetaCompositor *compositor,
|
||||
MetaWindow *window);
|
||||
void meta_compositor_sync_window_geometry (MetaCompositor *compositor,
|
||||
MetaWindow *window);
|
||||
void meta_compositor_set_updates (MetaCompositor *compositor,
|
||||
void meta_compositor_set_updates_frozen (MetaCompositor *compositor,
|
||||
MetaWindow *window,
|
||||
gboolean updates);
|
||||
gboolean updates_frozen);
|
||||
|
||||
void meta_compositor_sync_stack (MetaCompositor *compositor,
|
||||
MetaScreen *screen,
|
||||
|
Loading…
Reference in New Issue
Block a user