source: GTP/trunk/App/Demos/Illum/Ogre/src/Common/src/FPSPlayer.cpp @ 2411

Revision 2411, 16.6 KB checked in by szirmay, 17 years ago (diff)
Line 
1#include "fpsplayer.h"
2
3FPSPlayer* FPSPlayer::thePlayer = NULL;
4unsigned int PlayerCharacter::frameListenerPriority = 1;
5
6class MyTrigger : public Trigger
7{
8public:
9        MyTrigger(const NxString& meshIdentifier, Scene* scene, ShapeDescription* shape, const NxOgre::Pose& pose, ActorParams params = ""):
10          Trigger(meshIdentifier, scene, shape, pose, params)
11          {
12          }
13
14         void onEnter(Actor* a)
15         {
16                int ize = 0;
17         }
18};
19
20class MyCharMoveController : public CharacterMovementVectorController
21{
22public:
23        MyCharMoveController(float speed = 1.5){movespeed = speed;}
24        float movespeed;
25        void move(NxVec3 &out, NxVec3 &moveVector, NxQuat &direction, NxVec3 &g, float t, Character*)
26        {
27                NxVec3 dir = direction.rot(moveVector);
28                out = ((dir * movespeed) + g) * t;             
29        }
30};
31
32PlayerCharacter::PlayerCharacter(String name, Scene* scene, SceneManager* sceneManager, Vector3 dimensions, Vector3 startPosition, bool debug)
33{
34        mName = name;
35        mPlayerDimensions = dimensions;
36        mDebug = debug;
37        mSceneManager = sceneManager;
38        mScene = scene;
39        CharacterParams cp;
40        cp.setToDefault();
41        cp.mDimensions = NxVec3(dimensions.x, dimensions.y, dimensions.z);
42        cp.mType = CharacterParams::CT_Box;
43        mPlayerCharacter = mScene->createCharacter(mName, startPosition, cp);
44        mPlayerCharacter->createNode();
45        mPlayerNode = mPlayerCharacter->getNode();
46       
47        mCharacterController = 0;
48        mCharacterController = new MyCharMoveController(2.0);
49        mPlayerCharacter->setMovementVectorController(mCharacterController);
50
51        if(mDebug)
52        {
53                mPlayerBoundDebugNode = mPlayerNode->createChildSceneNode(mName + "_BoundDebugNode");
54                mPlayerBoundDebugNode->setScale(dimensions);
55                mPlayerBoundDebugNode->attachObject(mSceneManager->createEntity(mName + "_BoundDebug", "cube.mesh"));
56        }
57
58        mCharacterMesh_AnimState = 0;
59        mForceAnimChange = false;
60        mWeapon = 0;
61        mWeaponBound = 0;
62        mWeaponBoundDebugNode = 0;
63        mCharacterMeshEntity = 0;
64        mWeaponEntity = 0;
65        mWeaponAttachBone = 0;
66    mWeaponNode = 0;
67        mWeaponBoundNode = 0;
68        mWeaponBoundDebugNode = 0;
69        mPlayerBoundDebugNode = 0;
70        mWeaponBound = 0;
71        mWeaponNode2 = 0;
72               
73        this->setPriority(frameListenerPriority++);
74        Root::getSingleton().addFrameListener(this);
75
76        //mPlayerCharacter->setCharacterCollisionGroup(NX_CHARACTER_COL_GROUP_CHARACTER);
77        //mScene->getNxScene()->setGroupCollisionFlag(NX_CHARACTER_COL_GROUP_CHARACTER, NX_CHARACTER_COL_GROUP_NON_COLLIDABLE,false);
78}
79
80FPSPlayer::FPSPlayer(Scene* scene, SceneManager* sceneManager, Vector3 dimensions, Vector3 startPosition, float cameraHeight, Camera* cam, bool debug)
81: PlayerCharacter("FPSPlayerCharacter", scene, sceneManager, dimensions, startPosition, debug)
82{
83        mCameraHeight = cameraHeight - dimensions.y / 2.0;
84        mCamera = cam;
85        mPlayerNode->attachObject(cam);
86       
87        thePlayer = this;
88}
89
90FPSPlayer::~FPSPlayer(void)
91{
92}
93
94void PlayerCharacter::addPlayerMesh(String meshname, float meshscale, bool rotateModel)
95{
96        mCharacterMeshEntity = mSceneManager->createEntity(mName, meshname);
97        mCharacterMeshEntity->setCastShadows(true);
98        mMeshScale = meshscale;
99        mCurrentAnimState = PLAYERANIMSTATE_STAND;
100        mCharacterMesh_AnimState = mCharacterMeshEntity->getAnimationState(getAnimStateName(PLAYERANIMSTATE_STAND));
101        mCharacterMesh_AnimState->setEnabled(true);
102        mCharacterMesh_AnimState->setLoop(true);
103        SceneNode* meshNode = mPlayerNode->createChildSceneNode(mName + "_MeshNode");
104        meshNode->attachObject(mCharacterMeshEntity);
105        meshNode->setPosition(0 ,-mPlayerDimensions.y / 2.0, 0);
106        meshNode->setScale(meshscale, meshscale, meshscale);
107        if(rotateModel)
108        meshNode->rotate(Vector3::UNIT_Y, Degree(180.0));
109        meshNode->_updateBounds();
110}
111
112void FPSPlayer::addPlayerMesh(String meshname, float meshscale, bool rotateModel)
113{
114        mCharacterMeshEntity = mSceneManager->createEntity(mName, meshname);
115        mCharacterMeshEntity->setCastShadows(true);
116        mMeshScale = meshscale;
117        mCurrentAnimState = PLAYERANIMSTATE_STAND;
118        mCharacterMesh_AnimState = mCharacterMeshEntity->getAnimationState(getAnimStateName(PLAYERANIMSTATE_STAND));
119        mCharacterMesh_AnimState->setEnabled(true);
120        mCharacterMesh_AnimState->setLoop(true);
121        SceneNode* FPSArmNode = mPlayerNode->createChildSceneNode(mName+"_ArmNode");
122        FPSArmNode->attachObject(mCharacterMeshEntity);
123        FPSArmNode->setPosition(0,mCameraHeight,0);
124        FPSArmNode->setScale(meshscale, meshscale, meshscale);
125        if(rotateModel)
126        FPSArmNode->rotate(Vector3::UNIT_Y, Degree(180.0));
127}
128
129void PlayerCharacter::addWeaponModel(String meshname, String attachBoneName)
130{
131       
132        mWeaponEntity = mSceneManager->createEntity(mName + "_Weapon", meshname);
133        mWeaponAttachBone = mCharacterMeshEntity->getSkeleton()->getBone(attachBoneName);
134        mWeaponNode = mCharacterMeshEntity->getParentSceneNode()->createChildSceneNode(mName + "_WeaponNode"); 
135        mWeaponNode->attachObject(mWeaponEntity);
136
137        AxisAlignedBox bb = mWeaponEntity->getBoundingBox();
138
139        Vector3 max = bb.getMaximum();
140        //max.z *= 2.0;
141        Vector3 min = bb.getMinimum();
142        Vector3 center = (min + max) / 2.0;
143        //center.z = max.z;
144
145        mWeaponBoundNode = mWeaponNode->createChildSceneNode(mName + "_WeaponBoundNode");
146        mWeaponBoundNode->setPosition(center);
147/*
148        SceneNode* ArmNode2 = mPlayerNode->createChildSceneNode();
149        ArmNode2->setPosition(0,mCameraHeight , -mPlayerDimensions.z);
150        ArmNode2->rotate(Vector3::UNIT_Y, Degree(180.0));
151        mWeaponNode2 = ArmNode2->createChildSceneNode();
152        mWeaponBoundNode = mWeaponNode2->createChildSceneNode();
153        mWeaponBoundNode->setPosition(center * mMeshScale );
154*/     
155
156        max *= mMeshScale;
157        min *= mMeshScale;
158        float dimX = max.x-min.x;
159        float dimY = max.y-min.y;
160        float dimZ = max.z-min.z;
161        Vector3 dim(dimX, dimY, dimZ);
162
163        mWeaponBound = new MyTrigger(mName + "_WeaponTrigger", mScene, new CubeShape(dimX, dimY, dimZ, "trigger: yes"), Vector3(0,0,0), "mass: 0, density: 0");
164        mScene->addTrigger((Trigger*)mWeaponBound);
165               
166        if(mDebug)
167        {
168                mWeaponBoundDebugNode = mSceneManager->getRootSceneNode()->createChildSceneNode(mName+"_WeaponBoundDebugNode");
169                mWeaponBoundDebugNode->setScale(dim);
170                mWeaponBoundDebugNode->attachObject(mSceneManager->createEntity(mName+"_WeaponBoundDebug", "cube.mesh"));
171        }
172
173        //mWeaponBound->setCharacterCollisionGroup(NX_CHARACTER_COL_GROUP_NON_COLLIDABLE);     
174}
175
176void FPSPlayer::addWeaponModel(String meshname, String attachBoneName)
177{
178       
179        mWeaponEntity = mSceneManager->createEntity(mName + "_Weapon", meshname);
180        mWeaponAttachBone = mCharacterMeshEntity->getSkeleton()->getBone(attachBoneName);
181        mWeaponNode = mCharacterMeshEntity->getParentSceneNode()->createChildSceneNode(mName+"_WeaponNode");   
182        mWeaponNode->attachObject(mWeaponEntity);
183
184        AxisAlignedBox bb = mWeaponEntity->getBoundingBox();
185
186        Vector3 max = bb.getMaximum();
187        //max.z *= 2.0;
188        Vector3 min = bb.getMinimum();
189        Vector3 center = (min + max) / 2.0;
190        //center.z = max.z;
191
192        //mWeaponBoundNode = mWeaponNode->createChildSceneNode();
193        //mWeaponBoundNode->setPosition(center);
194
195        SceneNode* ArmNode2 = mPlayerNode->createChildSceneNode(mName+"_ArmNode2");
196        ArmNode2->setPosition(0,mCameraHeight , -mPlayerDimensions.z);
197        ArmNode2->rotate(Vector3::UNIT_Y, Degree(180.0));
198        mWeaponNode2 = ArmNode2->createChildSceneNode();
199        mWeaponBoundNode = mWeaponNode2->createChildSceneNode(mName+"_WeaponBoundNode");
200        mWeaponBoundNode->setPosition(center * mMeshScale );
201       
202
203        max *= mMeshScale;
204        min *= mMeshScale;
205        float dimX = max.x-min.x;
206        float dimY = max.y-min.y;
207        dimY *=3;
208        float dimZ = max.z-min.z;
209        Vector3 dim(dimX, dimY, dimZ);
210
211//      mWeaponBound = mScene->createActor("FPSPlayerWeapon", new CubeShape(dimX, dimY, dimZ), Vector3(0,0,0), "kinematic: yes, mass: 10");
212        mWeaponBound = new MyTrigger(mName + "_WeaponTrigger", mScene, new CubeShape(dimX, dimY, dimZ, "trigger: yes"), Vector3(0,0,0), "mass: 0, density: 0");
213        mScene->addTrigger((Trigger*)mWeaponBound);
214       
215        if(mDebug)
216        {
217                mWeaponBoundDebugNode = mSceneManager->getRootSceneNode()->createChildSceneNode(mName+"_WeaponBoundDebugNode");
218                mWeaponBoundDebugNode->setScale(dim);
219                mWeaponBoundDebugNode->attachObject(mSceneManager->createEntity(mName+"_WeaponBoundDebug", "cube.mesh"));
220        }
221
222        mWeaponBound->setCharacterCollisionGroup(NX_CHARACTER_COL_GROUP_NON_COLLIDABLE);       
223}
224
225void PlayerCharacter::doAction(float dt)
226{
227        FPSPlayer* thePlayer = FPSPlayer::getPlayer();
228
229        if(thePlayer)
230        {
231                Vector3 playerPos = thePlayer->getPosition();
232                Vector3 myPos = mPlayerNode->getWorldPosition();
233                Vector3 dir = playerPos - myPos;
234                dir.y = 0;
235                //if( dir.length() > 1.0)
236                //{
237                        dir.normalise();
238                        Vector3 right = -dir.crossProduct(Vector3::UNIT_Y);
239                        Quaternion q;                   
240                        q.FromAxes(right,Vector3::UNIT_Y,dir);
241                        mPlayerCharacter->setDirection(q);
242                        if(mCharacterController )
243                        ((MyCharMoveController*)mCharacterController)->movespeed = 1.5;
244                        mPlayerCharacter->addMovement(Character::DR_StepRight);
245                //}
246
247        }
248        if(mCharacterMeshEntity)
249        setAnimState(PLAYERANIMSTATE_WALK);
250}
251
252bool PlayerCharacter::frameStarted(const FrameEvent& evt)
253{
254//      LogManager::getSingleton().logMessage("CHARACTERPLAYER_FRAMESTARTED");
255        doAction(evt.timeSinceLastFrame);
256
257        float dt = evt.timeSinceLastFrame;
258               
259        if(mCharacterMesh_AnimState)
260        {
261                float animspeed = 1.2;
262                if(mCurrentAnimState == PLAYERANIMSTATE_WALK && !mRunning)
263                        animspeed /= 2;
264
265                mCharacterMesh_AnimState->addTime(dt*animspeed);       
266        }
267
268        return true;
269}
270
271void FPSPlayer::processKeyInputs(InputReader* inputDevice)
272{               
273                mMoving = false;
274                if (inputDevice->isKeyDown(KC_W))
275                {
276                        mPlayerCharacter->addMovement(Character::DR_StepLeft);
277                        mMoving = true;
278                }       
279                if (inputDevice->isKeyDown(KC_S))
280                {
281                        mPlayerCharacter->addMovement(Character::DR_StepRight);
282                        mMoving = true;
283                }
284                if (inputDevice->isKeyDown(KC_A))
285                {
286                        mPlayerCharacter->addMovement(Character::DR_Forward);
287                        mMoving = true;
288                }
289                if (inputDevice->isKeyDown(KC_D))
290                {
291                        mPlayerCharacter->addMovement(Character::DR_Backward);
292                        mMoving = true;
293                }
294
295                if (inputDevice->isKeyDown(KC_1))
296                {
297                        mWeapon = 0;
298                        mForceAnimChange = true;
299                }
300                if (inputDevice->isKeyDown(KC_2))
301                {
302                        mWeapon = 1;
303                        mForceAnimChange = true;
304                }
305
306                if (inputDevice->isKeyDown(KC_LSHIFT))
307                {
308                        if(mCharacterController)
309                        ((MyCharMoveController*)mCharacterController)->movespeed = 4.0;
310                        mRunning = true;
311                }
312                else
313                {
314                        if(mCharacterController)
315                        ((MyCharMoveController*)mCharacterController)->movespeed = 2.0;
316                        mRunning = false;
317                }
318}
319
320void FPSPlayer::processMouseInputs(InputReader* inputDevice)
321{
322        if( inputDevice->getMouseButton( 0 ) )//attack
323                setAnimState(PLAYERANIMSTATE_ATTACK);
324               
325        else if( inputDevice->getMouseButton( 1 ) )//block
326                setAnimState(PLAYERANIMSTATE_BLOCK);
327
328        Quaternion q;
329        q.FromAngleAxis( Radian(Degree(-inputDevice->getMouseRelX() * 0.13)), Vector3::UNIT_Y );
330        q = mPlayerCharacter->getGlobalOrientation() * q;
331        mPlayerCharacter->setDirection(q);
332
333        mCamera->pitch(Radian(Degree(-inputDevice->getMouseRelY() * 0.13)));           
334}
335
336bool FPSPlayer::frameStarted(const FrameEvent& evt)
337{
338//      LogManager::getSingleton().logMessage("FPSPLAYER_FRAMESTARTED");
339
340        float dt = evt.timeSinceLastFrame;
341               
342        if(mCharacterMesh_AnimState)
343        {
344                float animspeed = 1.2;
345                if(mCurrentAnimState == PLAYERANIMSTATE_WALK && !mRunning)
346                        animspeed /= 2;
347
348                mCharacterMesh_AnimState->addTime(dt*animspeed);       
349        }
350
351        static float moveTime=0;
352       
353        float movecameraup = 0;
354        if(mDebug)movecameraup = 1.0;
355
356        if(mMoving)
357        {
358                setAnimState(PLAYERANIMSTATE_WALK);
359
360                moveTime += dt;
361                mCamera->setPosition(Vector3(0,mCameraHeight + movecameraup,0) + Vector3(0,0.009 * pow(sin(moveTime*5.0), 2),0));
362        }
363        else
364        {
365                if(Math::UnitRandom() > 0.98)
366                        setAnimState(PLAYERANIMSTATE_IDLE);
367                else
368                        setAnimState(PLAYERANIMSTATE_STAND);
369
370                moveTime = 0;
371                mCamera->setPosition(Vector3(0,mCameraHeight + movecameraup,0));
372        }
373
374        if(mCharacterMeshEntity)
375        this->mCharacterMeshEntity->_updateAnimation();
376
377        if(mWeaponEntity)
378        {
379                mWeaponNode->setPosition(mWeaponAttachBone->getWorldPosition());
380                mWeaponNode->setOrientation(mWeaponAttachBone->getWorldOrientation());
381
382                mWeaponNode2->setPosition(mWeaponAttachBone->getWorldPosition() * mMeshScale);
383                mWeaponNode2->setOrientation(mWeaponAttachBone->getWorldOrientation());
384
385                Vector3 translation = mWeaponBoundNode->getWorldPosition();
386                Quaternion orientation = mWeaponBoundNode->getWorldOrientation();
387               
388                mWeaponBound->setGlobalOrientation(orientation);               
389                mWeaponBound->setGlobalPosition(translation);
390
391                //mWeaponBound->setGlobalPosition(translation);         
392                //mWeaponBound->setGlobalOrientation(orientation);
393
394                if(mDebug)
395                {
396                        mWeaponBoundDebugNode->setPosition(translation);
397                        mWeaponBoundDebugNode->setOrientation(orientation);
398                }
399        }
400
401        return true;
402}
403
404String FPSPlayer::getAnimStateName(PlayerAnimState as, int option)
405{
406        switch (as)
407        {
408                case PLAYERANIMSTATE_IDLE:
409                {
410                        if(mWeapon < 1)
411                                return "sword_idle";
412                        else
413                                return "magic_idle";
414                }
415                case PLAYERANIMSTATE_STAND:
416                {
417                        if(mWeapon < 1)
418                                return "sword_stand";
419                        else
420                                return "magic_stand";
421                }
422                case PLAYERANIMSTATE_BLOCK:
423                {
424                                return "block";                 
425                }
426                case PLAYERANIMSTATE_WALK:
427                {
428                                return "walk";                 
429                }
430                case PLAYERANIMSTATE_ATTACK:
431                {
432                        if(option)
433                        {
434                                if(mWeapon < 1)
435                                        return "attack1";
436                                else
437                                        return "magic_attack";
438                        }
439                        else
440                        {
441                                if(mWeapon < 1)
442                                        return "attack2";
443                                else
444                                        return "magic_attack";
445                        }
446                }
447        }
448        return "";
449}
450
451void FPSPlayer::setAnimState(PlayerAnimState as)
452{
453        if(!mCharacterMeshEntity)
454                return;
455
456        switch(as)     
457        {
458                case PLAYERANIMSTATE_STAND:
459                {
460                        if(mCurrentAnimState != PLAYERANIMSTATE_STAND || mForceAnimChange)
461                        {
462                                //wait until anim finishes
463                                if(mCharacterMesh_AnimState->getTimePosition() >=
464                                        mCharacterMesh_AnimState->getLength() || mCharacterMesh_AnimState->getLoop())
465                                {
466                                        mCurrentAnimState = PLAYERANIMSTATE_STAND;
467                                        mCharacterMesh_AnimState->setEnabled(false);
468                                        mCharacterMesh_AnimState = mCharacterMeshEntity->getAnimationState(getAnimStateName(PLAYERANIMSTATE_STAND));
469                                        mCharacterMesh_AnimState->setLoop(true);
470                                        mCharacterMesh_AnimState->setEnabled(true);
471                                }
472                        }
473                        break;
474                }
475                case PLAYERANIMSTATE_IDLE:
476                {
477                        if(mCurrentAnimState != PLAYERANIMSTATE_IDLE || mForceAnimChange)
478                        {
479                                //wait until anim finishes
480                                if(mCharacterMesh_AnimState->getTimePosition() >=
481                                        mCharacterMesh_AnimState->getLength() || mCharacterMesh_AnimState->getLoop() || mCurrentAnimState == PLAYERANIMSTATE_IDLE)
482                                {
483                                        mCurrentAnimState = PLAYERANIMSTATE_IDLE;
484                                        mCharacterMesh_AnimState->setEnabled(false);
485                                        mCharacterMesh_AnimState = mCharacterMeshEntity->getAnimationState(getAnimStateName(PLAYERANIMSTATE_IDLE));
486                                        mCharacterMesh_AnimState->setTimePosition(0);
487                                        mCharacterMesh_AnimState->setLoop(false);
488                                        mCharacterMesh_AnimState->setEnabled(true);
489                                }
490                        }
491                        break;
492                }
493                case PLAYERANIMSTATE_WALK:
494                {
495                        if(mCurrentAnimState != PLAYERANIMSTATE_WALK)
496                        {
497                                if(mCurrentAnimState == PLAYERANIMSTATE_IDLE || mCurrentAnimState == PLAYERANIMSTATE_STAND)
498                                {
499                                        mCurrentAnimState = PLAYERANIMSTATE_WALK;
500                                        mCharacterMesh_AnimState->setEnabled(false);
501                                        mCharacterMesh_AnimState = mCharacterMeshEntity->getAnimationState(getAnimStateName(PLAYERANIMSTATE_WALK));
502                                        mCharacterMesh_AnimState->setLoop(true);
503                                        mCharacterMesh_AnimState->setEnabled(true);
504                                }
505                        }
506                        break;
507                }
508                case PLAYERANIMSTATE_ATTACK:
509                {
510                        if(mCharacterMesh_AnimState->getTimePosition() >=
511                                        mCharacterMesh_AnimState->getLength() || mCharacterMesh_AnimState->getLoop() || mCurrentAnimState == PLAYERANIMSTATE_IDLE)
512                        {
513                            int attackType = 0;
514                                if(Math::UnitRandom() > 0.5)
515                                         attackType = 1;
516
517                                mCurrentAnimState = PLAYERANIMSTATE_ATTACK;
518                                mCharacterMesh_AnimState->setEnabled(false);
519                                mCharacterMesh_AnimState = mCharacterMeshEntity->getAnimationState(getAnimStateName(PLAYERANIMSTATE_ATTACK, attackType));
520                                mCharacterMesh_AnimState->setTimePosition(0);
521                                mCharacterMesh_AnimState->setLoop(false);
522                                mCharacterMesh_AnimState->setEnabled(true);
523                        }
524                        break;
525                }               
526                case PLAYERANIMSTATE_BLOCK:
527                {
528                        if(mCharacterMesh_AnimState->getTimePosition() >=
529                                        mCharacterMesh_AnimState->getLength() || mCharacterMesh_AnimState->getLoop() || mCurrentAnimState == PLAYERANIMSTATE_IDLE)
530                        {
531                                mCurrentAnimState = PLAYERANIMSTATE_BLOCK;
532                                mCharacterMesh_AnimState->setEnabled(false);
533                                mCharacterMesh_AnimState = mCharacterMeshEntity->getAnimationState(getAnimStateName(PLAYERANIMSTATE_BLOCK));
534                                mCharacterMesh_AnimState->setTimePosition(0);
535                                mCharacterMesh_AnimState->setLoop(false);
536                                mCharacterMesh_AnimState->setEnabled(true);
537                        }
538                        break;
539                }
540        }
541
542        if(mForceAnimChange)
543                mForceAnimChange = false;
544}
Note: See TracBrowser for help on using the repository browser.