diff --git a/Content.Server/GameTicking/GameTicker.GameRule.cs b/Content.Server/GameTicking/GameTicker.GameRule.cs index 84ceac547d..38086994db 100644 --- a/Content.Server/GameTicking/GameTicker.GameRule.cs +++ b/Content.Server/GameTicking/GameTicker.GameRule.cs @@ -1,6 +1,9 @@ using System.Collections.Generic; using System.Linq; +using Content.Server.Administration; using Content.Server.GameTicking.Rules; +using Content.Shared.Administration; +using Robust.Shared.Console; using Robust.Shared.ViewVariables; namespace Content.Server.GameTicking @@ -14,6 +17,34 @@ namespace Content.Server.GameTicking [ViewVariables] private readonly HashSet _startedGameRules = new(); public IEnumerable StartedGameRules => _startedGameRules; + private void InitializeGameRules() + { + // Add game rule command. + _consoleHost.RegisterCommand("addgamerule", + string.Empty, + "addgamerule ", + AddGameRuleCommand); + + // End game rule command. + _consoleHost.RegisterCommand("endgamerule", + string.Empty, + "endgamerule ", + EndGameRuleCommand); + + // Clear game rules command. + _consoleHost.RegisterCommand("cleargamerules", + string.Empty, + "cleargamerules", + ClearGameRulesCommand); + } + + private void ShutdownGameRules() + { + _consoleHost.UnregisterCommand("addgamerule"); + _consoleHost.UnregisterCommand("endgamerule"); + _consoleHost.UnregisterCommand("cleargamerules"); + } + /// /// Game rules can be 'started' separately from being added. 'Starting' them usually /// happens at round start while they can be added and removed before then. @@ -97,6 +128,50 @@ namespace Content.Server.GameTicking EndGameRule(rule); } } + + #region Command Implementations + + [AdminCommand(AdminFlags.Fun)] + private void AddGameRuleCommand(IConsoleShell shell, string argstr, string[] args) + { + if (args.Length == 0) + return; + + foreach (var ruleId in args) + { + if (!_prototypeManager.TryIndex(ruleId, out var rule)) + continue; + + AddGameRule(rule); + + // Start rule if we're already in the middle of a round. + if(RunLevel == GameRunLevel.InRound) + StartGameRule(rule); + } + } + + [AdminCommand(AdminFlags.Fun)] + private void EndGameRuleCommand(IConsoleShell shell, string argstr, string[] args) + { + if (args.Length == 0) + return; + + foreach (var ruleId in args) + { + if (!_prototypeManager.TryIndex(ruleId, out var rule)) + continue; + + EndGameRule(rule); + } + } + + [AdminCommand(AdminFlags.Fun)] + private void ClearGameRulesCommand(IConsoleShell shell, string argstr, string[] args) + { + ClearGameRules(); + } + + #endregion } /// diff --git a/Content.Server/GameTicking/GameTicker.cs b/Content.Server/GameTicking/GameTicker.cs index 99cbea426c..1cc672d879 100644 --- a/Content.Server/GameTicking/GameTicker.cs +++ b/Content.Server/GameTicking/GameTicker.cs @@ -15,6 +15,7 @@ using Robust.Server; using Robust.Server.Maps; using Robust.Server.ServerStatus; using Robust.Shared.Configuration; +using Robust.Shared.Console; #if EXCEPTION_TOLERANCE using Robust.Shared.Exceptions; #endif @@ -52,6 +53,7 @@ namespace Content.Server.GameTicking InitializeLobbyMusic(); InitializeLobbyBackground(); InitializeGamePreset(); + InitializeGameRules(); InitializeJobController(); InitializeUpdates(); @@ -69,6 +71,13 @@ namespace Content.Server.GameTicking _postInitialized = true; } + public override void Shutdown() + { + base.Shutdown(); + + ShutdownGameRules(); + } + private void SendServerMessage(string message) { var msg = new MsgChatMessage(); @@ -97,6 +106,7 @@ namespace Content.Server.GameTicking [Dependency] private readonly IGameMapManager _gameMapManager = default!; [Dependency] private readonly IServerDbManager _db = default!; [Dependency] private readonly ILogManager _logManager = default!; + [Dependency] private readonly IConsoleHost _consoleHost = default!; #if EXCEPTION_TOLERANCE [Dependency] private readonly IRuntimeLog _runtimeLog = default!; #endif