Beispiel #1
0
        public void Read(SellCancelMail mail)
        {
            var avatarAddress   = States.Instance.CurrentAvatarState.address;
            var attachment      = (SellCancellation.Result)mail.attachment;
            var itemBase        = attachment.itemUsable ?? (ItemBase)attachment.costume;
            var nonFungibleItem = attachment.itemUsable ?? (INonFungibleItem)attachment.costume;
            //TODO 관련 기획이 끝나면 별도 UI를 생성
            var popup = Find <ItemCountAndPricePopup>();
            var model = new UI.Model.ItemCountAndPricePopup();

            model.TitleText.Value         = L10nManager.Localize("UI_RETRIEVE");
            model.InfoText.Value          = L10nManager.Localize("UI_SELL_CANCEL_INFO");
            model.PriceInteractable.Value = false;
            model.Price.Value             = attachment.shopItem.Price;
            model.CountEnabled.Value      = false;
            model.Item.Value = new CountEditableItem(itemBase, 1, 1, 1);
            model.OnClickSubmit.Subscribe(_ =>
            {
                LocalLayerModifier.AddItem(avatarAddress, nonFungibleItem.ItemId, false);
                LocalLayerModifier.RemoveNewAttachmentMail(avatarAddress, mail.id);
                popup.Close();
            }).AddTo(gameObject);
            model.OnClickCancel.Subscribe(_ =>
            {
                //TODO 재판매 처리추가되야함\
                LocalLayerModifier.AddItem(avatarAddress, nonFungibleItem.ItemId, false);
                LocalLayerModifier.RemoveNewAttachmentMail(avatarAddress, mail.id);
                popup.Close();
            }).AddTo(gameObject);
            popup.Pop(model);
        }
        private void RapidCombination()
        {
            LocalLayerModifier.RemoveItem(States.Instance.CurrentAvatarState.address, _row.ItemId,
                                          _cost);
            var blockIndex = Game.Game.instance.Agent.BlockIndex;

            LocalLayerModifier.UnlockCombinationSlot(_slotIndex, blockIndex);
            var slotAddress = States.Instance.CurrentAvatarState.address.Derive(
                string.Format(
                    CultureInfo.InvariantCulture,
                    CombinationSlotState.DeriveFormat,
                    _slotIndex
                    )
                );
            var slotState = States.Instance.CombinationSlotStates[slotAddress];
            var result    = (CombinationConsumable.ResultModel)slotState.Result;

            LocalLayerModifier.AddNewResultAttachmentMail(
                States.Instance.CurrentAvatarState.address, result.id, blockIndex);
            var format = L10nManager.Localize("NOTIFICATION_COMBINATION_COMPLETE");

            Notification.Push(
                MailType.Workshop,
                string.Format(CultureInfo.InvariantCulture, format,
                              result.itemUsable.GetLocalizedName())
                );
            Notification.CancelReserve(result.itemUsable.ItemId);
            Game.Game.instance.ActionManager.RapidCombination(_slotIndex);
        }
Beispiel #3
0
        public IObservable <ActionBase.ActionEvaluation <ItemEnhancement> > ItemEnhancement(
            Guid itemId,
            Guid materialId,
            int slotIndex)
        {
            var avatarAddress = States.Instance.CurrentAvatarState.address;

            // NOTE: 장착했는지 안 했는지에 상관없이 해제 플래그를 걸어 둔다.
            LocalLayerModifier.SetItemEquip(avatarAddress, itemId, false, false);
            LocalLayerModifier.SetItemEquip(avatarAddress, materialId, false, false);

            var action = new ItemEnhancement
            {
                itemId        = itemId,
                materialId    = materialId,
                avatarAddress = avatarAddress,
                slotIndex     = slotIndex,
            };

            ProcessAction(action);

            return(_renderer.EveryRender <ItemEnhancement>()
                   .Where(eval => eval.Action.Id.Equals(action.Id))
                   .Take(1)
                   .Last()
                   .ObserveOnMainThread()
                   .Timeout(ActionTimeout)
                   .DoOnError(e => HandleException(action.Id, e)));
        }
        private void DailyReward()
        {
            _renderer.EveryRender <DailyReward>()
            .Where(ValidateEvaluationForCurrentAgent)
            .ObserveOnMainThread()
            .Subscribe(eval =>
            {
                LocalLayer.Instance
                .ClearAvatarModifiers <AvatarDailyRewardReceivedIndexModifier>(
                    eval.Action.avatarAddress);

                UpdateCurrentAvatarState(eval);

                if (eval.Exception is null)
                {
                    UI.Notification.Push(
                        Nekoyume.Model.Mail.MailType.System,
                        L10nManager.Localize("UI_RECEIVED_DAILY_REWARD"));
                    var avatarAddress = eval.Action.avatarAddress;
                    var itemId        = eval.Action.dailyRewardResult.materials.First().Key.ItemId;
                    var itemCount     = eval.Action.dailyRewardResult.materials.First().Value;
                    LocalLayerModifier.RemoveItem(avatarAddress, itemId, itemCount);
                    LocalLayerModifier.AddNewAttachmentMail(avatarAddress, eval.Action.dailyRewardResult.id);
                    WidgetHandler.Instance.Menu.SetActiveActionPointLoading(false);
                }
            }).AddTo(_disposables);
        }
