diff --git a/Equipments/Equipments.cs b/Equipments/Equipments.cs index 5b2fff9..f31b146 100644 --- a/Equipments/Equipments.cs +++ b/Equipments/Equipments.cs @@ -10,13 +10,13 @@ namespace Equipments; public class Equipments : BasePlugin, IPluginConfig { public override string ModuleName => "Equipments"; - public override string ModuleVersion => "0.0.3"; + public override string ModuleVersion => "0.0.4"; public override string ModuleAuthor => "exkludera"; public EquipmentsConfig Config { get; set; } = new EquipmentsConfig(); public List GlobalEquipmentsItems { get; set; } = []; public List GlobalEquipmentsItemTypes { get; set; } = []; - + public int GlobalTickrate { get; set; } = 0; public static Equipments Instance { get; set; } = new(); public override void Load(bool hotReload) @@ -29,8 +29,9 @@ public override void Load(bool hotReload) Command.Load(); Item_Hat.OnPluginStart(); - Item_Wing.OnPluginStart(); + Item_Wings.OnPluginStart(); Item_Backpack.OnPluginStart(); + Item_Trail.OnPluginStart(); if (hotReload) { @@ -48,7 +49,7 @@ public override void Unload(bool hotReload) public void OnConfigParsed(EquipmentsConfig config) { - if (string.IsNullOrEmpty(config.Database.Host) || string.IsNullOrEmpty(config.Database.Name) || string.IsNullOrEmpty(config.Database.User)) + if (string.IsNullOrEmpty(config.Database.Host) || string.IsNullOrEmpty(config.Database.DBName) || string.IsNullOrEmpty(config.Database.User)) throw new Exception("Setup Database in config!"); Task.Run(async () => { diff --git a/Equipments/Items/backpack.cs b/Equipments/Items/backpack.cs index 6dff841..50bcd16 100644 --- a/Equipments/Items/backpack.cs +++ b/Equipments/Items/backpack.cs @@ -39,7 +39,12 @@ public static bool OnUnequip(CCSPlayerController player, Dictionary { + + if (!Functions.PlayerAlive(player)) + return; + Equipments_Items? playerItems = Instance.GlobalEquipmentsItems.FirstOrDefault(p => p.SteamID == player.SteamID && p.Type == "backpack"); if (playerItems == null) return; @@ -63,7 +68,7 @@ public static void UnEquip(CCSPlayerController player) public static void CreateItem(CCSPlayerController player, string itemName) { - var entity = Utilities.CreateEntityByName("prop_dynamic_override"); + var entity = Utilities.CreateEntityByName("prop_dynamic_override"); Instance.AddTimer(0.1f, () => { entity!.Globalname = $"{player.SteamID}({itemName})#{Functions.RandomString(6)}"; diff --git a/Equipments/Items/hat.cs b/Equipments/Items/hat.cs index a8f02ae..8d6c8e1 100644 --- a/Equipments/Items/hat.cs +++ b/Equipments/Items/hat.cs @@ -39,7 +39,12 @@ public static bool OnUnequip(CCSPlayerController player, Dictionary { + + if (!Functions.PlayerAlive(player)) + return; + Equipments_Items? playerItems = Instance.GlobalEquipmentsItems.FirstOrDefault(p => p.SteamID == player.SteamID && p.Type == "hat"); if (playerItems == null) return; @@ -63,7 +68,7 @@ public static void UnEquip(CCSPlayerController player) public static void CreateItem(CCSPlayerController player, string itemName) { - var entity = Utilities.CreateEntityByName("prop_dynamic_override"); + var entity = Utilities.CreateEntityByName("prop_dynamic_override"); Instance.AddTimer(0.1f, () => { entity!.Globalname = $"{player.SteamID}({itemName})#{Functions.RandomString(6)}"; diff --git a/Equipments/Items/trail.cs b/Equipments/Items/trail.cs new file mode 100644 index 0000000..bb5b73a --- /dev/null +++ b/Equipments/Items/trail.cs @@ -0,0 +1,93 @@ +using CounterStrikeSharp.API; +using CounterStrikeSharp.API.Core; +using CounterStrikeSharp.API.Modules.Utils; +using System.Globalization; + +using static Equipments.Equipments; +using static EquipmentsAPI.Equipments; + +namespace Equipments; + +public static class Item_Trail +{ + private static bool trailExists = false; + public static void OnPluginStart() + { + Item.RegisterType("trail", OnServerPrecacheResources, OnEquip, OnUnequip, true, null); + if (Item.GetItemsByType("trail").Count > 0) trailExists = true; + } + public static void OnServerPrecacheResources(ResourceManifest manifest) + { + List>> items = Item.GetItemsByType("trail"); + + foreach (KeyValuePair> item in items) + { + manifest.AddResource(item.Value["uniqueid"]); + } + } + public static bool OnEquip(CCSPlayerController player, Dictionary item) + { + return true; + } + public static bool OnUnequip(CCSPlayerController player, Dictionary item) + { + return true; + } + + public static void OnTick(CCSPlayerController player) + { + if (!trailExists) + return; + + Equipments_Items? playertrail = Instance.GlobalEquipmentsItems.FirstOrDefault(p => p.SteamID == player.SteamID && p.Type == "trail"); + if (playertrail == null) return; + + Dictionary? itemdata = Item.GetItem(playertrail.Type, playertrail.UniqueId); + if (itemdata == null) return; + + Vector? absorigin = player.PlayerPawn.Value?.AbsOrigin; + if (absorigin == null) return; + + float lifetime = 1.3f; + + if (itemdata.TryGetValue("lifetime", out string? ltvalue) && float.TryParse(ltvalue, CultureInfo.InvariantCulture, out float lt)) + lifetime = lt; + + CreateParticle(absorigin, playertrail.UniqueId, lifetime, itemdata, player); + } + + public static void CreateParticle(Vector absOrigin, string effectName, float lifetime, Dictionary itemdata, CCSPlayerController player) + { + CParticleSystem? entity = Utilities.CreateEntityByName("info_particle_system"); + + if (entity == null || !entity.IsValid) return; + + if (!itemdata.TryGetValue("acceptInputValue", out string? acceptinputvalue) || string.IsNullOrEmpty(acceptinputvalue)) + acceptinputvalue = "Start"; + + QAngle angle = new(); + + if (!itemdata.TryGetValue("angleValue", out string? angleValue) || string.IsNullOrEmpty(angleValue)) + angle.X = 90; + else + { + string[] angleValues = angleValue.Split(' '); + + angle.X = int.Parse(angleValues[0]); + angle.Y = int.Parse(angleValues[0]); + angle.Z = int.Parse(angleValues[0]); + } + + entity.EffectName = effectName; + entity.DispatchSpawn(); + entity.Teleport(absOrigin, angle, new Vector()); + entity.AcceptInput(acceptinputvalue!); + entity.AcceptInput("FollowEntity", player.PlayerPawn?.Value!, player.PlayerPawn?.Value!, "!activator"); + + Instance.AddTimer(lifetime, () => + { + if (entity != null && entity.IsValid) + entity.Remove(); + }); + } +} \ No newline at end of file diff --git a/Equipments/Items/wings.cs b/Equipments/Items/wings.cs index 2cbbe7d..82048d3 100644 --- a/Equipments/Items/wings.cs +++ b/Equipments/Items/wings.cs @@ -7,18 +7,18 @@ namespace Equipments; -public static class Item_Wing +public static class Item_Wings { private static Dictionary Equipment = new(); public static void OnPluginStart() { - Item.RegisterType("wing", OnServerPrecacheResources, OnEquip, OnUnequip, true, null); + Item.RegisterType("wings", OnServerPrecacheResources, OnEquip, OnUnequip, true, null); Instance.RegisterEventHandler(OnPlayerSpawn); } public static void OnServerPrecacheResources(ResourceManifest manifest) { - List>> items = Item.GetItemsByType("wing"); + List>> items = Item.GetItemsByType("wings"); foreach (KeyValuePair> item in items) { @@ -39,8 +39,13 @@ public static bool OnUnequip(CCSPlayerController player, Dictionary { - Equipments_Items? playerItems = Instance.GlobalEquipmentsItems.FirstOrDefault(p => p.SteamID == player.SteamID && p.Type == "wing"); + + if (!Functions.PlayerAlive(player)) + return; + + Equipments_Items? playerItems = Instance.GlobalEquipmentsItems.FirstOrDefault(p => p.SteamID == player.SteamID && p.Type == "wings"); if (playerItems == null) return; Dictionary? itemdata = Item.GetItem(playerItems.Type, playerItems.UniqueId); @@ -63,7 +68,7 @@ public static void UnEquip(CCSPlayerController player) public static void CreateItem(CCSPlayerController player, string itemName) { - var entity = Utilities.CreateEntityByName("prop_dynamic_override"); + var entity = Utilities.CreateEntityByName("prop_dynamic_override"); Instance.AddTimer(0.1f, () => { entity!.Globalname = $"{player.SteamID}({itemName})#{Functions.RandomString(6)}"; diff --git a/Equipments/Player/events.cs b/Equipments/Player/events.cs index 42840c6..5dc3a96 100644 --- a/Equipments/Player/events.cs +++ b/Equipments/Player/events.cs @@ -14,6 +14,7 @@ public static void Unload() { Instance.RemoveListener(OnServerPrecacheResources); Instance.RemoveListener(OnClientAuthorized); + Instance.RemoveListener(OnTick); } public static void Load() @@ -21,6 +22,7 @@ public static void Load() Instance.RegisterListener(OnServerPrecacheResources); Instance.RegisterListener(OnClientAuthorized); Instance.RegisterEventHandler(OnPlayerDisconnect); + Instance.RegisterListener(OnTick); } public static void OnServerPrecacheResources(ResourceManifest manifest) @@ -30,6 +32,24 @@ public static void OnServerPrecacheResources(ResourceManifest manifest) }); } + public static void OnTick() + { + Instance.GlobalTickrate++; + + if (Instance.GlobalTickrate % 10 != 0) + return; + + Instance.GlobalTickrate = 0; + + foreach (CCSPlayerController player in Utilities.GetPlayers()) + { + if (!Functions.PlayerAlive(player)) + continue; + + Item_Trail.OnTick(player); + } + } + private static void OnClientAuthorized(int playerSlot, SteamID steamId) { CCSPlayerController? player = Utilities.GetPlayerFromSlot(playerSlot); diff --git a/Equipments/Plugin/config.cs b/Equipments/Plugin/config.cs index ba91e55..68f74a4 100644 --- a/Equipments/Plugin/config.cs +++ b/Equipments/Plugin/config.cs @@ -7,18 +7,18 @@ public class EquipmentsConfig : BasePluginConfig { public class Config_Database { - public string Host { get; set; } = string.Empty; - public uint Port { get; set; } = 3306; - public string User { get; set; } = string.Empty; - public string Password { get; set; } = string.Empty; - public string Name { get; set; } = string.Empty; + public string Host { get; set; } = "localhost"; + public string User { get; set; } = "username"; + public string Password { get; set; } = "password"; + public string DBName { get; set; } = "database"; public string DBTable { get; set; } = "equipments"; + public uint Port { get; set; } = 3306; } [JsonPropertyName("Database")] public Config_Database Database { get; set; } = new Config_Database(); public class Config_Command { - public string[] OpenMenu { get; set; } = ["equipments", "equipment", "hats", "wings"]; + public string[] OpenMenu { get; set; } = ["equipments", "equipment"]; public string[] ResetPlayer { get; set; } = ["equipments-resetplayer"]; public string[] ResetDatabase { get; set; } = ["equipments-resetdatabase"]; } @@ -27,7 +27,7 @@ public class Config_Command public class Config_Settings { public string Flag { get; set; } = "@css/reservation"; - public bool HudMenu { get; set; } + public bool HudMenu { get; set; } = true; } [JsonPropertyName("Settings")] public Config_Settings Settings { get; set; } = new Config_Settings(); diff --git a/Equipments/Plugin/database.cs b/Equipments/Plugin/database.cs index 5090f87..ca1dda5 100644 --- a/Equipments/Plugin/database.cs +++ b/Equipments/Plugin/database.cs @@ -33,7 +33,7 @@ public static async Task CreateDatabaseAsync(EquipmentsConfig config) MySqlConnectionStringBuilder builder = new() { Server = config.Database.Host, - Database = config.Database.Name, + Database = config.Database.DBName, UserID = config.Database.User, Password = config.Database.Password, Port = config.Database.Port, diff --git a/Equipments/Plugin/functions.cs b/Equipments/Plugin/functions.cs index 7c3f7d1..893964c 100644 --- a/Equipments/Plugin/functions.cs +++ b/Equipments/Plugin/functions.cs @@ -11,6 +11,14 @@ static public void PrintToChatMessage(this CCSPlayerController player, string me player.PrintToChat($" {Instance.Localizer["prefix"]} {Instance.Localizer[message, args]}"); } + public static bool PlayerAlive(CCSPlayerController player) + { + if (player == null || !player.IsValid || player.Pawn == null || !player.PlayerPawn.IsValid || !player.PawnIsAlive) + return false; + + return true; + } + public static string RandomString(int length) { const string chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789"; diff --git a/Equipments/lang/en.json b/Equipments/lang/en.json index 26c7010..bdca7ea 100644 --- a/Equipments/lang/en.json +++ b/Equipments/lang/en.json @@ -7,10 +7,11 @@ "menu": "Equipments", "menu<back>": "-> Back", + "menu_item<hat>": "Hats", - "menu_item<wing>": "Wings", + "menu_item<wings>": "Wings", "menu_item<backpack>": "Backpacks", - "menu_item<other>": "Other", + "menu_item<trail>": "Trails", "No matching client": "{white}There is no matching client", "More than one client matched": "{white}There are more than one client matched",