Initial release: HSUI v1.0.0.0 - HUD replacement with configurable hotbars

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-01-30 23:52:46 -05:00
commit f37369cdda
202 changed files with 40137 additions and 0 deletions
+69
View File
@@ -0,0 +1,69 @@
/*
* Computes HUD layout addon name hashes at runtime using the game's own hash function.
* AddonConfigEntry uses CRC32 of "name_a" - UIGlobals.ComputeAddonNameHash does this.
* This ensures correct hashes across game patches without hardcoded values.
*/
using FFXIVClientStructs.FFXIV.Client.UI;
using System;
using System.Collections.Generic;
namespace HSUI.Helpers
{
public static class HudLayoutHashHelper
{
private static readonly Dictionary<string, uint> _cache = new();
private static DateTime _lastResolveErrorLog = DateTime.MinValue;
private const double ResolveErrorLogIntervalSeconds = 10.0;
/// <summary>Get AddonNameHash for a layout addon. Addon name is without _a suffix (e.g. "_ParameterWidget").</summary>
public static uint GetHash(string addonName)
{
if (string.IsNullOrEmpty(addonName))
return 0;
if (_cache.TryGetValue(addonName, out var cached))
return cached;
try
{
uint hash = UIGlobals.ComputeAddonNameHash(addonName);
_cache[addonName] = hash;
return hash;
}
catch (Exception ex)
{
var now = DateTime.UtcNow;
if ((now - _lastResolveErrorLog).TotalSeconds >= ResolveErrorLogIntervalSeconds)
{
_lastResolveErrorLog = now;
Plugin.Logger.Warning($"[HSUI] HudLayoutHashHelper: resolver not ready (e.g. '{addonName}'): {ex.Message}");
}
return 0;
}
}
/// <summary>Dump all HudLayout addon names and their hashes to the log (for debugging).</summary>
public static void DumpHudLayoutAddonsToLog()
{
try
{
var span = FFXIVClientStructs.FFXIV.Client.UI.Misc.HudLayoutAddon.GetSpan();
Plugin.Logger.Information("[HSUI] HudLayout addon names and hashes (name -> hash):");
for (int i = 0; i < span.Length; i++)
{
ref var addon = ref span[i];
if (!addon.AddonName.HasValue) continue;
string name = addon.AddonName.ToString() ?? "(null)";
if (string.IsNullOrEmpty(name)) continue;
uint hash = GetHash(name);
Plugin.Logger.Information($" [{i}] {name} -> 0x{hash:X8}");
}
}
catch (Exception ex)
{
Plugin.Logger.Error($"[HSUI] HudLayoutHashHelper.DumpHudLayoutAddonsToLog failed: {ex.Message}\n{ex.StackTrace}");
}
}
}
}