Update UIDebug2, ImGuiComponents, ImGuiHelpers (#2081)

* Update ImGuiComponents & ImGuiHelpers
Took some helper functions created for `UiDebug2`, and incorporated them into `ImGuiComponents` / `ImGuiHelpers` instead

- `IconButton()` (and its various overloads) now includes an optional size parameter
- `IconButtonSelect()` has been added, allowing a row or grid of IconButtons to serve as a radio-like input
- `HelpMarker()` now includes an optional color parameter
- `ClickToCopyText()` now includes an optional color parameter, and includes the `FontAwesome.Copy` icon in the tooltip.
- Implemented ImRaii in these files

These changes are intended not to break any existing calls in plugins or within Dalamud itself.

* Fix ambiguous overloads

* UiDebug2 Updates
- Fixed XY coordinate display
- Added AtkValue table to AddonTree display
- Restored old behaviour wherein the Addon display initially only shows the Root node and a collapsed node list
- The above should also fix the Element Selector / Search behaviour, allowing it to scroll correctly to the searched node
- Now displays field offsets for any node/component whose pointer exists in the addon struct
- Tidied up node tree headers by removing memory addresses (they're still readable in the opened tree, of course)
This commit is contained in:
ItsBexy 2024-11-14 16:36:27 -07:00 committed by GitHub
parent 94f16ac16e
commit ee63f60877
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
18 changed files with 649 additions and 278 deletions

View file

@ -3,6 +3,7 @@ using System.Linq;
using System.Numerics;
using Dalamud.Interface.Components;
using FFXIVClientStructs.FFXIV.Component.GUI;
using ImGuiNET;
@ -19,14 +20,12 @@ namespace Dalamud.Interface.Internal.UiDebug2.Browsing;
/// </summary>
public unsafe partial class AddonTree : IDisposable
{
private readonly nint initialPtr;
private AddonPopoutWindow? window;
private AddonTree(string name, nint ptr)
{
this.AddonName = name;
this.initialPtr = ptr;
this.InitialPtr = ptr;
this.PopulateFieldNames(ptr);
}
@ -35,6 +34,11 @@ public unsafe partial class AddonTree : IDisposable
/// </summary>
internal string AddonName { get; init; }
/// <summary>
/// Gets the addon's pointer at the time this <see cref="AddonTree"/> was created.
/// </summary>
internal nint InitialPtr { get; init; }
/// <summary>
/// Gets or sets a collection of trees representing nodes within this addon.
/// </summary>
@ -81,7 +85,7 @@ public unsafe partial class AddonTree : IDisposable
{
if (AddonTrees.TryGetValue(name, out var tree))
{
if (tree.initialPtr == ptr)
if (tree.InitialPtr == ptr)
{
return tree;
}
@ -143,34 +147,47 @@ public unsafe partial class AddonTree : IDisposable
ImGui.SetTooltip("Toggle Popout Window");
}
ImGui.Separator();
PrintFieldValuePair("Address", $"{(nint)addon:X}");
PaddedSeparator(1);
var uldManager = addon->UldManager;
PrintFieldValuePair("Address", $"{(nint)addon:X}");
PrintFieldValuePair("Agent", $"{GameGui.FindAgentInterface(addon):X}");
PrintFieldValuePairs(
("X", $"{addon->X}"),
("Y", $"{addon->X}"),
("Y", $"{addon->Y}"),
("Scale", $"{addon->Scale}"),
("Widget Count", $"{uldManager.ObjectCount}"));
ImGui.Separator();
var addonObj = this.GetAddonObj(addon);
if (addonObj != null)
{
PaddedSeparator();
ShowStruct(addonObj, (ulong)addon);
}
ImGui.Dummy(new(25 * ImGui.GetIO().FontGlobalScale));
ImGui.Separator();
PaddedSeparator();
ResNodeTree.PrintNodeList(uldManager.NodeList, uldManager.NodeListCount, this);
PrintAtkValues(addon);
ImGui.Dummy(new(25 * ImGui.GetIO().FontGlobalScale));
ImGui.Separator();
if (addon->RootNode != null)
{
ResNodeTree.GetOrCreate(addon->RootNode, this).Print(0);
PaddedSeparator();
}
ResNodeTree.PrintNodeListAsTree(addon->CollisionNodeList, (int)addon->CollisionNodeListCount, "Collision List", this, new(0.5F, 0.7F, 1F, 1F));
if (uldManager.NodeList != null)
{
var count = uldManager.NodeListCount;
ResNodeTree.PrintNodeListAsTree(uldManager.NodeList, count, $"Node List [{count}]:", this, new(0, 0.85F, 1, 1));
PaddedSeparator();
}
if (addon->CollisionNodeList != null)
{
ResNodeTree.PrintNodeListAsTree(addon->CollisionNodeList, (int)addon->CollisionNodeListCount, "Collision List", this, new(0.5F, 0.7F, 1F, 1F));
}
if (SearchResults.Length > 0 && Countdown <= 0)
{
@ -218,7 +235,7 @@ public unsafe partial class AddonTree : IDisposable
private bool ValidateAddon(out AtkUnitBase* addon)
{
addon = (AtkUnitBase*)GameGui.GetAddonByName(this.AddonName);
if (addon == null || (nint)addon != this.initialPtr)
if (addon == null || (nint)addon != this.InitialPtr)
{
this.Dispose();
return false;
@ -231,7 +248,7 @@ public unsafe partial class AddonTree : IDisposable
{
if (this.window == null)
{
this.window = new AddonPopoutWindow(this, $"{this.AddonName}###addonPopout{this.initialPtr}");
this.window = new AddonPopoutWindow(this, $"{this.AddonName}###addonPopout{this.InitialPtr}");
PopoutWindows.AddWindow(this.window);
}
else