feat: add in game command handler

This commit is contained in:
Naruse
2025-06-14 14:13:48 +08:00
parent 684eab933b
commit 07ec2f9abf
10 changed files with 201 additions and 34 deletions

View File

@@ -71,12 +71,11 @@ public class ServerOption
public class ServerProfile public class ServerProfile
{ {
public string Name { get; set; } = "Server"; public string Name { get; set; } = "Ai-chan";
public int Uid { get; set; } = 80; public int Uid { get; set; } = 80;
public string Signature { get; set; } = "Type /help for a list of commands"; public int AvatarId { get; set; } = 3201;
public int Level { get; set; } = 1; public int DressId { get; set; } = 593201;
public int HeadIcon { get; set; } = 200105; public int FrameId { get; set; } = 200001;
public int ChatBubbleId { get; set; } = 220001; public int HeadId { get; set; } = 161080;
public int DisplayAvatarId { get; set; } = 1001;
public int DisplayAvatarLevel { get; set; } = 1;
} }

View File

@@ -11,16 +11,16 @@ public class PlayerData : BaseDatabaseDataHelper
{ {
public string? Name { get; set; } = ""; public string? Name { get; set; } = "";
public string? Signature { get; set; } = "KianaPS"; public string? Signature { get; set; } = "KianaPS";
public uint Level { get; set; } = 88; public int Level { get; set; } = 88;
public uint Exp { get; set; } = 0; public int Exp { get; set; } = 0;
public uint HCoin { get; set; } = 0; public int HCoin { get; set; } = 0;
public uint Stamina { get; set; } = 240; public int Stamina { get; set; } = 240;
public uint HeadIcon { get; set; } = 161090; public int HeadIcon { get; set; } = 161090;
public uint HeadFrame { get; set; } = 200001; public int HeadFrame { get; set; } = 200001;
public uint WarshipId { get; set; } = 400004; public int WarshipId { get; set; } = 400004;
public uint PhonePendantId { get; set; } = 350005; public int PhonePendantId { get; set; } = 350005;
public uint AssistantAvatarId { get; set; } = 101; public int AssistantAvatarId { get; set; } = 101;
public uint BirthDay { get; set; } = 0; public int BirthDay { get; set; } = 0;
[SugarColumn(IsJson = true)] public WarshipAvatarData WarshipAvatar { get; set; } = new(); [SugarColumn(IsJson = true)] public WarshipAvatarData WarshipAvatar { get; set; } = new();
[SugarColumn(IsNullable = true)] public long LastActiveTime { get; set; } [SugarColumn(IsNullable = true)] public long LastActiveTime { get; set; }
public long RegisterTime { get; set; } = Extensions.GetUnixSec(); public long RegisterTime { get; set; } = Extensions.GetUnixSec();
@@ -35,23 +35,23 @@ public class PlayerData : BaseDatabaseDataHelper
return new GetMainDataRsp return new GetMainDataRsp
{ {
IsAll = true, IsAll = true,
AssistantAvatarId = 0, AssistantAvatarId = (uint)AssistantAvatarId,
Birthday = BirthDay, Birthday = (uint)BirthDay,
Nickname = Name, Nickname = Name,
Level = Level, Level = (uint)Level,
Exp = Exp, Exp = (uint)Exp,
Hcoin = HCoin, Hcoin = (uint)HCoin,
CustomHeadId = HeadIcon, CustomHeadId = (uint)HeadIcon,
RegisterTime = (uint)RegisterTime, RegisterTime = (uint)RegisterTime,
WarshipAvatar = new Proto.WarshipAvatarData WarshipAvatar = new Proto.WarshipAvatarData
{ {
WarshipFirstAvatarId = 0, WarshipFirstAvatarId = (uint)WarshipAvatar.FirstAvatarId,
WarshipSecondAvatarId = 0, WarshipSecondAvatarId = (uint)WarshipAvatar.SecondAvatarId,
}, },
SelfDesc = Signature, SelfDesc = Signature,
UseFrameId = HeadFrame, UseFrameId = (uint)HeadFrame,
OnPhonePendantId = PhonePendantId, OnPhonePendantId = (uint)PhonePendantId,
Stamina = Stamina, Stamina = (uint)Stamina,
StaminaRecoverConfigTime = GameConstants.STAMINA_RECOVERY_TIME, StaminaRecoverConfigTime = GameConstants.STAMINA_RECOVERY_TIME,
StaminaRecoverLeftTime = GameConstants.STAMINA_RECOVERY_TIME, StaminaRecoverLeftTime = GameConstants.STAMINA_RECOVERY_TIME,
EquipmentSizeLimit = GameConstants.INVENTORY_MAX_EQUIPMENT, EquipmentSizeLimit = GameConstants.INVENTORY_MAX_EQUIPMENT,
@@ -59,7 +59,7 @@ public class PlayerData : BaseDatabaseDataHelper
LevelLockId = 1, LevelLockId = 1,
WarshipTheme = new WarshipThemeData WarshipTheme = new WarshipThemeData
{ {
WarshipId=0 WarshipId=(uint)WarshipId
}, },
TotalLoginDays = 1 TotalLoginDays = 1
}; };
@@ -68,6 +68,6 @@ public class PlayerData : BaseDatabaseDataHelper
public class WarshipAvatarData public class WarshipAvatarData
{ {
public uint FirstAvatarId { get; set; } = 101; public int FirstAvatarId { get; set; } = 101;
public uint SecondAvatarId { get; set; } = 0; public int SecondAvatarId { get; set; } = 0;
} }

View File

@@ -1,5 +1,6 @@
using KianaBH.Enums.Player; using KianaBH.Enums.Player;
using KianaBH.GameServer.Game.Player; using KianaBH.GameServer.Game.Player;
using KianaBH.GameServer.Server.Packet.Send.Chat;
using KianaBH.Util; using KianaBH.Util;
namespace KianaBH.GameServer.Command; namespace KianaBH.GameServer.Command;
@@ -31,7 +32,7 @@ public class PlayerCommandSender(PlayerInstance player) : ICommandSender
public async ValueTask SendMsg(string msg) public async ValueTask SendMsg(string msg)
{ {
// TODO SEND MSG await Player.SendPacket(new PacketRecvChatMsgNotify(msg));
} }
public int GetSender() public int GetSender()

View File

@@ -0,0 +1,52 @@
using KianaBH.Enums.Player;
using KianaBH.Internationalization;
using KianaBH.Util.Extensions;
namespace KianaBH.GameServer.Command.Commands;
[CommandInfo("help", "Game.Command.Help.Desc", "Game.Command.Help.Usage", ["h"], [PermEnum.Support, PermEnum.Trial])]
public class CommandHelp : ICommands
{
[CommandDefault]
public async static ValueTask Help(CommandArg arg)
{
if (arg.Args.Count == 1)
{
var cmd = arg.Args[0];
if (CommandManager.CommandInfo == null || !CommandManager.CommandInfo.TryGetValue(cmd, out var command))
{
await arg.SendMsg(I18NManager.Translate("Game.Command.Notice.CommandNotFound"));
return;
}
var msg =
$"/{command.Name} - {I18NManager.Translate(command.Description)}\n{I18NManager.Translate(command.Usage)}";
if (command.Alias.Length > 0)
msg +=
$"\n{I18NManager.Translate("Game.Command.Help.CommandAlias")} {command.Alias.ToList().ToArrayString()}";
if (command.Perm != null)
msg += $"\n{I18NManager.Translate("Game.Command.Help.CommandPermission")} {string.Join(", ", command.Perm.Select(perm => perm.ToString()))}";
await arg.SendMsg(msg + "\n");
return;
}
else
{
await arg.SendMsg(I18NManager.Translate("Game.Command.Help.Commands"));
if (CommandManager.CommandInfo == null) return;
foreach (var command in CommandManager.CommandInfo.Values)
{
var msg =
$"/{command.Name} - {I18NManager.Translate(command.Description)}\n{I18NManager.Translate(command.Usage)}";
if (command.Alias.Length > 0)
msg +=
$"\n{I18NManager.Translate("Game.Command.Help.CommandAlias")} {command.Alias.ToList().ToArrayString()}";
if (command.Perm != null)
msg += $"\n{I18NManager.Translate("Game.Command.Help.CommandPermission")} {string.Join(", ", command.Perm.Select(perm => perm.ToString()))}";
await arg.SendMsg(msg + "\n");
}
}
}
}

View File

@@ -0,0 +1,31 @@
using KianaBH.GameServer.Command;
using KianaBH.GameServer.Game.Player;
using KianaBH.GameServer.Server.Packet.Send.Chat;
using KianaBH.Proto;
using KianaBH.Util.Extensions;
namespace KianaBH.GameServer.Game.Battle;
public class WorldChatManager(PlayerInstance player) : BasePlayerManager(player)
{
public List<ChatMsg> Chats { get; set; } = [];
public async ValueTask SendMessage(string message, ChatMsg chatMsg)
{
chatMsg.Uid = (uint)Player.Data.Uid;
chatMsg.Nickname = Player.Data.Name;
chatMsg.Time = (uint)Extensions.GetUnixSec();
chatMsg.AvatarId = (uint)Player.Data.AssistantAvatarId;
chatMsg.DressId = (uint)Player.AvatarManager!.AvatarData.Avatars.Where(avatar => avatar.AvatarId == Player.Data.AssistantAvatarId).First().DressId;
chatMsg.FrameId = (uint)Player.Data.HeadFrame;
chatMsg.CustomHeadId = (uint)Player.Data.HeadIcon;
await Player.SendPacket(new PacketRecvChatMsgNotify(chatMsg));
if (message.StartsWith('/') == true)
{
var cmd = message[1..];
CommandExecutor.ExecuteCommand(new PlayerCommandSender(Player), cmd);
}
}
}

View File

@@ -4,6 +4,7 @@ using KianaBH.Database.Account;
using KianaBH.Database.Client; using KianaBH.Database.Client;
using KianaBH.Database.Player; using KianaBH.Database.Player;
using KianaBH.GameServer.Game.Avatar; using KianaBH.GameServer.Game.Avatar;
using KianaBH.GameServer.Game.Battle;
using KianaBH.GameServer.Game.Inventory; using KianaBH.GameServer.Game.Inventory;
using KianaBH.GameServer.Server; using KianaBH.GameServer.Server;
using KianaBH.KcpSharp; using KianaBH.KcpSharp;
@@ -20,6 +21,7 @@ public class PlayerInstance(PlayerData data)
public PlayerData Data { get; set; } = data; public PlayerData Data { get; set; } = data;
public ClientData? ClientData { get; private set; } public ClientData? ClientData { get; private set; }
public GuideData? GuideData { get; private set; } public GuideData? GuideData { get; private set; }
public WorldChatManager? WorldChatManager { get; private set; }
public int Uid { get; set; } public int Uid { get; set; }
public Connection? Connection { get; set; } public Connection? Connection { get; set; }
public bool Initialized { get; set; } public bool Initialized { get; set; }
@@ -53,6 +55,7 @@ public class PlayerInstance(PlayerData data)
InventoryManager = new InventoryManager(this); InventoryManager = new InventoryManager(this);
ClientData = InitializeDatabase<ClientData>(); ClientData = InitializeDatabase<ClientData>();
GuideData = InitializeDatabase<GuideData>(); GuideData = InitializeDatabase<GuideData>();
WorldChatManager = new WorldChatManager(this);
Data.LastActiveTime = Extensions.GetUnixSec(); Data.LastActiveTime = Extensions.GetUnixSec();
await Task.CompletedTask; await Task.CompletedTask;

View File

@@ -175,6 +175,10 @@ public class Connection(KcpConversation conversation, IPEndPoint remote) : KcpCo
} }
return; return;
} }
if (ConfigManager.Config.ServerOption.EnableDebug &&
ConfigManager.Config.ServerOption.DebugNoHandlerPacket)
Logger.Error($"No handler found for {packetName}({opcode})");
} }
private async Task SendDummy(string packetName) private async Task SendDummy(string packetName)

