private static GachaContent HandleSmartGender(GachaMetadata gacha, Gender playerGender)
    {
        Random random = Random.Shared;
        int    index  = random.Next(gacha.Contents.Count);

        GachaContent contents = gacha.Contents[index];

        if (!contents.SmartGender)
        {
            return(contents);
        }

        Gender itemGender = ItemMetadataStorage.GetLimitMetadata(contents.ItemId).Gender;

        if (playerGender != itemGender || itemGender != Gender.Neutral) // if it's not the same gender or unisex, roll again
        {
            bool sameGender = false;
            do
            {
                int indexReroll = random.Next(gacha.Contents.Count);

                GachaContent rerollContents       = gacha.Contents[indexReroll];
                Gender       rerollContentsGender = ItemMetadataStorage.GetLimitMetadata(rerollContents.ItemId).Gender;

                if (rerollContentsGender == playerGender || rerollContentsGender == Gender.Neutral)
                {
                    return(rerollContents);
                }
            } while (!sameGender);
        }

        return(contents);
    }
        private static GachaContent HandleSmartGender(GachaMetadata gacha, byte playerGender)
        {
            Random random = RandomProvider.Get();
            int    index  = random.Next(gacha.Contents.Count);

            GachaContent contents = gacha.Contents[index];

            if (!contents.SmartGender)
            {
                return(contents);
            }

            byte itemGender = ItemMetadataStorage.GetGender(contents.ItemId);

            if (playerGender != itemGender || itemGender != 2)  // if it's not the same gender or unisex, roll again
            {
                bool sameGender = false;
                do
                {
                    int indexReroll = random.Next(gacha.Contents.Count);

                    GachaContent rerollContents       = gacha.Contents[indexReroll];
                    byte         rerollContentsGender = ItemMetadataStorage.GetGender(rerollContents.ItemId);

                    if (rerollContentsGender == playerGender || rerollContentsGender == 2)
                    {
                        return(rerollContents);
                    }
                } while (!sameGender);
            }
            return(contents);
        }
示例#3
0
    private void CreateNewStats(Item item)
    {
        Constants          = new();
        Statics            = new();
        Randoms            = new();
        Enchants           = new();
        LimitBreakEnchants = new();
        GemSockets         = new();
        if (item.Rarity is 0 or > 6)
        {
            return;
        }

        int   optionId          = ItemMetadataStorage.GetOptionMetadata(item.Id).OptionId;
        float optionLevelFactor = ItemMetadataStorage.GetOptionMetadata(item.Id).OptionLevelFactor;

        ConstantStats.GetStats(item, optionId, optionLevelFactor, out Dictionary <StatAttribute, ItemStat> constantStats);
        Constants = constantStats;
        StaticStats.GetStats(item, optionId, optionLevelFactor, out Dictionary <StatAttribute, ItemStat> staticStats);
        Statics = staticStats;
        RandomStats.GetStats(item, out Dictionary <StatAttribute, ItemStat> randomStats);
        Randoms = randomStats;
        if (item.EnchantLevel > 0)
        {
            Enchants = EnchantHelper.GetEnchantStats(item.EnchantLevel, item.Type, item.Level);
        }
        GetGemSockets(item, optionLevelFactor);
    }
示例#4
0
 public Item(int id)
 {
     Id               = id;
     Uid              = GuidGenerator.Long();
     InventoryTab     = ItemMetadataStorage.GetTab(id);
     ItemSlot         = ItemMetadataStorage.GetSlot(id);
     GemSlot          = ItemMetadataStorage.GetGem(id);
     Rarity           = ItemMetadataStorage.GetRarity(id);
     StackLimit       = ItemMetadataStorage.GetStackLimit(id);
     EnableBreak      = ItemMetadataStorage.GetEnableBreak(id);
     IsTwoHand        = ItemMetadataStorage.GetIsTwoHand(id);
     IsDress          = ItemMetadataStorage.GetIsDress(id);
     IsTemplate       = ItemMetadataStorage.GetIsTemplate(id);
     PlayCount        = ItemMetadataStorage.GetPlayCount(id);
     FileName         = ItemMetadataStorage.GetFileName(id);
     SkillId          = ItemMetadataStorage.GetSkillID(id);
     RecommendJobs    = ItemMetadataStorage.GetRecommendJobs(id);
     Content          = ItemMetadataStorage.GetContent(id);
     FunctionName     = ItemMetadataStorage.GetFunctionName(id);
     FunctionId       = ItemMetadataStorage.GetFunctionId(id);
     FunctionDuration = ItemMetadataStorage.GetFunctionDuration(id);
     FunctionFieldId  = ItemMetadataStorage.GetFunctionFieldId(id);
     FunctionCapacity = ItemMetadataStorage.GetFunctionCapacity(id);
     Slot             = -1;
     Amount           = 1;
     Stats            = new ItemStats(id, Rarity);
     CanRepackage     = true; // If false, item becomes untradable
 }
