Esempio n. 1
0
        public override void RunCommand([NotNull] ITwitchMessage twitchMessage)
        {
            var    worker   = ArgWorker.CreateInstance(CommandFilter.Parse(twitchMessage.Message).Skip(1));
            string argument = worker.GetNext();

            switch (argument.ToLowerInvariant())
            {
            case "accept":
                ProcessAccept(twitchMessage.Username, worker.GetNextAsViewer());

                return;

            case "decline":
                ProcessDecline(twitchMessage.Username, worker.GetNextAsViewer());

                return;

            default:
                Viewer viewer = Viewers.All.Find(v => string.Equals(v.username, argument, StringComparison.InvariantCultureIgnoreCase));

                if (viewer != null)
                {
                    ProcessRequest(twitchMessage.Username, viewer);
                }
                else
                {
                    MessageHelper.ReplyToUser(twitchMessage.Username, "TKUtils.InvalidViewerQuery".LocalizeKeyed(worker.GetLast()));
                }

                return;
            }
        }
Esempio n. 2
0
        public override bool CanHappen(string msg, [NotNull] Viewer viewer)
        {
            if (!PurchaseHelper.TryGetPawn(viewer.username, out _pawn))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.NoPawn".Localize());

                return(false);
            }

            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));

            if (!worker.TryGetNextAsSkill(out SkillDef skillDef))
            {
                return(false);
            }

            _target = _pawn !.skills.skills.Where(s => !s.TotallyDisabled).FirstOrDefault(s => s.def.Equals(skillDef));

            if (_target == null)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidSkillQuery".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if ((int)_target.passion < 3)
            {
                return(true);
            }

            MessageHelper.ReplyToUser(viewer.username, "TKUtils.Passion.Full".Localize());

            return(false);
        }
Esempio n. 3
0
        private void PerformItemLookup([NotNull] string query, int quantity)
        {
            var worker = ArgWorker.CreateInstance(query);

            if (!worker.TryGetNextAsItem(out ArgWorker.ItemProxy item) || !item.IsValid() || item.Thing?.Cost <= 0)
            {
                return;
            }

            if (item.TryGetError(out string error))
            {
                MessageHelper.ReplyToUser(_invoker, error);

                return;
            }

            int price = item.Quality.HasValue ? item.Thing !.GetItemPrice(item.Stuff, item.Quality.Value) : item.Thing !.GetItemPrice(item.Stuff);

            if (!PurchaseHelper.TryMultiply(price, quantity, out int total))
            {
                MessageHelper.ReplyToUser(_invoker, "TKUtils.Overflowed".Localize());

                return;
            }

            NotifyLookupComplete("TKUtils.Price.Limited".LocalizeKeyed(item.AsString().CapitalizeFirst(), total.ToString("N0")));
        }
Esempio n. 4
0
        public override bool CanHappen(string msg, [NotNull] Viewer viewer)
        {
            if (!PurchaseHelper.TryGetPawn(viewer.username, out _pawn))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.NoPawn".Localize());

                return(false);
            }

            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));

            if (!worker.TryGetNextAsItem(out _item) || !_item.IsValid())
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidItemQuery".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if (_item.TryGetError(out string error))
            {
                MessageHelper.ReplyToUser(viewer.username, error);

                return(false);
            }

            if (!(_item.Thing.Thing is { IsWeapon : true }) || _item.Thing.ItemData?.IsEquippable != true)
Esempio n. 5
0
        public override void RunCommand([NotNull] ITwitchMessage twitchMessage)
        {
            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(twitchMessage.Message).Skip(1));

            if (!worker.TryGetNextAsInt(out int amount, 1))
            {
                return;
            }

            List <string> viewers = Viewers.ParseViewersFromJsonAndFindActiveViewers();

            if (viewers == null || viewers.Count <= 0)
            {
                return;
            }

            var count = 0;

            foreach (string username in viewers)
            {
                Viewers.GetViewer(username).GiveViewerCoins(amount);
                count++;
            }

            twitchMessage.Reply("TKUtils.GiveAll".LocalizeKeyed(amount.ToString("N0"), count.ToString("N0")));
        }