View File

@@ -0,0 +1,21 @@
using KianaBH.GameServer.Command;
using KianaBH.GameServer.Server.Packet.Send.Chat;
using KianaBH.Proto;
namespace KianaBH.GameServer.Server.Packet.Recv.Chat;
[Opcode(CmdIds.SendChatMsgNotify)]
public class HandlerSendChatMsgNotify : Handler
{
public override async Task OnHandle(Connection connection, byte[] header, byte[] data)
{
var req = SendChatMsgNotify.Parser.ParseFrom(data);
var player = connection.Player!;
if (player == null) return;
string msg = req.ChatMsg.Content.Items.Where(item => item.MsgStr != null).FirstOrDefault()?.MsgStr!;
if (msg == null) return;
await player.WorldChatManager!.SendMessage(msg,req.ChatMsg);
}
}

View File

@@ -12,8 +12,8 @@ public class HandlerSetWarshipAvatarReq : Handler
var player = connection.Player!; var player = connection.Player!;
var req = SetWarshipAvatarReq.Parser.ParseFrom(data); var req = SetWarshipAvatarReq.Parser.ParseFrom(data);
player.Data.WarshipAvatar.FirstAvatarId = req.FirstAvatarId; player.Data.WarshipAvatar.FirstAvatarId = (int)req.FirstAvatarId;
player.Data.WarshipAvatar.SecondAvatarId = req.SecondAvatarId; player.Data.WarshipAvatar.SecondAvatarId = (int)req.SecondAvatarId;
await connection.SendPacket(new PacketGetMainDataRsp(req.FirstAvatarId,req.SecondAvatarId)); await connection.SendPacket(new PacketGetMainDataRsp(req.FirstAvatarId,req.SecondAvatarId));
await connection.SendPacket(CmdIds.SetWarshipAvatarRsp); await connection.SendPacket(CmdIds.SetWarshipAvatarRsp);