Beispiel #5
0
        private IEnumerator CoGetDailyRewardAnimation()
        {
            var blockCount = Game.Game.instance.Agent.BlockIndex -
                             States.Instance.CurrentAvatarState.dailyRewardReceivedIndex + 1;

            LocalLayerModifier.IncreaseAvatarDailyRewardReceivedIndex(
                States.Instance.CurrentAvatarState.address,
                blockCount);
            animator.SetTrigger(GetReward);
            VFXController.instance.Create <ItemMoveVFX>(boxImageTransform.position);

            if (actionPoint != null)
            {
                ItemMoveAnimation.Show(actionPoint.Image.sprite,
                                       boxImageTransform.position,
                                       actionPoint.Image.transform.position,
                                       Vector2.one,
                                       true,
                                       true,
                                       1f,
                                       0.8f);

                yield return(new WaitForSeconds(1.5f));
            }
        }
Beispiel #6
0
        private static void UpdateLocalState(int questId, Dictionary <int, int> rewards)
        {
            if (rewards is null)
            {
                var sb = new StringBuilder($"[{nameof(CelebratesPopup)}]");
                sb.Append($"Argument {nameof(rewards)} is null.");
                Debug.LogError(sb.ToString());
                return;
            }

            var avatarAddress = States.Instance.CurrentAvatarState.address;

            foreach (var reward in rewards)
            {
                var materialRow = Game.Game.instance.TableSheets.MaterialItemSheet
                                  .First(pair => pair.Key == reward.Key);

                LocalLayerModifier.AddItem(
                    avatarAddress,
                    materialRow.Value.ItemId,
                    reward.Value,
                    false);
            }

            LocalLayerModifier.RemoveReceivableQuest(avatarAddress, questId);
        }
Beispiel #7
0
        private void ResponseUnrenderItemEnhancement(ActionBase.ActionEvaluation <ItemEnhancement5> eval)
        {
            var agentAddress  = eval.Signer;
            var avatarAddress = eval.Action.avatarAddress;
            var slot          = eval.OutputStates.GetCombinationSlotState(avatarAddress, eval.Action.slotIndex);
            var result        = (ItemEnhancement.ResultModel)slot.Result;
            var itemUsable    = result.itemUsable;
            var avatarState   = eval.OutputStates.GetAvatarState(avatarAddress);

            // NOTE: 사용한 자원에 대한 레이어 다시 추가하기.
            LocalLayerModifier.ModifyAgentGold(agentAddress, -result.gold);
            LocalLayerModifier.RemoveItem(avatarAddress, itemUsable.ItemId);
            foreach (var itemId in result.materialItemIdList)
            {
                // NOTE: 최종적으로 UpdateCurrentAvatarState()를 호출한다면, 그곳에서 상태를 새로 설정할 것이다.
                LocalLayerModifier.RemoveItem(avatarAddress, itemId);
            }

            // NOTE: 메일 레이어 다시 없애기.
            LocalLayerModifier.AddItem(avatarAddress, itemUsable.ItemId, false);
            LocalLayerModifier.RemoveNewAttachmentMail(avatarAddress, result.id);

            // NOTE: 워크샵 슬롯의 모든 휘발성 상태 변경자를 다시 추가하기.
            var otherItemId = result.materialItemIdList.First();

            LocalLayerModifier.ModifyCombinationSlotItemEnhancement(
                itemUsable.ItemId,
                otherItemId,
                eval.Action.slotIndex);

            UpdateAgentState(eval);
            UpdateCurrentAvatarState(eval);
            UpdateCombinationSlotState(slot);
            UnrenderQuest(avatarAddress, avatarState.questList.completedQuestIds);
        }
