public static float ApproxDaysUntilRot(List <ThingCount> potentiallyFood, int tile, WorldPath path = null, float nextTileCostLeft = 0f, int caravanTicksPerMove = 3300)
 {
     DaysUntilRotCalculator.tmpTicksToArrive.Clear();
     if (path != null && path.Found)
     {
         CaravanArrivalTimeEstimator.EstimatedTicksToArriveToEvery(tile, path.LastNode, path, nextTileCostLeft, caravanTicksPerMove, Find.TickManager.TicksAbs, DaysUntilRotCalculator.tmpTicksToArrive);
     }
     DaysUntilRotCalculator.tmpNutritions.Clear();
     for (int i = 0; i < potentiallyFood.Count; i++)
     {
         ThingCount thingCount = potentiallyFood[i];
         if (thingCount.Count > 0 && thingCount.Thing.def.IsNutritionGivingIngestible)
         {
             CompRottable compRottable = thingCount.Thing.TryGetComp <CompRottable>();
             float        first;
             if (compRottable != null && compRottable.Active)
             {
                 first = (float)DaysUntilRotCalculator.ApproxTicksUntilRot_AssumeTimePassesBy(compRottable, tile, DaysUntilRotCalculator.tmpTicksToArrive) / 60000f;
             }
             else
             {
                 first = 600f;
             }
             float second = thingCount.Thing.GetStatValue(StatDefOf.Nutrition, true) * (float)thingCount.Count;
             DaysUntilRotCalculator.tmpNutritions.Add(new Pair <float, float>(first, second));
         }
     }
     return(GenMath.WeightedMedian(DaysUntilRotCalculator.tmpNutritions, 600f, 0.5f));
 }
        public static int EstimatedTicksToArrive(Caravan caravan, bool allowCaching)
        {
            if (allowCaching && caravan == CaravanArrivalTimeEstimator.cachedForCaravan && caravan.pather.Destination == CaravanArrivalTimeEstimator.cachedForDest && Find.TickManager.TicksGame - CaravanArrivalTimeEstimator.cacheTicks < 100)
            {
                return(CaravanArrivalTimeEstimator.cachedResult);
            }
            int to;
            int result;

            if (!caravan.Spawned || !caravan.pather.Moving || caravan.pather.curPath == null)
            {
                to     = -1;
                result = 0;
            }
            else
            {
                to     = caravan.pather.Destination;
                result = CaravanArrivalTimeEstimator.EstimatedTicksToArrive(caravan.Tile, to, caravan.pather.curPath, caravan.pather.nextTileCostLeft, caravan.TicksPerMove, Find.TickManager.TicksAbs);
            }
            if (allowCaching)
            {
                CaravanArrivalTimeEstimator.cacheTicks       = Find.TickManager.TicksGame;
                CaravanArrivalTimeEstimator.cachedForCaravan = caravan;
                CaravanArrivalTimeEstimator.cachedForDest    = to;
                CaravanArrivalTimeEstimator.cachedResult     = result;
            }
            return(result);
        }
Ejemplo n.º 3
0
        private string GetTileTip(int tile, int pathIndex)
        {
            int           num           = paths[pathIndex].NodesReversed.IndexOf(tile);
            int           num2          = ((num > 0) ? paths[pathIndex].NodesReversed[num - 1] : ((pathIndex >= paths.Count - 1 || paths[pathIndex + 1].NodesReversed.Count < 2) ? (-1) : paths[pathIndex + 1].NodesReversed[paths[pathIndex + 1].NodesReversed.Count - 2]));
            int           num3          = cachedTicksToWaypoint[pathIndex] + CaravanArrivalTimeEstimator.EstimatedTicksToArrive(paths[pathIndex].FirstNode, tile, paths[pathIndex], 0f, CaravanTicksPerMove, GenTicks.TicksAbs + cachedTicksToWaypoint[pathIndex]);
            int           num4          = GenTicks.TicksAbs + num3;
            StringBuilder stringBuilder = new StringBuilder();

            if (num3 != 0)
            {
                stringBuilder.AppendLine("EstimatedTimeToTile".Translate(num3.ToStringTicksToDays("0.##")));
            }
            stringBuilder.AppendLine("ForagedFoodAmount".Translate() + ": " + Find.WorldGrid[tile].biome.forageability.ToStringPercent());
            stringBuilder.Append(VirtualPlantsUtility.GetVirtualPlantsStatusExplanationAt(tile, num4));
            if (num2 != -1)
            {
                stringBuilder.AppendLine();
                stringBuilder.AppendLine();
                StringBuilder stringBuilder2 = new StringBuilder();
                float         num5           = WorldPathGrid.CalculatedMovementDifficultyAt(num2, perceivedStatic: false, num4, stringBuilder2);
                float         roadMovementDifficultyMultiplier = Find.WorldGrid.GetRoadMovementDifficultyMultiplier(tile, num2, stringBuilder2);
                stringBuilder.Append("TileMovementDifficulty".Translate() + ":\n" + stringBuilder2.ToString().Indented("  "));
                stringBuilder.AppendLine();
                stringBuilder.Append("  = ");
                stringBuilder.Append((num5 * roadMovementDifficultyMultiplier).ToString("0.#"));
            }
            return(stringBuilder.ToString());
        }
