114 lines
3.5 KiB
C#
114 lines
3.5 KiB
C#
using System.Numerics;
|
|
using Dalamud.Interface;
|
|
using Dalamud.Interface.Internal;
|
|
using Dalamud.Interface.Utility;
|
|
using ImGuiNET;
|
|
using Screenie.Util;
|
|
|
|
namespace Screenie.Ui;
|
|
|
|
internal class Viewer : IDrawable {
|
|
private Plugin Plugin { get; }
|
|
private Guid Id { get; } = Guid.NewGuid();
|
|
private IDalamudTextureWrap? Image { get; set; }
|
|
private Exception? Error { get; set; }
|
|
private bool _disposed;
|
|
private bool _visible = true;
|
|
internal string ImagePath { get; }
|
|
internal Vector2? DotPosition { get; set; }
|
|
|
|
internal Viewer(Plugin plugin, string path) {
|
|
this.Plugin = plugin;
|
|
this.ImagePath = path;
|
|
|
|
Task.Factory.StartNew(async () => {
|
|
try {
|
|
var bytes = await File.ReadAllBytesAsync(this.ImagePath);
|
|
this.Image = await ImageHelper.LoadImageAsync(this.Plugin.Interface.UiBuilder, bytes);
|
|
} catch (Exception ex) {
|
|
this.Error = ex;
|
|
Plugin.Log.Warning(ex, $"Failed to load image at {this.ImagePath}");
|
|
}
|
|
});
|
|
}
|
|
|
|
public void Dispose() {
|
|
if (this._disposed) {
|
|
return;
|
|
}
|
|
|
|
this._disposed = true;
|
|
|
|
// if (this.Image != null) {
|
|
// this.Plugin.Framework.RunOnTick(this.Image.Dispose);
|
|
// }
|
|
this.Image?.Dispose();
|
|
}
|
|
|
|
public DrawStatus Draw()
|
|
{
|
|
if (!this._visible)
|
|
{
|
|
return DrawStatus.Finished;
|
|
}
|
|
|
|
ImGui.PushID($"viewer-{this.ImagePath}-{this.Id}");
|
|
using var popId = new OnDispose(ImGui.PopID);
|
|
|
|
using var end = new OnDispose(ImGui.End);
|
|
if (!ImGui.Begin($"View {Path.GetFileName(this.ImagePath)}", ref this._visible, ImGuiWindowFlags.NoSavedSettings))
|
|
{
|
|
return DrawStatus.Continuing;
|
|
}
|
|
|
|
var viewport = ImGui.GetWindowViewport();
|
|
var viewportSize = viewport.Size;
|
|
|
|
ImGui.SetWindowSize(viewportSize * new Vector2(0.20f), ImGuiCond.Appearing);
|
|
|
|
if (this.Error != null)
|
|
{
|
|
ImGuiHelpers.CenteredText("An error ocurred loading the image.");
|
|
|
|
ImGui.PushFont(UiBuilder.MonoFont);
|
|
using var popFont = new OnDispose(ImGui.PopFont);
|
|
|
|
ImGui.TextUnformatted(this.Error.Message);
|
|
}
|
|
|
|
if (this.Image == null) {
|
|
return DrawStatus.Continuing;
|
|
}
|
|
|
|
var beforeImage = ImGui.GetCursorScreenPos();
|
|
var avail = ImGui.GetContentRegionAvail();
|
|
var imageSize = this.Image.Size;
|
|
|
|
var constrainedX = avail.X < imageSize.X;
|
|
var constrainedY = avail.Y < imageSize.Y;
|
|
var ratio = 1f;
|
|
|
|
var sizeToUse = imageSize;
|
|
if (constrainedX || constrainedY) {
|
|
var dividend = avail / imageSize;
|
|
// scale the image based on the more-constrained dimension
|
|
ratio = dividend.Y > dividend.X
|
|
? dividend.X // X is more constrained
|
|
: dividend.Y; // Y is more constrained
|
|
sizeToUse = imageSize * ratio;
|
|
}
|
|
|
|
ImGui.Image(this.Image.ImGuiHandle, sizeToUse);
|
|
|
|
if (this.DotPosition is { } pos) {
|
|
var scaledPos = pos * ratio;
|
|
var posCoord = beforeImage + scaledPos;
|
|
|
|
ImGui.GetWindowDrawList().AddCircleFilled(posCoord, 6 * ImGuiHelpers.GlobalScale, 0xFF000000);
|
|
ImGui.GetWindowDrawList().AddCircleFilled(posCoord, 4 * ImGuiHelpers.GlobalScale, 0xFFFFFFFF);
|
|
}
|
|
|
|
return DrawStatus.Continuing;
|
|
}
|
|
}
|