Пример #1
0
 public TreeNode_UIOption_ReservedItem(Building_Shelf shelf, ThingDef reservedThing, IntVec3 cell, bool forcedOpen = false)
     : base(reservedThing.LabelCap, "AS.ReservedItem.ToolTip".Translate(cell.ToString()), forcedOpen, () => true)
 {
     this.shelf         = shelf;
     this.reservedThing = reservedThing;
     this.cell          = cell;
 }
Пример #2
0
 public void CreateListingFor(Building_Shelf shelf)
 {
     SetupListing(shelf);
     if (!shelf.filterChangedSignalManager.receivers.Contains(this))
     {
         shelf.filterChangedSignalManager.RegisterReceiver(this);
         shelf.itemsHeldChangedSignalManager.RegisterReceiver(this);
     }
 }
Пример #3
0
        public static void Prefix(StorageSettings __instance, ref StoragePriority value)
        {
            Building_Shelf shelf = __instance.owner as Building_Shelf;

            if (value != __instance.Priority)
            {
                shelf?.Notify_PriorityChanging(value);
            }
        }
        public override bool HasJobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            Building_Shelf shelf = t as Building_Shelf;

            if (shelf == null || !shelf.HasEmptyCell())
            {
                return(false);
            }

            if (!shelf.slotGroup.EmptyCells().Any(cell =>
                                                  pawn.CanReserveAndReach(new LocalTargetInfo(cell), PathEndMode.Touch, pawn.NormalMaxDanger(), 1, -1, null, false)))
            {
                return(false);
            }

            LocalTargetInfo target = t;

            if (!pawn.CanReserve(target, 1, -1, null, false))
            {
                JobFailReason.Is("ShelfReserved".Translate());
                return(false);
            }

            foreach (SlotGroup sg in pawn.Map?.haulDestinationManager.AllGroupsListInPriorityOrder ?? Enumerable.Empty <SlotGroup>())
            {
                if (sg.Settings.Priority > shelf.settings.Priority ||
                    ((sg.Settings.Priority == shelf.settings.Priority) && (sg.parent is Building_Shelf)) ||
                    sg.parent == shelf)
                {
                    continue;
                }
                else
                {
                    foreach (Thing thing in sg.HeldThings)
                    {
                        if ((thing.stackCount >= thing.def.stackLimit || forced) && shelf.settings.filter.Allows(thing) &&
                            StockingUtility.PawnCanAutomaticallyHaul(pawn, thing, forced, shelf.InForbiddenMode))
                        {
                            return(true);
                        }
                    }
                }
            }
            if (!JobFailReason.HaveReason)
            {
                JobFailReason.Is("FillEmptyStock_NoItemsFound_JobFailReason".Translate());
            }
            if (JobFailReason.Reason == "ForbiddenLower".Translate())
            {
                JobFailReason.Is("FillEmptyStock_AllItemsFoundAreForbidden_JobFailReason".Translate());
            }
            return(false);
        }
        public override Job JobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            Thing          stockSource = null;
            IntVec3        destCell    = IntVec3.Invalid;
            Building_Shelf s           = t as Building_Shelf;

            if (s.CanOverlayThing(out stockSource, out destCell))
            {
                return(new Job(StockingJobDefOf.OverlayThing, t, stockSource, destCell));
            }
            return(null);
        }
        public static void Copy(Building_Shelf shelf)
        {
            StorageSettingsClipboard.Copy(shelf.settings);
            StockingSettingsClipboard.copiedShelf = shelf;
            StockingSettingsClipboard.copied      = true;

            //As both this and StorageSettingsClipboard are static without constructors
            //  I have a timing issue setting up callbacks. I will do so during the first copy
            if (!setupCallback)
            {
                SetupCallback();
            }
        }