Beispiel #8
0
        public void Read(CombinationMail mail)
        {
            var avatarAddress   = States.Instance.CurrentAvatarState.address;
            var attachment      = (CombinationConsumable.ResultModel)mail.attachment;
            var itemBase        = attachment.itemUsable ?? (ItemBase)attachment.costume;
            var nonFungibleItem = attachment.itemUsable ?? (INonFungibleItem)attachment.costume;
            var popup           = Find <CombinationResultPopup>();
            var materialItems   = attachment.materials
                                  .Select(pair => new { pair, item = pair.Key })
                                  .Select(t => new CombinationMaterial(
                                              t.item,
                                              t.pair.Value,
                                              t.pair.Value,
                                              t.pair.Value))
                                  .ToList();
            var model = new UI.Model.CombinationResultPopup(new CountableItem(itemBase, 1))
            {
                isSuccess     = true,
                materialItems = materialItems
            };

            model.OnClickSubmit.Subscribe(_ =>
            {
                LocalLayerModifier.AddItem(avatarAddress, nonFungibleItem.ItemId, false);
                LocalLayerModifier.RemoveNewAttachmentMail(avatarAddress, mail.id, false);
                LocalLayerModifier.RemoveAttachmentResult(avatarAddress, mail.id);
                LocalLayerModifier.ModifyAvatarItemRequiredIndex(
                    avatarAddress,
                    nonFungibleItem.ItemId,
                    Game.Game.instance.Agent.BlockIndex);
            });
            popup.Pop(model);
        }
        private void ResponseItemEnhancement(ActionBase.ActionEvaluation <ItemEnhancement> eval)
        {
            if (eval.Exception is null)
            {
                var agentAddress  = eval.Signer;
                var avatarAddress = eval.Action.avatarAddress;
                var slot          = eval.OutputStates.GetCombinationSlotState(avatarAddress, eval.Action.slotIndex);
                var result        = (ItemEnhancement.ResultModel)slot.Result;
                var itemUsable    = result.itemUsable;
                var avatarState   = eval.OutputStates.GetAvatarState(avatarAddress);

                // NOTE: 사용한 자원에 대한 레이어 벗기기.
                LocalLayerModifier.ModifyAgentGold(agentAddress, result.gold);
                LocalLayerModifier.AddItem(avatarAddress, itemUsable.ItemId, false);
                foreach (var itemId in result.materialItemIdList)
                {
                    // NOTE: 최종적으로 UpdateCurrentAvatarState()를 호출한다면, 그곳에서 상태를 새로 설정할 것이다.
                    LocalLayerModifier.AddItem(avatarAddress, itemId, false);
                }

                // NOTE: 메일 레이어 씌우기.
                LocalLayerModifier.RemoveItem(avatarAddress, itemUsable.ItemId);
                LocalLayerModifier.AddNewAttachmentMail(avatarAddress, result.id);

                // NOTE: 워크샵 슬롯의 모든 휘발성 상태 변경자를 제거하기.
                LocalLayerModifier.ResetCombinationSlot(slot);

                // NOTE: 노티 예약 걸기.
                var format = L10nManager.Localize("NOTIFICATION_ITEM_ENHANCEMENT_COMPLETE");
                UI.Notification.Reserve(
                    MailType.Workshop,
                    string.Format(format, result.itemUsable.GetLocalizedName()),
                    slot.UnlockBlockIndex,
                    result.itemUsable.ItemId);

                //[TentuPlay] 장비강화, 골드사용
                //Local에서 변경하는 States.Instance 보다는 블락에서 꺼내온 eval.OutputStates를 사용
                if (eval.OutputStates.TryGetGoldBalance(agentAddress, GoldCurrency, out var outAgentBalance))
                {
                    var total = outAgentBalance -
                                new FungibleAssetValue(outAgentBalance.Currency, result.gold, 0);
                    new TPStashEvent().CharacterCurrencyUse(
                        player_uuid: agentAddress.ToHex(),
                        character_uuid: States.Instance.CurrentAvatarState.address.ToHex().Substring(0, 4),
                        currency_slug: "gold",
                        currency_quantity: (float)result.gold,
                        currency_total_quantity: float.Parse(total.GetQuantityString()),
                        reference_entity: entity.Items, //강화가 가능하므로 장비
                        reference_category_slug: "item_enhancement",
                        reference_slug: itemUsable.Id.ToString());
                }

                UpdateAgentState(eval);
                UpdateCurrentAvatarState(eval);
                UpdateCombinationSlotState(slot);
                RenderQuest(avatarAddress, avatarState.questList.completedQuestIds);
            }
        }
