diff options
| author | FluorescentCIAAfricanAmerican <[email protected]> | 2020-04-22 12:56:21 -0400 |
|---|---|---|
| committer | FluorescentCIAAfricanAmerican <[email protected]> | 2020-04-22 12:56:21 -0400 |
| commit | 3bf9df6b2785fa6d951086978a3e66f49427166a (patch) | |
| tree | 2c0f1f0c63c4832882bc93814ebd2c2b1c6224e5 /dedicated/vgui | |
| download | archived-source-engine-2018-hl2-src-master.tar.xz archived-source-engine-2018-hl2-src-master.zip | |
Diffstat (limited to 'dedicated/vgui')
| -rw-r--r-- | dedicated/vgui/CreateMultiplayerGameServerPage.cpp | 872 | ||||
| -rw-r--r-- | dedicated/vgui/CreateMultiplayerGameServerPage.h | 126 | ||||
| -rw-r--r-- | dedicated/vgui/MainPanel.cpp | 274 | ||||
| -rw-r--r-- | dedicated/vgui/MainPanel.h | 89 | ||||
| -rw-r--r-- | dedicated/vgui/vguihelpers.cpp | 187 | ||||
| -rw-r--r-- | dedicated/vgui/vguihelpers.h | 26 | ||||
| -rw-r--r-- | dedicated/vgui/vguihelpers_linux.cpp | 39 |
7 files changed, 1613 insertions, 0 deletions
diff --git a/dedicated/vgui/CreateMultiplayerGameServerPage.cpp b/dedicated/vgui/CreateMultiplayerGameServerPage.cpp new file mode 100644 index 0000000..d4e6308 --- /dev/null +++ b/dedicated/vgui/CreateMultiplayerGameServerPage.cpp @@ -0,0 +1,872 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +// $NoKeywords: $ +//=============================================================================// + +#ifdef _WIN32 +#include <stdio.h> + +#include "CreateMultiplayerGameServerPage.h" +#include <Winsock2.h> + +using namespace vgui; + +#include <vgui_controls/Controls.h> +#include <KeyValues.h> +#include <vgui_controls/ListPanel.h> +#include <vgui_controls/ComboBox.h> +#include <vgui_controls/MessageBox.h> +#include <vgui_controls/CheckButton.h> +#include <vgui/IVGui.h> + +#include <OfflineMode.h> + +#include "filesystem.h" +#include "mainpanel.h" +#include "tier0/icommandline.h" +#include "netapi.h" +// for SRC +#include <vstdlib/random.h> + +// memdbgon must be the last include file in a .cpp file!!! +#include "tier0/memdbgon.h" + + +//#define ALLOW_OLD_ENGINE_GAMES + + +bool IsEp1EraAppID( int iSteamAppId ) +{ + return iSteamAppId == 211 || iSteamAppId == 215; +} + +// Checks the liblist.gam file for a "fallback_dir" +const char *GetLiblistFallbackDir( const char *pszGameDir ) +{ + static char szFallback[512]; + char szTemp[512]; + + szFallback[0] = 0; + + V_sprintf_safe( szTemp, "%s\\liblist.gam", pszGameDir ); + g_pFullFileSystem->GetLocalCopy( szTemp ); + + FileHandle_t hFile = g_pFullFileSystem->Open( szTemp, "rt" ); + + if ( hFile ) + { + char szLine[512]; + + // look for the line starting with 'fallback_dir' + while ( !g_pFullFileSystem->EndOfFile( hFile ) ) + { + // get a single line + szLine[0] = 0; + g_pFullFileSystem->ReadLine( szLine, sizeof(szLine) - 1, hFile ); + szLine[sizeof(szLine) - 1] = 0; + + if ( !strnicmp( szLine, "fallback_dir", 12 ) ) + { + // we got the line, get the value between the quotes + char *start = strchr( szLine, '\"' ); + + if ( !start ) + { + break; + } + + char *end = strchr( start + 1, '\"' ); + if ( !end ) + { + break; + } + + // copy out between start and end + int bytesToCopy = end - start - 1; + if ( bytesToCopy >= sizeof(szFallback) - 1 ) + { + bytesToCopy = sizeof(szFallback) - 1; + break; + } + + if ( bytesToCopy > 0 ) + { + strncpy( szFallback, start + 1, bytesToCopy ); + szFallback[bytesToCopy] = 0; + } + } + } + + g_pFullFileSystem->Close( hFile ); + } + + return szFallback; +} + + +//----------------------------------------------------------------------------- +// Purpose: Constructor +//----------------------------------------------------------------------------- +CCreateMultiplayerGameServerPage::CCreateMultiplayerGameServerPage(vgui::Panel *parent, const char *name) : Frame(parent, name) +{ + memset(&m_iServer,0x0,sizeof(serveritem_t)); + + m_MainPanel = parent; // as we are a popup frame we need to store this seperately + m_pSavedData = NULL; + m_pGameInfo = NULL; + + SetMinimumSize(310, 350); + SetSize(310, 350); + SetSizeable(false); + + + SetTitle("#Start_Server_Title",true); + + m_pMapList = new ComboBox(this, "MapList",10,false); + m_pMapList->SetEnabled(false); // a mod needs to be chosen first to populate the map list + m_pMapList->SetEditable(false); + + m_pNetworkCombo = new ComboBox(this, "NetworkCombo",10,false); + int defaultItem = m_pNetworkCombo->AddItem("#Internet", NULL); + int lanItem = m_pNetworkCombo->AddItem("#LAN", NULL); + if ( CommandLine()->CheckParm("-steam") && IsSteamInOfflineMode() ) + { + defaultItem = lanItem; + } + m_pNetworkCombo->ActivateItem(defaultItem); + + m_pNumPlayers = new ComboBox(this, "NumPlayers",10,false); + char num[3]; + int i; + for( i = 1 ; i <= MAX_PLAYERS ; i++ ) + { + V_sprintf_safe(num, "%i", i); + m_pNumPlayers->AddItem(num, NULL); + } + m_pNumPlayers->ActivateItemByRow(23); // 24 players by default + + m_pGameCombo = new ComboBox(this,"MODCombo", 10, false); + + m_pStartServerButton = new Button(this, "StartButton", "#Start_Server_Button"); + m_pStartServerButton->SetCommand("start"); + + m_pCancelButton = new Button(this, "CancelButton", "#Start_Server_Cancel"); + m_pCancelButton->SetCommand("cancel"); + + m_pSecureCheck = new CheckButton(this, "SecureCheck", "#Start_Server_Secure"); + m_pSecureCheck->SetSelected(true); + + LoadControlSettingsAndUserConfig("Admin/CreateMultiplayerGameServerPage.res"); + + // load some defaults into the controls + SetControlString("ServerNameEdit", "Half-Life dedicated server"); + V_strcpy_safe(m_szGameName, "Half-Life"); + + LoadMODList(); + + m_pGameCombo->RequestFocus(); + + // get default port from commandline if possible + m_iPort = 27015; + const char *portVal = NULL; + if (CommandLine()->CheckParm("-port", &portVal) && portVal && atoi(portVal) > 0) + { + m_iPort = atoi(portVal); + } + SetControlInt("PortEdit", m_iPort); + + LoadConfig(); + + m_szMapName[0] = 0; + m_szHostName[0] = 0; + m_szPassword[0] = 0; + m_iMaxPlayers = 24; + + if ( CommandLine()->CheckParm("-steam") && IsSteamInOfflineMode() ) + { + m_pNetworkCombo->SetEnabled( false ); + } + + SetVisible(true); + + if ( CommandLine()->CheckParm("-steam") && IsSteamInOfflineMode() ) + { + MessageBox *box = new vgui::MessageBox( "#Start_Server_Offline_Title", "#Start_Server_Offline_Warning" ); + box->DoModal(); + } +} + +//----------------------------------------------------------------------------- +// Purpose: Destructor +//----------------------------------------------------------------------------- +CCreateMultiplayerGameServerPage::~CCreateMultiplayerGameServerPage() +{ + SaveConfig(); + if (m_pSavedData) + { + m_pSavedData->deleteThis(); + m_pSavedData = NULL; + } + if ( m_pGameInfo ) + { + m_pGameInfo->deleteThis(); + m_pGameInfo = NULL; + } +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void CCreateMultiplayerGameServerPage::OnResetData() +{ + m_pGameCombo->SetEnabled(true); +} + +//----------------------------------------------------------------------------- +// Purpose: loads settings from a config file +//----------------------------------------------------------------------------- +void CCreateMultiplayerGameServerPage::LoadConfig() +{ + // free any old filters + if (m_pSavedData) + { + m_pSavedData->deleteThis(); + } + m_pSavedData = new KeyValues ("Server"); + + if (!m_pSavedData->LoadFromFile(g_pFullFileSystem, "Server.vdf", "CONFIG")) + { + // file not successfully loaded + } + else + { + if (m_pSavedData->FindKey("RconPassword", false)) + { + const char *password = m_pSavedData->GetString("RconPassword", ""); + if (strlen(password)>0) + { + SetControlString("RCONPasswordEdit", password); + } + } + if (m_pSavedData->FindKey("MaxPlayers", false)) + { + int maxPlayers = m_pSavedData->GetInt("MaxPlayers", -1); + if (maxPlayers > 0 && maxPlayers <= 32) + { + m_pNumPlayers->ActivateItemByRow(maxPlayers - 1); + } + } + if (m_pSavedData->FindKey("MOD", false)) + { + const char *mod = m_pSavedData->GetString("MOD", ""); + if (strlen(mod) > 0) + { + // look for the item in the dropdown + m_szMod[0] = 0; + for (int i = 0; i < m_pGameCombo->GetItemCount(); i++) + { + if (!m_pGameCombo->IsItemIDValid(i)) + continue; + + if (!stricmp(m_pGameCombo->GetItemUserData(i)->GetString("gamedir"), mod)) + { + // item found in list, activate + m_pGameCombo->ActivateItem(i); + break; + } + } + } + } + if (m_pSavedData->FindKey("Map", false)) + { + const char *map = m_pSavedData->GetString("Map", ""); + if (strlen(map) > 0) + { + SetControlString("MapList", map); + } + } + + if (m_pSavedData->FindKey("Network", false)) + { + int nwIndex = m_pSavedData->GetInt("Network"); + if (nwIndex > 0 && nwIndex < 2) + { + m_pNetworkCombo->ActivateItemByRow(nwIndex); + } + } + if (m_pSavedData->FindKey("Secure", false)) + { + int secure = m_pSavedData->GetInt("Secure"); + m_pSecureCheck->SetSelected(secure); + } + if (m_pSavedData->FindKey("ServerName", false)) + { + const char *serverName = m_pSavedData->GetString("ServerName",""); + if (strlen(serverName) > 0) + { + SetControlString("ServerNameEdit", serverName); + } + } + m_iPort = m_pSavedData->GetInt("Port", m_iPort); + SetControlInt("PortEdit", m_iPort); + } +} + + +//----------------------------------------------------------------------------- +// Purpose: data accessor +//----------------------------------------------------------------------------- +void CCreateMultiplayerGameServerPage::SetConfig(const char *serverName, const char *rconPassword, int maxPlayers, const char *mod, const char *map, int network, int secure, int port) +{ + m_pSavedData->SetInt("MaxPlayers", maxPlayers); + m_pSavedData->SetString("RconPassword", rconPassword); + m_pSavedData->SetString("ServerName", serverName); + m_pSavedData->SetString("MOD", mod); + m_pSavedData->SetString("Map", map); + m_pSavedData->SetInt("Secure", secure); + m_pSavedData->SetInt("Network", network); + m_pSavedData->SetInt("Port", port); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void CCreateMultiplayerGameServerPage::SaveConfig() +{ + m_pSavedData->SaveToFile(g_pFullFileSystem, "Server.vdf", "CONFIG"); +} + +//----------------------------------------------------------------------------- +// Purpose: returns true if one of the characters in the string is not a valid alpha numeric character +//----------------------------------------------------------------------------- +bool CCreateMultiplayerGameServerPage::BadRconChars(const char *pass) +{ + bool bad = false; + + for(unsigned int i=0;i<strlen(pass);i++) + { + bad |= !( V_isalnum(pass[i]) ? true : false ); + } + return bad; +} + +const char *ToString( int val ) +{ + static char text[256]; + Q_snprintf( text, sizeof(text), "%i", val ); + return text; +} + + +//----------------------------------------------------------------------------- +// Purpose: called to get the info from the dialog +//----------------------------------------------------------------------------- +void CCreateMultiplayerGameServerPage::OnCommand(const char *cmd) +{ + char cvars[1024]; + int secure = GetControlInt("SecureCheck", 1); + m_pNumPlayers->GetText(cvars, 1024); + m_iMaxPlayers = atoi(cvars); + V_strcpy_safe(m_szHostName, GetControlString("ServerNameEdit", "")); + V_strcpy_safe(m_szPassword, GetControlString("RCONPasswordEdit", "")); + m_iPort = GetControlInt("PortEdit", 27015); + + if (!stricmp(cmd, "cancel")) + { + vgui::ivgui()->PostMessage( m_MainPanel->GetVPanel(), new KeyValues("Quit"), NULL); + Close(); + } + else if (!stricmp(cmd, "start")) + { + // save our current settings + SetConfig(m_szHostName, m_szPassword, m_iMaxPlayers, m_szMod, GetMapName(), m_pNetworkCombo->GetActiveItem() != 0, secure, m_iPort); + SaveConfig(); + + // create the command to execute + bool isLanOnly = (m_pNetworkCombo->GetActiveItem() != 0); + CommandLine()->AppendParm("-game", m_szMod); + CommandLine()->AppendParm("-maxplayers", ToString(m_iMaxPlayers)); + CommandLine()->AppendParm("+sv_lan", ToString(isLanOnly)); + CommandLine()->AppendParm("+map", GetMapName()); + CommandLine()->AppendParm("-port", ToString(m_iPort)); + if (!secure) // if they don't want it secure... + { + CommandLine()->AppendParm("-insecure", ""); + } + + + // V_strcpy_safe(m_szPassword, GetControlString("RCONPasswordEdit", "")); + if (strlen(m_szPassword) < 3 || BadRconChars(m_szPassword)) + { + MessageBox *dlg = new MessageBox("#Start_Server_RCON_Error_Title", "#Start_Server_RCON_Error"); + dlg->DoModal(); + } + else + { + V_sprintf_safe(cvars, "rcon_password \"%s\"\nsetmaster enable\nhostname \"%s\"\n", m_szPassword, m_szHostName); + + m_pGameCombo->SetEnabled(false); + m_pNumPlayers->SetEnabled(false); + + netadr_t local; + net->GetLocalIP(&local); + local.port = ::htons(m_iPort); + + for (int i = 0; i < 4; i++) + { + m_iServer.ip[i] = local.ip[i]; + } + m_iServer.port = (local.port & 0xff) << 8 | (local.port & 0xff00) >> 8;; + + V_strcpy_safe(m_iServer.name, m_szHostName); + V_strcpy_safe(m_iServer.map, GetMapName()); + V_strcpy_safe(m_iServer.gameDir, m_szMod); + m_iServer.maxPlayers = m_iMaxPlayers; + + SetVisible(false); + + KeyValues *gameData = m_pGameCombo->GetActiveItemUserData(); + +// // mount the caches +// if (CommandLine()->CheckParm("-steam")) +// { +// if (gameData) +// { +// KeyValues *pFileSystem = gameData->FindKey( "FileSystem" ); +// if ( !pFileSystem ) +// Error( "Game %s missing FileSystem key.", gameData->GetString( "game" ) ); +// +// // Mods just specify their app ID (CS, HL2, HL2MP, etc), and it mounts all the necessary caches. +// int iAppId = pFileSystem->GetInt( "SteamAppId" ); +// if ( iAppId ) +// { +// CUtlVector<unsigned int> depList; +// MountDependencies( iAppId, depList ); +// +// char gameinfoFilename[MAX_PATH]; +// Q_snprintf( gameinfoFilename, sizeof( gameinfoFilename ), "%s\\gameinfo.txt", m_iServer.gameDir ); +// g_pFullFileSystem->GetLocalCopy( gameinfoFilename ); +// } +// } +// } + + // Launch the old dedicated server if necessary. + if ( LaunchOldDedicatedServer( gameData ) ) + { + vgui::ivgui()->PostMessage( m_MainPanel->GetVPanel(), new KeyValues("Quit"), NULL); + Close(); + } + + CMainPanel::GetInstance()->StartServer(cvars); + } + } +} + +bool CCreateMultiplayerGameServerPage::LaunchOldDedicatedServer( KeyValues *pGameInfo ) +{ +#if defined( ALLOW_OLD_ENGINE_GAMES ) + // Validate the gameinfo.txt format.. + KeyValues *pSub = pGameInfo->FindKey( "FileSystem" ); + if ( pSub ) + { + int iSteamAppId = pSub->GetInt( "SteamAppId", -1 ); + if ( iSteamAppId != -1 ) + { + if ( IsEp1EraAppID( iSteamAppId ) ) + { + // Old-skool app. Launch the old dedicated server. + char steamDir[MAX_PATH]; + if ( !system()->GetRegistryString( "HKEY_CURRENT_USER\\Software\\Valve\\Steam\\SteamPath", steamDir, sizeof( steamDir ) ) ) + Error( "LaunchOldDedicatedServer: can't get SteamPath." ); + + V_FixSlashes( steamDir ); + V_AppendSlash( steamDir, sizeof( steamDir ) ); + + char commandLine[1024 * 4]; + commandLine[0] = 0; + V_snprintf( commandLine, sizeof( commandLine ), "\"%ssteam.exe\" -applaunch 205 -HiddenLaunch", steamDir ); + + // Feed it all the parameters chosen in the UI so it doesn't redisplay the UI. + STARTUPINFO si; + memset( &si, 0, sizeof( si ) ); + si.cb = sizeof( si ); + + PROCESS_INFORMATION pi; + if ( !CreateProcess( NULL, commandLine, NULL, NULL, false, 0, NULL, steamDir, &si, &pi ) ) + { + Error( "LaunchOldDedicatedServer: Unable to launch old srcds." ); + } + + return true; + } + } + } +#endif + + return false; +} + +//----------------------------------------------------------------------------- +// Purpose: loads the list of available maps into the map list +//----------------------------------------------------------------------------- +void CCreateMultiplayerGameServerPage::LoadMODList() +{ + m_pGameCombo->DeleteAllItems(); + + // add steam games + if (CommandLine()->CheckParm("-steam")) + { + const char *pSteamGamesFilename = "hlds_steamgames.vdf"; + + KeyValues *gamesFile = new KeyValues( pSteamGamesFilename ); + + if ( gamesFile->LoadFromFile( g_pFullFileSystem, pSteamGamesFilename, NULL ) ) + { + for ( KeyValues *kv = gamesFile->GetFirstSubKey(); kv != NULL; kv = kv->GetNextKey() ) + { + const char *pGameDir = kv->GetString( "gamedir", NULL ); + if ( !pGameDir ) + Error( "Mod %s in %s missing 'gamedir'.", kv->GetName(), pSteamGamesFilename ); + + AddMod( pGameDir, pSteamGamesFilename, kv ); + } + } + gamesFile->deleteThis(); + gamesFile = NULL; + } + + + // For backward compatibility, check inside the dedicated server's own directory for mods. + LoadModListInDirectory( "." ); + + // Also, check in SourceMods. + char sourceModsDir[MAX_PATH]; + if ( system()->GetRegistryString( "HKEY_CURRENT_USER\\Software\\Valve\\Steam\\SourceModInstallPath", sourceModsDir, sizeof( sourceModsDir ) ) ) + LoadModListInDirectory( sourceModsDir ); + + m_pGameCombo->ActivateItem(0); +} + + +void CCreateMultiplayerGameServerPage::LoadModListInDirectory( const char *pDirectoryName ) +{ + char searchString[MAX_PATH*2]; + V_strcpy_safe( searchString, pDirectoryName ); + Q_AppendSlash( searchString, sizeof( searchString ) ); + Q_strncat( searchString, "*.*", sizeof( searchString ), COPY_ALL_CHARACTERS ); + + FileFindHandle_t findHandle = NULL; + const char *filename = g_pFullFileSystem->FindFirst( searchString, &findHandle ); + while ( filename ) + { + // add to the mod list + if (filename[0] != '.' && g_pFullFileSystem->FindIsDirectory(findHandle)) + { + char fullFilename[MAX_PATH]; + if ( Q_stricmp( pDirectoryName, "." ) == 0 ) + { + // If we don't do this, then the games in hlds_steamgames.vdf will get listed twice + // since their gamedir is listed as "cstrike" and "hl2mp", not ".\cstrike" or ".\hl2mp". + V_strcpy_safe( fullFilename, filename ); + } + else + { + V_strcpy_safe( fullFilename, pDirectoryName ); + Q_AppendSlash( fullFilename, sizeof( fullFilename ) ); + Q_strncat( fullFilename, filename, sizeof( fullFilename ), COPY_ALL_CHARACTERS ); + } + + LoadPossibleMod( fullFilename ); + } + + filename = g_pFullFileSystem->FindNext(findHandle); + } + g_pFullFileSystem->FindClose(findHandle); +} + + +void CCreateMultiplayerGameServerPage::LoadPossibleMod( const char *pGameDirName ) +{ + char gameInfoFilename[1024]; + Q_snprintf(gameInfoFilename, sizeof(gameInfoFilename) - 1, "%s\\gameinfo.txt", pGameDirName); + if ( !g_pFullFileSystem->FileExists(gameInfoFilename) ) + return; + + // don't want to add single player games to the list + KeyValues *pGameInfo = new KeyValues( "GameInfo" ); + bool loadedFile = pGameInfo->LoadFromFile( g_pFullFileSystem, gameInfoFilename ); + if ( !loadedFile ) + return; + + AddMod( pGameDirName, gameInfoFilename, pGameInfo ); + + pGameInfo->deleteThis(); + pGameInfo = NULL; +} + + +void CCreateMultiplayerGameServerPage::AddMod( const char *pGameDirName, const char *pGameInfoFilename, KeyValues *pGameInfo ) +{ + // Don't re-add something with the same gamedir name (this can happen with games listed in hlds_steamgames.vdf, + // since after the first time a game is run, it'll also have a gameinfo.txt that will be found). + for ( int i=0; i < m_pGameCombo->GetItemCount(); i++ ) + { + if ( !m_pGameCombo->IsItemIDValid(i) ) + continue; + + if ( Q_stricmp( m_pGameCombo->GetItemUserData(i)->GetString("gamedir"), pGameDirName ) == 0 ) + return; + } + + // If this mod supports multiplayer, then we'll add it. + const char *gameType = pGameInfo->GetString( "type", "singleplayer_only" ); + if ( Q_stricmp(gameType, "singleplayer_only") != 0 ) + { + // Validate the gameinfo.txt format.. + KeyValues *pSub = pGameInfo->FindKey( "FileSystem" ); + if ( !pSub ) + Error( "%s missing FileSystem key.", pGameInfoFilename ); + + int iSteamAppId = pSub->GetInt( "SteamAppId", -1 ); + if ( iSteamAppId == -1 ) + Error( "%s missing FileSystem\\SteamAppId key.", pGameInfoFilename ); + +#if !defined( ALLOW_OLD_ENGINE_GAMES ) + // If we're not supporting old games in here and its appid is old, forget about it. + if ( IsEp1EraAppID( iSteamAppId ) ) + return; +#endif + + const char *gameName = pGameInfo->GetString( "game", NULL ); + if ( !gameName ) + Error( "%s missing 'game' key.", pGameInfoFilename ); + + + // add to drop-down combo and mod list + KeyValues *kv = pGameInfo->MakeCopy(); + kv->SetString( "gamedir", pGameDirName ); + + m_pGameCombo->AddItem( gameName, kv ); + + kv->deleteThis(); + kv = NULL; + } +} + + +//----------------------------------------------------------------------------- +// Purpose: loads the list of available maps for the given path into the map list +// Returns: number of maps loaded into the list +//----------------------------------------------------------------------------- +int CCreateMultiplayerGameServerPage::LoadMaps( const char *pszMod ) +{ + // iterate the filesystem getting the list of all the files + // UNDONE: steam wants this done in a special way, need to support that + FileFindHandle_t findHandle = NULL; + char szSearch[256]; + sprintf( szSearch, "%s/maps/*.bsp", pszMod ); + + int iMapsFound = 0; + + const char *pszFilename = g_pFullFileSystem->FindFirst( szSearch, &findHandle ); + + KeyValues *hiddenMaps = NULL; + if ( m_pGameInfo ) + { + hiddenMaps = m_pGameInfo->FindKey( "hidden_maps" ); + } + + while ( pszFilename ) + { + // remove the text 'maps/' and '.bsp' from the file name to get the map name + char mapname[256]; + const char *str = strstr( pszFilename, "maps" ); + if ( str ) + { + V_strcpy_safe( mapname, str + 5 ); // maps + \\ = 5 + } + else + { + V_strcpy_safe( mapname, pszFilename ); + } + + char *ext = strstr( mapname, ".bsp" ); + if ( ext ) + { + *ext = 0; + } + + //!! hack: strip out single player HL maps + // this needs to be specified in a seperate file + if ( ( mapname[0] == 'c' || mapname[0] == 't' ) && mapname[2] == 'a' && mapname[1] >= '0' && mapname[1] <= '5' ) + { + goto nextFile; + } + + // strip out maps that shouldn't be displayed + if ( hiddenMaps ) + { + if ( hiddenMaps->GetInt( mapname, 0 ) ) + { + goto nextFile; + } + } + + iMapsFound++; + + // add to the map list + m_pMapList->AddItem( mapname, NULL ); + + // get the next file + nextFile: + pszFilename = g_pFullFileSystem->FindNext( findHandle ); + } + + g_pFullFileSystem->FindClose( findHandle ); + + return iMapsFound; +} + +//----------------------------------------------------------------------------- +// Purpose: loads the list of available maps into the map list +//----------------------------------------------------------------------------- +void CCreateMultiplayerGameServerPage::LoadMapList() +{ + int iMapsFound = 0; + + // clear the current list (if any) + m_pMapList->DeleteAllItems(); + + Assert( strlen(m_szMod ) > 0); + if ( strlen( m_szMod ) < 1) + { + m_pMapList->SetEnabled( false ); + return; + } + + m_pMapList->SetEnabled( true ); + m_pStartServerButton->SetEnabled( true ); + + if ( CommandLine()->CheckParm( "-steam" ) ) + { + KeyValues *userData = m_pGameCombo->GetActiveItemUserData(); + if ( userData && userData->GetString( "DedicatedServerStartMap", NULL ) ) + { + // set only + m_pMapList->AddItem( userData->GetString( "DedicatedServerStartMap" ), NULL ); + m_pMapList->ActivateItemByRow( 0 ); + m_pMapList->SetEnabled( false ); + return; + } + } + + // Load the maps for the GameDir + iMapsFound += LoadMaps( m_szMod ); + + // If we're using a "fallback_dir" in liblist.gam then include those maps... + const char *pszFallback = GetLiblistFallbackDir( m_szMod ); + if ( pszFallback[0] ) + { + iMapsFound += LoadMaps( pszFallback ); + } + + if ( iMapsFound < 1 ) + { + m_pMapList->SetEnabled( false ); + } + + // set the first item to be selected + m_pMapList->ActivateItemByRow( 0 ); +} + +//----------------------------------------------------------------------------- +// Purpose: returns the name of the map selected from the map combo +//----------------------------------------------------------------------------- +const char *CCreateMultiplayerGameServerPage::GetMapName() +{ + m_pMapList->GetText(m_szMapName, DATA_STR_LENGTH); + return m_szMapName; +} + +//----------------------------------------------------------------------------- +// Purpose: data accessor +//----------------------------------------------------------------------------- +const char *CCreateMultiplayerGameServerPage::GetRconPassword() +{ + return m_szPassword; +} + +//----------------------------------------------------------------------------- +// Purpose: updates "s" with the details of the chosen server to run +//----------------------------------------------------------------------------- +void CCreateMultiplayerGameServerPage::GetServer(serveritem_t &s) +{ + s=m_iServer; + V_strcpy_safe(s.name,m_iServer.name); + V_strcpy_safe(s.rconPassword,m_iServer.rconPassword); + memcpy(s.ip,m_iServer.ip,sizeof(m_iServer.ip)); + memcpy(s.pings,m_iServer.pings,3*sizeof(int)); + V_strcpy_safe(s.gameDir,m_iServer.gameDir); + V_strcpy_safe(s.map,m_iServer.map); + V_strcpy_safe(s.gameDescription,m_iServer.gameDescription); +} + +//----------------------------------------------------------------------------- +// Purpose: Handles changes to combo boxes +//----------------------------------------------------------------------------- +void CCreateMultiplayerGameServerPage::OnTextChanged(Panel *panel) +{ + if (panel == m_pGameCombo) + { + // see if we should update the game name + bool updateHostname = false; + char hostname[256]; + GetControlString("ServerNameEdit", m_szHostName, sizeof(m_szHostName)); + V_sprintf_safe(hostname, "%s dedicated server", m_szGameName); + if (!stricmp(m_szHostName, hostname)) + { + updateHostname = true; + } + + // update the game name + m_pGameCombo->GetText( m_szGameName, sizeof(m_szGameName) ); + + + // Copy the gamedir into m_szMod. + KeyValues *gameData = m_pGameCombo->GetActiveItemUserData(); + if ( !gameData ) + Error( "Missing gameData for active item." ); + + const char *pGameDir = gameData->GetString( "gamedir", NULL ); + if ( !pGameDir ) + Error( "Game %s missing 'gamedir' key.", m_szGameName ); + + V_strcpy_safe( m_szMod, pGameDir ); + + + // re-load the GameInfo KeyValues + if ( m_pGameInfo ) + { + m_pGameInfo->deleteThis(); + } + char liblist[1024]; + Q_snprintf(liblist, sizeof(liblist) - 1, "%s\\gameinfo.txt", m_szMod); + m_pGameInfo = new KeyValues( "GameInfo" ); + m_pGameInfo->LoadFromFile( g_pFullFileSystem, liblist ); + + // redo the hostname with the new game name + if (updateHostname) + { + V_sprintf_safe(hostname, "%s dedicated server", m_szGameName); + SetControlString("ServerNameEdit", hostname); + } + + // reload the list of maps we display + LoadMapList(); + } +} + +#endif // _WIN32 + diff --git a/dedicated/vgui/CreateMultiplayerGameServerPage.h b/dedicated/vgui/CreateMultiplayerGameServerPage.h new file mode 100644 index 0000000..6cabef4 --- /dev/null +++ b/dedicated/vgui/CreateMultiplayerGameServerPage.h @@ -0,0 +1,126 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +// $NoKeywords: $ +//=============================================================================// + +#ifndef CREATEMULTIPLAYERGAMESERVERPAGE_H +#define CREATEMULTIPLAYERGAMESERVERPAGE_H +#ifdef _WIN32 +#pragma once +#endif + +#include <vgui_controls/Frame.h> +#include <vgui_controls/Button.h> +#include <vgui_controls/ComboBox.h> + +//----------------------------------------------------------------------------- +// Purpose: Data describing a single server +//----------------------------------------------------------------------------- +struct serveritem_t +{ + serveritem_t() + { + pings[0] = 0; + pings[1] = 0; + pings[2] = 0; + } + + unsigned char ip[4]; + int port; + int received; + float time; + int ping; // current ping time, derived from pings[] + int pings[3]; // last 3 ping times + bool hadSuccessfulResponse; // server has responded successfully in the past + bool doNotRefresh; // server is marked as not responding and should no longer be refreshed + char gameDir[32]; // current game directory + char map[32]; // current map + char gameDescription[64]; // game description + char name[64]; // server name + int players; + int maxPlayers; + int botPlayers; + bool proxy; + bool password; + bool secure; + bool loadedFromFile; // true if this entry was loaded from file rather than comming from the master + unsigned int serverID; + int listEntryID; + char rconPassword[64]; // the rcon password for this server +}; + +//----------------------------------------------------------------------------- +// Purpose: server options page of the create game server dialog +//----------------------------------------------------------------------------- +class CCreateMultiplayerGameServerPage : public vgui::Frame +{ + DECLARE_CLASS_SIMPLE( CCreateMultiplayerGameServerPage, vgui::Frame ); +public: + CCreateMultiplayerGameServerPage(vgui::Panel *parent, const char *name); + ~CCreateMultiplayerGameServerPage(); + + // returns currently entered information about the server + int GetMaxPlayers() { return m_iMaxPlayers; } + const char *GetPassword() { return m_szPassword; } + const char *GetHostName() { return m_szHostName; } + const char *GetMapName(); + const char *GetModName() { return m_szMod; } + const char *GetGameName() { return m_szGameName; } + void LoadMapList(); + int LoadMaps( const char *pszMod ); + + virtual void OnCommand(const char *cmd); + + virtual void OnResetData(); + + void GetServer(serveritem_t &s); + const char *GetRconPassword(); + +private: + enum { MAX_PLAYERS = 32 }; + enum { DATA_STR_LENGTH = 64 }; + + void LoadConfig(); + void SaveConfig(); + void SetConfig(const char *serverName, const char *rconPassword, int maxPlayers, const char *map, const char *mod, int network, int secure, int port); + + bool LaunchOldDedicatedServer( KeyValues *pGameInfo ); + + //void OnCommand(const char *text); + void LoadMODList(); + void LoadModListInDirectory( const char *pDirectoryName ); + void LoadPossibleMod( const char *pGameDirName ); + void AddMod( const char *pGameDirName, const char *pGameInfoFilename, KeyValues *pGameInfo ); + + bool BadRconChars(const char *pass); + + vgui::ComboBox *m_pGameCombo; + vgui::ComboBox *m_pMapList; + vgui::ComboBox *m_pNumPlayers; + vgui::ComboBox *m_pNetworkCombo; + vgui::Button *m_pStartServerButton; + vgui::Button *m_pCancelButton; + vgui::CheckButton *m_pSecureCheck; + + MESSAGE_FUNC_PTR( OnTextChanged, "TextChanged", panel ); + + serveritem_t m_iServer; + + char m_szHostName[DATA_STR_LENGTH]; + char m_szPassword[DATA_STR_LENGTH]; + char m_szMapName[DATA_STR_LENGTH]; + char m_szMod[DATA_STR_LENGTH]; + char m_szGameName[DATA_STR_LENGTH]; + char m_szExtra[DATA_STR_LENGTH*2]; + int m_iMaxPlayers; + int m_iPort; + + vgui::Panel *m_MainPanel; + KeyValues *m_pSavedData; // data to save away + KeyValues *m_pGameInfo; +}; + + +#endif // CREATEMULTIPLAYERGAMESERVERPAGE_H diff --git a/dedicated/vgui/MainPanel.cpp b/dedicated/vgui/MainPanel.cpp new file mode 100644 index 0000000..f7fc51b --- /dev/null +++ b/dedicated/vgui/MainPanel.cpp @@ -0,0 +1,274 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +// $Workfile: $ +// $Date: $ +// +//----------------------------------------------------------------------------- +// $Log: $ +// +// $NoKeywords: $ +//=============================================================================// +#ifdef _WIN32 +#include <stdio.h> +#include <string.h> +#include <stdarg.h> + +#include <windows.h> +// base vgui interfaces +#include <vgui/vgui.h> +#include <vgui_controls/Panel.h> +#include <vgui/IVGui.h> +#include <vgui/ISurface.h> +#include <vgui/Cursor.h> +#include <vgui_controls/ProgressBox.h> + +#include "filesystem.h" +#include "IAdminServer.h" + +#include "MainPanel.h" +#include <imanageserver.h> +#include "ivguimodule.h" +#include <vgui/IVGui.h> + +// memdbgon must be the last include file in a .cpp file!!! +#include "tier0/memdbgon.h" + +using namespace vgui; + +static CMainPanel *s_InternetDlg = NULL; +CSysModule *g_hAdminServerModule = NULL; +extern IAdminServer *g_pAdminServer; +char *gpszCvars = NULL; + + +void Sys_Sleep_Old( int msec ); + +extern BOOL gbAppHasBeenTerminated; // used to signal the server thread + +//----------------------------------------------------------------------------- +// Purpose: Constructor +//----------------------------------------------------------------------------- +CMainPanel::CMainPanel( ) : Panel(NULL, "CMainPanel") +{ + SetPaintBackgroundEnabled( false ); + SetFgColor( Color( 0,0,0,0 ) ); + m_bStarting = false; + m_flPreviousSteamProgress = 0.0f; + m_pGameServer= NULL; +} + +//----------------------------------------------------------------------------- +// Purpose: Destructor +//----------------------------------------------------------------------------- +CMainPanel::~CMainPanel() +{ + if (gpszCvars) + { + free(gpszCvars); + } + +} + +//----------------------------------------------------------------------------- +// Purpose: Called once to set up +//----------------------------------------------------------------------------- +void CMainPanel::Initialize( ) +{ + s_InternetDlg = this; + m_pGameServer = NULL; + + m_bStarted = false; + m_bIsInConfig = true; + m_bClosing = false; + m_pProgressBox = NULL; + m_hShutdown = NULL; + + MoveToFront(); + + m_pConfigPage = new CCreateMultiplayerGameServerPage(this, "Config"); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void CMainPanel::Open( void ) +{ + m_pConfigPage->SetVisible(true); + m_pConfigPage->MoveToFront(); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void CMainPanel::OnClose() +{ + DoStop(); +} + +//----------------------------------------------------------------------------- +// Purpose: returns a pointer to a static instance of this dialog +//----------------------------------------------------------------------------- +CMainPanel *CMainPanel::GetInstance() +{ + return s_InternetDlg; +} + +//----------------------------------------------------------------------------- +// Purpose: Changes to the console page and starts up the actual server +//----------------------------------------------------------------------------- +void CMainPanel::StartServer(const char *cvars) +{ + surface()->SetCursor(dc_hourglass); + m_pConfigPage->GetServer(s1); + + // hide the config page and close it + m_pConfigPage->SetVisible(false); + m_pConfigPage->Close(); + + gpszCvars = strdup(cvars); + + // show the basic progress box immediately + m_pProgressBox = new ProgressBox("#Start_Server_Loading_Title", "#Server_UpdatingSteamResources", "Starting dedicated server..."); + m_pProgressBox->SetCancelButtonVisible(true); + m_pProgressBox->ShowWindow(); + + // make sure we have all the steam content for this mod + char reslist[_MAX_PATH]; + _snprintf(reslist, sizeof(reslist), "reslists/%s/preload.lst", m_pConfigPage->GetGameName()); + m_hResourceWaitHandle = g_pFullFileSystem->WaitForResources(reslist); + if (!m_hResourceWaitHandle) + { + Assert( 0 ); + } + + m_pProgressBox->SetCancelButtonEnabled(false); + + m_hShutdown = CreateEvent( NULL, TRUE, FALSE, NULL ); + ivgui()->AddTickSignal(GetVPanel()); +} + +//----------------------------------------------------------------------------- +// Purpose: lets us delay the loading of the management screen until the server has started +//----------------------------------------------------------------------------- +void CMainPanel::OnTick() +{ + if (m_hResourceWaitHandle) + { + // see if we've been cancelled + if (!m_pProgressBox.Get() || !m_pProgressBox->IsVisible()) + { + // cancel out + g_pFullFileSystem->CancelWaitForResources(m_hResourceWaitHandle); + m_hResourceWaitHandle = NULL; + DoStop(); + return; + } + + // update resource waiting + bool complete; + float progress; + if (g_pFullFileSystem->GetWaitForResourcesProgress(m_hResourceWaitHandle, &progress, &complete)) + { + vgui::ivgui()->DPrintf2( "progress %.2f %s\n", progress, complete ? "not complete" : "complete" ); + + // don't set the progress if we've jumped straight from 0 to 100% complete + if (!(progress == 1.0f && m_flPreviousSteamProgress == 0.0f)) + { + m_pProgressBox->SetProgress(progress); + m_flPreviousSteamProgress = progress; + } + } + + // This is here because without it, the dedicated server will consume a lot of CPU and it will slow Steam down + // so much that it'll download at 64k instead of 6M. + Sleep( 200 ); + + // see if we're done + if (complete) + { + m_hResourceWaitHandle = NULL; + m_bStarting = true; + m_bIsInConfig = false; + // at this stage in the process the user can no longer cancel + m_pProgressBox->SetCancelButtonEnabled(false); + } + } + + if (m_bStarting) // if we are actively launching the app + { + static int count = 0; + if (WAIT_OBJECT_0 == WaitForSingleObject(m_hShutdown, 10) || count > 5000) + { + if (!m_bStarted) + { + serveritem_t server; + m_pConfigPage->GetServer(server); + ManageServerUIHandle_t managePage = g_pAdminServer->OpenManageServerDialog(server.name, server.gameDir); + m_pGameServer = g_pAdminServer->GetManageServerInterface(managePage); + m_bStarted = true; + + if (m_pProgressBox) + { + m_pProgressBox->Close(); + m_pProgressBox = NULL; + } + } + else // must be stopping the server + { + DoStop(); + } + + surface()->SetCursor(dc_user); + m_bStarting = false; + ResetEvent(m_hShutdown); + } + else + { + count++; + } + } +} + +//----------------------------------------------------------------------------- +// Purpose: stops VGUI and kills any progress dialog we may have been displaying +//----------------------------------------------------------------------------- +void CMainPanel::DoStop() +{ + surface()->SetCursor(dc_user); + + m_bStarted = false; + m_bClosing = true; + + if (m_pProgressBox) + { + m_pProgressBox->Close(); + m_pProgressBox = NULL; + } + + ivgui()->Stop(); +} + +//----------------------------------------------------------------------------- +// Purpose: Pushes text into the console +//----------------------------------------------------------------------------- +void CMainPanel::AddConsoleText(const char *msg) +{ + if (m_pGameServer) + { + m_pGameServer->AddToConsole(msg); + } +} + +//----------------------------------------------------------------------------- +// Purpose: Message map +//----------------------------------------------------------------------------- +MessageMapItem_t CMainPanel::m_MessageMap[] = +{ + MAP_MESSAGE( CMainPanel, "Quit", OnClose ), +}; + +IMPLEMENT_PANELMAP(CMainPanel, BaseClass); + +#endif // _WIN32 diff --git a/dedicated/vgui/MainPanel.h b/dedicated/vgui/MainPanel.h new file mode 100644 index 0000000..04f558e --- /dev/null +++ b/dedicated/vgui/MainPanel.h @@ -0,0 +1,89 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +// $Workfile: $ +// $Date: $ +// $NoKeywords: $ +//===========================================================================// +#ifndef CMAINPANEL_H +#define CMAINPANEL_H +#ifdef _WIN32 +#pragma once +#endif + +#include <vgui_controls/Frame.h> +#include <vgui_controls/Panel.h> +#include <vgui_controls/ListPanel.h> +#include <vgui_controls/PHandle.h> +#include "utlvector.h" + +//#include <GamePanelInfo.h> + +#include "imanageserver.h" +//#include "gameserver.h" +#include "CreateMultiplayerGameServerPage.h" + +class IAdminServer; + +//----------------------------------------------------------------------------- +// Purpose: Root panel for dedicated server GUI +//----------------------------------------------------------------------------- +class CMainPanel : public vgui::Panel +{ +public: + // Construction/destruction + CMainPanel( ); + virtual ~CMainPanel(); + + virtual void Initialize( ); + + // displays the dialog, moves it into focus, updates if it has to + virtual void Open( void ); + + // returns a pointer to a static instance of this dialog + // valid for use only in sort functions + static CMainPanel *GetInstance(); + virtual void StartServer(const char *cvars); + + void ActivateBuildMode(); + + void *GetShutdownHandle() { return m_hShutdown; } + + void AddConsoleText(const char *msg); + + bool Stopping() { return m_bClosing; } + + bool IsInConfig() { return m_bIsInConfig; } + +private: + + // called when dialog is shut down + virtual void OnClose(); + virtual void OnTick(); + void DoStop(); + + // GUI elements + IManageServer *m_pGameServer; + + // the popup menu + vgui::DHANDLE<vgui::ProgressBox> m_pProgressBox; + CCreateMultiplayerGameServerPage *m_pConfigPage; + + // Event that lets the thread tell the main window it shutdown + void *m_hShutdown; + + bool m_bStarting; // whether the server is currently starting + bool m_bStarted; // whether the server has been started or not + bool m_bClosing; // whether we are shutting down + bool m_bIsInConfig; + serveritem_t s1; + int m_hResourceWaitHandle; + float m_flPreviousSteamProgress; + + typedef vgui::Panel BaseClass; + DECLARE_PANELMAP(); + +}; + +#endif // CMAINPANEL_H
\ No newline at end of file diff --git a/dedicated/vgui/vguihelpers.cpp b/dedicated/vgui/vguihelpers.cpp new file mode 100644 index 0000000..11cf33e --- /dev/null +++ b/dedicated/vgui/vguihelpers.cpp @@ -0,0 +1,187 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//===========================================================================// +#ifdef _WIN32 +#include <windows.h> +#include <direct.h> + +// includes for the VGUI version +#include <vgui_controls/Panel.h> +#include <vgui_controls/Controls.h> +#include <vgui/ISystem.h> +#include <vgui/IVGui.h> +#include <vgui/IPanel.h> +#include "filesystem.h" +#include <vgui/ILocalize.h> +#include <vgui/IScheme.h> +#include <vgui/ISurface.h> +#include <IVGuiModule.h> + +#include "vgui/MainPanel.h" +#include "IAdminServer.h" + +// memdbgon must be the last include file in a .cpp file!!! +#include "tier0/memdbgon.h" + + +static CMainPanel *g_pMainPanel = NULL; // the main panel to show +static CSysModule *g_hAdminServerModule; +IAdminServer *g_pAdminServer = NULL; +static IVGuiModule *g_pAdminVGuiModule = NULL; + +void* DedicatedFactory(const char *pName, int *pReturnCode); + + +//----------------------------------------------------------------------------- +// Purpose: Starts up the VGUI system and loads the base panel +//----------------------------------------------------------------------------- +int StartVGUI( CreateInterfaceFn dedicatedFactory ) +{ + // the "base dir" so we can scan mod name + g_pFullFileSystem->AddSearchPath(".", "MAIN"); + // the main platform dir + g_pFullFileSystem->AddSearchPath( "platform", "PLATFORM", PATH_ADD_TO_HEAD); + + vgui::ivgui()->SetSleep(false); + + // find our configuration directory + char szConfigDir[512]; + const char *steamPath = getenv("SteamInstallPath"); + if (steamPath) + { + // put the config dir directly under steam + Q_snprintf(szConfigDir, sizeof(szConfigDir), "%s/config", steamPath); + } + else + { + // we're not running steam, so just put the config dir under the platform + Q_strncpy( szConfigDir, "platform/config", sizeof(szConfigDir)); + } + g_pFullFileSystem->CreateDirHierarchy("config", "PLATFORM"); + g_pFullFileSystem->AddSearchPath(szConfigDir, "CONFIG", PATH_ADD_TO_HEAD); + + // initialize the user configuration file + vgui::system()->SetUserConfigFile("DedicatedServerDialogConfig.vdf", "CONFIG"); + + // Init the surface + g_pMainPanel = new CMainPanel( ); + g_pMainPanel->SetVisible(true); + + vgui::surface()->SetEmbeddedPanel(g_pMainPanel->GetVPanel()); + + // load the scheme + vgui::scheme()->LoadSchemeFromFile("Resource/SourceScheme.res", NULL); + + // localization + g_pVGuiLocalize->AddFile( "Resource/platform_%language%.txt" ); + g_pVGuiLocalize->AddFile( "Resource/vgui_%language%.txt" ); + g_pVGuiLocalize->AddFile( "Admin/server_%language%.txt" ); + + // Start vgui + vgui::ivgui()->Start(); + + // load the module + g_pFullFileSystem->GetLocalCopy("bin/AdminServer.dll"); + g_hAdminServerModule = g_pFullFileSystem->LoadModule("AdminServer"); + Assert(g_hAdminServerModule != NULL); + CreateInterfaceFn adminFactory = NULL; + + if (!g_hAdminServerModule) + { + vgui::ivgui()->DPrintf2("Admin Error: module version (Admin/AdminServer.dll, %s) invalid, not loading\n", IMANAGESERVER_INTERFACE_VERSION ); + } + else + { + // make sure we get the right version + adminFactory = Sys_GetFactory(g_hAdminServerModule); + g_pAdminServer = (IAdminServer *)adminFactory(ADMINSERVER_INTERFACE_VERSION, NULL); + g_pAdminVGuiModule = (IVGuiModule *)adminFactory("VGuiModuleAdminServer001", NULL); + Assert(g_pAdminServer != NULL); + Assert(g_pAdminVGuiModule != NULL); + if (!g_pAdminServer || !g_pAdminVGuiModule) + { + vgui::ivgui()->DPrintf2("Admin Error: module version (Admin/AdminServer.dll, %s) invalid, not loading\n", IMANAGESERVER_INTERFACE_VERSION ); + } + } + + // finish initializing admin module + g_pAdminVGuiModule->Initialize( &dedicatedFactory, 1 ); + g_pAdminVGuiModule->PostInitialize(&adminFactory, 1); + g_pAdminVGuiModule->SetParent( g_pMainPanel->GetVPanel() ); + + // finish setting up main panel + g_pMainPanel->Initialize( ); + g_pMainPanel->Open(); + + return 0; +} + + + +//----------------------------------------------------------------------------- +// Purpose: Shuts down the VGUI system +//----------------------------------------------------------------------------- +void StopVGUI() +{ + SetEvent(g_pMainPanel->GetShutdownHandle()); + + delete g_pMainPanel; + g_pMainPanel = NULL; + + if (g_hAdminServerModule) + { + g_pAdminVGuiModule->Shutdown( ); + Sys_UnloadModule(g_hAdminServerModule); + } +} + +//----------------------------------------------------------------------------- +// Purpose: Run a single VGUI frame +//----------------------------------------------------------------------------- +void RunVGUIFrame() +{ + vgui::ivgui()->RunFrame(); +} + + +bool VGUIIsStopping() +{ + return g_pMainPanel->Stopping(); +} + + +bool VGUIIsRunning() +{ + return vgui::ivgui()->IsRunning(); +} + +bool VGUIIsInConfig() +{ + return g_pMainPanel->IsInConfig(); +} + +void VGUIFinishedConfig() +{ + Assert( g_pMainPanel ); + if(g_pMainPanel) // engine is loaded, pass the message on + { + SetEvent(g_pMainPanel->GetShutdownHandle()); + } +} + +void VGUIPrintf( const char *msg ) +{ + if ( !g_pMainPanel || VGUIIsInConfig() || VGUIIsStopping() ) + { + OutputDebugStringA( msg ); + } + else if ( g_pMainPanel ) + { + g_pMainPanel->AddConsoleText( msg ); + } +} + +#endif // _WIN32 + diff --git a/dedicated/vgui/vguihelpers.h b/dedicated/vgui/vguihelpers.h new file mode 100644 index 0000000..e29203e --- /dev/null +++ b/dedicated/vgui/vguihelpers.h @@ -0,0 +1,26 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//===========================================================================// + +#ifndef VGUIHELPERS_H +#define VGUIHELPERS_H + +#ifdef _WIN32 +#pragma once +#endif + +#include "tier1/interface.h" + +int StartVGUI( CreateInterfaceFn dedicatedFactory ); +void StopVGUI(); +void RunVGUIFrame(); +bool VGUIIsRunning(); +bool VGUIIsStopping(); +bool VGUIIsInConfig(); +void VGUIFinishedConfig(); +void VGUIPrintf( const char *msg ); + +#endif // VGUIHELPERS_H + diff --git a/dedicated/vgui/vguihelpers_linux.cpp b/dedicated/vgui/vguihelpers_linux.cpp new file mode 100644 index 0000000..4b8f474 --- /dev/null +++ b/dedicated/vgui/vguihelpers_linux.cpp @@ -0,0 +1,39 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +//=============================================================================// +#include "interface.h" + +bool InitializeVGui(CreateInterfaceFn *factorylist, int factorycount) +{ +} + +int StartVGUI() +{ +} + +void StopVGUI() +{ +} + +void RunVGUIFrame() +{ +} + +bool VGUIIsRunning() +{ +} + +bool VGUIIsStopping() +{ +} + +bool VGUIIsInConfig() +{ +} + +void VGUIFinishedConfig() +{ +} + |