Пример #7
0
        public void CopyStockSettingsFrom(Building_Shelf other)
        {
            settings.CopyFrom(other.settings);
            InRackMode                     = other.InRackMode;
            InForbiddenMode                = other.InForbiddenMode;
            InPriorityCyclingMode          = other.InPriorityCyclingMode;
            PawnShouldOrganizeAfterFilling = other.PawnShouldOrganizeAfterFilling;
            FillEmptyStockPriority         = other.FillEmptyStockPriority;
            OrganizeStockPriority          = other.OrganizeStockPriority;
            overlayLimit                   = other.overlayLimit;
            stackLimits                    = new Dictionary <ThingDef, int>(other.stackLimits);

            RecalcOverlays();
        }
 private static Gizmo PasteGizmoFor(Building_Shelf shelf)
 {
     return(new Command_Action()
     {
         icon = ContentFinder <Texture2D> .Get("UI/Commands/PasteSettings", true),
         defaultLabel = "CommandPasteStockingSettingsLabel".Translate(),
         defaultDesc = "CommandPasteStockingSettingsDesc".Translate(),
         action = delegate {
             SoundDefOf.Tick_High.PlayOneShotOnCamera(null);
             StockingSettingsClipboard.PasteInto(shelf);
         },
         hotKey = KeyBindingDefOf.Misc5
     });
 }
Пример #9
0
        public void Notify_SignalReceived(Signal signal)
        {
            Building_Shelf shelf = signal.args[0] as Building_Shelf;

            if (shelf != displayingFor)               //Cannot remove OnClose, will do so when erroneous signal sent
            {
                shelf.filterChangedSignalManager.DeregisterReceiver(this);
                shelf.itemsHeldChangedSignalManager.DeregisterReceiver(this);
            }
            else
            {
                SetupListing(shelf);
            }
        }
        public override bool HasJobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            Building_Shelf shelf = t as Building_Shelf;

            LocalTargetInfo target = t;

            if (!pawn.CanReserveAndReach(target, PathEndMode.Touch, pawn.NormalMaxDanger(), 1, -1, null, false))
            {
                return(false);
            }

            return((shelf != null) && shelf.InRackMode &&
                   shelf.CanOverlayThing(out Thing source, out IntVec3 dest) &&
                   pawn.CanReserve(source, 1, -1, null, false));
        }
        public override string GetExplanationUnfinalized(StatRequest req, ToStringNumberSense numberSense)
        {
            StringBuilder  stringBuilder = new StringBuilder();
            Building_Shelf shelf         = req.Thing as Building_Shelf;

            stringBuilder.AppendLine("StatWorker.OverlayLimit.Desc.ModSettings".Translate(AS_Mod.settings.maxOverlayLimit));
            if (shelf.MaxOverlayLimit < AS_Mod.settings.maxOverlayLimit && shelf.HeaviestAllowedThing != null)
            {
                stringBuilder.AppendLine("StatWorker.OverlayLimit.Desc.MassContraint"
                                         .Translate(shelf.HeaviestAllowedThing.LabelCap
                                                    , shelf.HeaviestAllowedThing.GetStatValueAbstract(StatDefOf.Mass)
                                                    , shelf.GetStatValue(StockingStatDefOf.MaxStockWeight)));
            }

            return(stringBuilder.ToString());
        }
        public override IEnumerable <Thing> PotentialWorkThingsGlobal(Pawn pawn)
        {
            List <SlotGroup> slotGroups = pawn.Map?.haulDestinationManager?.AllGroupsListForReading;

            if (slotGroups == null)
            {
                yield break;
            }
            for (int i = 0; i < slotGroups.Count; i++)
            {
                Building_Shelf shelf = slotGroups[i].parent as Building_Shelf;
                if (shelf != null)
                {
                    yield return(shelf);
                }
            }
        }