Ejemplo n.º 4
0
        private void RecreatePaths()
        {
            ReleasePaths();
            WorldPathFinder worldPathFinder = Find.WorldPathFinder;

            for (int i = 1; i < waypoints.Count; i++)
            {
                paths.Add(worldPathFinder.FindPath(waypoints[i - 1].Tile, waypoints[i].Tile, null));
            }
            cachedTicksToWaypoint.Clear();
            int num = 0;
            int caravanTicksPerMove = CaravanTicksPerMove;

            for (int j = 0; j < waypoints.Count; j++)
            {
                if (j == 0)
                {
                    cachedTicksToWaypoint.Add(0);
                }
                else
                {
                    num += CaravanArrivalTimeEstimator.EstimatedTicksToArrive(waypoints[j - 1].Tile, waypoints[j].Tile, paths[j - 1], 0f, caravanTicksPerMove, GenTicks.TicksAbs + num);
                    cachedTicksToWaypoint.Add(num);
                }
            }
        }
 public static int EstimatedTicksToArrive(int from, int to, Caravan caravan)
 {
     using (WorldPath worldPath = Find.WorldPathFinder.FindPath(from, to, caravan, null))
     {
         if (worldPath == WorldPath.NotFound)
         {
             return(0);
         }
         return(CaravanArrivalTimeEstimator.EstimatedTicksToArrive(from, to, worldPath, 0f, CaravanTicksPerMoveUtility.GetTicksPerMove(caravan), Find.TickManager.TicksAbs));
     }
 }
        public static int EstimatedTicksToArrive(int from, int to, Caravan caravan)
        {
            int result;

            using (WorldPath worldPath = Find.WorldPathFinder.FindPath(from, to, caravan, null))
            {
                if (!worldPath.Found)
                {
                    result = 0;
                }
                else
                {
                    result = CaravanArrivalTimeEstimator.EstimatedTicksToArrive(from, to, worldPath, 0f, (caravan == null) ? 3300 : caravan.TicksPerMove, Find.TickManager.TicksAbs);
                }
            }
            return(result);
        }
Ejemplo n.º 7
0
        public override GizmoResult GizmoOnGUI(Vector2 topLeft, float maxWidth)
        {
            if (!caravan.Spawned)
            {
                return(new GizmoResult(GizmoState.Clear));
            }
            Rect rect = new Rect(topLeft.x, topLeft.y, GetWidth(maxWidth), 75f);

            Widgets.DrawWindowBackground(rect);
            GUI.BeginGroup(rect);
            Rect          rect2         = rect.AtZero();
            int?          ticksToArrive = (caravan.pather.Moving ? new int?(CaravanArrivalTimeEstimator.EstimatedTicksToArrive(caravan, allowCaching: true)) : null);
            StringBuilder stringBuilder = new StringBuilder();

            CaravanUIUtility.DrawCaravanInfo(new CaravanUIUtility.CaravanInfo(tilesPerDay: TilesPerDayCalculator.ApproxTilesPerDay(caravan, stringBuilder), massUsage: caravan.MassUsage, massCapacity: caravan.MassCapacity, massCapacityExplanation: caravan.MassCapacityExplanation, tilesPerDayExplanation: stringBuilder.ToString(), daysWorthOfFood: caravan.DaysWorthOfFood, foragedFoodPerDay: caravan.forage.ForagedFoodPerDay, foragedFoodPerDayExplanation: caravan.forage.ForagedFoodPerDayExplanation, visibility: caravan.Visibility, visibilityExplanation: caravan.VisibilityExplanation), null, caravan.Tile, ticksToArrive, -9999f, rect2, lerpMassColor: true, null, multiline: true);
            GUI.EndGroup();
            GenUI.AbsorbClicksInRect(rect);
            return(new GizmoResult(GizmoState.Clear));
        }
        public static int ApproxTicksUntilRot_AssumeTimePassesBy(CompRottable rot, int tile, List <Pair <int, int> > ticksToArrive = null)
        {
            float num  = 0f;
            int   num2 = Find.TickManager.TicksAbs;

            while (num < 1f && (float)num2 < (float)Find.TickManager.TicksAbs + 3.606E+07f)
            {
                int tile2 = (!ticksToArrive.NullOrEmpty <Pair <int, int> >()) ? CaravanArrivalTimeEstimator.TileIllBeInAt(num2, ticksToArrive, Find.TickManager.TicksAbs) : tile;
                int num3  = Mathf.FloorToInt((float)rot.ApproxTicksUntilRotWhenAtTempOfTile(tile2, num2) * (1f - num));
                if (num3 <= 0)
                {
                    break;
                }
                int num4 = Mathf.Min(num3, 26999);
                num  += (float)num4 / (float)num3;
                num2 += num4;
            }
            return(num2 - Find.TickManager.TicksAbs);
        }
