Initial release: HSUI v1.0.0.0 - HUD replacement with configurable hotbars
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -0,0 +1,859 @@
|
||||
using Dalamud.Interface;
|
||||
using HSUI.Config;
|
||||
using HSUI.Config.Attributes;
|
||||
using HSUI.Enums;
|
||||
using HSUI.Helpers;
|
||||
using HSUI.Interface.Bars;
|
||||
using HSUI.Interface.GeneralElements;
|
||||
using Dalamud.Bindings.ImGui;
|
||||
using Lumina.Excel;
|
||||
using Lumina.Excel.Sheets;
|
||||
using Newtonsoft.Json;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Numerics;
|
||||
|
||||
namespace HSUI.Interface.StatusEffects
|
||||
{
|
||||
[Section("Buffs and Debuffs")]
|
||||
[SubSection("Player Buffs", 0)]
|
||||
public class PlayerBuffsListConfig : UnitFrameStatusEffectsListConfig
|
||||
{
|
||||
public new static PlayerBuffsListConfig DefaultConfig()
|
||||
{
|
||||
var screenSize = ImGui.GetMainViewport().Size;
|
||||
var pos = new Vector2(screenSize.X * 0.38f, -screenSize.Y * 0.45f);
|
||||
var iconConfig = new StatusEffectIconConfig();
|
||||
iconConfig.DispellableBorderConfig.Enabled = false;
|
||||
|
||||
return new PlayerBuffsListConfig(pos, HUDConstants.DefaultStatusEffectsListSize, true, false, true, GrowthDirections.Left | GrowthDirections.Down, iconConfig);
|
||||
}
|
||||
|
||||
public PlayerBuffsListConfig(Vector2 position, Vector2 size, bool showBuffs, bool showDebuffs, bool showPermanentEffects,
|
||||
GrowthDirections growthDirections, StatusEffectIconConfig iconConfig)
|
||||
: base(position, size, showBuffs, showDebuffs, showPermanentEffects, growthDirections, iconConfig)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
[Section("Buffs and Debuffs")]
|
||||
[SubSection("Player Debuffs", 0)]
|
||||
public class PlayerDebuffsListConfig : UnitFrameStatusEffectsListConfig
|
||||
{
|
||||
public new static PlayerDebuffsListConfig DefaultConfig()
|
||||
{
|
||||
var screenSize = ImGui.GetMainViewport().Size;
|
||||
var pos = new Vector2(screenSize.X * 0.38f, -screenSize.Y * 0.45f + HUDConstants.DefaultStatusEffectsListSize.Y);
|
||||
var iconConfig = new StatusEffectIconConfig();
|
||||
|
||||
return new PlayerDebuffsListConfig(pos, HUDConstants.DefaultStatusEffectsListSize, false, true, true, GrowthDirections.Left | GrowthDirections.Down, iconConfig);
|
||||
}
|
||||
|
||||
public PlayerDebuffsListConfig(Vector2 position, Vector2 size, bool showBuffs, bool showDebuffs, bool showPermanentEffects,
|
||||
GrowthDirections growthDirections, StatusEffectIconConfig iconConfig)
|
||||
: base(position, size, showBuffs, showDebuffs, showPermanentEffects, growthDirections, iconConfig)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
[Section("Buffs and Debuffs")]
|
||||
[SubSection("Target Buffs", 0)]
|
||||
public class TargetBuffsListConfig : UnitFrameStatusEffectsListConfig
|
||||
{
|
||||
public new static TargetBuffsListConfig DefaultConfig()
|
||||
{
|
||||
var pos = new Vector2(0, -1);
|
||||
var iconConfig = new StatusEffectIconConfig();
|
||||
iconConfig.DispellableBorderConfig.Enabled = false;
|
||||
|
||||
var config = new TargetBuffsListConfig(pos, HUDConstants.DefaultStatusEffectsListSize, true, false, true, GrowthDirections.Right | GrowthDirections.Up, iconConfig);
|
||||
config.AnchorToUnitFrame = true;
|
||||
config.UnitFrameAnchor = DrawAnchor.TopLeft;
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
public TargetBuffsListConfig(Vector2 position, Vector2 size, bool showBuffs, bool showDebuffs, bool showPermanentEffects,
|
||||
GrowthDirections growthDirections, StatusEffectIconConfig iconConfig)
|
||||
: base(position, size, showBuffs, showDebuffs, showPermanentEffects, growthDirections, iconConfig)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
[Section("Buffs and Debuffs")]
|
||||
[SubSection("Target Debuffs", 0)]
|
||||
public class TargetDebuffsListConfig : UnitFrameStatusEffectsListConfig
|
||||
{
|
||||
public new static TargetDebuffsListConfig DefaultConfig()
|
||||
{
|
||||
var pos = new Vector2(0, -85);
|
||||
var iconConfig = new StatusEffectIconConfig();
|
||||
iconConfig.DispellableBorderConfig.Enabled = false;
|
||||
|
||||
var config = new TargetDebuffsListConfig(pos, HUDConstants.DefaultStatusEffectsListSize, false, true, true, GrowthDirections.Right | GrowthDirections.Up, iconConfig);
|
||||
config.AnchorToUnitFrame = true;
|
||||
config.UnitFrameAnchor = DrawAnchor.TopLeft;
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
public TargetDebuffsListConfig(Vector2 position, Vector2 size, bool showBuffs, bool showDebuffs, bool showPermanentEffects,
|
||||
GrowthDirections growthDirections, StatusEffectIconConfig iconConfig)
|
||||
: base(position, size, showBuffs, showDebuffs, showPermanentEffects, growthDirections, iconConfig)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
[Section("Buffs and Debuffs")]
|
||||
[SubSection("Focus Target Buffs", 0)]
|
||||
public class FocusTargetBuffsListConfig : UnitFrameStatusEffectsListConfig
|
||||
{
|
||||
public new static FocusTargetBuffsListConfig DefaultConfig()
|
||||
{
|
||||
var pos = new Vector2(0, -1);
|
||||
var iconConfig = new StatusEffectIconConfig();
|
||||
iconConfig.DispellableBorderConfig.Enabled = false;
|
||||
|
||||
var config = new FocusTargetBuffsListConfig(pos, HUDConstants.DefaultStatusEffectsListSize, true, false, true, GrowthDirections.Right | GrowthDirections.Up, iconConfig);
|
||||
config.AnchorToUnitFrame = true;
|
||||
config.UnitFrameAnchor = DrawAnchor.TopLeft;
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
public FocusTargetBuffsListConfig(Vector2 position, Vector2 size, bool showBuffs, bool showDebuffs, bool showPermanentEffects,
|
||||
GrowthDirections growthDirections, StatusEffectIconConfig iconConfig)
|
||||
: base(position, size, showBuffs, showDebuffs, showPermanentEffects, growthDirections, iconConfig)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
[Section("Buffs and Debuffs")]
|
||||
[SubSection("Focus Target Debuffs", 0)]
|
||||
public class FocusTargetDebuffsListConfig : UnitFrameStatusEffectsListConfig
|
||||
{
|
||||
public new static FocusTargetDebuffsListConfig DefaultConfig()
|
||||
{
|
||||
var pos = new Vector2(0, -85);
|
||||
var iconConfig = new StatusEffectIconConfig();
|
||||
iconConfig.DispellableBorderConfig.Enabled = false;
|
||||
|
||||
var config = new FocusTargetDebuffsListConfig(pos, HUDConstants.DefaultStatusEffectsListSize, false, true, true, GrowthDirections.Right | GrowthDirections.Up, iconConfig);
|
||||
config.AnchorToUnitFrame = true;
|
||||
config.UnitFrameAnchor = DrawAnchor.TopLeft;
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
public FocusTargetDebuffsListConfig(Vector2 position, Vector2 size, bool showBuffs, bool showDebuffs, bool showPermanentEffects,
|
||||
GrowthDirections growthDirections, StatusEffectIconConfig iconConfig)
|
||||
: base(position, size, showBuffs, showDebuffs, showPermanentEffects, growthDirections, iconConfig)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
public abstract class UnitFrameStatusEffectsListConfig : StatusEffectsListConfig
|
||||
{
|
||||
[Checkbox("Anchor to Unit Frame")]
|
||||
[Order(16)]
|
||||
public bool AnchorToUnitFrame = false;
|
||||
|
||||
[Anchor("Unit Frame Anchor")]
|
||||
[Order(17, collapseWith = nameof(AnchorToUnitFrame))]
|
||||
public DrawAnchor UnitFrameAnchor = DrawAnchor.TopLeft;
|
||||
|
||||
[NestedConfig("Visibility", 200)]
|
||||
public VisibilityConfig VisibilityConfig = new VisibilityConfig();
|
||||
|
||||
public UnitFrameStatusEffectsListConfig(Vector2 position, Vector2 size, bool showBuffs, bool showDebuffs, bool showPermanentEffects,
|
||||
GrowthDirections growthDirections, StatusEffectIconConfig iconConfig)
|
||||
: base(position, size, showBuffs, showDebuffs, showPermanentEffects, growthDirections, iconConfig)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
public class StatusEffectsListConfig : MovablePluginConfigObject
|
||||
{
|
||||
public bool ShowBuffs;
|
||||
public bool ShowDebuffs;
|
||||
|
||||
[DragInt2("Size", min = 1, max = 4000)]
|
||||
[Order(15)]
|
||||
public Vector2 Size;
|
||||
|
||||
[DragInt2("Icon Padding", min = 0, max = 500)]
|
||||
[Order(19)]
|
||||
public Vector2 IconPadding = new(2, 2);
|
||||
|
||||
[Checkbox("Preview", isMonitored = true)]
|
||||
[Order(20)]
|
||||
public bool Preview;
|
||||
|
||||
[Checkbox("Fill Rows First", spacing = true)]
|
||||
[Order(25)]
|
||||
public bool FillRowsFirst = true;
|
||||
|
||||
[Combo("Icons Growth Direction",
|
||||
"Right and Down",
|
||||
"Right and Up",
|
||||
"Left and Down",
|
||||
"Left and Up",
|
||||
"Centered and Up",
|
||||
"Centered and Down",
|
||||
"Centered and Left",
|
||||
"Centered and Right"
|
||||
)]
|
||||
[Order(30)]
|
||||
public int Directions;
|
||||
|
||||
[DragInt("Limit (-1 for no limit)", min = -1, max = 1000)]
|
||||
[Order(35)]
|
||||
public int Limit = -1;
|
||||
|
||||
[Checkbox("Permanent Effects", spacing = true)]
|
||||
[Order(40)]
|
||||
public bool ShowPermanentEffects;
|
||||
|
||||
[Checkbox("Permanent Effects First")]
|
||||
[Order(41)]
|
||||
public bool ShowPermanentFirst;
|
||||
|
||||
[Checkbox("Only My Effects", spacing = true)]
|
||||
[Order(42)]
|
||||
public bool ShowOnlyMine = false;
|
||||
|
||||
[Checkbox("My Effects First")]
|
||||
[Order(43)]
|
||||
public bool ShowMineFirst = false;
|
||||
|
||||
[Checkbox("Pet As Own Effect")]
|
||||
[Order(44)]
|
||||
public bool IncludePetAsOwn = false;
|
||||
|
||||
[Checkbox("Sort by Duration", spacing = true, help = "If enabled, \"Permanent Effects First\" and \"My Effects First\" will be ignored!")]
|
||||
[Order(45)]
|
||||
public bool SortByDuration = false;
|
||||
|
||||
[RadioSelector("Ascending", "Descending")]
|
||||
[Order(46, collapseWith = nameof(SortByDuration))]
|
||||
public StatusEffectDurationSortType DurationSortType = StatusEffectDurationSortType.Ascending;
|
||||
|
||||
[Checkbox("Tooltips", spacing = true)]
|
||||
[Order(47)]
|
||||
public bool ShowTooltips = true;
|
||||
|
||||
[Checkbox("Disable Interaction", help = "Enabling this will disable right clicking buffs off, or the shortcut to blacklist/whitelist a status effect.")]
|
||||
[Order(48)]
|
||||
public bool DisableInteraction = false;
|
||||
|
||||
[Checkbox("Hide when Dead")]
|
||||
[Order(49)]
|
||||
public bool HideWhenDead = true;
|
||||
|
||||
[NestedConfig("Icons", 65)]
|
||||
public StatusEffectIconConfig IconConfig;
|
||||
|
||||
[NestedConfig("Filter Status Effects", 70, separator = true, spacing = false, collapsingHeader = false)]
|
||||
public StatusEffectsBlacklistConfig BlacklistConfig = new StatusEffectsBlacklistConfig();
|
||||
|
||||
|
||||
public StatusEffectsListConfig(Vector2 position, Vector2 size, bool showBuffs, bool showDebuffs, bool showPermanentEffects,
|
||||
GrowthDirections growthDirections, StatusEffectIconConfig iconConfig)
|
||||
{
|
||||
Position = position;
|
||||
Size = size;
|
||||
ShowBuffs = showBuffs;
|
||||
ShowDebuffs = showDebuffs;
|
||||
ShowPermanentEffects = showPermanentEffects;
|
||||
|
||||
SetGrowthDirections(growthDirections);
|
||||
|
||||
IconConfig = iconConfig;
|
||||
|
||||
Strata = StrataLevel.HIGH;
|
||||
}
|
||||
|
||||
private void SetGrowthDirections(GrowthDirections growthDirections)
|
||||
{
|
||||
Directions = LayoutHelper.IndexFromGrowthDirections(growthDirections);
|
||||
}
|
||||
}
|
||||
|
||||
[Exportable(false)]
|
||||
[Disableable(false)]
|
||||
public class StatusEffectIconConfig : PluginConfigObject
|
||||
{
|
||||
[DragInt2("Icon Size", min = 1, max = 1000)]
|
||||
[Order(5)]
|
||||
public Vector2 Size = new(40, 40);
|
||||
|
||||
[Checkbox("Crop Icon", spacing = true)]
|
||||
[Order(20)]
|
||||
public bool CropIcon = true;
|
||||
|
||||
[NestedConfig("Border", 25, collapseWith = nameof(CropIcon), collapsingHeader = false)]
|
||||
public StatusEffectIconBorderConfig BorderConfig = new();
|
||||
|
||||
[NestedConfig("Shadow", 26, collapseWith = nameof(CropIcon), collapsingHeader = false)]
|
||||
public ShadowConfig ShadowConfig = new ShadowConfig() { Enabled = false };
|
||||
|
||||
[NestedConfig("Dispellable Effects Border", 30, collapseWith = nameof(CropIcon), collapsingHeader = false)]
|
||||
public StatusEffectIconBorderConfig DispellableBorderConfig = new(new PluginConfigColor(new Vector4(141f / 255f, 206f / 255f, 229f / 255f, 100f / 100f)), 2);
|
||||
|
||||
[NestedConfig("My Effects Border", 35, collapseWith = nameof(CropIcon), collapsingHeader = false)]
|
||||
public StatusEffectIconBorderConfig OwnedBorderConfig = new(new PluginConfigColor(new Vector4(35f / 255f, 179f / 255f, 69f / 255f, 100f / 100f)), 1);
|
||||
|
||||
[NestedConfig("Duration", 50)]
|
||||
public LabelConfig DurationLabelConfig;
|
||||
|
||||
[NestedConfig("Stacks", 60)]
|
||||
public LabelConfig StacksLabelConfig;
|
||||
|
||||
public StatusEffectIconConfig(LabelConfig? durationLabelConfig = null, LabelConfig? stacksLabelConfig = null)
|
||||
{
|
||||
DurationLabelConfig = durationLabelConfig ?? StatusEffectsListsDefaults.DefaultDurationLabelConfig();
|
||||
StacksLabelConfig = stacksLabelConfig ?? StatusEffectsListsDefaults.DefaultStacksLabelConfig();
|
||||
}
|
||||
}
|
||||
|
||||
[Exportable(false)]
|
||||
public class StatusEffectIconBorderConfig : PluginConfigObject
|
||||
{
|
||||
[ColorEdit4("Color")]
|
||||
[Order(5)]
|
||||
public PluginConfigColor Color = new(Vector4.UnitW);
|
||||
|
||||
[DragInt("Thickness", min = 1, max = 100)]
|
||||
[Order(10)]
|
||||
public int Thickness = 1;
|
||||
|
||||
public StatusEffectIconBorderConfig()
|
||||
{
|
||||
}
|
||||
|
||||
public StatusEffectIconBorderConfig(PluginConfigColor color, int thickness)
|
||||
{
|
||||
Color = color;
|
||||
Thickness = thickness;
|
||||
}
|
||||
}
|
||||
|
||||
internal class StatusEffectsListsDefaults
|
||||
{
|
||||
internal static LabelConfig DefaultDurationLabelConfig()
|
||||
{
|
||||
return new LabelConfig(Vector2.Zero, "", DrawAnchor.Center, DrawAnchor.Center);
|
||||
}
|
||||
|
||||
internal static LabelConfig DefaultStacksLabelConfig()
|
||||
{
|
||||
var config = new LabelConfig(new Vector2(16, -11), "", DrawAnchor.Center, DrawAnchor.Center);
|
||||
config.Color = new(Vector4.UnitW);
|
||||
config.OutlineColor = new(Vector4.One);
|
||||
config.ShadowConfig.Color = new(Vector4.One);
|
||||
|
||||
return config;
|
||||
}
|
||||
}
|
||||
|
||||
public enum FilterType
|
||||
{
|
||||
Blacklist,
|
||||
Whitelist
|
||||
}
|
||||
|
||||
[Exportable(false)]
|
||||
public class StatusEffectsBlacklistConfig : PluginConfigObject
|
||||
{
|
||||
[RadioSelector(typeof(FilterType))]
|
||||
[Order(5)]
|
||||
public FilterType FilterType;
|
||||
|
||||
public SortedList<string, uint> List = new SortedList<string, uint>();
|
||||
|
||||
[JsonIgnore] private string? _errorMessage = null;
|
||||
[JsonIgnore] private string? _importString = null;
|
||||
[JsonIgnore] private bool _clearingList = false;
|
||||
|
||||
private string KeyName(Status status)
|
||||
{
|
||||
return $"{status.Name}[{status.RowId.ToString()}]";
|
||||
}
|
||||
|
||||
public bool StatusAllowed(Status status)
|
||||
{
|
||||
bool inList = List.Any(pair => pair.Value == status.RowId);
|
||||
if ((inList && FilterType == FilterType.Blacklist) || (!inList && FilterType == FilterType.Whitelist))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public bool AddNewEntry(Status? status)
|
||||
{
|
||||
if (status != null && status.HasValue && !List.ContainsKey(KeyName(status.Value)))
|
||||
{
|
||||
List.Add(KeyName(status.Value), status.Value.RowId);
|
||||
_input = "";
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
private bool AddNewEntry(string input, ExcelSheet<Status>? sheet)
|
||||
{
|
||||
if (input.Length > 0 && sheet != null)
|
||||
{
|
||||
List<Status> statusToAdd = new List<Status>();
|
||||
|
||||
// try id
|
||||
if (uint.TryParse(input, out uint uintValue))
|
||||
{
|
||||
if (uintValue > 0)
|
||||
{
|
||||
Status? status = sheet.GetRow(uintValue);
|
||||
if (status != null && status.HasValue)
|
||||
{
|
||||
statusToAdd.Add(status.Value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// try name
|
||||
if (statusToAdd.Count == 0)
|
||||
{
|
||||
var enumerator = sheet.GetEnumerator();
|
||||
|
||||
while (enumerator.MoveNext())
|
||||
{
|
||||
Status item = enumerator.Current;
|
||||
if (item.Name.ToString().ToLower() == input.ToLower())
|
||||
{
|
||||
statusToAdd.Add(item);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool added = false;
|
||||
foreach (Status status in statusToAdd)
|
||||
{
|
||||
added |= AddNewEntry(status);
|
||||
}
|
||||
return added;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
private string ExportList()
|
||||
{
|
||||
string exportString = "";
|
||||
|
||||
for (int i = 0; i < List.Keys.Count; i++)
|
||||
{
|
||||
exportString += List.Keys[i] + "|";
|
||||
exportString += List.Values[i] + "|";
|
||||
}
|
||||
|
||||
return exportString;
|
||||
}
|
||||
|
||||
private string? ImportList(string importString)
|
||||
{
|
||||
SortedList<string, uint> tmpList = new SortedList<string, uint>();
|
||||
|
||||
try
|
||||
{
|
||||
string[] strings = importString.Trim().Split("|", StringSplitOptions.RemoveEmptyEntries);
|
||||
for (int i = 0; i < strings.Length; i += 2)
|
||||
{
|
||||
if (i + 1 >= strings.Length)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
string key = strings[i];
|
||||
uint value = uint.Parse(strings[i + 1]);
|
||||
|
||||
tmpList.Add(key, value);
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
return "Error importing list!";
|
||||
}
|
||||
|
||||
List = tmpList;
|
||||
return null;
|
||||
}
|
||||
|
||||
[JsonIgnore]
|
||||
private string _input = "";
|
||||
|
||||
[ManualDraw]
|
||||
public bool Draw(ref bool changed)
|
||||
{
|
||||
if (!Enabled)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
var flags =
|
||||
ImGuiTableFlags.RowBg |
|
||||
ImGuiTableFlags.Borders |
|
||||
ImGuiTableFlags.BordersOuter |
|
||||
ImGuiTableFlags.BordersInner |
|
||||
ImGuiTableFlags.ScrollY |
|
||||
ImGuiTableFlags.SizingFixedSame;
|
||||
|
||||
var sheet = Plugin.DataManager.GetExcelSheet<Status>();
|
||||
var iconSize = new Vector2(30, 30);
|
||||
var indexToRemove = -1;
|
||||
|
||||
if (ImGui.BeginChild("Filter Effects", new Vector2(0, 360), false, ImGuiWindowFlags.NoSavedSettings | ImGuiWindowFlags.NoScrollbar | ImGuiWindowFlags.NoScrollWithMouse))
|
||||
{
|
||||
ImGui.Text(" ");
|
||||
ImGui.SameLine();
|
||||
ImGui.Text("Type an ID or Name");
|
||||
|
||||
ImGui.Text(" ");
|
||||
ImGui.SameLine();
|
||||
ImGui.PushItemWidth(300);
|
||||
if (ImGui.InputText("", ref _input, 64, ImGuiInputTextFlags.EnterReturnsTrue))
|
||||
{
|
||||
changed |= AddNewEntry(_input, sheet);
|
||||
ImGui.SetKeyboardFocusHere(-1);
|
||||
}
|
||||
|
||||
// add
|
||||
ImGui.SameLine();
|
||||
ImGui.PushFont(UiBuilder.IconFont);
|
||||
if (ImGui.Button(FontAwesomeIcon.Plus.ToIconString(), new Vector2(0, 0)))
|
||||
{
|
||||
changed |= AddNewEntry(_input, sheet);
|
||||
ImGui.SetKeyboardFocusHere(-2);
|
||||
}
|
||||
|
||||
// export
|
||||
ImGui.SameLine();
|
||||
ImGui.SetCursorPosX(ImGui.GetCursorPosX() + 154);
|
||||
if (ImGui.Button(FontAwesomeIcon.Upload.ToIconString(), new Vector2(0, 0)))
|
||||
{
|
||||
ImGui.SetClipboardText(ExportList());
|
||||
ImGui.OpenPopup("export_succes_popup");
|
||||
}
|
||||
ImGui.PopFont();
|
||||
ImGuiHelper.SetTooltip("Export List to Clipboard");
|
||||
|
||||
// export success popup
|
||||
if (ImGui.BeginPopup("export_succes_popup"))
|
||||
{
|
||||
ImGui.Text("List exported to clipboard!");
|
||||
ImGui.EndPopup();
|
||||
}
|
||||
|
||||
// import
|
||||
ImGui.SameLine();
|
||||
ImGui.PushFont(UiBuilder.IconFont);
|
||||
if (ImGui.Button(FontAwesomeIcon.Download.ToIconString(), new Vector2(0, 0)))
|
||||
{
|
||||
_importString = ImGui.GetClipboardText();
|
||||
}
|
||||
ImGui.PopFont();
|
||||
ImGuiHelper.SetTooltip("Import List from Clipboard");
|
||||
|
||||
// clear
|
||||
ImGui.SameLine();
|
||||
ImGui.PushFont(UiBuilder.IconFont);
|
||||
if (ImGui.Button(FontAwesomeIcon.Trash.ToIconString(), new Vector2(0, 0)))
|
||||
{
|
||||
_clearingList = true;
|
||||
}
|
||||
ImGui.PopFont();
|
||||
ImGuiHelper.SetTooltip("Clear List");
|
||||
|
||||
ImGui.Text(" ");
|
||||
ImGui.SameLine();
|
||||
|
||||
if (ImGui.BeginTable("table", 4, flags, new Vector2(583, List.Count > 0 ? 200 : 40)))
|
||||
{
|
||||
ImGui.TableSetupColumn("Icon", ImGuiTableColumnFlags.WidthFixed, 0, 0);
|
||||
ImGui.TableSetupColumn("ID", ImGuiTableColumnFlags.WidthFixed, 0, 1);
|
||||
ImGui.TableSetupColumn("Name", ImGuiTableColumnFlags.WidthStretch, 0, 2);
|
||||
ImGui.TableSetupColumn("", ImGuiTableColumnFlags.WidthFixed, 0, 3);
|
||||
|
||||
ImGui.TableSetupScrollFreeze(0, 1);
|
||||
ImGui.TableHeadersRow();
|
||||
|
||||
for (int i = 0; i < List.Count; i++)
|
||||
{
|
||||
var id = List.Values[i];
|
||||
var name = List.Keys[i];
|
||||
var row = sheet?.GetRow(id);
|
||||
|
||||
if (_input != "" && !name.ToUpper().Contains(_input.ToUpper()))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
ImGui.PushID(i.ToString());
|
||||
ImGui.TableNextRow(ImGuiTableRowFlags.None, iconSize.Y);
|
||||
|
||||
// icon
|
||||
if (ImGui.TableSetColumnIndex(0))
|
||||
{
|
||||
if (row != null)
|
||||
{
|
||||
DrawHelper.DrawIcon<Status>(row, ImGui.GetCursorPos(), iconSize, false, true);
|
||||
}
|
||||
}
|
||||
|
||||
// id
|
||||
if (ImGui.TableSetColumnIndex(1))
|
||||
{
|
||||
ImGui.Text(id.ToString());
|
||||
}
|
||||
|
||||
// name
|
||||
if (ImGui.TableSetColumnIndex(2))
|
||||
{
|
||||
ImGui.Text(row != null && row.HasValue ? row.Value.Name.ToString() : name);
|
||||
}
|
||||
|
||||
// remove
|
||||
if (ImGui.TableSetColumnIndex(3))
|
||||
{
|
||||
ImGui.PushFont(UiBuilder.IconFont);
|
||||
ImGui.PushStyleColor(ImGuiCol.Button, Vector4.Zero);
|
||||
ImGui.PushStyleColor(ImGuiCol.ButtonActive, Vector4.Zero);
|
||||
ImGui.PushStyleColor(ImGuiCol.ButtonHovered, Vector4.Zero);
|
||||
if (ImGui.Button(FontAwesomeIcon.Trash.ToIconString(), iconSize))
|
||||
{
|
||||
changed = true;
|
||||
indexToRemove = i;
|
||||
}
|
||||
ImGui.PopFont();
|
||||
ImGui.PopStyleColor(3);
|
||||
}
|
||||
ImGui.PopID();
|
||||
}
|
||||
|
||||
ImGui.EndTable();
|
||||
}
|
||||
ImGui.Text(" ");
|
||||
ImGui.SameLine();
|
||||
ImGui.Text("Tip: You can [Ctrl + Alt + Shift] + Left Click on a status effect to automatically add it to the list.");
|
||||
|
||||
}
|
||||
|
||||
if (indexToRemove >= 0)
|
||||
{
|
||||
List.RemoveAt(indexToRemove);
|
||||
}
|
||||
|
||||
ImGui.EndChild();
|
||||
|
||||
// error message
|
||||
if (_errorMessage != null)
|
||||
{
|
||||
if (ImGuiHelper.DrawErrorModal(_errorMessage))
|
||||
{
|
||||
_errorMessage = null;
|
||||
}
|
||||
}
|
||||
|
||||
// import confirmation
|
||||
if (_importString != null)
|
||||
{
|
||||
string[] message = new string[] {
|
||||
"All the elements in the list will be replaced.",
|
||||
"Are you sure you want to import?"
|
||||
};
|
||||
var (didConfirm, didClose) = ImGuiHelper.DrawConfirmationModal("Import?", message);
|
||||
|
||||
if (didConfirm)
|
||||
{
|
||||
_errorMessage = ImportList(_importString);
|
||||
changed = true;
|
||||
}
|
||||
|
||||
if (didConfirm || didClose)
|
||||
{
|
||||
_importString = null;
|
||||
}
|
||||
}
|
||||
|
||||
// clear confirmation
|
||||
if (_clearingList)
|
||||
{
|
||||
string message = "Are you sure you want to clear the list?";
|
||||
|
||||
var (didConfirm, didClose) = ImGuiHelper.DrawConfirmationModal("Clear List?", message);
|
||||
|
||||
if (didConfirm)
|
||||
{
|
||||
List.Clear();
|
||||
changed = true;
|
||||
}
|
||||
|
||||
if (didConfirm || didClose)
|
||||
{
|
||||
_clearingList = false;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public class StatusEffectsBlacklistConfigConverter : PluginConfigObjectConverter
|
||||
{
|
||||
public StatusEffectsBlacklistConfigConverter()
|
||||
{
|
||||
NewTypeFieldConverter<bool, FilterType> converter;
|
||||
converter = new NewTypeFieldConverter<bool, FilterType>("FilterType", FilterType.Blacklist, (oldValue) =>
|
||||
{
|
||||
return oldValue ? FilterType.Whitelist : FilterType.Blacklist;
|
||||
});
|
||||
|
||||
FieldConvertersMap.Add("UseAsWhitelist", converter);
|
||||
}
|
||||
|
||||
public override bool CanConvert(Type objectType)
|
||||
{
|
||||
return objectType == typeof(StatusEffectsBlacklistConfig);
|
||||
}
|
||||
}
|
||||
|
||||
[Section("Buffs and Debuffs")]
|
||||
[SubSection("Custom Effects", 0)]
|
||||
public class CustomEffectsListConfig : StatusEffectsListConfig
|
||||
{
|
||||
public new static CustomEffectsListConfig DefaultConfig()
|
||||
{
|
||||
var iconConfig = new StatusEffectIconConfig();
|
||||
iconConfig.DispellableBorderConfig.Enabled = false;
|
||||
iconConfig.Size = new Vector2(30, 30);
|
||||
|
||||
var pos = new Vector2(0, HUDConstants.BaseHUDOffsetY);
|
||||
var size = new Vector2(250, iconConfig.Size.Y * 3 + 10);
|
||||
|
||||
var config = new CustomEffectsListConfig(pos, size, true, true, false, GrowthDirections.Centered | GrowthDirections.Up, iconConfig);
|
||||
config.Enabled = false;
|
||||
config.Directions = 5;
|
||||
|
||||
// pre-populated white list
|
||||
config.BlacklistConfig.FilterType = FilterType.Whitelist;
|
||||
|
||||
ExcelSheet<Status>? sheet = Plugin.DataManager.GetExcelSheet<Status>();
|
||||
if (sheet != null)
|
||||
{
|
||||
// Left Eye
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1184));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1454));
|
||||
|
||||
// Battle Litany
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(786));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1414));
|
||||
|
||||
// Brotherhood
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1185));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2174));
|
||||
|
||||
// Battle Voice
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(141));
|
||||
|
||||
// Devilment
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1825));
|
||||
|
||||
// Technical Finish
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1822));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2050));
|
||||
|
||||
// Standard Finish
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1821));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2024));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2105));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2113));
|
||||
|
||||
// Embolden
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1239));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1297));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2282));
|
||||
|
||||
// Devotion
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1213));
|
||||
|
||||
// Divination
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1878));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2034));
|
||||
|
||||
// Chain Stratagem
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1221));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1406));
|
||||
|
||||
// Radiant Finale
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2722));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2964));
|
||||
|
||||
// Arcane Circle
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2599));
|
||||
|
||||
// Searing Light
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(2703));
|
||||
|
||||
// Trick Attack
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(638));
|
||||
|
||||
// ------ AST Card Buffs -------
|
||||
// The Balance
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(829));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1338));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1882));
|
||||
|
||||
// The Bole
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(830));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1339));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1883));
|
||||
|
||||
// The Arrow
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(831));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1884));
|
||||
|
||||
// The Spear
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(832));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1885));
|
||||
|
||||
// The Ewer
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(833));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1340));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1886));
|
||||
|
||||
// The Spire
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(834));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1341));
|
||||
config.BlacklistConfig.AddNewEntry(sheet.GetRow(1887));
|
||||
}
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
public CustomEffectsListConfig(Vector2 position, Vector2 size, bool showBuffs, bool showDebuffs, bool showPermanentEffects,
|
||||
GrowthDirections growthDirections, StatusEffectIconConfig iconConfig)
|
||||
: base(position, size, showBuffs, showDebuffs, showPermanentEffects, growthDirections, iconConfig)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
public enum StatusEffectDurationSortType
|
||||
{
|
||||
Ascending,
|
||||
Descending
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user