示例#5
0
        // Example: "item id:20000027"
        private static void ProcessItemCommand(GameSession session, string command)
        {
            Dictionary <string, string> config = command.ToMap();

            if (!int.TryParse(config.GetValueOrDefault("id", "20000027"), out int itemId))
            {
                return;
            }
            if (!ItemMetadataStorage.IsValid(itemId))
            {
                session.SendNotice("Invalid item: " + itemId);
                return;
            }

            _ = int.TryParse(config.GetValueOrDefault("rarity", "5"), out int rarity);
            _ = int.TryParse(config.GetValueOrDefault("amount", "1"), out int amount);

            Item item = new Item(itemId)
            {
                CreationTime = DateTimeOffset.UtcNow.ToUnixTimeSeconds(),
                TransferFlag = TransferFlag.Splitable | TransferFlag.Tradeable,
                PlayCount    = itemId.ToString().StartsWith("35") ? 10 : 0,
                Rarity       = rarity,
                Amount       = amount,
                Stats        = new ItemStats(itemId, rarity)
            };

            // Simulate looting item
            InventoryController.Add(session, item, true);
        }
示例#6
0
    public static List <Item> GetItemsFromDropGroup(DropGroupContent dropContent, Gender playerGender, Job job)
    {
        List <Item> items  = new();
        Random      rng    = RandomProvider.Get();
        int         amount = rng.Next((int)dropContent.MinAmount, (int)dropContent.MaxAmount);

        foreach (int id in dropContent.ItemIds)
        {
            if (dropContent.SmartGender)
            {
                Gender itemGender = ItemMetadataStorage.GetGender(id);
                if (itemGender != playerGender && itemGender is not Gender.Neutral)
                {
                    continue;
                }
            }

            List <Job> recommendJobs = ItemMetadataStorage.GetRecommendJobs(id);
            if (recommendJobs.Contains(job) || recommendJobs.Contains(Job.None))
            {
                Item newItem = new(id)
                {
                    Enchants = dropContent.EnchantLevel,
                    Amount   = amount,
                    Rarity   = dropContent.Rarity
                };
                items.Add(newItem);
            }
        }
        return(items);
    }
示例#7
0
    public static void GetStats(Item item, int optionId, float optionLevelFactor, out Dictionary <StatAttribute, ItemStat> staticStats)
    {
        staticStats = new();
        if (optionLevelFactor < 50)
        {
            return;
        }

        int staticId = ItemMetadataStorage.GetOptionMetadata(item.Id).Static;

        ItemOptionsStatic staticOptions = ItemOptionStaticMetadataStorage.GetMetadata(staticId, item.Rarity);

        if (staticOptions == null)
        {
            GetDefault(item, staticStats, optionId, optionLevelFactor);
            return;
        }

        foreach (ParserStat stat in staticOptions.Stats)
        {
            staticStats[stat.Attribute] = new BasicStat(stat);
        }

        foreach (ParserSpecialStat stat in staticOptions.SpecialStats)
        {
            staticStats[stat.Attribute] = new SpecialStat(stat);
        }

        // TODO: Implement Hidden ndd (defense) and wapmax (Max Weapon Attack)

        GetDefault(item, staticStats, optionId, optionLevelFactor);
    }
示例#8
0
 public Item(int id)
 {
     Id                    = id;
     Level                 = ItemMetadataStorage.GetLevel(id);
     Uid                   = GuidGenerator.Long();
     InventoryTab          = ItemMetadataStorage.GetTab(id);
     ItemSlot              = ItemMetadataStorage.GetSlot(id);
     GemSlot               = ItemMetadataStorage.GetGem(id);
     Rarity                = ItemMetadataStorage.GetRarity(id);
     StackLimit            = ItemMetadataStorage.GetStackLimit(id);
     EnableBreak           = ItemMetadataStorage.GetEnableBreak(id);
     IsTwoHand             = ItemMetadataStorage.GetIsTwoHand(id);
     IsDress               = ItemMetadataStorage.GetIsDress(id);
     IsTemplate            = ItemMetadataStorage.GetIsTemplate(id);
     IsCustomScore         = ItemMetadataStorage.GetIsCustomScore(id);
     Gender                = ItemMetadataStorage.GetGender(id);
     RemainingGlamorForges = ItemExtractionMetadataStorage.GetExtractionCount(id);
     PlayCount             = ItemMetadataStorage.GetPlayCount(id);
     FileName              = ItemMetadataStorage.GetFileName(id);
     SkillId               = ItemMetadataStorage.GetSkillID(id);
     RecommendJobs         = ItemMetadataStorage.GetRecommendJobs(id);
     Content               = ItemMetadataStorage.GetContent(id);
     Function              = ItemMetadataStorage.GetFunction(id);
     Tag                   = ItemMetadataStorage.GetTag(id);
     ShopID                = ItemMetadataStorage.GetShopID(id);
     Slot                  = -1;
     Amount                = 1;
     Score                 = new MusicScore();
     Stats                 = new ItemStats(id, Rarity, Level);
     Color                 = ItemMetadataStorage.GetEquipColor(id);
     CanRepackage          = true; // If false, item becomes untradable
 }
示例#9
0
        public override void Handle(GameSession session, PacketReader packet)
        {
            // [bow] Henesys 47 Bow - 15100216
            // [staff] Modded Student Staff - 15200223
            // [longsword] Sword of tria - 13200220
            // [shield] Shield of tria - 14100190
            // [greatsword] Riena - 15000224
            // [scepter] Saint Mushliel Mace - 13300219
            // [codex] Words of Saint mushliel - 14000181
            // [cannon] Cannon of beginnings - 15300199
            // [dagger] Walker knife - 13100225
            // [star] Rook's Star - 13400218
            // [blade] Runesteel Blade - 15400274
            // [knuckles] Pugilist knuckles - 15500514
            // [orb] Guidance training orb - 15600514

            int[] itemIds = new int[] { 15100216, 15200223, 13200220, 14100190, 15000224, 13300219, 14000181, 15300199, 13100225, 13400218, 15400274, 15500514, 15600514 };
            foreach (int id in itemIds)
            {
                ItemMetadata metadata = ItemMetadataStorage.GetMetadata(id);

                if (!metadata.RecommendJobs.Contains((int)session.Player.Job))
                {
                    continue;
                }

                Item item = new Item(id);
                if (session.Player.Job == Job.Thief || session.Player.Job == Job.Assassin)
                {
                    item.Amount = 2;
                }

                InventoryController.Add(session, item, true);
            }
        }
