Implementing event callbacks.
diff --git a/Source/Actor.cpp b/Source/Actor.cpp
index f991e9e..d48191e 100644
--- a/Source/Actor.cpp
+++ b/Source/Actor.cpp
@@ -20,6 +20,8 @@
 	m_Components(nullptr),
 	m_Nodes(nullptr),
 	m_Root(nullptr),
+	m_EventCallbackUserData(nullptr),
+	m_EventCallback(nullptr),
 	m_MaxTextureIndex(0),
 	m_ImageNodeCount(0),
 	m_SolverNodeCount(0),
@@ -27,6 +29,7 @@
 	m_ImageNodes(nullptr),
 	m_Solvers(nullptr),
 	m_Animations(nullptr)
+
 {
 
 }
@@ -93,6 +96,12 @@
 	return nullptr;
 }
 
+void Actor::eventCallback(ActorAnimationEvent::Callback callback, void* userdata)
+{
+	m_EventCallbackUserData = userdata;
+	m_EventCallback = callback;
+}
+
 ActorAnimation* Actor::animation(const std::string& name) const
 {
 	for(int i = 0; i < m_AnimationsCount; i++)
@@ -106,6 +115,16 @@
 	return nullptr;
 }
 
+ActorAnimationInstance* Actor::animationInstance(const std::string& name)
+{
+	ActorAnimation* a = animation(name);
+	if(a == nullptr)
+	{
+		return nullptr;
+	}
+	return new ActorAnimationInstance(this, a);
+}
+
 void Actor::load(unsigned char* bytes, unsigned int length)
 {
 	dispose();
diff --git a/Source/Actor.hpp b/Source/Actor.hpp
index 2d9f8e0..dcd534d 100644
--- a/Source/Actor.hpp
+++ b/Source/Actor.hpp
@@ -6,6 +6,7 @@
 #include "BlockReader.hpp"
 #include "Solver.hpp"
 #include "Animation/ActorAnimation.hpp"
+#include "Animation/ActorAnimationInstance.hpp"
 
 namespace nima
 {
@@ -25,9 +26,10 @@
 		ActorIKTarget = 11,
 		ActorEvent = 12
 	};
-
+	
 	class Actor
 	{
+		friend class ActorAnimationInstance;
 		public:
 			Actor();
 			virtual ~Actor();
@@ -45,6 +47,8 @@
 			ActorComponent** m_Components;
 			ActorNode** m_Nodes;
 			ActorNode* m_Root;
+			void* m_EventCallbackUserData;
+			ActorAnimationEvent::Callback m_EventCallback;
 			void readComponentsBlock(BlockReader* block);
 			void readAnimationsBlock(BlockReader* block);
 			
@@ -70,6 +74,8 @@
 			ActorComponent* component(unsigned int index) const;
 			ActorComponent* component(unsigned short index) const;
 			ActorComponent* component(const std::string& name) const;
+
+			void eventCallback(ActorAnimationEvent::Callback callback, void* userdata = nullptr);
 			
 			template<typename T>
 			T component(const std::string& name) const
@@ -79,6 +85,7 @@
 
 			ActorNode* root() const;
 			ActorAnimation* animation(const std::string& name) const;
+			ActorAnimationInstance* animationInstance(const std::string& name);
 
 			void copy(const Actor& actor);
 			const int textureCount() const;
diff --git a/Source/Animation/ActorAnimation.cpp b/Source/Animation/ActorAnimation.cpp
index c2774a4..cd1ef4d 100644
--- a/Source/Animation/ActorAnimation.cpp
+++ b/Source/Animation/ActorAnimation.cpp
@@ -42,11 +42,11 @@
 	}
 }
 
-void ActorAnimation::triggerEvents(ActorComponent** components, float fromTime, float toTime, std::vector<ActorAnimationEvent>& events)
+void ActorAnimation::triggerEvents(Actor* actor, float fromTime, float toTime, std::vector<ActorAnimationEvent>& events)
 {
 	for(auto keyedComponent : m_TriggerComponents)
 	{
-		keyedComponent->triggerEvents(components, fromTime, toTime, events);
+		keyedComponent->triggerEvents(actor, fromTime, toTime, events);
 	}
 }
 
diff --git a/Source/Animation/ActorAnimation.hpp b/Source/Animation/ActorAnimation.hpp
index d83149e..c8eb748 100644
--- a/Source/Animation/ActorAnimation.hpp
+++ b/Source/Animation/ActorAnimation.hpp
@@ -3,6 +3,7 @@
 
 #include <string>
 #include <vector>
+#include <functional>
 #include "ComponentAnimation.hpp"
 
 namespace nima
