From c30fdd74c8a26ebed5b9a190956a96aeff8b6c95 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=B0=B8=E5=AE=89404?= <101850798+YongAn404@users.noreply.github.com> Date: Fri, 31 Oct 2025 08:38:05 +0800 Subject: [PATCH 1/6] up 14.2 --- Features/MusicManager.cs | 8 ++++---- Features/PlayerUI.cs | 2 +- Features/Players/FramePlayer.cs | 7 +++++++ Features/Roles/CustomRolePlus.cs | 2 +- YongAnFrame.csproj | 6 +++--- 5 files changed, 16 insertions(+), 9 deletions(-) diff --git a/Features/MusicManager.cs b/Features/MusicManager.cs index 92ae08e..f034656 100644 --- a/Features/MusicManager.cs +++ b/Features/MusicManager.cs @@ -149,11 +149,11 @@ public static VoicePlayerBase Play(string musicName, string npcName, TrackEvent? { if (distance == 0) { - voicePlayerBase.BroadcastTo.Add(npc.PlayerId); + voicePlayerBase.BroadcastTo.Add(npc); } else { - voicePlayerBase.BroadcastTo = [.. FramePlayer.List.Where(p => Vector3.Distance(p.ExPlayer!.Position, source.ExPlayer!.Position) <= distance).Select((s) => s.ExPlayer!.Id)]; + voicePlayerBase.BroadcastTo = [.. FramePlayer.List.Where(p => Vector3.Distance(p.ExPlayer!.Position, source.ExPlayer!.Position) <= distance).Select((s) => s)]; } } @@ -161,9 +161,9 @@ public static VoicePlayerBase Play(string musicName, string npcName, TrackEvent? { foreach (var player in extraPlay) { - if (!voicePlayerBase.BroadcastTo.Contains(player.ExPlayer.Id)) + if (!voicePlayerBase.BroadcastTo.Contains(player)) { - voicePlayerBase.BroadcastTo.Add(player.ExPlayer.Id); + voicePlayerBase.BroadcastTo.Add(player); } } } diff --git a/Features/PlayerUI.cs b/Features/PlayerUI.cs index 0ae1bfb..4751c04 100644 --- a/Features/PlayerUI.cs +++ b/Features/PlayerUI.cs @@ -163,7 +163,7 @@ public PlayerUI(FramePlayer fPlayer) MessageList = new(7, UpdateMessageUI); ChatList = new(7, UpdateChatUI); coroutine = Timing.RunCoroutine(Timer()); - PlayerDisplay = PlayerDisplay.Get(fPlayer); + PlayerDisplay = PlayerDisplay.Get(referenceHub:fPlayer); PlayerDisplay.AddHint(customRoleHint); PlayerDisplay.AddHint(chatHint); PlayerDisplay.AddHint(messageHint); diff --git a/Features/Players/FramePlayer.cs b/Features/Players/FramePlayer.cs index c3d800f..f989910 100644 --- a/Features/Players/FramePlayer.cs +++ b/Features/Players/FramePlayer.cs @@ -419,5 +419,12 @@ public void Invalid() /// /// 框架玩家 public static implicit operator Player(FramePlayer yPlayer) => yPlayer.ExPlayer; + + /// + /// 隐性转换 + /// + /// 框架玩家 + public static implicit operator ReferenceHub(FramePlayer yPlayer) => yPlayer; + } } diff --git a/Features/Roles/CustomRolePlus.cs b/Features/Roles/CustomRolePlus.cs index 8001a56..d346a14 100644 --- a/Features/Roles/CustomRolePlus.cs +++ b/Features/Roles/CustomRolePlus.cs @@ -29,7 +29,7 @@ public abstract class CustomRolePlus : CustomRole /// /// 不要修改这个值 /// - public override bool IgnoreSpawnSystem { get; set; } = false; + public override bool IgnoreSpawnSystem { get; set; } = true; /// /// 获取禁用的自定义角色生成 /// diff --git a/YongAnFrame.csproj b/YongAnFrame.csproj index beeb5cf..79069d8 100644 --- a/YongAnFrame.csproj +++ b/YongAnFrame.csproj @@ -52,9 +52,9 @@ - - - + + + From 267903a6499f74313d6e748db19aba064aefd5fa Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=B0=B8=E5=AE=89404?= <101850798+YongAn404@users.noreply.github.com> Date: Mon, 3 Nov 2025 09:31:58 +0800 Subject: [PATCH 2/6] =?UTF-8?q?=E5=90=9E=E5=B9=B6=E5=90=8C=E6=AD=A5?= =?UTF-8?q?=E6=8F=92=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Commands/Chats/AChatCommand.cs | 39 ++++++++ Commands/Chats/BChatCommand.cs | 47 +++++++++ Commands/Chats/CChatCommand.cs | 37 +++++++ Commands/Chats/ChatBanCommand.cs | 38 +++++++ Commands/ExpCommand.cs | 2 +- Commands/KillCommand.cs | 29 ++++++ Commands/MessageCommand.cs | 5 +- Commands/PlayerCommand.cs | 4 +- Commands/TitleCommand.cs | 110 +++++++++++++++++++++ Config.cs | 15 +++ Features/MusicManager.cs | 4 +- Features/PlayerUI.cs | 4 +- Features/Players/CustomPlayer.cs | 4 +- Features/Players/FramePlayer.cs | 163 +++++++++++++++++++++++++++++-- Features/Players/PlayerTitle.cs | 92 ++++++++++++++--- Features/Roles/CustomRolePlus.cs | 3 +- Patch/AddLogPatch.cs | 92 ++++++++--------- YongAnFrame.csproj | 3 +- YongAnFramePlugin.cs | 10 +- 19 files changed, 611 insertions(+), 90 deletions(-) create mode 100644 Commands/Chats/AChatCommand.cs create mode 100644 Commands/Chats/BChatCommand.cs create mode 100644 Commands/Chats/CChatCommand.cs create mode 100644 Commands/Chats/ChatBanCommand.cs create mode 100644 Commands/KillCommand.cs create mode 100644 Commands/TitleCommand.cs diff --git a/Commands/Chats/AChatCommand.cs b/Commands/Chats/AChatCommand.cs new file mode 100644 index 0000000..0f2cf0a --- /dev/null +++ b/Commands/Chats/AChatCommand.cs @@ -0,0 +1,39 @@ +using CommandSystem; +using Exiled.API.Features; +using System; +using System.Linq; +using YongAnFrame.Features.Players; +using YongAnFrame.Features.UI.Enums; +using YongAnFrame.Features.UI.Texts; + +namespace SyncPlugin.Commands.Chats +{ + [CommandHandler(typeof(ClientCommandHandler))] + public class AChatCommand : ICommand + { + public string Command => "achat"; + + public string[] Aliases => ["ac"]; + + public string Description => ""; + + public bool Execute(ArraySegment arguments, ICommandSender sender, out string response) + { + if (arguments.Array.Length >= 2) + { + if (Player.TryGet(sender, out Player player)) + { + foreach (var player1 in FramePlayer.List.Where((p) => { return p.ExPlayer.RemoteAdminAccess; })) + { + player1.UI.MessageList.Add(new MessageText(arguments.Array[1], 30, MessageType.Feedback)); + } + + response = "OK"; + return true; + } + } + response = "NO"; + return false; + } + } +} diff --git a/Commands/Chats/BChatCommand.cs b/Commands/Chats/BChatCommand.cs new file mode 100644 index 0000000..6ef4f8d --- /dev/null +++ b/Commands/Chats/BChatCommand.cs @@ -0,0 +1,47 @@ +using CommandSystem; +using Exiled.API.Features; +using System; +using YongAnFrame.Extensions; +using YongAnFrame.Features.Players; +using YongAnFrame.Features.UI.Enums; +using YongAnFrame.Features.UI.Texts; + +namespace SyncPlugin.Commands.Chats +{ + [CommandHandler(typeof(ClientCommandHandler))] + public class BChatCommand : ICommand + { + public string Command => "bchat"; + + public string[] Aliases => ["bc"]; + + public string Description => ""; + + public bool Execute(ArraySegment arguments, ICommandSender sender, out string response) + { + if (arguments.Array.Length == 2) + { + if (Player.TryGet(sender, out Player player)) + { + FramePlayer framePlayer = player.ToFPlayer(); + + //if (framePlayer.IsChatBan) + //{ + // response = "无法发送聊天,你已收到临时聊天禁令"; + // return false; + //} + + foreach (var item in FramePlayer.List) + { + item.UI.ChatList.Add(new ChatText(arguments.Array[1], 10, ChatType.All, framePlayer)); + } + + response = "OK"; + return true; + } + } + response = "NO"; + return false; + } + } +} diff --git a/Commands/Chats/CChatCommand.cs b/Commands/Chats/CChatCommand.cs new file mode 100644 index 0000000..1e85cf3 --- /dev/null +++ b/Commands/Chats/CChatCommand.cs @@ -0,0 +1,37 @@ +using CommandSystem; +using Exiled.API.Features; +using System; +using YongAnFrame.Extensions; +using YongAnFrame.Features.UI.Enums; +using YongAnFrame.Features.UI.Texts; + +namespace SyncPlugin.Commands.Chats +{ + [CommandHandler(typeof(ClientCommandHandler))] + public class CChatCommand : ICommand + { + public string Command => "cchat"; + + public string[] Aliases => ["cc"]; + + public string Description => ""; + + public bool Execute(ArraySegment arguments, ICommandSender sender, out string response) + { + if (arguments.Array.Length == 2) + { + if (Player.TryGet(sender, out Player player)) + { + foreach (var player1 in Player.Get(player.Role.Side)) + { + player1.ToFPlayer().UI.ChatList.Add(new ChatText(arguments.Array[1], 10, ChatType.All, player.ToFPlayer())); + } + response = "OK"; + return true; + } + } + response = "NO"; + return false; + } + } +} diff --git a/Commands/Chats/ChatBanCommand.cs b/Commands/Chats/ChatBanCommand.cs new file mode 100644 index 0000000..b441879 --- /dev/null +++ b/Commands/Chats/ChatBanCommand.cs @@ -0,0 +1,38 @@ +using CommandSystem; +using Exiled.Permissions.Extensions; +using System; +using YongAnFrame.Features.Players; + +namespace SyncPlugin.Commands.Chats +{ + [CommandHandler(typeof(RemoteAdminCommandHandler))] + public class ChatBanCommand : ICommand + { + public string Command => "chat_ban"; + + public string[] Aliases => ["cb"]; + + public string Description => "用于Ban Chat"; + + public bool Execute(ArraySegment arguments, ICommandSender sender, out string response) + { + response = "NO"; + if (sender.CheckPermission("yongan404.chat.ban")) + { + if (arguments.Array.Length > 1) + { + FramePlayer? framePlayer = FramePlayer.Get(int.Parse(arguments.Array[1])); + //framePlayer.IsChatBan = true; + response = "OK"; + return true; + } + } + else + { + response = "请保证你有yongan404.chat.ban权限"; + } + + return false; + } + } +} diff --git a/Commands/ExpCommand.cs b/Commands/ExpCommand.cs index 419ec5a..b109ec0 100644 --- a/Commands/ExpCommand.cs +++ b/Commands/ExpCommand.cs @@ -19,7 +19,7 @@ public class ExpCommand : ICommand /// /// 次要指令名 /// - public string[] Aliases => ["pexp","pe"]; + public string[] Aliases => ["pexp", "pe"]; /// /// 指令描述 /// diff --git a/Commands/KillCommand.cs b/Commands/KillCommand.cs new file mode 100644 index 0000000..689fa53 --- /dev/null +++ b/Commands/KillCommand.cs @@ -0,0 +1,29 @@ +using CommandSystem; +using Exiled.API.Features; +using PlayerStatsSystem; +using System; + +namespace SyncPlugin.Commands +{ + [CommandHandler(typeof(ClientCommandHandler))] + public class KillCommand : ICommand + { + public string Command => "debug"; + + public string[] Aliases => ["kill", "db"]; + + public string Description => "debug指令"; + public bool Execute(ArraySegment arguments, ICommandSender sender, out string response) + { + if (Player.TryGet(sender, out Player player)) + { + player.Kill(new CustomReasonDamageHandler("都死了啦,都你害啦,死亡原因自杀")); + response = "Ok"; + return true; + } + response = "No"; + + return false; + } + } +} diff --git a/Commands/MessageCommand.cs b/Commands/MessageCommand.cs index 1d50525..5b44971 100644 --- a/Commands/MessageCommand.cs +++ b/Commands/MessageCommand.cs @@ -3,7 +3,6 @@ using Exiled.Permissions.Extensions; using System; using System.Collections.Generic; -using System.Runtime.ConstrainedExecution; using YongAnFrame.Extensions; using YongAnFrame.Features.Players; using YongAnFrame.Features.UI.Enums; @@ -78,9 +77,9 @@ public bool Execute(ArraySegment arguments, ICommandSender sender, out s return false; } - foreach (FramePlayer yPlayer in choicePlayer) + foreach (FramePlayer framePlayer in choicePlayer) { - yPlayer.UI.MessageList.Add(new MessageText($"{arguments.Array[2]}", duration, MessageType.Admin)); + framePlayer.UI.MessageList.Add(new MessageText($"{arguments.Array[2]}", duration, MessageType.Admin)); } response = "已成功运行"; return true; diff --git a/Commands/PlayerCommand.cs b/Commands/PlayerCommand.cs index ff86f0b..f77aa26 100644 --- a/Commands/PlayerCommand.cs +++ b/Commands/PlayerCommand.cs @@ -1,8 +1,6 @@ using CommandSystem; using Exiled.API.Features; using System; -using YongAnFrame.Extensions; -using YongAnFrame.Features.Players; namespace YongAnFrame.Commands { @@ -15,7 +13,7 @@ public class PlayerCommand : ICommand /// public string Command => "FramePlayer"; /// - public string[] Aliases => ["player", "fp" ,"p"]; + public string[] Aliases => ["player", "fp", "p"]; /// public string Description => "用于管理自己的YongAnFrame用户"; /// diff --git a/Commands/TitleCommand.cs b/Commands/TitleCommand.cs new file mode 100644 index 0000000..a2c2d0d --- /dev/null +++ b/Commands/TitleCommand.cs @@ -0,0 +1,110 @@ +using CommandSystem; +using Exiled.Permissions.Extensions; +using System; +using YongAnFrame.Features.Players; + +namespace SyncPlugin.Commands +{ + [CommandHandler(typeof(RemoteAdminCommandHandler))] + public class TitleCommand : ICommand + { + public string Command => "title"; + + public string[] Aliases => ["tit", "ti"]; + + public string Description => "title指令"; + + public bool Execute(ArraySegment arguments, ICommandSender sender, out string response) + { + PlayerTitle? titleData; + switch (arguments.Array[1]) + { + case "new": + if (!sender.CheckPermission("yongan404.title.new")) + { + response = "请保证你有yongan404.title.new权限"; + return false; + } + + if (arguments.Array[2] == "dynamic") + { + titleData = new(0, "", "", bool.Parse(arguments.Array[3]), arguments.Array[4]); + titleData.Insert(arguments.Array[4]); + } + else + { + titleData = new(0, arguments.Array[2], arguments.Array[3], bool.Parse(arguments.Array[4])); + titleData.Insert(null); + } + response = "OK"; + return true; + case "up": + if (!sender.CheckPermission("yongan404.title.update")) + { + response = "请保证你有yongan404.title.update权限"; + return false; + } + + titleData = PlayerTitle.Get(uint.Parse(arguments.Array[2])); + if (titleData is null) + { + response = "无效的称号ID"; + return false; + } + + switch (arguments.Array[3]) + { + case "name": + titleData.Name = arguments.Array[4]; + break; + case "color": + titleData.Color = arguments.Array[4]; + break; + case "pro": + titleData.IsRank = bool.Parse(arguments.Array[4]); + break; + case "dc": + titleData.SetDynamicCommand(arguments.Array[4]); + break; + } + titleData.Update(); + response = "OK"; + return true; + case "set": + if (!sender.CheckPermission("yongan404.title.set")) + { + response = "请保证你有yongan404.title.set权限"; + return false; + } + + FramePlayer? framePlayer = FramePlayer.Get(int.Parse(arguments.Array[2])); + titleData = PlayerTitle.Get(uint.Parse(arguments.Array[3])); + + if (framePlayer is null) + { + response = "无效的玩家ID"; + return false; + } + if (titleData is null) + { + response = "无效的称号ID"; + return false; + } + + if (titleData.IsRank) + { + framePlayer.UsingRankTitles = titleData; + } + else + { + framePlayer.UsingTitles = titleData; + } + framePlayer.UpdateShowInfo(); + response = "OK"; + return true; + } + response = "???"; + return false; + } + } +} diff --git a/Config.cs b/Config.cs index 295a27b..30e3b9b 100644 --- a/Config.cs +++ b/Config.cs @@ -14,6 +14,21 @@ public sealed class Config : IConfig public bool IsEnabled { get; set; } = true; /// public bool Debug { get; set; } + + [Description("是否MySql数据库异常时踢出玩家")] + public bool IsMySqlErrorKick { get; set; } = true; + [Description("MySql数据库服务器")] + public string MySqlServer { get; set; } = "localhost"; + + [Description("MySql数据库用户")] + public string MySqlUser { get; set; } = "root"; + + [Description("MySql数据库密码")] + public string MySqlPassword { get; set; } = "root"; + + [Description("MySql数据库数据表名称")] + public string MySqlDatabaseName { get; set; } = "test"; + /// /// 获取或设置全局的经验加成 /// diff --git a/Features/MusicManager.cs b/Features/MusicManager.cs index f034656..ff1ebf2 100644 --- a/Features/MusicManager.cs +++ b/Features/MusicManager.cs @@ -35,7 +35,7 @@ private static void TrackLoaded(TrackLoadedEventArgs args) { if (trackEventDic.TryGetValue(args.VoicePlayerBase, out TrackEvent trackEvent)) { - trackEvent.PlayMusicAction?.Invoke(args); + trackEvent.PlayMusicAction?.Invoke(args); } } @@ -45,7 +45,7 @@ private static void FinishedTrack(TrackFinishedEventArgs args) { trackEvent.StopMusicAction?.Invoke(args); } - + } private static ReferenceHub CreateMusicNpc(string name) diff --git a/Features/PlayerUI.cs b/Features/PlayerUI.cs index 4751c04..a60c5ff 100644 --- a/Features/PlayerUI.cs +++ b/Features/PlayerUI.cs @@ -37,7 +37,7 @@ public class PlayerUI #region Hint private readonly Hint versionHint = new() { - Text = "YongAnFrame 1.0.0-beta6+002", + Text = "YongAnFrame 1.0.0-beta7", FontSize = 20, Alignment = HintAlignment.Center, YCoordinateAlign = HintVerticalAlign.Top, @@ -163,7 +163,7 @@ public PlayerUI(FramePlayer fPlayer) MessageList = new(7, UpdateMessageUI); ChatList = new(7, UpdateChatUI); coroutine = Timing.RunCoroutine(Timer()); - PlayerDisplay = PlayerDisplay.Get(referenceHub:fPlayer); + PlayerDisplay = PlayerDisplay.Get(referenceHub: fPlayer); PlayerDisplay.AddHint(customRoleHint); PlayerDisplay.AddHint(chatHint); PlayerDisplay.AddHint(messageHint); diff --git a/Features/Players/CustomPlayer.cs b/Features/Players/CustomPlayer.cs index 627ba95..7efc56e 100644 --- a/Features/Players/CustomPlayer.cs +++ b/Features/Players/CustomPlayer.cs @@ -53,7 +53,7 @@ public abstract class CustomPlayer(FramePlayer player) /// /// 隐性转换 /// - /// 自定义玩家 - public static implicit operator FramePlayer(CustomPlayer yPlayer) => yPlayer.FramePlayer; + /// 自定义玩家 + public static implicit operator FramePlayer(CustomPlayer customPlayer) => customPlayer.FramePlayer; } } diff --git a/Features/Players/FramePlayer.cs b/Features/Players/FramePlayer.cs index f989910..8f3ee8f 100644 --- a/Features/Players/FramePlayer.cs +++ b/Features/Players/FramePlayer.cs @@ -1,10 +1,10 @@ using Exiled.API.Features; -using Exiled.CustomRoles; using Exiled.CustomRoles.API; using Exiled.CustomRoles.API.Features; using Exiled.Events.EventArgs.Player; using Exiled.Events.Features; using MEC; +using MySqlConnector; using System; using System.Collections.Generic; using System.Collections.ObjectModel; @@ -34,9 +34,9 @@ public sealed class FramePlayer : ICustomAlgorithm /// 在运行事件后实例无效,再调用可能会引发异常
/// 玩家退出后必须不再引用,否则会造成数字ID重复的问题 /// - public Player ExPlayer + public Player ExPlayer { - get + get { if (exPlayer is null) { @@ -89,6 +89,9 @@ public CustomRolePlus? CustomRolePlus /// 获取或设置玩家的经验倍率 /// public float ExpMultiplier { get; set; } + + public List PosTitles { get; private set; } = []; + /// /// 获取或设置玩家的批准绕过DNT /// @@ -386,11 +389,11 @@ public static FramePlayer Get(Player? player) { throw new InvalidCastException("Player实例无效"); } - if (!dictionary.TryGetValue(player.Id, out FramePlayer yPlayer)) + if (!dictionary.TryGetValue(player.Id, out FramePlayer framePlayer)) { throw new InvalidCastException("FramePlayer实例无效"); } - return yPlayer; + return framePlayer; } /// @@ -400,6 +403,145 @@ public static FramePlayer Get(Player? player) /// 框架玩家 public static FramePlayer Get(int numId) => Get(Player.Get(numId)); + /// + /// 不推荐直接访问,请尝试使用ToFPlayer() + /// + /// + /// + public static FramePlayer? Load(Player player) + { + if (player.IsNPC) + { + return new(player.ToFPlayer()) + { + Level = 1, + Exp = 0, + PosTitles = [], + UsingTitles = null, + UsingRankTitles = null, + }; + } + + FramePlayer? framePlayer = null; + + string queryString = "select * from player_data where Id = @Id"; + try + { + using MySqlConnection connection = new(YongAnFramePlugin.Instance.ConnectionString); + connection.Open(); + using MySqlCommand command = new(queryString, connection); + command.Parameters.AddWithValue("Id", player.UserId); + using MySqlDataReader reader = command.ExecuteReader(); + if (reader.Read()) + { + List posTitles = []; + if (reader["PosTitles"].ToString() != "") + { + foreach (string posTitleIdString in reader["PosTitles"].ToString().Split(',')) + { + PlayerTitle? title = PlayerTitle.Get(uint.Parse(posTitleIdString)); + if (title != null) + { + posTitles.Add(title); + } + } + } + framePlayer = new(player) + { + Level = (ulong)reader["Level"], + Exp = (ulong)reader["Exp"], + ExpMultiplier = (float)reader["ExpMultiplier"], + PosTitles = posTitles, + UsingTitles = PlayerTitle.Get((uint)reader["UsingTitles"]), + UsingRankTitles = PlayerTitle.Get((uint)reader["UsingRankTitles"]), + }; + } + } + catch (Exception text) + { + Log.Error($"数据库查找FramePlayer数据异常({player.UserId}) 错误原因:{text}"); + if (YongAnFramePlugin.Instance.Config.IsMySqlErrorKick) + { + player.Kick("不要慌张!你的数据库数据可能存在异常,为了保证你的游戏数据不被覆盖,你已被踢出服务器!\n请将错误联系到管理员(数据库查找FramePlayer数据异常)"); + } + return null; + } + + if (framePlayer == null) + { + framePlayer = new(player) + { + Level = 1, + Exp = 0, + ExpMultiplier = 1, + PosTitles = [], + UsingTitles = null, + UsingRankTitles = null, + }; + try + { + using MySqlConnection connection = new(YongAnFramePlugin.Instance.ConnectionString); + connection.Open(); + using MySqlCommand cmd = new("insert into player_data set Id=@Id,Level=@Level,Exp=@Exp,ExpMultiplier=@ExpMultiplier,PosTitles=@PosTitles,UsingTitles=@UsingTitles,UsingRankTitles=@UsingRankTitles", connection); + cmd.Parameters.AddWithValue("Id", framePlayer.ExPlayer.UserId); + cmd.Parameters.AddWithValue("Level", framePlayer.Level); + cmd.Parameters.AddWithValue("Exp", framePlayer.Exp); + cmd.Parameters.AddWithValue("ExpMultiplier", framePlayer.ExpMultiplier); + string posTitleString = ""; + foreach (var item in framePlayer.PosTitles) + { + posTitleString += $",{item.Id}"; + } + if (posTitleString.Length > 0) + posTitleString.Remove(0, 1); + + cmd.Parameters.AddWithValue("PosTitles", posTitleString); + cmd.Parameters.AddWithValue("UsingTitles", framePlayer.UsingTitles != null ? framePlayer.UsingTitles.Id : 0); + cmd.Parameters.AddWithValue("UsingRankTitles", framePlayer.UsingRankTitles != null ? framePlayer.UsingRankTitles.Id : 0); + cmd.ExecuteNonQuery(); + } + catch (Exception text) + { + Log.Error("数据库插入数据异常 错误原因:" + text); + return null; + } + } + return framePlayer; + } + + public bool Save() + { + if (ExPlayer.IsNPC || (!IsBDNT && ExPlayer.DoNotTrack)) return false; + + try + { + using MySqlConnection connection = new(YongAnFramePlugin.Instance.ConnectionString); + connection.Open(); + using MySqlCommand cmd = new("update player_data set Level=@Level,Exp=@Exp,ExpMultiplier=@ExpMultiplier,PosTitles=@PosTitles,UsingTitles=@UsingTitles,UsingRankTitles=@UsingRankTitles where Id=@Id", connection); + cmd.Parameters.AddWithValue("Id", ExPlayer.UserId); + cmd.Parameters.AddWithValue("Exp", Exp); + cmd.Parameters.AddWithValue("ExpMultiplier", ExpMultiplier); + cmd.Parameters.AddWithValue("Level", Level); + string posTitleString = ""; + foreach (var item in PosTitles) + { + posTitleString += $",{item.Id}"; + } + if (posTitleString.Length > 0) + posTitleString.Remove(0, 1); + cmd.Parameters.AddWithValue("PosTitles", posTitleString); + cmd.Parameters.AddWithValue("UsingTitles", UsingTitles != null ? UsingTitles.Id : 0); + cmd.Parameters.AddWithValue("UsingRankTitles", UsingRankTitles != null ? UsingRankTitles.Id : 0); + cmd.ExecuteNonQuery(); + return true; + } + catch (Exception text) + { + Log.Error("数据库数据更新异常 错误原因:" + text); + return false; + } + } + /// /// 调用后该实例会立刻无效
/// 调用后该实例会立刻无效
@@ -407,6 +549,7 @@ public static FramePlayer Get(Player? player) ///
public void Invalid() { + Save(); Events.Handlers.FramePlayer.OnFramePlayerInvalidating(new FramePlayerInvalidatingEventArgs(this)); CustomRolePlus?.RemoveRole(this); dictionary.Remove(ExPlayer.Id); @@ -417,14 +560,14 @@ public void Invalid() /// /// 隐性转换 /// - /// 框架玩家 - public static implicit operator Player(FramePlayer yPlayer) => yPlayer.ExPlayer; + /// 框架玩家 + public static implicit operator Player(FramePlayer framePlayer) => framePlayer.ExPlayer; /// /// 隐性转换 /// - /// 框架玩家 - public static implicit operator ReferenceHub(FramePlayer yPlayer) => yPlayer; - + /// 框架玩家 + public static implicit operator ReferenceHub(FramePlayer framePlayer) => framePlayer; + } } diff --git a/Features/Players/PlayerTitle.cs b/Features/Players/PlayerTitle.cs index 652cee5..ab9d30b 100644 --- a/Features/Players/PlayerTitle.cs +++ b/Features/Players/PlayerTitle.cs @@ -1,4 +1,5 @@ using Exiled.API.Features; +using MySqlConnector; using System; using System.Collections.Generic; @@ -14,10 +15,7 @@ public sealed class PlayerTitle /// 获取有效的玩家称号列表 ///
public static IReadOnlyCollection List => [.. dictionary.Values]; - /// - /// 获取或设置加载称号委托 - /// - public static Func? LoadFunc { get; set; } + /// /// 获取或设置称号的ID /// @@ -81,19 +79,91 @@ public void SetDynamicCommand(string? dynamicCommandString) /// 获取的称号 public static PlayerTitle? Get(uint id) { - if (LoadFunc is null) - { - Log.Error("称号功能无法在框架内获取,请设置PlayerTitle.LoadFunc属性或写个缓存"); - return null; - } - if (dictionary.TryGetValue(id, out PlayerTitle? title)) { return title; } - title = LoadFunc.Invoke(id); if (title != null) dictionary.Add(id, title); return title; } + + public static PlayerTitle? Load(uint Id) + { + string queryString = "select * from title_data where Id = @Id"; + try + { + using MySqlConnection connection = new(YongAnFramePlugin.Instance.ConnectionString); + connection.Open(); + + using MySqlCommand command = new(queryString, connection); + command.Parameters.AddWithValue("@Id", Id); + + using MySqlDataReader reader = command.ExecuteReader(); + if (reader.Read()) + { + return new(Id, reader["Name"].ToString(), reader["Color"].ToString(), (byte)reader["Pro"] != 0, reader["DynamicCommand"].ToString()); + } + return null; + } + catch (Exception text) + { + Log.Error("数据库查找异常 错误原因:" + text); + return null; + } + } + + public bool Insert(string? dynamicCommand) + { + try + { + using MySqlConnection connection = new(YongAnFramePlugin.Instance.ConnectionString); + connection.Open(); + using MySqlCommand cmd = new("insert into title_data set Id=@Id,Name=@Name,Color=@Color,Pro=@Pro,DynamicCommand=@DynamicCommand", connection); + Id = (uint)cmd.LastInsertedId; + cmd.Parameters.AddWithValue("Id", Id); + cmd.Parameters.AddWithValue("Name", Name); + cmd.Parameters.AddWithValue("Color", Color); + cmd.Parameters.AddWithValue("Pro", IsRank ? 1 : 0); + cmd.Parameters.AddWithValue("DynamicCommand", dynamicCommand); + cmd.ExecuteNonQuery(); + return true; + } + catch (Exception text) + { + Log.Error("数据库插入数据异常 错误原因:" + text); + return false; + } + } + public bool Update() + { + try + { + using MySqlConnection connection = new(YongAnFramePlugin.Instance.ConnectionString); + connection.Open(); + using MySqlCommand cmd = new("update title_data set Name=@Name,Color=@Color,Pro=@Pro,DynamicCommand=@DynamicCommand where Id=@Id", connection); + cmd.Parameters.AddWithValue("Id", (uint)cmd.LastInsertedId); + cmd.Parameters.AddWithValue("Name", Name); + cmd.Parameters.AddWithValue("Color", Color); + cmd.Parameters.AddWithValue("Pro", IsRank ? 1 : 0); + string? dynamicString = null; + if (DynamicCommand is not null) + { + foreach (var command in DynamicCommand) + { + dynamicString = string.Join(",", command) + ";"; + } + dynamicString = dynamicString?.Substring(0, dynamicString.Length - 1); + } + + cmd.Parameters.AddWithValue("DynamicCommand", dynamicString); + cmd.ExecuteNonQuery(); + return true; + } + catch (Exception text) + { + Log.Error("数据库数据更新异常 错误原因:" + text); + return false; + } + } } } diff --git a/Features/Roles/CustomRolePlus.cs b/Features/Roles/CustomRolePlus.cs index d346a14..d40515b 100644 --- a/Features/Roles/CustomRolePlus.cs +++ b/Features/Roles/CustomRolePlus.cs @@ -10,7 +10,6 @@ using PlayerRoles; using System; using System.Collections.Generic; -using System.Diagnostics.CodeAnalysis; using YongAnFrame.Extensions; using YongAnFrame.Features.Players; using YongAnFrame.Features.Roles.Enums; @@ -175,7 +174,7 @@ public override void RemoveRole(Player player) { RemoveRole(player.ToFPlayer()); } - catch (InvalidCastException){ } + catch (InvalidCastException) { } } /// /// 给玩家移除这个角色 diff --git a/Patch/AddLogPatch.cs b/Patch/AddLogPatch.cs index 6231603..7a3a4f5 100644 --- a/Patch/AddLogPatch.cs +++ b/Patch/AddLogPatch.cs @@ -1,65 +1,57 @@ using HarmonyLib; using System; -using System.Collections.Concurrent; using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Text; using System.Threading.Tasks; using YongAnFrame.Features; +using static ServerLogs; namespace YongAnFrame.Patch { - /// - /// 在添加的补丁 - /// - [HarmonyPatch(typeof(ServerConsole), nameof(ServerConsole.AddLog))] - public static class AddLogPatch - { -#pragma warning disable IDE0060 // 删除未使用的参数 - private static void Prefix(string q, ConsoleColor color = ConsoleColor.Gray, bool hideFromOutputs = false) -#pragma warning restore IDE0060 // 删除未使用的参数 - { - SaveLog(q, new StackTrace()); - } +// /// +// /// 在添加的补丁 +// /// +// [HarmonyPatch(typeof(ServerLogs), nameof(AddLog))] +// public static class AddLogPatch +// { +//#pragma warning disable IDE0060 // 删除未使用的参数 +// private static void Prefix(Modules module, string msg, ServerLogType type, bool init = false) +//#pragma warning restore IDE0060 // 删除未使用的参数 +// { +// SaveLog(q); +// } - private static readonly Queue logQueue = new(); - private static readonly Task logTask = new(async () => - { - while (true) - { - while (logQueue.Count != 0) - { - InfoData infoData = logQueue.Dequeue(); - using StreamWriter writer = new($"{PathManager.Log}/{DateTime.Now:yyyy-MM-dd}.log", true, Encoding.UTF8); - writer.WriteLine(infoData); - } - await Task.Delay(1000); - } - }); +// private static readonly Queue logQueue = new(); +// private static readonly Task logTask = new(async () => +// { +// while (true) +// { +// while (logQueue.Count != 0) +// { +// InfoData infoData = logQueue.Dequeue(); +// using StreamWriter writer = new($"{PathManager.Log}/{DateTime.Now:yyyy-MM-dd}.log", true, Encoding.UTF8); +// writer.WriteLine(infoData); +// } +// await Task.Delay(1000); +// } +// }); - /// - /// 启动日志任务 - /// - public static void StartTask() - { - if (logTask.Status == TaskStatus.Created) - { - logTask.Start(); - } - } +// /// +// /// 启动日志任务 +// /// +// public static void StartTask() +// { +// if (logTask.Status == TaskStatus.Created) +// { +// logTask.Start(); +// } +// } - private static void SaveLog(string log, StackTrace trace) - { - logQueue.Enqueue(new InfoData(log, trace)); - } - - private readonly struct InfoData(string content, StackTrace trace) - { - public string Content { get; } = content; - public StackTrace StackTrace { get; } = trace; - public override readonly string ToString() => $"{Content}::{StackTrace}"; - public static implicit operator string(InfoData data) => data.ToString(); - } - } +// private static void SaveLog(string log, StackTrace trace) +// { +// logQueue.Enqueue(new InfoData(log, trace)); +// } +// } } diff --git a/YongAnFrame.csproj b/YongAnFrame.csproj index 79069d8..f014035 100644 --- a/YongAnFrame.csproj +++ b/YongAnFrame.csproj @@ -8,7 +8,7 @@ True zh-Hans False - 1.0.0-beta6 + 1.0.0-beta7 YongAn404 $(Authors) Copyright © YongAn404 @@ -55,6 +55,7 @@ + diff --git a/YongAnFramePlugin.cs b/YongAnFramePlugin.cs index 0fb00fb..7d45f48 100644 --- a/YongAnFramePlugin.cs +++ b/YongAnFramePlugin.cs @@ -18,8 +18,8 @@ public sealed class YongAnFramePlugin : Plugin /// /// 获取单例 /// - public static YongAnFramePlugin Instance - { + public static YongAnFramePlugin Instance + { get { if (instance is null) @@ -29,6 +29,10 @@ public static YongAnFramePlugin Instance return instance; } } + + public string ConnectionString => $"server={Config.MySqlServer}; User Id = {Config.MySqlUser} ;Password = {Config.MySqlPassword} ;Database = {Config.MySqlDatabaseName};Charset = utf8"; + + /// /// 获取实例 /// @@ -45,7 +49,7 @@ public override void OnEnabled() PathManager.CheckPath(); FramePlayer.SubscribeStaticEvents(); CustomRolePlus.SubscribeStaticEvents(); - AddLogPatch.StartTask(); + //AddLogPatch.StartTask(); Harmony.PatchAll(); base.OnEnabled(); } From 462146c947b2de3eac8f2e7a46b5262a6b228aa3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=B0=B8=E5=AE=89404?= <101850798+YongAn404@users.noreply.github.com> Date: Mon, 3 Nov 2025 09:39:27 +0800 Subject: [PATCH 3/6] Code scanning --- .github/workflows/dev.yml | 2 ++ .github/workflows/master.yml | 2 ++ 2 files changed, 4 insertions(+) diff --git a/.github/workflows/dev.yml b/.github/workflows/dev.yml index 21f12f6..e37e725 100644 --- a/.github/workflows/dev.yml +++ b/.github/workflows/dev.yml @@ -2,6 +2,8 @@ # For more information see: https://docs.github.com/en/actions/automating-builds-and-tests/building-and-testing-net name: YongAnFrame Dev CI +permissions: + contents: read on: push: diff --git a/.github/workflows/master.yml b/.github/workflows/master.yml index ee5ae43..fb0c1c0 100644 --- a/.github/workflows/master.yml +++ b/.github/workflows/master.yml @@ -2,6 +2,8 @@ # For more information see: https://docs.github.com/en/actions/automating-builds-and-tests/building-and-testing-net name: YongAnFrame Master CI +permissions: + contents: read on: push: From fd7becb234579fde655404d1977ffa500b790d24 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=B0=B8=E5=AE=89404?= <101850798+YongAn404@users.noreply.github.com> Date: Mon, 3 Nov 2025 11:14:04 +0800 Subject: [PATCH 4/6] README --- README.md | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/README.md b/README.md index 051e850..791c9cb 100644 --- a/README.md +++ b/README.md @@ -1,20 +1,22 @@ # YongAnFrame [![FOSSA Status](https://app.fossa.com/api/projects/git%2Bgithub.com%2FSCP-SL-Plugin-YongAnTeam%2FYongAnFrame.svg?type=shield)](https://app.fossa.com/projects/git%2Bgithub.com%2FSCP-SL-Plugin-YongAnTeam%2FYongAnFrame?ref=badge_shield) -基于[EXILED](https://github.com/ExSLMod-Team/EXILED)写的框架,为国内服务器常见的插件需求简化开发 +基于[EXILED](https://github.com/ExMod-Team/EXILED)写的框架,为国内服务器常见的插件需求简化开发 ## YongAnFrame是什么类型的插件/框架? -**YongAnFrame** 是一个集成了命令系统、整合了自定义角色及技能系统、称号系统、UI系统等的免费框架,使用 **[EXILED](https://github.com/ExMod-Team/EXILED)** 开发。\ +**YongAnFrame** 是一个整合了自定义角色及技能系统、称号系统、UI系统等的免费框架,使用 **[EXILED](https://github.com/ExMod-Team/EXILED)** 开发。\ 您可以通过安装该插件并使用该框架开发插件,简化您的开发流程。 ## 功能 -- 称号系统:提供动态指令运行集 +- 称号功能:提供名字称号和地位称号,支持动态/彩色功能(使用动态运行集) +- 聊天功能:提供ac、bc、cc等常用聊天功能 +- 持久化: 提供数据持久化,使用MySQL存储数据 - DNT检测和BDNT(Bypass DNT)请求:使信息获取和保存符合VSR规则 -- UI系统:使用[HSM](https://github.com/MeowServer/HintServiceMeow)预制一些比较常用的UI +- UI功能:提供一些比较常用的UI方法,使用[HSM](https://github.com/MeowServer/HintServiceMeow) - 自定义角色:提供对[EXILED](https://github.com/ExMod-Team/EXILED)的自定义角色升级,部分兼容[EXILED](https://github.com/ExMod-Team/EXILED)自定义角色 -- 等级系统:提供整合统一的等级API,支持自定义算法 +- 等级功能:提供整合统一的等级API,支持自定义算法 - 自定义算法:提供一个可替换主要算法的属性(该功能不支持多元化,只能采用一个主要算法) -- 音频API:提供更方便调用SCPSLAudioApi +- 音频API:提供更方便调用AudioApi ## 为服务端安装框架 如图,下载 **Release下的最新压缩包** 全部解压并合并到**EXILED目录**,如C:\Users\Administrator\Appdata\Roaming\ ,安装后请启动一次服务端,并在EXILED\Config内根据提示调整配置文件. From 59f810c47531ef26f3fe7b77382efbd716e95227 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=B0=B8=E5=AE=89404?= <101850798+YongAn404@users.noreply.github.com> Date: Sun, 28 Dec 2025 11:37:58 +0800 Subject: [PATCH 5/6] 114514 --- bin/Debug/net48/HintServiceMeow-Exiled.dll | Bin 0 -> 165888 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 bin/Debug/net48/HintServiceMeow-Exiled.dll diff --git a/bin/Debug/net48/HintServiceMeow-Exiled.dll b/bin/Debug/net48/HintServiceMeow-Exiled.dll new file mode 100644 index 0000000000000000000000000000000000000000..cb7623dc88d050e9d1e6dd5b45c7100e8df43462 GIT binary patch literal 165888 zcmcG%34B!5`96N`y)$>VBxEwl%w$i1gv(442!Rm77B*32RY4Y&#a)oAGoZ+1Vi2W@ zxNo3U!QHm5RjaLA)vC3wRa-aWj#h1})~#0K|9RhY=gyrFEdBcb@ge7&=RNOv&wJjp zpL_0|S&PpXnh?T;zaM@O;$HaluY=tmce)W>Q2pBiahLCz+Iy9m&(t1t%(2Ou6B6dp ziRH)F9KL+@YI9A^iX&?hYggACySirToC9l)H;*{7DL>yo*b+T=nh-~9QpLOn7Jr|~ z?Nc$ZCZG-%;xtt%mWin0K(|63g&om4(dge>AmTs$)5Nkf?2>da2~MF5)MT(t$r32^ zuqr+!!|dVTOINF+Z4YsKMXnKIUk78;nj_b(0Zw;AdBkzqt#V}8Kwj3ANG1*kfpvq9 zTydx8GIrR7&ZOM4Pdcc=Ew)}SMCVIFux&vrUayFU>oRE1=`%593Gki}D>LB5V`Yg( zLWnFMu8CvdgB&z`iqK6z9KW7;4-6(+fxo^BaW1nC!9cvCNHOXW%F`34Dqt8w47yh` zBF+GAe7&cjNa+oGA>Awo;SD!S*3CSKo)?KJsA5$N6hrqH1*BhNI%3pucYUT^#zG4-l35|r3iyGt5Hoc&8`%}7#>(Uf|VW}*%H z%`rru1+h+i0Wj+059GlD?UX=TLXS0dQ7O!^l9oa{cf|&(TABk@Y6_!)Bya!(cZR?L z5YXQw2M0j#WC$Dp0o5ZpH~@k#L*M`i{tSTwAOtc54uFuCA#ebM{0xBusE^QampG1V z26YqR0>C3J)#Nx7uP*UBYDeQa_+loQCau+Kf0~q4%hRMHLDEdEOp`up^?)>~fmq5M z9%X5@q%xyOnl*)LcEv`h1{#lUTunsMNf&=dE2DpEasp+YJQ`JBS6ymOgl|sFk_L*7 zQB%#8ePh!>%FLN|AjXR+yE9sn5xcyf*mS5LF;7mm#8k01bz#%oO(~(~O6#Agd~cXW z?wKiFVw)6=k4&jnS0%e(#WcEb7Qon9P)s02@m(FTBf8o?NRXU_u-T1}nj-d0-1I(i zlsXf)Z*ClQMZF7M8sf?P<~=0MNhNFUPNhOHHMWm~+x#6;$7ZXVffk{gm2g(l*r3NI zs9N}(jTjPLGzRFglTusInv(#&b7Z6_sc?gvW5A0Oq?Ba1M|B7MA}RkG-u$m2*PDKe2BS?IT9nNuNr z!~@w9*K!#!WaX3?!_beEm}C2tm}%J(SF>0q(ztxBU0$knyS!9WU2nswYmC%)?L?qg ze+s2cPJ@bM9PopLOL#{46e;n+Tw zVOrKQgIFvRWn0MFhFZOC8)~mz@4#``=1*DMP>f|8;>@*8ma<3N5KFFYvXmU#5P3J- z4B^Ng88!dCcefj;WO_>4wB$=84CeCk%a+|e(td& zZiqD{@>Ov{Hw_iBTV+4#>H%;V^a%*G8XLv1L5Y_dMAw_SyiaC%DaPg{19iQX%lpSH zFU3e+OpFl#Oz)|v<(HEGl$@?Gwo)`~cQwk9CKgqrWs9CBwyrP{OpKKN`WW>oEDLB^ z8B9Kn%+SBn?`F94Ui}$T03)a0fT`mFPoom^nAd^GVm#&y7K0gaf5_*ESov^8phmIE z6hY=P5$E^EgGIuai4Z}_3c@T98h2rZCwjveus)azLgit$`dG3pxg>Lqg$3hA-qR3w^aCsNJ1NNd39 zCu)ox)s&ova5tHgR$2!T`v_-R=t%38#qd3(>+_bb?~{GYSYZklDJIhT8;4tyVZg&P z7PNkWw4Q`Gp6MJ(Jm!I*dNeuSW2Ji#X+k1-J>n9lBTuYyg2_KydG4a@wDbq?x-i|q zRzyM8^C{~H3kW!3Jmvz*K~GVNB2{YGU}>1=&1i@vmP12}-OJi}UAA@ylXjFV*=Yya z=`iV2PxG6L;Aq?f`=kGc_>peAm5%)W()FctI%+E?!xmWS1=ZwGWRymA_|@bR3LZj1 z-YjU5VTFkU(E<{OQ!_Xe5$jd7$r5zRavj@`5>#`!CwUkpTT01NSvS3`F9Ac7AKh>T zycq9^?tl({=%8&OfoN?v+pSG=u~bMT%>v;(PmyXIP6AS-pH`%qN5F3=Rei>hHrbat z3SskTIQ15zZXQF?x^b+{Wgf>t(xcgsDyK-Q4 z28+{fpdvth*c6RJ1jweWGzMVUC`V~kDqW>|Wj0>c%H>V1g4hjY%t(GuNsr&tpzAU# zm$Y#>=0m2k&-+B%q->rv-tSGGLo<1@{k)En?REBc{!?bk{2$R8e3~?1ixSh=h+2xO zIZciXN;0>G*lQLyBP+Zczl@Z^SPsVHJZ`UKXEkvL8cF1w%`it@m_hP*WOhyD9JEi6 zFs*e@+}#l(Vyq^i}c*SXd{~X>`n4ssM>57_@21&)KFU z=^>yv8*8QvDn^!IS*DHtn2hjV$-tD(njK~-ydDZ$!4!gMAF7xRJ+XPB>9iBH^ykp6 zNT}&A*w@nkV&9eilKqnOXY6-MHp7h?DH4o~E)t3QRs~8-CuRMVJw-*&bC%uf=%1Og zlU@@cBk0iU@0_oi{s;S7`k(BVq(5Q5Q$`!Q)Q6DN=N&b9DisU4Qv)rAmsBona4a6;d(xQFtK{mJ?2>;H0FEF z&G2z#B}B6l(-TKSzQ;HlwDf9j$qB!2FN1#LM&Kzq6oZTG0sI&^E^1l`EWvdkxnXY@8Ghn zGAeqF0JqUNhmG$6^kc@gLy z0}HKqgU+WnF;CaOk$`sw-yqPdzfLB(1blVf6l3_noX543?=dd}J-HQ5$mKD&k?(H1 z6BQS9o0k)U*^Dv>Fs}gOs%%H~3s6fyHT;m(mw0#;65g~)CLrlI{z3;Bqn zJ;WIJ`CJE$pqf{MPc<;C>kU3NH3B4mPq}KK^WaEA!aOy_tlKGHI-0Zc42YUIO=l!m z6{u1EXEC!}Elm|uPxne?it?N<*HV5i?s>7C`sq@ST0r*OfCgPrF+>N_rRYDQ-AS|m-AV%EfoiBSGC zuA>-Ar*?VJb-1nS2=wajpWPDaa2YxX)Ch1*3|*mxDif+-0>7DSTnO?PzuYFi!i1ocF@3i zBAC{*I=QA%r3}oHy4rOUiR+{sv-RFKC1Y<*yaF8@^~Lqh^(9l@Op27rCg8_7BL}H8 z)yK~5Nb17;!<$-u5VR8Eozxd)m2<<%rZRp(!j|?ctY<<0Nq$L58v0K%sDE;%nQceX zH|#e0@Sn0}#<0r&oNc|!n_KJeXKS5eWUcqxT*$&~kiDvfOq<_lUPd2Ppc(C^4|nrneSvdPZ>ENuq);-C?Dz!!pvm|M|{(5z`o#1T29v?6g5D50)xYQK&3iDSm zML!E$Dl`2XG$^~S?O+PE6zW9WQe^wU>O_uQOtYeIfneiSGIXC2iPwIkAu9siGHX9P zUE{eizE$9|_I8z=>>^$0oEdg#I;%H!53=;K)DvKo0_HPuFXk|JHOugka%A=J-& z)tjamHHDGcaouyeR0ALEqvoeeuU}YU#y)RwK%nlXB2Kq)kh?MN9s}CI2wqYvtn0SCf~2axF1~I)EX_)gbto` zx~YL-a0p?&5Jf&^+-5pJTnk3kuQ#g2G2N`f5XWboL&1Yp3Fhpv;PLALk7hgo(Q6if zJ5TK-s@G%WqvQB>Ps^J$?$8-hf9W3juj$<4Q>3SVYVu(!<^+hhEHROTBcND%5(SI# zFZndhpi{C;(<$iO_&#TEBhnp+b2WHW7pE_9H+a-Eea#Xp2YJ0={FzzF`vr+fT5&c!l2PbqU4CE;3FgSC~)g;P^h ziCJu|0rnGZ8!}~5#bK~*70Sf6a}4)vJM&M-Fb`+*s)5Gm&-XRx(rzF;L%Pt}yxJSa z0zGp!PX;xgMVxcMKt(FhT}AJz8Y71Z6(`X9A1L*}(w>?%J<;I z5s26Gwl@&38hH7(Z4&}oTy%|He3tKR`Rv&;sul^}$$v-25x^9Xwu<(cn^c2Z! z2zk&Yz9EK}z+hmYMidsb*8!y?;Lv%hPh-R9@^l5^@+LqE{*2Q7g#}X#9X-S$?%zay zg~Wx3kfO9kF@i=(7Soy`zeqD)hrcpU^TI+~CN4JK0Laz|t?Z<^Lb05TwDlx!X z1Jd|*GUTE#!Q^*HyNB@&8~r_wZ{L&kABQ&9_}1X|h1@-LYVv#(GUVc}jE(l2;HVF} z5al?-54tmJEJI8_PL{R*Ctg=mZ`v&ibF)8l*M;`a)Zb(sOzc|+WHgNj_8d!R*4aK0 zuFlw674iQj=PfEtuAoevMQSo~G_l{0%jtR>Vz_<3gFvtTF5KjMMC+y)^L;pda>?pD zYJ$vXv4+t^bv$-5?j~F9PQIsqGM0(`aogO-G@+Kx|J6eOMP_r^qAipK@c)z&$vcsaY`5V!&H^10W+(2>@EE^GBRrr*^Y%gbH8Ipld* zp0$*F$hnlujKdx=&3dl*=Uhd3S(vLREemZ$8=+`DY{+Y7bo3lu+xyjZ4=YVeq{n2D zma-4#C@aTWkJx9H90O?_S&cj~ZU>VET!(nRhN`k;@v0Y%et=ykrC^p*(&y#C!T<4>eqsDa-YqyZgY$oOdBa)c#SdM($0LL(hIbt1@4=!PSJG%XLsgBf2pInWf10*OJVvNuG|JtCazo>PQdB;w zhn`CouwRnKb#35INjA!15DOWffjw5%wJ*u4QoGrwc}o}NDxWI^6D2y9@SlS(AV-@-)984T<3COYk}f&xf&dVS)KF zwJ&ivrKVye{|yJbY4cn7^-`8EamJ5Cdwq#(`;UGeRc2Y__u$woi-cT#QbjT*IV>aW z8a7?X&B_H`j)F;w+d=UqUd-qg(tU|9ZQ!v|2lakRi~}@JE;+Uj^Vc=1^|4~(Kd_A) zA6?=kw8!CSkMiLurZm0L70&B9LY=$z5NM1o_B3rSpGTPAA({C-9Nc2*h1U?zE~D~w z^9PVZxaBAm_-+p`hJ85FbDIxBYENNEm&a+D8xG-E<{3Fu5Gz)QLd^FHjbRyvFC5M9Uto1?uJF zNIXsUr)Od$qWcA&`r;%86FohP2skUlg##S1>*?8q={PNO17Qx0T{JJdM3pAQ2-LC0 z`*wfQ4T%B0Ybb_4-iF|y2>bU6nn~pTonm1=2SD4v%4RJ_v}R*8fHlPxSDfjp>CK z(%ZTeXsDYgjGrG|hdfCv+Q{L2nn1JDirPBuioPz=n-tOiUpD zpx4B-;t%D=hZW@;IJoeK3e;eM$9NWI2n`4hXo$cn0~}WI1P8EQV8?lhzwt@Tr}@3% zarS%~q!T(+h@Ql;hu^4#Hbxbkx~_PxK2@Yo5qRplDaH&T*o7seQ|D^pDP|suF{(*g z4V;kA8}yktrNK$Qd}4l5FF!HYQC0SdA2lx%CoDLROGG@F0I;9J;}sKUH+aO*b_QB5 zo-RZQ;qie{3&D-aV9>-7fDbTL{7N-_q2`{D02{N>?~{t^8F{2hTmY&CM|^lSmuCU(Ft zfKUI3|L6F-0JKH`r<_xOCn4^)@SXgNfU%GfpE>BX#yt~wBzgzkHNpCm)-WmR|9Xm$ zc{TNateX4Mp^l!$Vl2bA2-r%3CnP$Z8e%bw#nFqXfIOGCSFZy(iPHIvK~#Zb)fA08 zR+=%0EYeM^ukl74=WIpvk()dgj5sLln^ZHgJoYz?_E|ZGJg%T;w>+a#s4oRw{JvB@ zTq!V#b5_iGNeot)@`AXYf>8>cx5#UtEyl-;f}t@Pdrfo!f5QhsZzda`E9l!T8{7xz zqaRYDWB6tEK`-YIFROqBtU}L2AxG9=%FW?~Noyu8WXnqRqyQ_;9HeROKh2_?G*osg z&HUVakiou_7h0<9Db0aMGvyuhVp}~j|PrMtk9E^(~`I7VA67p&pdx(oG~xGyd5U(HDT8fmJ1$>GSd zo9Z%l0B$Nf+EfzTMY?n97C$31;Gb+txTJ~*Ek&cC)rd4XI4*^GtOm6^(?W}BIhbTK ztHWJemPF&`A}e|c%Qy}C*wH-j9?Hq6?Z%!>H2d&I&Rm2OiztNspeu1Dg$|(5A1QPo zg}$fIK?u>&=wC4MHhNU!ukd4$%sycS$~Bt$R`!-%gBp&hCLYfE3q{v_q;@`ONKE&m z#&HHj_bQ{Rxf$)LbP+w$^XGLf0JGP`=;+VyDG28~Pp`B0+N;Ir1)1{#H@~a#KjlBm z&c8#=D%04aMx-)PsZ8XYYtc^Y!qwxiG+UvNQHO#1zi24WGpfa+b(u3CP5c340R5B4 z0%Q$-vAQlXkMuZ`Rwi|cLmlDc9pO_PVZ3N-^PlAiU*-t!aD?x3g#Y9SKj#SVbcDZj zg!2R0ydsWp+z}q*2v2c@=Q+Yl9O0FY@LES0FAm$~I@=LG&k^3{2;bre-{%NF;RwI$ z2>;U&{@M}#!4cN-vN}W@;URXoo0_I<^KLOo6?Ba)h(`~}(bP8D;KXnuM6ct=aZ$yU zY6k`0Sa>VpkAt5a569oN5Q6Z&2MzDIy5~twgdfuqEyyY{p7O(h>Q79{frSd^lb4)? zILro%AS2`s;|7cycSsLMBU0%xq3(`0Ve(prSl;JgjzgTwwbGn|bZQFgLA+Kp72$Bm z(}n{efn__rgW?)KR88UV$E9TmLC>PdLhhAv#FcEgo8!ToaXrYY{VpV@;Y)f{06}wyw^NXesdFy>WWHshj(N)vMwvDxR&ljMs=X9VDxOvJ3_`K=DQ` z8pqVQjO1ev$L|l}=zJ$q;Qkk78(BziCAs4DKGm6DHlJKRnMmV-XX1CX@W|KzlOc^p zC^{|-`NGX%+a}m_&;TV(;iFf8{SCOpw43_amCSRdqcuL(E>u4}H=!muyg#Ht=b7*@*&m8%HFX%fhrrd7*pSe@ z9k;;JNVKyIY7XWsBnS`pppI%L$I+UYI2*)cS6Yq4z}6Y}K&H8nc^H4tNz~wvHU{xF z&6o@3LM6VBW?*Sap>cL-gk~H7T0>078vI-N-w^Fv<$9^ zEsbA={qYGCsw#OOBh57!PIDE?NXh}i$Q)KREu@s(kxkSpf@B_ZF@mx6KPpk`=o0IZ z=~%P{UU*_+c6OQSaV_Ju>IqhF#!3SB4oaG077H%zQK>THf?qdYMkfq-aG~65^+CCu z<;x`1``b11*0t{I>0sGHTGkghi{TdPUR8aE~3kks>$tiCjMR zmmnklq_O8v{Na7#SB<575T6{2wGai?j=h%{+ljHvk;~Y(Wc&$ZAEEd%icd_(kj@XL z+p&TYZFsr~;yjy(jjd?=R3Rd*MkOcCr9|87Or&+LBvR&Wk27(Jog9li(RK$DX=N)p z?<3BiGx0>5^I;*9{9ieuKguD8CoIaddJqYEtg!ST7&iCJ zftH_m9hQ`f;!;(^VZhtyHVp;RI6BYX5paEAbCrWjG2SAsLcCGMLxzV35aLtvGt!E| zryB1NA9^VdHpCFfVbF|sC4BA4+VF+^k?;Aj(vn0~wi%R?H;i-Vn8 z9JG=39a(18KUOw&WH8eh3bV0e?N}6-sw~0_6q0&i->6bMYGvQ3upM=3-zd4_A%T}U zqh!S$&Xt5N*EcF`%BZk4UR{BPIiAL=F4`?s`-~%y(yyCG!fWW%&7(+=c{E(}7&ykU zZ~~GX&60VD!?EOTnd}-Xe2Kel5b`DNvq3ms<;jazpi9(D_AG|? z=OEZSdJx-M6_~L3pLHpjR^=-0WaE^>pQaU>b6&UR|K#x$xr`!{IBD^xY4}r_Lk-)<6G84?2r?e^9z`A=^|C)glaF#Sc>7}+kR*WD{;>d}PkDWe z?kl;=x{kIIvoGi3sdhQmQ0B)_=E=1b#L1bZN4!=|F~a3ZNaMGdjFZ4)o(xBeEGksA z@bK5M-jvU>C&9iL$U31w8ha#umW^!^{E{^G)9^bbnZ5=^&$0Ik=6 z9zvgxU!>5IF|5n5>>(X>a~-ng{;ATP0WqZ?{!_q`!>^m`N$V6Pondssi!4h1lMG~8 zCWRFR-KAyY(T&^8Q!1u!)*1^Fe}qDb7fGuVQNH!6rkSWV-9=Au_1F#lvY6;;IyO(= zg9SUqZ-^5*Q@fr9A9WCP7r0tfjSlr7)!m@GBTe3Tq3&Af$9;P1tZ1RX0MDfgTvpT~ zN7N#}rZ2>I&iYpntxY$+8dytkdFdJ7KFAw?$Qy?E0THsqe9{<*mwNb+ zF%J`0Ir7k3y;jI?-7a~P&xNepB_vdyyOfB!c6sjd_+IHGk1pwnHOU~o&{$b7R~X;3 z_@3%`KmqC)-Q2%k-liQ{m{H}-9{n=!E_-C;__LOy(UM#9yaz)kjmJ2g zHF>`*c{KBMBDTx16MY~+W4G+B2#76I#FdM|20!-qtDPuon`DloY)0W?5`KMZbH~C~!m!Qo6{iA^j zZ++fIt@97mI(cMDQx4FBGJqZ=pY$O4qzB2zyDn*xukuUF<|Y`RF=8#myNS+CG|gG# z@=_G$XvB+_CGfi@pfT}N`SIMUMpCQ7&H~$SilMK;#p7t85%8v2mX!`?Ue0u*vgs(s zz*rua8NxOjphIkPb~HvI>Ft)pf3k&SmM)c^rs~DUSx}&1fJA&jg)U;!G7k1q>0J(f z&q=dhacV#hrF8N&Cu1`bgBh2DiCEXD)rVvBZ2^C5h1%%W8ddBp8Z`Jg;?~Ss@Wh(X zd!D* z4$kk?{0s#19PoBc%G6~C0=;@0)#bT}sOzQ}`Z#BtKIIoT&jWF{PhnVNw@*y9?n!3y z-T%Mki#>>JLo(knl<)bRFU1(mly4d3d%<4kJ0Inpx#xVbl`=1cu*OjGB9f`5$O@X* zyco#qGB1JWd}N`9UCB#9Glo(#fowTX`NYWandcXp_$BDGkY^Z+6tc48^(?J%yv%|P zZC(aZ`FPhzGqxh+qKk(ZJR^P(E=LgW8qF)xdc!O1I|P<~_!I?ejq_r6Pe;&|O^L4< zMPZ>v?47wJ<`s~W^PZQE_dp|#Qs}r!gL}9ba8=yEuEL!lsE=?!Y}k@5(-MW>c?`0d z`YTuG?&X?gl`G_en(>i*KMW@qIPr1edES*&)>07pzNNpR0Ovq#@1Q%fhz=c_3vh))KIH4cSuf}7cj2~x0^aqIw7O8PaJwww%wo+ zin;ykInJSH*Oc6@kK?yY*Qc01T|XZecVzR7OG z=TVp(RZEesQeiE10fot-&myqU?I?Wan-9yyj9mcv-^&K$b46XY*LH#^e;zyHhG`S!6Vz3Gri0oryJ<2j{K>b_9}mweoWu=WW2pf zzbE}kz~1YRQEi_Yc2Fq3Qg8~qGbS%IQK`R?5kDArq!|BI>p?c zs}nVxpQ00`&*&sO%JlzLC))Gp)HAi+z0_%3KX&S*^qO%k`a9m`Bx7-BNG#feVi{Wv z9+qpX1%36R&a_v0Iqn8KdM|fIvejs)#DfS^aAR~PYA`tw<2Rim>1x8Yp01bvSk{DGA+#J&*P8G ze<;et`I|W1(*r0_z;66JBza;;n<-Ppkc>>{cVl==;WBAS92jPFKg-s=kG5HPrS^AY zXMjHK~(Hw$OeJIBa=`#7b~^d}0d{Nnju_3;(5hOm3Vx?E3UwabTmdhA>| zbeoTYqNZqywYE9Q>(EE&Rb(8QI$9kJNPEQNGJOk^!TPD`i%A;4IB_kN0Als-oeD1DAzJoqP8 z{*QVs?z`@wd1Ej28l9Qf9kU)!KACj~&q0Zedr-+aaaxJu^uTC_7{S=)jeMTn= ztBFhYR;SZ&(+mqd7jA`M;^cJ;Rw!5>W|tbgcemF#dt~o#g+OwoFfD~;pDRrcW_-#~ zW~-$rTh6=B44zpF#>I$3vuo1@nL7C&^l(cRtlX`H(I3yVYQIdLvd(s!pQ&hjS!eyO z8z_BF`(~RbZrnq~?e(}$7XB%EQTiOcxXKa_{f~Mb(zlIMmG7lq{q{RbpK0UVU=x4c zgGzhscZc@XiJIO|(TUP$bfU1D_;_!1+N=)3hph1LzKQZnQP)v=x?g~Y{^=V4=s_R* z_+=U?zH+4h1P;&X=03 zccfz9c9@;l4NDl z!*Tvi4Ln)bV-!l=Op@UL!t(J@NB*1}2N3bA41ojZW}arIDIp%uQaaUb;Ni0l4^L28 z>MfKAiEp+1+sIGYX(<|MDHe}*ITFmbTg-QmzrbcDGMJePt~)KRU*~cW8C*;S*Ig7# zKXu1}_KYwC&%5y0Gx<2Y?wwMSJQW_OMfmrzVtW(F)Wi(U+>h=tq~3)n`2cpesP}e@ z!exQ?LA3JAB*4SWU7!}L{L3rmZ|GV<)(A(@VU8=k3Lbw~`R`~)%eWnVf<)*;|9}_J z>v7j{A5Us9fO#YON7%dxE`6EpX881Y1eYfKjT6;you9wQkDHaBf?1Vc<;O$vk!a~V zaom7YV2VH&Ag{Ni9UVq3u~I?KuOO#q;##y4rLNIcAC3>GS3Ca+R^t}LgnPB#V0}+@ zNOr+QevsaZGjBx{f4IZ?qCrn7z6D?1D>Y#i@B+eZBsr8zHf{$o2CeAXk%C_vSp9RM zoeB&Sh}Bn%YUrUby_)}B=0!PDfxG)d0%Qyjb@}m|dxv=QhrrImhM1M5Xk09p%Y?}BgX{`TV_Hk7Xild>&3iKV^i@b-Lb-ys-s7rBl5Dd56|@dprS zoWvs}=}DKx-K3fPfeB2nZPcOv2p#ZysffVq%AMr*mK=iz-8@E8I!JmDlJfg1>Z7k+ z%3sI853nMgfiV;xt+w>`vEDt+A>Cuu9F>NDyMk9Ui76OLWf6nA@i0VX#?l(R;D)i3 zbuO01WR>w?pNG`4eq*ghnQ4;~Q7lYDq7HUzhA+oe*(PUzwh(_c79DN!2Ncw9lkZZS z)S<22bZCu1_iYhj*mCOgZDu43a>zG2aR9R5E|3SaX);3YDsVF>qzKB?T%nuZwVv0!_F0%{`ENik)8wHGYpO3iPz#vk(8F zrUzcX{8q9RQ;PNj_4ANY4-h_ctNW7^sh)EnJC%M33wv{VQ6 zh7?ZvUFH)`?#&v1Qdi|~&~k7@K3=@SH9J?YLRZVev8RB;!1Ckp5aj3Iu4srl>G*X+ zV!@J|?y+SumhERb>H%vYtkcQz`29oTyozdnR?d%1;q5wNNKK|Hff=zjV>}($aX(2? zi>+_NW`FkV4Yn_a7W$W2chfH%h3CtA6d004Z7u)gk^OtqwrR?cbFOKyKx}6v%1K{z ztgMagsEYog#&D`iih9y%Ydcldo>NutIaSS`Q`PP{)xh0S@tlArA`V2IXeMckAHh&l zgNXBwq%heJ{r*RJGF5CBYOtMA4#|9qB-)GkGzKU74KMT>4$;~U3uG3v-NzD6MGvaFe@NGZ4d+di2-hQJl!sfoi50Fs<~*c{ zJ0;l|Bi9#%jr|}yW2%E2fng>c7e(xS; zHD3j$E!u1Ft*sdeRefoU9hej_R=bKc)fh|bj*C$U{GJ0y`D!P5y(Q2?Zp|naWgT%(|9!VI^|bwOMjz zT}yj2dRu$h<+4qx!VnkV&p*!qdVzRur#(kek?eKDFlt+4L9tt>Y!jH<=oMMJP0Xd@ z;T@bg>~~6NjFa_4NY>9jn)wDSkhla3B{}3aC0i(q@y;v;V!2!d!^9{Mq(D=0G;wt} zxkhM?t8(Zw_%G)p%qIeyan%1l;Kx^lzQY8g^Geh>3DZ)*T9r&itjY^vud$Qrg=h6F z)nj1ki_uc{XOAc@x7Q-mkW@3UUZug5#<+)(=kc5;^#-&#>Kt;<-|jKq0x;hu=N&lI zp5BGuIF1*xlmPANJ@RBHLVFqy%k`Y7rihBhL|$*niO7rBu#^Ns-iMdxF?PZ8njgUJ z3F0@)7^7)@NCbNa#JRBeoR*R$JJ(=Ayh9;^a{W>u&bY{K8`P_F)?l}z+^f0V)H6|T z>Zo?Phf){9;>*wdh>ke8AIWl40&K`b&G65e~WXZYZT#?MIH4DVrjdnR{M9C@Vbc`t`my=q!-@r`aPuz@F zY<`4Lz!Oe>3_s6negdy+9C-Kz2I@JzdNa(B{5vA*x+%uMLOyQ(6FA?O{1hI(F1R%4 z&VF3EabD0}-EMwHQMi#DZk`l$hjBA`BnZZFa9+S$=lH=Id`jbUB6X0we^KZQa=wHU z^71=0xOeO|zXC>k_!?ea$lZ8JPa#H^fb%*U~oA7B(Fb99MzJCRO z1^AF3~y=16h|Klz!)P2FU2?9yM#C&{yGeIgAQDiICk~XN#gMS z9G{d3f;Rs^@ga^?DgQy!=kGTa{x`s<*8@*pWv(D*{6qPagO}bD@KGVZRa)p98I=1S z_*;iRC?{rs2?GhAjiW-vB+xOuF(28{W&I6=kGV%&hrcTPCGZD!E(iIve}#c>P8V;Nk^2a{kCjunlif?$jWPZ4 z()EzAnccIP(#w*kl^t0LIfHwfba6u&xm!yIkAt+xtF?a7YW%sjK$MmLxmFjw&95SS zQ}EBVMdH``A%0yvpcCcwAr$-Ykm|OT;>?m zbWyV|>g!)cju(c=T~jm*`Y#zs;iKK;POB+LDL&&|Ru81uttg8w=0-@`RiSMSABY*4 zDRgo35TYDbhQ21Y)={eJl2>bgEsE-d_<_q36MqUF=F`O+T;2=VJ;g)PzH<}*e4Qk0 zcW-N`R!C-%c&nCjd*DUn!}(k zZ>$pgjd>HgZD&1SVx32D%h?we*2PRO>GlQmsS>WLH=C+NrM}N7U99F3ZR8Ri6r*z8 z;@M}^2=Uvo^9RG)wP*N7h?6QPykW>0u*u`@eMVJ@SK#X6c9wq;w5<|%1*mi@jH-NH zwCK0gREci_Ps810P9sCe`h))|R2JKO9yjp4QhkmWkEu_Qr_v`Y572Xps9p z+7I%rq&E3f6WRG^p@WC$;y-mHXGc4=`8PSdJwB__FY04tlNxp(7*658!9Fo@SS8iw zQB{;`1Y71=w)ucON=56kIqGrPiq(s6;)!^@_-#u9`Brgzd!5_c5A1#)5p_-Cnn;De zNw|wD&^||wqxN~VPI-C#)Jm(0DVIvrLY0^_jB4cAArziBgls;rj@&OJZ#E4SpAXTC zb#cH*ioJAjRellPa-~*uE0^ex>^2T7ZyF))DeQKV2@J*a4mjuDN<-$Kz|Su~~?;|vBvpbntrKtjy@{7fnI1Jw4Zo_rCc#|!B9d^bKLA1xLKUW=tf4jh_e{|mC^0u97dNix>KCb=pjaT;WT?Yq;z}Ais&Ogmnu7eZi-8^ zjpMFvlIU_q_k<+6jyWG6Ez$KHx3X5E8#u0Ws6;n1`fP|qH!)|}kmwhTo^6xpSIqg~ z7>RD-I8B%6w~U5bGVf>3CoS}-f+C4uM=A!suiTCA{Sg{gOz1xP`XA6VMh{wO45LRZ z&irx2`3DOf(N5@378)~>(6bhLc_5)bTWDc`&|iSG+Cni8v*dEIlMvd=e6+UZ;$87H zquZdta`B#cmeEZd_r7@Efp&>MD;g|+M=f!FC|=^YUwZK)t>P2$GNX?$KD-e80ukO%rs^e`HPv1g~~6>mAx>B>7C_crI?Q+6pTbiBsEn~+ML z@*&6l4kg+t@{~^;=>{nOV05UPawt+hXU?HqqGIJsMqe{3QNEUl%N|v}Wkk=3FiI)k zG1`~)ELVCNP2_YH3SOj!1?k!Ca#5+Mj25z#Dg`&45Qkq)L0q+hdmTW77}Y5FeJh|j zjA|7>quUt`#Oqz0j-?Dz3K*?sG+4n$5Rk4NR$7i;i|_T+W@^(=$~dkQdhQgB3f||i zdpxtKi*bTjqFWgadWp zX&KeZT&|U=%2-ARS!g25{2SNNRAmaI@3}UoE7KTlWwgICozY*JbB?l~+9FU;G*frU`h}{?RiT)M4_k+?bf`J`ctyq@- z+u~aBH{&6=)0-cKs|=;^(Hwq(>BA6i7H5op26V~4GWasWpB26e`VYf)!u1dT8z>)C zm#Ve+kYgji&K$fvp5H?BE}+Bt+;sDOi1`wF{N4=T2Rs~ZXLY@?h9Os?ahZH?E@U% z*>*g_+nN(_qeD+dsvCxO!u=$+0q!}GO>iSziW|Tm6q|!*m(1&K9I`{3*Zo874y{>C z9CJR>dP0}LT~d1k+{)Tt!le?mikbC0v{rF7yKC7!lig)-o5ee<|Fw-b7SHQ`sNybY zSQq*Y(o(q;(Kd!GJihID=#U}ED@vq`d*No<-b2F{h86L_+XRcj)oR zWpRE2^zr#SG({X0I2qyR&@wZ&`tztxP_8N>i~SJTfbfj5WUDfEPht0$>^|iq`pxW) zA4K60yGOBmA-iScHbKI=_OszmhyBr#2cAzdONswrcK7FYYm`uHysM40I=Af-@Z6Ah zIb5RDiq{LThUV1QkTyu1^>Ay&uThFx@kk-LN3vCAf0PtwDx&N9i@s&*g6^Y6Ul(4` zeG0qR6i*P1(PR+X|3%aijk~`o3Zb^nda`dg>p8z*QIc)SM zP!6dgw`3r>U$>E)06oLAt>|n}&Z;}xrrbK>B}l%P-4kOk+49?loDa^&Lge~ky^Mt8 zMxPAIB6jE0P&ht@+%!{8_MaSX74v+*4r7n(xfkwIFS$>$dx1*fLCU>hT}<^;TavCm z`f5-#j4-;OaJ`t^ewkV?iu|{!x_GR1KHT52dqn9ngr6O-E=G2XZV=SE?vwU7*}+$677?;C5uU(L(wL6A>AeDYkMEYhz+YMV$3M& z%OsO@Xofx^jkNmM)e1M_?SQ+^I~V$#gONuUUyV8(;UO67i2oSGu2GMN`;hDSNUews z*gse+P93laZfrncH*2hmD5A*I33q{e6PNmIq`lE~K8LSB_z%iQ70E8&9YHs&F~>q% z8b2pq3k|QQxMdP4|0(|(aqltO6ul^plRfbXqYI+j;;yJme8cE*?}B2t>JmR#XnCBF zUMukLaqqCfUT_v#Xe^_03%xhC0C9sQ66JZ6!>JaU#OMJ=8^o_h6od0k3!OAv!Rg^H zMp84k_(u-Zjmppu+S%n zD-hRO$cJ3Niga(MF_e1Db_XIXZ6*ji7stOBrnvD_RSIk~W$cEfO2ENG%pSY&0zz7I)id zX0%j1ZKDID$qLal;MzRc3#6m0XtE#T(6tT=kCq<`<6D%|`wkbMI{Kb)O zx_Hlun-DuUI$f;6S$f7UGekF|OT}knwnk@&GcDwA-5%XvY`4%1pjqNxoAVdZIpSfP z^Umm8@ruoPXY>H^DI*$R+&Dj5(@6R4QrZG9D)YruoM#f+Z^To|!Qx&EZK!xkStQ!< zh(w4D;=<9J)g|Is3+(_pL~Lh7GVhNbDh3aiQa)&XGdrh5oq_~L@^kmM58Ep`^`ag~yDT+ss%njm1 zjDtsug%;}ae;GYmT+4|1ZEy4#@dhJV@5hNlS}5Hv<%8Bh>2YE^-|*ZZ-fS%@T`B%! zq4L(s($!+{D4D|n&9TxG#1>qY%+%3|;z~xFyvHN=6VVSSZkKOnUTf)z{8JUs%)2me z9MHa_DQ<)JF%>h&7CMDYHk< zEnOqNvCw{@#ib{SPxuMcE@j*htfWOJu0e2Z!e;Bl(-tD@t`jx5m_RnWYcQb`Ec64` z%ce< z%?+(Ux{-AJAvSrB06ImiVni+E*wXdlm=1~~)E4a)7c-Lmc7v#xL~*kIP7|Lpx=2vJ zJx#2eOmVw>XAV8R^fb|Jq05GD2HI+&2jdr%ZWP-s^w;=hK=(4*ApRJ4oAbD{cnjE)r=gZU*8m78l#7P+TIOvC&^jFBNZD>8@&3#AV_O zEAH9Wou!wFW&6tf&ToFNbgOuh(I)Y1>!+pLgtlKM?%$=CizuT_;-1z};Bs-gjf~(G z;$aK@snu2Xb1`xTrQ0O_)S6#*l~`w?bDE=N+r~`Uv zEjd4Joff@QlrfU+`ff3t(FQyZR&a(q#X@hm2raZwk8(uW-Qo&HmwMl5H-WBUbb<_+ffg-)PCVh@d|v#A(WRoO z@^| zcUkD)^)t#}5fw+sxQCk+JPWzXLbo$|*h0R_P~cUu?~#)8yNXcYHSx`{5`8dYUis@{ z`*9MTT`{kGrx>|Xq9caQD}PgTT4)0}-xiNq=N- zDt&qR`{Eo6%`Q3`=n_V|l)NFU%Xf)uEVL@Vy8Hui8zU+6L-89%Qs#%^QAQ*)S^lAT zO2&C-7o7t1lAX>i{w4+=FU#;MM(>ZrF^qO89TnZ>ABn9t+EV_pc!813;S=$mOy`|a zdu{nA;uA)s%Pl~z)g*J5(olMD`QOD58$D9~PjQfqo-6-cTyLSuk*}A3C7!g=JLO-C zV!DU`DbG}WQvPo-)kgm+|5n^&q2Vo`lz%VYu+ewry<*J?GTjNohL$VJHH^p-T7^rw znUO4mOL@cMyrjy9xHu-@OdWZY7Dkk=sKTR+W3)@TyCnj&)Iz_nuK+sUkz(Oml2t_RP;0Qw17Fx?_h(t7RLdt9_Zusy?6$6w77W%kl zCeUFP`XkZ}P>!;Mwfb@8oR0@ zqJ-CwT`u+h1*lXR$Y_%|tnQ?Wa^*0I*t!+UF^qQkP7I_gDwORO`WaBA@-m|hVte59 ziYnz3na+F1u(K^0kOXJF0j5c{+8TwR3gHqGUGQA%UeI96;h4#z;Yel27-9lQxtu`ue zS;!wKq~|+nnQmNQXGN2;%tA8)?*iRrp{*6um0`*k7P`K|Eru!kcFA3)W|vC733+J?BX$|n}O)3?++PHEUAIUn?WR54CD-9i^2ZoKlC zg|0;0c%|ZJlCyTuQtt%i5DN_(^ijnGRK!hGW}Ye2?Td6B$`%V9 zjJOWvJqsleH%S?MmgGDQag&rz3%xfsQaM?<-$I{_tpqCEEIDVi53Zb|%(c+L?J=P1 zBw|}nRi3m_bLCWJ?%9-%&rvF;DUUJQfKjyZILo7N_fvju zq3@y}RqUsHVIdmNW+)@ik?H>3GO2Qga;Am04cxbKf8|LF-8yhKP{p~-3C+~XnaV_o zywvJuDbp=Pt!|dGgwf+-D_ZMp

Mi6`fx>TPZ$I=C>v9kjgpAObcBNG*>xYB5@kd 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 literal 0 HcmV?d00001 From d2079dee137fddd98a83b08ad1525916801c088c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=B0=B8=E5=AE=89404?= <101850798+YongAn404@users.noreply.github.com> Date: Sun, 28 Dec 2025 11:38:04 +0800 Subject: [PATCH 6/6] 114514 --- Commands/Chats/AChatCommand.cs | 2 +- Commands/Chats/CChatCommand.cs | 4 +- Commands/ExpCommand.cs | 4 +- Commands/KillCommand.cs | 8 +-- Config.cs | 11 +++- Features/PlayerUI.cs | 36 +++++++++--- Features/Players/FramePlayer.cs | 30 ++++++---- Features/Roles/CustomRolePlus.cs | 14 ++--- Patch/AddLogPatch.cs | 57 ------------------- YongAnFrame.csproj | 14 ++--- YongAnFramePlugin.cs | 98 +++++++++++++++++++++++++++++++- 11 files changed, 174 insertions(+), 104 deletions(-) delete mode 100644 Patch/AddLogPatch.cs diff --git a/Commands/Chats/AChatCommand.cs b/Commands/Chats/AChatCommand.cs index 0f2cf0a..51882d4 100644 --- a/Commands/Chats/AChatCommand.cs +++ b/Commands/Chats/AChatCommand.cs @@ -1,4 +1,4 @@ -using CommandSystem; +using CommandSystem; using Exiled.API.Features; using System; using System.Linq; diff --git a/Commands/Chats/CChatCommand.cs b/Commands/Chats/CChatCommand.cs index 1e85cf3..b8a2638 100644 --- a/Commands/Chats/CChatCommand.cs +++ b/Commands/Chats/CChatCommand.cs @@ -1,4 +1,4 @@ -using CommandSystem; +using CommandSystem; using Exiled.API.Features; using System; using YongAnFrame.Extensions; @@ -24,7 +24,7 @@ public bool Execute(ArraySegment arguments, ICommandSender sender, out s { foreach (var player1 in Player.Get(player.Role.Side)) { - player1.ToFPlayer().UI.ChatList.Add(new ChatText(arguments.Array[1], 10, ChatType.All, player.ToFPlayer())); + player1.ToFPlayer().UI.ChatList.Add(new ChatText(arguments.Array[1], 10, ChatType.Team, player.ToFPlayer())); } response = "OK"; return true; diff --git a/Commands/ExpCommand.cs b/Commands/ExpCommand.cs index b109ec0..53b34e4 100644 --- a/Commands/ExpCommand.cs +++ b/Commands/ExpCommand.cs @@ -1,4 +1,4 @@ -using CommandSystem; +using CommandSystem; using Exiled.API.Features; using Exiled.Permissions.Extensions; using System; @@ -39,7 +39,7 @@ public bool Execute(ArraySegment arguments, ICommandSender sender, out s { if (arguments.Count >= 1) { - Player.Get(arguments.Array[1]).ToFPlayer().Level += ulong.Parse(arguments.Array[2]); + Player.Get(arguments.Array[1]).ToFPlayer().AddExp(ulong.Parse(arguments.Array[2]), "管理员签发"); response = "OK"; return true; } diff --git a/Commands/KillCommand.cs b/Commands/KillCommand.cs index 689fa53..7e0b833 100644 --- a/Commands/KillCommand.cs +++ b/Commands/KillCommand.cs @@ -1,4 +1,4 @@ -using CommandSystem; +using CommandSystem; using Exiled.API.Features; using PlayerStatsSystem; using System; @@ -8,11 +8,11 @@ namespace SyncPlugin.Commands [CommandHandler(typeof(ClientCommandHandler))] public class KillCommand : ICommand { - public string Command => "debug"; + public string Command => "killme"; - public string[] Aliases => ["kill", "db"]; + public string[] Aliases => ["kill", "s"]; - public string Description => "debug指令"; + public string Description => "自杀指令"; public bool Execute(ArraySegment arguments, ICommandSender sender, out string response) { if (Player.TryGet(sender, out Player player)) diff --git a/Config.cs b/Config.cs index 30e3b9b..49c4c27 100644 --- a/Config.cs +++ b/Config.cs @@ -1,4 +1,4 @@ -using Exiled.API.Interfaces; +using Exiled.API.Interfaces; using System.Collections.Generic; using System.ComponentModel; using YongAnFrame.Features.Roles; @@ -43,5 +43,14 @@ public sealed class Config : IConfig /// [Description("禁用自定义角色生成(只能用于继承CustomRolePlus的类)")] public List DisableCustomRolePlus { get; set; } = ["114514", "1"]; + + ///

+ /// 获取或设置禁用指令 + /// + /// + /// 只能用于继承的类 + /// + [Description("禁用指令")] + public List DisableCommand { get; set; } = ["AChatCommand", "1"]; } } diff --git a/Features/PlayerUI.cs b/Features/PlayerUI.cs index a60c5ff..ba165c3 100644 --- a/Features/PlayerUI.cs +++ b/Features/PlayerUI.cs @@ -1,4 +1,5 @@ -using HintServiceMeow.Core.Enum; +using Exiled.API.Features.Waves; +using HintServiceMeow.Core.Enum; using HintServiceMeow.Core.Models.Hints; using HintServiceMeow.Core.Utilities; using MEC; @@ -37,7 +38,7 @@ public class PlayerUI #region Hint private readonly Hint versionHint = new() { - Text = "YongAnFrame 1.0.0-beta7", + Text = "YongAnFrame 1.0.0-beta8", FontSize = 20, Alignment = HintAlignment.Center, YCoordinateAlign = HintVerticalAlign.Top, @@ -54,13 +55,17 @@ public class PlayerUI { FontSize = 20, Alignment = HintAlignment.Right, - YCoordinate = 400 + YCoordinate = 600 }; private readonly Hint messageHint = new() { FontSize = 20, Alignment = HintAlignment.Left, - YCoordinate = 400 + YCoordinate = 600 + }; + public readonly Hint waveTimerHint = new() + { + YCoordinate = 190 }; #endregion @@ -68,7 +73,7 @@ private IEnumerator Timer() { while (true) { - + UpdateWaveTimerUI(); for (int i = 0; i < MessageList.Count; i++) { @@ -78,8 +83,8 @@ private IEnumerator Timer() MessageList.Remove(message); i--; } - UpdateMessageUI(); } + UpdateMessageUI(); bool isUpdate = false; @@ -107,6 +112,20 @@ public void UpdateUI() UpdateCustomRoleUI(); UpdateMessageUI(); UpdateChatUI(); + UpdateWaveTimerUI(); + } + + public void UpdateWaveTimerUI() + { + if (FPlayer.ExPlayer.IsDead) + { + waveTimerHint.Text = $"下一波九尾狐刷新:{(int)WaveTimer.GetWaveTimers()[0].TimeLeft.TotalSeconds}\n" + + $"下一波混沌刷新:{(int)WaveTimer.GetWaveTimers()[1].TimeLeft.TotalSeconds}"; + } + else + { + waveTimerHint.Text = null; + } } /// @@ -162,12 +181,13 @@ public PlayerUI(FramePlayer fPlayer) FPlayer = fPlayer; MessageList = new(7, UpdateMessageUI); ChatList = new(7, UpdateChatUI); - coroutine = Timing.RunCoroutine(Timer()); - PlayerDisplay = PlayerDisplay.Get(referenceHub: fPlayer); + PlayerDisplay = PlayerDisplay.Get(FPlayer.ExPlayer.ReferenceHub); PlayerDisplay.AddHint(customRoleHint); PlayerDisplay.AddHint(chatHint); PlayerDisplay.AddHint(messageHint); PlayerDisplay.AddHint(versionHint); + PlayerDisplay.AddHint(waveTimerHint); + coroutine = Timing.RunCoroutine(Timer()); } /// /// 解构方法 diff --git a/Features/Players/FramePlayer.cs b/Features/Players/FramePlayer.cs index 8f3ee8f..0eb8831 100644 --- a/Features/Players/FramePlayer.cs +++ b/Features/Players/FramePlayer.cs @@ -1,4 +1,4 @@ -using Exiled.API.Features; +using Exiled.API.Features; using Exiled.CustomRoles.API; using Exiled.CustomRoles.API.Features; using Exiled.Events.EventArgs.Player; @@ -89,13 +89,15 @@ public CustomRolePlus? CustomRolePlus /// 获取或设置玩家的经验倍率 /// public float ExpMultiplier { get; set; } - - public List PosTitles { get; private set; } = []; - /// /// 获取或设置玩家的批准绕过DNT /// - public bool IsBDNT { get; set; } + public bool IsBDNT { get; set; } = false; + /// + /// 获取玩家是否无效 + /// + public bool IsInvalid => exPlayer is null; + public List PosTitles { get; private set; } = []; /// /// 获取或设置玩家正在使用的名称称号 /// @@ -185,18 +187,21 @@ public static void SubscribeStaticEvents() /// public static void UnsubscribeStaticEvents() { - Exiled.Events.Handlers.Player.Verified += new CustomEventHandler(OnStaticVerified); - Exiled.Events.Handlers.Player.Destroying += new CustomEventHandler(OnStaticDestroying); + Exiled.Events.Handlers.Player.Verified -= new CustomEventHandler(OnStaticVerified); + Exiled.Events.Handlers.Player.Destroying -= new CustomEventHandler(OnStaticDestroying); } private static void OnStaticVerified(VerifiedEventArgs args) { - new FramePlayer(args.Player); + Load(args.Player)!.UpdateShowInfo(); } private static void OnStaticDestroying(DestroyingEventArgs args) { FramePlayer fPlayer = args.Player.ToFPlayer(); - fPlayer.Invalid(); + if (!fPlayer.IsInvalid) + { + fPlayer.Invalid(); + } } #endregion @@ -212,7 +217,6 @@ internal FramePlayer(Player player) UI = new(this); CustomAlgorithm = this; Events.Handlers.FramePlayer.OnFramePlayerCreated(new FramePlayerCreatedEventArgs(this)); - UpdateShowInfo(); } /// @@ -412,7 +416,7 @@ public static FramePlayer Get(Player? player) { if (player.IsNPC) { - return new(player.ToFPlayer()) + return new(player) { Level = 1, Exp = 0, @@ -446,6 +450,7 @@ public static FramePlayer Get(Player? player) } } } + framePlayer = new(player) { Level = (ulong)reader["Level"], @@ -462,7 +467,7 @@ public static FramePlayer Get(Player? player) Log.Error($"数据库查找FramePlayer数据异常({player.UserId}) 错误原因:{text}"); if (YongAnFramePlugin.Instance.Config.IsMySqlErrorKick) { - player.Kick("不要慌张!你的数据库数据可能存在异常,为了保证你的游戏数据不被覆盖,你已被踢出服务器!\n请将错误联系到管理员(数据库查找FramePlayer数据异常)"); + player.Kick("不要慌张!你的数据库数据可能存在异常,为了保证你的游戏数据不被覆盖,你已被踢出服务器!\n请将错误联系到管理员(数据库查找FramePlayer数据异常)"); } return null; } @@ -506,6 +511,7 @@ public static FramePlayer Get(Player? player) return null; } } + return framePlayer; } diff --git a/Features/Roles/CustomRolePlus.cs b/Features/Roles/CustomRolePlus.cs index d40515b..80bcd48 100644 --- a/Features/Roles/CustomRolePlus.cs +++ b/Features/Roles/CustomRolePlus.cs @@ -1,4 +1,4 @@ -using Exiled.API.Features; +using Exiled.API.Features; using Exiled.API.Features.DamageHandlers; using Exiled.API.Features.Spawn; using Exiled.CustomRoles.API; @@ -135,7 +135,7 @@ public virtual void AddRole(FramePlayer fPlayer) fPlayer.ExPlayer.EnableEffect(Exiled.API.Enums.EffectType.MovementBoost); fPlayer.ExPlayer.ChangeEffectIntensity(Exiled.API.Enums.EffectType.MovementBoost, (byte)((BaseProperties.BaseMovementSpeedMultiplier - 1f) * 100)); } - if (!string.IsNullOrEmpty(SpawnProperties.Info)) Cassie.MessageTranslated($""/*ADMINISTER TEAM DESIGNATED {CASSIEDeathName} HASENTERED*/, SpawnProperties.Info, true, true, true); + if (!string.IsNullOrEmpty(SpawnProperties.Info)) Exiled.API.Features.Cassie.MessageTranslated($""/*ADMINISTER TEAM DESIGNATED {CASSIEDeathName} HASENTERED*/, SpawnProperties.Info, true, true, true); if (!string.IsNullOrEmpty(SpawnProperties.MusicNameName)) { MusicManager.Play(SpawnProperties.MusicNameName!, $"{Name}"); @@ -186,7 +186,7 @@ public virtual void RemoveRole(FramePlayer fPlayer) { if (!data.IsDeathHandling) { - Cassie.MessageTranslated($"Died", $"{Name}游玩二游被榨干而死(非常正常死亡)"); + Exiled.API.Features.Cassie.MessageTranslated($"Died", $"{Name}游玩二游被榨干而死(非常正常死亡)"); } base.RemoveRole(fPlayer.ExPlayer); BaseData.Remove(fPlayer); @@ -339,7 +339,7 @@ private void OnDying(DyingEventArgs args) { if (args.Attacker is null) { - Cassie.MessageTranslated($"Died", $"{Name}被充满恶意的游戏环境草飞了"); + Exiled.API.Features.Cassie.MessageTranslated($"Died", $"{Name}被充满恶意的游戏环境草飞了"); data.IsDeathHandling = true; } else @@ -349,16 +349,16 @@ private void OnDying(DyingEventArgs args) CustomRole customRole = args.Attacker.GetCustomRoles()[0]; if (RoleDeathText.TryGetValue(customRole.Id, out string text)) { - Cassie.MessageTranslated($"Died", text.Replace("{Name}", Name).Replace("{Attacker}", customRole.Name)); + Exiled.API.Features.Cassie.MessageTranslated($"Died", text.Replace("{Name}", Name).Replace("{Attacker}", customRole.Name)); } else { - Cassie.MessageTranslated($"Died", $"({Name})被({customRole.Name})斩杀"); + Exiled.API.Features.Cassie.MessageTranslated($"Died", $"({Name})被({customRole.Name})斩杀"); } } else { - Cassie.MessageTranslated($"Died", $"({Name})被({args.Attacker.Nickname})斩杀"); + Exiled.API.Features.Cassie.MessageTranslated($"Died", $"({Name})被({args.Attacker.Nickname})斩杀"); } } data.IsDeathHandling = true; diff --git a/Patch/AddLogPatch.cs b/Patch/AddLogPatch.cs deleted file mode 100644 index 7a3a4f5..0000000 --- a/Patch/AddLogPatch.cs +++ /dev/null @@ -1,57 +0,0 @@ -using HarmonyLib; -using System; -using System.Collections.Generic; -using System.Diagnostics; -using System.IO; -using System.Text; -using System.Threading.Tasks; -using YongAnFrame.Features; -using static ServerLogs; - -namespace YongAnFrame.Patch -{ -// /// -// /// 在添加的补丁 -// /// -// [HarmonyPatch(typeof(ServerLogs), nameof(AddLog))] -// public static class AddLogPatch -// { -//#pragma warning disable IDE0060 // 删除未使用的参数 -// private static void Prefix(Modules module, string msg, ServerLogType type, bool init = false) -//#pragma warning restore IDE0060 // 删除未使用的参数 -// { -// SaveLog(q); -// } - -// private static readonly Queue logQueue = new(); -// private static readonly Task logTask = new(async () => -// { -// while (true) -// { -// while (logQueue.Count != 0) -// { -// InfoData infoData = logQueue.Dequeue(); -// using StreamWriter writer = new($"{PathManager.Log}/{DateTime.Now:yyyy-MM-dd}.log", true, Encoding.UTF8); -// writer.WriteLine(infoData); -// } -// await Task.Delay(1000); -// } -// }); - -// /// -// /// 启动日志任务 -// /// -// public static void StartTask() -// { -// if (logTask.Status == TaskStatus.Created) -// { -// logTask.Start(); -// } -// } - -// private static void SaveLog(string log, StackTrace trace) -// { -// logQueue.Enqueue(new InfoData(log, trace)); -// } -// } -} diff --git a/YongAnFrame.csproj b/YongAnFrame.csproj index f014035..783d12c 100644 --- a/YongAnFrame.csproj +++ b/YongAnFrame.csproj @@ -8,13 +8,12 @@ True zh-Hans False - 1.0.0-beta7 + 1.0.0 + beta8 YongAn404 $(Authors) Copyright © YongAn404 $(AssemblyName) - 1.0.0.0 - 1.0.0.0 disable True LGPL-3.0-only @@ -38,6 +37,7 @@ + @@ -52,10 +52,10 @@ - - - - + + + + diff --git a/YongAnFramePlugin.cs b/YongAnFramePlugin.cs index 7d45f48..4a835f7 100644 --- a/YongAnFramePlugin.cs +++ b/YongAnFramePlugin.cs @@ -1,11 +1,14 @@ -using Exiled.API.Enums; +using CommandSystem; +using Exiled.API.Enums; using Exiled.API.Features; using HarmonyLib; +using RemoteAdmin; using System; +using System.Collections.Generic; +using System.Reflection; using YongAnFrame.Features; using YongAnFrame.Features.Players; using YongAnFrame.Features.Roles; -using YongAnFrame.Patch; namespace YongAnFrame { @@ -49,7 +52,6 @@ public override void OnEnabled() PathManager.CheckPath(); FramePlayer.SubscribeStaticEvents(); CustomRolePlus.SubscribeStaticEvents(); - //AddLogPatch.StartTask(); Harmony.PatchAll(); base.OnEnabled(); } @@ -63,5 +65,95 @@ public override void OnDisabled() Harmony.UnpatchAll(); base.OnDisabled(); } + + /// + public override void OnRegisteringCommands() + { + Dictionary> dictionary = []; + Type[] types = Assembly.GetTypes(); + foreach (Type type in types) + { + if (type.GetInterface("ICommand") != typeof(ICommand) || Config.DisableCommand.Contains(type.Name) || !Attribute.IsDefined(type, typeof(CommandHandlerAttribute))) + { + continue; + } + + foreach (CustomAttributeData customAttributesDatum in type.GetCustomAttributesData()) + { + try + { + if (customAttributesDatum.AttributeType != typeof(CommandHandlerAttribute)) + { + continue; + } + + Type type2 = (Type)customAttributesDatum.ConstructorArguments[0].Value; + ICommand command = GetCommand(type) ?? ((ICommand)Activator.CreateInstance(type)); + if (typeof(ParentCommand).IsAssignableFrom(type2)) + { + if (GetCommand(type2) is not ParentCommand parentCommand) + { + if (!dictionary.TryGetValue(type2, out var value)) + { + dictionary.Add(type2, [command]); + } + else + { + value.Add(command); + } + } + else + { + parentCommand.RegisterCommand(command); + } + + continue; + } + + try + { + if (type2 == typeof(RemoteAdminCommandHandler)) + { + CommandProcessor.RemoteAdminCommandHandler.RegisterCommand(command); + } + else if (type2 == typeof(GameConsoleCommandHandler)) + { + GameCore.Console.ConsoleCommandHandler.RegisterCommand(command); + } + else if (type2 == typeof(ClientCommandHandler)) + { + QueryProcessor.DotCommandHandler.RegisterCommand(command); + } + } + catch (ArgumentException ex) + { + if (ex.Message.StartsWith("An")) + { + Log.Error("Command with same name has already registered! Command: " + command.Command); + } + else + { + Log.Error($"An error has occurred while registering a command: {ex}"); + } + } + + Commands[type2][type] = command; + } + catch (Exception arg) + { + Log.Error($"An error has occurred while registering a command: {arg}"); + } + } + } + + foreach (KeyValuePair> item in dictionary) + { + ParentCommand parentCommand2 = GetCommand(item.Key) as ParentCommand; + foreach (ICommand item2 in item.Value) + { + parentCommand2.RegisterCommand(item2); + } + } + } } }