mirror of
https://github.com/goatcorp/Dalamud.git
synced 2025-12-12 18:27:23 +01:00
Update docs and exposed API
This commit is contained in:
parent
7eb4bf8ab4
commit
e7c7cdaa29
6 changed files with 128 additions and 95 deletions
|
|
@ -699,35 +699,38 @@ internal class InterfaceManager : IDisposable, IServiceType
|
|||
{
|
||||
this.dalamudAtlas = fontAtlasFactory
|
||||
.CreateFontAtlas(nameof(InterfaceManager), FontAtlasAutoRebuildMode.Disable);
|
||||
this.defaultFontHandle = (IFontHandle.IInternal)this.dalamudAtlas.NewDelegateFontHandle(
|
||||
e => e.OnPreBuild(tk => tk.AddDalamudDefaultFont(DefaultFontSizePx)));
|
||||
this.iconFontHandle = (IFontHandle.IInternal)this.dalamudAtlas.NewDelegateFontHandle(
|
||||
e => e.OnPreBuild(
|
||||
tk => tk.AddFontAwesomeIconFont(
|
||||
new()
|
||||
{
|
||||
SizePx = DefaultFontSizePx,
|
||||
GlyphMinAdvanceX = DefaultFontSizePx,
|
||||
GlyphMaxAdvanceX = DefaultFontSizePx,
|
||||
})));
|
||||
this.monoFontHandle = (IFontHandle.IInternal)this.dalamudAtlas.NewDelegateFontHandle(
|
||||
e => e.OnPreBuild(
|
||||
tk => tk.AddDalamudAssetFont(
|
||||
DalamudAsset.InconsolataRegular,
|
||||
new() { SizePx = DefaultFontSizePx })));
|
||||
this.dalamudAtlas.BuildStepChange += e => e.OnPostPromotion(
|
||||
tk =>
|
||||
{
|
||||
// Note: the first call of this function is done outside the main thread; this is expected.
|
||||
// Do not use DefaultFont, IconFont, and MonoFont.
|
||||
// Use font handles directly.
|
||||
using (this.dalamudAtlas.SuppressAutoRebuild())
|
||||
{
|
||||
this.defaultFontHandle = (IFontHandle.IInternal)this.dalamudAtlas.NewDelegateFontHandle(
|
||||
e => e.OnPreBuild(tk => tk.AddDalamudDefaultFont(DefaultFontSizePx)));
|
||||
this.iconFontHandle = (IFontHandle.IInternal)this.dalamudAtlas.NewDelegateFontHandle(
|
||||
e => e.OnPreBuild(
|
||||
tk => tk.AddFontAwesomeIconFont(
|
||||
new()
|
||||
{
|
||||
SizePx = DefaultFontSizePx,
|
||||
GlyphMinAdvanceX = DefaultFontSizePx,
|
||||
GlyphMaxAdvanceX = DefaultFontSizePx,
|
||||
})));
|
||||
this.monoFontHandle = (IFontHandle.IInternal)this.dalamudAtlas.NewDelegateFontHandle(
|
||||
e => e.OnPreBuild(
|
||||
tk => tk.AddDalamudAssetFont(
|
||||
DalamudAsset.InconsolataRegular,
|
||||
new() { SizePx = DefaultFontSizePx })));
|
||||
this.dalamudAtlas.BuildStepChange += e => e.OnPostPromotion(
|
||||
tk =>
|
||||
{
|
||||
// Note: the first call of this function is done outside the main thread; this is expected.
|
||||
// Do not use DefaultFont, IconFont, and MonoFont.
|
||||
// Use font handles directly.
|
||||
|
||||
// Fill missing glyphs in MonoFont from DefaultFont
|
||||
tk.CopyGlyphsAcrossFonts(this.defaultFontHandle.ImFont, this.monoFontHandle.ImFont, true);
|
||||
// Fill missing glyphs in MonoFont from DefaultFont
|
||||
tk.CopyGlyphsAcrossFonts(this.defaultFontHandle.ImFont, this.monoFontHandle.ImFont, true);
|
||||
|
||||
// Broadcast to auto-rebuilding instances
|
||||
this.AfterBuildFonts?.Invoke();
|
||||
});
|
||||
// Broadcast to auto-rebuilding instances
|
||||
this.AfterBuildFonts?.Invoke();
|
||||
});
|
||||
}
|
||||
|
||||
// This will wait for scene on its own. We just wait for this.dalamudAtlas.BuildTask in this.InitScene.
|
||||
_ = this.dalamudAtlas.BuildFontsAsync(false);
|
||||
|
|
|
|||
|
|
@ -1,7 +1,6 @@
|
|||
using System.Threading.Tasks;
|
||||
|
||||
using Dalamud.Interface.GameFonts;
|
||||
using Dalamud.Interface.ManagedFontAtlas.Internals;
|
||||
|
||||
using ImGuiNET;
|
||||
|
||||
|
|
@ -54,25 +53,73 @@ public interface IFontAtlas : IDisposable
|
|||
/// </summary>
|
||||
bool IsGlobalScaled { get; }
|
||||
|
||||
/// <inheritdoc cref="GamePrebakedFontHandle.HandleManager.NewFontHandle"/>
|
||||
/// <summary>
|
||||
/// Suppresses automatically rebuilding fonts for the scope.
|
||||
/// </summary>
|
||||
/// <returns>An instance of <see cref="IDisposable"/> that will release the suppression.</returns>
|
||||
/// <remarks>
|
||||
/// Use when you will be creating multiple new handles, and want rebuild to trigger only when you're done doing so.
|
||||
/// This function will effectively do nothing, if <see cref="AutoRebuildMode"/> is set to
|
||||
/// <see cref="FontAtlasAutoRebuildMode.Disable"/>.
|
||||
/// </remarks>
|
||||
/// <example>
|
||||
/// <code>
|
||||
/// using (atlas.SuppressBuild()) {
|
||||
/// this.font1 = atlas.NewGameFontHandle(...);
|
||||
/// this.font2 = atlas.NewDelegateFontHandle(...);
|
||||
/// }
|
||||
/// </code>
|
||||
/// </example>
|
||||
public IDisposable SuppressAutoRebuild();
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new <see cref="IFontHandle"/> from game's built-in fonts.
|
||||
/// </summary>
|
||||
/// <param name="style">Font to use.</param>
|
||||
/// <returns>Handle to a font that may or may not be ready yet.</returns>
|
||||
public IFontHandle NewGameFontHandle(GameFontStyle style);
|
||||
|
||||
/// <inheritdoc cref="DelegateFontHandle.HandleManager.NewFontHandle"/>
|
||||
/// <summary>
|
||||
/// Creates a new IFontHandle using your own callbacks.
|
||||
/// </summary>
|
||||
/// <param name="buildStepDelegate">Callback for <see cref="IFontAtlas.BuildStepChange"/>.</param>
|
||||
/// <returns>Handle to a font that may or may not be ready yet.</returns>
|
||||
/// <example>
|
||||
/// <b>On initialization</b>:
|
||||
/// <code>
|
||||
/// this.fontHandle = atlas.NewDelegateFontHandle(e => e.OnPreBuild(tk => {
|
||||
/// var config = new SafeFontConfig { SizePx = 16 };
|
||||
/// config.MergeFont = tk.AddFontFromFile(@"C:\Windows\Fonts\comic.ttf", config);
|
||||
/// tk.AddGameSymbol(config);
|
||||
/// tk.AddExtraGlyphsForDalamudLanguage(config);
|
||||
/// // optionally do the following if you have to add more than one font here,
|
||||
/// // to specify which font added during this delegate is the final font to use.
|
||||
/// tk.Font = config.MergeFont;
|
||||
/// }));
|
||||
/// // or
|
||||
/// this.fontHandle = atlas.NewDelegateFontHandle(e => e.OnPreBuild(tk => tk.AddDalamudDefaultFont(36)));
|
||||
/// </code>
|
||||
/// <br />
|
||||
/// <b>On use</b>:
|
||||
/// <code>
|
||||
/// using (this.fontHandle.Push())
|
||||
/// ImGui.TextUnformatted("Example");
|
||||
/// </code>
|
||||
/// </example>
|
||||
public IFontHandle NewDelegateFontHandle(FontAtlasBuildStepDelegate buildStepDelegate);
|
||||
|
||||
/// <inheritdoc cref="IFontHandleManager.FreeFontHandle"/>
|
||||
public void FreeFontHandle(IFontHandle handle);
|
||||
|
||||
/// <summary>
|
||||
/// Queues rebuilding fonts, on the main thread.<br />
|
||||
/// Note that <see cref="BuildTask"/> would not necessarily get changed from calling this function.
|
||||
/// </summary>
|
||||
/// <exception cref="InvalidOperationException">If <see cref="AutoRebuildMode"/> is <see cref="FontAtlasAutoRebuildMode.Async"/>.</exception>
|
||||
void BuildFontsOnNextFrame();
|
||||
|
||||
/// <summary>
|
||||
/// Rebuilds fonts immediately, on the current thread.<br />
|
||||
/// Even the callback for <see cref="FontAtlasBuildStep.PostPromotion"/> will be called on the same thread.
|
||||
/// </summary>
|
||||
/// <exception cref="InvalidOperationException">If <see cref="AutoRebuildMode"/> is <see cref="FontAtlasAutoRebuildMode.Async"/>.</exception>
|
||||
void BuildFontsImmediately();
|
||||
|
||||
/// <summary>
|
||||
|
|
@ -80,5 +127,6 @@ public interface IFontAtlas : IDisposable
|
|||
/// </summary>
|
||||
/// <param name="callPostPromotionOnMainThread">Call <see cref="FontAtlasBuildStep.PostPromotion"/> on the main thread.</param>
|
||||
/// <returns>The task.</returns>
|
||||
/// <exception cref="InvalidOperationException">If <see cref="AutoRebuildMode"/> is <see cref="FontAtlasAutoRebuildMode.OnNewFrame"/>.</exception>
|
||||
Task BuildFontsAsync(bool callPostPromotionOnMainThread = true);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -88,11 +88,7 @@ internal class DelegateFontHandle : IFontHandle.IInternal
|
|||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new IFontHandle using your own callbacks.
|
||||
/// </summary>
|
||||
/// <param name="buildStepDelegate">Callback for <see cref="IFontAtlas.BuildStepChange"/>.</param>
|
||||
/// <returns>Handle to a font that may or may not be ready yet.</returns>
|
||||
/// <inheritdoc cref="IFontAtlas.NewDelegateFontHandle"/>
|
||||
public IFontHandle NewFontHandle(FontAtlasBuildStepDelegate buildStepDelegate)
|
||||
{
|
||||
var key = new DelegateFontHandle(this, buildStepDelegate);
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@
|
|||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
using System.Linq;
|
||||
using System.Reactive.Disposables;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
|
|
@ -203,6 +204,9 @@ internal sealed partial class FontAtlasFactory
|
|||
private Task<FontAtlasBuiltData> buildTask = EmptyTask;
|
||||
private FontAtlasBuiltData builtData;
|
||||
|
||||
private int buildSuppressionCounter;
|
||||
private bool buildSuppressionSuppressed;
|
||||
|
||||
private int buildIndex;
|
||||
private bool buildQueued;
|
||||
private bool disposed = false;
|
||||
|
|
@ -356,6 +360,19 @@ internal sealed partial class FontAtlasFactory
|
|||
GC.SuppressFinalize(this);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public IDisposable SuppressAutoRebuild()
|
||||
{
|
||||
this.buildSuppressionCounter++;
|
||||
return Disposable.Create(
|
||||
() =>
|
||||
{
|
||||
this.buildSuppressionCounter--;
|
||||
if (this.buildSuppressionSuppressed)
|
||||
this.OnRebuildRecommend();
|
||||
});
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public IFontHandle NewGameFontHandle(GameFontStyle style) => this.gameFontHandleManager.NewFontHandle(style);
|
||||
|
||||
|
|
@ -363,15 +380,6 @@ internal sealed partial class FontAtlasFactory
|
|||
public IFontHandle NewDelegateFontHandle(FontAtlasBuildStepDelegate buildStepDelegate) =>
|
||||
this.delegateFontHandleManager.NewFontHandle(buildStepDelegate);
|
||||
|
||||
/// <inheritdoc/>
|
||||
public void FreeFontHandle(IFontHandle handle)
|
||||
{
|
||||
foreach (var manager in this.fontHandleManagers)
|
||||
{
|
||||
manager.FreeFontHandle(handle);
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public void BuildFontsOnNextFrame()
|
||||
{
|
||||
|
|
@ -688,6 +696,13 @@ internal sealed partial class FontAtlasFactory
|
|||
if (this.disposed)
|
||||
return;
|
||||
|
||||
if (this.buildSuppressionCounter > 0)
|
||||
{
|
||||
this.buildSuppressionSuppressed = true;
|
||||
return;
|
||||
}
|
||||
|
||||
this.buildSuppressionSuppressed = false;
|
||||
this.factory.Framework.RunOnFrameworkThread(
|
||||
() =>
|
||||
{
|
||||
|
|
|
|||
|
|
@ -157,11 +157,7 @@ internal class GamePrebakedFontHandle : IFontHandle.IInternal
|
|||
this.Substance = null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new <see cref="IFontHandle"/> from game's built-in fonts.
|
||||
/// </summary>
|
||||
/// <param name="style">Font to use.</param>
|
||||
/// <returns>Handle to a font that may or may not be ready yet.</returns>
|
||||
/// <inheritdoc cref="IFontAtlas.NewGameFontHandle"/>
|
||||
public IFontHandle NewFontHandle(GameFontStyle style)
|
||||
{
|
||||
var handle = new GamePrebakedFontHandle(this, style);
|
||||
|
|
|
|||
|
|
@ -37,7 +37,6 @@ public sealed class UiBuilder : IDisposable
|
|||
private readonly DalamudConfiguration configuration = Service<DalamudConfiguration>.Get();
|
||||
|
||||
private readonly DisposeSafety.ScopedFinalizer scopedFinalizer = new();
|
||||
private readonly IFontAtlas privateAtlas;
|
||||
|
||||
private bool hasErrorWindow = false;
|
||||
private bool lastFrameUiHideState = false;
|
||||
|
|
@ -61,14 +60,14 @@ public sealed class UiBuilder : IDisposable
|
|||
this.interfaceManager.ResizeBuffers += this.OnResizeBuffers;
|
||||
this.scopedFinalizer.Add(() => this.interfaceManager.ResizeBuffers -= this.OnResizeBuffers);
|
||||
|
||||
this.privateAtlas =
|
||||
this.FontAtlas =
|
||||
this.scopedFinalizer
|
||||
.Add(
|
||||
Service<FontAtlasFactory>
|
||||
.Get()
|
||||
.CreateFontAtlas(namespaceName, FontAtlasAutoRebuildMode.Disable));
|
||||
this.privateAtlas.BuildStepChange += this.PrivateAtlasOnBuildStepChange;
|
||||
this.privateAtlas.RebuildRecommend += this.RebuildFonts;
|
||||
this.FontAtlas.BuildStepChange += this.PrivateAtlasOnBuildStepChange;
|
||||
this.FontAtlas.RebuildRecommend += this.RebuildFonts;
|
||||
}
|
||||
catch
|
||||
{
|
||||
|
|
@ -104,7 +103,7 @@ public sealed class UiBuilder : IDisposable
|
|||
/// (at any time), so you should both reload your custom fonts and restore those
|
||||
/// pointers inside this handler.
|
||||
/// </summary>
|
||||
[Obsolete($"Use {nameof(NewDelegateFontHandle)} instead.", false)]
|
||||
[Obsolete($"Use {nameof(this.FontAtlas)} instead.", false)]
|
||||
public event Action? BuildFonts;
|
||||
|
||||
/// <summary>
|
||||
|
|
@ -113,7 +112,7 @@ public sealed class UiBuilder : IDisposable
|
|||
/// (at any time), so you should both reload your custom fonts and restore those
|
||||
/// pointers inside this handler.
|
||||
/// </summary>
|
||||
[Obsolete($"Use {nameof(NewDelegateFontHandle)} instead.", false)]
|
||||
[Obsolete($"Use {nameof(this.FontAtlas)} instead.", false)]
|
||||
public event Action? AfterBuildFonts;
|
||||
|
||||
/// <summary>
|
||||
|
|
@ -145,7 +144,7 @@ public sealed class UiBuilder : IDisposable
|
|||
/// <remarks>
|
||||
/// A font handle corresponding to this font can be obtained with:
|
||||
/// <code>
|
||||
/// uiBuilderOrFontAtlas.NewDelegateFontHandle(
|
||||
/// fontAtlas.NewDelegateFontHandle(
|
||||
/// e => e.OnPreBuild(
|
||||
/// tk => tk.AddDalamudDefaultFont(UiBuilder.DefaultFontSizePt)));
|
||||
/// </code>
|
||||
|
|
@ -159,7 +158,7 @@ public sealed class UiBuilder : IDisposable
|
|||
/// <remarks>
|
||||
/// A font handle corresponding to this font can be obtained with:
|
||||
/// <code>
|
||||
/// uiBuilderOrFontAtlas.NewDelegateFontHandle(
|
||||
/// fontAtlas.NewDelegateFontHandle(
|
||||
/// e => e.OnPreBuild(
|
||||
/// tk => tk.AddFontAwesomeIconFont(new() { SizePt = UiBuilder.DefaultFontSizePt })));
|
||||
/// </code>
|
||||
|
|
@ -173,7 +172,7 @@ public sealed class UiBuilder : IDisposable
|
|||
/// <remarks>
|
||||
/// A font handle corresponding to this font can be obtained with:
|
||||
/// <code>
|
||||
/// uiBuilderOrFontAtlas.NewDelegateFontHandle(
|
||||
/// fontAtlas.NewDelegateFontHandle(
|
||||
/// e => e.OnPreBuild(
|
||||
/// tk => tk.AddDalamudAssetFont(
|
||||
/// DalamudAsset.InconsolataRegular,
|
||||
|
|
@ -251,6 +250,11 @@ public sealed class UiBuilder : IDisposable
|
|||
/// </summary>
|
||||
public bool UiPrepared => Service<InterfaceManager.InterfaceManagerWithScene>.GetNullable() != null;
|
||||
|
||||
/// <summary>
|
||||
/// Gets the plugin-private font atlas.
|
||||
/// </summary>
|
||||
public IFontAtlas FontAtlas { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a value indicating whether statistics about UI draw time should be collected.
|
||||
/// </summary>
|
||||
|
|
@ -418,40 +422,11 @@ public sealed class UiBuilder : IDisposable
|
|||
/// </summary>
|
||||
/// <param name="style">Font to get.</param>
|
||||
/// <returns>Handle to the game font which may or may not be available for use yet.</returns>
|
||||
[Obsolete($"Use {nameof(NewGameFontHandle)} instead.", false)]
|
||||
[Obsolete($"Use {nameof(this.FontAtlas)}.{nameof(IFontAtlas.NewGameFontHandle)} instead.", false)]
|
||||
public GameFontHandle GetGameFontHandle(GameFontStyle style) => new(
|
||||
(IFontHandle.IInternal)this.NewGameFontHandle(style),
|
||||
(IFontHandle.IInternal)this.FontAtlas.NewGameFontHandle(style),
|
||||
Service<FontAtlasFactory>.Get());
|
||||
|
||||
/// <inheritdoc cref="IFontAtlas.NewGameFontHandle"/>
|
||||
public IFontHandle NewGameFontHandle(GameFontStyle style) => this.privateAtlas.NewGameFontHandle(style);
|
||||
|
||||
/// <inheritdoc cref="IFontAtlas.NewDelegateFontHandle"/>
|
||||
/// <example>
|
||||
/// <b>On initialization</b>:
|
||||
/// <code>
|
||||
/// this.fontHandle = uiBuilder.NewDelegateFontHandle(e => e.OnPreBuild(tk => {
|
||||
/// var config = new SafeFontConfig { SizePx = 16 };
|
||||
/// config.MergeFont = tk.AddFontFromFile(@"C:\Windows\Fonts\comic.ttf", config);
|
||||
/// tk.AddGameSymbol(config);
|
||||
/// tk.AddExtraGlyphsForDalamudLanguage(config);
|
||||
/// // optionally do the following if you have to add more than one font here,
|
||||
/// // to specify which font added during this delegate is the final font to use.
|
||||
/// tk.Font = config.MergeFont;
|
||||
/// }));
|
||||
/// // or
|
||||
/// this.fontHandle = uiBuilder.NewDelegateFontHandle(e => e.OnPreBuild(tk => tk.AddDalamudDefaultFont(36)));
|
||||
/// </code>
|
||||
/// <br />
|
||||
/// <b>On use</b>:
|
||||
/// <code>
|
||||
/// using (this.fontHandle.Push())
|
||||
/// ImGui.TextUnformatted("Example");
|
||||
/// </code>
|
||||
/// </example>
|
||||
public IFontHandle NewDelegateFontHandle(FontAtlasBuildStepDelegate buildStepDelegate) =>
|
||||
this.privateAtlas.NewDelegateFontHandle(buildStepDelegate);
|
||||
|
||||
/// <summary>
|
||||
/// Call this to queue a rebuild of the font atlas.<br/>
|
||||
/// This will invoke any <see cref="BuildFonts"/> and <see cref="AfterBuildFonts"/> handlers and ensure that any
|
||||
|
|
@ -461,9 +436,9 @@ public sealed class UiBuilder : IDisposable
|
|||
{
|
||||
Log.Verbose("[FONT] {0} plugin is initiating FONT REBUILD", this.namespaceName);
|
||||
if (this.AfterBuildFonts is null && this.BuildFonts is null)
|
||||
this.privateAtlas.BuildFontsAsync();
|
||||
this.FontAtlas.BuildFontsAsync();
|
||||
else
|
||||
this.privateAtlas.BuildFontsOnNextFrame();
|
||||
this.FontAtlas.BuildFontsOnNextFrame();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
|
@ -579,7 +554,7 @@ public sealed class UiBuilder : IDisposable
|
|||
}
|
||||
|
||||
// just in case, if something goes wrong, prevent drawing; otherwise it probably will crash.
|
||||
if (!this.privateAtlas.BuildTask.IsCompletedSuccessfully
|
||||
if (!this.FontAtlas.BuildTask.IsCompletedSuccessfully
|
||||
&& (this.BuildFonts is not null || this.AfterBuildFonts is not null))
|
||||
{
|
||||
return;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue