[clutter/clutter-1.16] stage: Add a paint callback



commit d061a47573fbfec69ed6f2fd02f233e218830a6d
Author: Emmanuele Bassi <ebassi gnome org>
Date:   Wed Apr 24 15:35:28 2013 -0400

    stage: Add a paint callback
    
    The ClutterActor::paint signal is deprecated, and connecting to it even
    to get notifications will disable clipped redraws because of violations
    of the paint volume.
    
    The only actual valid use case for notifications of a successful frame
    is on the ClutterStage, so we should add new (experimental) API for it,
    so that users can actually subscribe to it — at least if you're writing
    a compositor.
    
    Shoving a signal in a performance critical path is not an option, and
    I'm not sure I want to commit to an API like this yet. I reserve the
    right to revisit this decision in the future.
    
    https://bugzilla.gnome.org/show_bug.cgi?id=698783

 clutter/clutter-stage.c |   55 ++++++++++++++++++++++++++++++++++++++++++++--
 clutter/clutter-stage.h |    9 +++++++
 clutter/clutter.symbols |    1 +
 3 files changed, 62 insertions(+), 3 deletions(-)
---
diff --git a/clutter/clutter-stage.c b/clutter/clutter-stage.c
index 333a3d3..51530ff 100644
--- a/clutter/clutter-stage.c
+++ b/clutter/clutter-stage.c
@@ -159,6 +159,10 @@ struct _ClutterStagePrivate
 
   ClutterStageState current_state;
 
+  ClutterStagePaintFunc paint_callback;
+  gpointer paint_data;
+  GDestroyNotify paint_notify;
+
   guint relayout_pending       : 1;
   guint redraw_pending         : 1;
   guint is_fullscreen          : 1;
@@ -210,8 +214,9 @@ static guint stage_signals[LAST_SIGNAL] = { 0, };
 
 static const ClutterColor default_stage_color = { 255, 255, 255, 255 };
 
-static void _clutter_stage_maybe_finish_queue_redraws (ClutterStage *stage);
+static void clutter_stage_maybe_finish_queue_redraws (ClutterStage *stage);
 static void free_queue_redraw_entry (ClutterStageQueueRedrawEntry *entry);
+static void clutter_stage_invoke_paint_callback (ClutterStage *stage);
 
 static void
 clutter_stage_real_add (ClutterContainer *container,
@@ -669,6 +674,8 @@ _clutter_stage_do_paint (ClutterStage                *stage,
   _clutter_stage_paint_volume_stack_free_all (stage);
   _clutter_stage_update_active_framebuffer (stage);
   clutter_actor_paint (CLUTTER_ACTOR (stage));
+
+  clutter_stage_invoke_paint_callback (stage);
 }
 
 static void
@@ -1226,7 +1233,7 @@ _clutter_stage_do_update (ClutterStage *stage)
   if (!priv->redraw_pending)
     return FALSE;
 
-  _clutter_stage_maybe_finish_queue_redraws (stage);
+  clutter_stage_maybe_finish_queue_redraws (stage);
 
   clutter_stage_do_redraw (stage);
 
@@ -1879,6 +1886,9 @@ clutter_stage_finalize (GObject *object)
   if (priv->fps_timer != NULL)
     g_timer_destroy (priv->fps_timer);
 
+  if (priv->paint_notify != NULL)
+    priv->paint_notify (priv->paint_data);
+
   G_OBJECT_CLASS (clutter_stage_parent_class)->finalize (object);
 }
 
@@ -4137,7 +4147,7 @@ _clutter_stage_queue_redraw_entry_invalidate (ClutterStageQueueRedrawEntry *entr
 }
 
 static void
-_clutter_stage_maybe_finish_queue_redraws (ClutterStage *stage)
+clutter_stage_maybe_finish_queue_redraws (ClutterStage *stage)
 {
   /* Note: we have to repeat until the pending_queue_redraws list is
    * empty because actors are allowed to queue redraws in response to
@@ -4581,3 +4591,42 @@ clutter_stage_skip_sync_delay (ClutterStage *stage)
   if (stage_window)
     _clutter_stage_window_schedule_update (stage_window, -1);
 }
+
+/**
+ * clutter_stage_set_paint_callback:
+ * @stage: a #ClutterStage
+ * @callback: (allow none): a callback
+ * @data: (allow none): data to be passed to @callback
+ * @notify: (allow none): function to be called when the callback is removed
+ *
+ * Sets a callback function to be invoked after the @stage has been
+ * painted.
+ *
+ * Since: 1.14
+ */
+void
+clutter_stage_set_paint_callback (ClutterStage          *stage,
+                                  ClutterStagePaintFunc  callback,
+                                  gpointer               data,
+                                  GDestroyNotify         notify)
+{
+  ClutterStagePrivate *priv;
+
+  g_return_if_fail (CLUTTER_IS_STAGE (stage));
+
+  priv = stage->priv;
+
+  if (priv->paint_notify != NULL)
+    priv->paint_notify (priv->paint_data);
+
+  priv->paint_callback = callback;
+  priv->paint_data = data;
+  priv->paint_notify = notify;
+}
+
+static void
+clutter_stage_invoke_paint_callback (ClutterStage *stage)
+{
+  if (stage->priv->paint_callback != NULL)
+    stage->priv->paint_callback (stage, stage->priv->paint_data);
+}
diff --git a/clutter/clutter-stage.h b/clutter/clutter-stage.h
index af6b091..36044c0 100644
--- a/clutter/clutter-stage.h
+++ b/clutter/clutter-stage.h
@@ -208,6 +208,15 @@ void            clutter_stage_set_sync_delay                    (ClutterStage
                                                                  gint                   sync_delay);
 CLUTTER_AVAILABLE_IN_1_14
 void            clutter_stage_skip_sync_delay                   (ClutterStage          *stage);
+
+typedef void (* ClutterStagePaintFunc) (ClutterStage *stage,
+                                        gpointer      data);
+
+CLUTTER_AVAILABLE_IN_1_14
+void            clutter_stage_set_paint_callback                (ClutterStage          *stage,
+                                                                 ClutterStagePaintFunc  callback,
+                                                                 gpointer               data,
+                                                                 GDestroyNotify         notify);
 #endif
 
 G_END_DECLS
diff --git a/clutter/clutter.symbols b/clutter/clutter.symbols
index 1ca0b94..7316538 100644
--- a/clutter/clutter.symbols
+++ b/clutter/clutter.symbols
@@ -1284,6 +1284,7 @@ clutter_stage_set_key_focus
 clutter_stage_set_minimum_size
 clutter_stage_set_motion_events_enabled
 clutter_stage_set_no_clear_hint
+clutter_stage_set_paint_callback
 clutter_stage_set_perspective
 clutter_stage_set_sync_delay
 clutter_stage_set_throttle_motion_events


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]