Main Page   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members   Related Pages  

CGameFramework Class Reference

Provides UI with access to CGame, and CGame access to the UI. More...

#include <CGameFramework.h>

Collaboration diagram for CGameFramework:

Collaboration graph
[legend]
List of all members.

Public Types

enum  TGameState { EDied, ELevelCompleted, EPaused }
 Current state of the game. More...


Public Methods

 ~CGameFramework ()
 delete level information. More...

TGameState RunL (TBool aReset)
 Run a level of the game. More...

void LoadLevelL (const TDesC &aLevelName, const TDesC &aMapName, TBool aResetShip)
 Load level and map files. More...

TInt Score ()
 Allow the ui access to the players score. More...

void CancelL ()
 Cancel paused game. More...


Static Public Methods

CGameFramework * NewL ()
 Leave safe constuction. More...


Private Methods

TBool Play (RWsSession &aWindSession)
 Loop getting window server events. More...


Static Private Methods

TInt GameThread (TAny *aGameData)
 Game thread start point. More...


Private Attributes

TGameData iData
 Game data, key presses level information etc. More...

RThread iGameThread
 Thread within which the CGame object runs. More...

TRequestStatus iGameStatus
 Status of game thread. More...

HBufC8 * iLevel
 Sprite, background and status sprites for level. More...

HBufC8 * iMap
 Map and path data for game. More...


Detailed Description

Provides UI with access to CGame, and CGame access to the UI.

Loads levels, starts/suspends the thread that owns the CGame object, talks direct to the window server to collect key presses and focus change events.

Definition at line 30 of file CGameFramework.h.


Member Enumeration Documentation

enum CGameFramework::TGameState
 

Current state of the game.

Enumeration values:
EDied  No game running, thread exited because player died.
ELevelCompleted  No game running, thread exited because player finished a level.
EPaused  Game paused, game thread is suspended.

Definition at line 33 of file CGameFramework.h.

Referenced by CGameAppUi::HandleCommandL(), and RunL().

00033                   {
00034     EDied, 
00035     ELevelCompleted, 
00036     EPaused, 
00037   };


Constructor & Destructor Documentation

CGameFramework::~CGameFramework  
 

delete level information.

Definition at line 31 of file CGameFramework.cpp.

References iLevel, and iMap.

00031                                 {
00032   delete iLevel;
00033   delete iMap;
00034 };


Member Function Documentation

CGameFramework * CGameFramework::NewL   [static]
 

Leave safe constuction.

Not really nessesary as there is no ConstuctL, but there might be in the future

Definition at line 25 of file CGameFramework.cpp.

Referenced by CGameAppUi::ConstructL().

00025                                     {
00026   CGameFramework* self= new (ELeave) CGameFramework;
00027   return(self);
00028 };

CGameFramework::TGameState CGameFramework::RunL TBool    aReset
 

Run a level of the game.

This class creates a connection to the window server, and creates a window to cover the screen. Sets iData.iForceRedraw so that is we are resuming a previous game the status screen is updated in full. If this returns and the game hasn't been paused the level has been deleted.

Parameters:
aReset  whether to reset lives and score, ie whether this is a new game or resuming an old one.
Returns:
Returns whether the level was paused, finished or the player died.

Definition at line 106 of file CGameFramework.cpp.

References EDied, ELevelCompleted, TGamePanics::ENoLevelLoaded, EPaused, iData, TGameData::iForceRedraw, iGameStatus, iGameThread, iLevel, TGameData::iLevelCompleted, TGameData::iLives, iMap, TGameData::iScore, TGamePanics::Panic(), Play(), and TGameState.

Referenced by CancelL(), and CGameAppUi::HandleCommandL().