示例#10
0
        public static void GetConstantStats(int itemId, int rarity, out List <NormalStat> normalStats, out List <SpecialStat> specialStats)
        {
            normalStats  = new List <NormalStat>();
            specialStats = new List <SpecialStat>();

            // Get Constant Stats
            int constantId = ItemMetadataStorage.GetOptionConstant(itemId);
            ItemOptionsConstant basicOptions = ItemOptionConstantMetadataStorage.GetMetadata(constantId, rarity);

            if (basicOptions == null)
            {
                return;
            }

            foreach (ParserStat stat in basicOptions.Stats)
            {
                normalStats.Add(new NormalStat(stat.Id, stat.Flat, stat.Percent));
            }

            foreach (ParserSpecialStat stat in basicOptions.SpecialStats)
            {
                specialStats.Add(new SpecialStat(stat.Id, stat.Flat, stat.Percent));
            }

            if (basicOptions.HiddenDefenseAdd > 0)
            {
                AddHiddenNormalStat(normalStats, ItemAttribute.Defense, basicOptions.HiddenDefenseAdd, basicOptions.DefenseCalibrationFactor);
            }

            if (basicOptions.HiddenWeaponAtkAdd > 0)
            {
                AddHiddenNormalStat(normalStats, ItemAttribute.MinWeaponAtk, basicOptions.HiddenWeaponAtkAdd, basicOptions.WeaponAtkCalibrationFactor);
                AddHiddenNormalStat(normalStats, ItemAttribute.MaxWeaponAtk, basicOptions.HiddenWeaponAtkAdd, basicOptions.WeaponAtkCalibrationFactor);
            }
        }
示例#11
0
    public bool Remove(GameSession session, long uid, int amount, out Item outItem)
    {
        outItem = null;
        if (!session.Player.Account.BankInventory.Items.Any(x => x is not null && x.Uid == uid))
        {
            return(false);
        }

        int outItemIndex = Array.FindIndex(Items, 0, Items.Length, x => x is not null && x.Uid == uid);

        outItem = Items[outItemIndex];

        if (ItemMetadataStorage.IsTradeDisabledWithinAccount(outItem.Id) && outItem.IsBound() && !outItem.IsSelfBound(session.Player.CharacterId))
        {
            return(false);
        }

        if (amount >= outItem.Amount)
        {
            Items[outItemIndex] = null;
            session.Send(StorageInventoryPacket.Remove(uid));
            return(true);
        }

        if (outItem.TrySplit(amount, out Item splitItem))
        {
            session.Send(StorageInventoryPacket.UpdateItem(outItem));

            outItem = splitItem;
            return(true);
        }

        return(false);
    }
示例#12
0
    public Item(int id, bool saveToDatabase = true)
    {
        Id = id;
        SetMetadataValues();
        Name       = ItemMetadataStorage.GetName(id);
        Level      = ItemMetadataStorage.GetLevel(id);
        ItemSlot   = ItemMetadataStorage.GetSlot(id);
        IsTemplate = ItemMetadataStorage.GetIsTemplate(id);
        if (GemSlot == GemSlot.TRANS)
        {
            TransparencyBadgeBools = new byte[10];
        }

        Rarity                = ItemMetadataStorage.GetRarity(id);
        PlayCount             = ItemMetadataStorage.GetPlayCount(id);
        Color                 = ItemMetadataStorage.GetEquipColor(id);
        CreationTime          = TimeInfo.Now();
        RemainingGlamorForges = ItemExtractionMetadataStorage.GetExtractionCount(id);
        Slot   = -1;
        Amount = 1;
        Score  = new();
        Stats  = new(id, Rarity, ItemSlot, Level);
        if (saveToDatabase)
        {
            Uid = DatabaseManager.Items.Insert(this);
        }
    }
    private static void GetReward(GameSession session, string type, string id, string value, string count)
    {
        switch (type)
        {
        case "item":
            Item item = new(int.Parse(id), int.Parse(count), int.Parse(value));
            session.Player.Inventory.AddItem(session, item, true);
            break;

        case "genderItem":
            List <int> ids    = id.Split(",").Select(int.Parse).ToList();
            List <int> values = value.Split(",").Select(int.Parse).ToList();
            List <int> counts = count.Split(",").Select(int.Parse).ToList();
            for (int i = 0; i < ids.Count; i++)
            {
                Gender gender = ItemMetadataStorage.GetLimitMetadata(ids[i]).Gender;
                if (gender != session.Player.Gender)
                {
                    continue;
                }

                Item genderItem = new(ids[i], counts[i], values[i]);
                session.Player.Inventory.AddItem(session, genderItem, true);
            }
            break;

        case "additionalEffect":
            // TODO: Handle giving player buff
            break;

        default:
            return;
        }
    }