Esempio n. 6
0
        public override bool CanHappen(string msg, [NotNull] Viewer viewer)
        {
            if (!PurchaseHelper.TryGetPawn(viewer.username, out _pawn))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.NoPawn".Localize());

                return(false);
            }

            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));

            if (!worker.TryGetNextAsTrait(out _thisShop) || !worker.TryGetNextAsTrait(out _thatShop))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidTraitQuery".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if (!IsUsable(_thisShop, _thatShop))
            {
                MessageHelper.ReplyToUser(
                    viewer.username,
                    $"TKUtils.{(_thisShop.CanRemove ? "" : "Remove")}Trait.Disabled".LocalizeKeyed((_thisShop.CanRemove ? _thatShop : _thisShop).Name.CapitalizeFirst())
                    );

                return(false);
            }

            if (TraitHelper.GetTotalTraits(_pawn) >= AddTraitSettings.maxTraits && WouldExceedLimit())
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.ReplaceTrait.Violation".LocalizeKeyed(_thisShop.Name, _thatShop.Name));

                return(false);
            }

            if (!viewer.CanAfford(TotalPrice))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InsufficientBalance".LocalizeKeyed(TotalPrice.ToString("N0"), viewer.GetViewerCoins().ToString("N0")));

                return(false);
            }

            if (!PassesCharacterCheck(viewer))
            {
                return(false);
            }

            if (!PassesModCheck(viewer))
            {
                return(false);
            }

            if (!PassesValidationCheck(viewer))
            {
                return(false);
            }

            return(true);
        }
Esempio n. 7
0
        public override bool CanHappen(string msg, [NotNull] Viewer viewer)
        {
            if (CommandBase.GetOrFindPawn(viewer.username) != null)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.HasPawn".Localize());

                return(false);
            }

            _map = Helper.AnyPlayerMap;

            if (_map == null)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.NoMap".Localize());

                return(false);
            }

            if (!CellFinder.TryFindRandomEdgeCellWith(p => _map.reachability.CanReachColony(p) && !p.Fogged(_map), _map, CellFinder.EdgeRoadChance_Neutral, out _loc))
            {
                TkUtils.Logger.Warn("No reachable location to spawn a viewer pawn!");

                return(false);
            }

            GetDefaultKind();

            if (!TkSettings.PurchasePawnKinds)
            {
                return(CanPurchaseRace(viewer, _pawnKindItem));
            }

            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));

            if (!worker.TryGetNextAsPawn(out PawnKindItem temp) || _pawnKindItem?.ColonistKindDef == null)
            {
                if (worker.GetLast().NullOrEmpty())
                {
                    return(CanPurchaseRace(viewer, _pawnKindItem !));
                }

                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidKindQuery".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            _pawnKindItem = temp;
            _kindDef      = _pawnKindItem.ColonistKindDef;

            if (_kindDef.RaceProps.Humanlike)
            {
                return(CanPurchaseRace(viewer, _pawnKindItem));
            }

            MessageHelper.ReplyToUser(viewer.username, "TKUtils.BuyPawn.Humanlike".Localize());

            return(false);
        }
Esempio n. 8
0
        public override void RunCommand([NotNull] ITwitchMessage twitchMessage)
        {
            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(twitchMessage.Message).Skip(1));

            if (!worker.TryGetNextAsViewer(out Viewer viewer) || !worker.TryGetNextAsInt(out int amount))
            {
                return;
            }

            viewer.GiveViewerCoins(amount);
            Store_Logger.LogGiveCoins(twitchMessage.Username, viewer.username, amount);
            twitchMessage.Reply("TKUtils.GiveCoins.Done".LocalizeKeyed(amount.ToString("N0"), viewer.username, viewer.GetViewerCoins().ToString("N0")));
        }
Esempio n. 9
0
        private static bool ResolvePurchasePrefix([NotNull] Viewer viewer, [NotNull] ITwitchMessage twitchMessage)
        {
            if (Purchase_Handler.CheckIfViewerIsInVariableCommandList(viewer.username))
            {
                return(false);
            }

            List <string> segments = CommandFilter.Parse(twitchMessage.Message).ToList();
            var           worker   = ArgWorker.CreateInstance(segments);

            if (!worker.HasNext())
            {
                return(false);
            }

            string query = segments.Skip(1).FirstOrFallback("");

            if (TryProcessIncident(viewer, twitchMessage, query))
            {
                return(false);
            }

            Helper.Log($"abr: {query} ");

            segments.Insert(1, "item");

            if (segments.Count < 4)
            {
                segments.Add("1");
            }

            if (!int.TryParse(segments[3], out int _))
            {
                segments.Insert(3, "1");
            }

            try
            {
                Purchase_Handler.ResolvePurchaseVariables(viewer, twitchMessage, StoreIncidentDefOf.Item, string.Join(" ", segments.ToArray()));
            }
            catch (Exception e)
            {
                TkUtils.Logger.Error("Could not resolve purchase", e);
            }

            return(false);
        }