Ejemplo n.º 9
0
        public override string GetInspectString()
        {
            StringBuilder stringBuilder = new StringBuilder();

            stringBuilder.Append(base.GetInspectString());
            if (stringBuilder.Length != 0)
            {
                stringBuilder.AppendLine();
            }
            int num  = 0;
            int num2 = 0;
            int num3 = 0;
            int num4 = 0;
            int num5 = 0;

            for (int i = 0; i < pawns.Count; i++)
            {
                if (pawns[i].IsColonist)
                {
                    num++;
                }
                else if (pawns[i].RaceProps.Animal)
                {
                    num2++;
                }
                else if (pawns[i].IsPrisoner)
                {
                    num3++;
                }
                if (pawns[i].Downed)
                {
                    num4++;
                }
                if (pawns[i].InMentalState)
                {
                    num5++;
                }
            }
            stringBuilder.Append("CaravanColonistsCount".Translate(num, (num != 1) ? Faction.OfPlayer.def.pawnsPlural : Faction.OfPlayer.def.pawnSingular));
            if (num2 == 1)
            {
                stringBuilder.Append(", " + "CaravanAnimal".Translate());
            }
            else if (num2 > 1)
            {
                stringBuilder.Append(", " + "CaravanAnimalsCount".Translate(num2));
            }
            if (num3 == 1)
            {
                stringBuilder.Append(", " + "CaravanPrisoner".Translate());
            }
            else if (num3 > 1)
            {
                stringBuilder.Append(", " + "CaravanPrisonersCount".Translate(num3));
            }
            stringBuilder.AppendLine();
            if (num5 > 0)
            {
                stringBuilder.Append("CaravanPawnsInMentalState".Translate(num5));
            }
            if (num4 > 0)
            {
                if (num5 > 0)
                {
                    stringBuilder.Append(", ");
                }
                stringBuilder.Append("CaravanPawnsDowned".Translate(num4));
            }
            if (num5 > 0 || num4 > 0)
            {
                stringBuilder.AppendLine();
            }
            if (pather.Moving)
            {
                if (pather.ArrivalAction != null)
                {
                    stringBuilder.Append(pather.ArrivalAction.ReportString);
                }
                else
                {
                    stringBuilder.Append("CaravanTraveling".Translate());
                }
            }
            else
            {
                SettlementBase settlementBase = CaravanVisitUtility.SettlementVisitedNow(this);
                if (settlementBase != null)
                {
                    stringBuilder.Append("CaravanVisiting".Translate(settlementBase.Label));
                }
                else
                {
                    stringBuilder.Append("CaravanWaiting".Translate());
                }
            }
            if (pather.Moving)
            {
                float num6 = (float)CaravanArrivalTimeEstimator.EstimatedTicksToArrive(this, allowCaching: true) / 60000f;
                stringBuilder.AppendLine();
                stringBuilder.Append("CaravanEstimatedTimeToDestination".Translate(num6.ToString("0.#")));
            }
            if (AllOwnersDowned)
            {
                stringBuilder.AppendLine();
                stringBuilder.Append("AllCaravanMembersDowned".Translate());
            }
            else if (AllOwnersHaveMentalBreak)
            {
                stringBuilder.AppendLine();
                stringBuilder.Append("AllCaravanMembersMentalBreak".Translate());
            }
            else if (ImmobilizedByMass)
            {
                stringBuilder.AppendLine();
                stringBuilder.Append("CaravanImmobilizedByMass".Translate());
            }
            if (needs.AnyPawnOutOfFood(out string malnutritionHediff))
            {
                stringBuilder.AppendLine();
                stringBuilder.Append("CaravanOutOfFood".Translate());
                if (!malnutritionHediff.NullOrEmpty())
                {
                    stringBuilder.Append(" ");
                    stringBuilder.Append(malnutritionHediff);
                    stringBuilder.Append(".");
                }
            }
            if (!pather.MovingNow)
            {
                int usedBedCount = beds.GetUsedBedCount();
                stringBuilder.AppendLine();
                stringBuilder.Append(CaravanBedUtility.AppendUsingBedsLabel("CaravanResting".Translate(), usedBedCount));
            }
            else
            {
                string inspectStringLine = carryTracker.GetInspectStringLine();
                if (!inspectStringLine.NullOrEmpty())
                {
                    stringBuilder.AppendLine();
                    stringBuilder.Append(inspectStringLine);
                }
                string inBedForMedicalReasonsInspectStringLine = beds.GetInBedForMedicalReasonsInspectStringLine();
                if (!inBedForMedicalReasonsInspectStringLine.NullOrEmpty())
                {
                    stringBuilder.AppendLine();
                    stringBuilder.Append(inBedForMedicalReasonsInspectStringLine);
                }
            }
            return(stringBuilder.ToString());
        }
