extending command for user and prevent err in build ship menu

This commit is contained in:
rfi
2024-02-22 21:22:48 +07:00
parent db93c8f49d
commit bdc8785fe1
8 changed files with 133 additions and 17 deletions

View File

@@ -30,8 +30,30 @@ public class ArgumentAttribute : Attribute
}
}
[Flags]
public enum CommandUsage
{
None = 0,
Console = 1,
User = 2
}
public abstract class Command
{
public virtual CommandUsage Usage
{
get
{
var usage = CommandUsage.None;
if (GetType().GetMethod(nameof(Execute), [typeof(Dictionary<string, string>), typeof(Connection)])?.DeclaringType == GetType())
usage |= CommandUsage.User;
if (GetType().GetMethod(nameof(Execute), [typeof(Dictionary<string, string>)])?.DeclaringType == GetType())
usage |= CommandUsage.Console;
return usage;
}
}
readonly Dictionary<string, PropertyInfo> argsProperties;
public Command()
@@ -50,6 +72,11 @@ public abstract class Command
}
}
public virtual void Execute(Dictionary<string, string> args, Connection connection)
{
Execute(args);
}
protected T Parse<T>(string? value, T fallback = default!)
{
var tryParseMethod = typeof(T).GetMethod("TryParse", [typeof(string), typeof(T).MakeByRefType()]);
@@ -72,10 +99,12 @@ public static class CommandHandlerFactory
public static readonly List<Command> Commands = new List<Command>();
static readonly Dictionary<string, Action<Dictionary<string, string>>> commandFunctions;
static readonly Dictionary<string, Action<Dictionary<string, string>, Connection>> commandFunctionsConn;
static CommandHandlerFactory()
{
commandFunctions = new Dictionary<string, Action<Dictionary<string, string>>>(StringComparer.OrdinalIgnoreCase);
commandFunctionsConn = new Dictionary<string, Action<Dictionary<string, string>, Connection>>(StringComparer.OrdinalIgnoreCase);
RegisterCommands(Assembly.GetExecutingAssembly());
}
@@ -91,24 +120,23 @@ public static class CommandHandlerFactory
if (commandAttribute != null)
{
var commandInstance = (Command)Activator.CreateInstance(commandType)!;
commandFunctions[commandAttribute.Name] = commandInstance.Execute;
if (commandInstance.Usage.HasFlag(CommandUsage.Console))
commandFunctions[commandAttribute.Name] = commandInstance.Execute;
if (commandInstance.Usage.HasFlag(CommandUsage.User))
commandFunctionsConn[commandAttribute.Name] = commandInstance.Execute;
Commands.Add(commandInstance);
}
}
}
public static void HandleCommand(string commandLine)
public static void HandleCommand(string commandLine, Connection? connection = null)
{
var parts = commandLine.Split(new[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
if (parts.Length == 0)
return;
if (!commandFunctions.TryGetValue(parts[0], out var command))
{
Logger.c.Warn($"Unknown command: {parts[0]}");
return;
}
var arguments = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
for (var i = 1; i < parts.Length; i++)
{
@@ -117,6 +145,25 @@ public static class CommandHandlerFactory
arguments[argParts[0]] = argParts[1];
}
command(arguments);
if (connection is not null)
{
if (!(commandFunctionsConn).TryGetValue(parts[0], out var command))
{
Logger.c.Warn($"Unknown command: {parts[0]}");
return;
}
command(arguments, connection);
}
else
{
if (!(commandFunctions).TryGetValue(parts[0], out var command))
{
Logger.c.Warn($"Unknown command: {parts[0]}");
return;
}
command(arguments);
}
}
}

View File

@@ -1,4 +1,5 @@
using System.Reflection;
using BLHX.Server.Game.Handlers;
using System.Reflection;
using System.Text;
namespace BLHX.Server.Game.Commands;
@@ -15,7 +16,29 @@ public class HelpCommand : Command
StringBuilder sb = new StringBuilder();
sb.AppendLine("Available Commands: ");
foreach (var command in CommandHandlerFactory.Commands)
foreach (var command in CommandHandlerFactory.Commands.Where(x => x.Usage.HasFlag(CommandUsage.Console)))
{
if (!commandAttributes.TryGetValue(command.GetType(), out var attr))
{
attr = command.GetType().GetCustomAttribute(typeof(CommandHandler)) as CommandHandler;
commandAttributes[command.GetType()] = attr;
}
if (attr != null)
sb.AppendLine($" {attr.Name} - {attr.Description} (Example: {attr.Example}), Usage: {command.Usage}");
}
Console.Write(sb.ToString());
}
public override void Execute(Dictionary<string, string> args, Connection connection)
{
base.Execute(args);
StringBuilder sb = new StringBuilder();
sb.AppendLine("Available Commands: ");
foreach (var command in CommandHandlerFactory.Commands.Where(x => x.Usage.HasFlag(CommandUsage.User)))
{
if (!commandAttributes.TryGetValue(command.GetType(), out var attr))
{
@@ -27,6 +50,6 @@ public class HelpCommand : Command
sb.AppendLine($" {attr.Name} - {attr.Description} (Example: {attr.Example})");
}
Console.Write(sb.ToString());
connection.SendSystemMsg(sb.ToString());
}
}

View File

@@ -7,7 +7,6 @@ using ProtoBuf;
using System.Buffers.Binary;
using System.Net;
using System.Net.Sockets;
using System.Reflection;
using System.Text;
namespace BLHX.Server.Game
@@ -148,7 +147,7 @@ namespace BLHX.Server.Game
DBManager.PlayerContext.Save();
this.NotifyResourceList();
#if DEBUG
c.Log($"Tick");
c.Log("Ticked!");
#endif
}
@@ -167,6 +166,8 @@ namespace BLHX.Server.Game
this.NotifyShopMonthData();
this.NotifyChapterData();
this.NotifyBagData();
this.NotifyBuildShipData();
this.NotifyActivityData();
this.NotifyDormData();
this.NotifyNavalAcademy();
}

View File

@@ -113,5 +113,10 @@ namespace BLHX.Server.Game.Handlers
{
connection.Send(new Sc11752());
}
public static void NotifyActivityData(this Connection connection)
{
connection.Send(new Sc11200());
}
}
}

View File

@@ -48,5 +48,10 @@ namespace BLHX.Server.Game.Handlers
});
}
}
public static void NotifyBuildShipData(this Connection connection)
{
connection.Send(new Sc12024());
}
}
}

View File

@@ -22,6 +22,12 @@ namespace BLHX.Server.Game.Handlers
{
var req = packet.Decode<Cs50102>();
if (req.Content.StartsWith("/"))
{
Commands.CommandHandlerFactory.HandleCommand(req.Content.Substring(1), connection);
return;
}
GameServer.ChatManager.SendChat(new()
{
Content = req.Content,
@@ -35,4 +41,27 @@ namespace BLHX.Server.Game.Handlers
});
}
}
static class P50ConnectionNotifyExtensions
{
public static void SendSystemMsg(this Connection connection, string msg)
{
var ntf = new Sc50101()
{
Content = msg,
Player = new()
{
Name = "System",
Display = new()
{
Icon = 107061
}
},
Type = 1
};
connection.Send(ntf);
}
}
}

View File

@@ -6,7 +6,7 @@ namespace BLHX.Server.Game.Managers
{
List<MsgInfo> messages = [];
public void SendChat(MsgInfo msgInfo)
public void SendChat(MsgInfo msgInfo, bool broadcast = true)
{
msgInfo.Timestamp = (uint)DateTimeOffset.Now.ToUnixTimeSeconds();