Пример #13
0
        public override bool HasJobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            Building_Shelf shelf = t as Building_Shelf;

            LocalTargetInfo target = t;

            if (!pawn.CanReserveAndReach(target, PathEndMode.Touch, pawn.NormalMaxDanger(), 1, -1, null, false))
            {
                return(false);
            }

            return((shelf != null) && shelf.CanCombineThings(out Thing source, out Thing dest) &&
                   (pawn.CanReserve(source, 1, -1, null, false) ||
                    (shelf.InForbiddenMode && source.IsForbidden(Faction.OfPlayer))) &&
                   (pawn.CanReserve(dest, 1, -1, null, false) ||
                    (shelf.InForbiddenMode && dest.IsForbidden(Faction.OfPlayer))));
        }
Пример #14
0
        public override void OnOpen()
        {
            Building_Shelf shelf = this.SelObject as Building_Shelf;

            if (shelf == null)
            {
                return;
            }
            if (shelf != this.displayingFor)
            {
                CreateListingFor(shelf);
            }
            else
            {
                RebuildReservationOptions();
            }
        }
Пример #15
0
        //If someone selects another Shelf while Tab is open, OnOpen won't be called inbetween
        protected override void FillTab()
        {
            Building_Shelf shelf = this.SelObject as Building_Shelf;

            if (shelf == null)
            {
                return;
            }
            if (shelf != this.displayingFor)
            {
                CreateListingFor(shelf);
            }

            Rect rect = new Rect(0, 30, ITab_Stock.WinSize.x, ITab_Stock.WinSize.y - 30).ContractedBy(CellSpacing);

            listing.Begin(rect);
            listing.DrawUIOptions();
            listing.End();
        }
Пример #16
0
        public override string GetExplanationUnfinalized(StatRequest req, ToStringNumberSense numberSense)
        {
            StringBuilder  stringBuilder = new StringBuilder();
            Building_Shelf shelf         = req.Thing as Building_Shelf;

            stringBuilder.AppendLine("StatWorker.OverstackLimit.Desc.ModSettings".Translate(AS_Mod.settings.maxOverstackRatio));

            if (AS_Mod.settings.overlaysReduceStacklimit)
            {
                if (AS_Mod.settings.overlaysReduceStacklimitPartially)
                {
                    stringBuilder.AppendLine("StatWorker.OverstackLimit.Desc.OverlayReduction.Partial"
                                             .Translate(shelf.OverlayLimit * 2f / 3f + 1f / 3f));
                }
                else
                {
                    stringBuilder.AppendLine("StatWorker.OverstackLimit.Desc.OverlayReduction".Translate(shelf.OverlayLimit));
                }
            }
            return(stringBuilder.ToString());
        }
 public static void PasteInto(Building_Shelf shelf)
 {
     shelf.CopyStockSettingsFrom(StockingSettingsClipboard.copiedShelf);
 }
