aboutsummaryrefslogtreecommitdiff
path: root/Northstar.CustomServers/mod/scripts/vscripts/gamemodes/_gamemode_lts.nut
blob: 8999231d353482abc67fe971bde3fd16261892c3 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
untyped
global function GamemodeLts_Init

struct {
	entity lastDamageInfoVictim
	entity lastDamageInfoAttacker
	int lastDamageInfoMethodOfDeath
	float lastDamageInfoTime
	
	bool shouldDoHighlights
	
	table< entity, int > pilotstreak
} file

void function GamemodeLts_Init()
{
	// gamemode settings
	SetShouldUsePickLoadoutScreen( true )
	SetSwitchSidesBased( true )
	SetRoundBased( true )
	SetRespawnsEnabled( false )
	Riff_ForceSetEliminationMode( eEliminationMode.PilotsTitans )
	Riff_ForceSetSpawnAsTitan( eSpawnAsTitan.Always )
	SetShouldUseRoundWinningKillReplay( true )
	SetRoundWinningKillReplayKillClasses( true, true ) // both titan and pilot kills are tracked
	ScoreEvent_SetupEarnMeterValuesForTitanModes()
	SetLoadoutGracePeriodEnabled( false )
	FlagSet( "ForceStartSpawn" )

	AddCallback_OnPilotBecomesTitan( RefreshThirtySecondWallhackHighlight )
	AddCallback_OnTitanBecomesPilot( RefreshThirtySecondWallhackHighlight )
	
	SetTimeoutWinnerDecisionFunc( CheckTitanHealthForDraw )
	TrackTitanDamageInPlayerGameStat( PGS_ASSAULT_SCORE )
	
	ClassicMP_SetCustomIntro( ClassicMP_DefaultNoIntro_Setup, ClassicMP_DefaultNoIntro_GetLength() )
	ClassicMP_ForceDisableEpilogue( true )
	AddCallback_GameStateEnter( eGameState.Playing, WaitForThirtySecondsLeft )
	
	AddCallback_OnClientConnected( SetupPlayerLTSChallenges ) //Just to make up the Match Goals tracking
	AddCallback_OnClientDisconnected( RemovePlayerLTSChallenges ) //Safety removal of data to prevent crashes
	AddCallback_OnPlayerKilled( LTSChallengeForPlayerKilled )
}

void function SetupPlayerLTSChallenges( entity player )
{
	file.pilotstreak[ player ] <- 0
}

void function RemovePlayerLTSChallenges( entity player )
{
	if( player in file.pilotstreak )
		delete file.pilotstreak[ player ]
}

void function LTSChallengeForPlayerKilled( entity victim, entity attacker, var damageInfo )
{
	if ( victim == attacker || !attacker.IsPlayer() || GetGameState() != eGameState.Playing )
		return
	
	if ( victim.IsPlayer() && attacker in file.pilotstreak )
	{
		file.pilotstreak[attacker]++
		if( file.pilotstreak[attacker] >= 2 && !HasPlayerCompletedMeritScore( attacker ) )
		{
			AddPlayerScore( attacker, "ChallengeLTS" )
			SetPlayerChallengeMeritScore( attacker )
		}
	}
}

void function WaitForThirtySecondsLeft()
{
	thread WaitForThirtySecondsLeftThreaded()
}

void function WaitForThirtySecondsLeftThreaded()
{
	svGlobal.levelEnt.EndSignal( "RoundEnd" ) // end this on round end
	
	float endTime = expect float ( GetServerVar( "roundEndTime" ) )
	
	// wait until 30sec left 
	wait ( endTime - 30 ) - Time()
	PlayMusicToAll( eMusicPieceID.LEVEL_LAST_MINUTE )
	
	foreach ( entity player in GetPlayerArray() )
	{	
		// warn there's 30 seconds left
		Remote_CallFunction_NonReplay( player, "ServerCallback_LTSThirtySecondWarning" )
		
		// do initial highlight
		RefreshThirtySecondWallhackHighlight( player, null )
	}
}

void function RefreshThirtySecondWallhackHighlight( entity player, entity titan )
{
	if ( TimeSpentInCurrentState() < expect float ( GetServerVar( "roundEndTime" ) ) - 30.0 )
		return
		
	Highlight_SetEnemyHighlight( player, "enemy_sonar" ) // i think this needs a different effect, this works for now tho
		
	if ( player.GetPetTitan() != null )
		Highlight_SetEnemyHighlight( player.GetPetTitan(), "enemy_sonar" )
}

int function CheckTitanHealthForDraw()
{
	int militiaTitans
	int imcTitans
	
	float militiaHealth
	float imcHealth
	
	foreach ( entity titan in GetTitanArray() )
	{
		if ( titan.GetTeam() == TEAM_MILITIA )
		{
			// doomed is counted as 0 health
			militiaHealth += titan.GetTitanSoul().IsDoomed() ? 0.0 : GetHealthFrac( titan )
			militiaTitans++
		}
		else
		{
			// doomed is counted as 0 health in this
			imcHealth += titan.GetTitanSoul().IsDoomed() ? 0.0 : GetHealthFrac( titan )
			imcTitans++
		}
	}
	
	// note: due to how stuff is set up rn, there's actually no way to do win/loss reasons outside of a SetWinner call, i.e. not in timeout winner decision
	// as soon as there is, strings in question are "#GAMEMODE_TITAN_TITAN_ADVANTAGE" and "#GAMEMODE_TITAN_TITAN_DISADVANTAGE"
	
	if ( militiaTitans != imcTitans )
		return militiaTitans > imcTitans ? TEAM_MILITIA : TEAM_IMC
	else if ( militiaHealth != imcHealth )
		return militiaHealth > imcHealth ? TEAM_MILITIA : TEAM_IMC
		
	return TEAM_UNASSIGNED
}