diff --git a/LLib b/LLib index 8944883..7f83ece 160000 --- a/LLib +++ b/LLib @@ -1 +1 @@ -Subproject commit 89448838a1295041293bbd5dd69501ad934bdf03 +Subproject commit 7f83ece6a0c07d0fbc1902502050563b5a8c09e4 diff --git a/Workshoppa/GameData/WorkshopCache.cs b/Workshoppa/GameData/WorkshopCache.cs index c853702..9a959e6 100644 --- a/Workshoppa/GameData/WorkshopCache.cs +++ b/Workshoppa/GameData/WorkshopCache.cs @@ -26,6 +26,7 @@ internal sealed class WorkshopCache WorkshopItemId = x.RowId, ResultItem = x.ResultItem.Row, Name = x.ResultItem.Value!.Name.ToString(), + IconId = x.ResultItem.Value!.Icon, Category = (WorkshopCraftCategory)x.CompanyCraftDraftCategory.Row, Type = x.CompanyCraftType.Row, Phases = x.CompanyCraftPart.Where(part => part.Row != 0) @@ -42,6 +43,7 @@ internal sealed class WorkshopCache { ItemId = itemMapping[item.SupplyItem].RowId, Name = itemMapping[item.SupplyItem].Name.ToString(), + IconId = itemMapping[item.SupplyItem].Icon, SetQuantity = item.SetQuantity, SetsRequired = item.SetsRequired, }) diff --git a/Workshoppa/GameData/WorkshopCraft.cs b/Workshoppa/GameData/WorkshopCraft.cs index 0b1d8cb..5a81350 100644 --- a/Workshoppa/GameData/WorkshopCraft.cs +++ b/Workshoppa/GameData/WorkshopCraft.cs @@ -7,6 +7,7 @@ internal sealed class WorkshopCraft public required uint WorkshopItemId { get; init; } public required uint ResultItem { get; init; } public required string Name { get; init; } + public required ushort IconId { get; init; } public required WorkshopCraftCategory Category { get; init; } public required uint Type { get; init; } public required IReadOnlyList Phases { get; init; } diff --git a/Workshoppa/GameData/WorkshopCraftItem.cs b/Workshoppa/GameData/WorkshopCraftItem.cs index 2cce343..4ae48d8 100644 --- a/Workshoppa/GameData/WorkshopCraftItem.cs +++ b/Workshoppa/GameData/WorkshopCraftItem.cs @@ -4,6 +4,7 @@ internal sealed class WorkshopCraftItem { public required uint ItemId { get; init; } public required string Name { get; init; } + public required ushort IconId { get; init; } public required int SetQuantity { get; init; } public required int SetsRequired { get; init; } public int TotalQuantity => SetQuantity * SetsRequired; diff --git a/Workshoppa/Windows/MainWindow.cs b/Workshoppa/Windows/MainWindow.cs index d089328..47f3f62 100644 --- a/Workshoppa/Windows/MainWindow.cs +++ b/Workshoppa/Windows/MainWindow.cs @@ -5,6 +5,7 @@ using System.Numerics; using Dalamud.Interface; using Dalamud.Interface.Colors; using Dalamud.Interface.Components; +using Dalamud.Interface.Internal; using Dalamud.Interface.Windowing; using Dalamud.Plugin; using Dalamud.Plugin.Services; @@ -23,12 +24,13 @@ internal sealed class MainWindow : Window private readonly IClientState _clientState; private readonly Configuration _configuration; private readonly WorkshopCache _workshopCache; + private readonly IconCache _iconCache; private string _searchString = string.Empty; private bool _checkInventory; public MainWindow(WorkshopPlugin plugin, DalamudPluginInterface pluginInterface, IClientState clientState, - Configuration configuration, WorkshopCache workshopCache) + Configuration configuration, WorkshopCache workshopCache, IconCache iconCache) : base("Workshoppa###WorkshoppaMainWindow") { _plugin = plugin; @@ -36,6 +38,7 @@ internal sealed class MainWindow : Window _clientState = clientState; _configuration = configuration; _workshopCache = workshopCache; + _iconCache = iconCache; Position = new Vector2(100, 100); PositionCondition = ImGuiCond.FirstUseEver; @@ -64,7 +67,18 @@ internal sealed class MainWindow : Window if (currentItem != null) { var currentCraft = _workshopCache.Crafts.Single(x => x.WorkshopItemId == currentItem.WorkshopItemId); - ImGui.Text($"Currently Crafting: {currentCraft.Name}"); + ImGui.Text($"Currently Crafting:"); + + IDalamudTextureWrap? icon = _iconCache.GetIcon(currentCraft.IconId); + if (icon != null) + { + ImGui.Image(icon.ImGuiHandle, new Vector2(23, 23)); + ImGui.SameLine(0, 3); + ImGui.SetCursorPosY(ImGui.GetCursorPosY() + 3); + } + + ImGui.TextUnformatted($"{currentCraft.Name}"); + ImGui.Spacing(); if (_plugin.CurrentStage == Stage.Stopped) { @@ -157,6 +171,13 @@ internal sealed class MainWindow : Window var item = _configuration.ItemQueue[i]; var craft = _workshopCache.Crafts.Single(x => x.WorkshopItemId == item.WorkshopItemId); + IDalamudTextureWrap? icon = _iconCache.GetIcon(craft.IconId); + if (icon != null) + { + ImGui.Image(icon.ImGuiHandle, new Vector2(23, 23)); + ImGui.SameLine(0, 3); + } + ImGui.SetNextItemWidth(100); int quantity = item.Quantity; if (ImGui.InputInt(craft.Name, ref quantity)) @@ -184,7 +205,7 @@ internal sealed class MainWindow : Window } ImGui.SetNextItemWidth(ImGui.GetContentRegionAvail().X); - if (ImGui.BeginCombo("##CraftSelection", "Add Craft...")) + if (ImGui.BeginCombo("##CraftSelection", "Add Craft...", ImGuiComboFlags.HeightLarge)) { ImGui.SetNextItemWidth(ImGui.GetContentRegionAvail().X); ImGui.InputTextWithHint("", "Filter...", ref _searchString, 256); @@ -193,6 +214,13 @@ internal sealed class MainWindow : Window .Where(x => x.Name.ToLower().Contains(_searchString.ToLower())) .OrderBy(x => x.WorkshopItemId)) { + IDalamudTextureWrap? icon = _iconCache.GetIcon(craft.IconId); + if (icon != null) + { + ImGui.Image(icon.ImGuiHandle, new Vector2(23, 23)); + ImGui.SameLine(); + ImGui.SetCursorPosY(ImGui.GetCursorPosY() + 3); + } if (ImGui.Selectable($"{craft.Name}##SelectCraft{craft.WorkshopItemId}")) { _configuration.ItemQueue.Add(new Configuration.QueuedItem @@ -265,11 +293,12 @@ internal sealed class MainWindow : Window var items = workshopItemIds.Select(x => _workshopCache.Crafts.Single(y => y.WorkshopItemId == x)) .SelectMany(x => x.Phases) .SelectMany(x => x.Items) - .GroupBy(x => new { x.Name, x.ItemId }) + .GroupBy(x => new { x.Name, x.ItemId, x.IconId }) .OrderBy(x => x.Key.Name) .Select(x => new { x.Key.ItemId, + x.Key.IconId, x.Key.Name, TotalQuantity = completedForCurrentCraft.TryGetValue(x.Key.ItemId, out var completed) ? x.Sum(y => y.TotalQuantity) - completed @@ -282,6 +311,15 @@ internal sealed class MainWindow : Window { int inInventory = inventoryManager->GetInventoryItemCount(item.ItemId, true, false, false) + inventoryManager->GetInventoryItemCount(item.ItemId, false, false, false); + + IDalamudTextureWrap? icon = _iconCache.GetIcon(item.IconId); + if (icon != null) + { + ImGui.Image(icon.ImGuiHandle, new Vector2(23, 23)); + ImGui.SameLine(0, 3); + ImGui.SetCursorPosY(ImGui.GetCursorPosY() + 3); + } + ImGui.TextColored(inInventory >= item.TotalQuantity ? ImGuiColors.HealerGreen : ImGuiColors.DalamudRed, $"{item.Name} ({inInventory} / {item.TotalQuantity})"); } diff --git a/Workshoppa/WorkshopPlugin.cs b/Workshoppa/WorkshopPlugin.cs index 7495f26..909e80b 100644 --- a/Workshoppa/WorkshopPlugin.cs +++ b/Workshoppa/WorkshopPlugin.cs @@ -8,6 +8,7 @@ using Dalamud.Game.Command; using Dalamud.Interface.Windowing; using Dalamud.Plugin; using Dalamud.Plugin.Services; +using LLib; using Workshoppa.External; using Workshoppa.GameData; using Workshoppa.Windows; @@ -17,7 +18,9 @@ namespace Workshoppa; [SuppressMessage("ReSharper", "UnusedType.Global")] public sealed partial class WorkshopPlugin : IDalamudPlugin { - private readonly IReadOnlyList _fabricationStationIds = new uint[] { 2005236, 2005238, 2005240, 2007821, 2011588 }.AsReadOnly(); + private readonly IReadOnlyList _fabricationStationIds = + new uint[] { 2005236, 2005238, 2005240, 2007821, 2011588 }.AsReadOnly(); + internal readonly IReadOnlyList WorkshopTerritories = new ushort[] { 423, 424, 425, 653, 984 }.AsReadOnly(); private readonly WindowSystem _windowSystem = new WindowSystem(nameof(WorkshopPlugin)); @@ -48,7 +51,8 @@ public sealed partial class WorkshopPlugin : IDalamudPlugin public WorkshopPlugin(DalamudPluginInterface pluginInterface, IGameGui gameGui, IFramework framework, ICondition condition, IClientState clientState, IObjectTable objectTable, IDataManager dataManager, - ICommandManager commandManager, IPluginLog pluginLog, IAddonLifecycle addonLifecycle, IChatGui chatGui) + ICommandManager commandManager, IPluginLog pluginLog, IAddonLifecycle addonLifecycle, IChatGui chatGui, + ITextureProvider textureProvider) { _pluginInterface = pluginInterface; _gameGui = gameGui; @@ -66,11 +70,13 @@ public sealed partial class WorkshopPlugin : IDalamudPlugin _workshopCache = new WorkshopCache(dataManager, _pluginLog); _gameStrings = new(dataManager, _pluginLog); - _mainWindow = new(this, _pluginInterface, _clientState, _configuration, _workshopCache); + _mainWindow = new(this, _pluginInterface, _clientState, _configuration, _workshopCache, + new IconCache(textureProvider)); _windowSystem.AddWindow(_mainWindow); _configWindow = new(_pluginInterface, _configuration); _windowSystem.AddWindow(_configWindow); - _repairKitWindow = new(this, _pluginInterface, _pluginLog, _gameGui, addonLifecycle, _configuration, _externalPluginHandler); + _repairKitWindow = new(this, _pluginInterface, _pluginLog, _gameGui, addonLifecycle, _configuration, + _externalPluginHandler); _windowSystem.AddWindow(_repairKitWindow); _ceruleumTankWindow = new(this, _pluginInterface, _pluginLog, _gameGui, addonLifecycle, _configuration, _externalPluginHandler); @@ -144,7 +150,8 @@ public sealed partial class WorkshopPlugin : IDalamudPlugin return; } - else if (_mainWindow.State is MainWindow.ButtonState.Start or MainWindow.ButtonState.Resume && CurrentStage == Stage.Stopped) + else if (_mainWindow.State is MainWindow.ButtonState.Start or MainWindow.ButtonState.Resume && + CurrentStage == Stage.Stopped) { // TODO Error checking, we should ensure the player has the required job level for *all* crafting parts _mainWindow.State = MainWindow.ButtonState.None; @@ -164,12 +171,12 @@ public sealed partial class WorkshopPlugin : IDalamudPlugin break; case Stage.TargetFabricationStation: - if (_configuration.CurrentlyCraftedItem is { StartedCrafting: true }) - CurrentStage = Stage.SelectCraftBranch; - else - CurrentStage = Stage.OpenCraftingLog; + if (_configuration.CurrentlyCraftedItem is { StartedCrafting: true }) + CurrentStage = Stage.SelectCraftBranch; + else + CurrentStage = Stage.OpenCraftingLog; - InteractWithFabricationStation(fabricationStation!); + InteractWithFabricationStation(fabricationStation!); break; @@ -234,7 +241,8 @@ public sealed partial class WorkshopPlugin : IDalamudPlugin private WorkshopCraft GetCurrentCraft() { - return _workshopCache.Crafts.Single(x => x.WorkshopItemId == _configuration.CurrentlyCraftedItem!.WorkshopItemId); + return _workshopCache.Crafts.Single( + x => x.WorkshopItemId == _configuration.CurrentlyCraftedItem!.WorkshopItemId); } private void ProcessCommand(string command, string arguments) diff --git a/Workshoppa/Workshoppa.csproj b/Workshoppa/Workshoppa.csproj index 6d2b1fb..f92fccd 100644 --- a/Workshoppa/Workshoppa.csproj +++ b/Workshoppa/Workshoppa.csproj @@ -1,7 +1,7 @@ net7.0-windows - 3.3 + 3.4 11.0 enable true