示例#14
0
        private static void HandleRandomHair(GameSession session, PacketReader packet)
        {
            int  shopId     = packet.ReadInt();
            bool useVoucher = packet.ReadBool();

            BeautyMetadata    beautyShop  = BeautyMetadataStorage.GetShopById(shopId);
            List <BeautyItem> beautyItems = BeautyMetadataStorage.GetGenderItems(beautyShop.ShopId, session.Player.Gender);

            if (!HandleShopPay(session, beautyShop, useVoucher))
            {
                return;
            }

            // Grab random hair
            Random     random     = new Random();
            int        indexHair  = random.Next(beautyItems.Count);
            BeautyItem chosenHair = beautyItems[indexHair];

            //Grab a preset hair and length of hair
            ItemMetadata beautyItemData = ItemMetadataStorage.GetMetadata(chosenHair.ItemId);
            int          indexPreset    = random.Next(beautyItemData.HairPresets.Count);
            HairPresets  chosenPreset   = beautyItemData.HairPresets[indexPreset];

            //Grab random front hair length
            double chosenFrontLength = random.NextDouble() *
                                       (beautyItemData.HairPresets[indexPreset].MaxScale - beautyItemData.HairPresets[indexPreset].MinScale) + beautyItemData.HairPresets[indexPreset].MinScale;

            //Grab random back hair length
            double chosenBackLength = random.NextDouble() *
                                      (beautyItemData.HairPresets[indexPreset].MaxScale - beautyItemData.HairPresets[indexPreset].MinScale) + beautyItemData.HairPresets[indexPreset].MinScale;

            // Grab random preset color
            ColorPaletteMetadata palette = ColorPaletteMetadataStorage.GetMetadata(2); // pick from palette 2. Seems like it's the correct palette for basic hair colors

            int        indexColor = random.Next(palette.DefaultColors.Count);
            MixedColor color      = palette.DefaultColors[indexColor];

            Dictionary <ItemSlot, Item> equippedInventory = session.Player.GetEquippedInventory(InventoryTab.Gear);

            Item newHair = new Item(chosenHair.ItemId)
            {
                Color      = EquipColor.Argb(color, indexColor, palette.PaletteId),
                HairD      = new HairData((float)chosenBackLength, (float)chosenFrontLength, chosenPreset.BackPositionCoord, chosenPreset.BackPositionRotation, chosenPreset.FrontPositionCoord, chosenPreset.FrontPositionRotation),
                IsTemplate = false
            };

            //Remove old hair
            if (session.Player.Equips.Remove(ItemSlot.HR, out Item previousHair))
            {
                previousHair.Slot = -1;
                session.Player.HairInventory.RandomHair = previousHair; // store the previous hair
                session.FieldManager.BroadcastPacket(EquipmentPacket.UnequipItem(session.FieldPlayer, previousHair));
            }

            equippedInventory[ItemSlot.HR] = newHair;

            session.FieldManager.BroadcastPacket(EquipmentPacket.EquipItem(session.FieldPlayer, newHair, ItemSlot.HR));
            session.Send(BeautyPacket.RandomHairOption(previousHair, newHair));
        }
示例#15
0
        public void GetStaticStats(int itemId, int rarity, List <NormalStat> normalStats, List <SpecialStat> specialStats)
        {
            //Get Static Stats
            int staticId = ItemMetadataStorage.GetOptionStatic(itemId);

            ItemOptionsStatic staticOptions = ItemOptionStaticMetadataStorage.GetMetadata(staticId, rarity);

            if (staticOptions == null)
            {
                BasicStats.AddRange(normalStats);
                BasicStats.AddRange(specialStats);
                return;
            }

            foreach (ParserStat stat in staticOptions.Stats)
            {
                NormalStat normalStat = normalStats.FirstOrDefault(x => x.ItemAttribute == stat.Id);
                if (normalStat == null)
                {
                    normalStats.Add(new NormalStat(stat.Id, stat.Flat, stat.Percent));
                    continue;
                }
                int   index         = normalStats.FindIndex(x => x.ItemAttribute == stat.Id);
                int   summedFlat    = normalStat.Flat + stat.Flat;
                float summedPercent = normalStat.Percent + stat.Percent;

                normalStats[index] = new NormalStat(stat.Id, summedFlat, summedPercent);
            }

            foreach (ParserSpecialStat stat in staticOptions.SpecialStats)
            {
                SpecialStat normalStat = specialStats.FirstOrDefault(x => x.ItemAttribute == stat.Id);
                if (normalStat == null)
                {
                    specialStats.Add(new SpecialStat(stat.Id, stat.Flat, stat.Percent));
                    continue;
                }

                int   index         = specialStats.FindIndex(x => x.ItemAttribute == stat.Id);
                float summedFlat    = normalStat.Flat + stat.Flat;
                float summedPercent = normalStat.Percent + stat.Percent;

                specialStats[index] = new SpecialStat(stat.Id, summedFlat, summedPercent);
            }

            if (staticOptions.HiddenDefenseAdd > 0)
            {
                AddHiddenNormalStat(normalStats, ItemAttribute.Defense, staticOptions.HiddenDefenseAdd, staticOptions.DefenseCalibrationFactor);
            }

            if (staticOptions.HiddenWeaponAtkAdd > 0)
            {
                AddHiddenNormalStat(normalStats, ItemAttribute.MinWeaponAtk, staticOptions.HiddenWeaponAtkAdd, staticOptions.WeaponAtkCalibrationFactor);
                AddHiddenNormalStat(normalStats, ItemAttribute.MaxWeaponAtk, staticOptions.HiddenWeaponAtkAdd, staticOptions.WeaponAtkCalibrationFactor);
            }

            BasicStats.AddRange(normalStats);
            BasicStats.AddRange(specialStats);
        }
