From ec256ac090f1555ef34d4df4120a8f69d6e037aa Mon Sep 17 00:00:00 2001 From: Liza Carvelli Date: Wed, 24 Jan 2024 16:25:13 +0100 Subject: [PATCH] Add 'Check Retainer Inventory' for lists to keep in stock --- ARControl/ARControl.csproj | 2 +- ARControl/AutoRetainerControlPlugin.cs | 7 ++-- ARControl/Configuration.cs | 1 + ARControl/External/AllaganToolsIpc.cs | 48 ++++++++++++++++++++++++++ ARControl/Windows/ConfigWindow.cs | 30 ++++++++++++++-- 5 files changed, 82 insertions(+), 6 deletions(-) create mode 100644 ARControl/External/AllaganToolsIpc.cs diff --git a/ARControl/ARControl.csproj b/ARControl/ARControl.csproj index 02882da..67f222a 100644 --- a/ARControl/ARControl.csproj +++ b/ARControl/ARControl.csproj @@ -1,7 +1,7 @@ net7.0-windows - 3.2 + 3.3 11.0 enable true diff --git a/ARControl/AutoRetainerControlPlugin.cs b/ARControl/AutoRetainerControlPlugin.cs index 7665b06..0ad8180 100644 --- a/ARControl/AutoRetainerControlPlugin.cs +++ b/ARControl/AutoRetainerControlPlugin.cs @@ -36,6 +36,7 @@ public sealed partial class AutoRetainerControlPlugin : IDalamudPlugin private readonly GameCache _gameCache; private readonly IconCache _iconCache; private readonly VentureResolver _ventureResolver; + private readonly AllaganToolsIpc _allaganToolsIpc; private readonly ConfigWindow _configWindow; private readonly AutoRetainerApi _autoRetainerApi; @@ -55,6 +56,7 @@ public sealed partial class AutoRetainerControlPlugin : IDalamudPlugin _iconCache = new IconCache(textureProvider); _ventureResolver = new VentureResolver(_gameCache, _pluginLog); DiscardHelperIpc discardHelperIpc = new(_pluginInterface); + _allaganToolsIpc = new AllaganToolsIpc(pluginInterface, pluginLog); _configWindow = new ConfigWindow(_pluginInterface, _configuration, _gameCache, _clientState, _commandManager, _iconCache, discardHelperIpc, _pluginLog); @@ -189,8 +191,9 @@ public sealed partial class AutoRetainerControlPlugin : IDalamudPlugin { QueuedItem = x, InventoryCount = inventoryManager->GetInventoryItemCount(x.ItemId) + - (venturesInProgress.TryGetValue(x.ItemId, out int inProgress) - ? inProgress + venturesInProgress.GetValueOrDefault(x.ItemId, 0) + + (list.CheckRetainerInventory + ? (int)_allaganToolsIpc.GetRetainerItemCount(x.ItemId) : 0), }) .Where(x => x.InventoryCount < x.RequestedCount) diff --git a/ARControl/Configuration.cs b/ARControl/Configuration.cs index cb7137f..5ed7725 100644 --- a/ARControl/Configuration.cs +++ b/ARControl/Configuration.cs @@ -21,6 +21,7 @@ internal sealed class Configuration : IPluginConfiguration public required string Name { get; set; } public required ListType Type { get; set; } = ListType.CollectOneTime; public required ListPriority Priority { get; set; } = ListPriority.InOrder; + public bool CheckRetainerInventory { get; set; } public List Items { get; set; } = new(); public string GetIcon() diff --git a/ARControl/External/AllaganToolsIpc.cs b/ARControl/External/AllaganToolsIpc.cs new file mode 100644 index 0000000..4fc80bd --- /dev/null +++ b/ARControl/External/AllaganToolsIpc.cs @@ -0,0 +1,48 @@ +using System.Linq; +using Dalamud.Plugin; +using Dalamud.Plugin.Ipc; +using Dalamud.Plugin.Ipc.Exceptions; +using Dalamud.Plugin.Services; +using FFXIVClientStructs.FFXIV.Client.Game; + +namespace ARControl.External; + +public class AllaganToolsIpc +{ + private readonly IPluginLog _pluginLog; + + private static readonly uint[] RetainerInventoryTypes = new[] + { + InventoryType.RetainerPage1, + InventoryType.RetainerPage2, + InventoryType.RetainerPage3, + InventoryType.RetainerPage4, + InventoryType.RetainerPage5, + InventoryType.RetainerPage6, + InventoryType.RetainerPage7, + } + .Select(x => (uint)x).ToArray(); + + private readonly ICallGateSubscriber _itemCountOwned; + + public AllaganToolsIpc(DalamudPluginInterface pluginInterface, IPluginLog pluginLog) + { + _pluginLog = pluginLog; + _itemCountOwned = pluginInterface.GetIpcSubscriber("AllaganTools.ItemCountOwned"); + } + + public uint GetRetainerItemCount(uint itemId) + { + try + { + uint itemCount = _itemCountOwned.InvokeFunc(itemId, true, RetainerInventoryTypes); + _pluginLog.Verbose($"Found {itemCount} items in retainer inventories for itemId {itemId}"); + return itemCount; + } + catch (IpcError e) + { + _pluginLog.Warning("Could not query allagantools for retainer inventory counts"); + return 0; + } + } +} diff --git a/ARControl/Windows/ConfigWindow.cs b/ARControl/Windows/ConfigWindow.cs index 0cd5b84..469e113 100644 --- a/ARControl/Windows/ConfigWindow.cs +++ b/ARControl/Windows/ConfigWindow.cs @@ -12,6 +12,7 @@ using Dalamud.Interface; using Dalamud.Interface.Colors; using Dalamud.Interface.Components; using Dalamud.Interface.Internal; +using Dalamud.Interface.Utility; using Dalamud.Plugin; using Dalamud.Plugin.Services; using ECommons; @@ -55,7 +56,8 @@ internal sealed class ConfigWindow : LImGui.LWindow { Name = string.Empty, ListType = Configuration.ListType.CollectOneTime, - ListPriority = Configuration.ListPriority.InOrder + ListPriority = Configuration.ListPriority.InOrder, + CheckRetainerInventory = false, }; public ConfigWindow( @@ -115,6 +117,7 @@ internal sealed class ConfigWindow : LImGui.LWindow Name = list.Name, ListType = list.Type, ListPriority = list.Priority, + CheckRetainerInventory = list.CheckRetainerInventory, }; ImGui.OpenPopup($"##EditList{list.Id}"); } @@ -163,7 +166,8 @@ internal sealed class ConfigWindow : LImGui.LWindow var (save, canSave) = DrawVentureListEditor(temporaryConfig, list); ImGui.BeginDisabled(!canSave || (list.Name == temporaryConfig.Name && list.Type == temporaryConfig.ListType && - list.Priority == temporaryConfig.ListPriority)); + list.Priority == temporaryConfig.ListPriority && + list.CheckRetainerInventory == temporaryConfig.CheckRetainerInventory)); save |= ImGuiComponents.IconButtonWithText(FontAwesomeIcon.Save, "Save"); ImGui.EndDisabled(); @@ -173,9 +177,15 @@ internal sealed class ConfigWindow : LImGui.LWindow list.Type = temporaryConfig.ListType; if (list.Type == Configuration.ListType.CollectOneTime) + { list.Priority = Configuration.ListPriority.InOrder; + list.CheckRetainerInventory = false; + } else + { list.Priority = temporaryConfig.ListPriority; + list.CheckRetainerInventory = temporaryConfig.CheckRetainerInventory; + } ImGui.CloseCurrentPopup(); Save(); @@ -230,13 +240,15 @@ internal sealed class ConfigWindow : LImGui.LWindow Name = _newList.Name, Type = _newList.ListType, Priority = _newList.ListPriority, + CheckRetainerInventory = _newList.CheckRetainerInventory, }); _newList = new() { Name = string.Empty, ListType = Configuration.ListType.CollectOneTime, - ListPriority = Configuration.ListPriority.InOrder + ListPriority = Configuration.ListPriority.InOrder, + CheckRetainerInventory = false, }; ImGui.CloseCurrentPopup(); @@ -250,6 +262,7 @@ internal sealed class ConfigWindow : LImGui.LWindow private (bool Save, bool CanSave) DrawVentureListEditor(TemporaryConfig temporaryConfig, Configuration.ItemList? list) { + ImGui.SetNextItemWidth(375 * ImGuiHelpers.GlobalScale); string listName = temporaryConfig.Name; bool save = ImGui.InputTextWithHint("", "List Name...", ref listName, 64, ImGuiInputTextFlags.EnterReturnsTrue); @@ -257,6 +270,7 @@ internal sealed class ConfigWindow : LImGui.LWindow temporaryConfig.Name = listName; ImGui.PushID($"Type{list?.Id ?? Guid.Empty}"); + ImGui.SetNextItemWidth(375 * ImGuiHelpers.GlobalScale); int type = (int)temporaryConfig.ListType; if (ImGui.Combo("", ref type, StockingTypeLabels, StockingTypeLabels.Length)) { @@ -270,10 +284,18 @@ internal sealed class ConfigWindow : LImGui.LWindow if (temporaryConfig.ListType == Configuration.ListType.KeepStocked) { ImGui.PushID($"Priority{list?.Id ?? Guid.Empty}"); + ImGui.SetNextItemWidth(375 * ImGuiHelpers.GlobalScale); int priority = (int)temporaryConfig.ListPriority; if (ImGui.Combo("", ref priority, PriorityLabels, PriorityLabels.Length)) temporaryConfig.ListPriority = (Configuration.ListPriority)priority; ImGui.PopID(); + + ImGui.PushID($"CheckRetainerInventory{list?.Id ?? Guid.Empty}"); + bool checkRetainerInventory = temporaryConfig.CheckRetainerInventory; + if (ImGui.Checkbox("Check Retainer Inventory for items (requires AllaganTools)", + ref checkRetainerInventory)) + temporaryConfig.CheckRetainerInventory = checkRetainerInventory; + ImGui.PopID(); } return (save, canSave); @@ -1038,6 +1060,7 @@ internal sealed class ConfigWindow : LImGui.LWindow Name = "---", Type = Configuration.ListType.CollectOneTime, Priority = Configuration.ListPriority.InOrder, + CheckRetainerInventory = false, } }.Concat(_configuration.ItemLists) .Select(x => (x.Id, $"{x.Name} {x.GetIcon()}".TrimEnd(), x)).ToList(); @@ -1303,5 +1326,6 @@ internal sealed class ConfigWindow : LImGui.LWindow public required string Name { get; set; } public Configuration.ListType ListType { get; set; } public Configuration.ListPriority ListPriority { get; set; } + public bool CheckRetainerInventory { get; set; } } }