Team Fortress 2 Source Code as on 22/4/2020
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
|
|
//========= Copyright Valve Corporation, All rights reserved. ============//
//
// Purpose: List of game managers to update
//
// $Revision: $
// $NoKeywords: $
//===========================================================================//
#include "gamemanager.h"
#include "tier0/icommandline.h"
// FIXME: REMOVE (for Sleep)
#include <windows.h>
//-----------------------------------------------------------------------------
// globals
//-----------------------------------------------------------------------------
int IGameManager::m_nFrameNumber = 0; bool IGameManager::m_bStopRequested = false; bool IGameManager::m_bIsRunning = false; bool IGameManager::m_bIsInitialized = false; bool IGameManager::m_bLevelStartRequested = false; bool IGameManager::m_bLevelShutdownRequested = false; float IGameManager::m_flCurrentTime = 0.0f; float IGameManager::m_flLastTime = 0.0f; LevelState_t IGameManager::m_LevelState = NOT_IN_LEVEL;
CUtlVector< IGameManager* > IGameManager::m_GameManagers;
//-----------------------------------------------------------------------------
// Adds a system to the list of systems to run
//-----------------------------------------------------------------------------
void IGameManager::Add( IGameManager* pSys ) { Assert( !m_bIsRunning ); m_GameManagers.AddToTail( pSys ); }
//-----------------------------------------------------------------------------
// Removes a system from the list of systems to update
//-----------------------------------------------------------------------------
void IGameManager::Remove( IGameManager* pSys ) { Assert( !m_bIsRunning ); m_GameManagers.FindAndRemove( pSys ); }
//-----------------------------------------------------------------------------
// Removes *all* systems from the list of systems to update
//-----------------------------------------------------------------------------
void IGameManager::RemoveAll( ) { m_GameManagers.RemoveAll(); }
//-----------------------------------------------------------------------------
// Invokes a method on all installed game systems in proper order
//-----------------------------------------------------------------------------
void IGameManager::InvokeMethod( GameManagerFunc_t f ) { int i; int nCount = m_GameManagers.Count(); for ( i = 0; i < nCount; ++i ) { (m_GameManagers[i]->*f)(); } }
void IGameManager::InvokeMethodReverseOrder( GameManagerFunc_t f ) { int i; int nCount = m_GameManagers.Count(); for ( i = nCount; --i >= 0; ) { (m_GameManagers[i]->*f)(); } }
bool IGameManager::InvokeMethod( GameManagerInitFunc_t f ) { int i; int nCount = m_GameManagers.Count(); for ( i = 0; i < nCount; ++i ) { if ( !(m_GameManagers[i]->*f)() ) return false; } return true; }
LevelRetVal_t IGameManager::InvokeLevelMethod( GameManagerLevelFunc_t f, bool bFirstCall ) { LevelRetVal_t nRetVal = FINISHED; int i; int nCount = m_GameManagers.Count(); for ( i = 0; i < nCount; ++i ) { LevelRetVal_t val = (m_GameManagers[i]->*f)( bFirstCall ); if ( val == FAILED ) return FAILED; if ( val == MORE_WORK ) { nRetVal = MORE_WORK; } } return nRetVal; }
LevelRetVal_t IGameManager::InvokeLevelMethodReverseOrder( GameManagerLevelFunc_t f, bool bFirstCall ) { LevelRetVal_t nRetVal = FINISHED; int i; int nCount = m_GameManagers.Count(); for ( i = 0; i < nCount; ++i ) { LevelRetVal_t val = ( m_GameManagers[i]->*f )( bFirstCall ); if ( val == FAILED ) { nRetVal = FAILED; } if ( ( val == MORE_WORK ) && ( nRetVal != FAILED ) ) { nRetVal = MORE_WORK; } } return nRetVal; }
//-----------------------------------------------------------------------------
// Init, shutdown game system
//-----------------------------------------------------------------------------
bool IGameManager::InitAllManagers() { m_nFrameNumber = 0; if ( !InvokeMethod( &IGameManager::Init ) ) return false;
m_bIsInitialized = true; return true; }
void IGameManager::ShutdownAllManagers() { if ( m_bIsInitialized ) { InvokeMethodReverseOrder( &IGameManager::Shutdown ); m_bIsInitialized = false; } }
//-----------------------------------------------------------------------------
// Updates the state machine related to loading levels
//-----------------------------------------------------------------------------
void IGameManager::UpdateLevelStateMachine() { // Do we want to switch into the level shutdown state?
bool bFirstLevelShutdownFrame = false; if ( m_bLevelShutdownRequested ) { if ( m_LevelState != LOADING_LEVEL ) { m_bLevelShutdownRequested = false; } if ( m_LevelState == IN_LEVEL ) { m_LevelState = SHUTTING_DOWN_LEVEL; bFirstLevelShutdownFrame = true; } }
// Perform level shutdown
if ( m_LevelState == SHUTTING_DOWN_LEVEL ) { LevelRetVal_t val = InvokeLevelMethodReverseOrder( &IGameManager::LevelShutdown, bFirstLevelShutdownFrame ); if ( val != MORE_WORK ) { m_LevelState = NOT_IN_LEVEL; } }
// Do we want to switch into the level startup state?
bool bFirstLevelStartFrame = false; if ( m_bLevelStartRequested ) { if ( m_LevelState != SHUTTING_DOWN_LEVEL ) { m_bLevelStartRequested = false; } if ( m_LevelState == NOT_IN_LEVEL ) { m_LevelState = LOADING_LEVEL; bFirstLevelStartFrame = true; } }
// Perform level load
if ( m_LevelState == LOADING_LEVEL ) { LevelRetVal_t val = InvokeLevelMethod( &IGameManager::LevelInit, bFirstLevelStartFrame ); if ( val == FAILED ) { m_LevelState = NOT_IN_LEVEL; } else if ( val == FINISHED ) { m_LevelState = IN_LEVEL; } } }
//-----------------------------------------------------------------------------
// Runs the main loop.
//-----------------------------------------------------------------------------
void IGameManager::Start() { Assert( !m_bIsRunning && m_bIsInitialized );
m_bIsRunning = true; m_bStopRequested = false;
// This option is useful when running the app twice on the same machine
// It makes the 2nd instance of the app run a lot faster
bool bPlayNice = ( CommandLine()->CheckParm( "-yieldcycles" ) != 0 );
float flStartTime = m_flCurrentTime = m_flLastTime = Plat_FloatTime(); int nFramesSimulated = 0; int nCount = m_GameManagers.Count(); while ( !m_bStopRequested ) { UpdateLevelStateMachine();
m_flLastTime = m_flCurrentTime; m_flCurrentTime = Plat_FloatTime(); int nSimulationFramesNeeded = 1 + (int)( ( m_flCurrentTime - flStartTime ) / TICK_INTERVAL ); while( nSimulationFramesNeeded > nFramesSimulated ) { for ( int i = 0; i < nCount; ++i ) { if ( m_GameManagers[i]->PerformsSimulation() ) { m_GameManagers[i]->Update(); } } ++m_nFrameNumber; ++nFramesSimulated; }
// Always do I/O related managers regardless of framerate
for ( int i = 0; i < nCount; ++i ) { if ( !m_GameManagers[i]->PerformsSimulation() ) { m_GameManagers[i]->Update(); } }
if ( bPlayNice ) { Sleep( 1 ); } }
m_bIsRunning = false; }
//-----------------------------------------------------------------------------
// Stops the main loop at the next appropriate time
//-----------------------------------------------------------------------------
void IGameManager::Stop() { if ( m_bIsRunning ) { m_bStopRequested = true; } }
//-----------------------------------------------------------------------------
// Returns the current frame number
//-----------------------------------------------------------------------------
int IGameManager::FrameNumber() { return m_nFrameNumber; }
float IGameManager::CurrentSimulationTime() { return m_nFrameNumber * TICK_INTERVAL; }
float IGameManager::SimulationDeltaTime() { return TICK_INTERVAL; }
//-----------------------------------------------------------------------------
// Used in rendering
//-----------------------------------------------------------------------------
float IGameManager::CurrentTime() { return m_flCurrentTime; }
float IGameManager::DeltaTime() { return m_flCurrentTime - m_flLastTime; }
//-----------------------------------------------------------------------------
// Returns the current level state
//-----------------------------------------------------------------------------
LevelState_t IGameManager::GetLevelState() { return m_LevelState; }
//-----------------------------------------------------------------------------
// Start loading a level
//-----------------------------------------------------------------------------
void IGameManager::StartNewLevel() { m_bLevelShutdownRequested = true; m_bLevelStartRequested = true; }
void IGameManager::ShutdownLevel() { m_bLevelShutdownRequested = true; }
|