source-sdk-2013/src/game/shared/tf/tf_match_description.h
2025-02-18 18:51:37 +00:00

207 lines
12 KiB
C++

//========= Copyright Valve Corporation, All rights reserved. ============//
#ifndef TF_MATCH_DESCRIPTION_H
#define TF_MATCH_DESCRIPTION_H
#ifdef _WIN32
#pragma once
#endif
#include "tf_matchmaking_shared.h"
#ifdef CLIENT_DLL
#include "tf_progression_description.h"
#include "basemodel_panel.h"
#endif // CLIENT_DLL
#ifdef GAME_DLL
// Can't foward declare CMatchInfo::PlayerMatchData_t because C++. Bummer.
#include "tf_gc_server.h"
#endif
class CSOTFLadderData;
class IProgressionDesc;
class IMatchGroupDescription;
const IMatchGroupDescription* GetMatchGroupDescription( const ETFMatchGroup& eGroup );
void RegisterMatchDesc( const ETFMatchGroup& eGroup, const IMatchGroupDescription* pDesc );
class CMatchDescRegister
{
public:
CMatchDescRegister( ETFMatchGroup eGroup, const IMatchGroupDescription* pDesc ) { RegisterMatchDesc( eGroup, pDesc ); }
};
#define REGISTER_MATCH_GROUP_TYPE( eGroup, pDesc ) CMatchDescRegister g_##eGroup##ConvFunc( eGroup, pDesc );
enum EMatchType_t
{
MATCH_TYPE_NONE = 0,
MATCH_TYPE_MVM,
MATCH_TYPE_COMPETITIVE,
MATCH_TYPE_CASUAL
};
class IMatchGroupDescription
{
public:
IMatchGroupDescription( ETFMatchGroup eMatchGroup );
#ifdef CLIENT_DLL
virtual bool BGetRoundStartBannerParameters( int& nSkin, int& nBodyGroup ) const = 0;
virtual bool BGetRoundDoorParameters( int& nSkin, int& nLogoBodyGroup ) const = 0;
virtual const char *GetMapLoadBackgroundOverride( bool bWideScreen ) const = 0;
virtual void SetupBadgePanel( CBaseModelPanel *pModelPanel, const LevelInfo_t& level, const CSteamID& steamID, bool bInPlacement ) const;
bool BPlayerIsInPlacement( CSteamID steamID ) const;
bool BLocalPlayerIsInPlacement() const;
int GetNumPlacementMatchesToGo( CSteamID steamID ) const;
struct PlayListData_t
{
const char* m_pszPlayListButtonToken;
const char* m_pszPlayListDescToken;
const char* m_pszPlayListBackground;
const char* m_pszSidePanelTitle;
const char* m_pszSidePanelDesc;
const char* m_pszSidePanelImage;
};
virtual const PlayListData_t* GetPlayListEntryData() const { return NULL; };
#endif
#ifdef GAME_DLL
// ! Check return, we might fail to setup
virtual bool InitServerSettingsForMatch( const CTFGSLobby* pLobby ) const;
virtual void InitGameRulesSettings() const = 0;
virtual void InitGameRulesSettingsPostEntity() const = 0;
virtual void PostMatchClearServerSettings() const = 0;
virtual bool ShouldRequestLateJoin() const = 0;
virtual bool BMatchIsSafeToLeaveForPlayer( const CMatchInfo* pMatchInfo, const CMatchInfo::PlayerMatchData_t *pMatchPlayer ) const = 0;
virtual bool BPlayWinMusic( int nWinningTeam, bool bGameOver ) const = 0;
#endif
// Accessors for param values
inline int GetMatchSize() const { return m_pmm_match_group_size->GetInt(); }
inline bool BShouldAutomaticallyRequeueOnMatchEnd() const { return m_bAutomaticallyRequeueAfterMatchEnds; }
inline bool BUsesMapVoteAfterMatchEnds() const { return m_bUsesMapVoteOnRoundEnd; }
inline bool BScramblesTeamsOnRollingMatch() const { return m_bScramblesTeamsOnRollingMatch; }
inline bool BUsesXP() const { return m_bUsesXP; }
inline bool BUsesDashboard() const { return m_bUsesDashboardOnRoundEnd; }
inline bool BUsesStrictMatchmakerScoring() const { return m_bStrictMatchmakerScoring; }
inline bool BRequiresCompleteMatches() const { return m_bRequireCompleteMatch; }
inline const char* GetNameLocToken() const { return m_pszModeNameLocToken; }
inline const char* GetRichPresenceLocToken() const { return m_pszRichPresenceLocToken; }
inline bool BAllowsPartyJoins() const { return m_bAllowPartyJoins; }
inline bool BAllowsPartySpectate() const { return m_bAllowPartySpectate; }
inline bool BAllowsQuestProgress() const { return m_bContractProgressAllowed; }
inline EMMPenaltyPool GetPenaltyPool() const { return m_ePenaltyPool; }
inline float GetRequiredMatchmakingScore() const { return m_pmm_required_score->GetFloat(); } // TODO: What if no m_pmm_required_score?
inline bool BSupportLowPriorityQueue() const { return m_bSupportsLowPriorityQueue; }
inline EMatchMode GetLateJoinMode() const { return m_eLateJoinMode; }
inline EMatchType_t GetMatchType() const { return m_eMatchType; }
inline bool BUsesFixedWeaponSpread() const { return m_bFixedWeaponSpread; }
inline bool BUsesAutoBalance() const { return m_bUseAutoBalance; }
inline bool BUsesAutoReady() const { return m_bAutoReady; }
inline bool BUsesPreRoundDoors() const { return m_bShowPreRoundDoors; }
inline bool BUsesPostRoundDoors() const { return m_bShowPostRoundDoors; }
inline bool BDistributePerformanceMedals() const { return m_bDistributePerformanceMedals; }
inline bool BUsesMatchHUD() const { return m_bUseMatchHud; }
inline bool BAllowDrawingAtMatchHistory() const { return m_bAllowDrawingAtMatchSummary; }
inline bool BUseMatchSummaryStage() const { return m_bUseMatchSummaryStage; }
inline const char* GetMatchEndKickWarning() const { return m_pszMatchEndKickWarning; }
inline bool BAllowTeamChange() const { return m_bAllowTeamChange; }
inline bool BAllowSpectatorModeChange() const { return m_bAllowSpecModeChange; }
inline bool BUsesRandomCrits() const { return m_bRandomWeaponCrits; }
inline bool BForceClientSettings() const { return m_bForceClientSettings; }
inline const char* GetMatchStartSound() const { return m_pszMatchStartSound; }
inline int GetNumWinsToExitPlacement() const { return m_nNumWinsToExitPlacement; }
inline int GetNumPlacementMatchesPerDay() const { return m_nNumPlacementMatchesPerDay; }
inline bool BUsesPlacementMatches() const { return m_nNumWinsToExitPlacement > 0; }
inline EMMRating GetCurrentDisplayRating() const { return m_eCurrentDisplayRating; }
inline EMMRating GetLastAckdDisplayRating() const { return m_eLastAckdDisplayRating; }
inline EMMRating GetCurrentDisplayRank() const { return m_eCurrentDisplayRank; }
inline EMMRating GetLastAckdDisplayRank() const { return m_eLastAckdDisplayRank; }
inline bool BUsesStickyRanks() const { return m_bUsesStickyRanks; }
inline bool BUsesStrictAbandons() const { return m_bUsesStrictAbandons; }
inline bool BRequiresCompetitiveAccess() const { return m_bRequiresCompetitiveAccess; }
inline EMatchGroupLeaderboard GetLeaderboard() const { return m_eLeaderboard; }
inline bool BUsesStrictSpectatorRules() const { return m_bUsesStrictSpectatorRules; }
// Meta-permissions that are based on other set flags
//
// Only match-vote modes need this ability right now
inline bool BCanServerRequestNewMatchForLobby() const { return BUsesMapVoteAfterMatchEnds(); }
// Auto-balance and anything that is allowed to roll new match lobbies needs to have this ability (for speculative
// matches if the GC is unavailable). It should be possible to add a mode where we do rolling matches, but only
// when the GC is responding, which would not need the unilateral-team-assignment ability
inline bool BCanServerChangeMatchPlayerTeams() const { return BCanServerRequestNewMatchForLobby() || m_bUseAutoBalance; }
inline bool BIsTrustedServersOnly() const { return m_bTrustedServersOnly; }
const ETFMatchGroup m_eMatchGroup;
const IProgressionDesc* m_pProgressionDesc;
protected:
bool m_bActive = false;
EMatchMode m_eLateJoinMode = eMatchMode_Invalid;
EMMPenaltyPool m_ePenaltyPool = eMMPenaltyPool_Invalid;
bool m_bUsesSkillRatings = false;
bool m_bSupportsLowPriorityQueue = false;
const ConVar* m_pmm_required_score = nullptr;
bool m_bUseMatchHud = false;
const char* m_pszExecFileName = nullptr;
const ConVar* m_pmm_match_group_size = nullptr;
const ConVar* m_pmm_match_group_size_minimum = nullptr; // Optional
bool m_bShowPreRoundDoors = true;
bool m_bShowPostRoundDoors = true;
const char* m_pszMatchEndKickWarning = nullptr;
const char* m_pszMatchStartSound = nullptr;
bool m_bAutoReady = false;
bool m_bUseMatchSummaryStage = false;
bool m_bDistributePerformanceMedals = false;
bool m_bUseFirstBlood = false;
bool m_bUseReducedBonusTime = false;
bool m_bUseAutoBalance = false;
bool m_bAllowTeamChange = false;
bool m_bRandomWeaponCrits = true;
bool m_bFixedWeaponSpread = false;
// If we should not allow match to complete without a complete set of players.
bool m_bRequireCompleteMatch = true;
bool m_bTrustedServersOnly = true;
bool m_bForceClientSettings = false;
bool m_bAllowDrawingAtMatchSummary = false;
bool m_bAllowSpecModeChange = false;
bool m_bAutomaticallyRequeueAfterMatchEnds = false;
bool m_bUsesMapVoteOnRoundEnd = false;
bool m_bScramblesTeamsOnRollingMatch = false;
bool m_bUsesXP = false;
bool m_bUsesDashboardOnRoundEnd = true;
bool m_bUsesSurveys = false;
// Be strict about finding quality matches, for more-competitive matchgroups that want to prioritize match quality
// over speed.
bool m_bStrictMatchmakerScoring = false;
const char* m_pszModeNameLocToken = nullptr;
// This has to be one of the TF_RichPresence_ values, because they must be propagated to steam
const char* m_pszRichPresenceLocToken = nullptr;
bool m_bAllowPartyJoins = false;
bool m_bAllowPartySpectate = false;
bool m_bContractProgressAllowed = false;
EMatchType_t m_eMatchType = MATCH_TYPE_NONE;
int m_nNumWinsToExitPlacement = 0;
int m_nNumPlacementMatchesPerDay = 0;
EMMRating m_eCurrentDisplayRating = k_nMMRating_Invalid;
EMMRating m_eLastAckdDisplayRating = k_nMMRating_Invalid;
EMMRating m_eCurrentDisplayRank = k_nMMRating_Invalid;
EMMRating m_eLastAckdDisplayRank = k_nMMRating_Invalid;
bool m_bUsesStickyRanks = false;
// Whether or not abandoning a match will incur a penalty. Also used by the client to choose when to show certain
// warnings about abandons.
bool m_bUsesStrictAbandons = false;
bool m_bRequiresCompetitiveAccess = false;
// If set, update this leaderboard on match results. Must provide BuildLeaderboardValue above.
EMatchGroupLeaderboard m_eLeaderboard = k_eMatchGroupLeaderboard_Invalid;
bool m_bUsesStrictSpectatorRules = false;
};
#endif //TF_MATCH_DESCRIPTION_H