From 28a898a22f82449cce524773bbdd24246e53bf9d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jonas=20=C3=85dahl?= Date: Wed, 8 Jun 2016 13:07:09 +0800 Subject: [PATCH] Use signals instead of onscreen framebuffer frame callbacks CoglFrameInfo is a frame info container associated with a single onscreen framebuffer. The clutter stage will eventually support drawing a stage frame with multiple onscreen framebuffers, thus needs its own frame info container. This patch introduces a new stage signal 'presented' and a accompaning ClutterFrameInfo and adapts the stage windows and past onscreen frame callbacks users to use the signal and new info container. https://bugzilla.gnome.org/show_bug.cgi?id=768976 --- clutter/clutter/clutter-mutter.h | 5 -- clutter/clutter/clutter-stage-private.h | 4 ++ clutter/clutter/clutter-stage-window.c | 19 ------ clutter/clutter/clutter-stage-window.h | 12 ---- clutter/clutter/clutter-stage.c | 38 ++++++++---- clutter/clutter/clutter-stage.h | 10 +++ clutter/clutter/clutter-types.h | 1 + clutter/clutter/cogl/clutter-stage-cogl.c | 34 ++++------- clutter/clutter/cogl/clutter-stage-cogl.h | 7 ++- clutter/clutter/x11/clutter-stage-x11.c | 59 ++++++++++-------- clutter/clutter/x11/clutter-stage-x11.h | 2 + cogl/cogl/cogl-frame-info-private.h | 2 + cogl/cogl/cogl-frame-info.c | 6 ++ cogl/cogl/cogl-frame-info.h | 5 ++ cogl/cogl/cogl-mutter.h | 1 + src/backends/native/meta-stage-native.c | 71 ++++++++++++---------- src/compositor/compositor-private.h | 1 - src/compositor/compositor.c | 29 ++++----- src/compositor/meta-window-actor-private.h | 2 +- src/compositor/meta-window-actor.c | 12 ++-- 20 files changed, 166 insertions(+), 154 deletions(-) diff --git a/clutter/clutter/clutter-mutter.h b/clutter/clutter/clutter-mutter.h index cdb6e4b64..b820e6b84 100644 --- a/clutter/clutter/clutter-mutter.h +++ b/clutter/clutter/clutter-mutter.h @@ -37,11 +37,6 @@ void clutter_set_custom_backend_func (ClutterBackend *(* func) (void)); CLUTTER_AVAILABLE_IN_MUTTER gboolean _clutter_get_sync_to_vblank (void); -CLUTTER_AVAILABLE_IN_MUTTER -CoglFrameClosure *clutter_stage_add_frame_callback (ClutterStage *stage, - CoglFrameCallback callback, - gpointer user_data); - CLUTTER_AVAILABLE_IN_MUTTER int64_t clutter_stage_get_frame_counter (ClutterStage *stage); diff --git a/clutter/clutter/clutter-stage-private.h b/clutter/clutter/clutter-stage-private.h index 6e06cf10f..517c9adda 100644 --- a/clutter/clutter/clutter-stage-private.h +++ b/clutter/clutter/clutter-stage-private.h @@ -125,6 +125,10 @@ gboolean _clutter_stage_update_state (ClutterStage *stag void _clutter_stage_set_scale_factor (ClutterStage *stage, int factor); +void _clutter_stage_presented (ClutterStage *stage, + CoglFrameEvent frame_event, + ClutterFrameInfo *frame_info); + G_END_DECLS #endif /* __CLUTTER_STAGE_PRIVATE_H__ */ diff --git a/clutter/clutter/clutter-stage-window.c b/clutter/clutter/clutter-stage-window.c index c6e7780df..97eb5e4be 100644 --- a/clutter/clutter/clutter-stage-window.c +++ b/clutter/clutter/clutter-stage-window.c @@ -338,25 +338,6 @@ _clutter_stage_window_get_views (ClutterStageWindow *window) return iface->get_views (window); } -CoglFrameClosure * -_clutter_stage_window_set_frame_callback (ClutterStageWindow *window, - CoglFrameCallback callback, - gpointer user_data) -{ - ClutterStageWindowIface *iface = CLUTTER_STAGE_WINDOW_GET_IFACE (window); - - return iface->set_frame_callback (window, callback, user_data); -} - -void -_clutter_stage_window_remove_frame_callback (ClutterStageWindow *window, - CoglFrameClosure *closure) -{ - ClutterStageWindowIface *iface = CLUTTER_STAGE_WINDOW_GET_IFACE (window); - - iface->remove_frame_callback (window, closure); -} - void _clutter_stage_window_finish_frame (ClutterStageWindow *window) { diff --git a/clutter/clutter/clutter-stage-window.h b/clutter/clutter/clutter-stage-window.h index 947eb87a4..452f9dede 100644 --- a/clutter/clutter/clutter-stage-window.h +++ b/clutter/clutter/clutter-stage-window.h @@ -87,11 +87,6 @@ struct _ClutterStageWindowIface int factor); int (* get_scale_factor) (ClutterStageWindow *stage_window); GList *(* get_views) (ClutterStageWindow *stage_window); - CoglFrameClosure *(* set_frame_callback) (ClutterStageWindow *stage_window, - CoglFrameCallback callback, - gpointer user_data); - void (* remove_frame_callback) (ClutterStageWindow *stage_window, - CoglFrameClosure *closure); int64_t (* get_frame_counter) (ClutterStageWindow *stage_window); void (* finish_frame) (ClutterStageWindow *stage_window); }; @@ -151,13 +146,6 @@ int _clutter_stage_window_get_scale_factor (ClutterStageWin GList * _clutter_stage_window_get_views (ClutterStageWindow *window); -CoglFrameClosure *_clutter_stage_window_set_frame_callback (ClutterStageWindow *window, - CoglFrameCallback callback, - gpointer user_data); - -void _clutter_stage_window_remove_frame_callback (ClutterStageWindow *stage_winow, - CoglFrameClosure *closure); - void _clutter_stage_window_finish_frame (ClutterStageWindow *window); int64_t _clutter_stage_window_get_frame_counter (ClutterStageWindow *window); diff --git a/clutter/clutter/clutter-stage.c b/clutter/clutter/clutter-stage.c index 6e5343546..804126220 100644 --- a/clutter/clutter/clutter-stage.c +++ b/clutter/clutter/clutter-stage.c @@ -190,6 +190,7 @@ enum DEACTIVATE, DELETE_EVENT, AFTER_PAINT, + PRESENTED, LAST_SIGNAL }; @@ -2167,6 +2168,21 @@ clutter_stage_class_init (ClutterStageClass *klass) NULL, NULL, NULL, G_TYPE_NONE, 0); + /** + * ClutterStage::presented: (skip) + * @stage: the stage that received the event + * @frame_event: a #CoglFrameEvent + * @frame_info: a #ClutterFrameInfo + */ + stage_signals[PRESENTED] = + g_signal_new (I_("presented"), + G_TYPE_FROM_CLASS (gobject_class), + G_SIGNAL_RUN_LAST, + 0, + NULL, NULL, NULL, + G_TYPE_NONE, 2, + G_TYPE_INT, G_TYPE_POINTER); + klass->fullscreen = clutter_stage_real_fullscreen; klass->activate = clutter_stage_real_activate; klass->deactivate = clutter_stage_real_deactivate; @@ -4628,19 +4644,6 @@ _clutter_stage_set_scale_factor (ClutterStage *stage, clutter_actor_queue_redraw (CLUTTER_ACTOR (stage)); } -CoglFrameClosure * -clutter_stage_add_frame_callback (ClutterStage *stage, - CoglFrameCallback callback, - gpointer user_data) -{ - ClutterStageWindow *stage_window; - - stage_window = _clutter_stage_get_window (stage); - return _clutter_stage_window_set_frame_callback (stage_window, - callback, - user_data); -} - int64_t clutter_stage_get_frame_counter (ClutterStage *stage) { @@ -4649,3 +4652,12 @@ clutter_stage_get_frame_counter (ClutterStage *stage) stage_window = _clutter_stage_get_window (stage); return _clutter_stage_window_get_frame_counter (stage_window); } + +void +_clutter_stage_presented (ClutterStage *stage, + CoglFrameEvent frame_event, + ClutterFrameInfo *frame_info) +{ + g_signal_emit (stage, stage_signals[PRESENTED], 0, + (int) frame_event, frame_info); +} diff --git a/clutter/clutter/clutter-stage.h b/clutter/clutter/clutter-stage.h index 47cff935a..e0911bce0 100644 --- a/clutter/clutter/clutter-stage.h +++ b/clutter/clutter/clutter-stage.h @@ -135,6 +135,16 @@ struct _ClutterFog gfloat z_far; }; +/** + * ClutterFrameInfo: (skip) + */ +struct _ClutterFrameInfo +{ + int64_t frame_counter; + int64_t presentation_time; + float refresh_rate; +}; + CLUTTER_AVAILABLE_IN_ALL GType clutter_perspective_get_type (void) G_GNUC_CONST; CLUTTER_DEPRECATED_IN_1_10 diff --git a/clutter/clutter/clutter-types.h b/clutter/clutter/clutter-types.h index fd4c7669a..1e26105fb 100644 --- a/clutter/clutter/clutter-types.h +++ b/clutter/clutter/clutter-types.h @@ -51,6 +51,7 @@ G_BEGIN_DECLS typedef struct _ClutterActor ClutterActor; typedef struct _ClutterStage ClutterStage; +typedef struct _ClutterFrameInfo ClutterFrameInfo; typedef struct _ClutterContainer ClutterContainer; /* dummy */ typedef struct _ClutterChildMeta ClutterChildMeta; typedef struct _ClutterLayoutMeta ClutterLayoutMeta; diff --git a/clutter/clutter/cogl/clutter-stage-cogl.c b/clutter/clutter/cogl/clutter-stage-cogl.c index 07e10a28f..d9c1c91c7 100644 --- a/clutter/clutter/cogl/clutter-stage-cogl.c +++ b/clutter/clutter/cogl/clutter-stage-cogl.c @@ -81,24 +81,15 @@ clutter_stage_cogl_unrealize (ClutterStageWindow *stage_window) ClutterStageCogl *stage_cogl = CLUTTER_STAGE_COGL (stage_window); CLUTTER_NOTE (BACKEND, "Unrealizing Cogl stage [%p]", stage_cogl); - - if (stage_cogl->frame_closure != NULL) - { - _clutter_stage_window_remove_frame_callback (stage_window, - stage_cogl->frame_closure); - stage_cogl->frame_closure = NULL; - } } -static void -frame_cb (CoglOnscreen *onscreen, - CoglFrameEvent event, - CoglFrameInfo *info, - void *user_data) +void +_clutter_stage_cogl_presented (ClutterStageCogl *stage_cogl, + CoglFrameEvent frame_event, + ClutterFrameInfo *frame_info) { - ClutterStageCogl *stage_cogl = user_data; - if (event == COGL_FRAME_EVENT_SYNC) + if (frame_event == COGL_FRAME_EVENT_SYNC) { /* Early versions of the swap_event implementation in Mesa * deliver BufferSwapComplete event when not selected for, @@ -112,13 +103,14 @@ frame_cb (CoglOnscreen *onscreen, if (stage_cogl->pending_swaps > 0) stage_cogl->pending_swaps--; } - else if (event == COGL_FRAME_EVENT_COMPLETE) + else if (frame_event == COGL_FRAME_EVENT_COMPLETE) { - gint64 presentation_time_cogl = cogl_frame_info_get_presentation_time (info); + gint64 presentation_time_cogl = frame_info->presentation_time; if (presentation_time_cogl != 0) { - CoglContext *context = cogl_framebuffer_get_context (COGL_FRAMEBUFFER (onscreen)); + ClutterBackend *backend = stage_cogl->backend; + CoglContext *context = clutter_backend_get_cogl_context (backend); gint64 current_time_cogl = cogl_get_clock_time (context); gint64 now = g_get_monotonic_time (); @@ -126,8 +118,10 @@ frame_cb (CoglOnscreen *onscreen, now + (presentation_time_cogl - current_time_cogl) / 1000; } - stage_cogl->refresh_rate = cogl_frame_info_get_refresh_rate (info); + stage_cogl->refresh_rate = frame_info->refresh_rate; } + + _clutter_stage_presented (stage_cogl->wrapper, frame_event, frame_info); } static gboolean @@ -148,10 +142,6 @@ clutter_stage_cogl_realize (ClutterStageWindow *stage_window) return FALSE; } - stage_cogl->frame_closure = - _clutter_stage_window_set_frame_callback (stage_window, - frame_cb, stage_window); - return TRUE; } diff --git a/clutter/clutter/cogl/clutter-stage-cogl.h b/clutter/clutter/cogl/clutter-stage-cogl.h index 6a4a773ac..6122f2b1e 100644 --- a/clutter/clutter/cogl/clutter-stage-cogl.h +++ b/clutter/clutter/cogl/clutter-stage-cogl.h @@ -51,8 +51,6 @@ struct _ClutterStageCogl float refresh_rate; int pending_swaps; - CoglFrameClosure *frame_closure; - gint64 last_presentation_time; gint64 update_time; @@ -78,6 +76,11 @@ struct _ClutterStageCoglClass CLUTTER_AVAILABLE_IN_MUTTER GType _clutter_stage_cogl_get_type (void) G_GNUC_CONST; +CLUTTER_AVAILABLE_IN_MUTTER +void _clutter_stage_cogl_presented (ClutterStageCogl *stage_cogl, + CoglFrameEvent frame_event, + ClutterFrameInfo *frame_info); + G_END_DECLS #endif /* __CLUTTER_STAGE_COGL_H__ */ diff --git a/clutter/clutter/x11/clutter-stage-x11.c b/clutter/clutter/x11/clutter-stage-x11.c index 28382927b..39ff031ca 100644 --- a/clutter/clutter/x11/clutter-stage-x11.c +++ b/clutter/clutter/x11/clutter-stage-x11.c @@ -443,6 +443,13 @@ clutter_stage_x11_unrealize (ClutterStageWindow *stage_window) if (cogl_get_draw_framebuffer () == COGL_FRAMEBUFFER (stage_x11->onscreen)) _clutter_backend_reset_cogl_framebuffer (stage_cogl->backend); + if (stage_x11->frame_closure) + { + cogl_onscreen_remove_frame_callback (stage_x11->onscreen, + stage_x11->frame_closure); + stage_x11->frame_closure = NULL; + } + clutter_stage_window_parent_iface->unrealize (stage_window); g_list_free (stage_x11->legacy_views); @@ -604,6 +611,23 @@ stage_events_device_added (ClutterDeviceManager *device_manager, stage_cogl->wrapper); } +static void +frame_cb (CoglOnscreen *onscreen, + CoglFrameEvent frame_event, + CoglFrameInfo *frame_info, + void *user_data) + +{ + ClutterStageCogl *stage_cogl = user_data; + ClutterFrameInfo clutter_frame_info = { + .frame_counter = cogl_frame_info_get_frame_counter (frame_info), + .presentation_time = cogl_frame_info_get_presentation_time (frame_info), + .refresh_rate = cogl_frame_info_get_refresh_rate (frame_info) + }; + + _clutter_stage_cogl_presented (stage_cogl, frame_event, &clutter_frame_info); +} + static gboolean clutter_stage_x11_realize (ClutterStageWindow *stage_window) { @@ -628,6 +652,14 @@ clutter_stage_x11_realize (ClutterStageWindow *stage_window) stage_x11->onscreen = cogl_onscreen_new (backend->cogl_context, width, height); + cogl_onscreen_set_swap_throttled (stage_x11->onscreen, + _clutter_get_sync_to_vblank ()); + stage_x11->frame_closure = + cogl_onscreen_add_frame_callback (stage_x11->onscreen, + frame_cb, + stage_cogl, + NULL); + if (stage_x11->legacy_view) g_object_set (G_OBJECT (stage_x11->legacy_view), "framebuffer", stage_x11->onscreen, @@ -929,31 +961,6 @@ clutter_stage_x11_get_views (ClutterStageWindow *stage_window) return stage_x11->legacy_views; } -static CoglFrameClosure * -clutter_stage_x11_set_frame_callback (ClutterStageWindow *stage_window, - CoglFrameCallback callback, - gpointer user_data) -{ - ClutterStageX11 *stage_x11 = CLUTTER_STAGE_X11 (stage_window); - - cogl_onscreen_set_swap_throttled (stage_x11->onscreen, - _clutter_get_sync_to_vblank ()); - - return cogl_onscreen_add_frame_callback (stage_x11->onscreen, - callback, - user_data, - NULL); -} - -static void -clutter_stage_x11_remove_frame_callback (ClutterStageWindow *stage_window, - CoglFrameClosure *closure) -{ - ClutterStageX11 *stage_x11 = CLUTTER_STAGE_X11 (stage_window); - - cogl_onscreen_remove_frame_callback (stage_x11->onscreen, closure); -} - static int64_t clutter_stage_x11_get_frame_counter (ClutterStageWindow *stage_window) { @@ -1037,8 +1044,6 @@ clutter_stage_window_iface_init (ClutterStageWindowIface *iface) iface->set_scale_factor = clutter_stage_x11_set_scale_factor; iface->get_scale_factor = clutter_stage_x11_get_scale_factor; iface->get_views = clutter_stage_x11_get_views; - iface->set_frame_callback = clutter_stage_x11_set_frame_callback; - iface->remove_frame_callback = clutter_stage_x11_remove_frame_callback; iface->get_frame_counter = clutter_stage_x11_get_frame_counter; } diff --git a/clutter/clutter/x11/clutter-stage-x11.h b/clutter/clutter/x11/clutter-stage-x11.h index e1ee03362..98ba53bc5 100644 --- a/clutter/clutter/x11/clutter-stage-x11.h +++ b/clutter/clutter/x11/clutter-stage-x11.h @@ -61,6 +61,8 @@ struct _ClutterStageX11 ClutterStageView *legacy_view; GList *legacy_views; + CoglFrameClosure *frame_closure; + gchar *title; guint clipped_redraws_cool_off; diff --git a/cogl/cogl/cogl-frame-info-private.h b/cogl/cogl/cogl-frame-info-private.h index 32f5ba8e0..16d393e1c 100644 --- a/cogl/cogl/cogl-frame-info-private.h +++ b/cogl/cogl/cogl-frame-info-private.h @@ -42,6 +42,8 @@ struct _CoglFrameInfo int64_t presentation_time; float refresh_rate; + int64_t global_frame_counter; + CoglOutput *output; }; diff --git a/cogl/cogl/cogl-frame-info.c b/cogl/cogl/cogl-frame-info.c index 0571960d3..4e7ac3aee 100644 --- a/cogl/cogl/cogl-frame-info.c +++ b/cogl/cogl/cogl-frame-info.c @@ -79,3 +79,9 @@ cogl_frame_info_get_output (CoglFrameInfo *info) { return info->output; } + +int64_t +cogl_frame_info_get_global_frame_counter (CoglFrameInfo *info) +{ + return info->global_frame_counter; +} diff --git a/cogl/cogl/cogl-frame-info.h b/cogl/cogl/cogl-frame-info.h index 7304c530f..3e44d747f 100644 --- a/cogl/cogl/cogl-frame-info.h +++ b/cogl/cogl/cogl-frame-info.h @@ -143,6 +143,11 @@ float cogl_frame_info_get_refresh_rate (CoglFrameInfo *info); CoglOutput * cogl_frame_info_get_output (CoglFrameInfo *info); +/** + * cogl_frame_info_get_global_frame_counter: (skip) + */ +int64_t cogl_frame_info_get_global_frame_counter (CoglFrameInfo *info); + G_END_DECLS #endif /* __COGL_FRAME_INFO_H */ diff --git a/cogl/cogl/cogl-mutter.h b/cogl/cogl/cogl-mutter.h index d490a9cb6..4bfac07fa 100644 --- a/cogl/cogl/cogl-mutter.h +++ b/cogl/cogl/cogl-mutter.h @@ -37,6 +37,7 @@ #include #include #include +#include #include #include #include diff --git a/src/backends/native/meta-stage-native.c b/src/backends/native/meta-stage-native.c index 1dd3c50d6..624c5142c 100644 --- a/src/backends/native/meta-stage-native.c +++ b/src/backends/native/meta-stage-native.c @@ -36,6 +36,7 @@ struct _MetaStageNative ClutterStageCogl parent; CoglOnscreen *pending_onscreen; + CoglClosure *frame_closure; }; static ClutterStageWindowIface *clutter_stage_window_parent_iface = NULL; @@ -136,6 +137,16 @@ meta_stage_native_unrealize (ClutterStageWindow *stage_window) clutter_stage_window_parent_iface->unrealize (stage_window); + if (stage_native->frame_closure) + { + CoglOnscreen *onscreen; + + onscreen = get_legacy_onscreen (stage_native); + cogl_onscreen_remove_frame_callback (onscreen, + stage_native->frame_closure); + stage_native->frame_closure = NULL; + } + g_clear_pointer (&stage_native->pending_onscreen, cogl_object_unref); } @@ -168,6 +179,23 @@ meta_stage_native_get_geometry (ClutterStageWindow *stage_window, } } +static void +frame_cb (CoglOnscreen *onscreen, + CoglFrameEvent frame_event, + CoglFrameInfo *frame_info, + void *user_data) +{ + MetaStageNative *stage_native = user_data; + ClutterStageCogl *stage_cogl = CLUTTER_STAGE_COGL (stage_native); + ClutterFrameInfo clutter_frame_info = { + .frame_counter = cogl_frame_info_get_frame_counter (frame_info), + .refresh_rate = cogl_frame_info_get_refresh_rate (frame_info), + .presentation_time = cogl_frame_info_get_presentation_time (frame_info) + }; + + _clutter_stage_cogl_presented (stage_cogl, frame_event, &clutter_frame_info); +} + static void ensure_legacy_view (ClutterStageWindow *stage_window) { @@ -179,6 +207,7 @@ ensure_legacy_view (ClutterStageWindow *stage_window) MetaRendererView *legacy_view; cairo_rectangle_int_t view_layout = { 0 }; CoglFramebuffer *framebuffer; + CoglOnscreen *onscreen; legacy_view = get_legacy_view (renderer); if (legacy_view) @@ -196,6 +225,16 @@ ensure_legacy_view (ClutterStageWindow *stage_window) "framebuffer", framebuffer, NULL); meta_renderer_set_legacy_view (renderer, legacy_view); + + onscreen = COGL_ONSCREEN (framebuffer); + cogl_onscreen_set_swap_throttled (onscreen, + _clutter_get_sync_to_vblank ()); + + stage_native->frame_closure = + cogl_onscreen_add_frame_callback (onscreen, + frame_cb, + stage_native, + NULL); } static GList * @@ -208,36 +247,6 @@ meta_stage_native_get_views (ClutterStageWindow *stage_window) return meta_renderer_get_views (renderer); } -static CoglClosure * -meta_stage_native_set_frame_callback (ClutterStageWindow *stage_window, - CoglFrameCallback callback, - gpointer user_data) -{ - MetaStageNative *stage_native = META_STAGE_NATIVE (stage_window); - CoglOnscreen *legacy_onscreen; - - legacy_onscreen = get_legacy_onscreen (stage_native); - cogl_onscreen_set_swap_throttled (legacy_onscreen, - _clutter_get_sync_to_vblank ()); - - return cogl_onscreen_add_frame_callback (legacy_onscreen, - callback, - user_data, - NULL); -} - -static void -meta_stage_native_remove_frame_callback (ClutterStageWindow *stage_window, - CoglFrameClosure *closure) -{ - MetaStageNative *stage_native = META_STAGE_NATIVE (stage_window); - CoglOnscreen *legacy_onscreen; - - legacy_onscreen = get_legacy_onscreen (stage_native); - - cogl_onscreen_remove_frame_callback (legacy_onscreen, closure); -} - static int64_t meta_stage_native_get_frame_counter (ClutterStageWindow *stage_window) { @@ -269,7 +278,5 @@ clutter_stage_window_iface_init (ClutterStageWindowIface *iface) iface->can_clip_redraws = meta_stage_native_can_clip_redraws; iface->get_geometry = meta_stage_native_get_geometry; iface->get_views = meta_stage_native_get_views; - iface->set_frame_callback = meta_stage_native_set_frame_callback; - iface->remove_frame_callback = meta_stage_native_remove_frame_callback; iface->get_frame_counter = meta_stage_native_get_frame_counter; } diff --git a/src/compositor/compositor-private.h b/src/compositor/compositor-private.h index 72dffe51f..4629fa5ff 100644 --- a/src/compositor/compositor-private.h +++ b/src/compositor/compositor-private.h @@ -29,7 +29,6 @@ struct _MetaCompositor GList *windows; Window output; - CoglFrameClosure *frame_closure; CoglContext *context; /* Used for unredirecting fullscreen windows */ diff --git a/src/compositor/compositor.c b/src/compositor/compositor.c index 0efb09b5a..59ad7f77e 100644 --- a/src/compositor/compositor.c +++ b/src/compositor/compositor.c @@ -83,6 +83,12 @@ #include "wayland/meta-wayland-private.h" #endif +static void +on_presented (ClutterStage *stage, + CoglFrameEvent event, + ClutterFrameInfo *frame_info, + MetaCompositor *compositor); + static gboolean is_modal (MetaDisplay *display) { @@ -475,6 +481,10 @@ meta_compositor_manage (MetaCompositor *compositor) compositor->stage = meta_backend_get_stage (backend); + g_signal_connect (compositor->stage, "presented", + G_CALLBACK (on_presented), + compositor); + /* We use connect_after() here to accomodate code in GNOME Shell that, * when benchmarking drawing performance, connects to ::after-paint * and calls glFinish(). The timing information from that will be @@ -998,17 +1008,16 @@ meta_compositor_sync_window_geometry (MetaCompositor *compositor, } static void -frame_callback (CoglOnscreen *onscreen, - CoglFrameEvent event, - CoglFrameInfo *frame_info, - void *user_data) +on_presented (ClutterStage *stage, + CoglFrameEvent event, + ClutterFrameInfo *frame_info, + MetaCompositor *compositor) { - MetaCompositor *compositor = user_data; GList *l; if (event == COGL_FRAME_EVENT_COMPLETE) { - gint64 presentation_time_cogl = cogl_frame_info_get_presentation_time (frame_info); + gint64 presentation_time_cogl = frame_info->presentation_time; gint64 presentation_time; if (presentation_time_cogl != 0) @@ -1045,14 +1054,6 @@ meta_pre_paint_func (gpointer data) MetaWindowActor *top_window; MetaCompositor *compositor = data; - if (!compositor->frame_closure) - { - compositor->frame_closure = - clutter_stage_add_frame_callback (CLUTTER_STAGE (compositor->stage), - frame_callback, - compositor); - } - if (compositor->windows == NULL) return TRUE; diff --git a/src/compositor/meta-window-actor-private.h b/src/compositor/meta-window-actor-private.h index 1f7947b09..ef21674a5 100644 --- a/src/compositor/meta-window-actor-private.h +++ b/src/compositor/meta-window-actor-private.h @@ -30,7 +30,7 @@ void meta_window_actor_process_x11_damage (MetaWindowActor *self, void meta_window_actor_pre_paint (MetaWindowActor *self); void meta_window_actor_post_paint (MetaWindowActor *self); void meta_window_actor_frame_complete (MetaWindowActor *self, - CoglFrameInfo *frame_info, + ClutterFrameInfo *frame_info, gint64 presentation_time); void meta_window_actor_invalidate_shadow (MetaWindowActor *self); diff --git a/src/compositor/meta-window-actor.c b/src/compositor/meta-window-actor.c index 197a19315..25a8f1176 100644 --- a/src/compositor/meta-window-actor.c +++ b/src/compositor/meta-window-actor.c @@ -2029,13 +2029,13 @@ do_send_frame_timings (MetaWindowActor *self, static void send_frame_timings (MetaWindowActor *self, FrameData *frame, - CoglFrameInfo *frame_info, + ClutterFrameInfo *frame_info, gint64 presentation_time) { float refresh_rate; int refresh_interval; - refresh_rate = cogl_frame_info_get_refresh_rate (frame_info); + refresh_rate = frame_info->refresh_rate; /* 0.0 is a flag for not known, but sanity-check against other odd numbers */ if (refresh_rate >= 1.0) refresh_interval = (int) (0.5 + 1000000 / refresh_rate); @@ -2046,9 +2046,9 @@ send_frame_timings (MetaWindowActor *self, } void -meta_window_actor_frame_complete (MetaWindowActor *self, - CoglFrameInfo *frame_info, - gint64 presentation_time) +meta_window_actor_frame_complete (MetaWindowActor *self, + ClutterFrameInfo *frame_info, + gint64 presentation_time) { MetaWindowActorPrivate *priv = self->priv; GList *l; @@ -2060,7 +2060,7 @@ meta_window_actor_frame_complete (MetaWindowActor *self, { GList *l_next = l->next; FrameData *frame = l->data; - gint64 frame_counter = cogl_frame_info_get_frame_counter (frame_info); + gint64 frame_counter = frame_info->frame_counter; if (frame->frame_counter != -1 && frame->frame_counter <= frame_counter) {