mirror of
https://github.com/EggLinks/DanhengServer-OpenSource.git
synced 2026-01-02 20:26:03 +08:00
370 lines
10 KiB
C#
370 lines
10 KiB
C#
using EggLink.DanhengServer.Data;
|
|
using EggLink.DanhengServer.Data.Excel;
|
|
using EggLink.DanhengServer.Enums.Item;
|
|
using EggLink.DanhengServer.Proto;
|
|
using EggLink.DanhengServer.Util;
|
|
using SqlSugar;
|
|
|
|
namespace EggLink.DanhengServer.Database.Inventory;
|
|
|
|
[SugarTable("InventoryData")]
|
|
public class InventoryData : BaseDatabaseDataHelper
|
|
{
|
|
[SugarColumn(IsJson = true)] public List<ItemData> MaterialItems { get; set; } = [];
|
|
|
|
[SugarColumn(IsJson = true)] public List<ItemData> EquipmentItems { get; set; } = [];
|
|
|
|
[SugarColumn(IsJson = true)] public List<ItemData> RelicItems { get; set; } = [];
|
|
|
|
[SugarColumn(IsJson = true)] public Dictionary<int, RelicPlanData> RelicPlans { get; set; } = [];
|
|
|
|
public int NextUniqueId { get; set; } = 100;
|
|
}
|
|
|
|
public class ItemData
|
|
{
|
|
public int UniqueId { get; set; }
|
|
public int ItemId { get; set; }
|
|
public int Count { get; set; }
|
|
public int Level { get; set; }
|
|
public int Exp { get; set; }
|
|
public int TotalExp { get; set; }
|
|
public int Promotion { get; set; }
|
|
public int Rank { get; set; } // Superimpose
|
|
public bool Locked { get; set; }
|
|
public bool Discarded { get; set; }
|
|
|
|
public int MainAffix { get; set; }
|
|
public List<ItemSubAffix> SubAffixes { get; set; } = [];
|
|
public List<ItemSubAffix> ReforgeSubAffixes { get; set; } = [];
|
|
|
|
public int EquipAvatar { get; set; }
|
|
|
|
#region Action
|
|
|
|
public void AddRandomRelicMainAffix()
|
|
{
|
|
GameData.RelicConfigData.TryGetValue(ItemId, out var config);
|
|
if (config == null) return;
|
|
GameData.RelicMainAffixData.TryGetValue(config.MainAffixGroup, out var affixes);
|
|
if (affixes == null) return;
|
|
List<int> affixList = [];
|
|
affixList.AddRange(from affix in affixes.Values select affix.AffixID);
|
|
MainAffix = affixList.RandomElement();
|
|
}
|
|
|
|
public void AddRelicSubAffix(List<(int, int)> subAffixes)
|
|
{
|
|
GameData.RelicConfigData.TryGetValue(ItemId, out var config);
|
|
if (config == null) return;
|
|
|
|
var subAffixConfig = GameData.RelicSubAffixData[config.SubAffixGroup];
|
|
|
|
foreach (var (subId, subCnt) in subAffixes)
|
|
{
|
|
if (!subAffixConfig.TryGetValue(subId, out var excel)) continue;
|
|
SubAffixes.Add(new ItemSubAffix(excel, subCnt));
|
|
}
|
|
}
|
|
|
|
public void AddRandomRelicSubAffix(int count = 1)
|
|
{
|
|
if (count <= 0 || MainAffix == 0) return;
|
|
GameData.RelicConfigData.TryGetValue(ItemId, out var config);
|
|
if (config == null) return;
|
|
|
|
var mainAffixConfig = GameData.RelicMainAffixData[config.MainAffixGroup];
|
|
var mainProperty = mainAffixConfig[MainAffix].Property;
|
|
var subAffixConfig = GameData.RelicSubAffixData[config.SubAffixGroup];
|
|
var subAffixKeys = subAffixConfig.Keys.ToList();
|
|
|
|
while (count > 0)
|
|
{
|
|
var subId = subAffixKeys.RandomElement();
|
|
if (SubAffixes.Any(x => x.Id == subId)) continue;
|
|
if (subAffixConfig[subId] != null &&
|
|
subAffixConfig[subId].Property == mainProperty) continue;
|
|
|
|
SubAffixes.Add(new ItemSubAffix(subAffixConfig[subId], 1));
|
|
count--;
|
|
}
|
|
}
|
|
|
|
public void IncreaseRandomRelicSubAffix(int times = 1)
|
|
{
|
|
if (times <= 0) return;
|
|
GameData.RelicConfigData.TryGetValue(ItemId, out var config);
|
|
if (config == null) return;
|
|
GameData.RelicSubAffixData.TryGetValue(config.SubAffixGroup, out var affixes);
|
|
if (affixes == null) return;
|
|
|
|
for (var i = 0; i < times; i++)
|
|
{
|
|
var element = SubAffixes.RandomElement();
|
|
var affix = affixes.Values.ToList().Find(x => x.AffixID == element.Id);
|
|
if (affix == null) return;
|
|
element.IncreaseStep(affix.StepNum);
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Init relic sub affixes based on rarity
|
|
* 20% chance to get one more affix
|
|
* r3 1-2
|
|
* r4 2-3
|
|
* r5 3-4
|
|
*/
|
|
public void InitRandomRelicSubAffixesByRarity(ItemRarityEnum rarity = ItemRarityEnum.Unknown)
|
|
{
|
|
if (rarity == ItemRarityEnum.Unknown)
|
|
{
|
|
GameData.ItemConfigData.TryGetValue(ItemId, out var config);
|
|
if (config == null) return;
|
|
rarity = config.Rarity;
|
|
}
|
|
|
|
int initSubAffixesCount;
|
|
switch (rarity)
|
|
{
|
|
case ItemRarityEnum.Rare:
|
|
initSubAffixesCount = 1 + LuckyRelicSubAffixCount();
|
|
break;
|
|
case ItemRarityEnum.VeryRare:
|
|
initSubAffixesCount = 2 + LuckyRelicSubAffixCount();
|
|
break;
|
|
case ItemRarityEnum.SuperRare:
|
|
initSubAffixesCount = 3 + LuckyRelicSubAffixCount();
|
|
break;
|
|
default:
|
|
return;
|
|
}
|
|
|
|
AddRandomRelicSubAffix(initSubAffixesCount);
|
|
}
|
|
|
|
public int LuckyRelicSubAffixCount()
|
|
{
|
|
return Random.Shared.Next(100) < 20 ? 1 : 0;
|
|
}
|
|
|
|
#endregion
|
|
|
|
public int CalcTotalExpGained()
|
|
{
|
|
if (Level <= 0) return Exp;
|
|
GameData.RelicConfigData.TryGetValue(ItemId, out var costExcel);
|
|
if (costExcel == null) return 0;
|
|
var exp = 0;
|
|
for (var i = 0; i < Level; i++)
|
|
{
|
|
GameData.RelicExpTypeData.TryGetValue(costExcel.ExpType * 100 + i, out var typeExcel);
|
|
if (typeExcel != null)
|
|
exp += typeExcel.Exp;
|
|
}
|
|
|
|
return exp + Exp;
|
|
}
|
|
|
|
#region Serialization
|
|
|
|
public Material ToMaterialProto()
|
|
{
|
|
return new Material
|
|
{
|
|
Tid = (uint)ItemId,
|
|
Num = (uint)Count
|
|
};
|
|
}
|
|
|
|
public Relic ToRelicProto()
|
|
{
|
|
Relic relic = new()
|
|
{
|
|
Tid = (uint)ItemId,
|
|
UniqueId = (uint)UniqueId,
|
|
Level = (uint)Level,
|
|
IsProtected = Locked,
|
|
Exp = (uint)Exp,
|
|
IsDiscarded = Discarded,
|
|
DressAvatarId = (uint)EquipAvatar,
|
|
MainAffixId = (uint)MainAffix
|
|
};
|
|
if (SubAffixes.Count > 0)
|
|
foreach (var subAffix in SubAffixes)
|
|
relic.SubAffixList.Add(subAffix.ToProto());
|
|
if (ReforgeSubAffixes.Count > 0)
|
|
foreach (var subAffix in ReforgeSubAffixes)
|
|
relic.ReforgeSubAffixList.Add(subAffix.ToProto());
|
|
return relic;
|
|
}
|
|
|
|
public Equipment ToEquipmentProto()
|
|
{
|
|
return new Equipment
|
|
{
|
|
Tid = (uint)ItemId,
|
|
UniqueId = (uint)UniqueId,
|
|
Level = (uint)Level,
|
|
Exp = (uint)Exp,
|
|
IsProtected = Locked,
|
|
Promotion = (uint)Promotion,
|
|
Rank = (uint)Rank,
|
|
DressAvatarId = (uint)EquipAvatar
|
|
};
|
|
}
|
|
|
|
public ChallengeBossEquipmentInfo ToChallengeEquipmentProto()
|
|
{
|
|
return new ChallengeBossEquipmentInfo
|
|
{
|
|
Tid = (uint)ItemId,
|
|
UniqueId = (uint)UniqueId,
|
|
Level = (uint)Level,
|
|
Promotion = (uint)Promotion,
|
|
Rank = (uint)Rank
|
|
};
|
|
}
|
|
|
|
public ChallengeBossRelicInfo ToChallengeRelicProto()
|
|
{
|
|
var proto = new ChallengeBossRelicInfo
|
|
{
|
|
Tid = (uint)ItemId,
|
|
UniqueId = (uint)UniqueId,
|
|
Level = (uint)Level,
|
|
MainAffixId = (uint)MainAffix
|
|
};
|
|
|
|
if (SubAffixes.Count < 1) return proto;
|
|
foreach (var subAffix in SubAffixes)
|
|
proto.SubAffixList.Add(subAffix.ToProto());
|
|
|
|
return proto;
|
|
}
|
|
|
|
public Item ToProto()
|
|
{
|
|
return new Item
|
|
{
|
|
ItemId = (uint)ItemId,
|
|
Num = (uint)Count,
|
|
Level = (uint)Level,
|
|
MainAffixId = (uint)MainAffix,
|
|
Rank = (uint)Rank,
|
|
Promotion = (uint)Promotion,
|
|
UniqueId = (uint)UniqueId
|
|
};
|
|
}
|
|
|
|
public PileItem ToPileProto()
|
|
{
|
|
return new PileItem
|
|
{
|
|
ItemId = (uint)ItemId,
|
|
ItemNum = (uint)Count
|
|
};
|
|
}
|
|
|
|
public DisplayEquipmentInfo ToDisplayEquipmentProto()
|
|
{
|
|
return new DisplayEquipmentInfo
|
|
{
|
|
Tid = (uint)ItemId,
|
|
Level = (uint)Level,
|
|
Exp = (uint)Exp,
|
|
Promotion = (uint)Promotion,
|
|
Rank = (uint)Rank
|
|
};
|
|
}
|
|
|
|
public DisplayRelicInfo ToDisplayRelicProto()
|
|
{
|
|
DisplayRelicInfo relic = new()
|
|
{
|
|
Tid = (uint)ItemId,
|
|
Level = (uint)Level,
|
|
Type = (uint)GameData.RelicConfigData[ItemId].Type,
|
|
MainAffixId = (uint)MainAffix
|
|
};
|
|
|
|
if (SubAffixes.Count >= 1)
|
|
foreach (var subAffix in SubAffixes)
|
|
relic.SubAffixList.Add(subAffix.ToProto());
|
|
|
|
return relic;
|
|
}
|
|
|
|
public ItemData Clone()
|
|
{
|
|
return new ItemData
|
|
{
|
|
UniqueId = UniqueId,
|
|
ItemId = ItemId,
|
|
Count = Count,
|
|
Level = Level,
|
|
Exp = Exp,
|
|
TotalExp = TotalExp,
|
|
Promotion = Promotion,
|
|
Rank = Rank,
|
|
Locked = Locked,
|
|
Discarded = Discarded,
|
|
MainAffix = MainAffix,
|
|
SubAffixes = [.. SubAffixes.Select(x => x.Clone())],
|
|
ReforgeSubAffixes = [.. ReforgeSubAffixes.Select(x => x.Clone())],
|
|
EquipAvatar = EquipAvatar
|
|
};
|
|
}
|
|
|
|
#endregion
|
|
}
|
|
|
|
public class ItemSubAffix
|
|
{
|
|
public int Id { get; set; }
|
|
public int Count { get; set; }
|
|
public int Step { get; set; }
|
|
|
|
public ItemSubAffix()
|
|
{
|
|
}
|
|
|
|
public ItemSubAffix(RelicSubAffixConfigExcel excel, int count)
|
|
{
|
|
Id = excel.AffixID;
|
|
Count = count;
|
|
Step = Extensions.RandomInt(0, excel.StepNum * count + 1);
|
|
}
|
|
|
|
public void IncreaseStep(int stepNum)
|
|
{
|
|
Count++;
|
|
Step += Extensions.RandomInt(0, stepNum + 1);
|
|
}
|
|
|
|
public RelicAffix ToProto()
|
|
{
|
|
return new RelicAffix
|
|
{
|
|
AffixId = (uint)Id,
|
|
Cnt = (uint)Count,
|
|
Step = (uint)Step
|
|
};
|
|
}
|
|
|
|
public ItemSubAffix Clone()
|
|
{
|
|
return new ItemSubAffix
|
|
{
|
|
Id = Id,
|
|
Count = Count,
|
|
Step = Step
|
|
};
|
|
}
|
|
}
|
|
|
|
public class RelicPlanData
|
|
{
|
|
public int EquipAvatar { get; set; }
|
|
public List<int> InsideRelic { get; set; } = [];
|
|
public List<int> OutsideRelic { get; set; } = [];
|
|
} |