00106                                                           {  
00107   // assert that LoadLevelL has been called and succeded in
00108   // loading a level
00109   __ASSERT_ALWAYS(iLevel!=NULL && iMap!=NULL,TGamePanics::Panic(TGamePanics::ENoLevelLoaded));
00110 
00111   // if this is a new game reset the score and lives
00112   if(aReset!=EFalse) {
00113     iData.iLives=3;
00114     iData.iScore=0;
00115   }
00116 
00117   // connect to the window server.
00118   RWsSession winSession;
00119   User::LeaveIfError(winSession.Connect());
00120   CleanupClosePushL(winSession);
00121   
00122   // these can be whatever we like, as long as they are unique,
00123   // as we have only one window and one windowgroup we don't
00124   // actually use them.
00125   const TUint32 KWindowHandle=1;
00126   const TUint32  KWindowGroupHandle=2;
00127 
00128   // create a window group so we can create a window
00129   RWindowGroup winGroup(winSession);
00130   User::LeaveIfError(winGroup.Construct(KWindowGroupHandle));
00131   CleanupClosePushL(winGroup);
00132   
00133   // create a blank window, blank windows can't be drawn on,
00134   // however as the game code writes directly to the screen this
00135   // isn't a problem.
00136   RBlankWindow window(winSession);
00137   User::LeaveIfError(window.Construct(winGroup,KWindowHandle));
00138   CleanupClosePushL(window);
00139   window.Activate();
00140   window.SetSize(TSize(640,200));
00141   // request focus events so we can pause the game thread when
00142   // we move to the background, this stops us writing over some other
00143   // apps screen.
00144   window.EnableFocusChangeEvents();
00145 
00146   // first time in we want want to redraw everything,
00147   iData.iForceRedraw=ETrue;
00148 
00149   // logon to the thread so we get informed when it exits.
00150   iGameThread.Logon(iGameStatus);
00151   iGameThread.Resume();
00152 
00153   // play the game
00154   TBool finished=Play(winSession);
00155 
00156   // cancel any outstanding request for key strokes/focus changes etc
00157   winSession.EventReadyCancel();
00158   // and watching the state of the thread
00159   iGameThread.LogonCancel(iGameStatus);
00160 
00161   // I think this is the EventReady completing.
00162   User::WaitForAnyRequest();
00163 
00164   // remove our window
00165   CleanupStack::PopAndDestroy(3,&winSession); //winGroup, window
00166   
00167 
00168   if(finished==EFalse) {
00169     // this is the thread notifying that it has suspended
00170     User::WaitForAnyRequest();
00171     // we have just paused the thread/game
00172     return EPaused;
00173   } else {
00174     // game finished, so close the thread, and delete the level
00175     iGameThread.Close();
00176     delete iLevel;
00177     iLevel=NULL;
00178     delete iMap;
00179     iMap=NULL;
00180 
00181     User::Heap().Compress();
00182 
00183     // did the player complete the level or die
00184     if(iData.iLevelCompleted==EFalse) {
00185       return EDied;
00186     } else {
00187       return ELevelCompleted;
00188     }
00189   }    
00190 };

void CGameFramework::LoadLevelL const TDesC &    aLevelName,
const TDesC &    aMapName,
TBool    aResetShip
 

Load level and map files.

This loads the level and map files setting the iData.iLevel members to the information in the files.

It also creates the game thread but doesn't resume it.

Parameters:
aLevelName  full path and file name of level file.
aMapName  full path and file name of map file.
aResetShip  whether to reset ship powerups to level data.

Definition at line 289 of file CGameFramework.cpp.

References TGamePanics::ELoadLevelWithLevelLoaded, GameThread(), TLevelData::iBackgrounds, TLevelData::iBadGuyDeathEndSprite, TLevelData::iBadGuyDeathStartSprite, TLevelData::iBulletPower1_StartSprite, TLevelData::iBulletPower2_StartSprite, TLevelData::iBulletPower3_StartSprite, TLevelData::iBulletPower4_StartSprite, iData, iGameThread, TGameData::iKeys, TGameData::iLevel, iLevel, TGameData::iLevelCompleted, iMap, TLevelData::iMapData, TLevelData::iPaths, TLevelData::iShipDeathEndSprite, TLevelData::iShipDeathStartSprite, TLevelData::iShipPowerups, TLevelData::iShipSprite, TLevelData::iShipStartHealth, TLevelData::iShipStartXPos, TLevelData::iShipStartYPos, TLevelData::iSprites, TLevelData::iStatus, and TGamePanics::Panic().

