svn merge https://svn.blender.org/svnroot/bf-blender/trunk/blender -r22205:22290
[blender.git] / source / gameengine / Ketsji / KX_IpoActuator.cpp
1 /**
2  * Do Ipo stuff
3  *
4  * $Id$
5  *
6  * ***** BEGIN GPL LICENSE BLOCK *****
7  *
8  * This program is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License
10  * as published by the Free Software Foundation; either version 2
11  * of the License, or (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, write to the Free Software Foundation,
20  * Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
21  *
22  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
23  * All rights reserved.
24  *
25  * The Original Code is: all of this file.
26  *
27  * Contributor(s): none yet.
28  *
29  * ***** END GPL LICENSE BLOCK *****
30  */
31
32 #if defined (__sgi)
33 #include <math.h>
34 #else
35 #include <cmath>
36 #endif
37  
38 #include "KX_IpoActuator.h"
39 #include "KX_GameObject.h"
40 #include "FloatValue.h"
41
42 #ifdef HAVE_CONFIG_H
43 #include <config.h>
44 #endif
45
46 #include "KX_KetsjiEngine.h"
47
48 /* ------------------------------------------------------------------------- */
49 /* Type strings                                                              */
50 /* ------------------------------------------------------------------------- */
51
52 STR_String KX_IpoActuator::S_KX_ACT_IPO_PLAY_STRING      = "Play";
53 STR_String KX_IpoActuator::S_KX_ACT_IPO_PINGPONG_STRING  = "PingPong";
54 STR_String KX_IpoActuator::S_KX_ACT_IPO_FLIPPER_STRING   = "Flipper";
55 STR_String KX_IpoActuator::S_KX_ACT_IPO_LOOPSTOP_STRING  = "LoopStop";
56 STR_String KX_IpoActuator::S_KX_ACT_IPO_LOOPEND_STRING   = "LoopEnd";
57 STR_String KX_IpoActuator::S_KX_ACT_IPO_KEY2KEY_STRING   = "Key2key";
58 STR_String KX_IpoActuator::S_KX_ACT_IPO_FROM_PROP_STRING = "FromProp";
59
60 /* ------------------------------------------------------------------------- */
61 /* Native functions                                                          */
62 /* ------------------------------------------------------------------------- */
63
64 KX_IpoActuator::KX_IpoActuator(SCA_IObject* gameobj,
65                                                            const STR_String& propname,
66                                                            const STR_String& framePropname,
67                                                            float starttime,
68                                                            float endtime,
69                                                            bool recurse,
70                                                            int acttype,
71                                                            bool ipo_as_force,
72                                                            bool ipo_add,
73                                                            bool ipo_local)
74         : SCA_IActuator(gameobj),
75         m_bNegativeEvent(false),
76         m_startframe (starttime),
77         m_endframe(endtime),
78         m_recurse(recurse),
79         m_localtime(starttime),
80         m_direction(1),
81         m_propname(propname),
82         m_framepropname(framePropname),
83         m_ipo_as_force(ipo_as_force),
84         m_ipo_add(ipo_add),
85         m_ipo_local(ipo_local),
86         m_type(acttype)
87 {
88         m_starttime = -2.0*fabs(m_endframe - m_startframe) - 1.0;
89         m_bIpoPlaying = false;
90 }
91
92 void KX_IpoActuator::SetStart(float starttime) 
93
94         m_startframe=starttime;
95 }
96
97 void KX_IpoActuator::SetEnd(float endtime) 
98
99         m_endframe=endtime;
100 }
101
102 bool KX_IpoActuator::ClampLocalTime()
103 {
104         if (m_startframe < m_endframe)
105         {
106                 if (m_localtime < m_startframe)
107                 {
108                         m_localtime = m_startframe;
109                         return true;
110                 } 
111                 else if (m_localtime > m_endframe)
112                 {
113                         m_localtime = m_endframe;
114                         return true;
115                 }
116         } else {
117                 if (m_localtime > m_startframe)
118                 {
119                         m_localtime = m_startframe;
120                         return true;
121                 }
122                 else if (m_localtime < m_endframe)
123                 {
124                         m_localtime = m_endframe;
125                         return true;
126                 }
127         }
128         return false;
129 }
130
131 void KX_IpoActuator::SetStartTime(float curtime)
132 {
133         float direction = m_startframe < m_endframe ? 1.0f : -1.0f;
134
135         if (m_direction > 0)
136                 m_starttime = curtime - direction*(m_localtime - m_startframe)/KX_KetsjiEngine::GetAnimFrameRate();
137         else
138                 m_starttime = curtime - direction*(m_endframe - m_localtime)/KX_KetsjiEngine::GetAnimFrameRate();
139 }
140
141 void KX_IpoActuator::SetLocalTime(float curtime)
142 {
143         float delta_time = (curtime - m_starttime)*KX_KetsjiEngine::GetAnimFrameRate();
144         
145         // negative delta_time is caused by floating point inaccuracy
146         // perhaps the inaccuracy could be reduced a bit
147         if ((m_localtime==m_startframe || m_localtime==m_endframe) && delta_time<0.0)
148         {
149                 delta_time = 0.0;
150         }
151         
152         if (m_endframe < m_startframe)
153                 delta_time = -delta_time;
154
155         if (m_direction > 0)
156                 m_localtime = m_startframe + delta_time;
157         else
158                 m_localtime = m_endframe - delta_time;
159 }
160
161 bool KX_IpoActuator::Update(double curtime, bool frame)
162 {
163         // result = true if animation has to be continued, false if animation stops
164         // maybe there are events for us in the queue !
165         bool bNegativeEvent = false;
166         bool numevents = false;
167         bool bIpoStart = false;
168
169         curtime -= KX_KetsjiEngine::GetSuspendedDelta();
170
171         if (frame)
172         {
173                 numevents = m_posevent || m_negevent;
174                 bNegativeEvent = IsNegativeEvent();
175                 RemoveAllEvents();
176         }
177         
178         float  start_smaller_then_end = ( m_startframe < m_endframe ? 1.0f : -1.0f);
179
180         bool result=true;
181         if (!bNegativeEvent)
182         {
183                 if (m_starttime < -2.0f*start_smaller_then_end*(m_endframe - m_startframe))
184                 {
185                         // start for all Ipo, initial start for LOOP_STOP
186                         m_starttime = curtime;
187                         m_bIpoPlaying = true;
188                         bIpoStart = true;
189                 }
190         }       
191
192         switch ((IpoActType)m_type)
193         {
194                 
195         case KX_ACT_IPO_PLAY:
196         {
197                 // Check if playing forwards.  result = ! finished
198                 
199                 if (start_smaller_then_end > 0.f)
200                         result = (m_localtime < m_endframe && m_bIpoPlaying);
201                 else
202                         result = (m_localtime > m_endframe && m_bIpoPlaying);
203                 
204                 if (result)
205                 {
206                         SetLocalTime(curtime);
207                 
208                         /* Perform clamping */
209                         ClampLocalTime();
210         
211                         if (bIpoStart)
212                                 ((KX_GameObject*)GetParent())->InitIPO(m_ipo_as_force, m_ipo_add, m_ipo_local);
213                         ((KX_GameObject*)GetParent())->UpdateIPO(m_localtime,m_recurse);
214                 } else
215                 {
216                         m_localtime=m_startframe;
217                         m_direction=1;
218                 }
219                 break;
220         }
221         case KX_ACT_IPO_PINGPONG:
222         {
223                 result = true;
224                 if (bNegativeEvent && !m_bIpoPlaying)
225                         result = false;
226                 else
227                         SetLocalTime(curtime);
228                         
229                 if (ClampLocalTime())
230                 {
231                         result = false;
232                         m_direction = -m_direction;
233                 }
234                 
235                 if (bIpoStart && m_direction > 0)
236                         ((KX_GameObject*)GetParent())->InitIPO(m_ipo_as_force, m_ipo_add, m_ipo_local);
237                 ((KX_GameObject*)GetParent())->UpdateIPO(m_localtime,m_recurse);
238                 break;
239         }
240         case KX_ACT_IPO_FLIPPER:
241         {
242                 if (bNegativeEvent && !m_bIpoPlaying)
243                         result = false;
244                 if (numevents)
245                 {
246                         float oldDirection = m_direction;
247                         if (bNegativeEvent)
248                                 m_direction = -1;
249                         else
250                                 m_direction = 1;
251                         if (m_direction != oldDirection)
252                                 // changing direction, reset start time
253                                 SetStartTime(curtime);
254                 }
255                 
256                 SetLocalTime(curtime);
257                 
258                 if (ClampLocalTime() && m_localtime == m_startframe)
259                         result = false;
260
261                 if (bIpoStart)
262                         ((KX_GameObject*)GetParent())->InitIPO(m_ipo_as_force, m_ipo_add, m_ipo_local);                 
263                 ((KX_GameObject*)GetParent())->UpdateIPO(m_localtime,m_recurse);
264                 break;
265         }
266
267         case KX_ACT_IPO_LOOPSTOP:
268         {
269                 if (numevents)
270                 {
271                         if (bNegativeEvent)
272                         {
273                                 result = false;
274                                 m_bNegativeEvent = false;
275                                 numevents = false;
276                         }
277                         if (!m_bIpoPlaying)
278                         {
279                                 // Ipo was stopped, make sure we will restart from where it stopped
280                                 SetStartTime(curtime);
281                                 if (!bNegativeEvent)
282                                         // positive signal will restart the Ipo
283                                         m_bIpoPlaying = true;
284                         }
285
286                 } // fall through to loopend, and quit the ipo animation immediatly 
287         }
288         case KX_ACT_IPO_LOOPEND:
289         {
290                 if (numevents){
291                         if (bNegativeEvent && m_bIpoPlaying){
292                                 m_bNegativeEvent = true;
293                         }
294                 }
295                 
296                 if (bNegativeEvent && !m_bIpoPlaying){
297                         result = false;
298                 } 
299                 else
300                 {
301                         if (m_localtime*start_smaller_then_end < m_endframe*start_smaller_then_end)
302                         {
303                                 SetLocalTime(curtime);
304                         }
305                         else{
306                                 if (!m_bNegativeEvent){
307                                         /* Perform wraparound */
308                                         SetLocalTime(curtime);
309                                         if (start_smaller_then_end > 0.f)
310                                                 m_localtime = m_startframe + fmod(m_localtime - m_startframe, m_endframe - m_startframe);
311                                         else
312                                                 m_localtime = m_startframe - fmod(m_startframe - m_localtime, m_startframe - m_endframe);
313                                         SetStartTime(curtime);
314                                         bIpoStart = true;
315                                 }
316                                 else
317                                 {       
318                                         /* Perform clamping */
319                                         m_localtime=m_endframe;
320                                         result = false;
321                                         m_bNegativeEvent = false;
322                                 }
323                         }
324                 }
325                 
326                 if (m_bIpoPlaying && bIpoStart)
327                         ((KX_GameObject*)GetParent())->InitIPO(m_ipo_as_force, m_ipo_add, m_ipo_local);
328                 ((KX_GameObject*)GetParent())->UpdateIPO(m_localtime,m_recurse);
329                 break;
330         }
331         
332         case KX_ACT_IPO_KEY2KEY:
333         {
334                 // not implemented yet
335                 result = false;
336                 break;
337         }
338         
339         case KX_ACT_IPO_FROM_PROP:
340         {
341                 result = !bNegativeEvent;
342
343                 CValue* propval = GetParent()->GetProperty(m_propname);
344                 if (propval)
345                 {
346                         m_localtime = propval->GetNumber(); 
347         
348                         if (bIpoStart)
349                                 ((KX_GameObject*)GetParent())->InitIPO(m_ipo_as_force, m_ipo_add, m_ipo_local);
350                         ((KX_GameObject*)GetParent())->UpdateIPO(m_localtime,m_recurse);
351                 } else
352                 {
353                         result = false;
354                 }
355                 break;
356         }
357                 
358         default:
359                 result = false;
360         }
361
362         /* Set the property if its defined */
363         if (m_framepropname[0] != '\0') {
364                 CValue* propowner = GetParent();
365                 CValue* oldprop = propowner->GetProperty(m_framepropname);
366                 CValue* newval = new CFloatValue(m_localtime);
367                 if (oldprop) {
368                         oldprop->SetValue(newval);
369                 } else {
370                         propowner->SetProperty(m_framepropname, newval);
371                 }
372                 newval->Release();
373         }
374
375         if (!result)
376         {
377                 if (m_type != KX_ACT_IPO_LOOPSTOP)
378                         m_starttime = -2.0*start_smaller_then_end*(m_endframe - m_startframe) - 1.0;
379                 m_bIpoPlaying = false;
380         }
381
382         return result;
383 }
384
385 int KX_IpoActuator::string2mode(char* modename) {
386         IpoActType res = KX_ACT_IPO_NODEF;
387
388         if (modename == S_KX_ACT_IPO_PLAY_STRING) { 
389                 res = KX_ACT_IPO_PLAY;
390         } else if (modename == S_KX_ACT_IPO_PINGPONG_STRING) {
391                 res = KX_ACT_IPO_PINGPONG;
392         } else if (modename == S_KX_ACT_IPO_FLIPPER_STRING) {
393                 res = KX_ACT_IPO_FLIPPER;
394         } else if (modename == S_KX_ACT_IPO_LOOPSTOP_STRING) {
395                 res = KX_ACT_IPO_LOOPSTOP;
396         } else if (modename == S_KX_ACT_IPO_LOOPEND_STRING) {
397                 res = KX_ACT_IPO_LOOPEND;
398         } else if (modename == S_KX_ACT_IPO_KEY2KEY_STRING) {
399                 res = KX_ACT_IPO_KEY2KEY;
400         } else if (modename == S_KX_ACT_IPO_FROM_PROP_STRING) {
401                 res = KX_ACT_IPO_FROM_PROP;
402         }
403
404         return res;
405 }
406
407 /* ------------------------------------------------------------------------- */
408 /* Python functions                                                          */
409 /* ------------------------------------------------------------------------- */
410
411
412
413 /* Integration hooks ------------------------------------------------------- */
414 PyTypeObject KX_IpoActuator::Type = {
415 #if (PY_VERSION_HEX >= 0x02060000)
416         PyVarObject_HEAD_INIT(NULL, 0)
417 #else
418         /* python 2.5 and below */
419         PyObject_HEAD_INIT( NULL )  /* required py macro */
420         0,                          /* ob_size */
421 #endif
422         "KX_IpoActuator",
423         sizeof(PyObjectPlus_Proxy),
424         0,
425         py_base_dealloc,
426         0,
427         0,
428         0,
429         0,
430         py_base_repr,
431         0,0,0,0,0,0,0,0,0,
432         Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,
433         0,0,0,0,0,0,0,
434         Methods,
435         0,
436         0,
437         &SCA_IActuator::Type,
438         0,0,0,0,0,0,
439         py_base_new
440 };
441
442 PyMethodDef KX_IpoActuator::Methods[] = {
443         // deprecated 
444         {"set", (PyCFunction) KX_IpoActuator::sPySet, METH_VARARGS, (PY_METHODCHAR)Set_doc},
445         {"setProperty", (PyCFunction) KX_IpoActuator::sPySetProperty, METH_VARARGS, (PY_METHODCHAR)SetProperty_doc},
446         {"setStart", (PyCFunction) KX_IpoActuator::sPySetStart, METH_VARARGS, (PY_METHODCHAR)SetStart_doc},
447         {"getStart", (PyCFunction) KX_IpoActuator::sPyGetStart, METH_NOARGS, (PY_METHODCHAR)GetStart_doc},
448         {"setEnd", (PyCFunction) KX_IpoActuator::sPySetEnd, METH_VARARGS, (PY_METHODCHAR)SetEnd_doc},
449         {"getEnd", (PyCFunction) KX_IpoActuator::sPyGetEnd, METH_NOARGS, (PY_METHODCHAR)GetEnd_doc},
450         {"setIpoAsForce", (PyCFunction) KX_IpoActuator::sPySetIpoAsForce, METH_VARARGS, (PY_METHODCHAR)SetIpoAsForce_doc},
451         {"getIpoAsForce", (PyCFunction) KX_IpoActuator::sPyGetIpoAsForce, METH_NOARGS, (PY_METHODCHAR)GetIpoAsForce_doc},
452         {"setIpoAdd", (PyCFunction) KX_IpoActuator::sPySetIpoAdd, METH_VARARGS, (PY_METHODCHAR)SetIpoAdd_doc},
453         {"getIpoAdd", (PyCFunction) KX_IpoActuator::sPyGetIpoAdd, METH_NOARGS, (PY_METHODCHAR)GetIpoAdd_doc},
454         {"setForceIpoActsLocal", (PyCFunction) KX_IpoActuator::sPySetForceIpoActsLocal, METH_VARARGS, (PY_METHODCHAR)SetForceIpoActsLocal_doc},
455         {"getForceIpoActsLocal", (PyCFunction) KX_IpoActuator::sPyGetForceIpoActsLocal, METH_NOARGS, (PY_METHODCHAR)GetForceIpoActsLocal_doc},
456         {"setType", (PyCFunction) KX_IpoActuator::sPySetType, METH_VARARGS, (PY_METHODCHAR)SetType_doc},
457         {"getType", (PyCFunction) KX_IpoActuator::sPyGetType, METH_NOARGS, (PY_METHODCHAR)GetType_doc}, 
458         {NULL,NULL} //Sentinel
459 };
460
461 PyAttributeDef KX_IpoActuator::Attributes[] = {
462         KX_PYATTRIBUTE_FLOAT_RW("frameStart", 0, 300000, KX_IpoActuator, m_startframe),
463         KX_PYATTRIBUTE_FLOAT_RW("frameEnd", 0, 300000, KX_IpoActuator, m_endframe),
464         KX_PYATTRIBUTE_STRING_RW("propName", 0, 64, false, KX_IpoActuator, m_propname),
465         KX_PYATTRIBUTE_STRING_RW("framePropName", 0, 64, false, KX_IpoActuator, m_framepropname),
466         KX_PYATTRIBUTE_INT_RW("mode", KX_ACT_IPO_NODEF+1, KX_ACT_IPO_MAX-1, true, KX_IpoActuator, m_type),
467         KX_PYATTRIBUTE_BOOL_RW("useIpoAsForce", KX_IpoActuator, m_ipo_as_force),
468         KX_PYATTRIBUTE_BOOL_RW("useIpoAdd", KX_IpoActuator, m_ipo_add),
469         KX_PYATTRIBUTE_BOOL_RW("useIpoLocal", KX_IpoActuator, m_ipo_local),
470         KX_PYATTRIBUTE_BOOL_RW("useChildren", KX_IpoActuator, m_recurse),
471         
472         { NULL }        //Sentinel
473 };
474
475
476 /* set --------------------------------------------------------------------- */
477 const char KX_IpoActuator::Set_doc[] = 
478 "set(type, startframe, endframe, mode?)\n"
479 "\t - type:       Play, PingPong, Flipper, LoopStop, LoopEnd or FromProp (string)\n"
480 "\t - startframe: first frame to use (int)\n"
481 "\t - endframe  : last frame to use (int)\n"
482 "\t - mode?     : special mode (0=normal, 1=interpret location as force, 2=additive)"
483 "\tSet the properties of the actuator.\n";
484 PyObject* KX_IpoActuator::PySet(PyObject* args) {
485         
486         ShowDeprecationWarning("set()", "a range properties");
487                                                                         
488         /* sets modes PLAY, PINGPONG, FLIPPER, LOOPSTOP, LOOPEND                 */
489         /* arg 1 = mode string, arg 2 = startframe, arg3 = stopframe,            */
490         /* arg4 = force toggle                                                   */
491         char* mode;
492         int forceToggle;
493         int modenum;
494         int startFrame, stopFrame;
495         if(!PyArg_ParseTuple(args, "siii:set", &mode, &startFrame, 
496                                                  &stopFrame, &forceToggle)) {
497                 return NULL;
498         }
499         modenum = string2mode(mode);
500         
501         switch (modenum) {
502         case KX_ACT_IPO_PLAY:
503         case KX_ACT_IPO_PINGPONG:
504         case KX_ACT_IPO_FLIPPER:
505         case KX_ACT_IPO_LOOPSTOP:
506         case KX_ACT_IPO_LOOPEND:
507                 m_type         = modenum;
508                 m_startframe    = startFrame;
509                 m_endframe      = stopFrame;
510                 m_ipo_as_force = forceToggle == 1;
511                 m_ipo_add = forceToggle == 2;
512                 break;
513         default:
514                 ; /* error */
515         }
516
517         Py_RETURN_NONE;
518 }
519
520 /* set property  ----------------------------------------------------------- */
521 const char KX_IpoActuator::SetProperty_doc[] = 
522 "setProperty(propname)\n"
523 "\t - propname: name of the property (string)\n"
524 "\tSet the property to be used in FromProp mode.\n";
525 PyObject* KX_IpoActuator::PySetProperty(PyObject* args) {
526
527         ShowDeprecationWarning("setProperty()", "the propName property");
528
529         /* mode is implicit here, but not supported yet... */
530         /* args: property */
531         char *propertyName;
532         if(!PyArg_ParseTuple(args, "s:setProperty", &propertyName)) {
533                 return NULL;
534         }
535
536         m_propname = propertyName;
537         
538         Py_RETURN_NONE;
539 }
540
541 /* 4. setStart:                                                              */
542 const char KX_IpoActuator::SetStart_doc[] = 
543 "setStart(frame)\n"
544 "\t - frame: first frame to use (int)\n"
545 "\tSet the frame from which the ipo starts playing.\n";
546 PyObject* KX_IpoActuator::PySetStart(PyObject* args) {
547
548         ShowDeprecationWarning("setStart()", "the frameStart property");
549
550         float startArg;
551         if(!PyArg_ParseTuple(args, "f:setStart", &startArg)) {
552                 return NULL;            
553         }
554         
555         m_startframe = startArg;
556
557         Py_RETURN_NONE;
558 }
559 /* 5. getStart:                                                              */
560 const char KX_IpoActuator::GetStart_doc[] = 
561 "getStart()\n"
562 "\tReturns the frame from which the ipo starts playing.\n";
563 PyObject* KX_IpoActuator::PyGetStart() {
564         ShowDeprecationWarning("getStart()", "the frameStart property");
565         return PyFloat_FromDouble(m_startframe);
566 }
567
568 /* 6. setEnd:                                                                */
569 const char KX_IpoActuator::SetEnd_doc[] = 
570 "setEnd(frame)\n"
571 "\t - frame: last frame to use (int)\n"
572 "\tSet the frame at which the ipo stops playing.\n";
573 PyObject* KX_IpoActuator::PySetEnd(PyObject* args) {
574         ShowDeprecationWarning("setEnd()", "the frameEnd property");
575         float endArg;
576         if(!PyArg_ParseTuple(args, "f:setEnd", &endArg)) {
577                 return NULL;            
578         }
579         
580         m_endframe = endArg;
581
582         Py_RETURN_NONE;
583 }
584 /* 7. getEnd:                                                                */
585 const char KX_IpoActuator::GetEnd_doc[] = 
586 "getEnd()\n"
587 "\tReturns the frame at which the ipo stops playing.\n";
588 PyObject* KX_IpoActuator::PyGetEnd() {
589         ShowDeprecationWarning("getEnd()", "the frameEnd property");
590         return PyFloat_FromDouble(m_endframe);
591 }
592
593 /* 6. setIpoAsForce:                                                           */
594 const char KX_IpoActuator::SetIpoAsForce_doc[] = 
595 "setIpoAsForce(force?)\n"
596 "\t - force?    : interpret this ipo as a force? (KX_TRUE, KX_FALSE)\n"
597 "\tSet whether to interpret the ipo as a force rather than a displacement.\n";
598 PyObject* KX_IpoActuator::PySetIpoAsForce(PyObject* args) { 
599         ShowDeprecationWarning("setIpoAsForce()", "the useIpoAsForce property");
600         int boolArg;
601         
602         if (!PyArg_ParseTuple(args, "i:setIpoAsForce", &boolArg)) {
603                 return NULL;
604         }
605
606         m_ipo_as_force = PyArgToBool(boolArg);
607         if (m_ipo_as_force)
608                 m_ipo_add = false;
609         
610         Py_RETURN_NONE; 
611 }
612 /* 7. getIpoAsForce:                                                         */
613 const char KX_IpoActuator::GetIpoAsForce_doc[] = 
614 "getIpoAsForce()\n"
615 "\tReturns whether to interpret the ipo as a force rather than a displacement.\n";
616 PyObject* KX_IpoActuator::PyGetIpoAsForce() {
617         ShowDeprecationWarning("getIpoAsForce()", "the useIpoAsForce property");
618         return BoolToPyArg(m_ipo_as_force);
619 }
620
621 /* 6. setIpoAsForce:                                                           */
622 const char KX_IpoActuator::SetIpoAdd_doc[] = 
623 "setIpoAdd(add?)\n"
624 "\t - add?    : add flag (KX_TRUE, KX_FALSE)\n"
625 "\tSet whether to interpret the ipo as additive rather than absolute.\n";
626 PyObject* KX_IpoActuator::PySetIpoAdd(PyObject* args) { 
627         ShowDeprecationWarning("setIpoAdd()", "the useIpoAdd property");
628         int boolArg;
629         
630         if (!PyArg_ParseTuple(args, "i:setIpoAdd", &boolArg)) {
631                 return NULL;
632         }
633
634         m_ipo_add = PyArgToBool(boolArg);
635         if (m_ipo_add)
636                 m_ipo_as_force = false;
637         
638         Py_RETURN_NONE; 
639 }
640 /* 7. getIpoAsForce:                                                         */
641 const char KX_IpoActuator::GetIpoAdd_doc[] = 
642 "getIpoAsAdd()\n"
643 "\tReturns whether to interpret the ipo as additive rather than absolute.\n";
644 PyObject* KX_IpoActuator::PyGetIpoAdd() {
645         ShowDeprecationWarning("getIpoAdd()", "the useIpoAdd property");
646         return BoolToPyArg(m_ipo_add);
647 }
648
649 /* 8. setType:                                                               */
650 const char KX_IpoActuator::SetType_doc[] = 
651 "setType(mode)\n"
652 "\t - mode: Play, PingPong, Flipper, LoopStop, LoopEnd or FromProp (string)\n"
653 "\tSet the operation mode of the actuator.\n";
654 PyObject* KX_IpoActuator::PySetType(PyObject* args) {
655         ShowDeprecationWarning("setType()", "the mode property");
656         int typeArg;
657         
658         if (!PyArg_ParseTuple(args, "i:setType", &typeArg)) {
659                 return NULL;
660         }
661         
662         if ( (typeArg > KX_ACT_IPO_NODEF) 
663                  && (typeArg < KX_ACT_IPO_MAX) ) {
664                 m_type = typeArg;
665         }
666         
667         Py_RETURN_NONE;
668 }
669 /* 9. getType:                                                               */
670 const char KX_IpoActuator::GetType_doc[] = 
671 "getType()\n"
672 "\tReturns the operation mode of the actuator.\n";
673 PyObject* KX_IpoActuator::PyGetType() {
674         ShowDeprecationWarning("getType()", "the mode property");
675         return PyLong_FromSsize_t(m_type);
676 }
677
678 /* 10. setForceIpoActsLocal:                                                 */
679 const char KX_IpoActuator::SetForceIpoActsLocal_doc[] = 
680 "setForceIpoActsLocal(local?)\n"
681 "\t - local?    : Apply the ipo-as-force in the object's local\n"
682 "\t               coordinates? (KX_TRUE, KX_FALSE)\n"
683 "\tSet whether to apply the force in the object's local\n"
684 "\tcoordinates rather than the world global coordinates.\n";
685 PyObject* KX_IpoActuator::PySetForceIpoActsLocal(PyObject* args) { 
686         ShowDeprecationWarning("setForceIpoActsLocal()", "the useIpoLocal property");
687         int boolArg;
688         
689         if (!PyArg_ParseTuple(args, "i:setForceIpoActsLocal", &boolArg)) {
690                 return NULL;
691         }
692
693         m_ipo_local = PyArgToBool(boolArg);
694         
695         Py_RETURN_NONE; 
696 }
697 /* 11. getForceIpoActsLocal:                                                */
698 const char KX_IpoActuator::GetForceIpoActsLocal_doc[] = 
699 "getForceIpoActsLocal()\n"
700 "\tReturn whether to apply the force in the object's local\n"
701 "\tcoordinates rather than the world global coordinates.\n";
702 PyObject* KX_IpoActuator::PyGetForceIpoActsLocal() {
703         ShowDeprecationWarning("getForceIpoActsLocal()", "the useIpoLocal property");
704         return BoolToPyArg(m_ipo_local);
705 }
706
707
708 /* eof */