fix(ui): port retail window control feedback

Map synthetic move and resize affordances to the exact DAT cursors, make chat top chrome movable, and replace stale primary-panel height caps with a dynamic screen-edge constraint. This keeps the retained wrapper adaptation aligned with retail Dragbar/Resizebar behavior.
This commit is contained in:
Erik 2026-07-17 09:40:08 +02:00
parent 3f3cfdac30
commit 06016014bc
16 changed files with 578 additions and 27 deletions

View file

@ -1,6 +1,11 @@
namespace AcDream.App.UI;
/// <summary>Retail global cursor enum metadata used outside LayoutDesc widget states.</summary>
/// <summary>
/// Retail cursor metadata used outside ordinary LayoutDesc widget-state lookup.
/// Global cursors resolve through enum table 6; synthetic retained-window control
/// regions use the exact direct cursor media authored on retail Dragbar/Resizebar
/// elements.
/// </summary>
internal static class RetailCursorCatalog
{
public const uint CursorEnumTable = 6;
@ -32,6 +37,31 @@ internal static class RetailCursorCatalog
return spec.IsValid;
}
/// <summary>
/// Direct <c>MD_Data_Cursor</c> surfaces authored on retail Type-2 Dragbar and
/// Type-9 Resizebar controls. The retained wrapper border has no LayoutDesc
/// element of its own, so it uses the same media through this shared seam.
/// </summary>
public static bool TryGetWindowControlCursor(
CursorFeedbackKind kind,
out UiCursorMedia cursor)
{
// MediaMachine::Update_Cursor @ 0x00465A80 installs these element-local
// cursor DIDs; UIElementManager::CheckCursor @ 0x0045ABF0 preserves the
// captured Dragbar/Resizebar cursor for the complete operation.
cursor = kind switch
{
CursorFeedbackKind.WindowMove => new UiCursorMedia(0x06006119u, 16, 16),
CursorFeedbackKind.ResizeHorizontal => new UiCursorMedia(0x06006128u, 16, 16),
CursorFeedbackKind.ResizeVertical => new UiCursorMedia(0x06005E66u, 16, 16),
CursorFeedbackKind.ResizeDiagonalNwse => new UiCursorMedia(0x06006126u, 16, 16),
CursorFeedbackKind.ResizeDiagonalNesw => new UiCursorMedia(0x06006127u, 16, 16),
_ => default,
};
return cursor.IsValid;
}
}
internal readonly record struct RetailCursorSpec(uint EnumId, int HotspotX, int HotspotY)