public static void Postfix(Pawn_PathFollower __instance) { if (!QuickFast.Settings.HatsIndoors) { return; } if (!UnityData.IsInMainThread) { return; } if (__instance.pawn.AnimalOrWildMan()) { return; } if (__instance.pawn.Drafted) { // return; } var UsesOutdoorTemperature = __instance.nextCell.UsesOutdoorTemperature(__instance.pawn.Map); if (!UsesOutdoorTemperature) { __instance.pawn.Drawer.renderer.graphics.apparelGraphics.RemoveAll(x => x.sourceApparel.def.apparel.LastLayer == ApparelLayerDefOf.Overhead); } if (UsesOutdoorTemperature) { __instance.pawn?.Drawer?.renderer?.graphics?.ResolveApparelGraphics(); } }
static void Postfix(Pawn_PathFollower __instance, Pawn ___pawn) { bool enablePathing = LoadedModManager.GetMod <RimCheats>().GetSettings <RimCheatsSettings>().enablePathing; if (___pawn.IsColonistPlayerControlled && __instance.Moving && enablePathing) { if (___pawn.CurJob != null && (___pawn.CurJob.def == JobDefOf.GotoWander || ___pawn.CurJob.def == JobDefOf.Wait_Wander)) { return; } if (__instance.nextCellCostLeft > 0f) { __instance.nextCellCostLeft = 0; } if (!___pawn.Position.Equals(lastPos)) { lastPos = ___pawn.Position; __instance.PatherTick(); } else { lastPos = ___pawn.Position; } } }
public override void CompTick() { base.CompTick(); if (pawn != null && pawnPather == null) { pawnPather = pawn.pather; } int currentTick = Find.TickManager.TicksGame; if (parent != null && parent.Spawned && pawn != null && pawnPather != null && pawnPather.Moving) { lastMovementTick = currentTick; } // Update at every position change and then after every 1/2 second from last position change. if (lastPosition != iv3Invalid && lastPosition != parent.Position) { lastPositionUpdateTick = currentTick; updateFoV(); } else if ((currentTick - lastPositionUpdateTick) % 30 == 0) { updateFoV(); } }
//public static Dictionary<Map, DebugPathFinder> debugPathers = new Dictionary<Map, DebugPathFinder>(); //public static bool FindPath(PathFinder __instance, IntVec3 start, LocalTargetInfo dest, TraverseParms traverseParms, PathEndMode peMode, ref PawnPath __result) //{ // Map map = (Map)AccessTools.Field(type: typeof(PathFinder), name: "map").GetValue(__instance); // //if (traverseParms != null && traverseParms.pawn is Pawn p && p.AnimalOrWildMan() && p.playerSettings != null) // //{ // if (debugPathers.Count == 0 || !debugPathers.ContainsKey(map)) // { // debugPathers.Add(map, new DebugPathFinder(map)); // } // __result = debugPathers[map].FindPath(start, dest, traverseParms, peMode); // return false; // //} // //return true; //} public static void CostToMoveIntoCell_PostFix_ChangeDoorPathCost(Pawn_PathFollower __instance, Pawn pawn, IntVec3 c, ref int __result) { //Edge cases var curMap = pawn.MapHeld; if (curMap == null) { return; } if (pawn == null || pawn.Faction != Faction.OfPlayerSilentFail) { return; } var curMapGridForDoors = curMap.GetComponent <MapGrid_DoorsExpanded>(); if (curMapGridForDoors == null) { return; } //Method if (curMapGridForDoors.HasDoorAtLocation(c)) { int adjustedPathCost = (int)(__result * 0.5f); //Log.Message($"DoorsExpanded: Newcost: {adjustedPathCost} - Oldcost: {__result}"); __result = Mathf.Max(adjustedPathCost, 1); } }
public static void PathOfNature(Pawn_PathFollower __instance, Pawn pawn, IntVec3 c, ref int __result) { if (pawn.def == YautjaDefOf.RRY_Alien_Yautja || pawn?.GetComp <Comp_Xenomorph>() is Comp_Xenomorph comp_Xenomorph) { int num; if (c.x == pawn.Position.x || c.z == pawn.Position.z) { num = pawn.TicksPerMoveCardinal; } else { num = pawn.TicksPerMoveDiagonal; } Building edifice = c.GetEdifice(pawn.Map); if (edifice != null) { num += (int)edifice.PathWalkCostFor(pawn); } if (num > 450) { num = 450; } if (pawn.jobs.curJob != null) { switch (pawn.jobs.curJob.locomotionUrgency) { case LocomotionUrgency.Amble: num *= 3; if (num < 60) { num = 60; } break; case LocomotionUrgency.Walk: num *= 2; if (num < 50) { num = 50; } break; case LocomotionUrgency.Jog: num *= 1; break; case LocomotionUrgency.Sprint: num = Mathf.RoundToInt((float)num * 0.75f); break; } } __result = Mathf.Max(num, 1); } }
public static void Postfix(Pawn_PathFollower __instance, Pawn ___pawn) { if ((___pawn.Map != null) && (__instance.MovingNow) && ___pawn.equipment?.Primary != null) { ___pawn.equipment.Primary.BroadcastCompSignal("Moving"); } }
public static void SetupMoveIntoNextCell(ref Pawn_PathFollower instance, Pawn pawn, LocalTargetInfo destination) { if (instance.curPath.NodesLeftCount <= 1) { Log.Error(string.Concat(new object[] { pawn, " at ", pawn.Position, " ran out of path nodes while pathing to ", destination, "." }), false); PatherFailedHelper(ref instance, pawn); return; } instance.nextCell = instance.curPath.ConsumeNextNode(); if (!GenGridShips.Walkable(instance.nextCell, MapExtensionUtility.GetExtensionToMap(pawn.Map))) { Log.Error(string.Concat(new object[] { pawn, " entering ", instance.nextCell, " which is unwalkable." }), false); } int num = CostToMoveIntoCellShips(pawn, instance.nextCell); instance.nextCellCostTotal = (float)num; instance.nextCellCostLeft = (float)num; //Doors? }
public void CheckMovement() { if (HarmonyPatchesFS.AnimatorIsOpen() && MainTabWindow_BaseAnimator.Pawn == this.Pawn) { this._isMoving = true; this._movedPercent = MainTabWindow_BaseAnimator.AnimationPercent; return; } if (this.IsRider) { this._isMoving = false; return; } // pawn started pathing Pawn_PathFollower pather = this.Pawn.pather; if ((pather != null) && (pather.Moving) && !this.Pawn.stances.FullBodyBusy && (pather.BuildingBlockingNextPathCell() == null) && (pather.NextCellDoorToWaitForOrManuallyOpen() == null) && !pather.WillCollideWithPawnOnNextPathCell()) { this._movedPercent = 1f - pather.nextCellCostLeft / pather.nextCellCostTotal; this._isMoving = true; } else { this._isMoving = false; } }
public static bool CostToMoveIntoCell(ref int __result, Pawn pawn, IntVec3 c) { int a = (c.x == pawn.Position.x || c.z == pawn.Position.z ? pawn.TicksPerMoveCardinal : pawn.TicksPerMoveDiagonal) + pawn.Map.pathing.For(pawn).pathGrid.CalculatedCostAt(c, false, pawn.Position); Building edifice = c.GetEdifice(pawn.Map); if (edifice != null) { a += (int)edifice.PathWalkCostFor(pawn); } if (a > 450) { a = 450; } if (pawn.CurJob != null) { Pawn locomotionUrgencySameAs = pawn?.jobs?.curDriver?.locomotionUrgencySameAs; //changed if (locomotionUrgencySameAs != null && locomotionUrgencySameAs != pawn && locomotionUrgencySameAs.Spawned) { int moveIntoCell = Pawn_PathFollower.CostToMoveIntoCell(locomotionUrgencySameAs, c); if (a < moveIntoCell) { a = moveIntoCell; } } else { switch (pawn.jobs.curJob.locomotionUrgency) { case LocomotionUrgency.Amble: a *= 3; if (a < 60) { a = 60; break; } break; case LocomotionUrgency.Walk: a *= 2; if (a < 50) { a = 50; break; } break; case LocomotionUrgency.Jog: //a = a; //commented out break; case LocomotionUrgency.Sprint: a = Mathf.RoundToInt((float)a * 0.75f); break; } } } __result = Mathf.Max(a, 1); return(false); }
public static void PatherArrivedHelper(Pawn_PathFollower instance, Pawn pawn) { instance.StopDead(); if (!(pawn.jobs.curJob is null)) { pawn.jobs.curDriver.Notify_PatherArrived(); } }
private void Init() { pather = new Pawn_PathFollower(this); stances = new Pawn_StanceTracker(this); health = new Pawn_HealthTracker(this); jobs = new Pawn_JobTracker(this); filth = new Pawn_FilthTracker(this); }
// Verse.AI.Pawn_PathFollower public static void PathOfNature(Pawn_PathFollower __instance, ref int __result, IntVec3 c) { Pawn pawn = Traverse.Create(__instance).Field("pawn").GetValue <Pawn>(); if (pawn?.GetComp <CompHulk>() is CompHulk compHulk && compHulk?.CurrentHulkForm?.def == WWDefOf.Hulk) { int num; if (c.x == pawn.Position.x || c.z == pawn.Position.z) { num = pawn.TicksPerMoveCardinal; } else { num = pawn.TicksPerMoveDiagonal; } //num += pawn.Map.pathGrid.CalculatedCostAt(c, false, pawn.Position); Building edifice = c.GetEdifice(pawn.Map); if (edifice != null) { num += (int)edifice.PathWalkCostFor(pawn); } if (num > 450) { num = 450; } if (pawn.jobs.curJob != null) { switch (pawn.jobs.curJob.locomotionUrgency) { case LocomotionUrgency.Amble: num *= 3; if (num < 60) { num = 60; } break; case LocomotionUrgency.Walk: num *= 2; if (num < 50) { num = 50; } break; case LocomotionUrgency.Jog: num *= 1; break; case LocomotionUrgency.Sprint: num = Mathf.RoundToInt((float)num * 0.75f); break; } } __result = Mathf.Max(num, 1); } }
/// <summary> /// Determine if next cell is walkable with final determination if vehicle is in cell or not /// </summary> /// <param name="__result"></param> /// <param name="___pawn"></param> /// <param name="nextCell"></param> public static void IsVehicleInNextCell(ref bool __result, Pawn ___pawn, Pawn_PathFollower __instance) { if (!__result) { //Peek 2 nodes ahead to avoid collision last second __result = (__instance.curPath.NodesLeftCount > 1 && PathingHelper.VehicleInCell(___pawn.Map, __instance.curPath.Peek(1))) || (__instance.curPath.NodesLeftCount > 2 && PathingHelper.VehicleInCell(___pawn.Map, __instance.curPath.Peek(2))); } }
public static void SetupMoveIntoNextCell_Postfix(Pawn_PathFollower __instance, Pawn ___pawn) { Building_DoorMat building_DoorMat = ___pawn.Map.thingGrid.ThingAt <Building_DoorMat>(__instance.nextCell); if (building_DoorMat != null) { building_DoorMat.Notify_PawnApproaching(___pawn); } }
static void Postfix(Pawn_PathFollower __instance, Pawn pawn, IntVec3 c, ref int __result) { bool appliesToPawn = false; if (settings.disableTerrainCost) { appliesToPawn = pawn.IsColonistPlayerControlled; } if (settings.disableTerrainCostNonHuman && !pawn.IsColonistPlayerControlled) { appliesToPawn = pawn.Faction != null && pawn.Faction.IsPlayer; } if (appliesToPawn) { // based off floating pawn code from Alpha Animals int cost = __result; if (cost < 10000) { if (c.x == pawn.Position.x || c.z == pawn.Position.z) { cost = pawn.TicksPerMoveCardinal; } else { cost = pawn.TicksPerMoveDiagonal; } TerrainDef terrainDef = pawn.Map.terrainGrid.TerrainAt(c); if (terrainDef == null) { cost = 10000; } else if (terrainDef.passability == Traversability.Impassable && !terrainDef.IsWater) { cost = 10000; } //else if (terrainDef.IsWater) //{ // cost = 10000; //} List <Thing> list = pawn.Map.thingGrid.ThingsListAt(c); for (int i = 0; i < list.Count; i++) { Thing thing = list[i]; if (thing.def.passability == Traversability.Impassable) { cost = 10000; } //if (thing is Building_Door) //{ // cost += 45; //} } __result = cost; } } }
public static void CostToMoveIntoCell_Postfix(ref int __result, Pawn_PathFollower __instance, Pawn ___pawn, Pawn pawn, IntVec3 c) { if (DoorMatsSettings.slowdown > 0) { Building_DoorMat building_DoorMat = ___pawn.Map.thingGrid.ThingAt <Building_DoorMat>(c); if (building_DoorMat != null) { __result += DoorMatsSettings.slowdown; } } }
public static void Postfix(Pawn_PathFollower __instance) { var pawn = __instance.pawn; if (pawn == curPawn) { __instance.nextCellCostLeft -= remaining; __instance.nextCellCostTotal -= remaining; curPawn = null; } }
private IntVec3 GetLastCell(Pawn_PathFollower _this) { if (_lastCell == null) { _lastCell = typeof(Pawn_PathFollower).GetField("lastCell", BindingFlags.Instance | BindingFlags.NonPublic); if (_lastCell == null) { Log.ErrorOnce("Unable to reflect Pawn_PathFollower.lastCell!", 0x12348765); } } return((IntVec3)_lastCell.GetValue(_this)); }
public static bool get_WillCloseSoon(Building_Door __instance, ref bool __result) { if (!__instance.Spawned) { __result = true; return(false); } if (!openInt(__instance)) { __result = true; return(false); } if (holdOpenInt(__instance)) { __result = false; return(false); } if (ticksUntilClose(__instance) > 0 && ticksUntilClose(__instance) <= 111 && !__instance.BlockedOpenMomentary) { __result = true; return(false); } if ((bool)canTryCloseAutomatically.GetValue(__instance, null) && !__instance.BlockedOpenMomentary) { __result = true; return(false); } for (int i = 0; i < 5; i++) { IntVec3 position = (__instance).Position; IntVec3 c = position + GenAdj.CardinalDirectionsAndInside[i]; Map map = (__instance).Map; if (c.InBounds(map)) { List <Thing> thingList = c.GetThingList(map); for (int j = 0; j < thingList.Count; j++) { if (thingList[j] is Pawn pawn) { Pawn_PathFollower pather1 = pawn.pather; if (null != pather1) { if (pawn != null && !pawn.HostileTo(__instance) && !pawn.Downed && (pawn.Position == position || (pather1.Moving && pather1.nextCell == position))) { return(true); } } } } } } return(false); }
public static bool GetPawnsStandingAtOrAboutToStandAt( IntVec3 at, Map map, out int pawnsCount, out int pawnsWithLowerIdCount, out bool forPawnFound, Pawn forPawn) { pawnsCount = 0; pawnsWithLowerIdCount = 0; forPawnFound = false; foreach (IntVec3 c in CellRect.SingleCell(at).ExpandedBy(1)) { if (c.InBounds(map)) { List <Thing> thingList = c.GetThingList(map); for (int index = 0; index < thingList.Count; ++index) { if (thingList[index] is Pawn p && p.GetPosture() == PawnPosture.Standing) { Pawn_PathFollower path = p.pather; if (null != path) { if (c != at) { if (!path.MovingNow || path.nextCell != path.Destination.Cell || path.Destination.Cell != at) { continue; } } else if (path.MovingNow) { continue; } } if (p == forPawn) { forPawnFound = true; } ++pawnsCount; if (p.thingIDNumber < forPawn.thingIDNumber) { ++pawnsWithLowerIdCount; } } } } } return(false); }
static bool Prefix(ref Pawn_PathFollower __instance, LocalTargetInfo dest, PathEndMode peMode, Pawn ___pawn) { if (___pawn.Map?.Parent is City) { dest = (LocalTargetInfo)GenPath.ResolvePathMode(___pawn, dest.ToTargetInfo(___pawn.Map), ref peMode); if (dest.HasThing && dest.ThingDestroyed) { Log.Warning(___pawn + " pathing to destroyed thing " + dest.Thing); // ReSharper disable once PossibleNullReferenceException typeof(Pawn_PathFollower).GetMethod("PatherFailed", BindingFlags.NonPublic).Invoke(__instance, new object[] { }); return(false); } } return(true); }
static void Postfix(Pawn_PathFollower __instance, Pawn pawn, IntVec3 c, ref int __result) { bool disableTerrainCost = LoadedModManager.GetMod <RimCheats>().GetSettings <RimCheatsSettings>().disableTerrainCost; if (pawn.IsColonistPlayerControlled && disableTerrainCost) { // based off floating pawn code from Alpha Animals int cost = __result; if (cost < 10000) { if (c.x == pawn.Position.x || c.z == pawn.Position.z) { cost = pawn.TicksPerMoveCardinal; } else { cost = pawn.TicksPerMoveDiagonal; } TerrainDef terrainDef = pawn.Map.terrainGrid.TerrainAt(c); if (terrainDef == null) { cost = 10000; } else if (terrainDef.passability == Traversability.Impassable && !terrainDef.IsWater) { cost = 10000; } //else if (terrainDef.IsWater) //{ // cost = 10000; //} List <Thing> list = pawn.Map.thingGrid.ThingsListAt(c); for (int i = 0; i < list.Count; i++) { Thing thing = list[i]; if (thing.def.passability == Traversability.Impassable) { cost = 10000; } //if (thing is Building_Door) //{ // cost += 45; //} } __result = cost; } } }
public static void Postfix(Pawn_PathFollower __instance, ref float __result) { var traverse = Traverse.Create(__instance); var pawn = traverse.Field("pawn").GetValue <Pawn>(); if (!pawn.IsWarframe()) { return; } if (__result < 1f) { __result = 1f; } }
// Verse.AI.Pawn_PathFollower public static bool StartPath_PreFix(Pawn_PathFollower __instance, LocalTargetInfo dest, PathEndMode peMode) { Pawn pawn = (Pawn)AccessTools.Field(typeof(Pawn_PathFollower), "pawn").GetValue(__instance); if (pawn != null) { CompVehicle compPilotable = pawn.GetComp <CompVehicle>(); if (compPilotable != null) { if (compPilotable.movingStatus == MovingState.frozen) { return(false); } } } return(true); }
public static void SetupMoveIntoNextCell_Postfix(Pawn_PathFollower __instance, Pawn ___pawn) { if (___pawn != null) { TerrainDef lava = ___pawn.Map.terrainGrid.TerrainAt(__instance.nextCell); if (lava.defName == "AB_SolidifiedLava") { if (___pawn.CanEverAttachFire()) { if (!___pawn.HasAttachment(ThingDefOf.Fire)) { TryAttachFire(___pawn, 1f); } } } } }
public static bool Prefix(Pawn_PathFollower __instance) { Pawn pawn = Traverse.Create(__instance).Field("pawn").GetValue <Pawn>(); if (pawn.RaceProps.Animal) { TerrainDef terrain = pawn.Position.GetTerrain(pawn.Map); if (terrain.HasTag("TKKN_Swim") || terrain.HasTag("TKKN_Lava")) { if (!PatchStartPath.PawnCanOccupy(pawn.Position, pawn) && !PatchStartPath.TryRecoverFromUnwalkablePosition(true, pawn)) { return(false); } } } return(true); }
public override void CompTick() { #if InternalProfile ProfilingUtils.startProfiling("CompFieldOfViewWatcher.tick"); #endif if (disabled) { return; } int currentTick = Find.TickManager.TicksGame; if (pawn != null) { // Update at every position change and then after every 1/2 second from last position change. if (pawnPather == null) { pawnPather = pawn.pather; } if (pawnPather != null && pawnPather.Moving) { lastMovementTick = currentTick; } if (lastPosition != iv3Invalid && lastPosition != parent.Position) { lastPositionUpdateTick = currentTick; updateFoV(); } else if ((currentTick - lastPositionUpdateTick) % 30 == 0) { updateFoV(); } // Non pawns update at most every 30 ticks or when position change. } else if ((lastPosition != iv3Invalid && lastPosition != parent.Position) || currentTick % 30 == 0) { updateFoV(); } #if InternalProfile ProfilingUtils.stopProfiling("CompFieldOfViewWatcher.tick"); #endif }
public static void PatherTick(Pawn_PathFollower __instance) { if (!InstantMoving) { return; } if (!WorkRebalancerMod.Instance.Prof.ShowInstantMovingIcon) { InstantMoving = false; return; } if (WorkRebalancerMod.Instance.Prof.RestoreWhenHostileDetected && HostileHandler.HostileDetected) { return; } if (WorkRebalancerMod.Instance.Prof.InstantMovingOnlyColonists && __instance.pawn.Faction != Faction.OfPlayer) { return; } if (__instance.destination.Cell == IntVec3.Zero) { return; } // move in middle path points if (WorkRebalancerMod.Instance.Prof.InstantMovingSmoother) { __instance.pawn.Position = __instance.nextCell; } // move in end point else { __instance.pawn.Position = __instance.destination.Cell; if (CellFinder.TryFindBestPawnStandCell(__instance.pawn, out IntVec3 intVec, true) && intVec != __instance.pawn.Position) { __instance.pawn.Position = intVec; } } __instance.ResetToCurrentPosition(); }
public static void CostToMoveIntoCell_Postfix(ref int __result, Pawn_PathFollower __instance, Pawn pawn, IntVec3 c) { if (DoorMatsSettings.slowdown > 0 && pawn != null && (pawn.IsColonist || pawn.IsPrisonerOfColony)) { if (pawn.Drafted || pawn.health.hediffSet.BleedRateTotal > 0.01) { return; } if (pawn.CurJob != null && (pawn.CurJobDef == JobDefOf.Flee || pawn.CurJobDef == JobDefOf.FleeAndCower || pawn.CurJobDef == JobDefOf.TendPatient || pawn.CurJobDef.driverClass == typeof(JobDriver_TakeToBed))) { return; } Building_DoorMat building_DoorMat = pawn.Map.thingGrid.ThingAt <Building_DoorMat>(c); if (building_DoorMat != null) { __result += DoorMatsSettings.slowdown; } } }
public static bool CanGoDirectlyToNextCell(ref bool __result, Pawn pawn) { IntVec3 nextCell = pawn.pather.nextCell; foreach (IntVec3 c in CellRect.FromLimits(nextCell, pawn.Position).ExpandedBy(1)) { //if (c.InBounds(pawn.Map)) //{ //Thing[] thingList = c.GetThingList(pawn.Map).ToArray<Thing>(); //for (int i = 0; i < thingList.Length; i++) foreach (Thing thing in pawn.Map.thingGrid.ThingsAt(c)) { Pawn pawn2 = thing as Pawn; if (pawn2 != null && pawn2 != pawn && pawn2.GetPosture() == PawnPosture.Standing) { Pawn_PathFollower pather1 = pawn2.pather; if (null != pather1) { if (pawn2.pather.MovingNow) { if (((pawn2.Position == nextCell && (bool)willBeFasterOnNextCell.Invoke(null, new object[] { pawn, pawn2 })) || pawn2.pather.nextCell == nextCell || pawn2.Position == pawn.Position || (pawn2.pather.nextCell == pawn.Position && (bool)willBeFasterOnNextCell.Invoke(null, new object[] { pawn2, pawn }))) && pawn2.thingIDNumber < pawn.thingIDNumber) { __result = false; return(false); } } } else if (pawn2.Position == pawn.Position || pawn2.Position == nextCell) { __result = false; return(false); } } } //} } __result = true; return(false); }