@@ -13,6 +14,7 @@
 
 	struct ActorAnimationEvent
 	{
+		typedef std::function<void(const ActorAnimationEvent&, void*)> Callback;
 		ActorEvent* actorEvent;
 		float keyFrameTime;
 		float elapsedTime;
@@ -50,7 +52,7 @@
 
 			void apply(float time, Actor* actor, float mix);
 
-			void triggerEvents(ActorComponent** components, float fromTime, float toTime, std::vector<ActorAnimationEvent>& events);
+			void triggerEvents(Actor* actor, float fromTime, float toTime, std::vector<ActorAnimationEvent>& events);
 
 	};
 }
diff --git a/Source/Animation/ActorAnimationInstance.cpp b/Source/Animation/ActorAnimationInstance.cpp
new file mode 100644
index 0000000..dcc7df4
--- /dev/null
+++ b/Source/Animation/ActorAnimationInstance.cpp
@@ -0,0 +1,168 @@
+#include "ActorAnimationInstance.hpp"
+#include "../Actor.hpp"
+#include <cmath>
+
+using namespace nima;
+
+ActorAnimationInstance::ActorAnimationInstance(Actor* actor, ActorAnimation* animation) :
+	m_Actor(actor),
+	m_Animation(animation),
+	m_Time(0.0f),
+	m_Min(0.0f),
+	m_Max(animation->duration()),
+	m_Range(animation->duration()),
+	m_Loop(animation->isLooping()),
+	m_EventCallbackUserData(nullptr),
+	m_EventCallback(nullptr)
+{
+
+}
+
+ActorAnimationInstance::~ActorAnimationInstance()
+{
+
+}
+
+float ActorAnimationInstance::duration() const
+{
+	return m_Range;
+}
+
+float ActorAnimationInstance::min() const
+{
+	return m_Min;
+}
+
+float ActorAnimationInstance::max() const
+{
+	return m_Max;
+}
+
+float ActorAnimationInstance::time() const
+{
+	return m_Time;
+}
+
+void ActorAnimationInstance::time(float value)
+{
+	float delta = value - m_Time;
+	float time = m_Time + std::fmod(delta, m_Range);
+
+	if(time < m_Min)
+	{
+		if(m_Loop)
+		{
+			time = m_Max - (m_Min - time);	
+		}
+		else
+		{
+			time = m_Min;
+		}
+	}
+	else if(time > m_Max)
+	{
+		if(m_Loop)
+		{
+			time = m_Min + (time - m_Max);
+		}
+		else
+		{
+			time = m_Max;
+		}
+	}
+	m_Time = time;
+}
+
+bool ActorAnimationInstance::isLooping() const
+{
+	return m_Loop;
+}
+
+void ActorAnimationInstance::isLooping(bool isIt)
+{
+	m_Loop = isIt;
+}
+
+void ActorAnimationInstance::eventCallback(ActorAnimationEvent::Callback callback, void* userdata)
+{
+	m_EventCallbackUserData = userdata;
+	m_EventCallback = callback;
+}
+
+void ActorAnimationInstance::advance(float seconds)
+{
+	float time = m_Time;
+	time += std::fmod(seconds, m_Range);
+	if(time < m_Min)
+	{
+		if(m_Loop)
+		{
+			m_Animation->triggerEvents(m_Actor, time, m_Time, m_Events);
+			time = m_Max - (m_Min - time);
+			m_Animation->triggerEvents(m_Actor, time, m_Max, m_Events);
+		}
+		else
+		{
+			time = m_Min;
+			if(m_Time != time)
+			{
+				m_Animation->triggerEvents(m_Actor, m_Min, m_Time, m_Events);
+			}
+		}
+	}
+	else if(time > m_Max)
+	{
+		if(m_Loop)
+		{
+			m_Animation->triggerEvents(m_Actor, time, m_Time, m_Events);
+			time = m_Min + (time - m_Max);
+			m_Animation->triggerEvents(m_Actor, m_Min-0.001f, time, m_Events);
+		}
+		else
+		{
+			time = m_Max;
+			if(m_Time != time)
+			{
+				m_Animation->triggerEvents(m_Actor, m_Time, m_Max, m_Events);
+			}
+		}
+	}
+	else if(time > m_Time)
+	{
+		m_Animation->triggerEvents(m_Actor, m_Time, time, m_Events);
+	}
+	else
+	{
+		m_Animation->triggerEvents(m_Actor, time, m_Time, m_Events);
+	}
+
+	for(const ActorAnimationEvent& ev : m_Events)
+	{
+		if(m_EventCallback != nullptr)
+		{
+			m_EventCallback(ev, m_EventCallbackUserData);
+		}
+		if(m_Actor->m_EventCallback != nullptr)
+		{
+			m_Actor->m_EventCallback(ev, m_Actor->m_EventCallbackUserData);
+		}
+        /*if (AnimationEvent != null)
+        {
+            AnimationEvent(this, ev);
+        }
+        m_Actor.OnAnimationEvent(ev);*/
+	}
+	m_Events.clear();
+	/*for(var i = 0; i < triggeredEvents.length; i++)
+	{
+		var event = triggeredEvents[i];
+		this.dispatch("animationEvent", event);
+		m_Actor.dispatch("animationEvent", event);
+	}*/
+	m_Time = time;
+}
+
+void ActorAnimationInstance::apply(float mix)
+{
+	m_Animation->apply(m_Time, m_Actor, mix);
+}
\ No newline at end of file
diff --git a/Source/Animation/ActorAnimationInstance.hpp b/Source/Animation/ActorAnimationInstance.hpp
new file mode 100644
index 0000000..8579ead
--- /dev/null
+++ b/Source/Animation/ActorAnimationInstance.hpp
@@ -0,0 +1,44 @@
+#ifndef _NIMA_ACTORANIMATIONINSTANCE_HPP_
+#define _NIMA_ACTORANIMATIONINSTANCE_HPP_
+
+#include <string>
+#include <vector>
+#include "ActorAnimation.hpp"
+
+namespace nima
+{
+	class ActorAnimationInstance
+	{
+		private:
+			Actor* m_Actor;
+			ActorAnimation* m_Animation;
+			float m_Time;
+			float m_Min;
+			float m_Max;
+			float m_Range;
+			bool m_Loop;
+			std::vector<ActorAnimationEvent> m_Events;
+			void* m_EventCallbackUserData;
+			ActorAnimationEvent::Callback m_EventCallback;
+
+		public:
+
+			ActorAnimationInstance(Actor* actor, ActorAnimation* animation);
+			~ActorAnimationInstance();
+
+			float duration() const;
+			float min() const;
+			float max() const;
+			float time() const;
+			void time(float value);
+			bool isLooping() const;
+			void isLooping(bool isIt);
+
+			void advance(float seconds);
+			void apply(float mix);
+
+			void eventCallback(ActorAnimationEvent::Callback callback, void* userdata = nullptr);
+
+	};
+}
+#endif
\ No newline at end of file
diff --git a/Source/Animation/ComponentAnimation.cpp b/Source/Animation/ComponentAnimation.cpp
index 551a811..039e2b5 100644
--- a/Source/Animation/ComponentAnimation.cpp
+++ b/Source/Animation/ComponentAnimation.cpp
@@ -33,7 +33,7 @@
 	}
 }
 
