From 018524fb8f73e8bbdf3d55b5648dabe67caca944 Mon Sep 17 00:00:00 2001 From: srkizer Date: Wed, 7 Aug 2024 05:31:24 +0900 Subject: [PATCH] Fix UIColor layout (#1998) * Fix UIColor layout * Handle correctly --- .../Internal/SeStringColorStackSet.cs | 10 +- .../Windows/Data/Widgets/UIColorWidget.cs | 161 +++++++++++------- 2 files changed, 105 insertions(+), 66 deletions(-) diff --git a/Dalamud/Interface/ImGuiSeStringRenderer/Internal/SeStringColorStackSet.cs b/Dalamud/Interface/ImGuiSeStringRenderer/Internal/SeStringColorStackSet.cs index dc99b7faa..5a7e87e1b 100644 --- a/Dalamud/Interface/ImGuiSeStringRenderer/Internal/SeStringColorStackSet.cs +++ b/Dalamud/Interface/ImGuiSeStringRenderer/Internal/SeStringColorStackSet.cs @@ -148,10 +148,12 @@ internal sealed class SeStringColorStackSet if (expr.TryGetUInt(out var bgra)) { - // NOTE: if it reads a `0`, then it seems to be doing something else. - // See case 0x12 from `Component::GUI::AtkFontAnalyzerBase.vf4`. - // Fix when someone figures what's this about. - rgbaStack.Add(ColorHelpers.SwapRedBlue(bgra) | 0xFF000000u); + // adds the color on the top of the stack. This makes usages like effectively + // become a no-op if no value is provided. + if (bgra == 0) + rgbaStack.Add(rgbaStack[^1]); + else + rgbaStack.Add(ColorHelpers.SwapRedBlue(bgra) | 0xFF000000u); return rgbaStack[^1]; } diff --git a/Dalamud/Interface/Internal/Windows/Data/Widgets/UIColorWidget.cs b/Dalamud/Interface/Internal/Windows/Data/Widgets/UIColorWidget.cs index b3e7346df..575bce23c 100644 --- a/Dalamud/Interface/Internal/Windows/Data/Widgets/UIColorWidget.cs +++ b/Dalamud/Interface/Internal/Windows/Data/Widgets/UIColorWidget.cs @@ -1,9 +1,13 @@ using System.Buffers.Binary; using System.Linq; using System.Numerics; +using System.Text; using Dalamud.Data; +using Dalamud.Interface.ImGuiNotification; +using Dalamud.Interface.ImGuiNotification.Internal; using Dalamud.Interface.ImGuiSeStringRenderer.Internal; +using Dalamud.Interface.Utility; using Dalamud.Storage.Assets; using ImGuiNET; @@ -41,21 +45,35 @@ internal class UiColorWidget : IDataWindowWidget this.colors ??= Service.Get().GetExcelSheet()?.ToArray(); if (this.colors is null) return; - ImGui.TextUnformatted("Color notation is #RRGGBB."); + Service.Get().CompileAndDrawWrapped( + "· Color notation is #" + + "RR" + + "GG" + + "BB.
" + + "· Click on a color to copy the color code.
" + + "· Hover on a color to preview the text with edge, when the next color has been used together."); if (!ImGui.BeginTable("UIColor", 5)) return; ImGui.TableSetupScrollFreeze(0, 1); - var basew = ImGui.CalcTextSize("9").X; - ImGui.TableSetupColumn("Row ID", ImGuiTableColumnFlags.WidthFixed, basew * 7); - ImGui.TableSetupColumn("Dark", ImGuiTableColumnFlags.WidthFixed, basew * 17); - ImGui.TableSetupColumn("Light", ImGuiTableColumnFlags.WidthFixed, basew * 17); - ImGui.TableSetupColumn("Classic FF", ImGuiTableColumnFlags.WidthFixed, basew * 17); - ImGui.TableSetupColumn("Clear Blue", ImGuiTableColumnFlags.WidthFixed, basew * 17); + var rowidw = ImGui.CalcTextSize("9999999").X; + var colorw = ImGui.CalcTextSize("#999999").X; + colorw = Math.Max(colorw, ImGui.CalcTextSize("#AAAAAA").X); + colorw = Math.Max(colorw, ImGui.CalcTextSize("#BBBBBB").X); + colorw = Math.Max(colorw, ImGui.CalcTextSize("#CCCCCC").X); + colorw = Math.Max(colorw, ImGui.CalcTextSize("#DDDDDD").X); + colorw = Math.Max(colorw, ImGui.CalcTextSize("#EEEEEE").X); + colorw = Math.Max(colorw, ImGui.CalcTextSize("#FFFFFF").X); + colorw += ImGui.GetFrameHeight() + ImGui.GetStyle().FramePadding.X; + ImGui.TableSetupColumn("Row ID", ImGuiTableColumnFlags.WidthFixed, rowidw); + ImGui.TableSetupColumn("Dark", ImGuiTableColumnFlags.WidthFixed, colorw); + ImGui.TableSetupColumn("Light", ImGuiTableColumnFlags.WidthFixed, colorw); + ImGui.TableSetupColumn("Classic FF", ImGuiTableColumnFlags.WidthFixed, colorw); + ImGui.TableSetupColumn("Clear Blue", ImGuiTableColumnFlags.WidthFixed, colorw); ImGui.TableHeadersRow(); var clipper = new ImGuiListClipperPtr(ImGuiNative.ImGuiListClipper_ImGuiListClipper()); - clipper.Begin(this.colors.Length); + clipper.Begin(this.colors.Length, ImGui.GetFrameHeightWithSpacing()); while (clipper.Step()) { for (var i = clipper.DisplayStart; i < clipper.DisplayEnd; i++) @@ -70,32 +88,32 @@ internal class UiColorWidget : IDataWindowWidget ImGui.TableNextColumn(); ImGui.AlignTextToFramePadding(); ImGui.PushID($"row{id}_col1"); - DrawColorColumn(this.colors[i].UIForeground); - if (id is >= 500 and < 580) + if (this.DrawColorColumn(this.colors[i].UIForeground) && + i + 1 < this.colors.Length && this.colors[i + 1].RowId == id + 1) DrawEdgePreview(id, this.colors[i].UIForeground, this.colors[i + 1].UIForeground); ImGui.PopID(); ImGui.TableNextColumn(); ImGui.AlignTextToFramePadding(); ImGui.PushID($"row{id}_col2"); - DrawColorColumn(this.colors[i].UIGlow); - if (id is >= 500 and < 580) + if (this.DrawColorColumn(this.colors[i].UIGlow) && + i + 1 < this.colors.Length && this.colors[i + 1].RowId == id + 1) DrawEdgePreview(id, this.colors[i].UIGlow, this.colors[i + 1].UIGlow); ImGui.PopID(); ImGui.TableNextColumn(); ImGui.AlignTextToFramePadding(); ImGui.PushID($"row{id}_col3"); - DrawColorColumn(this.colors[i].Unknown2); - if (id is >= 500 and < 580) + if (this.DrawColorColumn(this.colors[i].Unknown2) && + i + 1 < this.colors.Length && this.colors[i + 1].RowId == id + 1) DrawEdgePreview(id, this.colors[i].Unknown2, this.colors[i + 1].Unknown2); ImGui.PopID(); ImGui.TableNextColumn(); ImGui.AlignTextToFramePadding(); ImGui.PushID($"row{id}_col4"); - DrawColorColumn(this.colors[i].Unknown3); - if (id is >= 500 and < 580) + if (this.DrawColorColumn(this.colors[i].Unknown3) && + i + 1 < this.colors.Length && this.colors[i + 1].RowId == id + 1) DrawEdgePreview(id, this.colors[i].Unknown3, this.colors[i + 1].Unknown3); ImGui.PopID(); } @@ -105,58 +123,77 @@ internal class UiColorWidget : IDataWindowWidget ImGui.EndTable(); } - private static void DrawColorColumn(uint sheetColor) - { - sheetColor = BinaryPrimitives.ReverseEndianness(sheetColor); - ImGui.Image( - Service.Get().White4X4.ImGuiHandle, - new(ImGui.GetFrameHeight()), - Vector2.Zero, - Vector2.One, - ImGui.ColorConvertU32ToFloat4(sheetColor | 0xFF000000u)); - ImGui.SameLine(); - ImGui.TextUnformatted($"#{sheetColor & 0xFF:X02}{(sheetColor >> 8) & 0xFF:X02}{(sheetColor >> 16) & 0xFF:X02}"); - } - private static void DrawEdgePreview(uint id, uint sheetColor, uint sheetColor2) { - ImGui.SameLine(); - if (Service.Get().Draw( - new("+E"u8), - new() - { - Edge = true, - Color = BinaryPrimitives.ReverseEndianness(sheetColor) | 0xFF000000u, - EdgeColor = BinaryPrimitives.ReverseEndianness(sheetColor2) | 0xFF000000u, - }, - "+E"u8).Clicked) - ImGui.SetClipboardText($"+E"); - if (ImGui.IsItemHovered()) - ImGui.SetTooltip($"+E"); + ImGui.BeginTooltip(); + Span buf = stackalloc byte[256]; + var ptr = 0; + ptr += Encoding.UTF8.GetBytes("", buf[ptr..]); + Service.Get().Draw( + buf[..ptr], + new() + { + Edge = true, + Color = BinaryPrimitives.ReverseEndianness(sheetColor) | 0xFF000000u, + EdgeColor = BinaryPrimitives.ReverseEndianness(sheetColor2) | 0xFF000000u, + WrapWidth = float.PositiveInfinity, + }); - ImGui.SameLine(); - ImGui.AlignTextToFramePadding(); - if (Service.Get().Draw( - new("+F"u8), - new() - { - Edge = true, - Color = BinaryPrimitives.ReverseEndianness(sheetColor2) | 0xFF000000u, - EdgeColor = BinaryPrimitives.ReverseEndianness(sheetColor) | 0xFF000000u, - }, - "+F"u8).Clicked) - ImGui.SetClipboardText($"+E"); - if (ImGui.IsItemHovered()) - ImGui.SetTooltip($"+E"); + ptr = 0; + ptr += Encoding.UTF8.GetBytes("", buf[ptr..]); + Service.Get().Draw( + buf[..ptr], + new() + { + Edge = true, + Color = BinaryPrimitives.ReverseEndianness(sheetColor2) | 0xFF000000u, + EdgeColor = BinaryPrimitives.ReverseEndianness(sheetColor) | 0xFF000000u, + WrapWidth = float.PositiveInfinity, + }); + ImGui.EndTooltip(); } - private Vector4 ConvertToVector4(uint color) + private bool DrawColorColumn(uint sheetColor) { - var r = (byte)(color >> 24); - var g = (byte)(color >> 16); - var b = (byte)(color >> 8); - var a = (byte)color; + sheetColor = BinaryPrimitives.ReverseEndianness(sheetColor); + var rgbtext = $"#{sheetColor & 0xFF:X02}{(sheetColor >> 8) & 0xFF:X02}{(sheetColor >> 16) & 0xFF:X02}"; + var size = new Vector2(ImGui.GetFrameHeight()); + size.X += ImGui.CalcTextSize(rgbtext).X + ImGui.GetStyle().FramePadding.X; - return new Vector4(r / 255.0f, g / 255.0f, b / 255.0f, a / 255.0f); + var off = ImGui.GetCursorScreenPos(); + ImGui.GetWindowDrawList().AddRectFilled( + off, + off + new Vector2(size.Y), + sheetColor | 0xFF000000u); + ImGui.GetWindowDrawList().AddText( + off + ImGui.GetStyle().FramePadding + new Vector2(size.Y, 0), + ImGui.GetColorU32(ImGuiCol.Text), + rgbtext); + + if (ImGui.InvisibleButton("##copy", size)) + { + ImGui.SetClipboardText(rgbtext); + Service.Get().AddNotification( + new() + { + Content = $"Copied \"{rgbtext}\".", + Title = this.DisplayName, + Type = NotificationType.Success, + }); + } + + return ImGui.IsItemHovered(); } }