UNFULLSCREEN,
ACTIVATE,
DEACTIVATE,
+ QUEUE_REDRAW,
+
LAST_SIGNAL
};
clutter_actor_allocate (CLUTTER_ACTOR (stage), &box, FALSE);
}
+static gboolean
+redraw_update_idle (gpointer user_data)
+{
+ ClutterStage *stage = user_data;
+ ClutterStagePrivate *priv = stage->priv;
+
+ if (priv->update_idle)
+ {
+ g_source_remove (priv->update_idle);
+ priv->update_idle = 0;
+ }
+
+ CLUTTER_NOTE (MULTISTAGE, "redrawing via idle for stage:%p", stage);
+ clutter_redraw (stage);
+
+ return FALSE;
+}
+
+static void
+clutter_stage_real_queue_redraw (ClutterStage *stage)
+{
+ ClutterStagePrivate *priv = stage->priv;
+
+ if (priv->update_idle == 0)
+ {
+ CLUTTER_TIMESTAMP (SCHEDULER, "Adding idle source for stage: %p", stage);
+
+ /* FIXME: weak_ref self in case we dissapear before paint? */
+ priv->update_idle =
+ clutter_threads_add_idle_full (CLUTTER_PRIORITY_REDRAW,
+ redraw_update_idle,
+ stage,
+ NULL);
+ }
+}
+
static void
clutter_stage_set_property (GObject *object,
guint prop_id,
NULL, NULL,
clutter_marshal_VOID__VOID,
G_TYPE_NONE, 0);
+ /**
+ * ClutterStage::queue-redraw:
+ * @stage: the stage which was queued for redraw
+ *
+ * The ::queue-redraw signal is emitted each time a #ClutterStage
+ * has been queued for a redraw. You can use this signal to know
+ * when clutter_stage_queue_redraw() has been called.
+ *
+ * Toolkits embedding a #ClutterStage which require a redraw and
+ * relayout cycle can stop the emission of this signal using the
+ * GSignal API, redraw the UI and then call clutter_redraw()
+ * themselves, like:
+ *
+ * |[
+ * static void
+ * on_redraw_complete (void)
+ * {
+ * /* execute the Clutter drawing pipeline */
+ * clutter_redraw ();
+ * }
+ *
+ * static void
+ * on_stage_queue_redraw (ClutterStage *stage)
+ * {
+ * /* this prevents the default handler to run */
+ * g_signal_stop_emission_by_name (stage, "queue-redraw");
+ *
+ * /* queue a redraw with the host toolkit and call
+ * * a function when the redraw has been completed
+ * */
+ * queue_a_redraw (G_CALLBACK (on_redraw_complete));
+ * }
+ * ]|
+ *
+ * <note><para>This signal is emitted before the Clutter paint
+ * pipeline is run. If you want to know when the pipeline has been
+ * completed you should connect to the ::paint signal on the Stage
+ * with g_signal_connect_after().</para></note>
+ *
+ * Since: 1.0
+ */
+ stage_signals[QUEUE_REDRAW] =
+ g_signal_new (I_("queue-redraw"),
+ G_TYPE_FROM_CLASS (gobject_class),
+ G_SIGNAL_RUN_FIRST,
+ G_STRUCT_OFFSET (ClutterStageClass, queue_redraw),
+ NULL, NULL,
+ clutter_marshal_VOID__VOID,
+ G_TYPE_NONE, 0);
klass->fullscreen = clutter_stage_real_fullscreen;
+ klass->queue_redraw = clutter_stage_real_queue_redraw;
g_type_class_add_private (gobject_class, sizeof (ClutterStagePrivate));
}
clutter_stage_queue_redraw (stage);
}
-static gboolean
-redraw_update_idle (gpointer user_data)
-{
- ClutterStage *stage = user_data;
- ClutterStagePrivate *priv = stage->priv;
-
- if (priv->update_idle)
- {
- g_source_remove (priv->update_idle);
- priv->update_idle = 0;
- }
-
- CLUTTER_NOTE (MULTISTAGE, "redrawing via idle for stage:%p", stage);
- clutter_redraw (stage);
-
- return FALSE;
-}
-
/**
* clutter_stage_queue_redraw:
* @stage: the #ClutterStage
{
g_return_if_fail (CLUTTER_IS_STAGE (stage));
- if (!stage->priv->update_idle)
- {
- CLUTTER_TIMESTAMP (SCHEDULER, "Adding idle source for stage: %p", stage);
-
- /* FIXME: weak_ref self in case we dissapear before paint? */
- stage->priv->update_idle =
- clutter_threads_add_idle_full (CLUTTER_PRIORITY_REDRAW,
- redraw_update_idle,
- stage,
- NULL);
- }
+ g_signal_emit (stage, stage_signals[QUEUE_REDRAW], 0);
}
/**