示例#16
0
    // Returns index 0~7 for equip level 70-
    // Returns index 8~15 for equip level 70+
    private static int Roll(int itemId)
    {
        float  itemLevelFactor = ItemMetadataStorage.GetOptionMetadata(itemId).OptionLevelFactor;
        Random random          = Random.Shared;

        if (itemLevelFactor >= 70)
        {
            return(random.NextDouble() switch
            {
示例#17
0
        // Returns index 0~7 for equip level 70-
        // Returns index 8~15 for equip level 70+
        private static int Roll(int itemId)
        {
            int    itemLevelFactor = ItemMetadataStorage.GetOptionLevelFactor(itemId);
            Random random          = RandomProvider.Get();

            if (itemLevelFactor >= 70)
            {
                return(random.NextDouble() switch
                {
示例#18
0
        // Roll new bonus stats and values except the locked stat
        public static List <ItemStat> RollBonusStatsWithStatLocked(Item item, short ignoreStat, bool isSpecialStat)
        {
            int id = item.Id;

            int randomId = ItemMetadataStorage.GetOptionRandom(id);
            ItemOptionRandom randomOptions = ItemOptionRandomMetadataStorage.GetMetadata(randomId, item.Rarity);

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

            Random random = new Random();

            List <ItemStat> itemStats = new List <ItemStat>();

            List <ParserStat>        attributes        = isSpecialStat ? randomOptions.Stats : randomOptions.Stats.Where(x => (short)x.Id != ignoreStat).ToList();
            List <ParserSpecialStat> specialAttributes = isSpecialStat ? randomOptions.SpecialStats.Where(x => (short)x.Id != ignoreStat).ToList() : randomOptions.SpecialStats;

            foreach (ParserStat attribute in attributes)
            {
                Dictionary <ItemAttribute, List <ParserStat> > dictionary = GetRange(randomId);
                if (!dictionary.ContainsKey(attribute.Id))
                {
                    continue;
                }

                NormalStat normalStat = new NormalStat(dictionary[attribute.Id][Roll(id)]);
                if (randomOptions.MultiplyFactor > 0)
                {
                    normalStat.Flat    *= (int)Math.Ceiling(randomOptions.MultiplyFactor);
                    normalStat.Percent *= randomOptions.MultiplyFactor;
                }
                itemStats.Add(normalStat);
            }

            foreach (ParserSpecialStat attribute in specialAttributes)
            {
                Dictionary <SpecialItemAttribute, List <ParserSpecialStat> > dictionary = GetSpecialRange(randomId);
                if (!dictionary.ContainsKey(attribute.Id))
                {
                    continue;
                }

                SpecialStat specialStat = new SpecialStat(dictionary[attribute.Id][Roll(id)]);
                if (randomOptions.MultiplyFactor > 0)
                {
                    specialStat.Flat    *= (int)Math.Ceiling(randomOptions.MultiplyFactor);
                    specialStat.Percent *= randomOptions.MultiplyFactor;
                }
                itemStats.Add(specialStat);
            }

            return(itemStats.OrderBy(x => random.Next()).Take(item.Stats.BonusStats.Count).ToList());
        }
示例#19
0
 public Item(int id)
 {
     this.Id            = id;
     this.InventoryType = ItemMetadataStorage.GetTab(id);
     this.ItemSlot      = ItemMetadataStorage.GetSlot(id);
     this.SlotMax       = ItemMetadataStorage.GetSlotMax(id);
     this.IsTemplate    = ItemMetadataStorage.GetIsTemplate(id);
     this.Slot          = -1;
     this.Amount        = 1;
     this.Stats         = new ItemStats();
     this.CanRepackage  = true; // If false, item becomes untradable
 }
示例#20
0
    private void GetGemSockets(Item item, float optionLevelFactor)
    {
        // Check for predefined sockets
        int socketId = ItemMetadataStorage.GetPropertyMetadata(item.Id).SocketDataId;

        if (socketId != 0)
        {
            ItemSocketRarityData socketData = ItemSocketMetadataStorage.GetMetadata(socketId, item.Rarity);
            if (socketData is not null)
            {
                for (int i = 0; i < socketData.MaxCount; i++)
                {
                    GemSockets.Add(new());
                }

                for (int j = 0; j < socketData.FixedOpenCount; j++)
                {
                    GemSockets[j].IsUnlocked = true;
                }
                return;
            }
        }

        Script   script     = ScriptLoader.GetScript("Functions/calcItemSocketMaxCount");
        DynValue dynValue   = script.RunFunction("calcItemSocketMaxCount", (int)item.Type, item.Rarity, optionLevelFactor, (int)item.InventoryTab);
        int      slotAmount = (int)dynValue.Number;

        if (slotAmount <= 0)
        {
            return;
        }

        // add sockets
        for (int i = 0; i < slotAmount; i++)
        {
            GemSocket socket = new();
            GemSockets.Add(socket);
        }

        // roll to unlock sockets
        for (int i = 0; i < GemSockets.Count; i++)
        {
            int successNumber = Random.Shared.Next(0, 100);

            // 5% success rate to unlock a gemsocket
            if (successNumber < 95)
            {
                break;
            }
            GemSockets[i].IsUnlocked = true;
        }
    }
示例#21
0
        private static void ModifyBeauty(GameSession session, PacketReader packet, Item beautyItem)
        {
            ItemSlot itemSlot = ItemMetadataStorage.GetSlot(beautyItem.Id);
            Dictionary <ItemSlot, Item> cosmetics = session.Player.Inventory.Cosmetics;

            if (cosmetics.TryGetValue(itemSlot, out Item removeItem))
            {
                // Only remove if it isn't the same item
                if (removeItem.Uid != beautyItem.Uid)
                {
                    cosmetics.Remove(itemSlot);
                    removeItem.Slot = -1;
                    DatabaseManager.Items.Delete(removeItem.Uid);
                    session.FieldManager.BroadcastPacket(EquipmentPacket.UnequipItem(session.FieldPlayer, removeItem));
                }
            }

            // equip & update new item
            switch (itemSlot)
            {
            case ItemSlot.HR:
                float  backLength            = BitConverter.ToSingle(packet.Read(4), 0);
                CoordF backPositionCoord     = packet.Read <CoordF>();
                CoordF backPositionRotation  = packet.Read <CoordF>();
                float  frontLength           = BitConverter.ToSingle(packet.Read(4), 0);
                CoordF frontPositionCoord    = packet.Read <CoordF>();
                CoordF frontPositionRotation = packet.Read <CoordF>();

                beautyItem.HairData = new HairData(backLength, frontLength, backPositionCoord, backPositionRotation, frontPositionCoord, frontPositionRotation);

                cosmetics[itemSlot] = beautyItem;

                session.FieldManager.BroadcastPacket(EquipmentPacket.EquipItem(session.FieldPlayer, beautyItem, itemSlot));
                break;

            case ItemSlot.FA:
                cosmetics[itemSlot] = beautyItem;

                session.FieldManager.BroadcastPacket(EquipmentPacket.EquipItem(session.FieldPlayer, beautyItem, itemSlot));
                break;

            case ItemSlot.FD:
                byte[] faceDecorationPosition = packet.Read(16);

                beautyItem.FaceDecorationData = faceDecorationPosition;

                cosmetics[itemSlot] = beautyItem;

                session.FieldManager.BroadcastPacket(EquipmentPacket.EquipItem(session.FieldPlayer, beautyItem, itemSlot));
                break;
            }
        }
示例#22
0
    public static void GiveItemFromSelectBox(GameSession session, Item sourceItem, int index)
    {
        SelectItemBox    box      = sourceItem.Function.SelectItemBox;
        ItemDropMetadata metadata = ItemDropMetadataStorage.GetItemDropMetadata(box.BoxId);

        if (metadata == null)
        {
            session.Send(NoticePacket.Notice("No items found", NoticeType.Chat));
            return;
        }

        Inventory inventory = session.Player.Inventory;

        inventory.ConsumeItem(session, sourceItem.Uid, 1);

        // Select boxes disregards group ID. Adding these all to a filtered list
        List <DropGroupContent> dropContentsList = new();

        foreach (DropGroup group in metadata.DropGroups)
        {
            foreach (DropGroupContent dropGroupContent in group.Contents)
            {
                if (dropGroupContent.SmartDropRate == 100)
                {
                    List <Job> recommendJobs = ItemMetadataStorage.GetRecommendJobs(dropGroupContent.ItemIds.First());
                    if (recommendJobs.Contains(session.Player.Job) || recommendJobs.Contains(Job.None))
                    {
                        dropContentsList.Add(dropGroupContent);
                    }
                    continue;
                }
                dropContentsList.Add(dropGroupContent);
            }
        }

        DropGroupContent dropContents = dropContentsList[index];

        Random rng    = RandomProvider.Get();
        int    amount = rng.Next((int)dropContents.MinAmount, (int)dropContents.MaxAmount);

        foreach (int id in dropContents.ItemIds)
        {
            Item newItem = new(id)
            {
                Enchants = dropContents.EnchantLevel,
                Amount   = amount,
                Rarity   = dropContents.Rarity
            };
            inventory.AddItem(session, newItem, true);
        }
    }
        // Example: "item id:20000027"
        private static void ProcessItemCommand(GameSession session, string command)
        {
            Dictionary <string, string> config = command.ToMap();

            if (!int.TryParse(config.GetValueOrDefault("id", "20000027"), out int itemId))
            {
                return;
            }
            if (!ItemMetadataStorage.IsValid(itemId))
            {
                session.SendNotice("Invalid item: " + itemId);
                return;
            }

            // Add some bonus attributes to equips and pets
            ItemStats stats = new ItemStats();

            if (ItemMetadataStorage.GetTab(itemId) == InventoryTab.Gear ||
                ItemMetadataStorage.GetTab(itemId) == InventoryTab.Pets)
            {
                Random rng = new Random();
                stats.BonusAttributes.Add(ItemStat.Of((ItemAttribute)rng.Next(35), 0.01f));
                stats.BonusAttributes.Add(ItemStat.Of((ItemAttribute)rng.Next(35), 0.01f));
            }

            Item item = new Item(itemId)
            {
                CreationTime = DateTimeOffset.UtcNow.ToUnixTimeSeconds(),
                TransferFlag = TransferFlag.Splitable | TransferFlag.Tradeable,
                Stats        = stats,
                PlayCount    = itemId.ToString().StartsWith("35") ? 10 : 0
            };

            if (int.TryParse(config.GetValueOrDefault("rarity", "5"), out int rarity))
            {
                item.Rarity = rarity;
            }
            if (int.TryParse(config.GetValueOrDefault("amount", "1"), out int amount))
            {
                item.Amount = amount;
            }

            // Simulate looting item
            InventoryController.Add(session, item, true);

            /*if (session.Player.Inventory.Add(item))
             * {
             *  session.Send(ItemInventoryPacket.Add(item));
             *  session.Send(ItemInventoryPacket.MarkItemNew(item, item.Amount));
             * }*/
        }
示例#24
0
        private static void ModifyBeauty(GameSession session, PacketReader packet, Item beautyItem)
        {
            ItemSlot itemSlot = ItemMetadataStorage.GetSlot(beautyItem.Id);

            // remove current item
            if (session.Player.Equips.Remove(itemSlot, out Item removeItem))
            {
                removeItem.Slot = -1;
                session.FieldManager.BroadcastPacket(EquipmentPacket.UnequipItem(session.FieldPlayer, removeItem));
            }
            // equip new item

            Dictionary <ItemSlot, Item> equippedInventory = session.Player.GetEquippedInventory(InventoryTab.Gear);

            switch (itemSlot)
            {
            case ItemSlot.HR:
                float  backLength            = BitConverter.ToSingle(packet.Read(4), 0);
                CoordF backPositionCoord     = packet.Read <CoordF>();
                CoordF backPositionRotation  = packet.Read <CoordF>();
                float  frontLength           = BitConverter.ToSingle(packet.Read(4), 0);
                CoordF frontPositionCoord    = packet.Read <CoordF>();
                CoordF frontPositionRotation = packet.Read <CoordF>();

                beautyItem.HairD = new HairData(backLength, frontLength, backPositionCoord, backPositionRotation, frontPositionCoord, frontPositionRotation);

                equippedInventory[itemSlot] = beautyItem;

                session.FieldManager.BroadcastPacket(EquipmentPacket.EquipItem(session.FieldPlayer, beautyItem, itemSlot));
                break;

            case ItemSlot.FA:

                equippedInventory[itemSlot] = beautyItem;

                session.FieldManager.BroadcastPacket(EquipmentPacket.EquipItem(session.FieldPlayer, beautyItem, itemSlot));
                break;

            case ItemSlot.FD:
                byte[] faceDecorationPosition = packet.Read(16);

                beautyItem.FaceDecorationD = faceDecorationPosition;

                equippedInventory[itemSlot] = beautyItem;

                session.FieldManager.BroadcastPacket(EquipmentPacket.EquipItem(session.FieldPlayer, beautyItem, itemSlot));
                break;
            }
        }
    public IEnumerable <PremiumMarketItem> FindAllByCategory(MeretMarketSection section, MeretMarketCategory category, GenderFlag gender, JobFlag jobFlag, string searchString)
    {
        List <PremiumMarketItem> items   = new();
        IEnumerable <dynamic>    results = QueryFactory.Query(TableName).Get();

        if (section != MeretMarketSection.All)
        {
            results = QueryFactory.Query(TableName).Where("section", (int)section).Get();
        }

        foreach (dynamic data in results)
        {
            if (category != MeretMarketCategory.None && (MeretMarketCategory)data.category != category)
            {
                continue;
            }

            if (data.parent_market_id != 0)
            {
                continue;
            }
            PremiumMarketItem meretMarketItem = ReadMeretMarketItem(data);

            if (!meretMarketItem.ItemName.ToLower().Contains(searchString.ToLower()))
            {
                continue;
            }

            List <Job> jobs = ItemMetadataStorage.GetRecommendJobs(meretMarketItem.ItemId);
            if (!JobHelper.CheckJobFlagForJob(jobs, jobFlag))
            {
                continue;
            }

            if (!MeretMarketHelper.CheckGender(gender, meretMarketItem.ItemId))
            {
                continue;
            }

            if (meretMarketItem.BannerId != 0)
            {
                meretMarketItem.Banner = DatabaseManager.Banners.FindById(meretMarketItem.BannerId);
            }

            items.Add(meretMarketItem);
        }

        return(items);
    }
示例#26
0
 public Item(int id)
 {
     this.Id           = id;
     this.Uid          = GuidGenerator.Long();
     this.InventoryTab = ItemMetadataStorage.GetTab(id);
     this.ItemSlot     = ItemMetadataStorage.GetSlot(id);
     this.GemSlot      = ItemMetadataStorage.GetGem(id);
     this.Rarity       = ItemMetadataStorage.GetRarity(id);
     this.SlotMax      = ItemMetadataStorage.GetSlotMax(id);
     this.IsTemplate   = ItemMetadataStorage.GetIsTemplate(id);
     this.PlayCount    = ItemMetadataStorage.GetPlayCount(id);
     this.Content      = ItemMetadataStorage.GetContent(id);
     this.Slot         = -1;
     this.Amount       = 1;
     this.Stats        = new ItemStats();
     this.CanRepackage = true; // If false, item becomes untradable
 }
示例#27
0
 public Item(int id)
 {
     Id = id;
     SetMetadataValues(id);
     Level                 = ItemMetadataStorage.GetLevel(id);
     ItemSlot              = ItemMetadataStorage.GetSlot(id);
     Rarity                = ItemMetadataStorage.GetRarity(id);
     PlayCount             = ItemMetadataStorage.GetPlayCount(id);
     Color                 = ItemMetadataStorage.GetEquipColor(id);
     CreationTime          = DateTimeOffset.Now.ToUnixTimeSeconds();
     RemainingGlamorForges = ItemExtractionMetadataStorage.GetExtractionCount(id);
     Slot         = -1;
     Amount       = 1;
     Score        = new MusicScore();
     Stats        = new ItemStats(id, Rarity, Level, IsTwoHand);
     CanRepackage = true; // If false, item becomes untradable
     Uid          = DatabaseManager.AddItem(this);
 }
示例#28
0
    public List <UGCMarketItem> FindItemsByCategory(List <string> categories, GenderFlag genderFlag, JobFlag job, short sort)
    {
        List <UGCMarketItem> items = new();

        foreach (UGCMarketItem item in Items.Values)
        {
            if (!categories.Contains(item.Item.Category) || item.Status != UGCMarketListingStatus.Active)
            {
                continue;
            }

            // check job
            if (!JobHelper.CheckJobFlagForJob(item.Item.RecommendJobs, job))
            {
                continue;
            }

            // check gender
            Gender itemGender = ItemMetadataStorage.GetGender(item.Item.Id);
            if (!genderFlag.HasFlag(GenderFlag.Male) && !genderFlag.HasFlag(GenderFlag.Female))
            {
                Gender gender = genderFlag.HasFlag(GenderFlag.Male) ? Gender.Male : Gender.Female;
            }

            items.Add(item);
        }

        UGCMarketSort marketSort = (UGCMarketSort)sort;

        switch (marketSort)
        {
        // TODO: Handle Most Popular sorting.
        case UGCMarketSort.MostPopular:
        case UGCMarketSort.TopSeller:
            items = items.OrderByDescending(x => x.SalesCount).ToList();
            break;

        case UGCMarketSort.MostRecent:
            items = items.OrderByDescending(x => x.CreationTimestamp).ToList();
            break;
        }

        return(items);
    }
示例#29
0
    public static List <Item> GetItemsFromDropGroup(DropGroupContent dropContent, Player player, Item sourceItem)
    {
        List <Item> items  = new();
        Random      rng    = Random.Shared;
        int         amount = rng.Next((int)dropContent.MinAmount, (int)dropContent.MaxAmount);

        foreach (int id in dropContent.ItemIds)
        {
            if (dropContent.SmartDropRate == 100)
            {
                List <Job> recommendJobs = ItemMetadataStorage.GetRecommendJobs(id);
                if (!recommendJobs.Contains(player.Job) && !recommendJobs.Contains(Job.None))
                {
                    continue;
                }
            }

            if (dropContent.SmartGender)
            {
                Gender itemGender = ItemMetadataStorage.GetLimitMetadata(id).Gender;
                if (itemGender != player.Gender && itemGender is not Gender.Neutral)
                {
                    continue;
                }
            }


            int rarity   = dropContent.Rarity;
            int constant = ItemMetadataStorage.GetOptionMetadata(sourceItem.Id).Constant;
            if (rarity == 0 && constant is > 0 and < 7)
            {
                rarity = constant;
            }

            Item newItem = new(id, amount, rarity, saveToDatabase : false)
            {
                EnchantLevel = dropContent.EnchantLevel
            };
            newItem.Stats = new(newItem);
            items.Add(newItem);
        }

        return(items);
    }
示例#30
0
    public static void ChangeHair(GameSession session, int hairId, out Item previousHair, out Item newHair)
    {
        Random random = Random.Shared;

        //Grab a preset hair and length of hair
        ItemCustomizeMetadata customize = ItemMetadataStorage.GetMetadata(hairId).Customize;
        int         indexPreset         = random.Next(customize.HairPresets.Count);
        HairPresets chosenPreset        = customize.HairPresets[indexPreset];

        //Grab random front hair length
        double chosenFrontLength = random.NextDouble() *
                                   (customize.HairPresets[indexPreset].MaxScale - customize.HairPresets[indexPreset].MinScale) + customize.HairPresets[indexPreset].MinScale;

        //Grab random back hair length
        double chosenBackLength = random.NextDouble() *
                                  (customize.HairPresets[indexPreset].MaxScale - customize.HairPresets[indexPreset].MinScale) + customize.HairPresets[indexPreset].MinScale;

        // Grab random preset color
        ColorPaletteMetadata palette = ColorPaletteMetadataStorage.GetMetadata(2); // pick from palette 2. Seems like it's the correct palette for basic hair colors

        int        indexColor = random.Next(palette.DefaultColors.Count);
        MixedColor color      = palette.DefaultColors[indexColor];

        newHair = new(hairId)
        {
            Color              = EquipColor.Argb(color, indexColor, palette.PaletteId),
            HairData           = new((float)chosenBackLength, (float)chosenFrontLength, chosenPreset.BackPositionCoord, chosenPreset.BackPositionRotation, chosenPreset.FrontPositionCoord, chosenPreset.FrontPositionRotation),
            IsEquipped         = true,
            OwnerCharacterId   = session.Player.CharacterId,
            OwnerCharacterName = session.Player.Name
        };
        Dictionary <ItemSlot, Item> cosmetics = session.Player.Inventory.Cosmetics;

        //Remove old hair
        if (cosmetics.Remove(ItemSlot.HR, out previousHair))
        {
            previousHair.Slot = -1;
            session.Player.HairInventory.RandomHair = previousHair; // store the previous hair
            DatabaseManager.Items.Delete(previousHair.Uid);
            session.FieldManager.BroadcastPacket(EquipmentPacket.UnequipItem(session.Player.FieldPlayer, previousHair));
        }

        cosmetics[ItemSlot.HR] = newHair;
    }