@@ -25,6 +25,15 @@ namespace NewMod.Patches
2525{
2626 public static class EndGamePatch
2727 {
28+ public static bool EndGameTriggered = false ;
29+
30+ [ RegisterEvent ]
31+ public static void OnGameStart ( RoundStartEvent evt )
32+ {
33+ EndGameTriggered = false ;
34+ EndGameResult . CachedWinners . Clear ( ) ;
35+ }
36+
2837 [ RegisterEvent ]
2938 public static void OnGameEnd ( GameEndEvent evt )
3039 {
@@ -68,6 +77,7 @@ public static void OnGameEnd(GameEndEvent evt)
6877 {
6978 poolablePlayer . SetFlipX ( i % 2 == 0 ) ;
7079 }
80+
7181 poolablePlayer . UpdateFromPlayerOutfit (
7282 playerData . Outfit ,
7383 PlayerMaterial . MaskType . None ,
@@ -151,6 +161,7 @@ public static void OnGameEnd(GameEndEvent evt)
151161 endGameManager . WinText . transform . position . y - 0.5f ,
152162 endGameManager . WinText . transform . position . z ) ;
153163 customWinTextObject . transform . localScale = new Vector3 ( 0.7f , 0.7f , 1f ) ;
164+
154165 var customWinTextComponent = customWinTextObject . GetComponent < TMPro . TMP_Text > ( ) ;
155166 customWinTextComponent . text = customWinText ;
156167 customWinTextComponent . color = customWinColor ;
@@ -173,6 +184,7 @@ public static string GetRoleName(CachedPlayerData playerData, out Color roleColo
173184 {
174185 return $ "{ newmodRole . RoleName } \n <size=65%>{ Utils . GetFactionDisplay ( ( INewModRole ) customRole ) } </size>";
175186 }
187+
176188 return customRole . RoleName ;
177189 }
178190 else
@@ -214,6 +226,20 @@ private static Color GetRoleColor(RoleTypes roleType)
214226 return Color . white ;
215227 }
216228 }
229+
230+ public static bool EndCustomGame ( GameOverReason reason , Action winners = null )
231+ {
232+ if ( EndGameTriggered ) return true ;
233+ if ( EndGameResult . CachedWinners . Count > 0 ) return true ;
234+
235+ EndGameTriggered = true ;
236+
237+ EndGameResult . CachedWinners . Clear ( ) ;
238+ winners ? . Invoke ( ) ;
239+
240+ GameManager . Instance . RpcEndGame ( reason , false ) ;
241+ return true ;
242+ }
217243 }
218244
219245 [ HarmonyPatch ( typeof ( LogicGameFlowNormal ) , nameof ( LogicGameFlowNormal . CheckEndCriteria ) ) ]
@@ -222,7 +248,10 @@ public static class CheckGameEndPatch
222248 public static bool Prefix ( ShipStatus __instance )
223249 {
224250 if ( DestroyableSingleton < TutorialManager > . InstanceExists ) return true ;
251+ if ( ! AmongUsClient . Instance . AmHost ) return true ;
225252 if ( Time . timeSinceLevelLoad < 2f ) return true ;
253+ if ( EndGamePatch . EndGameTriggered ) return false ;
254+
226255 if ( CheckForEndGameFaction < WraithCaller > ( __instance , ( GameOverReason ) NewModEndReasons . WraithCallerWin ) ) return false ;
227256 if ( CheckForEndGameFaction < Shade > ( __instance , ( GameOverReason ) NewModEndReasons . ShadeWin ) ) return false ;
228257 if ( CheckForEndGameFaction < PulseBlade > ( __instance , ( GameOverReason ) NewModEndReasons . PulseBladeWin ) ) return false ;
@@ -231,18 +260,22 @@ public static bool Prefix(ShipStatus __instance)
231260 if ( CheckEndGameForRole < SpecialAgent > ( __instance , ( GameOverReason ) NewModEndReasons . SpecialAgentWin ) ) return false ;
232261 if ( CheckEndGameForRole < Prankster > ( __instance , ( GameOverReason ) NewModEndReasons . PranksterWin , 3 ) ) return false ;
233262 if ( CheckEndGameForRole < EnergyThief > ( __instance , ( GameOverReason ) NewModEndReasons . EnergyThiefWin ) ) return false ;
263+ if ( CheckEndGameForRole < InjectorRole > ( __instance , ( GameOverReason ) NewModEndReasons . InjectorWin ) ) return false ;
264+
234265 return true ;
235266 }
267+
236268 public static bool CheckForEndGameFaction < TFaction > ( ShipStatus __instance , GameOverReason winReason , int maxCount = 1 ) where TFaction : INewModRole
237269 {
238270 var players = PlayerControl . AllPlayerControls . ToArray ( )
239- . Where ( p => p . Data . Role is TFaction )
240- . Take ( maxCount )
241- . ToList ( ) ;
271+ . Where ( p => p . Data . Role is TFaction )
272+ . Take ( maxCount )
273+ . ToList ( ) ;
242274
243275 foreach ( var player in players )
244276 {
245277 bool shouldEndGame = false ;
278+ Action extraWinners = null ;
246279
247280 if ( typeof ( TFaction ) == typeof ( PulseBlade ) )
248281 {
@@ -260,51 +293,58 @@ public static bool CheckForEndGameFaction<TFaction>(ShipStatus __instance, GameO
260293 shouldEndGame = true ;
261294 }
262295 }
296+
263297 if ( typeof ( TFaction ) == typeof ( Tyrant ) )
264298 {
265299 if ( Tyrant . ApexThroneReady && Tyrant . ApexThroneOutcomeSet )
266300 {
267301 shouldEndGame = true ;
268302
269- var tyrantRole = player . Data . Role as Tyrant ;
270- byte champId = tyrantRole . GetChampion ( ) ;
271- var champion = Utils . PlayerById ( champId ) ;
303+ extraWinners = ( ) =>
304+ {
305+ var tyrantRole = player . Data . Role as Tyrant ;
306+ byte champId = tyrantRole . GetChampion ( ) ;
307+ var champion = Utils . PlayerById ( champId ) ;
272308
273- bool championWin = Tyrant . Outcome == Tyrant . ThroneOutcome . ChampionSideWin ;
309+ bool championWin = Tyrant . Outcome == Tyrant . ThroneOutcome . ChampionSideWin ;
274310
275- if ( champion && championWin )
276- {
277- EndGameResult . CachedWinners . Add ( new ( champion . Data ) ) ;
278- }
311+ if ( champion && championWin )
312+ {
313+ EndGameResult . CachedWinners . Add ( new ( champion . Data ) ) ;
314+ }
315+ } ;
279316 }
280317 }
318+
281319 if ( typeof ( TFaction ) == typeof ( WraithCaller ) )
282320 {
283321 int required = ( int ) OptionGroupSingleton < WraithCallerOptions > . Instance . RequiredNPCsToSend ;
284322 int current = WraithCallerUtilities . GetKillsNPC ( player . PlayerId ) ;
285323 shouldEndGame = current >= required ;
286324 }
325+
287326 if ( typeof ( TFaction ) == typeof ( Shade ) )
288327 {
289328 Shade . ShadeKills . TryGetValue ( player . PlayerId , out var count ) ;
290329 int required = ( int ) OptionGroupSingleton < ShadeOptions > . Instance . RequiredKills ;
291330 shouldEndGame = count >= required ;
292331 }
332+
293333 if ( shouldEndGame )
294334 {
295- GameManager . Instance . RpcEndGame ( winReason , false ) ;
296- CustomStatsManager . IncrementRoleWin ( ( INewModRole ) player . Data . Role ) ;
297- return true ;
335+ return EndGamePatch . EndCustomGame ( winReason , extraWinners ) ;
298336 }
299337 }
338+
300339 return false ;
301340 }
341+
302342 public static bool CheckEndGameForRole < T > ( ShipStatus __instance , GameOverReason winReason , int maxCount = 1 ) where T : RoleBehaviour
303343 {
304344 var rolePlayers = PlayerControl . AllPlayerControls . ToArray ( )
305- . Where ( p => p . Data . Role is T )
306- . Take ( maxCount )
307- . ToList ( ) ;
345+ . Where ( p => p . Data . Role is T )
346+ . Take ( maxCount )
347+ . ToList ( ) ;
308348
309349 foreach ( var player in rolePlayers )
310350 {
@@ -316,40 +356,43 @@ public static bool CheckEndGameForRole<T>(ShipStatus __instance, GameOverReason
316356 bool isSabotageActive = Utils . IsSabotage ( ) ;
317357 shouldEndGame = tasksCompleted && isSabotageActive ;
318358 }
359+
319360 if ( typeof ( T ) == typeof ( EnergyThief ) )
320361 {
321362 int drainCount = Utils . GetDrainCount ( player . PlayerId ) ;
322363 int requiredDrainCount = ( int ) OptionGroupSingleton < EnergyThiefOptions > . Instance . RequiredDrainCount ;
323-
324364 shouldEndGame = drainCount >= requiredDrainCount ;
325365 }
366+
326367 if ( typeof ( T ) == typeof ( Prankster ) )
327368 {
328369 int WinReportCount = 2 ;
329370 int currentReportCount = PranksterUtilities . GetReportCount ( player . PlayerId ) ;
330371 shouldEndGame = currentReportCount >= WinReportCount ;
331372 }
373+
332374 if ( typeof ( T ) == typeof ( SpecialAgent ) )
333375 {
334376 int missionSuccessCount = Utils . GetMissionSuccessCount ( player . PlayerId ) ;
335377 int missionFailureCount = Utils . GetMissionFailureCount ( player . PlayerId ) ;
336378 int netScore = missionSuccessCount - missionFailureCount ;
337379 shouldEndGame = netScore >= OptionGroupSingleton < SpecialAgentOptions > . Instance . RequiredMissionsToWin ;
338380 }
381+
339382 if ( typeof ( T ) == typeof ( InjectorRole ) )
340383 {
341384 int injectedCount = Utils . GetInjectedCount ( ) ;
342385 int required = ( int ) OptionGroupSingleton < InjectorOptions > . Instance . RequiredInjectCount ;
343386 shouldEndGame = injectedCount >= required ;
344387 }
388+
345389 if ( shouldEndGame )
346390 {
347- GameManager . Instance . RpcEndGame ( winReason , false ) ;
348- CustomStatsManager . IncrementRoleWin ( ( ICustomRole ) player . Data . Role ) ;
349- return true ;
391+ return EndGamePatch . EndCustomGame ( winReason ) ;
350392 }
351393 }
394+
352395 return false ;
353396 }
354397 }
355- }
398+ }
0 commit comments