Esempio n. 10
0
        public override bool CanHappen(string msg, [NotNull] Viewer viewer)
        {
            if (!PurchaseHelper.TryGetPawn(viewer.username, out _pawn))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.NoPawn".Localize());

                return(false);
            }

            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));

            if (!worker.TryGetNextAsTrait(out _buyableTrait) || !_buyableTrait.CanAdd || _buyableTrait.TraitDef == null)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidTraitQuery".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if (!viewer.CanAfford(_buyableTrait !.CostToAdd))
            {
                MessageHelper.ReplyToUser(
                    viewer.username,
                    "TKUtils.InsufficientBalance".LocalizeKeyed(_buyableTrait.CostToAdd.ToString("N0"), viewer.GetViewerCoins().ToString("N0"))
                    );

                return(false);
            }

            if (TraitHelper.GetTotalTraits(_pawn) >= AddTraitSettings.maxTraits && _buyableTrait.TraitData?.CanBypassLimit != true)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.Trait.LimitReached".LocalizeKeyed(AddTraitSettings.maxTraits));

                return(false);
            }

            if (!PassesCharacterChecks(viewer, worker))
            {
                return(false);
            }

            _trait = new Trait(_buyableTrait.TraitDef, _buyableTrait.Degree);

            return(PassesValidationChecks(viewer) && PassesModChecks(viewer));
        }
Esempio n. 11
0
        /// <inheritdoc/>
        public override void RunCommand([NotNull] ITwitchMessage twitchMessage)
        {
            if (!PurchaseHelper.TryGetPawn(twitchMessage.Username, out Pawn pawn))
            {
                MessageHelper.ReplyToUser(twitchMessage.Username, "TKUtils.NoPawn".Localize());

                return;
            }

            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(twitchMessage.Message).Skip(1));

            if (!worker.TryGetNextAsViewer(out Viewer viewer) || !PurchaseHelper.TryGetPawn(viewer.username, out Pawn target))
            {
                MessageHelper.ReplyToUser(twitchMessage.Username, "TKUtils.PawnNotFound".LocalizeKeyed(worker.GetLast()));

                return;
            }

            TkUtils.Context.Post(c => PerformDivorce(pawn, target), null);
        }
Esempio n. 12
0
        private void PerformWeaponLookup([NotNull] string query)
        {
            var worker = ArgWorker.CreateInstance(query);

            if (!worker.TryGetNextAsItem(out ArgWorker.ItemProxy item) || !item.IsValid() || !item.Thing.Thing.IsWeapon)
            {
                MessageHelper.ReplyToUser(_invoker, "TKUtils.InvalidItemQuery".LocalizeKeyed(worker.GetLast()));

                return;
            }

            if (item.TryGetError(out string error))
            {
                MessageHelper.ReplyToUser(_invoker, error);

                return;
            }

            var result = new List <string>();

            Thing thing = PurchaseHelper.MakeThing(item.Thing.Thing, item.Stuff.Thing, item.Quality);

            CommandRouter.MainThreadCommands.Enqueue(
                () =>
            {
                result.AddRange(WeaponStats.Select(s => s.ValueToString(thing.GetStatValue(s))));

                if (item.Thing.Thing.IsMeleeWeapon)
                {
                    result.AddRange(MeleeWeaponStats.Select(s => s.ValueToString(thing.GetStatValue(s))));
                }

                if (item.Thing.Thing.IsRangedWeapon)
                {
                    result.AddRange(RangedWeaponStats.Select(s => s.ValueToString(thing.GetStatValue(s))));
                }

                NotifyLookupComplete(ResponseHelper.JoinPair(item.Thing.ToString(), result.GroupedJoin()));
            }
                );
        }