Referenced by CGameAppUi::LoadLevelL().

00289                                                                                                {
00290   __ASSERT_ALWAYS(iLevel==NULL && iMap==NULL,TGamePanics::Panic(TGamePanics::ELoadLevelWithLevelLoaded));
00291   
00292   RFs fs;
00293   User::LeaveIfError(fs.Connect());  
00294   CleanupClosePushL(fs);
00295 
00296 
00297   // load level file
00298   RFile levelFile;
00299   User::LeaveIfError(levelFile.Open(fs,aLevelName,EFileRead));  
00300   CleanupClosePushL(levelFile);                    
00301 
00302   TInt size;
00303   User::LeaveIfError(levelFile.Size(size));
00304   size-=16; //skip uids on front of file
00305   HBufC8 *levelDes= HBufC8::NewLC(size);
00306   TPtr8 levelPtr=levelDes->Des();
00307   User::LeaveIfError(levelFile.Read(16,levelPtr,size));
00308 
00309 
00310   // load map file
00311   RFile mapFile;
00312   User::LeaveIfError(mapFile.Open(fs,aMapName,EFileRead));
00313   CleanupClosePushL(mapFile);
00314 
00315   User::LeaveIfError(mapFile.Size(size));
00316   size-=16; //skip uids on front of file
00317   HBufC8 *mapDes= HBufC8::NewLC(size);
00318   TPtr8 mapPtr=mapDes->Des();
00319   User::LeaveIfError(mapFile.Read(16,mapPtr,size));
00320 
00321 
00322 
00323 
00324   // create a thread within which to run the game,
00325   _LIT(KGameThread,"RealGame");
00326   // 4k stack,
00327   const TInt KStackSize=4*1024;
00328   
00329   // create but don't resume as the iData isn't set up yet.
00330   User::LeaveIfError(iGameThread.Create(KGameThread,GameThread,KStackSize,NULL,&iData));
00331   // as we want to respond to key presses the game thread
00332   // has a lower priority than getting events
00333   iGameThread.SetPriority(EPriorityLess);
00334   
00335 
00336 
00337 
00338   
00339   CleanupStack::Pop(mapDes);
00340   iMap=mapDes;
00341   CleanupStack::PopAndDestroy(&mapFile);
00342   CleanupStack::Pop(levelDes);
00343   iLevel=levelDes;
00344   CleanupStack::PopAndDestroy(2,&fs); // levelFile
00345 
00346 
00347   // setup level data
00348   TInt32* level= (TInt32*) (iLevel->Ptr());
00349   TInt32* map= (TInt32*) (iMap->Ptr());
00350   
00351   iData.iKeys=0;
00352   iData.iLevelCompleted=EFalse;
00353 
00354   iData.iLevel.iMapData=(TInt16*) (iMap->Ptr()+map[0]);
00355   iData.iLevel.iPaths=(TInt16*) (iMap->Ptr()+map[1]);
00356 
00357   iData.iLevel.iBackgrounds=(TUint16*) (iLevel->Ptr()+level[0]);
00358   iData.iLevel.iSprites=(TUint16*) (iLevel->Ptr()+level[1]);
00359   iData.iLevel.iStatus=(TUint16*) (iLevel->Ptr()+level[2]);
00360 
00361   iData.iLevel.iShipSprite=(TInt16) map[2];
00362   iData.iLevel.iShipDeathStartSprite=(TInt16) map[3];
00363   iData.iLevel.iShipDeathEndSprite=(TInt16) map[4];
00364   iData.iLevel.iBadGuyDeathStartSprite=(TInt16) map[5];
00365   iData.iLevel.iBadGuyDeathEndSprite=(TInt16) map[6];
00366   iData.iLevel.iBulletPower1_StartSprite=(TInt16) map[7];
00367   iData.iLevel.iBulletPower2_StartSprite=(TInt16) map[8];
00368   iData.iLevel.iBulletPower3_StartSprite=(TInt16) map[9];
00369   iData.iLevel.iBulletPower4_StartSprite=(TInt16) map[10];
00370   iData.iLevel.iShipStartXPos=(TInt16) map[11];
00371   iData.iLevel.iShipStartYPos=(TInt16) map[12];
00372   iData.iLevel.iShipStartHealth=(TInt16) map[13];
00373   if(aResetShip!=EFalse) {
00374     iData.iLevel.iShipPowerups=(TInt16) map[14];
00375   }
00376 }

