(Vector) Fix invalid callback issue 53/295753/2
authorHeeyong Song <heeyong.song@samsung.com>
Thu, 13 Jul 2023 07:49:31 +0000 (16:49 +0900)
committerHeeyong Song <heeyong.song@samsung.com>
Thu, 13 Jul 2023 08:27:30 +0000 (17:27 +0900)
Do not execute a callback with lock
Reset callback pointers after removing

Change-Id: I1f617af4ee89e43c8ab891efbd0beaea14feaea1

dali-toolkit/internal/visuals/animated-vector-image/vector-animation-task.cpp
dali-toolkit/internal/visuals/animated-vector-image/vector-animation-thread.cpp
dali-toolkit/internal/visuals/animated-vector-image/vector-animation-thread.h

index 6d4b2ef..b1e9bea 100644 (file)
@@ -106,10 +106,12 @@ void VectorAnimationTask::Finalize()
   if(mAnimationFinishedCallback)
   {
     mVectorAnimationThread.RemoveEventTriggerCallback(mAnimationFinishedCallback.get());
+    mAnimationFinishedCallback.reset();
   }
   if(mLoadCompletedCallback)
   {
     mVectorAnimationThread.RemoveEventTriggerCallback(mLoadCompletedCallback.get());
+    mLoadCompletedCallback.reset();
   }
 
   mVectorRenderer.Finalize();
@@ -139,7 +141,7 @@ bool VectorAnimationTask::Load(bool synchronousLoading)
     DALI_LOG_ERROR("VectorAnimationTask::Load: Load failed [%s]\n", mUrl.c_str());
     mLoadRequest = false;
     mLoadFailed  = true;
-    if(!synchronousLoading)
+    if(!synchronousLoading && mLoadCompletedCallback)
     {
       mVectorAnimationThread.AddEventTriggerCallback(mLoadCompletedCallback.get());
     }
@@ -154,7 +156,7 @@ bool VectorAnimationTask::Load(bool synchronousLoading)
   mFrameDurationMicroSeconds = MICROSECONDS_PER_SECOND / mFrameRate;
 
   mLoadRequest = false;
-  if(!synchronousLoading)
+  if(!synchronousLoading && mLoadCompletedCallback)
   {
     mVectorAnimationThread.AddEventTriggerCallback(mLoadCompletedCallback.get());
   }
index 08b52d6..9d2cfbe 100644 (file)
@@ -263,15 +263,25 @@ void VectorAnimationThread::Rasterize()
 
 void VectorAnimationThread::OnEventCallbackTriggered()
 {
+  while(CallbackBase* callback = GetNextEventCallback())
+  {
+    CallbackBase::Execute(*callback);
+  }
+}
+
+CallbackBase* VectorAnimationThread::GetNextEventCallback()
+{
   ConditionalWait::ScopedLock lock(mConditionalWait);
 
-  for(auto&& iter : mTriggerEventCallbacks)
+  if(!mTriggerEventCallbacks.empty())
   {
-    CallbackBase::Execute(*iter);
+    auto          iter     = mTriggerEventCallbacks.begin();
+    CallbackBase* callback = *iter;
+    mTriggerEventCallbacks.erase(iter);
+    return callback;
   }
-
-  mTriggerEventCallbacks.clear();
   mEventTriggered = false;
+  return nullptr;
 }
 
 VectorAnimationThread::SleepThread::SleepThread(CallbackBase* callback)
index 79d1a48..14aa6c9 100644 (file)
@@ -95,7 +95,7 @@ protected:
 
 private:
   /**
-   * Rasterizes the tasks.
+   * @brief Rasterizes the tasks.
    */
   void Rasterize();
 
@@ -105,6 +105,11 @@ private:
   void OnEventCallbackTriggered();
 
   /**
+   * @brief Gets next event callback to process.
+   */
+  CallbackBase* GetNextEventCallback();
+
+  /**
    * @brief The thread to sleep until the next frame time.
    */
   class SleepThread : public Thread