[gnome-todo] timeline: Use frame ticks to account for delay



commit a43030a5e0e3f1314898e7a59880d6c6ecc93243
Author: Georges Basile Stavracas Neto <georges stavracas gmail com>
Date:   Sun Mar 7 14:13:57 2021 -0300

    timeline: Use frame ticks to account for delay
    
    Instead of using a timeout source, account for the delay in the frame
    tick callback.

 src/animation/gtd-timeline-private.h | 31 -----------------
 src/animation/gtd-timeline.c         | 64 +++++++++++++-----------------------
 src/gui/gtd-widget.c                 |  4 +--
 3 files changed, 23 insertions(+), 76 deletions(-)
---
diff --git a/src/animation/gtd-timeline.c b/src/animation/gtd-timeline.c
index e6cd8c10..ebe272f7 100644
--- a/src/animation/gtd-timeline.c
+++ b/src/animation/gtd-timeline.c
@@ -79,7 +79,6 @@
 
 #include "gtd-debug.h"
 #include "gnome-todo.h"
-#include "gtd-timeline-private.h"
 
 typedef struct
 {
@@ -88,8 +87,6 @@ typedef struct
   GtdWidget *widget;
   guint frame_tick_id;
 
-  guint delay_id;
-
   gint64 duration_us;
   gint64 delay_us;
 
@@ -102,6 +99,8 @@ typedef struct
   /* Time we last advanced the elapsed time and showed a frame */
   gint64 last_frame_time_us;
 
+  gint64 start_us;
+
   /* How many times the timeline should repeat */
   gint repeat_count;
 
@@ -168,6 +167,14 @@ ms_to_us (gint64 us)
   return us * 1000;
 }
 
+static inline gboolean
+is_waiting_for_delay (GtdTimeline *self,
+                      gint64       frame_time_us)
+{
+  GtdTimelinePrivate *priv = gtd_timeline_get_instance_private (self);
+  return priv->start_us + priv->delay_us > frame_time_us;
+}
+
 static void
 emit_frame_signal (GtdTimeline *self)
 {
@@ -316,6 +323,12 @@ tick_timeline (GtdTimeline *self,
   elapsed_us = tick_time_us - priv->last_frame_time_us;
   priv->last_frame_time_us = tick_time_us;
 
+  if (is_waiting_for_delay (self, tick_time_us))
+    {
+      GTD_TRACE_MSG ("- waiting for delay");
+      return G_SOURCE_CONTINUE;
+    }
+
   /* if the clock rolled back between ticks we need to
    * account for it; the best course of action, since the
    * clock roll back can happen by any arbitrary amount
@@ -416,7 +429,8 @@ set_is_playing (GtdTimeline *self,
 
   if (priv->is_playing)
     {
-      priv->last_frame_time_us = g_get_monotonic_time ();
+      priv->start_us = g_get_monotonic_time ();
+      priv->last_frame_time_us = priv->start_us;
       priv->current_repeat = 0;
 
       add_tick_callback (self);
@@ -427,21 +441,6 @@ set_is_playing (GtdTimeline *self,
     }
 }
 
-static gboolean
-delay_timeout_func (gpointer data)
-{
-  GtdTimeline *self = data;
-  GtdTimelinePrivate *priv = gtd_timeline_get_instance_private (self);
-
-  priv->delay_id = 0;
-  priv->delta_us = 0;
-  set_is_playing (self, TRUE);
-
-  g_signal_emit (self, timeline_signals[STARTED], 0);
-
-  return G_SOURCE_REMOVE;
-}
-
 static gdouble
 timeline_progress_func (GtdTimeline *self,
                         gdouble      elapsed,
@@ -553,8 +552,6 @@ gtd_timeline_dispose (GObject *object)
   GtdTimeline *self = GTD_TIMELINE (object);
   GtdTimelinePrivate *priv = gtd_timeline_get_instance_private (self);
 
-  gtd_timeline_cancel_delay (self);
-
   if (priv->progress_notify != NULL)
     {
       priv->progress_notify (priv->progress_data);
@@ -874,23 +871,16 @@ gtd_timeline_start (GtdTimeline *self)
 
   priv = gtd_timeline_get_instance_private (self);
 
-  if (priv->delay_id || priv->is_playing)
+  if (priv->is_playing)
     return;
 
   if (priv->duration_us == 0)
     return;
 
-  if (priv->delay_us)
-    {
-      priv->delay_id = g_timeout_add (us_to_ms (priv->delay_us), delay_timeout_func, self);
-    }
-  else
-    {
-      priv->delta_us = 0;
-      set_is_playing (self, TRUE);
+  priv->delta_us = 0;
+  set_is_playing (self, TRUE);
 
-      g_signal_emit (self, timeline_signals[STARTED], 0);
-    }
+  g_signal_emit (self, timeline_signals[STARTED], 0);
 }
 
 /**
@@ -908,8 +898,6 @@ gtd_timeline_pause (GtdTimeline *self)
 
   priv = gtd_timeline_get_instance_private (self);
 
-  gtd_timeline_cancel_delay (self);
-
   if (!priv->is_playing)
     return;
 
@@ -1593,14 +1581,6 @@ gtd_timeline_get_current_repeat (GtdTimeline *self)
   return priv->current_repeat;
 }
 
-void
-gtd_timeline_cancel_delay (GtdTimeline *self)
-{
-  GtdTimelinePrivate *priv = gtd_timeline_get_instance_private (self);
-
-  g_clear_handle_id (&priv->delay_id, g_source_remove);
-}
-
 /**
  * gtd_timeline_get_widget:
  * @timeline: a #GtdTimeline
diff --git a/src/gui/gtd-widget.c b/src/gui/gtd-widget.c
index 63917bd4..e5bece41 100644
--- a/src/gui/gtd-widget.c
+++ b/src/gui/gtd-widget.c
@@ -23,7 +23,7 @@
 #include "gtd-debug.h"
 #include "gtd-animation-enums.h"
 #include "gtd-interval.h"
-#include "gtd-timeline-private.h"
+#include "gtd-timeline.h"
 #include "gtd-property-transition.h"
 
 #include <graphene-gobject.h>
@@ -129,8 +129,6 @@ transition_closure_free (gpointer data)
 
       if (gtd_timeline_is_playing (timeline))
         gtd_timeline_stop (timeline);
-      else if (gtd_timeline_get_delay (timeline) > 0)
-        gtd_timeline_cancel_delay (timeline);
 
       g_object_unref (closure->transition);
 


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