Beispiel #10
0
        public void Read(SellerMail sellerMail)
        {
            var agentAddress  = States.Instance.AgentState.address;
            var avatarAddress = States.Instance.CurrentAvatarState.address;
            var attachment    = (Buy.SellerResult)sellerMail.attachment;

            //TODO 관련 기획이 끝나면 별도 UI를 생성
            LocalLayerModifier.ModifyAgentGold(agentAddress, attachment.gold);
            LocalLayerModifier.RemoveNewAttachmentMail(avatarAddress, sellerMail.id);
        }
Beispiel #11
0
        // TODO: QuestPreparation.Quest(bool repeat) 와 로직이 흡사하기 때문에 정리할 여지가 있습니다.
        private void HackAndSlash(int stageId)
        {
            var sheets   = Game.Game.instance.TableSheets;
            var stageRow = sheets.StageSheet.OrderedList.FirstOrDefault(row => row.Id == stageId);

            if (stageRow is null)
            {
                return;
            }

            var requiredCost = stageRow.CostAP;

            if (States.Instance.CurrentAvatarState.actionPoint < requiredCost)
            {
                // NOTE: AP가 부족합니다.
                return;
            }

            if (!sheets.WorldSheet.TryGetByStageId(stageId, out var worldRow))
            {
                return;
            }

            var worldId = worldRow.Id;

            Find <BottomMenu>().Close(true);
            Find <LoadingScreen>().Show();

            var stage = Game.Game.instance.Stage;

            stage.isExitReserved = false;
            stage.repeatStage    = false;
            var player = stage.GetPlayer();

            player.StartRun();
            ActionCamera.instance.ChaseX(player.transform);
            ActionRenderHandler.Instance.Pending = true;
            Game.Game.instance.ActionManager
            .HackAndSlash(player, worldId, stageId)
            .Subscribe(_ =>
            {
                LocalLayerModifier.ModifyAvatarActionPoint(
                    States.Instance.CurrentAvatarState.address,
                    requiredCost);
            }, e => ActionRenderHandler.BackToMain(false, e))
            .AddTo(this);
            LocalLayerModifier.ModifyAvatarActionPoint(States.Instance.CurrentAvatarState.address,
                                                       -requiredCost);
            var props = new Value
            {
                ["StageID"] = stageId,
            };

            Mixpanel.Track("Unity/Click Guided Quest Enter Dungeon", props);
        }
        private void ResponseCombinationConsumable(ActionBase.ActionEvaluation <CombinationConsumable> eval)
        {
            if (eval.Exception is null)
            {
                var agentAddress  = eval.Signer;
                var avatarAddress = eval.Action.AvatarAddress;
                var slot          = eval.OutputStates.GetCombinationSlotState(avatarAddress, eval.Action.slotIndex);
                var result        = (CombinationConsumable.ResultModel)slot.Result;
                var itemUsable    = result.itemUsable;
                var avatarState   = eval.OutputStates.GetAvatarState(avatarAddress);

                LocalLayerModifier.ModifyAgentGold(agentAddress, result.gold);
                LocalLayerModifier.ModifyAvatarActionPoint(avatarAddress, result.actionPoint);
                foreach (var pair in result.materials)
                {
                    // NOTE: 최종적으로 UpdateCurrentAvatarState()를 호출한다면, 그곳에서 상태를 새로 설정할 것이다.
                    LocalLayerModifier.AddItem(avatarAddress, pair.Key.ItemId, pair.Value, false);
                }

                LocalLayerModifier.RemoveItem(avatarAddress, itemUsable.ItemId);
                LocalLayerModifier.AddNewAttachmentMail(avatarAddress, result.id);
                LocalLayerModifier.ResetCombinationSlot(slot);

                var format = L10nManager.Localize("NOTIFICATION_COMBINATION_COMPLETE");
                UI.Notification.Reserve(
                    MailType.Workshop,
                    string.Format(format, result.itemUsable.GetLocalizedName()),
                    slot.UnlockBlockIndex,
                    result.itemUsable.ItemId
                    );
                AnalyticsManager.Instance.OnEvent(AnalyticsManager.EventName.ActionCombinationSuccess);

                //[TentuPlay] Consumable 합성에 사용한 골드 기록
                //Local에서 변경하는 States.Instance 보다는 블락에서 꺼내온 eval.OutputStates를 사용
                if (eval.OutputStates.TryGetGoldBalance(agentAddress, GoldCurrency, out var balance))
                {
                    var total = balance - new FungibleAssetValue(balance.Currency, result.gold, 0);
                    new TPStashEvent().CharacterCurrencyUse(
                        player_uuid: agentAddress.ToHex(),
                        character_uuid: States.Instance.CurrentAvatarState.address.ToHex().Substring(0, 4),
                        currency_slug: "gold",
                        currency_quantity: (float)result.gold,
                        currency_total_quantity: float.Parse(total.GetQuantityString()),
                        reference_entity: entity.Items,
                        reference_category_slug: "consumables_combination",
                        reference_slug: result.itemUsable.Id.ToString());
                }

                UpdateAgentState(eval);
                UpdateCurrentAvatarState(eval);
                UpdateCombinationSlotState(slot);
                RenderQuest(avatarAddress, avatarState.questList.completedQuestIds);
            }
        }
 private void ResponseChargeActionPoint(ActionBase.ActionEvaluation <ChargeActionPoint> eval)
 {
     if (eval.Exception is null)
     {
         var avatarAddress = eval.Action.avatarAddress;
         LocalLayerModifier.ModifyAvatarActionPoint(avatarAddress, -States.Instance.GameConfigState.ActionPointMax);
         var row = Game.Game.instance.TableSheets.MaterialItemSheet.Values.First(r =>
                                                                                 r.ItemSubType == ItemSubType.ApStone);
         LocalLayerModifier.AddItem(avatarAddress, row.ItemId, 1);
         UpdateCurrentAvatarState(eval);
     }
 }