Ejemplo n.º 10
0
        private static float ApproxDaysWorthOfFood(List <Pawn> pawns, List <ThingDefCount> extraFood, int tile, IgnorePawnsInventoryMode ignoreInventory, Faction faction, WorldPath path = null, float nextTileCostLeft = 0f, int caravanTicksPerMove = 3300, bool assumeCaravanMoving = true)
        {
            if (!AnyFoodEatingPawn(pawns))
            {
                return(600f);
            }
            if (!assumeCaravanMoving)
            {
                path = null;
            }
            tmpFood.Clear();
            if (extraFood != null)
            {
                int i = 0;
                for (int count = extraFood.Count; i < count; i++)
                {
                    ThingDefCount item = extraFood[i];
                    if (item.ThingDef.IsNutritionGivingIngestible && item.Count > 0)
                    {
                        tmpFood.Add(item);
                    }
                }
            }
            int j = 0;

            for (int count2 = pawns.Count; j < count2; j++)
            {
                Pawn pawn = pawns[j];
                if (InventoryCalculatorsUtility.ShouldIgnoreInventoryOf(pawn, ignoreInventory))
                {
                    continue;
                }
                ThingOwner <Thing> innerContainer = pawn.inventory.innerContainer;
                int k = 0;
                for (int count3 = innerContainer.Count; k < count3; k++)
                {
                    Thing thing = innerContainer[k];
                    if (thing.def.IsNutritionGivingIngestible)
                    {
                        tmpFood.Add(new ThingDefCount(thing.def, thing.stackCount));
                    }
                }
            }
            tmpFood2.Clear();
            tmpFood2.AddRange(tmpFood);
            tmpFood.Clear();
            int l = 0;

            for (int count4 = tmpFood2.Count; l < count4; l++)
            {
                ThingDefCount item2 = tmpFood2[l];
                bool          flag  = false;
                int           m     = 0;
                for (int count5 = tmpFood.Count; m < count5; m++)
                {
                    ThingDefCount thingDefCount = tmpFood[m];
                    if (thingDefCount.ThingDef == item2.ThingDef)
                    {
                        tmpFood[m] = thingDefCount.WithCount(thingDefCount.Count + item2.Count);
                        flag       = true;
                        break;
                    }
                }
                if (!flag)
                {
                    tmpFood.Add(item2);
                }
            }
            tmpDaysWorthOfFoodForPawn.Clear();
            int n = 0;

            for (int count6 = pawns.Count; n < count6; n++)
            {
                tmpDaysWorthOfFoodForPawn.Add(0f);
            }
            int ticksAbs = Find.TickManager.TicksAbs;

            tmpTicksToArrive.Clear();
            if (path != null && path.Found)
            {
                CaravanArrivalTimeEstimator.EstimatedTicksToArriveToEvery(tile, path.LastNode, path, nextTileCostLeft, caravanTicksPerMove, ticksAbs, tmpTicksToArrive);
            }
            cachedNutritionBetweenHungryAndFed.Clear();
            cachedTicksUntilHungryWhenFed.Clear();
            cachedMaxFoodLevel.Clear();
            int num = 0;

            for (int count7 = pawns.Count; num < count7; num++)
            {
                Pawn pawn2 = pawns[num];
                if (pawn2.RaceProps.EatsFood)
                {
                    Need_Food food = pawn2.needs.food;
                    cachedNutritionBetweenHungryAndFed.Add(food.NutritionBetweenHungryAndFed);
                    cachedTicksUntilHungryWhenFed.Add(food.TicksUntilHungryWhenFedIgnoringMalnutrition);
                    cachedMaxFoodLevel.Add(food.MaxLevel);
                }
                else
                {
                    cachedNutritionBetweenHungryAndFed.Add(0f);
                    cachedTicksUntilHungryWhenFed.Add(0);
                    cachedMaxFoodLevel.Add(0f);
                }
            }
            float     num2      = 0f;
            float     num3      = 0f;
            float     num4      = 0f;
            bool      flag2     = false;
            WorldGrid worldGrid = Find.WorldGrid;
            bool      flag3;

            do
            {
                flag3 = false;
                int   num5            = ticksAbs + (int)(num3 * 60000f);
                int   num6            = ((path != null) ? CaravanArrivalTimeEstimator.TileIllBeInAt(num5, tmpTicksToArrive, ticksAbs) : tile);
                bool  flag4           = CaravanNightRestUtility.WouldBeRestingAt(num6, num5);
                float progressPerTick = ForagedFoodPerDayCalculator.GetProgressPerTick(assumeCaravanMoving && !flag4, flag4);
                float num7            = 1f / progressPerTick;
                bool  flag5           = VirtualPlantsUtility.EnvironmentAllowsEatingVirtualPlantsAt(num6, num5);
                float num8            = num3 - num2;
                if (num8 > 0f)
                {
                    num4 += num8 * 60000f;
                    if (num4 >= num7)
                    {
                        BiomeDef biome       = worldGrid[num6].biome;
                        int      num9        = Mathf.RoundToInt(ForagedFoodPerDayCalculator.GetForagedFoodCountPerInterval(pawns, biome, faction));
                        ThingDef foragedFood = biome.foragedFood;
                        while (num4 >= num7)
                        {
                            num4 -= num7;
                            if (num9 <= 0)
                            {
                                continue;
                            }
                            bool flag6 = false;
                            for (int num10 = tmpFood.Count - 1; num10 >= 0; num10--)
                            {
                                ThingDefCount thingDefCount2 = tmpFood[num10];
                                if (thingDefCount2.ThingDef == foragedFood)
                                {
                                    tmpFood[num10] = thingDefCount2.WithCount(thingDefCount2.Count + num9);
                                    flag6          = true;
                                    break;
                                }
                            }
                            if (!flag6)
                            {
                                tmpFood.Add(new ThingDefCount(foragedFood, num9));
                            }
                        }
                    }
                }
                num2 = num3;
                int num11 = 0;
                for (int count8 = pawns.Count; num11 < count8; num11++)
                {
                    Pawn pawn3 = pawns[num11];
                    if (!pawn3.RaceProps.EatsFood)
                    {
                        continue;
                    }
                    if (flag5 && VirtualPlantsUtility.CanEverEatVirtualPlants(pawn3))
                    {
                        if (tmpDaysWorthOfFoodForPawn[num11] < num3)
                        {
                            tmpDaysWorthOfFoodForPawn[num11] = num3;
                        }
                        else
                        {
                            tmpDaysWorthOfFoodForPawn[num11] += 0.45f;
                        }
                        flag3 = true;
                    }
                    else
                    {
                        float num12 = cachedNutritionBetweenHungryAndFed[num11];
                        int   num13 = cachedTicksUntilHungryWhenFed[num11];
                        do
                        {
                            int num14 = BestEverEdibleFoodIndexFor(pawn3, tmpFood);
                            if (num14 < 0)
                            {
                                if (tmpDaysWorthOfFoodForPawn[num11] < num3)
                                {
                                    flag2 = true;
                                }
                                break;
                            }
                            ThingDefCount thingDefCount3 = tmpFood[num14];
                            float         num15          = Mathf.Min(thingDefCount3.ThingDef.ingestible.CachedNutrition, num12);
                            float         num16          = num15 / num12 * (float)num13 / 60000f;
                            int           num17          = Mathf.Min(Mathf.CeilToInt(Mathf.Min(0.2f, cachedMaxFoodLevel[num11]) / num15), thingDefCount3.Count);
                            tmpDaysWorthOfFoodForPawn[num11] += num16 * (float)num17;
                            tmpFood[num14] = thingDefCount3.WithCount(thingDefCount3.Count - num17);
                            flag3          = true;
                        }while (tmpDaysWorthOfFoodForPawn[num11] < num3);
                    }
                    if (flag2)
                    {
                        break;
                    }
                    num3 = Mathf.Max(num3, tmpDaysWorthOfFoodForPawn[num11]);
                }
            }while (!(!flag3 || flag2) && !(num3 > 601f));
            float num18 = 600f;
            int   num19 = 0;

            for (int count9 = pawns.Count; num19 < count9; num19++)
            {
                if (pawns[num19].RaceProps.EatsFood)
                {
                    num18 = Mathf.Min(num18, tmpDaysWorthOfFoodForPawn[num19]);
                }
            }
            return(num18);
        }
        public static void EstimatedTicksToArriveToEvery(int from, int to, WorldPath path, float nextTileCostLeft, int caravanTicksPerMove, int curTicksAbs, List <Pair <int, int> > outTicksToArrive)
        {
            outTicksToArrive.Clear();
            outTicksToArrive.Add(new Pair <int, int>(from, 0));
            if (from == to)
            {
                outTicksToArrive.Add(new Pair <int, int>(to, 0));
                return;
            }
            int num  = 0;
            int num2 = from;
            int num3 = 0;
            int num4 = Mathf.CeilToInt(20000f) - 1;
            int num5 = 60000 - num4;
            int num6 = 0;
            int num7 = 0;
            int num9;

            if (CaravanNightRestUtility.WouldBeRestingAt(from, (long)curTicksAbs))
            {
                if (Caravan_PathFollower.IsValidFinalPushDestination(to) && (path.Peek(0) == to || (nextTileCostLeft <= 0f && path.NodesLeftCount >= 2 && path.Peek(1) == to)))
                {
                    float costToMove = CaravanArrivalTimeEstimator.GetCostToMove(nextTileCostLeft, path.Peek(0) == to, curTicksAbs, num, caravanTicksPerMove, from, to);
                    int   num8       = Mathf.CeilToInt(costToMove / 1f);
                    if (num8 <= 10000)
                    {
                        num += num8;
                        outTicksToArrive.Add(new Pair <int, int>(to, num));
                        return;
                    }
                }
                num += CaravanNightRestUtility.LeftRestTicksAt(from, (long)curTicksAbs);
                num9 = num5;
            }
            else
            {
                num9 = CaravanNightRestUtility.LeftNonRestTicksAt(from, (long)curTicksAbs);
            }
            for (;;)
            {
                num7++;
                if (num7 >= 10000)
                {
                    break;
                }
                if (num6 <= 0)
                {
                    if (num2 == to)
                    {
                        goto Block_10;
                    }
                    bool firstInPath = num3 == 0;
                    int  num10       = num2;
                    num2 = path.Peek(num3);
                    num3++;
                    outTicksToArrive.Add(new Pair <int, int>(num10, num));
                    float costToMove2 = CaravanArrivalTimeEstimator.GetCostToMove(nextTileCostLeft, firstInPath, curTicksAbs, num, caravanTicksPerMove, num10, num2);
                    num6 = Mathf.CeilToInt(costToMove2 / 1f);
                }
                if (num9 < num6)
                {
                    num  += num9;
                    num6 -= num9;
                    if (num2 == to && num6 <= 10000 && Caravan_PathFollower.IsValidFinalPushDestination(to))
                    {
                        goto Block_14;
                    }
                    num += num4;
                    num9 = num5;
                }
                else
                {
                    num  += num6;
                    num9 -= num6;
                    num6  = 0;
                }
            }
            Log.ErrorOnce("Could not calculate estimated ticks to arrive. Too many iterations.", 1837451324, false);
            outTicksToArrive.Add(new Pair <int, int>(to, num));
            return;

Block_10:
            outTicksToArrive.Add(new Pair <int, int>(to, num));
            return;

Block_14:
            num += num6;
            outTicksToArrive.Add(new Pair <int, int>(to, num));
        }
 public static int EstimatedTicksToArrive(int from, int to, WorldPath path, float nextTileCostLeft, int caravanTicksPerMove, int curTicksAbs)
 {
     CaravanArrivalTimeEstimator.tmpTicksToArrive.Clear();
     CaravanArrivalTimeEstimator.EstimatedTicksToArriveToEvery(from, to, path, nextTileCostLeft, caravanTicksPerMove, curTicksAbs, CaravanArrivalTimeEstimator.tmpTicksToArrive);
     return(CaravanArrivalTimeEstimator.EstimatedTicksToArrive(to, CaravanArrivalTimeEstimator.tmpTicksToArrive));
 }
        private static float ApproxDaysWorthOfFood(List <Pawn> pawns, List <ThingDefCount> extraFood, int tile, IgnorePawnsInventoryMode ignoreInventory, Faction faction, WorldPath path = null, float nextTileCostLeft = 0f, int caravanTicksPerMove = 3500, bool assumeCaravanMoving = true)
        {
            float result;

            if (!DaysWorthOfFoodCalculator.AnyFoodEatingPawn(pawns))
            {
                result = 600f;
            }
            else
            {
                if (!assumeCaravanMoving)
                {
                    path = null;
                }
                DaysWorthOfFoodCalculator.tmpFood.Clear();
                if (extraFood != null)
                {
                    int i     = 0;
                    int count = extraFood.Count;
                    while (i < count)
                    {
                        ThingDefCount item = extraFood[i];
                        if (item.ThingDef.IsNutritionGivingIngestible && item.Count > 0)
                        {
                            DaysWorthOfFoodCalculator.tmpFood.Add(item);
                        }
                        i++;
                    }
                }
                int j      = 0;
                int count2 = pawns.Count;
                while (j < count2)
                {
                    Pawn pawn = pawns[j];
                    if (!InventoryCalculatorsUtility.ShouldIgnoreInventoryOf(pawn, ignoreInventory))
                    {
                        ThingOwner <Thing> innerContainer = pawn.inventory.innerContainer;
                        int k      = 0;
                        int count3 = innerContainer.Count;
                        while (k < count3)
                        {
                            Thing thing = innerContainer[k];
                            if (thing.def.IsNutritionGivingIngestible)
                            {
                                DaysWorthOfFoodCalculator.tmpFood.Add(new ThingDefCount(thing.def, thing.stackCount));
                            }
                            k++;
                        }
                    }
                    j++;
                }
                DaysWorthOfFoodCalculator.tmpFood2.Clear();
                DaysWorthOfFoodCalculator.tmpFood2.AddRange(DaysWorthOfFoodCalculator.tmpFood);
                DaysWorthOfFoodCalculator.tmpFood.Clear();
                int l      = 0;
                int count4 = DaysWorthOfFoodCalculator.tmpFood2.Count;
                while (l < count4)
                {
                    ThingDefCount item2  = DaysWorthOfFoodCalculator.tmpFood2[l];
                    bool          flag   = false;
                    int           m      = 0;
                    int           count5 = DaysWorthOfFoodCalculator.tmpFood.Count;
                    while (m < count5)
                    {
                        ThingDefCount thingDefCount = DaysWorthOfFoodCalculator.tmpFood[m];
                        if (thingDefCount.ThingDef == item2.ThingDef)
                        {
                            DaysWorthOfFoodCalculator.tmpFood[m] = thingDefCount.WithCount(thingDefCount.Count + item2.Count);
                            flag = true;
                            break;
                        }
                        m++;
                    }
                    if (!flag)
                    {
                        DaysWorthOfFoodCalculator.tmpFood.Add(item2);
                    }
                    l++;
                }
                DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn.Clear();
                int n      = 0;
                int count6 = pawns.Count;
                while (n < count6)
                {
                    DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn.Add(0f);
                    n++;
                }
                int ticksAbs = Find.TickManager.TicksAbs;
                DaysWorthOfFoodCalculator.tmpTicksToArrive.Clear();
                if (path != null && path.Found)
                {
                    CaravanArrivalTimeEstimator.EstimatedTicksToArriveToEvery(tile, path.LastNode, path, nextTileCostLeft, caravanTicksPerMove, ticksAbs, DaysWorthOfFoodCalculator.tmpTicksToArrive);
                }
                DaysWorthOfFoodCalculator.cachedNutritionBetweenHungryAndFed.Clear();
                DaysWorthOfFoodCalculator.cachedTicksUntilHungryWhenFed.Clear();
                DaysWorthOfFoodCalculator.cachedMaxFoodLevel.Clear();
                int num    = 0;
                int count7 = pawns.Count;
                while (num < count7)
                {
                    Pawn      pawn2 = pawns[num];
                    Need_Food food  = pawn2.needs.food;
                    DaysWorthOfFoodCalculator.cachedNutritionBetweenHungryAndFed.Add(food.NutritionBetweenHungryAndFed);
                    DaysWorthOfFoodCalculator.cachedTicksUntilHungryWhenFed.Add(food.TicksUntilHungryWhenFed);
                    DaysWorthOfFoodCalculator.cachedMaxFoodLevel.Add(food.MaxLevel);
                    num++;
                }
                float     num2      = 0f;
                float     num3      = 0f;
                float     num4      = 0f;
                bool      flag2     = false;
                WorldGrid worldGrid = Find.WorldGrid;
                bool      flag3;
                do
                {
                    flag3 = false;
                    int   num5            = ticksAbs + (int)(num3 * 60000f);
                    int   num6            = (path == null) ? tile : CaravanArrivalTimeEstimator.TileIllBeInAt(num5, DaysWorthOfFoodCalculator.tmpTicksToArrive, ticksAbs);
                    bool  flag4           = CaravanRestUtility.WouldBeRestingAt(num6, (long)num5);
                    float progressPerTick = ForagedFoodPerDayCalculator.GetProgressPerTick(assumeCaravanMoving && !flag4, flag4, null);
                    float num7            = 1f / progressPerTick;
                    bool  flag5           = VirtualPlantsUtility.EnvironmentAllowsEatingVirtualPlantsAt(num6, num5);
                    float num8            = num3 - num2;
                    if (num8 > 0f)
                    {
                        num4 += num8 * 60000f;
                        if (num4 >= num7)
                        {
                            BiomeDef biome       = worldGrid[num6].biome;
                            int      num9        = Mathf.RoundToInt(ForagedFoodPerDayCalculator.GetForagedFoodCountPerInterval(pawns, biome, faction, null));
                            ThingDef foragedFood = biome.foragedFood;
                            while (num4 >= num7)
                            {
                                num4 -= num7;
                                if (num9 > 0)
                                {
                                    bool flag6 = false;
                                    for (int num10 = DaysWorthOfFoodCalculator.tmpFood.Count - 1; num10 >= 0; num10--)
                                    {
                                        ThingDefCount thingDefCount2 = DaysWorthOfFoodCalculator.tmpFood[num10];
                                        if (thingDefCount2.ThingDef == foragedFood)
                                        {
                                            DaysWorthOfFoodCalculator.tmpFood[num10] = thingDefCount2.WithCount(thingDefCount2.Count + num9);
                                            flag6 = true;
                                            break;
                                        }
                                    }
                                    if (!flag6)
                                    {
                                        DaysWorthOfFoodCalculator.tmpFood.Add(new ThingDefCount(foragedFood, num9));
                                    }
                                }
                            }
                        }
                    }
                    num2 = num3;
                    int num11  = 0;
                    int count8 = pawns.Count;
                    while (num11 < count8)
                    {
                        Pawn pawn3 = pawns[num11];
                        if (pawn3.RaceProps.EatsFood)
                        {
                            if (flag5 && VirtualPlantsUtility.CanEverEatVirtualPlants(pawn3))
                            {
                                if (DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn[num11] < num3)
                                {
                                    DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn[num11] = num3;
                                }
                                else
                                {
                                    List <float> list;
                                    int          index;
                                    (list = DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn)[index = num11] = list[index] + 0.45f;
                                }
                                flag3 = true;
                            }
                            else
                            {
                                float num12 = DaysWorthOfFoodCalculator.cachedNutritionBetweenHungryAndFed[num11];
                                int   num13 = DaysWorthOfFoodCalculator.cachedTicksUntilHungryWhenFed[num11];
                                do
                                {
                                    int num14 = DaysWorthOfFoodCalculator.BestEverEdibleFoodIndexFor(pawn3, DaysWorthOfFoodCalculator.tmpFood);
                                    if (num14 < 0)
                                    {
                                        goto Block_27;
                                    }
                                    ThingDefCount thingDefCount3 = DaysWorthOfFoodCalculator.tmpFood[num14];
                                    float         num15          = Mathf.Min(thingDefCount3.ThingDef.ingestible.CachedNutrition, num12);
                                    float         num16          = num15 / num12 * (float)num13 / 60000f;
                                    int           num17          = Mathf.Min(Mathf.CeilToInt(Mathf.Min(0.2f, DaysWorthOfFoodCalculator.cachedMaxFoodLevel[num11]) / num15), thingDefCount3.Count);
                                    List <float>  list;
                                    int           index2;
                                    (list = DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn)[index2 = num11] = list[index2] + num16 * (float)num17;
                                    DaysWorthOfFoodCalculator.tmpFood[num14] = thingDefCount3.WithCount(thingDefCount3.Count - num17);
                                    flag3 = true;
                                }while (DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn[num11] < num3);
                                goto IL_633;
Block_27:
                                if (DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn[num11] < num3)
                                {
                                    flag2 = true;
                                }
                            }
IL_633:
                            if (flag2)
                            {
                                break;
                            }
                            num3 = Mathf.Max(num3, DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn[num11]);
                        }
                        num11++;
                    }
                }while (flag3 && !flag2 && num3 <= 601f);
                float num18  = 600f;
                int   num19  = 0;
                int   count9 = pawns.Count;
                while (num19 < count9)
                {
                    if (pawns[num19].RaceProps.EatsFood)
                    {
                        num18 = Mathf.Min(num18, DaysWorthOfFoodCalculator.tmpDaysWorthOfFoodForPawn[num19]);
                    }
                    num19++;
                }
                result = num18;
            }
            return(result);
        }
