diff --git a/src/dumper/dumper.cs b/src/dumper/dumper.cs index fc1e1db..67e183a 100644 --- a/src/dumper/dumper.cs +++ b/src/dumper/dumper.cs @@ -53,6 +53,13 @@ struct CustomizationItemInfo public ECustomizationCategory category; } +struct AddonInfo +{ + public string id { get; set; } + public string name { get; set; } + public string iconFilePath { get; set; } + public EPlayerRole role { get; set; } +} class Dumper { private DefaultFileProvider? _provider; @@ -65,6 +72,7 @@ class Dumper private readonly Dictionary _itemMap = new(); private readonly Dictionary _offeringMap = new(); private readonly Dictionary _customizationItemMap = new(); + private readonly Dictionary _addonMap = new(); public Dumper(string outDir) { @@ -193,6 +201,37 @@ class Dumper WriteJson("items", _itemMap.Values); } + public void DumpAddons() + { + ProcessDataTables("/ItemAddonDB.uasset", "addons", (rowKey, props) => + { + if (!TryGetProp(props, "Role", out EPlayerRole role) + || !TryGetProp(props, "UIData", out FStructFallback uiDataFb) + || !TryGetProp(props, "Inventory", out bool isInventory) + || !TryGetProp(props, "IsFakeItem", out bool isFakeItem)) + throw new KeyNotFoundException($"Required properties missing for Addon: {rowKey}"); + + UIDataStruct uiData = uiDataFb.MapToStruct(); + + if (!isInventory || isFakeItem) + return; + + if (uiData.IconAssetList.Length == 0) + throw new InvalidDataException("Addon's UIData had no icons"); + + _addonMap[rowKey] = new AddonInfo + { + id = rowKey, + name = uiData.DisplayName.ToString(), + iconFilePath = uiData.IconAssetList[0].ToString(), + role = role + }; + }); + + _log.Info("Dumped {0} addons", _addonMap.Count); + WriteJson("addons", _addonMap.Values); + } + public void DumpOfferings() { ProcessDataTables("/OfferingDB.uasset", "offerings", (rowKey, props) => @@ -291,6 +330,7 @@ class Dumper public void DumpCharacterIcons() => ExportIcons(_characterMap.Values.Select(x => x.iconFilePath), "character", "/character-icons/"); public void DumpItemIcons() => ExportIcons(_itemMap.Values.Select(x => x.iconFilePath), "item", "/item-icons/"); + public void DumpAddonIcons() => ExportIcons(_addonMap.Values.Select(x => x.iconFilePath), "addon", "/addon-icons/"); public void DumpOfferingIcons() => ExportIcons(_offeringMap.Values.Select(x => x.iconFilePath), "offering", "/offering-icons/"); public void DumpCustomizationIcons() { diff --git a/src/dumper/main.cs b/src/dumper/main.cs index b941348..f25af96 100644 --- a/src/dumper/main.cs +++ b/src/dumper/main.cs @@ -14,8 +14,9 @@ var dumpTasks = new (string Name, Action Execute)[] { ("character", () => { dumper.DumpCharacters(); dumper.DumpCharacterIcons(); }), ("item", () => { dumper.DumpItems(); dumper.DumpItemIcons(); }), + ("addon", () => { dumper.DumpAddons(); dumper.DumpAddonIcons(); }), ("offering", () => { dumper.DumpOfferings(); dumper.DumpOfferingIcons(); }), - ("customizations", () => { dumper.DumpCustomizations(); dumper.DumpCustomizationIcons(); }), + ("customization", () => { dumper.DumpCustomizations(); dumper.DumpCustomizationIcons(); }), ("dlc", () => { dumper.DumpDLCs(); }) };