Beispiel #14
0
        private void LocalStateItemEquipModify(ItemBase itemBase, bool equip)
        {
            if (!(itemBase is INonFungibleItem nonFungibleItem))
            {
                return;
            }

            LocalLayerModifier.SetItemEquip(
                States.Instance.CurrentAvatarState.address,
                nonFungibleItem.ItemId,
                equip);
        }
Beispiel #15
0
        public void UnrenderQuest(Address avatarAddress, IEnumerable <int> ids)
        {
            foreach (var id in ids)
            {
                LocalLayerModifier.RemoveReceivableQuest(avatarAddress, id);

                var currentAvatarState = States.Instance.CurrentAvatarState;
                if (currentAvatarState.address != avatarAddress)
                {
                    continue;
                }
            }
        }
Beispiel #16
0
        private void ResponseSell(ActionBase.ActionEvaluation <Sell3> eval)
        {
            if (!(eval.Exception is null))
            {
                return;
            }

            var avatarAddress = eval.Action.sellerAvatarAddress;
            var itemId        = eval.Action.itemId;

            LocalLayerModifier.RemoveItem(avatarAddress, itemId);
            UpdateCurrentAvatarState(eval);
        }
Beispiel #17
0
 private static void ChargeActionPoint(CountableItem item)
 {
     if (item.ItemBase.Value is Nekoyume.Model.Item.Material material)
     {
         Notification.Push(Nekoyume.Model.Mail.MailType.System,
                           L10nManager.Localize("UI_CHARGE_AP"));
         Game.Game.instance.ActionManager.ChargeActionPoint();
         LocalLayerModifier.RemoveItem(States.Instance.CurrentAvatarState.address,
                                       material.ItemId, 1);
         LocalLayerModifier.ModifyAvatarActionPoint(
             States.Instance.CurrentAvatarState.address,
             States.Instance.GameConfigState.ActionPointMax);
     }
 }
Beispiel #18
0
        private void ResponseSellCancellation(ActionBase.ActionEvaluation <SellCancellation4> eval)
        {
            if (!(eval.Exception is null))
            {
                return;
            }

            var result          = eval.Action.result;
            var nonFungibleItem = result.itemUsable ?? (INonFungibleItem)result.costume;
            var avatarAddress   = eval.Action.sellerAvatarAddress;
            var itemId          = nonFungibleItem.ItemId;

            LocalLayerModifier.AddItem(avatarAddress, itemId);
            UpdateCurrentAvatarState(eval);
        }