Ejemplo n.º 14
0
        public override string GetInspectString()
        {
            StringBuilder stringBuilder = new StringBuilder();

            stringBuilder.Append(base.GetInspectString());
            if (stringBuilder.Length != 0)
            {
                stringBuilder.AppendLine();
            }
            if (this.Resting)
            {
                stringBuilder.Append("CaravanResting".Translate());
            }
            else if (this.AnyPawnHasExtremeMentalBreak)
            {
                stringBuilder.Append("CaravanMemberMentalBreak".Translate(new object[]
                {
                    this.FirstPawnWithExtremeMentalBreak.LabelShort
                }));
            }
            else if (this.AllOwnersDowned)
            {
                stringBuilder.Append("AllCaravanMembersDowned".Translate());
            }
            else if (this.AllOwnersHaveMentalBreak)
            {
                stringBuilder.Append("AllCaravanMembersMentalBreak".Translate());
            }
            else if (this.pather.Moving)
            {
                if (this.pather.arrivalAction != null)
                {
                    stringBuilder.Append(this.pather.arrivalAction.ReportString);
                }
                else
                {
                    stringBuilder.Append("CaravanTraveling".Translate());
                }
            }
            else
            {
                Settlement settlement = CaravanVisitUtility.SettlementVisitedNow(this);
                if (settlement != null)
                {
                    stringBuilder.Append("CaravanVisiting".Translate(new object[]
                    {
                        settlement.Label
                    }));
                }
                else
                {
                    stringBuilder.Append("CaravanWaiting".Translate());
                }
            }
            if (this.pather.Moving)
            {
                float num = (float)CaravanArrivalTimeEstimator.EstimatedTicksToArrive(this, true) / 60000f;
                stringBuilder.AppendLine();
                stringBuilder.Append("CaravanEstimatedTimeToDestination".Translate(new object[]
                {
                    num.ToString("0.#")
                }));
            }
            if (this.ImmobilizedByMass)
            {
                stringBuilder.AppendLine();
                stringBuilder.Append("CaravanImmobilizedByMass".Translate());
            }
            string text;

            if (CaravanPawnsNeedsUtility.AnyPawnOutOfFood(this, out text))
            {
                stringBuilder.AppendLine();
                stringBuilder.Append("CaravanOutOfFood".Translate());
                if (!text.NullOrEmpty())
                {
                    stringBuilder.Append(" ");
                    stringBuilder.Append(text);
                    stringBuilder.Append(".");
                }
            }
            else if (this.DaysWorthOfFood.First < 1000f)
            {
                Pair <float, float> daysWorthOfFood = this.DaysWorthOfFood;
                stringBuilder.AppendLine();
                if (daysWorthOfFood.Second < 1000f)
                {
                    stringBuilder.Append("CaravanDaysOfFoodRot".Translate(new object[]
                    {
                        daysWorthOfFood.First.ToString("0.#"),
                        daysWorthOfFood.Second.ToString("0.#")
                    }));
                }
                else
                {
                    stringBuilder.Append("CaravanDaysOfFood".Translate(new object[]
                    {
                        daysWorthOfFood.First.ToString("0.#")
                    }));
                }
            }
            stringBuilder.AppendLine();
            stringBuilder.AppendLine(string.Concat(new string[]
            {
                "CaravanBaseMovementTime".Translate(),
                ": ",
                ((float)this.TicksPerMove / 2500f).ToString("0.##"),
                " ",
                "CaravanHoursPerTile".Translate()
            }));
            stringBuilder.AppendLine("CurrentTileMovementTime".Translate() + ": " + Caravan_PathFollower.CostToDisplay(this, base.Tile, this.pather.nextTile, -1f).ToStringTicksToPeriod(true, false, true));
            stringBuilder.Append("StealthFactor".Translate() + ": " + CaravanIncidentUtility.CalculateCaravanStealthFactor(this.PawnsListForReading.Count).ToString("F1"));
            return(stringBuilder.ToString());
        }
