using System.Collections.Generic; public class HiresManagerRebirth { private static HiresManagerRebirth instance = null; private static readonly object Locker = new object(); public static bool loadedHires = false; private const string saveFile = "RebirthManager.dat"; private static ThreadManager.ThreadInfo dataSaveThreadInfo; public static List playerHires = new List(); public static List observers = new List(); private static float updateCheck = 0f; private static float updateTick = 10f; public static bool HasInstance => instance != null; public class chunkObservers { public int entityID; public ChunkManager.ChunkObserver observerRef; public chunkObservers() { } public chunkObservers(int entityID, ChunkManager.ChunkObserver observerRef) { this.entityID = entityID; this.observerRef = observerRef; } } public class hireInfo { public int playerID; public int hireID; public string name; public string className; public Vector3 spawnPosition; public Vector3 spawnRotation; public Vector3 reSpawnPosition; public Vector3 reSpawnRotation; public int numKills; public int numMine; public int order; public bool playerSpawned; //eventually add backpack and toolbelt content public hireInfo() { } public hireInfo(int playerID, int hireID, string name, string className, Vector3 spawnPosition, Vector3 spawnRotation, Vector3 reSpawnPosition, Vector3 reSpawnRotation, int numKills, int numMine, int order, bool playerSpawned = false ) { this.playerID = playerID; this.hireID = hireID; this.name = name; this.className = className; this.spawnPosition = spawnPosition; this.spawnRotation = spawnRotation; this.reSpawnPosition = reSpawnPosition; this.reSpawnRotation = reSpawnRotation; this.numKills = numKills; this.numMine = numMine; this.order = order; this.playerSpawned = playerSpawned; } } public static HiresManagerRebirth Instance { get { return instance; } } public static void Init() { HiresManagerRebirth.instance = new HiresManagerRebirth(); //Log.Out("Starting Hires Manager"); Load(); //Log.Out("HiresManagerRebirth-Init LOADED HIRES"); loadedHires = true; ModEvents.GameUpdate.RegisterHandler(Update); } public static void Update() { //lock (Locker) { if (!RebirthUtilities.IsHordeNight() && (Time.time - updateCheck) > updateTick) { updateCheck = Time.time; bool isClient = SingletonMonoBehaviour.Instance.IsClient; if (!isClient) { for (int i = 0; i < observers.Count; i++) { bool foundHire = false; foreach (hireInfo hire in playerHires) { if (observers[i].entityID == hire.hireID && (hire.order == 1 || hire.order == 2)) { foundHire = true; break; } } if (!foundHire) { GameManager.Instance.RemoveChunkObserver(observers[i].observerRef); observers.RemoveAt(i); //Log.Out("HiresManagerRebirth-Update A REMOVED OBSERVER"); break; } } List spawnedPlayers = new List(); foreach (hireInfo hire in playerHires) { EntityPlayer player = GameManager.Instance.World.GetEntity(hire.playerID) as EntityPlayer; if (player) { if (player.IsSpawned() && !player.AttachedToEntity) { if (!spawnedPlayers.Contains(player)) { spawnedPlayers.Add(player); } //Log.Out("HiresManagerRebirth-Update Player Spawned: " + hire.playerID); if (hire.order == 1 || hire.order == 2) { bool foundHire = false; foreach (chunkObservers observer in observers) { if (observer.entityID == hire.hireID) { foundHire = true; break; } } if (!foundHire) { //Log.Out("HiresManagerRebirth-Update ADDED CHUNK OBSERVER for: " + hire.hireID); ChunkManager.ChunkObserver observerRef = GameManager.Instance.AddChunkObserver(hire.spawnPosition, false, 3, -1); observers.Add(new chunkObservers(hire.hireID, observerRef)); } } else if (hire.order == 0) { for (int i = 0; i < observers.Count; i++) { if (observers[i].entityID == hire.hireID) { GameManager.Instance.RemoveChunkObserver(observers[i].observerRef); observers.RemoveAt(i); //Log.Out("HiresManagerRebirth-Update REMOVED OBSERVER"); break; } } } hire.playerSpawned = true; } else { //Log.Out("HiresManagerRebirth-Update Player NOT Spawned: " + hire.playerID); } } ////Log.Out("HiresManagerRebirth-Update hire.playerID: " + hire.playerID); //Log.Out("HiresManagerRebirth-Update hire.hireID: " + hire.hireID); //Log.Out("HiresManagerRebirth-Update hire.name: " + hire.name); //Log.Out("HiresManagerRebirth-Update hire.className: " + hire.className); //Log.Out("HiresManagerRebirth-Update hire.spawnPosition: " + hire.spawnPosition); //Log.Out("HiresManagerRebirth-Update hire.spawnRotation: " + hire.spawnRotation); //Log.Out("HiresManagerRebirth-Update hire.reSpawnPosition: " + hire.reSpawnPosition); //Log.Out("HiresManagerRebirth-Update hire.reSpawnRotation: " + hire.reSpawnRotation); ////Log.Out("HiresManagerRebirth-Update hire.numKills: " + hire.numKills); ////Log.Out("HiresManagerRebirth-Update hire.numMine: " + hire.numMine); ////Log.Out("HiresManagerRebirth-Update hire.order: " + hire.order); //Log.Out("HiresManagerRebirth-Update hire.playerSpawned: " + hire.playerSpawned); } //Log.Out("HiresManagerRebirth-Update observers.Count: " + observers.Count); /*foreach (chunkObservers observer in observers) { //Log.Out("HiresManagerRebirth-Update observer: " + observer.entityID); //Log.Out("HiresManagerRebirth-Update observer.observerRef.position: " + observer.observerRef.position); }*/ foreach (EntityPlayer player in spawnedPlayers) { //Log.Out("HiresManagerRebirth-Update CHECKING PLAYER: " + player.entityId + " / OWNED HIRES: " + playerHires.Count); if (player.Buffs.HasBuff("god") || player.Buffs.HasBuff("FuriousRamsayDelay-10") || player.Buffs.HasBuff("FuriousRamsayDelay-5") || player.AttachedToEntity) { continue; } Chunk chunkPlayer = (Chunk)GameManager.Instance.World.GetChunkFromWorldPos((int)player.position.x, (int)player.position.z); for (int i = 0; i < playerHires.Count; i++) { hireInfo hire = playerHires[i]; //Log.Out("HiresManagerRebirth-Update CHECKING HIRE: " + hire.hireID + " / entity: " + hire.className + " / rsSpawnPosition: " + hire.reSpawnPosition); if (hire.playerID == player.entityId) { EntityNPCRebirth hiredNPC = GameManager.Instance.World.GetEntity(hire.hireID) as EntityNPCRebirth; if (hiredNPC == null) { //Log.Out("HiresManagerRebirth-Update HIRE COULDN'T BE FOUND IN WORLD"); Vector3 respawnPosition = new Vector3(0, 0, 0); Vector3 respawnRotation = new Vector3(0, 0, 0); if (hire.reSpawnPosition != new Vector3(0, 0, 0)) { //Log.Out("HiresManagerRebirth-CheckHires RESPAWN POINT WAS SET, USING IT"); respawnPosition = hire.reSpawnPosition; respawnRotation.y = player.rotation.y; } else { //Log.Out("HiresManagerRebirth-CheckHires NO RESPAWN POINT WAS SET, USING BEDROLL IF ONE EXISTS"); SpawnPosition spawnPoint = RebirthUtilities.GetSpawnPoint(player); if (spawnPoint.IsUndef()) { //Log.Out("HiresManagerRebirth-CheckHires NO BEDROLL FOUND, USING PLAYER'S POSITION"); respawnPosition = player.position; respawnRotation.y = player.rotation.y; continue; } else { //Log.Out("HiresManagerRebirth-CheckHires BEDROLL FOUND, USING IT"); respawnPosition = spawnPoint.position; respawnRotation.y = player.rotation.y; } } //Log.Out("HiresManagerRebirth-CheckHires Player's position: " + player.position); //Log.Out("HiresManagerRebirth-CheckHires respawnPosition: " + respawnPosition); Chunk chunkHire = (Chunk)GameManager.Instance.World.GetChunkFromWorldPos((int)respawnPosition.x, (int)respawnPosition.z); //Log.Out("HiresManagerRebirth-Update chunkPlayer pos: " + chunkPlayer.ChunkPos); if (chunkHire != null && ( ((chunkHire.ChunkPos.x == chunkPlayer.ChunkPos.x) && (chunkHire.ChunkPos.z == chunkPlayer.ChunkPos.z)) || ((chunkHire.ChunkPos.x == chunkPlayer.ChunkPos.x + 1) && (chunkHire.ChunkPos.z == chunkPlayer.ChunkPos.z)) || ((chunkHire.ChunkPos.x == chunkPlayer.ChunkPos.x - 1) && (chunkHire.ChunkPos.z == chunkPlayer.ChunkPos.z)) || ((chunkHire.ChunkPos.x == chunkPlayer.ChunkPos.x) && (chunkHire.ChunkPos.z == chunkPlayer.ChunkPos.z - 1)) || ((chunkHire.ChunkPos.x == chunkPlayer.ChunkPos.x + 1) && (chunkHire.ChunkPos.z == chunkPlayer.ChunkPos.z - 1)) || ((chunkHire.ChunkPos.x == chunkPlayer.ChunkPos.x - 1) && (chunkHire.ChunkPos.z == chunkPlayer.ChunkPos.z)) || ((chunkHire.ChunkPos.x == chunkPlayer.ChunkPos.x) && (chunkHire.ChunkPos.z == chunkPlayer.ChunkPos.z + 1)) || ((chunkHire.ChunkPos.x == chunkPlayer.ChunkPos.x + 1) && (chunkHire.ChunkPos.z == chunkPlayer.ChunkPos.z + 1)) || ((chunkHire.ChunkPos.x == chunkPlayer.ChunkPos.x - 1) && (chunkHire.ChunkPos.z == chunkPlayer.ChunkPos.z)) ) ) { //Log.Out("HiresManagerRebirth-Update chunkHire pos: " + chunkHire.ChunkPos); Entity entity = player.world.GetEntity(hire.hireID); if (entity == null) { //Log.Out("HiresManagerRebirth-Update ADDED MISSING HIRE: " + hire.hireID); EntityNPCRebirth NewEntity = EntityFactory.CreateEntity(EntityClass.FromString(hire.className), respawnPosition, respawnRotation) as EntityNPCRebirth; NewEntity.SetSpawnerSource(EnumSpawnerSource.StaticSpawner); NewEntity._strMyName = hire.name; RebirthUtilities.SetLeaderAndOwner(NewEntity.entityId, player.entityId); NewEntity.IsEntityUpdatedInUnloadedChunk = true; NewEntity.bWillRespawn = true; NewEntity.bIsChunkObserver = true; NewEntity.belongsPlayerId = player.entityId; NewEntity.guardPosition = respawnPosition; bool addObserver = false; GameManager.Instance.World.SpawnEntityInWorld(NewEntity); int oldHireID = hire.hireID; hire.hireID = NewEntity.entityId; hire.order = 1; SaveCurrent(); //Log.Out("HiresManagerRebirth-Update player.entityId: " + player.entityId); //Log.Out("HiresManagerRebirth-Update NewEntity.entityId: " + NewEntity.entityId); RebirthManager.UpdateHireInfo(oldHireID, "newid", "", "", "", NewEntity.entityId); if (hire.order == (int)EntityUtilities.Orders.None) { //Log.Out("HiresManagerRebirth-Update SET TO FOLLOW"); NewEntity.Buffs.SetCustomVar("CurrentOrder", (int)EntityUtilities.Orders.Follow); } else if (hire.order == (int)EntityUtilities.Orders.Follow) { //Log.Out("HiresManagerRebirth-Update SET TO STAY"); NewEntity.Buffs.SetCustomVar("CurrentOrder", (int)EntityUtilities.Orders.Stay); addObserver = true; } else { //Log.Out("HiresManagerRebirth-Update SET TO STAY (GUARD)"); NewEntity.Buffs.SetCustomVar("CurrentOrder", (int)EntityUtilities.Orders.Stay); addObserver = true; } RebirthUtilities.SetLeaderAndOwner(NewEntity.entityId, player.entityId); bool foundObserver = false; for (int j = 0; j < observers.Count; j++) { if (observers[j].entityID == hire.hireID) { //Log.Out("HiresManagerRebirth-CheckHires UPDATED OBSERVER, hire: " + hire.hireID); observers[j].entityID = NewEntity.entityId; foundObserver = true; break; } } float flMode = player.Buffs.GetCustomVar("varNPCModMode"); float flHalt = player.Buffs.GetCustomVar("varNPCModStopAttacking"); if (flMode == 0) { NewEntity.Buffs.AddBuff("buffNPCModFullControlMode"); } else { NewEntity.Buffs.RemoveBuff("buffNPCModFullControlMode"); } if (flHalt == 1) { NewEntity.Buffs.AddBuff("buffNPCModStopAttacking"); } else { NewEntity.Buffs.RemoveBuff("buffNPCModStopAttacking"); } if (addObserver && !foundObserver) { //Log.Out("HiresManagerRebirth-CheckHires ADDED CHUNK OBSERVER, hire: " + hire.hireID); ChunkManager.ChunkObserver observerRef = GameManager.Instance.AddChunkObserver(NewEntity.position, false, 3, -1); observers.Add(new chunkObservers(NewEntity.entityId, observerRef)); } } else { //Log.Out("HiresManagerRebirth-CheckHires HIRE EXISTS AT THIS POSITION: " + entity.position); } } } } } } } else { /*foreach (hireInfo hire in playerHires) { Log.Out("HiresManagerRebirth-Update hire.hireID: " + hire.hireID); Log.Out("HiresManagerRebirth-Update hire.className: " + hire.className); Log.Out("HiresManagerRebirth-Update hire.playerSpawned: " + hire.playerSpawned); }*/ } } } } public static void RemoveHire(int entityID, bool removeObserver = false) { //Log.Out("HiresManagerRebirth-RemoveHire entityID: " + entityID); bool foundHire = false; for (int i = 0; i < playerHires.Count; i++) { //Log.Out("HiresManagerRebirth-RemoveHire 2, playerHires[i].hireID: " + playerHires[i].hireID); if (playerHires[i].hireID == entityID) { foundHire = true; //Log.Out("HiresManagerRebirth-RemoveHire 3"); if (SingletonMonoBehaviour.Instance.IsServer) { //Log.Out("HiresManagerRebirth-RemoveHire IS SERVER"); if (RebirthUtilities.SendToClient(playerHires[i].playerID)) { SingletonMonoBehaviour.Instance.SendPackage(NetPackageManager.GetPackage().Setup(entityID ), false, playerHires[i].playerID, -1, -1, null, 192); //Log.Out("HiresManagerRebirth-RemoveHire SENT TO CLIENT"); } playerHires.RemoveAt(i); if (removeObserver) { //Log.Out("HiresManagerRebirth-RemoveHire 4"); for (int j = 0; j < observers.Count; j++) { if (observers[j].entityID == entityID) { //Log.Out("HiresManagerRebirth-RemoveHire REMOVED OBSERVER, hire: " + entityID); GameManager.Instance.RemoveChunkObserver(observers[j].observerRef); observers.RemoveAt(j); break; } } } SaveCurrent(); } else { SingletonMonoBehaviour.Instance.SendToServer(NetPackageManager.GetPackage().Setup(entityID ), false); playerHires.RemoveAt(i); //Log.Out("HiresManagerRebirth-RemoveHire SENT TO SERVER"); } //Log.Out("HiresManagerRebirth-RemoveHire Removed Hire: " + entityID); break; } } if (!foundHire) { //Log.Out("HiresManagerRebirth-RemoveHire COULD NOT FIND HIRE"); if (SingletonMonoBehaviour.Instance.IsClient) { //Log.Out("HiresManagerRebirth-RemoveHire IS CLIENT"); SingletonMonoBehaviour.Instance.SendToServer(NetPackageManager.GetPackage().Setup(entityID ), false); } } } public static void AddHire(int playerID, int hireID, string name, string className, Vector3 spawnPosition, Vector3 spawnRotation, Vector3 reSpawnPosition, Vector3 reSpawnRotation, int numKills, int numMine, int order, bool playerSpawned ) { bool foundHire = false; foreach (hireInfo hire in playerHires) { if (hire.playerID == playerID && hire.hireID == hireID) { foundHire = true; break; } } if (!foundHire) { hireInfo newHire = new hireInfo(); newHire.playerID = playerID; newHire.hireID = hireID; newHire.name = name; newHire.className = className; newHire.spawnPosition = spawnPosition; newHire.spawnRotation = spawnRotation; newHire.reSpawnPosition = reSpawnPosition; newHire.reSpawnRotation = reSpawnRotation; newHire.numMine = numKills; newHire.numKills = numMine; newHire.order = order; newHire.playerSpawned = playerSpawned; playerHires.Add(newHire); EntityAlive entity = GameManager.Instance.World.GetEntity(hireID) as EntityAlive; if (entity != null) { entity.Buffs.SetCustomVar("$Leader", playerID); } } if (SingletonMonoBehaviour.Instance.IsServer) { SaveCurrent(); if (RebirthUtilities.SendToClient(playerID)) { SingletonMonoBehaviour.Instance.SendPackage(NetPackageManager.GetPackage().Setup(playerID, hireID, name, className, spawnPosition, spawnRotation, reSpawnPosition, reSpawnRotation, numKills, numMine, order, playerSpawned ), false, playerID, -1, -1, null, 192); //Log.Out("HiresManagerRebirth-AddHire SENT TO CLIENT"); } } else { SingletonMonoBehaviour.Instance.SendToServer(NetPackageManager.GetPackage().Setup(playerID, hireID, name, className, spawnPosition, spawnRotation, reSpawnPosition, reSpawnRotation, numKills, numMine, order, playerSpawned ), false); //Log.Out("HiresManagerRebirth-AddHire SENT TO SERVER"); } //Log.Out("HiresManagerRebirth-AddHire Added Hire: " + hireID); } public static void UpdateHireInfo(int hiredID, string action, string value, string position = "", string rotation = "", int newhiredID = -1) { //Log.Out("HiresManagerRebirth-UpdateHireInfo START"); //Log.Out("HiresManagerRebirth-UpdateHireInfo hireID: " + hiredID); //Log.Out("HiresManagerRebirth-UpdateHireInfo action: " + action); //Log.Out("HiresManagerRebirth-UpdateHireInfo value: " + value); //Log.Out("HiresManagerRebirth-UpdateHireInfo position: " + position); //Log.Out("HiresManagerRebirth-UpdateHireInfo rotation: " + rotation); //Log.Out("HiresManagerRebirth-UpdateHireInfo newhiredID: " + newhiredID); foreach (hireInfo hire in playerHires) { if (hire.hireID == hiredID || hire.hireID == newhiredID) { //Log.Out("HiresManagerRebirth-UpdateHireInfo FOUND HIRE"); bool changed = false; bool addObserver = false; bool removeObserver = false; if (action == "newid") { changed = true; } else if (action == "order") { //Log.Out("HiresManagerRebirth-UpdateHireInfo order value: " + value); if (value == "follow") { hire.order = 0; changed = true; removeObserver = true; } else if (value == "stay") { hire.order = 1; hire.spawnPosition = StringParsers.ParseVector3(position); hire.spawnRotation = StringParsers.ParseVector3(rotation); changed = true; addObserver = true; } else if (value == "guard") { hire.order = 2; hire.spawnPosition = StringParsers.ParseVector3(position); hire.spawnRotation = StringParsers.ParseVector3(rotation); changed = true; addObserver = true; } } else if (action == "reSpawnPosition") { //Log.Out("HiresManagerRebirth-UpdateHireInfo reSpawnPosition: " + position); //Log.Out("HiresManagerRebirth-UpdateHireInfo reSpawnRotation: " + rotation); hire.reSpawnPosition = StringParsers.ParseVector3(position); hire.reSpawnRotation = StringParsers.ParseVector3(rotation); hire.spawnPosition = StringParsers.ParseVector3(position); hire.spawnRotation = StringParsers.ParseVector3(rotation); changed = true; } if (changed) { //Log.Out("HiresManagerRebirth-UpdateHireInfo CHANGE HIRE INFO"); if (SingletonMonoBehaviour.Instance.IsServer) { SaveCurrent(); bool sendToClient = RebirthUtilities.SendToClient(hire.playerID); //Log.Out("HiresManagerRebirth-UpdateHireInfo sendToClient: " + sendToClient); if (sendToClient) { //Log.Out("HiresManagerRebirth-UpdateHireInfo current ID: " + hiredID); //Log.Out("HiresManagerRebirth-UpdateHireInfo new ID: " + newhiredID); SingletonMonoBehaviour.Instance.SendPackage(NetPackageManager.GetPackage().Setup(hire.playerID, hiredID, hire.name, hire.spawnPosition, hire.spawnRotation, hire.reSpawnPosition, hire.reSpawnRotation, hire.numKills, hire.numMine, hire.order, hire.playerSpawned, action, value, newhiredID ), false, hire.playerID, -1, -1, null, 192); //Log.Out("HiresManagerRebirth-UpdateHireInfo SENT TO CLIENT"); } } else { SingletonMonoBehaviour.Instance.SendToServer(NetPackageManager.GetPackage().Setup(hire.playerID, hiredID, hire.name, hire.spawnPosition, hire.spawnRotation, hire.reSpawnPosition, hire.reSpawnRotation, hire.numKills, hire.numMine, hire.order, hire.playerSpawned, action, value, newhiredID ), false); //Log.Out("HiresManagerRebirth-UpdateHireInfo SENT TO SERVER"); } } } } } public static bool CheckHires(int playerID, int hireID) { EntityPlayer player = GameManager.Instance.World.GetEntity(playerID) as EntityPlayer; if (player == null) { return true; } if (!player.IsSpawned()) { return true; } Chunk chunkPlayer = (Chunk)GameManager.Instance.World.GetChunkFromWorldPos((int)player.position.x, (int)player.position.z); //Log.Out("HiresManagerRebirth-CheckHires START"); foreach (hireInfo hire in playerHires) { if (hire.playerID == playerID && hire.hireID == hireID && hire.playerSpawned) { if (SingletonMonoBehaviour.Instance.IsServer) { bool addObserver = false; //Log.Out("HiresManagerRebirth-CheckHires playerID: " + playerID + " / hireID: " + hireID);*/ Vector3 position = player.position; Vector3 rotation = player.rotation; bool setPosition = false; if (hire.order == 1 || hire.order == 2 && hire.spawnPosition != new Vector3(0, 0, 0)) { position = hire.spawnPosition; rotation = hire.spawnRotation; setPosition = true; //Log.Out("HiresManagerRebirth-CheckHires SPAWN WHERE THEY LAST STAYED: " + position); } if (hire.reSpawnPosition != new Vector3(0, 0, 0)) { position = hire.reSpawnPosition; rotation = hire.reSpawnRotation; hire.order = 1; setPosition = true; //Log.Out("HiresManagerRebirth-CheckHires SPAWNING AT REGROUP POINT: " + position); } if (!setPosition) { SpawnPosition spawnPoint = RebirthUtilities.GetSpawnPoint(player); if (!spawnPoint.IsUndef() && spawnPoint.position != new Vector3(0, 0, 0)) { position = spawnPoint.position; rotation = player.rotation; hire.order = 1; setPosition = true; //Log.Out("HiresManagerRebirth-CheckHires SPAWNING AT BEDROLL: " + position); } else { //Log.Out("HiresManagerRebirth-CheckHires SPAWNING AT PLAYER LOCATION: " + position); } } Chunk chunkHire = (Chunk)GameManager.Instance.World.GetChunkFromWorldPos((int)position.x, (int)position.z); if (chunkHire != null) { //Log.Out("HiresManagerRebirth-CheckHires chunkHire pos: " + chunkHire.ChunkPos); //Log.Out("HiresManagerRebirth-CheckHires chunkPlayer pos: " + chunkPlayer.ChunkPos); } if (chunkHire != null) { Entity entity = GameManager.Instance.World.GetEntity(hire.hireID) as Entity; if (entity == null) { bool skipEntity = true; // false; if (!skipEntity) { ////Log.Out("HiresManagerRebirth-CheckHires Couldn't find owned entity in the world"); //Log.Out("HiresManagerRebirth-CheckHires Created Missing Hire: " + hireID + " / " + hire.className + " / " + hire.name); EntityNPCRebirth NewEntity = EntityFactory.CreateEntity(EntityClass.FromString(hire.className), position, rotation) as EntityNPCRebirth; NewEntity.SetSpawnerSource(EnumSpawnerSource.StaticSpawner); NewEntity._strMyName = hire.name; RebirthUtilities.SetLeaderAndOwner(NewEntity.entityId, player.entityId); NewEntity.IsEntityUpdatedInUnloadedChunk = true; NewEntity.bWillRespawn = true; NewEntity.bIsChunkObserver = true; NewEntity.belongsPlayerId = playerID; NewEntity.guardPosition = position; if (hire.order == (int)EntityUtilities.Orders.None) { //Log.Out("HiresManagerRebirth-Update SET TO FOLLOW B"); NewEntity.Buffs.SetCustomVar("CurrentOrder", (int)EntityUtilities.Orders.Follow); } else if (hire.order == (int)EntityUtilities.Orders.Follow) { //Log.Out("HiresManagerRebirth-Update SET TO STAY B"); NewEntity.Buffs.SetCustomVar("CurrentOrder", (int)EntityUtilities.Orders.Stay); addObserver = true; } else { //Log.Out("HiresManagerRebirth-Update SET TO STAY (GUARD) B"); NewEntity.Buffs.SetCustomVar("CurrentOrder", (int)EntityUtilities.Orders.Stay); addObserver = true; } GameManager.Instance.World.SpawnEntityInWorld(NewEntity); hire.hireID = NewEntity.entityId; RebirthUtilities.SetLeaderAndOwner(NewEntity.entityId, player.entityId); bool foundObserver = false; for (int i = 0; i < observers.Count; i++) { if (observers[i].entityID == hireID) { //Log.Out("HiresManagerRebirth-CheckHires UPDATED OBSERVER, hire: " + hireID); observers[i].entityID = NewEntity.entityId; foundObserver = true; break; } } float flMode = player.Buffs.GetCustomVar("varNPCModMode"); float flHalt = player.Buffs.GetCustomVar("varNPCModStopAttacking"); if (flMode == 0) { NewEntity.Buffs.AddBuff("buffNPCModFullControlMode"); } else { NewEntity.Buffs.RemoveBuff("buffNPCModFullControlMode"); } if (flHalt == 1) { NewEntity.Buffs.AddBuff("buffNPCModStopAttacking"); } else { NewEntity.Buffs.RemoveBuff("buffNPCModStopAttacking"); } if (addObserver && !foundObserver) { //Log.Out("HiresManagerRebirth-CheckHires ADDED CHUNK OBSERVER, hire: " + hireID); ChunkManager.ChunkObserver observerRef = GameManager.Instance.AddChunkObserver(position, false, 3, -1); observers.Add(new chunkObservers(NewEntity.entityId, observerRef)); } return true; } } } else { //Log.Out("HiresManagerRebirth-CheckHires CAN'T LOAD HIRE CHUNK: " + position); return true; } } } } return false; } public static void Write(BinaryWriter _bw) { //Log.Out("HiresManagerRebirth-Write playerHires.Count: " + playerHires.Count); foreach (hireInfo hire in playerHires) { //Log.Out("HiresManagerRebirth-Write hire.playerID: " + hire.playerID); //Log.Out("HiresManagerRebirth-Write hire.hireID: " + hire.hireID); //Log.Out("HiresManagerRebirth-Write hire.name: " + hire.name); _bw.Write(hire.playerID.ToString()); _bw.Write(hire.hireID.ToString()); _bw.Write(hire.name); _bw.Write(hire.className); _bw.Write(hire.spawnPosition.ToString()); _bw.Write(hire.spawnRotation.ToString()); _bw.Write(hire.reSpawnPosition.ToString()); _bw.Write(hire.reSpawnRotation.ToString()); _bw.Write(hire.numKills.ToString()); _bw.Write(hire.numMine.ToString()); _bw.Write(hire.order.ToString()); _bw.Write(hire.playerSpawned); } } public static void Read(BinaryReader _br) { //Log.Out("HiresManagerRebirth-Read START"); while (_br.BaseStream.Position != _br.BaseStream.Length) { hireInfo hire = new hireInfo(); hire.playerID = int.Parse(_br.ReadString()); hire.hireID = int.Parse(_br.ReadString()); hire.name = _br.ReadString(); hire.className = _br.ReadString(); hire.spawnPosition = StringParsers.ParseVector3(_br.ReadString()); hire.spawnRotation = StringParsers.ParseVector3(_br.ReadString()); hire.reSpawnPosition = StringParsers.ParseVector3(_br.ReadString()); hire.reSpawnRotation = StringParsers.ParseVector3(_br.ReadString()); hire.numKills = int.Parse(_br.ReadString()); hire.numMine = int.Parse(_br.ReadString()); hire.order = int.Parse(_br.ReadString()); hire.playerSpawned = _br.ReadBoolean(); playerHires.Add(hire); //Log.Out("NetPackageGetHiresRebirth-Read Added playerID: " + hire.playerID); //Log.Out("NetPackageGetHiresRebirth-Read Added hire: " + hire.hireID); //Log.Out("NetPackageGetHiresRebirth-Read Added name: " + hire.name); //Log.Out("NetPackageGetHiresRebirth-Read hire.order: " + hire.order); ////Log.Out("NetPackageGetHiresRebirth-Read GameManager.IsDedicatedServer: " + GameManager.IsDedicatedServer); } } private static int saveDataThreaded(ThreadManager.ThreadInfo _threadInfo) { //Log.Out("HiresManagerRebirth-saveDataThreaded START"); PooledExpandableMemoryStream pooledExpandableMemoryStream = (PooledExpandableMemoryStream)_threadInfo.parameter; string text = string.Format("{0}/{1}", GameIO.GetSaveGameDir(), saveFile); if (!Directory.Exists(GameIO.GetSaveGameDir())) { Directory.CreateDirectory(GameIO.GetSaveGameDir()); } if (File.Exists(text)) { File.Copy(text, string.Format("{0}/{1}", GameIO.GetSaveGameDir(), $"{saveFile}.bak"), true); } pooledExpandableMemoryStream.Position = 0L; StreamUtils.WriteStreamToFile(pooledExpandableMemoryStream, text); pooledExpandableMemoryStream.Dispose(); ////Log.Out($"Broadcast Manager {text} Saving: {Broadcastmap.Count}"); return -1; } public static void Save() { //Log.Out("HiresManagerRebirth-Save START"); if (dataSaveThreadInfo == null || !ThreadManager.ActiveThreads.ContainsKey("silent_HiresManagerDataSave")) { PooledExpandableMemoryStream pooledExpandableMemoryStream = MemoryPools.poolMemoryStream.AllocSync(true); using (PooledBinaryWriter pooledBinaryWriter = MemoryPools.poolBinaryWriter.AllocSync(false)) { pooledBinaryWriter.SetBaseStream(pooledExpandableMemoryStream); Write(pooledBinaryWriter); } dataSaveThreadInfo = ThreadManager.StartThread("silent_HiresManagerDataSave", null, new ThreadManager.ThreadFunctionLoopDelegate(saveDataThreaded), null, System.Threading.ThreadPriority.Normal, pooledExpandableMemoryStream, null, false); } } public static void Load() { //Log.Out("HiresManagerRebirth-Load START"); string path = string.Format("{0}/{1}", GameIO.GetSaveGameDir(), saveFile); if (Directory.Exists(GameIO.GetSaveGameDir()) && File.Exists(path)) { //Log.Out("HiresManagerRebirth-Load 1"); try { using (FileStream fileStream = File.OpenRead(path)) { using (PooledBinaryReader pooledBinaryReader = MemoryPools.poolBinaryReader.AllocSync(false)) { //Log.Out("HiresManagerRebirth-Load 2"); pooledBinaryReader.SetBaseStream(fileStream); Read(pooledBinaryReader); } } } catch (Exception) { path = string.Format("{0}/{1}", GameIO.GetSaveGameDir(), $"{saveFile}.bak"); if (File.Exists(path)) { //Log.Out("HiresManagerRebirth-Load 3"); using (FileStream fileStream2 = File.OpenRead(path)) { using (PooledBinaryReader pooledBinaryReader2 = MemoryPools.poolBinaryReader.AllocSync(false)) { //Log.Out("HiresManagerRebirth-Load 4"); pooledBinaryReader2.SetBaseStream(fileStream2); Read(pooledBinaryReader2); } } } } } } private static void WaitOnSave() { if (dataSaveThreadInfo != null) { dataSaveThreadInfo.WaitForEnd(); dataSaveThreadInfo = null; } } public static void Cleanup() { if (instance != null) { SaveAndClear(); } } public static void SaveCurrent() { //Log.Out("HiresManagerRebirth-SaveCurrent SAVED CURRENT"); WaitOnSave(); Save(); WaitOnSave(); } private static void SaveAndClear() { WaitOnSave(); Save(); WaitOnSave(); playerHires.Clear(); observers.Clear(); instance = null; //Log.Out("Hires Manager stopped"); } }