Beispiel #19
0
        private void ResponseDailyReward(ActionBase.ActionEvaluation <DailyReward> eval)
        {
            if (!(eval.Exception is null))
            {
                return;
            }

            var avatarAddress = eval.Action.avatarAddress;
            var itemId        = eval.Action.dailyRewardResult.materials.First().Key.ItemId;
            var itemCount     = eval.Action.dailyRewardResult.materials.First().Value;

            LocalLayerModifier.AddItem(avatarAddress, itemId, itemCount);
            UpdateCurrentAvatarState(eval);

            WidgetHandler.Instance.Menu.SetActiveActionPointLoading(true);
        }
        private void ResponseSellCancellation(ActionBase.ActionEvaluation <SellCancellation4> eval)
        {
            if (eval.Exception is null)
            {
                var avatarAddress   = eval.Action.sellerAvatarAddress;
                var result          = eval.Action.result;
                var nonFungibleItem = result.itemUsable ?? (INonFungibleItem)result.costume;
                var itemBase        = result.itemUsable ?? (ItemBase)result.costume;

                LocalLayerModifier.RemoveItem(avatarAddress, nonFungibleItem.ItemId);
                LocalLayerModifier.AddNewAttachmentMail(avatarAddress, result.id);
                var format = L10nManager.Localize("NOTIFICATION_SELL_CANCEL_COMPLETE");
                UI.Notification.Push(MailType.Auction, string.Format(format, itemBase.GetLocalizedName()));
                UpdateCurrentAvatarState(eval);
            }
        }
Beispiel #21
0
        private void ResponseBuy(ActionBase.ActionEvaluation <Buy4> eval)
        {
            if (!(eval.Exception is null))
            {
                return;
            }

            var        buyerAvatarAddress = eval.Action.buyerAvatarAddress;
            var        price = eval.Action.sellerResult.shopItem.Price;
            Address    renderQuestAvatarAddress;
            List <int> renderQuestCompletedQuestIds;

            if (buyerAvatarAddress == States.Instance.CurrentAvatarState.address)
            {
                var buyerAgentAddress = States.Instance.AgentState.address;
                var result            = eval.Action.buyerResult;

                var itemId      = result.itemUsable?.ItemId ?? result.costume.ItemId;
                var buyerAvatar = eval.OutputStates.GetAvatarState(buyerAvatarAddress);

                LocalLayerModifier.ModifyAgentGold(buyerAgentAddress, -price);
                LocalLayerModifier.AddItem(buyerAvatarAddress, itemId);
                LocalLayerModifier.RemoveNewAttachmentMail(buyerAvatarAddress, result.id);

                renderQuestAvatarAddress     = buyerAvatarAddress;
                renderQuestCompletedQuestIds = buyerAvatar.questList.completedQuestIds;
            }
            else
            {
                var sellerAvatarAddress = eval.Action.sellerAvatarAddress;
                var sellerAgentAddress  = eval.Action.sellerAgentAddress;
                var result       = eval.Action.sellerResult;
                var gold         = result.gold;
                var sellerAvatar = eval.OutputStates.GetAvatarState(sellerAvatarAddress);

                LocalLayerModifier.ModifyAgentGold(sellerAgentAddress, gold);
                LocalLayerModifier.RemoveNewAttachmentMail(sellerAvatarAddress, result.id);

                renderQuestAvatarAddress     = sellerAvatarAddress;
                renderQuestCompletedQuestIds = sellerAvatar.questList.completedQuestIds;
            }

            UpdateAgentState(eval);
            UpdateCurrentAvatarState(eval);
            UnrenderQuest(renderQuestAvatarAddress, renderQuestCompletedQuestIds);
        }
        private void UpdateCurrentAvatarState()
        {
            _blockRenderer.EveryBlock()
            .ObserveOnMainThread()
            .Subscribe(_ =>
            {
                IAgent agent              = Game.Game.instance.Agent;
                ShopState shop            = States.Instance.ShopState;
                AvatarState avatar        = States.Instance.CurrentAvatarState;
                List <ShopItem> shopItems = new List <ShopItem>();
                bool replace              = false;

                if (!(avatar is null))
                {
                    shopItems = shop.Products.Values.Where(r =>
                                                           r.SellerAvatarAddress == avatar.address && r.ExpiredBlockIndex != 0 &&
                                                           r.ExpiredBlockIndex <= agent.BlockIndex).ToList();
                }

                if (!shopItems.Any())
                {
                    return;
                }

                var avatarState = new AvatarState((Dictionary)agent.GetState(avatar.address));
                List <SellCancelMail> sellCancelMails = avatarState.mailBox.OfType <SellCancelMail>().ToList();
                int prevCount = _mailRecords.Count;
                foreach (var mail in shopItems.Select(shopItem => sellCancelMails.FirstOrDefault(m =>
                                                                                                 ((SellCancellation.Result)m.attachment).shopItem.ProductId == shopItem.ProductId))
                         .Where(mail => !(mail is null) && !_mailRecords.Contains(mail.id)))
                {
                    _mailRecords.Add(mail.id);
                    LocalLayerModifier.AddNewAttachmentMail(avatar.address, mail.id);
                }

                if (_mailRecords.Count > prevCount)
                {
                    States.Instance.AddOrReplaceAvatarState(avatarState, States.Instance.CurrentAvatarKey);
                }
            })
            .AddTo(_disposables);
        }