View File

@@ -0,0 +1,56 @@
using KianaBH.KcpSharp;
using KianaBH.Proto;
using KianaBH.Util;
using KianaBH.Util.Extensions;
namespace KianaBH.GameServer.Server.Packet.Send.Chat;
public class PacketRecvChatMsgNotify : BasePacket
{
public PacketRecvChatMsgNotify(ChatMsg msgs) : base(CmdIds.RecvChatMsgNotify)
{
var proto = new RecvChatMsgNotify
{
ChatMsgList = { msgs }
};
SetData(proto);
}
public PacketRecvChatMsgNotify(string message) : base(CmdIds.RecvChatMsgNotify)
{
var proto = new RecvChatMsgNotify
{
ChatMsgList =
{
new ChatMsg
{
Uid = (uint)ConfigManager.Config.ServerOption.ServerProfile.Uid,
Nickname = ConfigManager.Config.ServerOption.ServerProfile.Name,
Time = (uint)Extensions.GetUnixSec(),
Msg = message,
Channel = ChatMsg.Types.MsgChannel.World,
AvatarId = (uint)ConfigManager.Config.ServerOption.ServerProfile.AvatarId,
DressId = (uint)ConfigManager.Config.ServerOption.ServerProfile.DressId,
FrameId = (uint)ConfigManager.Config.ServerOption.ServerProfile.FrameId,
CustomHeadId = (uint)ConfigManager.Config.ServerOption.ServerProfile.HeadId,
CheckResult = new ChatMsgSensitiveCheckResult
{
RewriteText = message
},
Content = new ChatMsgContent
{
Items =
{
new ChatMsgItem
{
MsgStr = message,
}
}
}
}
}
};
SetData(proto);
}
}