using GTANetworkAPI; using ReallifeGamemode.Server.Entities; using ReallifeGamemode.Server.Models; using System; using System.Collections.Generic; using System.Timers; namespace ReallifeGamemode.Server.Managers { public class VehicleManager { private static readonly List _enabledMods = new List() { "models", "polamggtr", "impaler3", "monster4", "monster5", "slamvan6", "issi6", "cerberus2", "cerberus3", "deathbike2", "dominator6", "deathbike3", "impaler4", "slamvan4", "slamvan5", "brutus", "brutus2", "brutus3", "deathbike", "dominator4", "dominator5", "bruiser", "bruiser2", "bruiser3", "rcbandito", "italigto", "cerberus", "impaler2", "monster3", "tulip", "scarab", "scarab2", "scarab3", "issi4", "issi5", "clique", "deveste", "vamos", "imperator", "imperator2", "imperator3", "toros", "deviant", "schlagen", "impaler", "zr380", "zr3802", "zr3803", "flashgt", "gb200", "dominator3", "tezeract", "entity2", "taipan", "g65amg" }; private static readonly Dictionary _serverVehicles = new Dictionary(); private static readonly Dictionary lastPositions = new Dictionary(); private static DateTime lastSave = DateTime.UtcNow; public static void StartTimer() { Timer timer = new Timer(500); timer.Elapsed += VehicleTimerTick; timer.Start(); } private static void VehicleTimerTick(object sender, ElapsedEventArgs e) { NAPI.Pools.GetAllVehicles().ForEach(v => { Vector3 lastPosition = v.Position; if (lastPositions.ContainsKey(v.Handle)) lastPosition = lastPositions[v.Handle]; double distanceDriven = v.HasSharedData("drivenDistance") ? (double)v.GetSharedData("drivenDistance") : 0D; distanceDriven += (lastPosition.DistanceTo(v.Position) / 1000.0); v.SetSharedData("drivenDistance", (float)distanceDriven); lastPositions[v.Handle] = v.Position; }); if (DateTime.UtcNow.Subtract(lastSave).Seconds >= 30) { lastSave = DateTime.UtcNow; // save to db using (var dbContext = new DatabaseContext()) { foreach (var key in lastPositions.Keys) { Vehicle v = key.Entity(); if (!v.HasSharedData("drivenDistance")) continue; ServerVehicle sVeh = VehicleManager.GetServerVehicleFromVehicle(v, dbContext); if (sVeh == null) continue; sVeh.DistanceDriven = (float)v.GetSharedData("drivenDistance"); } dbContext.SaveChanges(); } } } public static void AddVehicle(ServerVehicle serverVehicle, Vehicle vehicle) { if (_serverVehicles.ContainsKey(serverVehicle.Id)) { return; } if (_serverVehicles.ContainsValue(vehicle.Handle)) { return; } _serverVehicles[serverVehicle.Id] = vehicle.Handle; } internal static void DeleteVehicle(Vehicle veh) { ServerVehicle sVeh; if ((sVeh = GetServerVehicleFromVehicle(veh)) != null) { _serverVehicles.Remove(sVeh.Id); } veh.Delete(); } public static Vehicle GetVehicleFromHandle(NetHandle handle) { return NAPI.Pools.GetAllVehicles().Find(v => v.Handle == handle); } public static Vehicle GetVehicleFromId(int id) { return NAPI.Pools.GetAllVehicles().Find(v => v.Handle.Value == id); } public static Vehicle GetVehicleFromServerVehicle(ServerVehicle serverVehicle) { if (!_serverVehicles.ContainsKey(serverVehicle.Id)) { return null; } return GetVehicleFromHandle(_serverVehicles[serverVehicle.Id]); } public static ServerVehicle GetServerVehicleFromVehicle(Vehicle veh, DatabaseContext dbContext = null) { dbContext = dbContext ?? new DatabaseContext(); foreach (KeyValuePair pair in _serverVehicles) { if (pair.Value == veh.Handle) { return dbContext.ServerVehicles.Find(pair.Key); } } return null; } public static bool IsValidHash(uint hash) { foreach (VehicleHash vh in Enum.GetValues(typeof(VehicleHash))) { if ((uint)vh == hash) return true; } foreach (string mod in _enabledMods) { if (NAPI.Util.GetHashKey(mod) == hash) return true; } return false; } } }