-void ComponentAnimation::triggerEvents(ActorComponent** components, float fromTime, float toTime, std::vector<ActorAnimationEvent>& events)
+void ComponentAnimation::triggerEvents(Actor* actor, float fromTime, float toTime, std::vector<ActorAnimationEvent>& events)
 {
 	for(int i = 0; i < m_PropertiesCount; i++)
 	{
@@ -81,7 +81,7 @@
 				{
 					if(property.keyFrame(0)->time() == toTime)
 					{
-						ActorEvent* actorEvent = reinterpret_cast<ActorEvent*>(components[m_ComponentIndex]);
+						ActorEvent* actorEvent = reinterpret_cast<ActorEvent*>(actor->component(m_ComponentIndex));
 						events.emplace_back(ActorAnimationEvent(actorEvent, toTime, 0.0f));
 						//ActorComponent component = components[keyedComponent.ComponentIndex];
 						//triggerEvents.Add(new AnimationEventArgs(component.Name, component, property.PropertyType, toTime, 0.0f));
@@ -95,7 +95,7 @@
 
 						if(frameTime > fromTime)
 						{
-							ActorEvent* actorEvent = reinterpret_cast<ActorEvent*>(components[m_ComponentIndex]);
+							ActorEvent* actorEvent = reinterpret_cast<ActorEvent*>(actor->component(m_ComponentIndex));
 							events.emplace_back(ActorAnimationEvent(actorEvent, frameTime, toTime-frameTime));
 
 							//ActorComponent component = components[keyedComponent.ComponentIndex];
diff --git a/Source/Animation/ComponentAnimation.hpp b/Source/Animation/ComponentAnimation.hpp
index a7b819e..aed4827 100644
--- a/Source/Animation/ComponentAnimation.hpp
+++ b/Source/Animation/ComponentAnimation.hpp
@@ -26,7 +26,7 @@
 
 			void read(BlockReader* reader, ActorComponent** components);
 			void apply(float time, Actor* actor, float mix);
-			void triggerEvents(ActorComponent** components, float fromTime, float toTime, std::vector<ActorAnimationEvent>& events);
+			void triggerEvents(Actor* actor, float fromTime, float toTime, std::vector<ActorAnimationEvent>& events);
 
 	};
 }
diff --git a/Source/BlockReader.hpp b/Source/BlockReader.hpp
index 7539374..b1a46c1 100644
--- a/Source/BlockReader.hpp
+++ b/Source/BlockReader.hpp
@@ -10,7 +10,6 @@
 	class Vec2D;
 
 	class BlockReader;
-	typedef std::shared_ptr<BlockReader> BlockReaderPtr;
 
 	class BlockReader : public BinaryReader
 	{