Beispiel #23
0
        public void Read(DailyRewardMail dailyRewardMail)
        {
            var avatarAddress = States.Instance.CurrentAvatarState.address;
            var attachment    = (DailyReward.DailyRewardResult)dailyRewardMail.attachment;
            var popup         = Find <DailyRewardItemPopup>();
            var materials     = attachment.materials;
            var material      = materials.First();

            var model = new UI.Model.ItemCountConfirmPopup();

            model.TitleText.Value = L10nManager.Localize("UI_DAILY_REWARD_POPUP_TITLE");
            model.Item.Value      = new CountEditableItem(material.Key, material.Value, material.Value, material.Value);
            model.OnClickSubmit.Subscribe(_ =>
            {
                LocalLayerModifier.AddItem(avatarAddress, material.Key.ItemId, material.Value, false);
                LocalLayerModifier.RemoveNewAttachmentMail(avatarAddress, dailyRewardMail.id);
                popup.Close();
            }).AddTo(gameObject);
            popup.Pop(model);
        }
Beispiel #24
0
        private void ResponseSell()
        {
            var avatarAddress = States.Instance.CurrentAvatarState.address;

            var item = SharedModel.ItemCountAndPricePopup.Value.Item.Value;

            SharedModel.ItemCountAndPricePopup.Value.Item.Value = null;

            if (!(item.ItemBase.Value is INonFungibleItem nonFungibleItem))
            {
                return;
            }

            LocalLayerModifier.RemoveItem(avatarAddress, nonFungibleItem.ItemId);
            AudioController.instance.PlaySfx(AudioController.SfxCode.InputItem);
            var format = L10nManager.Localize("NOTIFICATION_SELL_START");

            Notification.Push(MailType.Auction,
                              string.Format(format, item.ItemBase.Value.GetLocalizedName()));
        }