TInt CGameFramework::Score  
 

Allow the ui access to the players score.

Definition at line 88 of file CGameFramework.cpp.

References iData, and TGameData::iScore.

Referenced by CGameAppUi::HandleCommandL().

00088                            {
00089   return(iData.iScore);
00090 }

void CGameFramework::CancelL  
 

Cancel paused game.

Simulates a quit key press then starts the game running. The game thread has to run so it can delete the CGame object.

Definition at line 41 of file CGameFramework.cpp.

References TGameData::EQuit, iData, TGameData::iKeys, and RunL().

Referenced by CGameAppUi::HandleCommandL().

00041                              {
00042   iData.iKeys |= TGameData::EQuit;
00043   RunL(EFalse);
00044 }

TInt CGameFramework::GameThread TAny *    aGameData [static, private]
 

Game thread start point.

This creates a CGame object and keeps calling Play on it while the player has lives, hasn't finished the level and hasn't quit.

The TGameData comunicates the level information and key presses to this thread and comunicates the score, lives left and outcome of the level back to the ui thread.

Parameters:
aGameData  a TGameData*
Returns:
error code if we failed to create CGame or CTrapCleanup objects

Definition at line 61 of file CGameFramework.cpp.

References TGameData::EQuit, TGameData::iKeys, TGameData::iLevelCompleted, TGameData::iLives, CGame::NewL(), and CGame::Play().

Referenced by LoadLevelL().

00061                                                {
00062   // create a cleanup stack
00063   CTrapCleanup* cleanup=CTrapCleanup::New();  
00064   if(cleanup==NULL)
00065     return KErrNoMemory;
00066 
00067   TInt error=KErrNone;
00068 
00069   TGameData& data= (*STATIC_CAST(TGameData*,aGameData));
00070 
00071   // look while we have lives, haven't got to the end of the level,
00072   // 'Q' hasn't been pressed, and haven't got an error creating the game.
00073   while(data.iLives!=0 && !(data.iKeys & TGameData::EQuit) &&
00074         data.iLevelCompleted==EFalse && error==KErrNone) {    
00075     // create a game and call play on it.
00076     CGame *game=NULL;
00077     TRAPD(error,game=CGame::NewL(data));
00078     if(error==KErrNone) {
00079       game->Play();
00080       delete game;
00081     }
00082   }
00083   delete cleanup;
00084   return error;
00085 };

TBool CGameFramework::Play RWsSession &    aWindSession [private]
 

Loop getting window server events.

This class loops waiting for requests.

If it is a window server key event we update the iData.iKeys bitmask to tell the game thread that a key was pressed.

If it is a window server key event 'P' or a focus lost event we suspend the game thread and return.

If it is the game thread exiting we return.

Otherwise we allow the active scheduler to handle it.

Returns:
ETrue if game thread completed, EFalse if it was suspended.

Definition at line 210 of file CGameFramework.cpp.

References TGameData::EAction1, TGameData::EAction2, TGameData::EAction3, TGameData::EAction4, TGameData::EDown, TGameData::ELeft, TGameData::EQuit, TGameData::ERight, TGameData::EUp, iData, iGameStatus, iGameThread, and TGameData::iKeys.

Referenced by RunL().

