diff --git a/MxValheim/EventSystem/Experience.cs b/MxValheim/EventSystem/Experience.cs index 8644367..850c0fc 100644 --- a/MxValheim/EventSystem/Experience.cs +++ b/MxValheim/EventSystem/Experience.cs @@ -15,30 +15,48 @@ namespace MxValheim.EventSystem return (level * 100); } - public static void AddExperience(string playerid, int amount) + public static float CalculateExpMultiplier(int level, Heightmap.Biome biome) { - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", playerid); - int level = Profiles.playerLevel; - int exp = Profiles.playerExperience; + Dictionary biomeBase = new Dictionary() + { + { 1, 1.0f }, + { 2, 1.5f }, + { 8, 2.0f }, + { 4, 2.5f }, + { 16, 3.0f }, + { 256, 3.5f }, + { 32, 4.0f }, + }; + + float rewardExpMulti = biomeBase[((int)biome)]; + + return rewardExpMulti; + } + + public static void AddExperience(int amount) + { + ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", "Event"); + int level = Profiles.serverLevel; + int exp = Profiles.serverExperience; exp += amount; - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_ServerSetUserExperience", playerid, exp); - exp = Profiles.playerExperience; + ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_ServerSetExperience", exp); + exp = Profiles.serverExperience; int maxexp = GetRequiredExpByLevel(level); - UpdateProgressBar(playerid); + UpdateProgressBar(); if (exp >= maxexp) { exp -= maxexp; level++; - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_ServerSetUserLevel", playerid, level); - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_ServerSetUserExperience", playerid, exp); - UpdateProgressBar(playerid); + ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_ServerSetLevel", level); + ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_ServerSetExperience", exp); + UpdateProgressBar(); } } - public static void UpdateProgressBar(string playerid) + public static void UpdateProgressBar() { - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", playerid); - float expPercentage = ((float)Profiles.playerExperience / GetRequiredExpByLevel(Profiles.playerLevel)); + ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", "Event"); + float expPercentage = ((float)Profiles.serverExperience / GetRequiredExpByLevel(Profiles.serverLevel)); if (Clock.m_barFill != null) { diff --git a/MxValheim/EventSystem/Patch.cs b/MxValheim/EventSystem/Patch.cs index 0f76252..d9ac643 100644 --- a/MxValheim/EventSystem/Patch.cs +++ b/MxValheim/EventSystem/Patch.cs @@ -24,14 +24,7 @@ namespace MxValheim.EventSystem { static void Postfix(Player __instance) { - // Only trigger for the actual human player, not NPCs/Dummies - if (__instance == Player.m_localPlayer) - { - string pid = GetUserPlayerID(Player.m_localPlayer).ToString(); - ZLog.Log($"[ProfileSystem] Spawning finished. Requesting profile for {pid}"); - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", pid); - } } } @@ -40,10 +33,7 @@ namespace MxValheim.EventSystem { static void Prefix(RandEventSystem __instance) { - // Use a small timer check so we don't spam the logic every single frame - // though for debugging, forcing these values is fine. - //__instance.m_eventIntervalMin = 10f; - //__instance.m_eventChance = 100f; + } } @@ -52,10 +42,47 @@ namespace MxValheim.EventSystem { static void Prefix(RandEventSystem __instance) { - + __instance.m_eventIntervalMin = 10f; + __instance.m_eventChance = 100f; } } + [HarmonyPatch(typeof(RandEventSystem), nameof(RandEventSystem.RPC_SetEvent))] + public static class RandEventEndPatch + { + private static readonly AccessTools.FieldRef ActiveEventField = AccessTools.FieldRefAccess("m_activeEvent"); + static void Prefix(RandEventSystem __instance, string eventName) + { + RandomEvent currentRaid = ActiveEventField(__instance); + if (string.IsNullOrEmpty(eventName) && currentRaid != null) + { + Vector3 playerPos = Player.m_localPlayer.transform.position; + float distance = Vector3.Distance(playerPos, currentRaid.m_pos); + + if (distance <= 96f) + { + Heightmap.Biome currentBiome = EnvMan.instance.GetCurrentBiome(); + Reward.GiveItemStatic("Coins", Reward.CalculateRewardCoin(Profiles.serverLevel, currentBiome)); + System.Random rand = new System.Random(); + Reward.GiveItemStatic("Feathers", rand.Next(5, 20)); + if (rand.Next(100) < 50) + { + Reward.GiveItemRandom(Reward.GetRewardPrefab(Profiles.serverLevel, "food"), 1); + } + if (rand.Next(100) < 25) + { + Reward.GiveItemRandom(Reward.GetRewardPrefab(Profiles.serverLevel, "heal"), 1); + } + if (rand.Next(100) < 10) + { + Reward.GiveItemRandom(Reward.GetRewardPrefab(Profiles.serverLevel, "metal"), rand.Next(5, 20)); + } + } + } + } + } + + /* [HarmonyPatch(typeof(Hud), nameof(Hud.Update))] public static class Hud_MonitorPatch { @@ -71,36 +98,14 @@ namespace MxValheim.EventSystem // 2. Logic: Detection if (activeEvent != null && _lastKnownEvent == null) { - Debug.Log($"MxEvent: HUD Heartbeat detected Raid Start: {activeEvent.m_name}"); - _lastKnownEvent = activeEvent; - - // Force HUD Creation and Display - //UpdateWave(true); + } else if (activeEvent == null && _lastKnownEvent != null) { - Debug.Log("MxEvent: HUD Heartbeat detected Raid End."); - string pid = GetUserPlayerID(Player.m_localPlayer).ToString(); - Heightmap.Biome currentBiome = EnvMan.instance.GetCurrentBiome(); - Reward.GiveItemStatic("Coins",Reward.CalculateRewardCoin(Profiles.playerLevel, currentBiome)); - System.Random rand = new System.Random(); - Reward.GiveItemStatic("Feathers", rand.Next(1,10)); - if (rand.Next(100) < 50) - { - Reward.GiveItemRandom(Reward.GetRewardPrefab(Profiles.playerLevel, "food"), 1); - } - if (rand.Next(100) < 25) - { - Reward.GiveItemRandom(Reward.GetRewardPrefab(Profiles.playerLevel, "heal"), 1); - } - if (rand.Next(100) < 10) - { - Reward.GiveItemRandom(Reward.GetRewardPrefab(Profiles.playerLevel, "metal"), 1); - } - _lastKnownEvent = null; + } } - } + }*/ [HarmonyPatch(typeof(Character), nameof(Character.ApplyDamage))] public static class DeathNotifier @@ -118,44 +123,25 @@ namespace MxValheim.EventSystem // 2. Check if a raid is active RandomEvent activeEvent = RandEventSystem.instance.GetActiveEvent(); if (activeEvent == null) return; - Debug.Log("MxEvent: Confirmed Active Event!"); Vector3 playerPos = Player.m_localPlayer.transform.position; - string pid = GetUserPlayerID(Player.m_localPlayer).ToString(); - Debug.Log($"EventSystem:ApplyDamage User {pid}"); float distance = Vector3.Distance(playerPos, activeEvent.m_pos); - Debug.Log($"MxEvent: Distance: {distance}"); if (distance <= 96f) { int level = __instance.GetLevel(); int exp = - (level == 1) ? 2: - (level == 2) ? 3: - (level == 3) ? 4: - 5; - - Experience.AddExperience(pid, exp); - - /* Send the update - ZRoutedRpc.instance.InvokeRoutedRPC( - ZRoutedRpc.Everybody, - "RPC_UpdateRaidHUD", - $"PHASE: {CurrentPhase}", - KillsInCurrentPhase, - GetTargetForPhase(CurrentPhase) - );*/ - } + (level == 1) ? 2 : + (level == 2) ? 4 : + (level == 3) ? 6 : + 6; + ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", "Event"); + Heightmap.Biome currentBiome = EnvMan.instance.GetCurrentBiome(); + int expFinal = (int)(exp * Experience.CalculateExpMultiplier(Profiles.serverLevel, currentBiome)); + Experience.AddExperience(expFinal); + } } } } - - // Hide HUD when raid ends - [HarmonyPatch(typeof(RandEventSystem), nameof(RandEventSystem.ResetRandomEvent))] - [HarmonyPostfix] - static void OnRaidEnd() - { - - } } } diff --git a/MxValheim/EventSystem/Profiles.cs b/MxValheim/EventSystem/Profiles.cs index 2c483f0..e5ffbbd 100644 --- a/MxValheim/EventSystem/Profiles.cs +++ b/MxValheim/EventSystem/Profiles.cs @@ -12,15 +12,13 @@ namespace MxValheim.EventSystem { public class ProfileRoot { - public string playerid { get; set; } - public string player_name { get; set; } public int level { get; set; } public int experience { get; set; } } public static bool userExists = false; - public static int playerLevel = 1; - public static int playerExperience = 0; + public static int serverLevel = 1; + public static int serverExperience = 0; public static void ServerUserExists(string playerid) @@ -28,9 +26,8 @@ namespace MxValheim.EventSystem // Check to ensure this is actually the server running this ZNet zn = new ZNet(); if (!zn.IsDedicated()) return; - string profilePath = Path.Combine(MxValheimMod.internalDataEventSystemPath, $"{playerid}.json"); - if (File.Exists(profilePath)) userExists = true; + if (File.Exists(MxValheimMod.internalDataEventSystem)) userExists = true; } public static void ServerReceiveCreateUser(long sender, string playerid, string playerName) @@ -39,129 +36,80 @@ namespace MxValheim.EventSystem ZNet zn = new ZNet(); if (!zn.IsDedicated()) return; - string profilePath = Path.Combine(MxValheimMod.internalDataEventSystemPath, $"{playerid}.json"); - ProfileRoot pr = new ProfileRoot { - playerid = playerid, - player_name = playerName, level = 1, experience = 0 }; var raw = JsonConvert.SerializeObject(pr, Formatting.Indented); - File.WriteAllText(profilePath, raw); + File.WriteAllText(MxValheimMod.internalDataEventSystem, raw); } - public static void ServerHandleProfileRequest(long sender, string playerid) + public static void ServerHandleProfileRequest(long sender, string required) { // Check to ensure this is actually the server running this ZNet zn = new ZNet(); if (!zn.IsDedicated()) return; - ZNetPeer peer = ZNet.instance.GetPeer(sender); - - string profilePath = Path.Combine(MxValheimMod.internalDataEventSystemPath, $"{playerid}.json"); - - if (File.Exists(profilePath)) + if (File.Exists(MxValheimMod.internalDataEventSystem)) { - string rawJson = File.ReadAllText(profilePath); - // Send ONLY to the 'sender' who requested it + string rawJson = File.ReadAllText(MxValheimMod.internalDataEventSystem); ZRoutedRpc.instance.InvokeRoutedRPC(sender, "RPC_ClientReceiveProfile", rawJson); } else { ProfileRoot pr = new ProfileRoot { - playerid = playerid, - player_name = peer.m_playerName, level = 1, experience = 0 }; var raw = JsonConvert.SerializeObject(pr, Formatting.Indented); - File.WriteAllText(profilePath, raw); + File.WriteAllText(MxValheimMod.internalDataEventSystem, raw); } } - public static void RequestCreateUser(string playerid, Player player) - { - string playerName = player.GetHoverName(); - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_ServerCreateUser", playerid, playerName); - } - - public static void ClientLoadProfile(long sender, string json) + public static void LoadProfile(long sender, string json) { ProfileRoot loadedProfile = JsonConvert.DeserializeObject(json); - playerLevel = loadedProfile.level; - playerExperience = loadedProfile.experience; - - //ZLog.Log($"[Client] Profile loaded! Level: {loadedProfile.level}"); + serverLevel = loadedProfile.level; + serverExperience = loadedProfile.experience; } - public static void CreateUser(string playerid, Player player) - { - // We only send the raw data; we let the server handle the file I/O - string playerName = player?.GetHoverName() ?? "Unknown"; - - // Invoke the RPC on the Server (0 is the server ID) - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_ServerCreateUser", playerid, playerName); - } - - public static void ServerSetUserExperience(long sender, string playerid, int exp) + public static void ServerSetExperience(long sender, int exp) { // Check to ensure this is actually the server running this ZNet zn = new ZNet(); if (!zn.IsDedicated()) return; - string profilePath = Path.Combine(MxValheimMod.internalDataEventSystemPath, $"{playerid}.json"); - ProfileRoot pro = JsonConvert.DeserializeObject(File.ReadAllText(profilePath)); + ProfileRoot pro = JsonConvert.DeserializeObject(File.ReadAllText(MxValheimMod.internalDataEventSystem)); ProfileRoot pr = new ProfileRoot { - playerid = playerid, - player_name = pro.player_name, level = pro.level, experience = exp }; var raw = JsonConvert.SerializeObject(pr, Formatting.Indented); - File.WriteAllText(profilePath, raw); - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", playerid); + File.WriteAllText(MxValheimMod.internalDataEventSystem, raw); + ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", "Event"); } - public static void SetUserExperience(string playerid, int exp) - { - string profilePath = Path.Combine(MxValheimMod.internalDataEventSystemPath, $"{playerid}.json"); - ProfileRoot pro = JsonConvert.DeserializeObject(File.ReadAllText(profilePath)); - ProfileRoot pr = new ProfileRoot - { - playerid = playerid, - player_name = pro.player_name, - level = pro.level, - experience = exp - }; - var raw = JsonConvert.SerializeObject(pr, Formatting.Indented); - File.WriteAllText(profilePath, raw); - } - - public static void ServerSetUserLevel(long sender, string playerid, int level) + public static void ServerSetLevel(long sender, int level) { // Check to ensure this is actually the server running this ZNet zn = new ZNet(); if (!zn.IsDedicated()) return; - string profilePath = Path.Combine(MxValheimMod.internalDataEventSystemPath, $"{playerid}.json"); - ProfileRoot pro = JsonConvert.DeserializeObject(File.ReadAllText(profilePath)); + ProfileRoot pro = JsonConvert.DeserializeObject(File.ReadAllText(MxValheimMod.internalDataEventSystem)); ProfileRoot pr = new ProfileRoot { - playerid = playerid, - player_name = pro.player_name, level = level, experience = pro.experience }; var raw = JsonConvert.SerializeObject(pr, Formatting.Indented); - File.WriteAllText(profilePath, raw); - ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", playerid); + File.WriteAllText(MxValheimMod.internalDataEventSystem, raw); + ZRoutedRpc.instance.InvokeRoutedRPC(0, "RPC_RequestProfile", "Event"); } } } diff --git a/MxValheim/EventSystem/Reward.cs b/MxValheim/EventSystem/Reward.cs index 5ece29a..48833b5 100644 --- a/MxValheim/EventSystem/Reward.cs +++ b/MxValheim/EventSystem/Reward.cs @@ -15,17 +15,17 @@ namespace MxValheim.EventSystem { { 1, 10 }, { 2, 20 }, - { 4, 30 }, - { 8, 40 }, + { 8, 30 }, + { 4, 40 }, { 16, 50 }, - { 512, 60 }, - { 64, 70 }, + { 256, 60 }, + { 32, 70 }, }; int rewardCoin = biomeBase[((int)biome)] * level; return rewardCoin; - } + } public static string GetRewardPrefab(int level, string type) { diff --git a/MxValheim/MxValheim.cs b/MxValheim/MxValheim.cs index f685c3d..81d5bbe 100644 --- a/MxValheim/MxValheim.cs +++ b/MxValheim/MxValheim.cs @@ -28,7 +28,7 @@ public class MxValheimMod : BaseUnityPlugin private const string ModGUID = "ovh.mxdev.mxvalheim"; private const string ModName = "MxValheim"; - private const string ModVersion = "1.6.1"; + private const string ModVersion = "1.6.2"; public static ConfigEntry Config_Locked; public static ConfigEntry Config_OreMultiplier; @@ -42,7 +42,7 @@ public class MxValheimMod : BaseUnityPlugin public static string modPath = Path.Combine(Paths.PluginPath, "MxValheim"); public static string internalConfigsPath = Path.Combine(modPath, "Configs"); public static string internalDataPath = Path.Combine(modPath, "Data"); - public static string internalDataEventSystemPath = Path.Combine(internalDataPath, "EventSystem"); + public static string internalDataEventSystem = Path.Combine(internalDataPath, "EventSystem.json"); public static string WeightConfigPath => Path.Combine(internalConfigsPath, "items_weight.json"); public static string AutoDoorConfigPath => Path.Combine(internalConfigsPath, "auto_doors.json"); public static DoorRoot CachedConfig; @@ -81,6 +81,8 @@ public class MxValheimMod : BaseUnityPlugin public static readonly Queue _doorQueueName = new Queue(); public static float _doorTimer; + public static readonly Queue _serverEvent = new Queue(); + void Awake() { Instance = this; @@ -139,10 +141,9 @@ public class MxValheimMod : BaseUnityPlugin ZRoutedRpc.instance.Register("RPC_ServerCreateUser", Profiles.ServerReceiveCreateUser); ZRoutedRpc.instance.Register("RPC_RequestProfile", Profiles.ServerHandleProfileRequest); - ZRoutedRpc.instance.Register("RPC_ClientReceiveProfile", Profiles.ClientLoadProfile); - ZRoutedRpc.instance.Register("RPC_UpdateProgressBar", Profiles.ClientLoadProfile); - ZRoutedRpc.instance.Register("RPC_ServerSetUserExperience", Profiles.ServerSetUserExperience); - ZRoutedRpc.instance.Register("RPC_ServerSetUserLevel", Profiles.ServerSetUserLevel); + ZRoutedRpc.instance.Register("RPC_ClientReceiveProfile", Profiles.LoadProfile); + ZRoutedRpc.instance.Register("RPC_ServerSetExperience", Profiles.ServerSetExperience); + ZRoutedRpc.instance.Register("RPC_ServerSetLevel", Profiles.ServerSetLevel); } } } @@ -153,7 +154,7 @@ public class MxValheimMod : BaseUnityPlugin if (Player.m_localPlayer != null) { string pid = GetUserPlayerID(Player.m_localPlayer).ToString(); - Experience.UpdateProgressBar(pid); + Experience.UpdateProgressBar(); } // Only run if we are actually in the game world @@ -177,7 +178,7 @@ public class MxValheimMod : BaseUnityPlugin if (initExpBar) { string pid = GetUserPlayerID(Player.m_localPlayer).ToString(); - Experience.UpdateProgressBar(pid); + Experience.UpdateProgressBar(); initExpBar = false; } } @@ -188,7 +189,7 @@ public class MxValheimMod : BaseUnityPlugin string timeString = clk.GetFormattedTime(); int day = EnvMan.instance.GetDay(); string pid = GetUserPlayerID(Player.m_localPlayer).ToString(); - Clock.m_textComponent.text = $"{Localization.instance.Localize("$clock_string_rank")} {Profiles.playerLevel} | {Localization.instance.Localize("$clock_string_day")} {day} | {timeString}"; + Clock.m_textComponent.text = $"{Localization.instance.Localize("$clock_string_rank")} {Profiles.serverLevel} | {Localization.instance.Localize("$clock_string_day")} {day} | {timeString}"; } }