diff --git a/Content.Client/Info/RulesManager.cs b/Content.Client/Info/RulesManager.cs index 2986b9c244..4cc361c5ba 100644 --- a/Content.Client/Info/RulesManager.cs +++ b/Content.Client/Info/RulesManager.cs @@ -3,29 +3,38 @@ using System.Globalization; using Content.Client.Lobby; using Content.Client.Viewport; using Content.Shared.CCVar; +using Content.Shared.Info; using Robust.Client.Console; using Robust.Client.State; using Robust.Client.UserInterface; using Robust.Shared.Configuration; using Robust.Shared.ContentPack; using Robust.Shared.IoC; +using Robust.Shared.Network; using Robust.Shared.Utility; namespace Content.Client.Info; -public sealed class RulesManager +public sealed class RulesManager : SharedRulesManager { [Dependency] private readonly IResourceManager _resource = default!; [Dependency] private readonly IConfigurationManager _configManager = default!; [Dependency] private readonly IUserInterfaceManager _userInterfaceManager = default!; [Dependency] private readonly IStateManager _stateManager = default!; [Dependency] private readonly IClientConsoleHost _consoleHost = default!; + [Dependency] private readonly INetManager _netManager = default!; public void Initialize() { + _netManager.RegisterNetMessage(OnShowRulesPopupMessage); _stateManager.OnStateChanged += OnStateChanged; } + private void OnShowRulesPopupMessage(ShowRulesPopupMessage message) + { + ShowRules(message.PopupTime); + } + private void OnStateChanged(StateChangedEventArgs args) { if (args.NewState is not (GameScreen or LobbyState)) diff --git a/Content.Server/Entry/EntryPoint.cs b/Content.Server/Entry/EntryPoint.cs index fa3bee9f45..c74441b013 100644 --- a/Content.Server/Entry/EntryPoint.cs +++ b/Content.Server/Entry/EntryPoint.cs @@ -8,6 +8,7 @@ using Content.Server.Connection; using Content.Server.Database; using Content.Server.EUI; using Content.Server.GameTicking; +using Content.Server.Info; using Content.Server.IoC; using Content.Server.Maps; using Content.Server.NodeContainer.NodeGroups; @@ -91,6 +92,7 @@ namespace Content.Server.Entry IoCManager.Resolve().Initialize(); IoCManager.Resolve().Initialize(); IoCManager.Resolve().Initialize(); + IoCManager.Resolve().Initialize(); _euiManager.Initialize(); IoCManager.Resolve().Initialize(); diff --git a/Content.Server/Info/RulesManager.cs b/Content.Server/Info/RulesManager.cs new file mode 100644 index 0000000000..975cb1a108 --- /dev/null +++ b/Content.Server/Info/RulesManager.cs @@ -0,0 +1,15 @@ +using Content.Shared.Info; +using Robust.Shared.IoC; +using Robust.Shared.Network; + +namespace Content.Server.Info; + +public class RulesManager : SharedRulesManager +{ + [Dependency] private readonly INetManager _netManager = default!; + + public void Initialize() + { + _netManager.RegisterNetMessage(); + } +} diff --git a/Content.Server/Info/ShowRulesCommand.cs b/Content.Server/Info/ShowRulesCommand.cs new file mode 100644 index 0000000000..101f1dd99c --- /dev/null +++ b/Content.Server/Info/ShowRulesCommand.cs @@ -0,0 +1,67 @@ +using Content.Server.Administration; +using Content.Shared.Administration; +using Content.Shared.CCVar; +using Content.Shared.Info; +using Robust.Server.Player; +using Robust.Shared.Configuration; +using Robust.Shared.Console; +using Robust.Shared.IoC; +using Robust.Shared.Network; + +namespace Content.Server.Info; + +[AdminCommand(AdminFlags.Admin)] +public class ShowRulesCommand : IConsoleCommand +{ + public string Command => "showrules"; + public string Description => "Opens the rules popup for the specified player."; + public string Help => "showrules [time]"; + public async void Execute(IConsoleShell shell, string argStr, string[] args) + { + string target; + float seconds; + + switch (args.Length) + { + case 1: + { + target = args[0]; + var configurationManager = IoCManager.Resolve(); + seconds = configurationManager.GetCVar(CCVars.RulesWaitTime); + break; + } + case 2: + { + if (float.TryParse(args[1], out seconds)) + return; + + target = args[0]; + shell.WriteLine($"{args[1]} is not a valid amount of minutes.\n{Help}"); + break; + } + default: + { + shell.WriteLine(Help); + return; + } + } + + var locator = IoCManager.Resolve(); + var located = await locator.LookupIdByNameOrIdAsync(target); + if (located == null) + { + shell.WriteError("Unable to find a player with that name."); + return; + } + + var message = new SharedRulesManager.ShowRulesPopupMessage + { + PopupTime = seconds + }; + + var player = IoCManager.Resolve() + .GetSessionByUserId(located.UserId); + IoCManager.Resolve() + .ServerSendMessage(message, player.ConnectedClient); + } +} diff --git a/Content.Server/IoC/ServerContentIoC.cs b/Content.Server/IoC/ServerContentIoC.cs index 196873a7e5..bef312b4bb 100644 --- a/Content.Server/IoC/ServerContentIoC.cs +++ b/Content.Server/IoC/ServerContentIoC.cs @@ -11,6 +11,7 @@ using Content.Server.DeviceNetwork; using Content.Server.EUI; using Content.Server.Holiday; using Content.Server.Holiday.Interfaces; +using Content.Server.Info; using Content.Server.Maps; using Content.Server.Module; using Content.Server.MoMMI; @@ -57,6 +58,7 @@ namespace Content.Server.IoC IoCManager.Register(); IoCManager.Register(); IoCManager.Register(); + IoCManager.Register(); } } } diff --git a/Content.Shared/Info/SharedRulesManager.cs b/Content.Shared/Info/SharedRulesManager.cs new file mode 100644 index 0000000000..abd8037934 --- /dev/null +++ b/Content.Shared/Info/SharedRulesManager.cs @@ -0,0 +1,26 @@ +using JetBrains.Annotations; +using Lidgren.Network; +using Robust.Shared.Network; + +namespace Content.Shared.Info; + +public abstract class SharedRulesManager +{ + [UsedImplicitly] + public sealed class ShowRulesPopupMessage : NetMessage + { + public override MsgGroups MsgGroup => MsgGroups.Command; + + public float PopupTime { get; set; } + + public override void ReadFromBuffer(NetIncomingMessage buffer) + { + PopupTime = buffer.ReadFloat(); + } + + public override void WriteToBuffer(NetOutgoingMessage buffer) + { + buffer.Write(PopupTime); + } + } +}