Esempio n. 13
0
        public override bool CanHappen(string msg, [NotNull] Viewer viewer)
        {
            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));

            if (!worker.TryGetNextAsItem(out ArgWorker.ItemProxy product) || !product.IsValid())
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidItemQuery".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if (product.TryGetError(out string error))
            {
                MessageHelper.ReplyToUser(viewer.username, error);

                return(false);
            }

            int amount = product.Thing.ItemData?.HasQuantityLimit == true?worker.GetNextAsInt(1, product.Thing.ItemData.QuantityLimit) : worker.GetNextAsInt(1);

            List <ResearchProjectDef> projects = product !.Thing.Thing.GetUnfinishedPrerequisites();

            if (BuyItemSettings.mustResearchFirst && projects.Count > 0)
            {
                MessageHelper.ReplyToUser(
                    viewer.username,
                    "TKUtils.ResearchRequired".LocalizeKeyed(product.Thing.Thing.LabelCap.RawText, projects.Select(p => p.LabelCap.RawText).SectionJoin())
                    );

                return(false);
            }

            if (worker.GetLast()?.Equals("*") ?? false)
            {
                amount = viewer.GetMaximumPurchaseAmount(product.Thing.Cost);
            }

            _purchaseRequest = new PurchaseRequest {
                Proxy = product, Quantity = amount, Purchaser = viewer, Map = Helper.AnyPlayerMap
            };

            if (_purchaseRequest.Price < ToolkitSettings.MinimumPurchasePrice)
            {
                MessageHelper.ReplyToUser(
                    viewer.username,
                    "TKUtils.Item.MinimumViolation".LocalizeKeyed(_purchaseRequest.Price.ToString("N0"), ToolkitSettings.MinimumPurchasePrice.ToString("N0"))
                    );

                return(false);
            }

            if (_purchaseRequest.Overflowed)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.Overflowed".Localize());

                return(false);
            }

            if (viewer.CanAfford(_purchaseRequest.Price))
            {
                return(_purchaseRequest.Map != null);
            }

            MessageHelper.ReplyToUser(
                viewer.username,
                "TKUtils.InsufficientBalance".LocalizeKeyed(_purchaseRequest.Price.ToString("N0"), viewer.GetViewerCoins().ToString("N0"))
                );

            return(false);
        }
Esempio n. 14
0
        public override bool CanHappen(string msg, [NotNull] Viewer viewer)
        {
            if (!PurchaseHelper.TryGetPawn(viewer.username, out _pawn))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.NoPawn".Localize());

                return(false);
            }

            List <Trait> traits = _pawn !.story.traits.allTraits;

            if (traits?.Count <= 0)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.RemoveTrait.None".Localize());

                return(false);
            }

            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));

            if (!worker.TryGetNextAsTrait(out _buyable))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidTraitQuery".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if (!_buyable !.CanRemove)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.RemoveTrait.Disabled".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if (!viewer.CanAfford(_buyable.CostToRemove))
            {
                MessageHelper.ReplyToUser(
                    viewer.username,
                    "TKUtils.InsufficientBalance".LocalizeKeyed(_buyable.CostToRemove.ToString("N0"), viewer.GetViewerCoins().ToString("N0"))
                    );

                return(false);
            }

            Trait target = traits?.FirstOrDefault(t => TraitHelper.CompareToInput(_buyable.GetDefaultName(_pawn.gender) !, t.Label));

            if (target == null)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.RemoveTrait.Missing".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if (!PassesModChecks(viewer, target, worker))
            {
                return(false);
            }

            _trait = target;

            return(true);
        }
Esempio n. 15
0
        public override bool CanHappen(string msg, Viewer viewer)
        {
            string[] traitQueries = CommandFilter.Parse(msg).Skip(2).ToArray();

            if (traitQueries.Length <= 0)
            {
                return(false);
            }

            if (!PurchaseHelper.TryGetPawn(viewer.username, out _pawn))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.NoPawn".Localize());

                return(false);
            }

            var worker             = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));
            List <TraitItem> items = worker.GetAllAsTrait().ToList();

            if (worker.HasNext() && !worker.GetLast().NullOrEmpty())
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidTraitQuery".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if (!TryProcessTraits(_pawn !, items, out _events))
            {
                TraitEvent errored = _events.FirstOrDefault(e => !e.Error.NullOrEmpty());

                if (errored != null)
                {
                    MessageHelper.ReplyToUser(viewer.username, errored.Error);
                }

                return(false);
            }

            if (_events.Count(e => e.ContributesToLimit) > AddTraitSettings.maxTraits)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.Trait.LimitReached".LocalizeKeyed(AddTraitSettings.maxTraits));

                return(false);
            }

            int total = _events.Sum(
                i =>
            {
                switch (i.Type)
                {
                case EventType.Add:
                    return(i.Item.CostToAdd);

                case EventType.Remove:
                    return(i.Item.CostToRemove);

                default:
                    return(0);
                }
            }
                );

            if (!viewer.CanAfford(total))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InsufficientBalance".LocalizeKeyed(total.ToString("N0"), viewer.GetViewerCoins().ToString("N0")));

                return(false);
            }

            return(true);
        }
