[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [61239] trunk/blender/intern/audaspace/ intern: Fix for [#37362] Audio strips sometimes are evaluated incorrectly.

Joerg Mueller nexyon at gmail.com
Tue Nov 12 19:29:08 CET 2013


Revision: 61239
          http://projects.blender.org/scm/viewvc.php?view=rev&root=bf-blender&revision=61239
Author:   nexyon
Date:     2013-11-12 18:29:08 +0000 (Tue, 12 Nov 2013)
Log Message:
-----------
Fix for [#37362] Audio strips sometimes are evaluated incorrectly.

For details see bug comments. The problem was that blender's animation system didn't update the audio animation system anymore due to an optimization. Fixed this in a complex but proper way in the audio animation system, so that it can handle gaps of missing values.

Modified Paths:
--------------
    trunk/blender/intern/audaspace/intern/AUD_AnimateableProperty.cpp
    trunk/blender/intern/audaspace/intern/AUD_AnimateableProperty.h

Modified: trunk/blender/intern/audaspace/intern/AUD_AnimateableProperty.cpp
===================================================================
--- trunk/blender/intern/audaspace/intern/AUD_AnimateableProperty.cpp	2013-11-12 18:18:06 UTC (rev 61238)
+++ trunk/blender/intern/audaspace/intern/AUD_AnimateableProperty.cpp	2013-11-12 18:29:08 UTC (rev 61239)
@@ -47,6 +47,15 @@
 	pthread_mutexattr_destroy(&attr);
 }
 
+void AUD_AnimateableProperty::updateUnknownCache(int start, int end)
+{
+	float* buf = getBuffer();
+
+	for(int i = start; i <= end; i++)
+		// TODO: maybe first instead of zero order interpolation?
+		memcpy(buf + i * m_count, buf + (start - 1) * m_count, m_count * sizeof(float));
+}
+
 AUD_AnimateableProperty::~AUD_AnimateableProperty()
 {
 	pthread_mutex_destroy(&m_mutex);
@@ -67,6 +76,7 @@
 	AUD_MutexLock lock(*this);
 
 	m_isAnimated = false;
+	m_unknown.clear();
 	memcpy(getBuffer(), data, m_count * sizeof(float));
 }
 
@@ -74,18 +84,85 @@
 {
 	AUD_MutexLock lock(*this);
 
+	int pos = getSize() / (sizeof(float) * m_count);
+
+	if(!m_isAnimated)
+		pos = 0;
+
 	m_isAnimated = true;
 
-	int pos = getSize() / (sizeof(float) * m_count);
-
 	assureSize((count + position) * m_count * sizeof(float), true);
 
 	float* buf = getBuffer();
 
 	memcpy(buf + position * m_count, data, count * m_count * sizeof(float));
 
-	for(int i = pos; i < position; i++)
-		memcpy(buf + i * m_count, buf + (pos - 1) * m_count, m_count * sizeof(float));
+	// have to fill up space between?
+	if(pos < position)
+	{
+		m_unknown.push_back(Unknown(pos, position - 1));
+
+		if(pos == 0)
+		{
+			memset(buf, 0, position * m_count * sizeof(float));
+		}
+		else
+			updateUnknownCache(pos, position - 1);
+	}
+	// otherwise it's not at the end, let's check if some unknown part got filled
+	else
+	{
+		for(std::list<Unknown>::iterator it = m_unknown.begin(); it != m_unknown.end(); it++)
+		{
+			// unknown area before position
+			if(it->end < position)
+				continue;
+
+			// we're after the new area, let's stop
+			if(it->start >= position + count)
+				break;
+
+			// we have an intersection, now 4 cases:
+			// the start is included
+			if(position <= it->start)
+			{
+				// the end is included
+				if(position + count > it->end)
+				{
+					// simply delete
+					std::list<Unknown>::iterator it2 = it;
+					it++;
+					m_unknown.erase(it2);
+				}
+				// the end is excluded, a second part remains
+				else
+				{
+					// update second part
+					it->start = position + count;
+					updateUnknownCache(it->start, it->end);
+					break;
+				}
+			}
+			// start is excluded, a first part remains
+			else
+			{
+				// the end is included
+				if(position + count > it->end)
+				{
+					// update first part
+					it->end = position - 1;
+				}
+				// the end is excluded, a second part remains
+				else
+				{
+					// add another item and update both parts
+					m_unknown.insert(it, Unknown(it->start, position - 1));
+					it->start = position + count;
+					updateUnknownCache(it->start, it->end);
+				}
+			}
+		}
+	}
 }
 
 void AUD_AnimateableProperty::read(float position, float* out)

Modified: trunk/blender/intern/audaspace/intern/AUD_AnimateableProperty.h
===================================================================
--- trunk/blender/intern/audaspace/intern/AUD_AnimateableProperty.h	2013-11-12 18:18:06 UTC (rev 61238)
+++ trunk/blender/intern/audaspace/intern/AUD_AnimateableProperty.h	2013-11-12 18:29:08 UTC (rev 61239)
@@ -34,6 +34,7 @@
 #include "AUD_ILockable.h"
 
 #include <pthread.h>
+#include <list>
 
 /**
  * This class saves animation data for float properties.
@@ -41,6 +42,14 @@
 class AUD_AnimateableProperty : private AUD_Buffer, public AUD_ILockable
 {
 private:
+	struct Unknown {
+		int start;
+		int end;
+
+		Unknown(int start, int end) :
+			start(start), end(end) {}
+	};
+
 	/// The count of floats for a single property.
 	const int m_count;
 
@@ -50,10 +59,15 @@
 	/// The mutex for locking.
 	pthread_mutex_t m_mutex;
 
+	/// The list of unknown buffer areas.
+	std::list<Unknown> m_unknown;
+
 	// hide copy constructor and operator=
 	AUD_AnimateableProperty(const AUD_AnimateableProperty&);
 	AUD_AnimateableProperty& operator=(const AUD_AnimateableProperty&);
 
+	void updateUnknownCache(int start, int end);
+
 public:
 	/**
 	 * Creates a new animateable property.




More information about the Bf-blender-cvs mailing list