From 3058e6bc6d3be61ef1a9999bac18b412ba11f2a1 Mon Sep 17 00:00:00 2001 From: Jon Kazama Date: Fri, 22 May 2026 23:57:12 +0200 Subject: [PATCH] refactor(settings): merge fonts, colours and window style into the Appearance tab --- HellionChat/Plugin.cs | 2 +- .../Resources/HellionStrings.Designer.cs | 16 +- HellionChat/Resources/HellionStrings.resx | 38 +- HellionChat/Ui/Settings.cs | 1 - HellionChat/Ui/SettingsOverview.cs | 9 +- HellionChat/Ui/SettingsTabs/Appearance.cs | 368 ++++++++++++++++-- .../Ui/SettingsTabs/FontsAndColours.cs | 317 --------------- 7 files changed, 372 insertions(+), 379 deletions(-) delete mode 100644 HellionChat/Ui/SettingsTabs/FontsAndColours.cs diff --git a/HellionChat/Plugin.cs b/HellionChat/Plugin.cs index 318f7a5..5c090a4 100755 --- a/HellionChat/Plugin.cs +++ b/HellionChat/Plugin.cs @@ -955,7 +955,7 @@ public sealed class Plugin : IAsyncDalamudPlugin // this same draw thread, so it cannot be null here. // v1.5.3 fix: also push RegularFont when the bundled Inter Light is // selected. Without this, UseHellionFont=true silently fell back to - // the FFXIV Axis font because FontsAndColours forces FontsEnabled + // the FFXIV Axis font because the Appearance tab forces FontsEnabled // off in that branch, and the bundled font never made it into draw. var useRegularFont = Config.FontsEnabled || Config.UseHellionFont; using ((useRegularFont ? FontManager.RegularFont! : FontManager.Axis).Push()) diff --git a/HellionChat/Resources/HellionStrings.Designer.cs b/HellionChat/Resources/HellionStrings.Designer.cs index ce73f14..a130710 100644 --- a/HellionChat/Resources/HellionStrings.Designer.cs +++ b/HellionChat/Resources/HellionStrings.Designer.cs @@ -369,10 +369,6 @@ internal class HellionStrings internal static string Appearance_UseCompactDensity_Description => Get(nameof(Appearance_UseCompactDensity_Description)); // Hellion Chat — v1.2.1 Settings Cleanup: new card titles + subtexts - internal static string Settings_Card_ThemeAndLayout_Title => Get(nameof(Settings_Card_ThemeAndLayout_Title)); - internal static string Settings_Card_ThemeAndLayout_Subtext => Get(nameof(Settings_Card_ThemeAndLayout_Subtext)); - internal static string Settings_Card_FontsAndColours_Title => Get(nameof(Settings_Card_FontsAndColours_Title)); - internal static string Settings_Card_FontsAndColours_Subtext => Get(nameof(Settings_Card_FontsAndColours_Subtext)); internal static string Settings_Card_DataManagement_Title => Get(nameof(Settings_Card_DataManagement_Title)); internal static string Settings_Card_DataManagement_Subtext => Get(nameof(Settings_Card_DataManagement_Subtext)); internal static string Settings_Card_Integrations_Title => Get(nameof(Settings_Card_Integrations_Title)); @@ -385,10 +381,6 @@ internal class HellionStrings internal static string Settings_ThemeAndLayout_WindowOpacity_Name => Get(nameof(Settings_ThemeAndLayout_WindowOpacity_Name)); internal static string Settings_ThemeAndLayout_WindowOpacity_Description => Get(nameof(Settings_ThemeAndLayout_WindowOpacity_Description)); - // Hellion Chat — v1.2.1 Fonts & Colours tab section headings - internal static string Settings_FontsAndColours_Fonts_Heading => Get(nameof(Settings_FontsAndColours_Fonts_Heading)); - internal static string Settings_FontsAndColours_Colours_Heading => Get(nameof(Settings_FontsAndColours_Colours_Heading)); - // Hellion Chat — v1.2.1 Data Management tab section headings internal static string Settings_DataManagement_Storage_Heading => Get(nameof(Settings_DataManagement_Storage_Heading)); internal static string Settings_DataManagement_Retention_Heading => Get(nameof(Settings_DataManagement_Retention_Heading)); @@ -496,4 +488,12 @@ internal class HellionStrings internal static string Settings_Section_Language => Get(nameof(Settings_Section_Language)); internal static string Settings_Section_Performance => Get(nameof(Settings_Section_Performance)); internal static string Settings_Section_Sound_TabsHint => Get(nameof(Settings_Section_Sound_TabsHint)); + + // v1.5.6: Appearance tab collapsible section titles (R6) + internal static string Settings_Section_Theme => Get(nameof(Settings_Section_Theme)); + internal static string Settings_Section_Fonts => Get(nameof(Settings_Section_Fonts)); + internal static string Settings_Section_Colours => Get(nameof(Settings_Section_Colours)); + internal static string Settings_Section_WindowStyle => Get(nameof(Settings_Section_WindowStyle)); + internal static string Settings_Section_Timestamps => Get(nameof(Settings_Section_Timestamps)); + internal static string Settings_Section_Animations => Get(nameof(Settings_Section_Animations)); } diff --git a/HellionChat/Resources/HellionStrings.resx b/HellionChat/Resources/HellionStrings.resx index 74ca24b..83dd0ba 100644 --- a/HellionChat/Resources/HellionStrings.resx +++ b/HellionChat/Resources/HellionStrings.resx @@ -854,18 +854,6 @@ Switches the message layout from the card-row default back to single-line `[HH:mm] Sender: Text` rows. - - Theme & Layout - - - Theme, window frame, and timestamp style. - - - Fonts & Colours - - - Font, font size, and chat colours per channel. - Data management @@ -893,12 +881,6 @@ How transparent the window background is. Lower values let more of the game show through. Tip: Dalamud's per-window menu (hamburger in the title bar) offers per-window overrides for opacity, background blur, click-through, and pinning. Those take precedence over this slider for the respective window. - - Fonts - - - Chat colours - Storage @@ -1152,4 +1134,24 @@ Which sound plays per tab is set in the Channels tab. + + + + Theme + + + Fonts + + + Colours + + + Window style + + + Timestamps + + + Animations + diff --git a/HellionChat/Ui/Settings.cs b/HellionChat/Ui/Settings.cs index 92b2e19..dd2ad5c 100755 --- a/HellionChat/Ui/Settings.cs +++ b/HellionChat/Ui/Settings.cs @@ -51,7 +51,6 @@ public sealed class SettingsWindow : Dalamud.Interface.Windowing.Window [ new General(Plugin, Mutable), new Appearance(Plugin, Mutable, loggerFactory.CreateLogger()), - new FontsAndColours(Plugin, Mutable, loggerFactory.CreateLogger()), new SettingsTabs.Window(Plugin, Mutable), new Chat(Plugin, Mutable), new SettingsTabs.Tabs(Plugin, Mutable), diff --git a/HellionChat/Ui/SettingsOverview.cs b/HellionChat/Ui/SettingsOverview.cs index be64b06..ad633bb 100644 --- a/HellionChat/Ui/SettingsOverview.cs +++ b/HellionChat/Ui/SettingsOverview.cs @@ -21,13 +21,8 @@ internal sealed class SettingsOverview ), ( FontAwesomeIcon.Palette, - HellionStrings.Settings_Card_ThemeAndLayout_Title, - HellionStrings.Settings_Card_ThemeAndLayout_Subtext - ), - ( - FontAwesomeIcon.Font, - HellionStrings.Settings_Card_FontsAndColours_Title, - HellionStrings.Settings_Card_FontsAndColours_Subtext + HellionStrings.Settings_Card_Appearance_Title, + HellionStrings.Settings_Card_Appearance_Subtext ), ( FontAwesomeIcon.WindowMaximize, diff --git a/HellionChat/Ui/SettingsTabs/Appearance.cs b/HellionChat/Ui/SettingsTabs/Appearance.cs index e541671..6dc985b 100644 --- a/HellionChat/Ui/SettingsTabs/Appearance.cs +++ b/HellionChat/Ui/SettingsTabs/Appearance.cs @@ -1,6 +1,11 @@ using System.Numerics; +using Dalamud; using Dalamud.Bindings.ImGui; +using Dalamud.Interface; +using Dalamud.Interface.FontIdentifier; +using Dalamud.Interface.Utility; using Dalamud.Interface.Utility.Raii; +using HellionChat.Code; using HellionChat.Resources; using HellionChat.Themes; using HellionChat.Util; @@ -17,7 +22,7 @@ internal sealed class Appearance : ISettingsTab private string? _applyDismissedFor; public string Name => - HellionStrings.Settings_Card_ThemeAndLayout_Title + "###tabs-themeandlayout"; + HellionStrings.Settings_Tab_Appearance + "###tabs-appearance"; internal Appearance(Plugin plugin, Configuration mutable, ILogger logger) { @@ -28,16 +33,25 @@ internal sealed class Appearance : ISettingsTab public void Draw(bool sectionJustEntered) { - DrawThemeSection(); + DrawThemeSection(sectionJustEntered); ImGui.Spacing(); - DrawWindowStyleSection(); + DrawFontsSection(sectionJustEntered); ImGui.Spacing(); - DrawTimestampStyleSection(); + DrawColoursSection(sectionJustEntered); + ImGui.Spacing(); + DrawWindowStyleSection(sectionJustEntered); + ImGui.Spacing(); + DrawTimestampSection(sectionJustEntered); + ImGui.Spacing(); + DrawAnimationsSection(sectionJustEntered); } - private void DrawThemeSection() + // ── Theme ────────────────────────────────────────────────────────────── + + private void DrawThemeSection(bool sectionJustEntered) { - using var tree = ImRaii.TreeNode(HellionStrings.Settings_ThemeAndLayout_Theme_Heading); + if (sectionJustEntered) ImGui.SetNextItemOpen(false); + using var tree = ImRaii.TreeNode(HellionStrings.Settings_Section_Theme); if (!tree.Success) return; @@ -228,11 +242,301 @@ internal sealed class Appearance : ISettingsTab ImGui.Spacing(); } - private void DrawWindowStyleSection() + // ── Fonts ────────────────────────────────────────────────────────────── + // R3 deliberately NOT applied here — the UseHellionFont/FontsEnabled + // visibility chain has priority over type grouping (R4). + + private void DrawFontsSection(bool sectionJustEntered) { - using var tree = ImRaii.TreeNode( - HellionStrings.Settings_ThemeAndLayout_WindowStyle_Heading + if (sectionJustEntered) ImGui.SetNextItemOpen(false); + using var tree = ImRaii.TreeNode(HellionStrings.Settings_Section_Fonts); + if (!tree.Success) + return; + + using (ImRaii.PushIndent(ImGui.GetStyle().IndentSpacing, false)) + { + if ( + ImGui.Checkbox(HellionStrings.Theme_UseHellionFont_Name, ref Mutable.UseHellionFont) + ) + { + if (Mutable.UseHellionFont) + Mutable.FontsEnabled = false; + } + ImGuiUtil.HelpMarker(HellionStrings.Theme_UseHellionFont_Description); + ImGui.Spacing(); + + if (Mutable.UseHellionFont) + { + // Bundled-font path: only the base font size matters; the + // global / japanese / italic chooser pickers do not apply. + ImGuiUtil.FontSizeCombo(Language.Options_FontSize_Name, ref Mutable.FontSizeV2); + ImGui.Spacing(); + } + else + { + ImGui.Checkbox(Language.Options_FontsEnabled, ref Mutable.FontsEnabled); + ImGui.Spacing(); + } + + var unused = false; + if (!Mutable.UseHellionFont && !Mutable.FontsEnabled) + { + ImGuiUtil.FontSizeCombo(Language.Options_FontSize_Name, ref Mutable.FontSizeV2); + } + else if (!Mutable.UseHellionFont) + { + var globalChooser = ImGuiUtil.FontChooser( + Language.Options_Font_Name, + Mutable.GlobalFontV2, + false, + ref unused + ); + globalChooser?.ResultTask.ContinueWith(r => + { + if (r.IsCompletedSuccessfully) + { + Plugin.Framework.Run(() => Mutable.GlobalFontV2 = r.Result); + } + }); + ImGui.SameLine(); + if (ImGui.Button("Reset##global")) + { + Mutable.GlobalFontV2 = new SingleFontSpec + { + FontId = new DalamudAssetFontAndFamilyId(DalamudAsset.NotoSansCjkRegular), + SizePt = 12.75f, + }; + } + + ImGuiUtil.HelpMarker( + string.Format(Language.Options_Font_Description, Plugin.PluginName) + ); + ImGuiUtil.WarningText(Language.Options_Font_Warning); + ImGui.Spacing(); + + var japaneseChooser = ImGuiUtil.FontChooser( + Language.Options_JapaneseFont_Name, + Mutable.JapaneseFontV2, + false, + ref unused, + id => !id.LocaleNames?.ContainsKey("ja-jp") ?? false, + "いろはにほへと ちりぬるを" + ); + japaneseChooser?.ResultTask.ContinueWith(r => + { + if (r.IsCompletedSuccessfully) + { + Plugin.Framework.Run(() => Mutable.JapaneseFontV2 = r.Result); + } + }); + ImGui.SameLine(); + if (ImGui.Button("Reset##japanese")) + { + Mutable.JapaneseFontV2 = new SingleFontSpec + { + FontId = new DalamudAssetFontAndFamilyId(DalamudAsset.NotoSansCjkMedium), + SizePt = 12.75f, + }; + } + + ImGuiUtil.HelpMarker( + string.Format(Language.Options_JapaneseFont_Description, Plugin.PluginName) + ); + ImGui.Spacing(); + + var italicChooser = ImGuiUtil.FontChooser( + Language.Options_ItalicFont_Name, + Mutable.ItalicFontV2, + true, + ref Mutable.ItalicEnabled + ); + italicChooser?.ResultTask.ContinueWith(r => + { + if (r.IsCompletedSuccessfully) + { + Plugin.Framework.Run(() => Mutable.ItalicFontV2 = r.Result); + } + }); + ImGui.SameLine(); + if (ImGui.Button("Reset##italic")) + { + Mutable.ItalicEnabled = false; + Mutable.ItalicFontV2 = new SingleFontSpec + { + FontId = new DalamudAssetFontAndFamilyId(DalamudAsset.NotoSansCjkRegular), + SizePt = 12.75f, + }; + } + + ImGuiUtil.HelpMarker( + string.Format(Language.Options_Italic_Description, Plugin.PluginName) + ); + ImGui.Spacing(); + } + + // v1.5.3: ExtraGlyphRanges is an atlas-wide property and stays + // reachable regardless of UseHellionFont / FontsEnabled state so + // users can verify or override the auto-activation on language change. + ImGui.Spacing(); + if (ImGui.CollapsingHeader(Language.Options_ExtraGlyphs_Name)) + { + ImGuiUtil.HelpMarker( + string.Format(Language.Options_ExtraGlyphs_Description, Plugin.PluginName) + ); + + var range = (int)Mutable.ExtraGlyphRanges; + foreach (var extra in Enum.GetValues()) + { + ImGui.CheckboxFlags(extra.Name(), ref range, (int)extra); + } + + Mutable.ExtraGlyphRanges = (ExtraGlyphRanges)range; + } + + ImGuiUtil.FontSizeCombo( + Language.Options_SymbolsFontSize_Name, + ref Mutable.SymbolsFontSizeV2 + ); + ImGuiUtil.HelpMarker(Language.Options_SymbolsFontSize_Description); + + ImGui.Spacing(); + } + } + + // ── Colours ──────────────────────────────────────────────────────────── + + private void DrawColoursSection(bool sectionJustEntered) + { + if (sectionJustEntered) ImGui.SetNextItemOpen(false); + using var tree = ImRaii.TreeNode(HellionStrings.Settings_Section_Colours); + if (!tree.Success) + return; + + using (ImRaii.PushIndent(ImGui.GetStyle().IndentSpacing, false)) + { + DrawColourPresetButtons(); + ImGui.TextDisabled(HellionStrings.Settings_Appearance_Colours_PresetsHint); + ImGui.Spacing(); + ImGui.Separator(); + ImGui.Spacing(); + + ImGui.Checkbox( + Language.Options_ColorSelectedInputChannelButton_Name, + ref Mutable.ColorSelectedInputChannelButton + ); + ImGuiUtil.HelpMarker(Language.Options_ColorSelectedInputChannelButton_Description); + ImGui.Spacing(); + + foreach (var (_, types) in ChatTypeExt.SortOrder) + { + foreach (var type in types) + { + if ( + ImGuiUtil.IconButton( + FontAwesomeIcon.UndoAlt, + $"{type}", + Language.Options_ChatColours_Reset + ) + ) + { + Mutable.ChatColours.Remove(type); + } + + ImGui.SameLine(); + + if ( + ImGuiUtil.IconButton( + FontAwesomeIcon.LongArrowAltDown, + $"{type}", + Language.Options_ChatColours_Import + ) + ) + { + var gameColour = Plugin.Functions.Chat.GetChannelColor(type); + Mutable.ChatColours[type] = gameColour ?? type.DefaultColor() ?? 0; + } + + ImGui.SameLine(); + + var vec = Mutable.ChatColours.TryGetValue(type, out var colour) + ? ColourUtil.RgbaToVector3(colour) + : ColourUtil.RgbaToVector3(type.DefaultColor() ?? 0); + if (ImGui.ColorEdit3(type.Name(), ref vec, ImGuiColorEditFlags.NoInputs)) + { + Mutable.ChatColours[type] = ColourUtil.Vector3ToRgba(vec); + } + } + } + + ImGui.Spacing(); + } + } + + private void DrawColourPresetButtons() + { + var first = true; + foreach (var (_, preset) in ChatColourPresets.All) + { + if (!first) + { + ImGui.SameLine(); + } + first = false; + + if (preset.IsBrandPreset) + { + var border = ColourUtil.RgbaToVector3(ColourUtil.ComponentsToRgba(255, 128, 200)); + var btn = ColourUtil.RgbaToVector3(ColourUtil.ComponentsToRgba(74, 42, 106)); + ImGui.PushStyleColor( + ImGuiCol.Border, + new System.Numerics.Vector4(border.X, border.Y, border.Z, 1f) + ); + ImGui.PushStyleColor( + ImGuiCol.Button, + new System.Numerics.Vector4(btn.X, btn.Y, btn.Z, 1f) + ); + ImGui.PushStyleVar(ImGuiStyleVar.FrameBorderSize, 1.5f); + } + + if (ImGui.Button(GetPresetLabel(preset))) + { + ApplyPreset(preset); + } + + if (preset.IsBrandPreset) + { + ImGui.PopStyleVar(); + ImGui.PopStyleColor(2); + } + } + } + + private static string GetPresetLabel(ChatColourPreset preset) + { + var localized = HellionStrings.ResourceManager.GetString( + preset.LocalizationKey, + HellionStrings.Culture ); + return string.IsNullOrEmpty(localized) ? preset.DisplayName : localized; + } + + private void ApplyPreset(ChatColourPreset preset) + { + foreach (var (channel, colour) in preset.Colours) + { + Mutable.ChatColours[channel] = colour; + } + Plugin.SaveConfig(); + GlobalParametersCache.Refresh(); + _logger.LogDebug($"Applied chat colour preset: {preset.DisplayName}"); + } + + // ── Window style ─────────────────────────────────────────────────────── + + private void DrawWindowStyleSection(bool sectionJustEntered) + { + if (sectionJustEntered) ImGui.SetNextItemOpen(false); + using var tree = ImRaii.TreeNode(HellionStrings.Settings_Section_WindowStyle); if (!tree.Success) return; @@ -313,28 +617,15 @@ internal sealed class Appearance : ISettingsTab Mutable.WindowOpacityInactive = inactiveOpacityPercent / 100f; } ImGuiUtil.HelpMarker(HellionStrings.Settings_ThemeAndLayout_WindowOpacityInactive_Description); - - ImGui.Spacing(); - ImGui.Separator(); - ImGui.Spacing(); - - // Master accessibility toggle for the v1.5.4 motion work: the - // theme crossfade, the sidebar/card hover lerps and the - // unread-tab pulse all read Config.ReduceMotion and snap - // instantly when it is on. - ImGui.Checkbox( - HellionStrings.Settings_ThemeAndLayout_ReduceMotion_Name, - ref Mutable.ReduceMotion - ); - ImGuiUtil.HelpMarker(HellionStrings.Settings_ThemeAndLayout_ReduceMotion_Description); } } - private void DrawTimestampStyleSection() + // ── Timestamps ───────────────────────────────────────────────────────── + + private void DrawTimestampSection(bool sectionJustEntered) { - using var tree = ImRaii.TreeNode( - HellionStrings.Settings_ThemeAndLayout_TimestampStyle_Heading - ); + if (sectionJustEntered) ImGui.SetNextItemOpen(false); + using var tree = ImRaii.TreeNode(HellionStrings.Settings_Section_Timestamps); if (!tree.Success) return; @@ -371,4 +662,27 @@ internal sealed class Appearance : ISettingsTab ImGuiUtil.HelpMarker(Language.Options_Use24HourClock_Description); } } + + // ── Animations ───────────────────────────────────────────────────────── + + private void DrawAnimationsSection(bool sectionJustEntered) + { + if (sectionJustEntered) ImGui.SetNextItemOpen(false); + using var tree = ImRaii.TreeNode(HellionStrings.Settings_Section_Animations); + if (!tree.Success) + return; + + using (ImRaii.PushIndent(ImGui.GetStyle().IndentSpacing, false)) + { + // Master accessibility toggle for the v1.5.4 motion work: the + // theme crossfade, the sidebar/card hover lerps and the + // unread-tab pulse all read Config.ReduceMotion and snap + // instantly when it is on. + ImGui.Checkbox( + HellionStrings.Settings_ThemeAndLayout_ReduceMotion_Name, + ref Mutable.ReduceMotion + ); + ImGuiUtil.HelpMarker(HellionStrings.Settings_ThemeAndLayout_ReduceMotion_Description); + } + } } diff --git a/HellionChat/Ui/SettingsTabs/FontsAndColours.cs b/HellionChat/Ui/SettingsTabs/FontsAndColours.cs deleted file mode 100644 index 14d95b6..0000000 --- a/HellionChat/Ui/SettingsTabs/FontsAndColours.cs +++ /dev/null @@ -1,317 +0,0 @@ -using Dalamud; -using Dalamud.Bindings.ImGui; -using Dalamud.Interface; -using Dalamud.Interface.FontIdentifier; -using Dalamud.Interface.Utility; -using Dalamud.Interface.Utility.Raii; -using HellionChat.Code; -using HellionChat.Resources; -using HellionChat.Util; -using Microsoft.Extensions.Logging; - -namespace HellionChat.Ui.SettingsTabs; - -internal sealed class FontsAndColours : ISettingsTab -{ - private Plugin Plugin { get; } - private Configuration Mutable { get; } - private readonly ILogger _logger; - - public string Name => - HellionStrings.Settings_Card_FontsAndColours_Title + "###tabs-fontsandcolours"; - - internal FontsAndColours(Plugin plugin, Configuration mutable, ILogger logger) - { - Plugin = plugin; - Mutable = mutable; - _logger = logger; - } - - public void Draw(bool sectionJustEntered) - { - DrawFontsSection(); - ImGui.Spacing(); - DrawColoursSection(); - } - - private void DrawFontsSection() - { - using var tree = ImRaii.TreeNode(HellionStrings.Settings_FontsAndColours_Fonts_Heading); - if (!tree.Success) - return; - - using (ImRaii.PushIndent(ImGui.GetStyle().IndentSpacing, false)) - { - if ( - ImGui.Checkbox(HellionStrings.Theme_UseHellionFont_Name, ref Mutable.UseHellionFont) - ) - { - if (Mutable.UseHellionFont) - Mutable.FontsEnabled = false; - } - ImGuiUtil.HelpMarker(HellionStrings.Theme_UseHellionFont_Description); - ImGui.Spacing(); - - if (Mutable.UseHellionFont) - { - // Bundled-font path: only the base font size matters; the - // global / japanese / italic chooser pickers do not apply. - ImGuiUtil.FontSizeCombo(Language.Options_FontSize_Name, ref Mutable.FontSizeV2); - ImGui.Spacing(); - } - else - { - ImGui.Checkbox(Language.Options_FontsEnabled, ref Mutable.FontsEnabled); - ImGui.Spacing(); - } - - var unused = false; - if (!Mutable.UseHellionFont && !Mutable.FontsEnabled) - { - ImGuiUtil.FontSizeCombo(Language.Options_FontSize_Name, ref Mutable.FontSizeV2); - } - else if (!Mutable.UseHellionFont) - { - var globalChooser = ImGuiUtil.FontChooser( - Language.Options_Font_Name, - Mutable.GlobalFontV2, - false, - ref unused - ); - globalChooser?.ResultTask.ContinueWith(r => - { - if (r.IsCompletedSuccessfully) - { - Plugin.Framework.Run(() => Mutable.GlobalFontV2 = r.Result); - } - }); - ImGui.SameLine(); - if (ImGui.Button("Reset##global")) - { - Mutable.GlobalFontV2 = new SingleFontSpec - { - FontId = new DalamudAssetFontAndFamilyId(DalamudAsset.NotoSansCjkRegular), - SizePt = 12.75f, - }; - } - - ImGuiUtil.HelpMarker( - string.Format(Language.Options_Font_Description, Plugin.PluginName) - ); - ImGuiUtil.WarningText(Language.Options_Font_Warning); - ImGui.Spacing(); - - var japaneseChooser = ImGuiUtil.FontChooser( - Language.Options_JapaneseFont_Name, - Mutable.JapaneseFontV2, - false, - ref unused, - id => !id.LocaleNames?.ContainsKey("ja-jp") ?? false, - "いろはにほへと ちりぬるを" - ); - japaneseChooser?.ResultTask.ContinueWith(r => - { - if (r.IsCompletedSuccessfully) - { - Plugin.Framework.Run(() => Mutable.JapaneseFontV2 = r.Result); - } - }); - ImGui.SameLine(); - if (ImGui.Button("Reset##japanese")) - { - Mutable.JapaneseFontV2 = new SingleFontSpec - { - FontId = new DalamudAssetFontAndFamilyId(DalamudAsset.NotoSansCjkMedium), - SizePt = 12.75f, - }; - } - - ImGuiUtil.HelpMarker( - string.Format(Language.Options_JapaneseFont_Description, Plugin.PluginName) - ); - ImGui.Spacing(); - - var italicChooser = ImGuiUtil.FontChooser( - Language.Options_ItalicFont_Name, - Mutable.ItalicFontV2, - true, - ref Mutable.ItalicEnabled - ); - italicChooser?.ResultTask.ContinueWith(r => - { - if (r.IsCompletedSuccessfully) - { - Plugin.Framework.Run(() => Mutable.ItalicFontV2 = r.Result); - } - }); - ImGui.SameLine(); - if (ImGui.Button("Reset##italic")) - { - Mutable.ItalicEnabled = false; - Mutable.ItalicFontV2 = new SingleFontSpec - { - FontId = new DalamudAssetFontAndFamilyId(DalamudAsset.NotoSansCjkRegular), - SizePt = 12.75f, - }; - } - - ImGuiUtil.HelpMarker( - string.Format(Language.Options_Italic_Description, Plugin.PluginName) - ); - ImGui.Spacing(); - } - - // v1.5.3: ExtraGlyphRanges is an atlas-wide property and stays - // reachable regardless of UseHellionFont / FontsEnabled state so - // users can verify or override the auto-activation on language change. - ImGui.Spacing(); - if (ImGui.CollapsingHeader(Language.Options_ExtraGlyphs_Name)) - { - ImGuiUtil.HelpMarker( - string.Format(Language.Options_ExtraGlyphs_Description, Plugin.PluginName) - ); - - var range = (int)Mutable.ExtraGlyphRanges; - foreach (var extra in Enum.GetValues()) - { - ImGui.CheckboxFlags(extra.Name(), ref range, (int)extra); - } - - Mutable.ExtraGlyphRanges = (ExtraGlyphRanges)range; - } - - ImGuiUtil.FontSizeCombo( - Language.Options_SymbolsFontSize_Name, - ref Mutable.SymbolsFontSizeV2 - ); - ImGuiUtil.HelpMarker(Language.Options_SymbolsFontSize_Description); - - ImGui.Spacing(); - } - } - - private void DrawColoursSection() - { - using var tree = ImRaii.TreeNode(HellionStrings.Settings_FontsAndColours_Colours_Heading); - if (!tree.Success) - return; - - using (ImRaii.PushIndent(ImGui.GetStyle().IndentSpacing, false)) - { - DrawColourPresetButtons(); - ImGui.TextDisabled(HellionStrings.Settings_Appearance_Colours_PresetsHint); - ImGui.Spacing(); - ImGui.Separator(); - ImGui.Spacing(); - - ImGui.Checkbox( - Language.Options_ColorSelectedInputChannelButton_Name, - ref Mutable.ColorSelectedInputChannelButton - ); - ImGuiUtil.HelpMarker(Language.Options_ColorSelectedInputChannelButton_Description); - ImGui.Spacing(); - - foreach (var (_, types) in ChatTypeExt.SortOrder) - { - foreach (var type in types) - { - if ( - ImGuiUtil.IconButton( - FontAwesomeIcon.UndoAlt, - $"{type}", - Language.Options_ChatColours_Reset - ) - ) - { - Mutable.ChatColours.Remove(type); - } - - ImGui.SameLine(); - - if ( - ImGuiUtil.IconButton( - FontAwesomeIcon.LongArrowAltDown, - $"{type}", - Language.Options_ChatColours_Import - ) - ) - { - var gameColour = Plugin.Functions.Chat.GetChannelColor(type); - Mutable.ChatColours[type] = gameColour ?? type.DefaultColor() ?? 0; - } - - ImGui.SameLine(); - - var vec = Mutable.ChatColours.TryGetValue(type, out var colour) - ? ColourUtil.RgbaToVector3(colour) - : ColourUtil.RgbaToVector3(type.DefaultColor() ?? 0); - if (ImGui.ColorEdit3(type.Name(), ref vec, ImGuiColorEditFlags.NoInputs)) - { - Mutable.ChatColours[type] = ColourUtil.Vector3ToRgba(vec); - } - } - } - - ImGui.Spacing(); - } - } - - private void DrawColourPresetButtons() - { - var first = true; - foreach (var (_, preset) in ChatColourPresets.All) - { - if (!first) - { - ImGui.SameLine(); - } - first = false; - - if (preset.IsBrandPreset) - { - var border = ColourUtil.RgbaToVector3(ColourUtil.ComponentsToRgba(255, 128, 200)); - var btn = ColourUtil.RgbaToVector3(ColourUtil.ComponentsToRgba(74, 42, 106)); - ImGui.PushStyleColor( - ImGuiCol.Border, - new System.Numerics.Vector4(border.X, border.Y, border.Z, 1f) - ); - ImGui.PushStyleColor( - ImGuiCol.Button, - new System.Numerics.Vector4(btn.X, btn.Y, btn.Z, 1f) - ); - ImGui.PushStyleVar(ImGuiStyleVar.FrameBorderSize, 1.5f); - } - - if (ImGui.Button(GetPresetLabel(preset))) - { - ApplyPreset(preset); - } - - if (preset.IsBrandPreset) - { - ImGui.PopStyleVar(); - ImGui.PopStyleColor(2); - } - } - } - - private static string GetPresetLabel(ChatColourPreset preset) - { - var localized = HellionStrings.ResourceManager.GetString( - preset.LocalizationKey, - HellionStrings.Culture - ); - return string.IsNullOrEmpty(localized) ? preset.DisplayName : localized; - } - - private void ApplyPreset(ChatColourPreset preset) - { - foreach (var (channel, colour) in preset.Colours) - { - Mutable.ChatColours[channel] = colour; - } - Plugin.SaveConfig(); - GlobalParametersCache.Refresh(); - _logger.LogDebug($"Applied chat colour preset: {preset.DisplayName}"); - } -}