Esempio n. 16
0
        public override bool CanHappen(string msg, [NotNull] Viewer viewer)
        {
            if (!PurchaseHelper.TryGetPawn(viewer.username, out _pawn))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.NoPawn".Localize());

                return(false);
            }

            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));

            if (!worker.TryGetNextAsItem(out ArgWorker.ItemProxy item) || !item.IsValid())
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidItemQuery".LocalizeKeyed(item?.Thing?.Name ?? worker.GetLast()));

                return(false);
            }

            _buyableItem = item.Thing;

            if (item.TryGetError(out string error))
            {
                MessageHelper.ReplyToUser(viewer.username, error);

                return(false);
            }

            if (!worker.TryGetNextAsInt(out _amount, 1, viewer.GetMaximumPurchaseAmount(_buyableItem.Cost)))
            {
                _amount = 1;
            }

            if (!PurchaseHelper.TryMultiply(_buyableItem.Cost, _amount, out int cost))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.Overflowed".Localize());

                return(false);
            }

            if (!viewer.CanAfford(cost))
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InsufficientBalance".LocalizeKeyed(cost.ToString("N0"), viewer.GetViewerCoins().ToString("N0")));

                return(false);
            }

            List <ResearchProjectDef> prerequisites = item.Thing.Thing.GetUnfinishedPrerequisites();

            if (BuyItemSettings.mustResearchFirst && prerequisites.Count > 0)
            {
                MessageHelper.ReplyToUser(
                    viewer.username,
                    "TKUtils.ResearchRequired".LocalizeKeyed(item.Thing.Thing.LabelCap.RawText, prerequisites.Select(p => p.LabelCap.RawText).SectionJoin())
                    );

                return(false);
            }

            foreach (IUsabilityHandler h in CompatRegistry.AllUsabilityHandlers)
            {
                if (!h.IsUsable(item.Thing.Thing))
                {
                    continue;
                }

                _handler = h;

                break;
            }

            if (_handler == null || item.Thing.ItemData?.IsUsable != true)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.DisabledItem".Localize());

                return(false);
            }

            _buyableItem = item !.Thing;

            return(true);
        }
Esempio n. 17
0
        public override bool CanHappen(string msg, [NotNull] Viewer viewer)
        {
            var worker = ArgWorker.CreateInstance(CommandFilter.Parse(msg).Skip(2));

            if (!PurchaseHelper.TryGetPawn(viewer.username, out Pawn pawn) || !pawn !.Spawned)
            {
                return(false);
            }

            if (!worker.TryGetNextAsItem(out ArgWorker.ItemProxy proxy) || !proxy.IsValid() || proxy !.Thing.Thing.race != null)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.InvalidItemQuery".LocalizeKeyed(worker.GetLast()));

                return(false);
            }

            if (proxy.TryGetError(out string error))
            {
                MessageHelper.ReplyToUser(viewer.username, error);

                return(false);
            }

            if (!worker.TryGetNextAsInt(out int amount, 1, viewer.GetMaximumPurchaseAmount(proxy !.Thing.Cost)))
            {
                amount = 1;
            }

            if (PurchaseHelper.TryGetUnfinishedPrerequisites(proxy.Thing.Thing, out List <ResearchProjectDef> projects))
            {
                MessageHelper.ReplyToUser(
                    viewer.username,
                    "TKUtils.ResearchRequired".LocalizeKeyed(proxy.Thing.Thing !.LabelCap.RawText, projects.Select(p => p.LabelCap.RawText).SectionJoin())
                    );

                return(false);
            }

            if (worker.GetLast().Equals("*"))
            {
                amount = viewer.GetMaximumPurchaseAmount(proxy.Thing.Cost);
            }

            if (proxy.Thing.ItemData?.HasQuantityLimit == true)
            {
                amount = Mathf.Clamp(amount, 1, proxy.Thing.ItemData.QuantityLimit);
            }

            _purchaseRequest = new PurchaseBackpackRequest {
                Proxy = proxy, Quantity = amount, Purchaser = viewer, Pawn = pawn
            };

            if (_purchaseRequest.Price < ToolkitSettings.MinimumPurchasePrice)
            {
                MessageHelper.ReplyToUser(
                    viewer.username,
                    "TKUtils.Item.MinimumViolation".LocalizeKeyed(_purchaseRequest.Price.ToString("N0"), ToolkitSettings.MinimumPurchasePrice.ToString("N0"))
                    );

                return(false);
            }

            if (_purchaseRequest.Overflowed)
            {
                MessageHelper.ReplyToUser(viewer.username, "TKUtils.Overflowed".Localize());

                return(false);
            }

            if (viewer.CanAfford(_purchaseRequest.Price))
            {
                return(_purchaseRequest.Map != null);
            }

            MessageHelper.ReplyToUser(
                viewer.username,
                "TKUtils.InsufficientBalance".LocalizeKeyed(_purchaseRequest.Price.ToString("N0"), viewer.GetViewerCoins().ToString("N0"))
                );

            return(false);
        }