Пример #18
0
        private void SetupListing(Building_Shelf shelf)
        {
            TreeNode_UIOption advancedStockingRootNode = new TreeNode_UIOption("AdvancedStocking.Label".Translate());

            (new TreeNode_UIOption_Checkbox("InRackMode.Label".Translate(),
                                            () => shelf.InRackMode, b => shelf.InRackMode = b, "InRackMode.ToolTip".Translate()))
            .AddAsChildTo(advancedStockingRootNode);

            (new TreeNode_UIOption_Checkbox("InPriorityCyclingMode_label".Translate(),
                                            () => shelf.InPriorityCyclingMode, b => shelf.InPriorityCyclingMode = b, "InPriorityCyclingMode_tooltip".Translate(), false))
            .AddAsChildTo(advancedStockingRootNode);
            //			advancedStockingRootNode.children.Add (new TreeNode_UIOptionCheckbox ("InSingleThingMode_label".Translate(),
            //				() => shelf.InSingleThingMode, b => shelf.InSingleThingMode = b, "Testing", false, () => shelf.InStockingMode));
            (new TreeNode_UIOption_Checkbox("InForbiddenMode_label".Translate(),
                                            () => shelf.InForbiddenMode, b => shelf.InForbiddenMode = b, "InForbiddenMode_tooltip".Translate(), false))
            .AddAsChildTo(advancedStockingRootNode);

            (new TreeNode_UIOption_Checkbox("AutoOrganizeAfterFilling_label".Translate(),
                                            () => shelf.PawnShouldOrganizeAfterFilling, b => shelf.PawnShouldOrganizeAfterFilling = b, "AutoOrganizeAfterFilling_tooltip".Translate(),
                                            false))
            .AddAsChildTo(advancedStockingRootNode);
            TreeNode_UIOption prioritiesSubtree = new TreeNode_UIOption("StockJobPriorities_label".Translate(), "StockJobPriorities_tooltip".Translate());

            prioritiesSubtree.AddAsChildTo(advancedStockingRootNode);

            (new TreeNode_UIOption_EnumMenuButton <StockingPriority>("Fill_Empty_Stock_Priority".Translate(),
                                                                     () => Enum.GetName(typeof(StockingPriority), shelf.FillEmptyStockPriority).Translate(),
                                                                     p => shelf.FillEmptyStockPriority = p,
                                                                     null, ITab_Stock.PriorityButtonWidth, "Fill_Empty_Stock_Priority_Tooltip".Translate(), false))
            .AddAsChildTo(prioritiesSubtree);
            (new TreeNode_UIOption_EnumMenuButton <StockingPriority>("Organize_Stock_Priority".Translate(),
                                                                     () => Enum.GetName(typeof(StockingPriority), shelf.OrganizeStockPriority).Translate(),
                                                                     p => shelf.OrganizeStockPriority = p,
                                                                     null, ITab_Stock.PriorityButtonWidth, "Organize_Stock_Priority_Tooltip".Translate(), false))
            .AddAsChildTo(prioritiesSubtree);

            TreeNode_UIOption stockingLimitsRootNode = new TreeNode_UIOption("StockingLimits.Label".Translate());

            if (shelf.MaxOverlayLimit > 1)
            {
                (new TreeNode_UIOption_Slider("OverlayLimit.Label".Translate(shelf.CurrentOverlaysUsed, shelf.MaxOverlayLimit)
                                              , valGetter: () => (float)shelf.OverlayLimit
                                              , valSetter: val => shelf.OverlayLimit = (int)val
                                              , minGetter: () => shelf.CurrentOverlaysUsed
                                              , maxGetter: () => shelf.MaxOverlayLimit
                                              , roundTo: 1f
                                              , toolTip: "OverlayLimit.ToolTip".Translate()))
                .AddAsChildTo(stockingLimitsRootNode);
            }

            IEnumerable <ThingDef> thingDefsToDisplay = null;

            if (shelf.settings.filter.AllowedDefCount <= Building_Shelf.MAX_UNHELD_STACKLIMITS_TO_DISPLAY)
            {
                thingDefsToDisplay = shelf.settings.filter.AllowedThingDefs;
            }
            else
            {
                thingDefsToDisplay = shelf.slotGroup.HeldThings.Select(thing => thing.def).Distinct();
            }

            foreach (var thingDef in thingDefsToDisplay)
            {
                (new TreeNode_UIOption_Slider(() => "StackLimit.Label".Translate(thingDef.LabelCap, shelf.GetMaxStackLimit(thingDef))
                                              , valGetter: () => (float)shelf.GetStackLimit(thingDef)
                                              , valSetter: value => shelf.SetStackLimit(thingDef, (int)value)
                                              , minGetter: () => 0f
                                              , maxGetter: () => shelf.GetMaxStackLimit(thingDef)
                                              , roundTo: 1f
                                              , toolTip: "StackLimit.ToolTip".Translate()))
                .AddAsChildTo(stockingLimitsRootNode);
            }

            if (stockingLimitsRootNode.children.NullOrEmpty())
            {
                stockingLimitsRootNode.label = "StockingLimits.Label.NoChildren".Translate();
            }

            Action <TreeNode, TreeNode> configureNodeOpenings = null;
            FieldInfo openBitsField = typeof(Verse.TreeNode).GetField("openBits", BindingFlags.Instance | BindingFlags.NonPublic);

            configureNodeOpenings = delegate(TreeNode oldNode, TreeNode newNode) {
                openBitsField.SetValue(newNode, openBitsField.GetValue(oldNode));
                IEnumerator <TreeNode> oldNodeEnum = oldNode.children?.GetEnumerator() ?? Enumerable.Empty <TreeNode>().GetEnumerator();
                IEnumerator <TreeNode> newNodeEnum = newNode.children?.GetEnumerator() ?? Enumerable.Empty <TreeNode>().GetEnumerator();
                while (oldNodeEnum.MoveNext() && newNodeEnum.MoveNext())
                {
                    configureNodeOpenings(oldNodeEnum.Current, newNodeEnum.Current);
                }
            };

            var newListing = new Listing_TreeUIOption(new List <TreeNode_UIOption>()
            {
                stockingLimitsRootNode
                , advancedStockingRootNode
            });
            int maxOptionIndex = Math.Min(this.listing?.RootOptions.Count ?? 0, newListing.RootOptions.Count);

            for (int i = 0; i < maxOptionIndex; i++)
            {
                configureNodeOpenings(this.listing.RootOptions[i], newListing.RootOptions[i]);
            }

            this.displayingFor = shelf;
            this.listing       = newListing;

            RebuildReservationOptions();    //Perform after nodeOpening configuration as reservations will change
        }
        public override Job JobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            Building_Shelf shelf      = t as Building_Shelf;
            List <Thing>   potentials = new List <Thing> ();

            if (shelf == null)
            {
                return(null);
            }

            foreach (SlotGroup sg in pawn.Map?.haulDestinationManager.AllGroupsListInPriorityOrder ?? Enumerable.Empty <SlotGroup>())
            {
                if (sg.Settings.Priority > shelf.settings.Priority ||
                    ((sg.Settings.Priority == shelf.settings.Priority) && (sg.parent is Building_Shelf)))
                {
                    continue;
                }
                else
                {
                    foreach (Thing thing in sg.HeldThings)
                    {
                        if ((thing.stackCount >= thing.def.stackLimit || forced) && shelf.settings.filter.Allows(thing) &&
                            StockingUtility.PawnCanAutomaticallyHaul(pawn, thing, forced, shelf.InForbiddenMode))
                        {
                            potentials.Add(thing);
                        }
                    }
                }
            }

            int   minDist = 200000000;
            float maxPartialFullStackFound = 0f;
            Thing chosenThing = null;

            foreach (Thing thing in potentials)                 //I KNOW THIS IS TERRIBLE, BUT I LOVE IT ANYWAYS
            {
                int dist = (thing.Position - pawn.Position).LengthHorizontalSquared + (thing.Position - shelf.Position).LengthHorizontalSquared;
                if (forced)
                {
                    float part = (float)thing.stackCount / (float)thing.def.stackLimit;
                    if (part < maxPartialFullStackFound)
                    {
                        continue;
                    }
                    if (part > maxPartialFullStackFound)
                    {
                        maxPartialFullStackFound = part;
                        chosenThing = thing;
                        minDist     = dist;
                        continue;
                    }
                }
                if (dist < minDist)
                {
                    minDist     = dist;
                    chosenThing = thing;
                }
            }

            if (chosenThing == null)
            {
                return(null);
            }
            IntVec3 destEmptyCell = shelf.slotGroup.EmptyCells().FirstOrDefault(cell =>
                                                                                pawn.CanReserveAndReach(new LocalTargetInfo(cell), PathEndMode.Touch, pawn.NormalMaxDanger(), 1, -1, null, false));

            if (destEmptyCell == default(IntVec3))
            {
                return(null);
            }
            Job job = new Job(StockingJobDefOf.FillEmptyStock, chosenThing, destEmptyCell, shelf);

            job.haulOpportunisticDuplicates = true;
            job.haulMode = HaulMode.ToCellStorage;
            job.count    = chosenThing.stackCount;

            return(job);
        }