Beispiel #25
0
        public void Read(ItemEnhanceMail itemEnhanceMail)
        {
            var avatarAddress   = States.Instance.CurrentAvatarState.address;
            var attachment      = (ItemEnhancement.ResultModel)itemEnhanceMail.attachment;
            var popup           = Find <CombinationResultPopup>();
            var itemBase        = attachment.itemUsable ?? (ItemBase)attachment.costume;
            var nonFungibleItem = attachment.itemUsable ?? (INonFungibleItem)attachment.costume;
            var model           = new UI.Model.CombinationResultPopup(new CountableItem(itemBase, 1))
            {
                isSuccess     = true,
                materialItems = new List <CombinationMaterial>()
            };

            model.OnClickSubmit.Subscribe(_ =>
            {
                LocalLayerModifier.AddItem(avatarAddress, nonFungibleItem.ItemId, false);
                LocalLayerModifier.RemoveNewAttachmentMail(avatarAddress, itemEnhanceMail.id);
            });
            popup.Pop(model);
        }
        private void ResponseRapidCombination(ActionBase.ActionEvaluation <RapidCombination2> eval)
        {
            var avatarAddress = eval.Action.avatarAddress;
            var slot          =
                eval.OutputStates.GetCombinationSlotState(avatarAddress, eval.Action.slotIndex);
            var result = (RapidCombination.ResultModel)slot.Result;

            foreach (var pair in result.cost)
            {
                // NOTE: 최종적으로 UpdateCurrentAvatarState()를 호출한다면, 그곳에서 상태를 새로 설정할 것이다.
                LocalLayerModifier.AddItem(avatarAddress, pair.Key.ItemId, pair.Value, false);
            }
            LocalLayerModifier.RemoveAvatarItemRequiredIndex(avatarAddress, result.itemUsable.ItemId);
            LocalLayerModifier.ResetCombinationSlot(slot);

            AnalyticsManager.Instance.OnEvent(AnalyticsManager.EventName.ActionCombinationSuccess);

            //[TentuPlay] RapidCombinationConsumable 합성에 사용한 골드 기록
            //Local에서 변경하는 States.Instance 보다는 블락에서 꺼내온 eval.OutputStates를 사용
            var agentAddress = eval.Signer;
            var qty          = eval.OutputStates.GetAvatarState(avatarAddress).inventory.Materials
                               .Count(i => i.ItemSubType == ItemSubType.Hourglass);
            var prevQty = eval.PreviousStates.GetAvatarState(avatarAddress).inventory.Materials
                          .Count(i => i.ItemSubType == ItemSubType.Hourglass);

            new TPStashEvent().CharacterItemUse(
                player_uuid: agentAddress.ToHex(),
                character_uuid: States.Instance.CurrentAvatarState.address.ToHex().Substring(0, 4),
                item_category: itemCategory.Consumable,
                item_slug: "hourglass",
                item_quantity: (float)(prevQty - qty),
                reference_entity: entity.Items,
                reference_category_slug: "consumables_rapid_combination",
                reference_slug: slot.Result.itemUsable.Id.ToString()
                );

            UpdateAgentState(eval);
            UpdateCurrentAvatarState(eval);
            UpdateCombinationSlotState(slot);
        }
        private void ResponseSell(ActionBase.ActionEvaluation <Sell> eval)
        {
            if (eval.Exception is null)
            {
                var avatarAddress = eval.Action.sellerAvatarAddress;
                var itemId        = eval.Action.itemId;

                // NOTE: 최종적으로 UpdateCurrentAvatarState()를 호출한다면, 그곳에서 상태를 새로 설정할 것이다.
                LocalLayerModifier.AddItem(avatarAddress, itemId, false);
                var format    = L10nManager.Localize("NOTIFICATION_SELL_COMPLETE");
                var shopState = new ShopState((Dictionary)eval.OutputStates.GetState(ShopState.Address));

                var shopItem = shopState.Products.Values.First(r =>
                {
                    var nonFungibleItem = r.ItemUsable ?? (INonFungibleItem)r.Costume;
                    return(nonFungibleItem.ItemId == itemId);
                });

                var itemBase = shopItem.ItemUsable ?? (ItemBase)shopItem.Costume;
                UI.Notification.Push(MailType.Auction, string.Format(format, itemBase.GetLocalizedName()));
                UpdateCurrentAvatarState(eval);
            }
        }
        public void RenderQuest(Address avatarAddress, IEnumerable <int> ids)
        {
            foreach (var id in ids)
            {
                LocalLayerModifier.AddReceivableQuest(avatarAddress, id);

                var currentAvatarState = States.Instance.CurrentAvatarState;
                if (currentAvatarState.address != avatarAddress)
                {
                    continue;
                }

                var quest     = currentAvatarState.questList.First(q => q.Id == id);
                var rewardMap = quest.Reward.ItemMap;

                foreach (var reward in rewardMap)
                {
                    var materialRow = Game.Game.instance.TableSheets.MaterialItemSheet
                                      .First(pair => pair.Key == reward.Key);

                    LocalLayerModifier.RemoveItem(avatarAddress, materialRow.Value.ItemId, reward.Value);
                }
            }
        }
Beispiel #29
0
        private void ResponseBuy(ShopItem shopItem)
        {
            SharedModel.ItemCountAndPricePopup.Value.Item.Value = null;

            var buyerAgentAddress = States.Instance.AgentState.address;
            var productId         = shopItem.ProductId.Value;

            LocalLayerModifier.ModifyAgentGold(buyerAgentAddress, -shopItem.Price.Value);
            try
            {
                States.Instance.ShopState.Unregister(productId);
            }
            catch (FailedToUnregisterInShopStateException e)
            {
                Debug.LogError(e.Message);
            }
            shopItems.SharedModel.RemoveItemSubTypeProduct(productId);

            AudioController.instance.PlaySfx(AudioController.SfxCode.BuyItem);
            var format = L10nManager.Localize("NOTIFICATION_BUY_START");

            Notification.Push(MailType.Auction,
                              string.Format(format, shopItem.ItemBase.Value.GetLocalizedName()));
        }
Beispiel #30
0
        public IObservable <ActionBase.ActionEvaluation <Sell> > Sell(INonFungibleItem item, FungibleAssetValue price)
        {
            var avatarAddress = States.Instance.CurrentAvatarState.address;

            // NOTE: 장착했는지 안 했는지에 상관없이 해제 플래그를 걸어 둔다.
            LocalLayerModifier.SetItemEquip(avatarAddress, item.ItemId, false, false);

            var action = new Sell
            {
                sellerAvatarAddress = avatarAddress,
                itemId = item.ItemId,
                price  = price
            };

            ProcessAction(action);

            return(_renderer.EveryRender <Sell>()
                   .Where(eval => eval.Action.Id.Equals(action.Id))
                   .Take(1)
                   .Last()
                   .ObserveOnMainThread()
                   .Timeout(ActionTimeout)
                   .DoOnError(e => HandleException(action.Id, e))); // Last() is for completion
        }