Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/branches/single_player_map/src/world_entities/npcs/generic_npc.cc @ 8825

Last change on this file since 8825 was 8825, checked in by patrick, 18 years ago

npc walking corrections

File size: 11.4 KB
Line 
1
2
3/*
4   orxonox - the future of 3D-vertical-scrollers
5
6   Copyright (C) 2004 orx
7
8   This program is free software; you can redistribute it and/or modify
9   it under the terms of the GNU General Public License as published by
10   the Free Software Foundation; either version 2, or (at your option)
11   any later version.
12
13   ### File Specific
14   main-programmer: Patrick Boenzli
15   co-programmer:
16*/
17#define DEBUG_SPECIAL_MODULE DEBUG_MODULE_WORLD_ENTITY
18
19
20#include "util/loading/factory.h"
21#include "util/loading/load_param.h"
22
23#include "interactive_model.h"
24#include "md2/md2Model.h"
25
26#include "sound_buffer.h"
27
28#include "loading/resource_manager.h"
29
30#include "generic_npc.h"
31
32#include "animation/animation3d.h"
33
34using namespace std;
35
36
37
38CREATE_FACTORY(GenericNPC, CL_GENERIC_NPC);
39
40#include "script_class.h"
41CREATE_SCRIPTABLE_CLASS(GenericNPC, CL_GENERIC_NPC,
42                        //addMethod("walkTo", ExecutorLua7ret<GenericNPC,float, float, float, float, float, float, float, float>(&GenericNPC::walkTo))
43                        addMethod("walkTo", ExecutorLua3ret<GenericNPC,float,float,float,float>(&GenericNPC::walkTo))
44                        ->addMethod("setTime", ExecutorLua1<GenericNPC,float>(&GenericNPC::setTime))
45                       );
46
47
48
49/**
50 * constructor
51 */
52GenericNPC::GenericNPC(const TiXmlElement* root)
53  : NPC(root)
54{
55  this->init();
56
57  if (root != NULL)
58    this->loadParams(root);
59}
60
61
62GenericNPC::GenericNPC()
63  : NPC(NULL)
64{
65
66}
67
68/**
69 * deconstructor
70 */
71GenericNPC::~GenericNPC ()
72{
73  if( this->currentAnim != NULL)
74    delete this->currentAnim;
75}
76
77
78/**
79 * initializing the npc enity
80 */
81void GenericNPC::init()
82{
83  this->setClassID(CL_GENERIC_NPC, "GenericNPC");
84  this->toList(OM_GROUP_00);
85
86  if (this->soundBuffer != NULL)
87    ResourceManager::getInstance()->unload(this->soundBuffer);
88  this->soundBuffer = (OrxSound::SoundBuffer*)ResourceManager::getInstance()->load("sound/rain.wav", WAV);
89
90  time = 30.0f;
91  // collision reaction registration
92//   this->subscribeReaction(CREngine::CR_PHYSICS_GROUND_WALK, CL_BSP_ENTITY);
93}
94
95
96/**
97 * loads the Settings of a MD2Creature from an XML-element.
98 * @param root the XML-element to load the MD2Creature's properties from
99 */
100void GenericNPC::loadParams(const TiXmlElement* root)
101{
102  NPC::loadParams(root);
103
104}
105
106
107/**
108 * sets the animation of this npc
109 * @param anumationIndex: the animation index
110 * @param anumPlaybackMode: the playback mode
111 */
112void GenericNPC::setAnimation(int animationIndex, int animPlaybackMode)
113{
114  if( likely(this->getModel(0) != NULL))
115    ((InteractiveModel*)this->getModel(0))->setAnimation(animationIndex, animPlaybackMode);
116}
117
118
119/**
120 * sets the animation of this npc
121 * @param anumationIndex: the animation index
122 * @param anumPlaybackMode: the playback mode
123 */
124void GenericNPC::playAnimation(int animationIndex, int animPlaybackMode)
125{
126  if( likely(this->getModel(0) != NULL))
127    ((InteractiveModel*)this->getModel(0))->setAnimation(animationIndex, animPlaybackMode);
128
129}
130
131
132/**
133 * play a sound
134 * @param filename: name of the file
135 */
136void GenericNPC::playSound(std::string filename)
137{
138
139}
140
141
142/**
143 * walt to
144 * @param coordinate: coordinate to go to
145 */
146float GenericNPC::walkTo(float x, float y, float z, float qu, float qx, float qy, float qz)
147{
148  Vector destCoor = Vector(x, y, z);
149  Quaternion destDir = Quaternion(Vector(qx, qy, qz), qu);
150
151  // check if this is the current goal
152  if( this->destCoor != destCoor || this->destDir != destDir)
153  {
154    this->destCoor = destCoor;
155    this->destDir = destDir;
156
157    float time = 100.0f;
158
159    if( this->currentAnim != NULL)
160      delete this->currentAnim;
161
162    this->currentAnim = new Animation3D(this);
163    this->currentAnim->addKeyFrame(this->getAbsCoor(), this->getAbsDir(), time, ANIM_LINEAR, ANIM_LINEAR);
164    this->currentAnim->addKeyFrame(this->destCoor, this->destDir, time, ANIM_LINEAR, ANIM_LINEAR);
165
166
167    this->currentAnim->setInfinity(ANIM_INF_CONSTANT);
168    this->currentAnim->play();
169
170    this->setAnimation(RUN, MD2_ANIM_LOOP);
171  }
172
173  // calculate the distance
174  Vector distance = this->getAbsCoor() - this->destCoor;
175  return distance.len();
176}
177
178
179/**
180 * walk to a specific place with direction
181 *
182 * @param x: x coordinate to go to
183 * @param y: y coordinate to go to
184 * @param z: z coordinate to go to
185 *
186 * without turning itself
187 */
188float GenericNPC::walkTo(float x, float y, float z)
189{
190  Quaternion q = this->getAbsDir();
191
192  //printf("%s moving to %f, %f, %f \n",this->getName(),x,y,z);
193
194  return this->walkTo(x, y, z, q.w, q.v.x, q.v.y, q.v.z);
195}
196
197/**
198 * walk to a specific place with direction
199 *
200 * @param x: x coordinate to go to
201 * @param y: y coordinate to go to
202 * @param qu: angle to rotate
203 * @param qx: x coordinate of rotation vector
204 * @param qy: y coordinate of rotation vector
205 * @param qz: z coordinate of rotation vector
206 *
207 */
208float GenericNPC::walkTo(float x, float y, float qu, float qx, float qy, float qz)
209{
210  return this->walkTo(x, y, 0.0f, qu, qx, qy, qz);
211}
212
213
214/**
215 * walk to a specific place with direction
216 *
217 * @param coor: vector place
218 * @param dir: direction
219 *
220 */
221float GenericNPC::walkTo(const Vector& coor, const Quaternion& dir)
222{
223  return this->walkTo(coor.x, coor.y, coor.z, dir.w, dir.v.x, dir.v.y, dir.v.z);
224}
225
226
227
228/**
229 * run to a specific place with direction
230 *
231 * @param x: x coordinate to go to
232 * @param y: y coordinate to go to
233 * @param z: z coordinate to go to
234 * @param qu: angle to rotate
235 * @param qx: x coordinate of rotation vector
236 * @param qy: y coordinate of rotation vector
237 * @param qz: z coordinate of rotation vector
238 *
239 */
240float GenericNPC::runTo(float x, float y, float z, float qu, float qx, float qy, float qz)
241{
242  Vector destCoor = Vector(x, y, z);
243  Quaternion destDir = Quaternion(Vector(qx, qy, qz), qu);
244
245  // check if this is the current goal
246  if( this->destCoor != destCoor || this->destDir != destDir)
247  {
248    this->destCoor = destCoor;
249    this->destDir = destDir;
250
251    float time = 5.0f;
252
253    if( this->currentAnim != NULL)
254      delete this->currentAnim;
255
256    this->currentAnim = new Animation3D(this);
257    this->currentAnim->addKeyFrame(this->getAbsCoor(), this->getAbsDir(), time, ANIM_LINEAR, ANIM_LINEAR);
258    this->currentAnim->addKeyFrame(this->destCoor, this->destDir, time, ANIM_LINEAR, ANIM_LINEAR);
259
260
261    this->currentAnim->setInfinity(ANIM_INF_CONSTANT);
262    this->currentAnim->play();
263
264    this->setAnimation(RUN, MD2_ANIM_LOOP);
265  }
266
267  // calculate the distance
268  Vector distance = this->getAbsCoor() - this->destCoor;
269  return distance.len();
270}
271
272
273/**
274 * run to a specific place with direction
275 *
276 * @param x: x coordinate to go to
277 * @param y: y coordinate to go to
278 * @param qu: angle to rotate
279 * @param qx: x coordinate of rotation vector
280 * @param qy: y coordinate of rotation vector
281 * @param qz: z coordinate of rotation vector
282 *
283 */
284float GenericNPC::runTo(float x, float y, float qu, float qx, float qy, float qz)
285{
286  this->runTo(x, y, 0.0f, qu, qx, qy, qz);
287}
288
289
290/**
291 * run to a specific place with direction
292 *
293 * @param coor: vector place
294 * @param dir: direction
295 *
296 */
297float GenericNPC::runTo(const Vector& coordinate, const Quaternion& dir)
298{
299  this->runTo(coordinate.x, coordinate.y, coordinate.z, dir.w, dir.v.x, dir.v.y, dir.v.z);
300}
301
302
303/**
304 * crouch to a specific place with direction
305 *
306 * @param x: x coordinate to go to
307 * @param y: y coordinate to go to
308 * @param z: z coordinate to go to
309 * @param qu: angle to rotate
310 * @param qx: x coordinate of rotation vector
311 * @param qy: y coordinate of rotation vector
312 * @param qz: z coordinate of rotation vector
313 *
314 */
315float GenericNPC::crouchTo(float x, float y, float z, float qu, float qx, float qy, float qz)
316{
317  Vector destCoor = Vector(x, y, z);
318  Quaternion destDir = Quaternion(Vector(qx, qy, qz), qu);
319
320  // check if this is the current goal
321  if( this->destCoor != destCoor || this->destDir != destDir)
322  {
323    this->destCoor = destCoor;
324    this->destDir = destDir;
325
326
327    if( this->currentAnim != NULL)
328      delete this->currentAnim;
329
330    this->currentAnim = new Animation3D(this);
331    this->currentAnim->addKeyFrame(this->getAbsCoor(), this->getAbsDir(), time, ANIM_LINEAR, ANIM_LINEAR);
332    this->currentAnim->addKeyFrame(this->destCoor, this->destDir, time, ANIM_LINEAR, ANIM_LINEAR);
333
334
335    this->currentAnim->setInfinity(ANIM_INF_CONSTANT);
336    this->currentAnim->play();
337
338    this->setAnimation(CROUCH_WALK, MD2_ANIM_LOOP);
339  }
340
341  // calculate the distance
342  Vector distance = this->getAbsCoor() - this->destCoor;
343  return distance.len();
344}
345
346
347/**
348 * couch to a specific place with direction
349 *
350 * @param x: x coordinate to go to
351 * @param y: y coordinate to go to
352 * @param qu: angle to rotate
353 * @param qx: x coordinate of rotation vector
354 * @param qy: y coordinate of rotation vector
355 * @param qz: z coordinate of rotation vector
356 *
357 */
358float GenericNPC::crouchTo(float x, float y, float qu, float qx, float qy, float qz)
359{
360  this->crouchTo(x, y, 0.0f, qu, qx, qy, qz);
361}
362
363
364
365/**
366 * crouch to a specific place with direction
367 *
368 * @param coor: vector place
369 * @param dir: direction
370 *
371 */
372float GenericNPC::crouchTo(const Vector& coordinate, const Quaternion& dir)
373{
374  this->crouchTo(coordinate.x, coordinate.y, coordinate.z, dir.w, dir.v.x, dir.v.y, dir.v.z);
375}
376
377
378/**
379 * stops the generic animation
380 */
381void GenericNPC::stop()
382{
383  if( this->currentAnim != NULL)
384  {
385    this->currentAnim->stop();
386    delete this->currentAnim;
387    this->currentAnim = NULL;
388
389    this->setAnimation(STAND, MD2_ANIM_LOOP);
390  }
391}
392
393
394/**
395 * lookat a world entity
396 * @param worldEntity: the worldentity to look at
397 */
398float GenericNPC::lookAt(WorldEntity* worldEntity)
399{}
400
401
402/**
403 * turns to a given direction
404 */
405bool GenericNPC::turnTo(float qu, float qx, float qy, float qz)
406{
407  Quaternion destDir = Quaternion(Vector(qx, qy, qz), qu);
408
409  // check if this is the current goal
410  if( this->destDir != destDir)
411  {
412    this->destCoor = destCoor;
413
414    float time = 5.0f;
415
416    if( this->currentAnim != NULL)
417      delete this->currentAnim;
418
419    this->currentAnim = new Animation3D(this);
420    this->currentAnim->addKeyFrame(this->getAbsCoor(), this->getAbsDir(), time, ANIM_LINEAR, ANIM_LINEAR);
421    this->currentAnim->addKeyFrame(this->getAbsCoor(), this->destDir, time, ANIM_LINEAR, ANIM_LINEAR);
422
423    this->currentAnim->setInfinity(ANIM_INF_CONSTANT);
424    this->currentAnim->play();
425
426    this->setAnimation(STAND, MD2_ANIM_LOOP);
427  }
428
429  // calculate the distance
430  Vector distance = this->getAbsCoor() - this->destCoor;
431  return distance.len();
432}
433
434
435
436/**
437 * talk to a world entity and play a sound/music/voice
438 * @param worldEntity: entity
439 * @param dialogNr: sound nr to be played (from the xml load tags)
440 */
441float GenericNPC::talkTo(WorldEntity* worldEntity, int dialogNr)
442{}
443
444
445/**
446 * world entity to shoot at if there is any weapon on the npc
447 * @param entity: entity to shoot entity
448 */
449void GenericNPC::shootAt(WorldEntity* entity)
450{}
451
452
453
454
455
456
457
458
459
460
461/**
462 * tick this world entity
463 * @param time: time in seconds expirded since the last tick
464 */
465void GenericNPC::tick (float time)
466{
467  if( likely(this->getModel(0) != NULL))
468    ((InteractiveModel*)this->getModel(0))->tick(time);
469
470  // tick this animation
471  if( this->currentAnim != NULL)
472    this->currentAnim->tick(time);
473}
474
475
476
477void GenericNPC::destroy()
478{
479  int randi = (int)(5.0f * (float)rand()/(float)RAND_MAX);
480
481  if( randi == 1)
482    this->setAnimation(DEATH_FALLBACK, MD2_ANIM_ONCE);
483  else if( randi == 2)
484    this->setAnimation(DEATH_FALLFORWARD, MD2_ANIM_ONCE);
485  else if( randi == 3)
486    this->setAnimation(DEATH_FALLBACKSLOW, MD2_ANIM_ONCE);
487  else if( randi == 4)
488    this->setAnimation(CROUCH_DEATH, MD2_ANIM_ONCE);
489  else
490    this->setAnimation(DEATH_FALLBACK, MD2_ANIM_ONCE);
491}
492
Note: See TracBrowser for help on using the repository browser.