using System.Collections.Generic; using GTANetworkAPI; using Newtonsoft.Json; using ReallifeGamemode.Server.Services; using System.Linq; using ReallifeGamemode.Services; using ReallifeGamemode.Database.Entities; using ReallifeGamemode.Database.Models; using Microsoft.EntityFrameworkCore; using System; using ReallifeGamemode.Server.Extensions; using Microsoft.Extensions.Logging; using ReallifeGamemode.Server.Log; /** * @overview Life of German Reallife - Server Factions Medic Medic.cs * @author VegaZ * @copyright (c) 2008 - 2018 Life of German */ namespace ReallifeGamemode.Server.Factions.Medic { public class Medic : Script { private static readonly ILogger logger = LogManager.GetLogger(); public static List ReviveTasks = new List(); public static List HealTasks = new List(); public static List FireTasks = new List(); public static List HealDecisions = new List(); public static int ReviveIncome = 50; public static int dutyMedics = 0; public static int reviveTaskTime = 120; public class HealDecision { public Player dMedic; public Player dTarget; public int dPrice; } public static void AddTaskToList(MedicTask task) { if (task == null) { return; } switch (task.Type) { case MedicTaskType.REVIVE: ReviveTasks.Add(task); break; case MedicTaskType.HEAL: HealTasks.Add(task); break; case MedicTaskType.FIRE: FireTasks.Add(task); break; } } public static void RemoveTaskFromList(MedicTask task) { if (task == null) { return; } switch (task.Type) { case MedicTaskType.REVIVE: ReviveTasks.Remove(task); break; case MedicTaskType.HEAL: HealTasks.Remove(task); break; case MedicTaskType.FIRE: FireTasks.Remove(task); break; } } public static void UpdateReviveSperre() { var allRevivedPlayers = NAPI.Pools.GetAllPlayers().Where(c => c.HasData("reviveSperre")); foreach (var player in allRevivedPlayers) { var timeLeft = player.GetData("reviveSperre"); if (timeLeft > 0) { player.SetData("reviveSperre", timeLeft - 1); } else { player.ResetData("reviveSperre"); } } } public static void CheckHealDecisionDistance() { foreach (var healAuftrag in HealDecisions.ToList()) { if (healAuftrag.dMedic.Position.DistanceTo(healAuftrag.dTarget.Position) > 5) { healAuftrag.dMedic.SendNotification("~r~Die Heal-Anfrage wurde abgebrochen"); healAuftrag.dTarget.SendNotification("~r~Die Heal-Anfrage wurde abgebrochen"); healAuftrag.dTarget.ResetData("healDecision"); var activeDecision = HealDecisions.FirstOrDefault(d => d.dTarget == healAuftrag.dTarget); HealDecisions.Remove(healAuftrag); } } } public static void MakeHealDecision(Player target, bool decision) { var activeDecision = HealDecisions.FirstOrDefault(d => d.dTarget == target); if (decision == false) { activeDecision.dMedic.SendNotification(activeDecision.dTarget.Name + " hat den Heal ~r~abgelehnt", false); activeDecision.dTarget.SendNotification("Du hast den Heal ~r~abgelehnt", false); } else { activeDecision.dMedic.SendNotification(activeDecision.dTarget.Name + " hat den Heal ~g~akzeptiert", false); activeDecision.dTarget.SendNotification("Du hast den Heal ~g~akzeptiert", false); using var dbContext = new DatabaseContext(); { User targetUser = target.GetUser(dbContext); if (targetUser.Handmoney >= activeDecision.dPrice) { targetUser.Handmoney -= activeDecision.dPrice; } else { int bankMoney = activeDecision.dPrice - targetUser.Handmoney; targetUser.Handmoney = 0; targetUser.BankAccount.Balance -= bankMoney; } logger.LogInformation("Player {0} accepted a heal for {1} dollars from medic {2}", target.Name, activeDecision.dPrice, activeDecision.dMedic.Name); dbContext.Factions.Include(f => f.BankAccount).Where(f => f.Id == 2).First().BankAccount.Balance += activeDecision.dPrice / 2; activeDecision.dMedic.GetUser(dbContext).Wage += activeDecision.dPrice / 2; dbContext.SaveChanges(); } activeDecision.dTarget.SafeSetHealth(100); activeDecision.dTarget.SendNotification($"Du wurdest von ~g~{activeDecision.dMedic.Name} ~s~ für ~g~{activeDecision.dPrice.ToMoneyString()} geheilt", false); activeDecision.dMedic.SendNotification($"Du hast ~g~{activeDecision.dTarget.Name} ~s~ für {activeDecision.dPrice.ToMoneyString()} geheilt", false); delHealTask(activeDecision.dTarget); } HealDecisions.Remove(activeDecision); } public static void UpdateTaskTimeLeft() { if (ReviveTasks.Count != 0) { DateTime actualTime = DateTime.Now; foreach (var task in ReviveTasks) { if (task.MedicName != "none") { var taskTimeLeft = Math.Abs((int)(((DateTimeOffset)actualTime).ToUnixTimeSeconds() - ((DateTimeOffset)task.Time).ToUnixTimeSeconds() - reviveTaskTime)); task.TimeLeft = taskTimeLeft; var medic = PlayerService.GetPlayerByNameOrId(task.MedicName); if (medic != null) medic.TriggerEvent("setTaskTimeLeft", taskTimeLeft); } } } } public static void UpdateHealTaskCheckpoint() { if (HealTasks.Count != 0) { foreach (var task in HealTasks) { if (task.MedicName != "none") { var medic = PlayerService.GetPlayerByNameOrId(task.MedicName); var victim = PlayerService.GetPlayerByNameOrId(task.Victim); if (medic == null || victim == null) { continue; } task.Position = victim.Position; medic.TriggerEvent("updateHealCheckpoint", victim.Position.X, victim.Position.Y, victim.Position.Z); } } } } public static void RemoveOldHealTask() { if (HealTasks.Count != 0) { foreach (var task in HealTasks.ToList()) { var taskActive = DateTime.Now - task.Time; if (taskActive > TimeSpan.FromMinutes(10) && task.MedicName == "none") { delHealTask(PlayerService.GetPlayerByNameOrId(task.Victim)); } } } } [RemoteEvent("loadMedicTasks")] public void LoadMedicTasks(Player player, int type) { switch (type) { case 0: player.TriggerEvent("showMedicTasks", 0, JsonConvert.SerializeObject(ReviveTasks)); break; case 1: player.TriggerEvent("showMedicTasks", 1, JsonConvert.SerializeObject(HealTasks)); break; case 2: player.TriggerEvent("showMedicTasks", 2, JsonConvert.SerializeObject(FireTasks)); break; } } [RemoteEvent("updateMedicTask")] public void UpdateMedicTasks(Player player, int type, string victim, bool isRemoved) { Player target = PlayerService.GetPlayerByNameOrId(victim); switch (type) { case 0: var reviveTask = ReviveTasks.FirstOrDefault(t => t.Victim == victim); if (isRemoved) { reviveTask.MedicName = "none"; } else { reviveTask.MedicName = player.Name; } ChatService.BroadcastFaction("~y~[MEDIC] ~w~" + player.Name + " hat den Reviveauftrag von " + victim + " angenommen.", new List() { 2 }); target.SendNotification("~w~Sanitäter~g~ " + player.Name + "~w~ eilt zur Rettung."); break; case 1: var healTask = HealTasks.FirstOrDefault(t => t.Victim == victim); if (isRemoved) { healTask.MedicName = "none"; } else { healTask.MedicName = player.Name; ChatService.BroadcastFaction("~y~[MEDIC] ~w~" + player.Name + " hat den Healauftrag von " + victim + " angenommen.", new List() { 2 }); target.SendNotification("~w~Sanitäter~g~ " + player.Name + "~w~ hat deinen Auftrag angenommen."); } break; case 2: //FireTasks[index].MedicName = player.Name; break; } } [RemoteEvent("delHealTask")] public static void delHealTask(Player player) { MedicTask task = HealTasks.FirstOrDefault(t => t.Victim == player.Name); if (task != null) { player.SetData("healauftrag", false); var medicPlayer = PlayerService.GetPlayerByNameOrId(task.MedicName); if (medicPlayer != null) { medicPlayer.TriggerEvent("destroyMedicTaskCheckpoint"); } RemoveTaskFromList(task); } } [RemoteEvent("delHealTaskAsMedic")] public static void delHealTaskAsMedic(Player player, string victimName) { MedicTask task = HealTasks.FirstOrDefault(t => t.Victim == victimName); RemoveTaskFromList(task); player.SetData("healauftrag", false); } public static void delReviveTask(Player target) { MedicTask task = ReviveTasks.FirstOrDefault(t => t.Victim == target.Name); if (task != null) { var medicPlayer = PlayerService.GetPlayerByNameOrId(task.MedicName); if (task.MedicName != "none") { medicPlayer.TriggerEvent("destroyMedicTaskCheckpoint"); } RemoveTaskFromList(task); } } [RemoteEvent("GetDutyMedics")] public static void UpdateDutyMedics() { dutyMedics = NAPI.Pools.GetAllPlayers().Where(c => c.IsDuty() == true && c.GetUser().FactionId == 2).ToList().Count; NAPI.ClientEvent.TriggerClientEventForAll("updateDutyMedics", dutyMedics); } } }