Ejemplo n.º 15
0
        public override GizmoResult GizmoOnGUI(Vector2 topLeft, float maxWidth)
        {
            if (!this.caravan.Spawned)
            {
                return(new GizmoResult(GizmoState.Clear));
            }
            Rect rect = new Rect(topLeft.x, topLeft.y, this.GetWidth(maxWidth), 75f);

            Widgets.DrawWindowBackground(rect);
            GUI.BeginGroup(rect);
            Rect          rect2         = rect.AtZero();
            int?          ticksToArrive = (!this.caravan.pather.Moving) ? null : new int?(CaravanArrivalTimeEstimator.EstimatedTicksToArrive(this.caravan, true));
            StringBuilder stringBuilder = new StringBuilder();
            float         tilesPerDay   = TilesPerDayCalculator.ApproxTilesPerDay(this.caravan, stringBuilder);

            CaravanUIUtility.DrawCaravanInfo(new CaravanUIUtility.CaravanInfo(this.caravan.MassUsage, this.caravan.MassCapacity, this.caravan.MassCapacityExplanation, tilesPerDay, stringBuilder.ToString(), this.caravan.DaysWorthOfFood, this.caravan.forage.ForagedFoodPerDay, this.caravan.forage.ForagedFoodPerDayExplanation, this.caravan.Visibility, this.caravan.VisibilityExplanation, -1f, -1f, null), null, this.caravan.Tile, ticksToArrive, -9999f, rect2, true, null, true);
            GUI.EndGroup();
            GenUI.AbsorbClicksInRect(rect);
            return(new GizmoResult(GizmoState.Clear));
        }