feat(fonts): restore the font-selection UI in the appearance tab

This commit is contained in:
2026-06-15 18:41:03 +02:00
parent fe0414dd2b
commit 18834cddae
3 changed files with 218 additions and 2 deletions
+6 -1
View File
@@ -173,11 +173,16 @@ internal static class PluginHostFactory
sp.GetRequiredService<ThemeRegistry>(),
sp.GetRequiredService<ILogger<Ui.Components.Settings.ThemeImportExportRow>>()
));
services.AddSingleton(sp => new Ui.Components.Settings.FontsSection(
sp.GetRequiredService<Plugin>(),
sp.GetRequiredService<FontManager>()
));
services.AddSingleton(sp => new Ui.Components.Settings.Tabs.AppearanceTab(
sp.GetRequiredService<Ui.Components.Settings.ThemePicker>(),
sp.GetRequiredService<Ui.Components.Settings.ColorPicker>(),
sp.GetRequiredService<Ui.Components.Settings.LivePreviewPanel>(),
sp.GetRequiredService<Ui.Components.Settings.ThemeImportExportRow>()
sp.GetRequiredService<Ui.Components.Settings.ThemeImportExportRow>(),
sp.GetRequiredService<Ui.Components.Settings.FontsSection>()
));
services.AddSingleton(sp => new Ui.Components.Settings.Tabs.GeneralTab(
sp.GetRequiredService<Plugin>()
@@ -0,0 +1,206 @@
using Dalamud;
using Dalamud.Bindings.ImGui;
using Dalamud.Interface.FontIdentifier;
using HellionChat.Resources;
using HellionChat.Util;
namespace HellionChat.Ui.Components.Settings;
// Restores the 1.5.6 font-selection UI (1d3b429:Appearance.cs:249-405): pick the
// bundled Hellion font vs a custom global/Japanese/italic font, sizes, and extra
// glyph ranges. v1.6.0 saves live, so any change persists and rebuilds the atlas
// at once (RebuildDelegateFonts, unconditional — a face change keeps the size, so
// the size-gated IfChanged path would miss it).
internal sealed class FontsSection
{
private readonly Plugin _plugin;
private readonly FontManager _fontManager;
public FontsSection(Plugin plugin, FontManager fontManager)
{
_plugin = plugin;
_fontManager = fontManager;
}
private void Apply()
{
_plugin.SaveConfig();
_fontManager.RebuildDelegateFonts();
}
public void Draw()
{
if (!ImGui.CollapsingHeader(HellionStrings.Settings_Section_Fonts))
return;
// Readout so the user can see which font is actually active.
var active =
Plugin.Config.UseHellionFont ? "Hellion Inter (bundled)"
: Plugin.Config.FontsEnabled
? $"Global: {Plugin.Config.GlobalFontV2.FontId.Family.EnglishName}"
: "FFXIV game font";
ImGui.TextDisabled($"Active: {active}");
ImGui.Spacing();
if (
ImGui.Checkbox(
HellionStrings.Theme_UseHellionFont_Name,
ref Plugin.Config.UseHellionFont
)
)
{
if (Plugin.Config.UseHellionFont)
Plugin.Config.FontsEnabled = false;
Apply();
}
ImGuiUtil.HelpMarker(HellionStrings.Theme_UseHellionFont_Description);
ImGui.Spacing();
if (Plugin.Config.UseHellionFont)
{
DrawSizeCombo(Language.Options_FontSize_Name, ref Plugin.Config.FontSizeV2);
ImGui.Spacing();
}
else if (ImGui.Checkbox(Language.Options_FontsEnabled, ref Plugin.Config.FontsEnabled))
{
Apply();
}
var unused = false;
if (!Plugin.Config.UseHellionFont && !Plugin.Config.FontsEnabled)
{
DrawSizeCombo(Language.Options_FontSize_Name, ref Plugin.Config.FontSizeV2);
}
else if (!Plugin.Config.UseHellionFont)
{
DrawFontChooser(
Language.Options_Font_Name,
Plugin.Config.GlobalFontV2,
false,
ref unused,
spec => Plugin.Config.GlobalFontV2 = spec,
() => Plugin.Config.GlobalFontV2 = DefaultFont(DalamudAsset.NotoSansCjkRegular),
"global"
);
ImGuiUtil.HelpMarker(
string.Format(Language.Options_Font_Description, Plugin.PluginName)
);
ImGuiUtil.WarningText(Language.Options_Font_Warning);
ImGui.Spacing();
DrawFontChooser(
Language.Options_JapaneseFont_Name,
Plugin.Config.JapaneseFontV2,
false,
ref unused,
spec => Plugin.Config.JapaneseFontV2 = spec,
() => Plugin.Config.JapaneseFontV2 = DefaultFont(DalamudAsset.NotoSansCjkMedium),
"japanese",
id => !id.LocaleNames?.ContainsKey("ja-jp") ?? false,
"いろはにほへと ちりぬるを"
);
ImGuiUtil.HelpMarker(
string.Format(Language.Options_JapaneseFont_Description, Plugin.PluginName)
);
ImGui.Spacing();
DrawFontChooser(
Language.Options_ItalicFont_Name,
Plugin.Config.ItalicFontV2,
true,
ref Plugin.Config.ItalicEnabled,
spec => Plugin.Config.ItalicFontV2 = spec,
() =>
{
Plugin.Config.ItalicEnabled = false;
Plugin.Config.ItalicFontV2 = DefaultFont(DalamudAsset.NotoSansCjkRegular);
},
"italic"
);
ImGuiUtil.HelpMarker(
string.Format(Language.Options_Italic_Description, Plugin.PluginName)
);
ImGui.Spacing();
}
// ExtraGlyphRanges stays reachable regardless of the font source so the
// user can verify/override the per-language auto-activation (v1.5.3 note).
ImGui.Spacing();
if (ImGui.CollapsingHeader(Language.Options_ExtraGlyphs_Name))
{
ImGuiUtil.HelpMarker(
string.Format(Language.Options_ExtraGlyphs_Description, Plugin.PluginName)
);
var range = (int)Plugin.Config.ExtraGlyphRanges;
var changed = false;
foreach (var extra in Enum.GetValues<ExtraGlyphRanges>())
changed |= ImGui.CheckboxFlags(extra.Name(), ref range, (int)extra);
if (changed)
{
Plugin.Config.ExtraGlyphRanges = (ExtraGlyphRanges)range;
Apply();
}
}
DrawSizeCombo(Language.Options_SymbolsFontSize_Name, ref Plugin.Config.SymbolsFontSizeV2);
ImGuiUtil.HelpMarker(Language.Options_SymbolsFontSize_Description);
ImGui.Spacing();
}
private void DrawSizeCombo(string label, ref float size)
{
var before = size;
ImGuiUtil.FontSizeCombo(label, ref size);
if (!size.Equals(before))
Apply();
}
private void DrawFontChooser(
string label,
SingleFontSpec font,
bool checkbox,
ref bool checkboxValue,
Action<SingleFontSpec> set,
Action reset,
string resetId,
Predicate<IFontFamilyId>? exclusion = null,
string? preview = null
)
{
var prevCheckbox = checkboxValue;
var chooser = ImGuiUtil.FontChooser(
label,
font,
checkbox,
ref checkboxValue,
exclusion,
preview
);
if (checkbox && checkboxValue != prevCheckbox)
Apply();
// The chooser dialog resolves on a worker thread; marshal the result back
// onto the framework thread before touching config + the font atlas.
chooser?.ResultTask.ContinueWith(r =>
{
if (r.IsCompletedSuccessfully)
Plugin.Framework.Run(() =>
{
set(r.Result);
Apply();
});
});
ImGui.SameLine();
if (ImGui.Button($"Reset##{resetId}"))
{
reset();
Apply();
}
}
private static SingleFontSpec DefaultFont(DalamudAsset asset) =>
new() { FontId = new DalamudAssetFontAndFamilyId(asset), SizePt = 12.75f };
}
@@ -11,18 +11,21 @@ internal sealed class AppearanceTab
private readonly ColorPicker _color;
private readonly LivePreviewPanel _preview;
private readonly ThemeImportExportRow _importExport;
private readonly FontsSection _fonts;
public AppearanceTab(
ThemePicker picker,
ColorPicker color,
LivePreviewPanel preview,
ThemeImportExportRow importExport
ThemeImportExportRow importExport,
FontsSection fonts
)
{
_picker = picker;
_color = color;
_preview = preview;
_importExport = importExport;
_fonts = fonts;
}
public void Draw()
@@ -38,6 +41,8 @@ internal sealed class AppearanceTab
ImGui.Spacing();
_importExport.Draw();
ImGui.Separator();
_fonts.Draw();
ImGui.Separator();
_color.Draw();
}
}