Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKester Maddock <Christopher.Maddock.1@uni.massey.ac.nz>2004-10-16 15:41:50 +0400
committerKester Maddock <Christopher.Maddock.1@uni.massey.ac.nz>2004-10-16 15:41:50 +0400
commit7b2567924b9b86961cd4c07b76653f49939cab1c (patch)
treeadcf1091db6f3f78c05c6b02c567a9b77fc10092 /source/gameengine/Ketsji/KX_IpoActuator.cpp
parent063982914038ecd578bab7849a1e94cccbb8d8b9 (diff)
Switch fixed time system. Logic updates should now happen at 30Hz, physics at 60Hz. (By default, use Python to set.) Some actuators still run at framerate (IPO, Action) for nice smooth animation, and an excuse to buy high end hardware.
Keyboard sensors can now hook escape key. Ctrl-Break can be used from within blender if you've forgotten an end game actuator. Fixed a stupid bug preventing some actuators working (like TrackTo).
Diffstat (limited to 'source/gameengine/Ketsji/KX_IpoActuator.cpp')
-rw-r--r--source/gameengine/Ketsji/KX_IpoActuator.cpp385
1 files changed, 208 insertions, 177 deletions
diff --git a/source/gameengine/Ketsji/KX_IpoActuator.cpp b/source/gameengine/Ketsji/KX_IpoActuator.cpp
index 7a894db6647..6234a5809f2 100644
--- a/source/gameengine/Ketsji/KX_IpoActuator.cpp
+++ b/source/gameengine/Ketsji/KX_IpoActuator.cpp
@@ -32,6 +32,8 @@
* ***** END GPL/BL DUAL LICENSE BLOCK *****
*/
+#include <cmath>
+
#include "KX_IpoActuator.h"
#include "KX_GameObject.h"
@@ -39,6 +41,8 @@
#include <config.h>
#endif
+#include "KX_KetsjiEngine.h"
+
/* ------------------------------------------------------------------------- */
/* Type strings */
/* ------------------------------------------------------------------------- */
@@ -100,10 +104,11 @@ KX_IpoActuator::KX_IpoActuator(SCA_IObject* gameobj,
PyTypeObject* T)
: SCA_IActuator(gameobj,T),
m_bNegativeEvent(false),
- m_starttime (starttime),
- m_endtime(endtime),
+ m_startframe (starttime),
+ m_endframe(endtime),
m_recurse(recurse),
m_localtime(starttime),
+ m_starttime(-1.0),
m_direction(1),
m_propname(propname),
m_ipo_as_force(ipo_as_force),
@@ -115,22 +120,35 @@ KX_IpoActuator::KX_IpoActuator(SCA_IObject* gameobj,
void KX_IpoActuator::SetStart(float starttime)
{
- m_starttime=starttime;
+ m_startframe=starttime;
}
void KX_IpoActuator::SetEnd(float endtime)
{
- m_endtime=endtime;
+ m_endframe=endtime;
}
+void KX_IpoActuator::SetStartTime(float curtime)
+{
+ if (m_direction > 0)
+ m_starttime = curtime - (m_localtime - m_startframe)/KX_FIXED_FRAME_PER_SEC;
+ else
+ m_starttime = curtime - (m_endframe - m_localtime)/KX_FIXED_FRAME_PER_SEC;
+}
-bool KX_IpoActuator::Update(double curtime,double delta_time)
+void KX_IpoActuator::SetLocalTime(float curtime)
+{
+ float delta_time = (curtime - m_starttime)*KX_FIXED_FRAME_PER_SEC;
+ if (m_direction > 0)
+ m_localtime = m_startframe + delta_time;
+ else
+ m_localtime = m_endframe - delta_time;
+}
+
+bool KX_IpoActuator::Update(double curtime, bool frame)
{
- SCA_IActuator::Update(curtime,delta_time);
// result = true if animation has to be continued, false if animation stops
// maybe there are events for us in the queue !
-
-
bool bNegativeEvent = false;
int numevents = m_events.size();
@@ -138,10 +156,8 @@ bool KX_IpoActuator::Update(double curtime,double delta_time)
{
i--;
if ((*i)->GetNumber() == 0.0f)
- {
- int ka=0;
bNegativeEvent = true;
- }
+
(*i)->Release();
m_events.pop_back();
}
@@ -152,101 +168,195 @@ bool KX_IpoActuator::Update(double curtime,double delta_time)
}
- double start_smaller_then_end = ( m_starttime < m_endtime ? 1.0 : -1.0);
-
- double deltaframetime = start_smaller_then_end * delta_time * KX_FIXED_FRAME_PER_SEC;
+ double start_smaller_then_end = ( m_startframe < m_endframe ? 1.0 : -1.0);
bool result=true;
+ if (m_starttime < 0.0)
+ m_starttime = curtime;
switch (m_type)
{
case KX_ACT_IPO_PLAY:
+ {
+ // Check if playing forwards. result = ! finished
+ if (start_smaller_then_end > 0.0)
+ result = (m_localtime < m_endframe && !(m_localtime == m_startframe && bNegativeEvent));
+ else
+ result = (m_localtime > m_endframe && !(m_localtime == m_startframe && bNegativeEvent));
+
+ if (result)
{
-
- if (start_smaller_then_end > 0.0)
- result = (m_localtime < m_endtime && !(m_localtime == m_starttime && bNegativeEvent));
- else
- result = (m_localtime > m_endtime && !(m_localtime == m_starttime && bNegativeEvent));
- if (result)
- {
- m_localtime += m_direction * deltaframetime;
-
- /* Perform clamping */
- if ((m_localtime*start_smaller_then_end)>(m_endtime*start_smaller_then_end))
- m_localtime=m_endtime;
-
- CIpoAction ipoaction(
- (KX_GameObject*)GetParent(),
- m_localtime,
- m_recurse,
- m_ipo_as_force,
- m_force_ipo_local);
- GetParent()->Execute(ipoaction);
- } else
- {
- m_localtime=m_starttime;
- m_direction=1;
- }
- break;
- }
- case KX_ACT_IPO_PINGPONG:
- {
- result = true;
- if (bNegativeEvent && ((m_localtime == m_starttime )|| (m_localtime == m_endtime)))
- {
- result = false;
- } else
- {
- m_localtime += m_direction * deltaframetime;
- }
-
- if (m_localtime*start_smaller_then_end < m_starttime*start_smaller_then_end)
- {
- m_localtime = m_starttime;
- result = false;
- m_direction = 1;
- }else
- if (m_localtime*start_smaller_then_end > m_endtime*start_smaller_then_end)
- {
- m_localtime = m_endtime;
- result = false;
- m_direction = -1;
- }
-
+ SetLocalTime(curtime);
+
+ /* Perform clamping */
+ if ((m_localtime*start_smaller_then_end)>(m_endframe*start_smaller_then_end))
+ m_localtime=m_endframe;
+
CIpoAction ipoaction(
- (KX_GameObject*) GetParent(),
- m_localtime,
+ (KX_GameObject*)GetParent(),
+ m_localtime,
m_recurse,
m_ipo_as_force,
m_force_ipo_local);
GetParent()->Execute(ipoaction);
- break;
+ } else
+ {
+ m_localtime=m_startframe;
+ m_starttime=curtime;
+ m_direction=1;
}
-
+ break;
+ }
+ case KX_ACT_IPO_PINGPONG:
+ {
+ result = true;
+ if (bNegativeEvent && ((m_localtime == m_startframe )|| (m_localtime == m_endframe)))
+ result = false;
+ else
+ SetLocalTime(curtime);
+
+ if (m_localtime*start_smaller_then_end < m_startframe*start_smaller_then_end)
+ {
+ m_localtime = m_startframe;
+ result = false;
+ m_direction = 1;
+ }
+ else if (m_localtime*start_smaller_then_end > m_endframe*start_smaller_then_end)
+ {
+ m_localtime = m_endframe;
+ result = false;
+ m_direction = -1;
+ }
+
+ CIpoAction ipoaction(
+ (KX_GameObject*) GetParent(),
+ m_localtime,
+ m_recurse,
+ m_ipo_as_force,
+ m_force_ipo_local);
+ GetParent()->Execute(ipoaction);
+ break;
+ }
case KX_ACT_IPO_FLIPPER:
+ {
+ result = true;
+ if (numevents)
+ {
+ if (bNegativeEvent)
+ m_direction = -1;
+ else
+ m_direction = 1;
+ SetStartTime(curtime);
+ }
+
+ SetLocalTime(curtime);
+
+ if (m_localtime*start_smaller_then_end > m_endframe*start_smaller_then_end)
+ {
+ m_localtime = m_endframe;
+ }
+ else if (m_localtime*start_smaller_then_end < m_startframe*start_smaller_then_end)
{
- result = true;
- if (numevents)
+ m_localtime = m_startframe;
+ result = false;
+ }
+
+ CIpoAction ipoaction(
+ (KX_GameObject*) GetParent(),
+ m_localtime,
+ m_recurse,
+ m_ipo_as_force,
+ m_force_ipo_local);
+ GetParent()->Execute(ipoaction);
+ break;
+ }
+
+ case KX_ACT_IPO_LOOPSTOP:
+ {
+ if (numevents)
+ {
+ if (bNegativeEvent)
+ {
+ result = false;
+ m_bNegativeEvent = false;
+ numevents = 0;
+ }
+ SetStartTime(curtime);
+ } // fall through to loopend, and quit the ipo animation immediatly
+ }
+ case KX_ACT_IPO_LOOPEND:
+ {
+ if (numevents){
+ if (bNegativeEvent){
+ m_bNegativeEvent = true;
+ }
+ }
+
+ if (bNegativeEvent && m_localtime == m_startframe){
+ result = false;
+ }
+ else{
+ if (m_localtime*start_smaller_then_end < m_endframe*start_smaller_then_end)
{
- if (bNegativeEvent)
- m_direction = -1;
+ SetLocalTime(curtime);
+ }
+ else{
+ if (!m_bNegativeEvent){
+ /* Perform wraparound */
+ SetLocalTime(curtime);
+ m_localtime = m_startframe + std::fmod(m_localtime, m_startframe - m_endframe);
+ SetStartTime(curtime);
+ }
else
- m_direction = 1;
+ {
+ /* Perform clamping */
+ m_localtime=m_endframe;
+ result = false;
+ m_bNegativeEvent = false;
+ }
}
+ }
+
+ CIpoAction ipoaction(
+ (KX_GameObject*) GetParent(),
+ m_localtime,
+ m_recurse,
+ m_ipo_as_force,
+ m_force_ipo_local);
+ GetParent()->Execute(ipoaction);
+ break;
+ }
+
+ case KX_ACT_IPO_KEY2KEY:
+ {
+ // not implemented yet
+ result = false;
+ break;
+ }
+
+ case KX_ACT_IPO_FROM_PROP:
+ {
+ result = !bNegativeEvent;
- m_localtime += m_direction * deltaframetime;
-
- if (m_localtime*start_smaller_then_end > m_endtime*start_smaller_then_end)
+ CValue* propval = GetParent()->GetProperty(m_propname);
+ if (propval)
+ {
+ float target = propval->GetNumber();
+ float delta_time = (curtime - m_starttime)*KX_FIXED_FRAME_PER_SEC;
+ if (target > m_localtime)
{
- m_localtime = m_endtime;
- } else
- if (m_localtime*start_smaller_then_end < m_starttime*start_smaller_then_end)
- {
- m_localtime = m_starttime;
- result = false;
- }
-
+ m_localtime += delta_time;
+ if (m_localtime > target)
+ m_localtime = target;
+ }
+ else
+ {
+ m_localtime -= delta_time;
+ if (m_localtime < target)
+ m_localtime = target;
+ }
+
CIpoAction ipoaction(
(KX_GameObject*) GetParent(),
m_localtime,
@@ -254,99 +364,20 @@ bool KX_IpoActuator::Update(double curtime,double delta_time)
m_ipo_as_force,
m_force_ipo_local);
GetParent()->Execute(ipoaction);
- break;
- }
- case KX_ACT_IPO_LOOPSTOP:
- {
- if (numevents)
- {
- if (bNegativeEvent)
- {
- result = false;
- m_bNegativeEvent = false;
- numevents = 0;
- }
- } // fall through to loopend, and quit the ipo animation immediatly
- }
-
- case KX_ACT_IPO_LOOPEND:
- {
- if (numevents){
- if (bNegativeEvent){
- m_bNegativeEvent = true;
- }
- }
-
- if (bNegativeEvent && m_localtime == m_starttime){
- result = false;
- }
- else{
- if (m_localtime*start_smaller_then_end < m_endtime*start_smaller_then_end){
- m_localtime += m_direction * deltaframetime;
- }
- else{
- if (!m_bNegativeEvent){
- /* Perform wraparound */
- float slop = m_localtime-m_endtime;
- float length = fabs(m_starttime-m_endtime);
- m_localtime = m_starttime + (slop - (int(slop/length)*(int(length))));
-
- }
- else
- {
- /* Perform clamping */
- if ((m_localtime*start_smaller_then_end)>(m_endtime*start_smaller_then_end))
- m_localtime=m_endtime;
-
- result = false;
- m_bNegativeEvent = false;
- }
- }
- }
- CIpoAction ipoaction(
- (KX_GameObject*) GetParent(),
- m_localtime,
- m_recurse,
- m_ipo_as_force,
- m_force_ipo_local);
- GetParent()->Execute(ipoaction);
- break;
- }
- case KX_ACT_IPO_KEY2KEY:
+ } else
{
- // not implemented yet
result = false;
- break;
- }
- case KX_ACT_IPO_FROM_PROP:
- {
- result = !bNegativeEvent;
-
- CValue* propval = GetParent()->GetProperty(m_propname);
- if (propval)
- {
- m_localtime = propval->GetNumber();
- CIpoAction ipoaction(
- (KX_GameObject*) GetParent(),
- m_localtime,
- m_recurse,
- m_ipo_as_force,
- m_force_ipo_local);
- GetParent()->Execute(ipoaction);
-
- } else
- {
- result = false;
- }
- break;
}
+ break;
+ }
default:
- {
- result = false;
- }
+ result = false;
}
+
+ if (!result && m_type != KX_ACT_IPO_LOOPSTOP)
+ m_starttime = -1.0;
return result;
}
@@ -472,8 +503,8 @@ PyObject* KX_IpoActuator::PySet(PyObject* self,
case KX_ACT_IPO_LOOPSTOP:
case KX_ACT_IPO_LOOPEND:
m_type = modenum;
- m_starttime = startFrame;
- m_endtime = stopFrame;
+ m_startframe = startFrame;
+ m_endframe = stopFrame;
m_ipo_as_force = PyArgToBool(forceToggle);
break;
default:
@@ -516,7 +547,7 @@ PyObject* KX_IpoActuator::PySetStart(PyObject* self,
return NULL;
}
- m_starttime = startArg;
+ m_startframe = startArg;
Py_Return;
}
@@ -527,7 +558,7 @@ char KX_IpoActuator::GetStart_doc[] =
PyObject* KX_IpoActuator::PyGetStart(PyObject* self,
PyObject* args,
PyObject* kwds) {
- return PyFloat_FromDouble(m_starttime);
+ return PyFloat_FromDouble(m_startframe);
}
/* 6. setEnd: */
@@ -543,7 +574,7 @@ PyObject* KX_IpoActuator::PySetEnd(PyObject* self,
return NULL;
}
- m_endtime = endArg;
+ m_endframe = endArg;
Py_Return;
}
@@ -554,7 +585,7 @@ char KX_IpoActuator::GetEnd_doc[] =
PyObject* KX_IpoActuator::PyGetEnd(PyObject* self,
PyObject* args,
PyObject* kwds) {
- return PyFloat_FromDouble(m_endtime);
+ return PyFloat_FromDouble(m_endframe);
}
/* 6. setIpoAsForce: */