00210                                                    {
00211   TRequestStatus normalEvent;
00212 
00213   // listen for key strokes/focus changes etc.
00214   aWindSession.EventReady(&normalEvent);
00215 
00216   for(;;) {
00217     User::WaitForAnyRequest();
00218     if(normalEvent!=KRequestPending) {
00219       TWsEvent event;
00220       aWindSession.GetEvent(event);
00221       aWindSession.EventReady(&normalEvent);        
00222       switch(event.Type()) {
00223       case EEventKeyDown: {
00224         TKeyEvent *key=event.Key();
00225         switch(key->iScanCode) {            
00226         case EStdKeyLeftArrow:   iData.iKeys |= TGameData::ELeft;    break;
00227         case EStdKeyRightArrow:  iData.iKeys |= TGameData::ERight;   break;
00228         case EStdKeyUpArrow:     iData.iKeys |= TGameData::EUp;      break;
00229         case EStdKeyDownArrow:   iData.iKeys |= TGameData::EDown;    break;
00230         case 'Q':                iData.iKeys |= TGameData::EQuit;    break;
00231         case 'A':                iData.iKeys |= TGameData::EAction1; break;
00232         case EStdKeySpace:       iData.iKeys |= TGameData::EAction2; break;
00233         case EStdKeyLeftShift:   iData.iKeys |= TGameData::EAction3; break;
00234         case EStdKeyEnter:       iData.iKeys |= TGameData::EAction4; break;
00235         case 'P': {
00236           iGameThread.Suspend();
00237           return EFalse;
00238         }
00239         }
00240       }
00241       break;
00242       case EEventKeyUp: {
00243         TKeyEvent *key=event.Key();
00244         switch(key->iScanCode) {            
00245         case EStdKeyLeftArrow:   iData.iKeys &= ~TGameData::ELeft;    break;
00246         case EStdKeyRightArrow:  iData.iKeys &= ~TGameData::ERight;   break;
00247         case EStdKeyUpArrow:     iData.iKeys &= ~TGameData::EUp;      break;
00248         case EStdKeyDownArrow:   iData.iKeys &= ~TGameData::EDown;    break;
00249         case 'A':                iData.iKeys &= ~TGameData::EAction1; break;
00250         case EStdKeySpace:       iData.iKeys &= ~TGameData::EAction2; break;
00251         case EStdKeyLeftShift:   iData.iKeys &= ~TGameData::EAction3; break;
00252         case EStdKeyEnter:       iData.iKeys &= ~TGameData::EAction4; break;
00253         }
00254       }        
00255       break;   
00256       case EEventFocusLost:
00257         // pause game if we go into the background
00258         iGameThread.Suspend();
00259         return EFalse;
00260         break;
00261       }
00262     } else if(iGameStatus!=KRequestPending) {
00263       // thread ended
00264       return ETrue;
00265     } else { 
00266       // event meant for active scheduler if there is one
00267       // I don't think it should never get here
00268       CActiveScheduler *sched=CActiveScheduler::Current();
00269       if(sched!=NULL) {
00270         TInt error;
00271         sched->RunIfReady(error,0);
00272       }
00273     }
00274   }
00275 }


Member Data Documentation

TGameData CGameFramework::iData [private]
 

Game data, key presses level information etc.

Definition at line 53 of file CGameFramework.h.

Referenced by CancelL(), LoadLevelL(), Play(), RunL(), and Score().

RThread CGameFramework::iGameThread [private]
 

Thread within which the CGame object runs.

Definition at line 54 of file CGameFramework.h.

Referenced by LoadLevelL(), Play(), and RunL().

TRequestStatus CGameFramework::iGameStatus [private]
 

Status of game thread.

Definition at line 55 of file CGameFramework.h.

Referenced by Play(), and RunL().

HBufC8* CGameFramework::iLevel [private]
 

Sprite, background and status sprites for level.

Definition at line 57 of file CGameFramework.h.

Referenced by LoadLevelL(), RunL(), and ~CGameFramework().

HBufC8* CGameFramework::iMap [private]
 

Map and path data for game.

Definition at line 58 of file CGameFramework.h.

Referenced by LoadLevelL(), RunL(), and ~CGameFramework().


The documentation for this class was generated from the following files:
Documentation for Game (Beta) version 1.44.