From f6574ae6043140b5dfa977ff2619477cf51824f2 Mon Sep 17 00:00:00 2001 From: Asriel Camora Date: Fri, 14 Jun 2024 13:21:04 -0700 Subject: [PATCH] C# 12 stuff & ExdSheets --- Craftimizer/Craftimizer.csproj | 3 +- Craftimizer/LuminaSheets.cs | 51 +----------------- Craftimizer/Plugin.cs | 2 +- Craftimizer/SimulatorUtils.cs | 8 ++- Craftimizer/Utils/CommunityMacros.cs | 5 +- Craftimizer/Utils/FoodStatus.cs | 8 +-- Craftimizer/Utils/FuzzyMatcher.cs | 2 +- Craftimizer/Utils/Gearsets.cs | 2 +- Craftimizer/Utils/MacroImport.cs | 13 ++--- Craftimizer/Utils/RecipeData.cs | 78 ++++++++++++---------------- Craftimizer/Utils/SynthesisValues.cs | 2 +- Craftimizer/Windows/MacroEditor.cs | 6 +-- Craftimizer/Windows/RecipeNote.cs | 8 ++- Craftimizer/packages.lock.json | 20 +++++-- 14 files changed, 77 insertions(+), 131 deletions(-) diff --git a/Craftimizer/Craftimizer.csproj b/Craftimizer/Craftimizer.csproj index 1f60295..0d7c145 100644 --- a/Craftimizer/Craftimizer.csproj +++ b/Craftimizer/Craftimizer.csproj @@ -39,8 +39,9 @@ + - + all runtime; build; native; contentfiles; analyzers; buildtransitive diff --git a/Craftimizer/LuminaSheets.cs b/Craftimizer/LuminaSheets.cs index 4485d83..7d04bb8 100644 --- a/Craftimizer/LuminaSheets.cs +++ b/Craftimizer/LuminaSheets.cs @@ -1,11 +1,9 @@ using Dalamud; +using ExdSheets; using Lumina; using Lumina.Data; using Lumina.Excel; -using Lumina.Excel.GeneratedSheets2; using System.Collections.Concurrent; -using Action = Lumina.Excel.GeneratedSheets2.Action; -using ItemFood = Lumina.Excel.GeneratedSheets.ItemFood; // BaseParam is too annoying with SoA namespace Craftimizer.Plugin; @@ -44,50 +42,3 @@ public static class LuminaSheets return parser.RowCount; } } - -#nullable disable - -[Sheet("SharlayanCraftWorksSupply", columnHash: 0x903b128e)] -public class SharlayanCraftWorksSupply : ExcelRow -{ - public class ItemData - { - public byte Level { get; set; } - public LazyRow Item { get; set; } - public ushort CollectabilityMid { get; set; } - public ushort CollectabilityHigh { get; set; } - public uint XPReward { get; set; } - public byte HighXPMultiplier { get; set; } - public ushort GilReward { get; set; } - public byte HighGilMultiplier { get; set; } - public byte Unknown8 { get; set; } - public byte ScripReward { get; set; } - public byte HighScripMultiplier { get; set; } - } - - public ItemData[] Items { get; set; } - - public override void PopulateData(RowParser parser, GameData gameData, Language language) - { - base.PopulateData(parser, gameData, language); - - Items = new ItemData[4]; - for (var i = 0; i < 4; i++) - { - Items[i] = new ItemData(); - Items[i].Level = parser.ReadColumn(0 * 4 + i); - Items[i].Item = new LazyRow(gameData, parser.ReadColumn(1 * 4 + i), language); - Items[i].CollectabilityMid = parser.ReadColumn(2 * 4 + i); - Items[i].CollectabilityHigh = parser.ReadColumn(3 * 4 + i); - Items[i].XPReward = parser.ReadColumn(4 * 4 + i); - Items[i].HighXPMultiplier = parser.ReadColumn(5 * 4 + i); - Items[i].GilReward = parser.ReadColumn(6 * 4 + i); - Items[i].HighGilMultiplier = parser.ReadColumn(7 * 4 + i); - Items[i].Unknown8 = parser.ReadColumn(8 * 4 + i); - Items[i].ScripReward = parser.ReadColumn(9 * 4 + i); - Items[i].HighScripMultiplier = parser.ReadColumn(10 * 4 + i); - } - } -} - -#nullable restore diff --git a/Craftimizer/Plugin.cs b/Craftimizer/Plugin.cs index 67809bf..4408443 100644 --- a/Craftimizer/Plugin.cs +++ b/Craftimizer/Plugin.cs @@ -124,7 +124,7 @@ public sealed class Plugin : IDalamudPlugin public void OpenEmptyMacroEditor() { var stats = GetDefaultStats(); - OpenMacroEditor(stats.Character, stats.Recipe, stats.Buffs, Enumerable.Empty(), null); + OpenMacroEditor(stats.Character, stats.Recipe, stats.Buffs, [], null); } public void OpenMacroEditor(CharacterStats characterStats, RecipeData recipeData, MacroEditor.CrafterBuffs buffs, IEnumerable actions, Action>? setter) diff --git a/Craftimizer/SimulatorUtils.cs b/Craftimizer/SimulatorUtils.cs index 2639641..ca2ffde 100644 --- a/Craftimizer/SimulatorUtils.cs +++ b/Craftimizer/SimulatorUtils.cs @@ -3,20 +3,18 @@ using Craftimizer.Simulator.Actions; using Dalamud.Game.Text.SeStringHandling.Payloads; using Dalamud.Interface.Internal; using Dalamud.Utility; -using FFXIVClientStructs.FFXIV.Client.Game; -using FFXIVClientStructs.FFXIV.Client.Game.Object; using FFXIVClientStructs.FFXIV.Client.Game.UI; -using Lumina.Excel.GeneratedSheets2; +using ExdSheets; using System; using System.Globalization; using System.Linq; using System.Numerics; using System.Text; -using Action = Lumina.Excel.GeneratedSheets2.Action; +using Action = ExdSheets.Action; using ActionType = Craftimizer.Simulator.Actions.ActionType; using ClassJob = Craftimizer.Simulator.ClassJob; using Condition = Craftimizer.Simulator.Condition; -using Status = Lumina.Excel.GeneratedSheets2.Status; +using Status = ExdSheets.Status; namespace Craftimizer.Plugin; diff --git a/Craftimizer/Utils/CommunityMacros.cs b/Craftimizer/Utils/CommunityMacros.cs index 29a357a..d85bab2 100644 --- a/Craftimizer/Utils/CommunityMacros.cs +++ b/Craftimizer/Utils/CommunityMacros.cs @@ -297,7 +297,7 @@ public sealed class CommunityMacros if (!string.IsNullOrEmpty(macro.Name)) { - if (Uri.TryCreate(macro.Name, UriKind.Relative, out var uri)) + if (Uri.TryCreate(macro.Name, UriKind.Relative, out _)) { var rotationId = macro.Name.Split('/')[^1]; if (!string.IsNullOrEmpty(rotationId)) @@ -474,8 +474,7 @@ public sealed class CommunityMacros private static async Task PostFromJsonAsync(HttpClient client, [StringSyntax(StringSyntaxAttribute.Uri)] string? requestUri, TRequest value, JsonSerializerOptions? options = null, CancellationToken cancellationToken = default) { - if (client is null) - throw new ArgumentNullException(nameof(client)); + ArgumentNullException.ThrowIfNull(client); var resp = client.PostAsJsonAsync(requestUri, value, options, cancellationToken); using var message = await resp.ConfigureAwait(false); diff --git a/Craftimizer/Utils/FoodStatus.cs b/Craftimizer/Utils/FoodStatus.cs index 8cf262c..ec87a45 100644 --- a/Craftimizer/Utils/FoodStatus.cs +++ b/Craftimizer/Utils/FoodStatus.cs @@ -1,6 +1,6 @@ using Craftimizer.Plugin; using Craftimizer.Plugin.Utils; -using Lumina.Excel.GeneratedSheets2; +using ExdSheets; using System.Collections.Frozen; using System.Collections.Generic; using System.Collections.Immutable; @@ -63,12 +63,12 @@ public static class FoodStatus continue; FoodStat? craftsmanship = null, control = null, cp = null; - foreach (var stat in itemFood.UnkData1) + foreach (var stat in itemFood.Params) { - if (stat.BaseParam == 0) + if (stat.BaseParam.Row == 0) continue; var foodStat = new FoodStat(stat.IsRelative, stat.Value, stat.Max, stat.ValueHQ, stat.MaxHQ); - switch ((uint)stat.BaseParam) + switch (stat.BaseParam.Row) { case Gearsets.ParamCraftsmanship: craftsmanship = foodStat; break; case Gearsets.ParamControl: control = foodStat; break; diff --git a/Craftimizer/Utils/FuzzyMatcher.cs b/Craftimizer/Utils/FuzzyMatcher.cs index 0613724..00913ef 100644 --- a/Craftimizer/Utils/FuzzyMatcher.cs +++ b/Craftimizer/Utils/FuzzyMatcher.cs @@ -50,7 +50,7 @@ internal readonly struct FuzzyMatcher if (wordStart >= 0) segments.Add((wordStart, span.Length - 1)); - return segments.ToArray(); + return [.. segments]; } public int Matches(string value) diff --git a/Craftimizer/Utils/Gearsets.cs b/Craftimizer/Utils/Gearsets.cs index 321753e..e1bad67 100644 --- a/Craftimizer/Utils/Gearsets.cs +++ b/Craftimizer/Utils/Gearsets.cs @@ -3,7 +3,7 @@ using Dalamud.Utility; using FFXIVClientStructs.FFXIV.Client.Game; using FFXIVClientStructs.FFXIV.Client.Game.UI; using FFXIVClientStructs.FFXIV.Client.UI.Misc; -using Lumina.Excel.GeneratedSheets2; +using ExdSheets; using System; using System.Linq; diff --git a/Craftimizer/Utils/MacroImport.cs b/Craftimizer/Utils/MacroImport.cs index 785cfde..f7d57dd 100644 --- a/Craftimizer/Utils/MacroImport.cs +++ b/Craftimizer/Utils/MacroImport.cs @@ -83,15 +83,12 @@ public static class MacroImport if (!TryParseUrl(url, out var uri)) throw new ArgumentException("Unsupported url", nameof(url)); - switch (uri.DnsSafeHost) + return uri.DnsSafeHost switch { - case "ffxivteamcraft.com": - return RetrieveTeamcraftUrl(uri, token); - case "craftingway.app": - return RetrieveCraftingwayUrl(uri, token); - default: - throw new UnreachableException("TryParseUrl should handle miscellaneous edge cases"); - } + "ffxivteamcraft.com" => RetrieveTeamcraftUrl(uri, token), + "craftingway.app" => RetrieveCraftingwayUrl(uri, token), + _ => throw new UnreachableException("TryParseUrl should handle miscellaneous edge cases"), + }; } private static async Task RetrieveTeamcraftUrl(Uri uri, CancellationToken token) diff --git a/Craftimizer/Utils/RecipeData.cs b/Craftimizer/Utils/RecipeData.cs index 03373be..6b8fb06 100644 --- a/Craftimizer/Utils/RecipeData.cs +++ b/Craftimizer/Utils/RecipeData.cs @@ -1,6 +1,7 @@ using Craftimizer.Plugin; using Craftimizer.Simulator; -using Lumina.Excel.GeneratedSheets2; +using ExdSheets; +using Lumina.Excel; using System; using System.Collections.Generic; using System.Linq; @@ -47,58 +48,47 @@ public sealed record RecipeData }; CollectableThresholds = null; - switch (Recipe.Unknown1) + if (Recipe.CollectableMetadata is LazyRow { Value: { } row }) + CollectableThresholds = new int?[] { row.LowCollectability, row.MidCollectability, row.HighCollectability }; + else if (Recipe.CollectableMetadata is LazyRow { Value: { } row2 }) { - case 1: - var data1 = LuminaSheets.CollectablesShopRefineSheet.GetRow(Recipe.Unknown0); - if (data1 == null) - break; - CollectableThresholds = new int?[] { data1.LowCollectability, data1.MidCollectability, data1.HighCollectability }; - break; - case 2: - var data2 = LuminaSheets.HWDCrafterSupplySheet.GetRow(Recipe.Unknown0); - if (data2 == null) - break; - foreach (var entry in data2.HWDCrafterSupplyParams) + foreach (var entry in row2.HWDCrafterSupplyParams) + { + if (entry.ItemTradeIn.Row == Recipe.ItemResult.Row) { - if (entry.ItemTradeIn.Row == Recipe.ItemResult.Row) - { - CollectableThresholds = new int?[] { entry.BaseCollectableRating, entry.MidCollectableRating, entry.HighCollectableRating }; - break; - } - } - break; - case 3: - var subRowCount = LuminaSheets.SatisfactionSupplySheet.GetSubRowCount(Recipe.Unknown0); - if (subRowCount is not { } subRowValue) + CollectableThresholds = new int?[] { entry.BaseCollectableRating, entry.MidCollectableRating, entry.HighCollectableRating }; break; + } + } + } + else if (Recipe.CollectableMetadata is LazyRow { } row4) + { + var subRowCount = LuminaSheets.SatisfactionSupplySheet.GetSubRowCount(row4.Row); + if (subRowCount is { } subRowValue) + { for (uint i = 0; i < subRowValue; ++i) { - var data3 = LuminaSheets.SatisfactionSupplySheet.GetRow(Recipe.Unknown0, i); - if (data3 == null) + var subRow = LuminaSheets.SatisfactionSupplySheet.GetRow(row4.Row, i); + if (subRow == null) continue; - if (data3.Item.Row == Recipe.ItemResult.Row) + if (subRow.Item.Row == Recipe.ItemResult.Row) { - CollectableThresholds = new int?[] { data3.CollectabilityLow, data3.CollectabilityMid, data3.CollectabilityHigh }; + CollectableThresholds = new int?[] { subRow.CollectabilityLow, subRow.CollectabilityMid, subRow.CollectabilityHigh }; break; } } - break; - case 4: - var data4 = LuminaSheets.SharlayanCraftWorksSupplySheet.GetRow(Recipe.Unknown0); - if (data4 == null) - break; - foreach (var item in data4.Items) + } + } + else if (Recipe.CollectableMetadata is LazyRow { Value: { } row5 }) + { + foreach (var item in row5.Item) + { + if (item.Id == Recipe.ItemResult.Row) { - if (item.Item.Row == Recipe.ItemResult.Row) - { - CollectableThresholds = new int?[] { null, item.CollectabilityMid, item.CollectabilityHigh }; - break; - } + CollectableThresholds = new int?[] { null, item.CollectabilityMid, item.CollectabilityHigh }; + break; } - break; - default: - break; + } } Ingredients = Recipe.Ingredient.Zip(Recipe.AmountIngredient) @@ -113,12 +103,10 @@ public sealed record RecipeData public int CalculateItemStartingQuality(int itemIdx, int amount) { - if (itemIdx >= Ingredients.Count) - throw new ArgumentOutOfRangeException(nameof(itemIdx)); + ArgumentOutOfRangeException.ThrowIfGreaterThanOrEqual(itemIdx, Ingredients.Count); var ingredient = Ingredients[itemIdx]; - if (amount > ingredient.Amount) - throw new ArgumentOutOfRangeException(nameof(amount)); + ArgumentOutOfRangeException.ThrowIfGreaterThan(amount, ingredient.Amount); if (!ingredient.Item.CanBeHq) return 0; diff --git a/Craftimizer/Utils/SynthesisValues.cs b/Craftimizer/Utils/SynthesisValues.cs index d3ad352..68e139b 100644 --- a/Craftimizer/Utils/SynthesisValues.cs +++ b/Craftimizer/Utils/SynthesisValues.cs @@ -67,7 +67,7 @@ internal sealed unsafe class SynthesisValues(AddonSynthesis* addon) var value = Values[i]; return value.Type switch { - ValueType.AllocatedString or + ValueType.ManagedString or ValueType.String => MemoryHelper.ReadSeStringNullTerminated((nint)value.String), _ => null diff --git a/Craftimizer/Windows/MacroEditor.cs b/Craftimizer/Windows/MacroEditor.cs index 2cfef5b..909f823 100644 --- a/Craftimizer/Windows/MacroEditor.cs +++ b/Craftimizer/Windows/MacroEditor.cs @@ -1060,12 +1060,12 @@ public sealed class MacroEditor : Window, IDisposable DynamicBars.Draw(datas); ImGui.TableNextColumn(); - datas = new List(3) - { + datas = + [ new("Progress", Colors.Progress, Reliability.Progress, State.Progress, RecipeData.RecipeInfo.MaxProgress), new("Quality", Colors.Quality, Reliability.Quality, State.Quality, RecipeData.RecipeInfo.MaxQuality), new("CP", Colors.CP, State.CP, CharacterStats.CP) - }; + ]; if (RecipeData.RecipeInfo.MaxQuality <= 0) datas.RemoveAt(1); DynamicBars.Draw(datas); diff --git a/Craftimizer/Windows/RecipeNote.cs b/Craftimizer/Windows/RecipeNote.cs index 8b376ac..2e0d7b7 100644 --- a/Craftimizer/Windows/RecipeNote.cs +++ b/Craftimizer/Windows/RecipeNote.cs @@ -401,7 +401,7 @@ public sealed unsafe class RecipeNote : Window, IDisposable Service.Plugin.OpenMacroListWindow(); if (ImGui.Button("Open in Macro Editor", new(availWidth, 0))) - Service.Plugin.OpenMacroEditor(CharacterStats!, RecipeData!, new(Service.ClientState.LocalPlayer!.StatusList), Enumerable.Empty(), null); + Service.Plugin.OpenMacroEditor(CharacterStats!, RecipeData!, new(Service.ClientState.LocalPlayer!.StatusList), [], null); } private void DrawCharacterStats() @@ -978,8 +978,7 @@ public sealed unsafe class RecipeNote : Window, IDisposable private static void DrawRequiredStatsTable(int current, int required) { - if (current >= required) - throw new ArgumentOutOfRangeException(nameof(current)); + ArgumentOutOfRangeException.ThrowIfGreaterThanOrEqual(current, required); using var table = ImRaii.Table("requiredStats", 2); if (table) @@ -1048,8 +1047,7 @@ public sealed unsafe class RecipeNote : Window, IDisposable return (ResolveNpcResidentName(level.Object.Row), territory, location, new(level.Territory.Row, level.Map.Row, location.X, location.Y)); } - // MapUtil.WorldToMap but for GeneratedSheets2 - private static Vector2 WorldToMap2(Vector2 worldCoordinates, Lumina.Excel.GeneratedSheets2.Map map) + private static Vector2 WorldToMap2(Vector2 worldCoordinates, ExdSheets.Map map) { return MapUtil.WorldToMap(worldCoordinates, map.OffsetX, map.OffsetY, map.SizeFactor); } diff --git a/Craftimizer/packages.lock.json b/Craftimizer/packages.lock.json index 46bfa68..397a713 100644 --- a/Craftimizer/packages.lock.json +++ b/Craftimizer/packages.lock.json @@ -8,6 +8,15 @@ "resolved": "2.1.12", "contentHash": "Sc0PVxvgg4NQjcI8n10/VfUQBAS4O+Fw2pZrAqBdRMbthYGeogzu5+xmIGCGmsEZ/ukMOBuAqiNiB5qA3MRalg==" }, + "ExdSheets": { + "type": "Direct", + "requested": "[1.0.0, )", + "resolved": "1.0.0", + "contentHash": "Zf1btj6qUkrzEm+MVCd2vRWguXizb+Ucy49xWHhFJ5HQj6gtLOxAX2gJqebAtg/uDBbEb9BHx/5Kz7Kuha5+cw==", + "dependencies": { + "Lumina": "3.15.2" + } + }, "MathNet.Numerics": { "type": "Direct", "requested": "[5.0.0, )", @@ -16,9 +25,14 @@ }, "Meziantou.Analyzer": { "type": "Direct", - "requested": "[2.0.106, )", - "resolved": "2.0.106", - "contentHash": "ygz0oT+Sfkn7Zfhf05iQkrLsrhH9+laOHsab8zq1okOVNjWGbQsXIBgeITF1DLEB/gVYgHHyVEK8YoNnhed/GQ==" + "requested": "[2.0.157, )", + "resolved": "2.0.157", + "contentHash": "gQ9xAHvpYeqwOqcyRs5f8kFrTt7Kg2atzjsETGhRjuyGXqKYrN84n52Je6NcGEkZWRwhrQTBJl1wlcsh2se7Fw==" + }, + "Lumina": { + "type": "Transitive", + "resolved": "3.15.2", + "contentHash": "EnoxYEYMepcvAoXdZhaFJiv2aiDBIPjgkgzxR/+ArOxlrALzCgheTsb5yD39a9sxNIi2tNECT93ulZvYjx8fZg==" }, "craftimizer.simulator": { "type": "Project"