mirror of
https://github.com/goatcorp/Dalamud.git
synced 2025-12-13 12:14:16 +01:00
GameGui namespace, Vector2 overloads, convert to properties
This commit is contained in:
parent
d823049635
commit
c7fd52d423
2 changed files with 79 additions and 26 deletions
|
|
@ -1,27 +1,22 @@
|
||||||
using System;
|
using System;
|
||||||
|
using System.Numerics;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
|
|
||||||
using Dalamud.Game.Gui;
|
using Dalamud.Game.Gui.Addons;
|
||||||
using Dalamud.Game.Gui.PartyFinder;
|
using Dalamud.Game.Gui.PartyFinder;
|
||||||
using Dalamud.Game.Text.SeStringHandling.Payloads;
|
using Dalamud.Game.Text.SeStringHandling.Payloads;
|
||||||
using Dalamud.Hooking;
|
using Dalamud.Hooking;
|
||||||
using Dalamud.Interface;
|
using Dalamud.Interface;
|
||||||
|
using Dalamud.Utility;
|
||||||
using Serilog;
|
using Serilog;
|
||||||
using SharpDX;
|
|
||||||
|
|
||||||
namespace Dalamud.Game.Internal.Gui
|
namespace Dalamud.Game.Gui
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// A class handling many aspects of the in-game UI.
|
/// A class handling many aspects of the in-game UI.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public sealed class GameGui : IDisposable
|
public sealed class GameGui : IDisposable
|
||||||
{
|
{
|
||||||
/// <summary>
|
|
||||||
/// The delegate of the native method that gets the Client::UI::UIModule address.
|
|
||||||
/// </summary>
|
|
||||||
/// <returns>The Client::UI::UIModule address.</returns>
|
|
||||||
public readonly GetBaseUIObjectDelegate GetBaseUIObject;
|
|
||||||
|
|
||||||
private readonly Dalamud dalamud;
|
private readonly Dalamud dalamud;
|
||||||
private readonly GameGuiAddressResolver address;
|
private readonly GameGuiAddressResolver address;
|
||||||
|
|
||||||
|
|
@ -148,6 +143,12 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public event EventHandler<bool> OnUiHideToggled;
|
public event EventHandler<bool> OnUiHideToggled;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets a callable delegate for the GetBaseUIObject game method.
|
||||||
|
/// </summary>
|
||||||
|
/// <returns>The Client::UI::UIModule address.</returns>
|
||||||
|
public GetBaseUIObjectDelegate GetBaseUIObject { get; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Gets the <see cref="Chat"/> instance.
|
/// Gets the <see cref="Chat"/> instance.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|
@ -229,13 +230,13 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
/// <param name="worldPos">Coordinates in the world.</param>
|
/// <param name="worldPos">Coordinates in the world.</param>
|
||||||
/// <param name="screenPos">Converted coordinates.</param>
|
/// <param name="screenPos">Converted coordinates.</param>
|
||||||
/// <returns>True if worldPos corresponds to a position in front of the camera.</returns>
|
/// <returns>True if worldPos corresponds to a position in front of the camera.</returns>
|
||||||
public bool WorldToScreen(Vector3 worldPos, out Vector2 screenPos)
|
public bool WorldToScreen(SharpDX.Vector3 worldPos, out SharpDX.Vector2 screenPos)
|
||||||
{
|
{
|
||||||
// Get base object with matrices
|
// Get base object with matrices
|
||||||
var matrixSingleton = this.getMatrixSingleton();
|
var matrixSingleton = this.getMatrixSingleton();
|
||||||
|
|
||||||
// Read current ViewProjectionMatrix plus game window size
|
// Read current ViewProjectionMatrix plus game window size
|
||||||
var viewProjectionMatrix = default(Matrix);
|
var viewProjectionMatrix = default(SharpDX.Matrix);
|
||||||
float width, height;
|
float width, height;
|
||||||
var windowPos = ImGuiHelpers.MainViewport.Pos;
|
var windowPos = ImGuiHelpers.MainViewport.Pos;
|
||||||
|
|
||||||
|
|
@ -250,9 +251,9 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
height = *(rawMatrix + 1);
|
height = *(rawMatrix + 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
Vector3.Transform(ref worldPos, ref viewProjectionMatrix, out Vector3 pCoords);
|
SharpDX.Vector3.Transform(ref worldPos, ref viewProjectionMatrix, out SharpDX.Vector3 pCoords);
|
||||||
|
|
||||||
screenPos = new Vector2(pCoords.X / pCoords.Z, pCoords.Y / pCoords.Z);
|
screenPos = new SharpDX.Vector2(pCoords.X / pCoords.Z, pCoords.Y / pCoords.Z);
|
||||||
|
|
||||||
screenPos.X = (0.5f * width * (screenPos.X + 1f)) + windowPos.X;
|
screenPos.X = (0.5f * width * (screenPos.X + 1f)) + windowPos.X;
|
||||||
screenPos.Y = (0.5f * height * (1f - screenPos.Y)) + windowPos.Y;
|
screenPos.Y = (0.5f * height * (1f - screenPos.Y)) + windowPos.Y;
|
||||||
|
|
@ -262,6 +263,39 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
screenPos.Y > windowPos.Y && screenPos.Y < windowPos.Y + height;
|
screenPos.Y > windowPos.Y && screenPos.Y < windowPos.Y + height;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Converts in-world coordinates to screen coordinates (upper left corner origin).
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="worldPos">Coordinates in the world.</param>
|
||||||
|
/// <param name="screenPos">Converted coordinates.</param>
|
||||||
|
/// <returns>True if worldPos corresponds to a position in front of the camera.</returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// This overload requires a conversion to SharpDX vectors, however the penalty should be negligible.
|
||||||
|
/// </remarks>
|
||||||
|
public bool WorldToScreen(Vector3 worldPos, out Vector2 screenPos)
|
||||||
|
{
|
||||||
|
var result = this.WorldToScreen(worldPos.ToSharpDX(), out var sharpScreenPos);
|
||||||
|
screenPos = sharpScreenPos.ToSystem();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Converts in-world coordinates to screen coordinates (upper left corner origin).
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="worldPos">Coordinates in the world.</param>
|
||||||
|
/// <param name="screenPos">Converted coordinates.</param>
|
||||||
|
/// <returns>True if worldPos corresponds to a position in front of the camera.</returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// This overload requires a conversion to SharpDX vectors, however the penalty should be negligible.
|
||||||
|
/// </remarks>
|
||||||
|
public bool WorldToScreen(Position3 worldPos, out Vector2 screenPos)
|
||||||
|
{
|
||||||
|
// This overload is necessary due to Positon3 implicit operators.
|
||||||
|
var result = this.WorldToScreen((SharpDX.Vector3)worldPos, out var sharpScreenPos);
|
||||||
|
screenPos = sharpScreenPos.ToSystem();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Converts screen coordinates to in-world coordinates via raycasting.
|
/// Converts screen coordinates to in-world coordinates via raycasting.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|
@ -269,7 +303,7 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
/// <param name="worldPos">Converted coordinates.</param>
|
/// <param name="worldPos">Converted coordinates.</param>
|
||||||
/// <param name="rayDistance">How far to search for a collision.</param>
|
/// <param name="rayDistance">How far to search for a collision.</param>
|
||||||
/// <returns>True if successful. On false, worldPos's contents are undefined.</returns>
|
/// <returns>True if successful. On false, worldPos's contents are undefined.</returns>
|
||||||
public bool ScreenToWorld(Vector2 screenPos, out Vector3 worldPos, float rayDistance = 100000.0f)
|
public bool ScreenToWorld(SharpDX.Vector2 screenPos, out SharpDX.Vector3 worldPos, float rayDistance = 100000.0f)
|
||||||
{
|
{
|
||||||
// The game is only visible in the main viewport, so if the cursor is outside
|
// The game is only visible in the main viewport, so if the cursor is outside
|
||||||
// of the game window, do not bother calculating anything
|
// of the game window, do not bother calculating anything
|
||||||
|
|
@ -287,7 +321,7 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
var matrixSingleton = this.getMatrixSingleton();
|
var matrixSingleton = this.getMatrixSingleton();
|
||||||
|
|
||||||
// Read current ViewProjectionMatrix plus game window size
|
// Read current ViewProjectionMatrix plus game window size
|
||||||
var viewProjectionMatrix = default(Matrix);
|
var viewProjectionMatrix = default(SharpDX.Matrix);
|
||||||
float width, height;
|
float width, height;
|
||||||
unsafe
|
unsafe
|
||||||
{
|
{
|
||||||
|
|
@ -302,18 +336,18 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
|
|
||||||
viewProjectionMatrix.Invert();
|
viewProjectionMatrix.Invert();
|
||||||
|
|
||||||
var localScreenPos = new Vector2(screenPos.X - windowPos.X, screenPos.Y - windowPos.Y);
|
var localScreenPos = new SharpDX.Vector2(screenPos.X - windowPos.X, screenPos.Y - windowPos.Y);
|
||||||
var screenPos3D = new Vector3
|
var screenPos3D = new SharpDX.Vector3
|
||||||
{
|
{
|
||||||
X = (localScreenPos.X / width * 2.0f) - 1.0f,
|
X = (localScreenPos.X / width * 2.0f) - 1.0f,
|
||||||
Y = -((localScreenPos.Y / height * 2.0f) - 1.0f),
|
Y = -((localScreenPos.Y / height * 2.0f) - 1.0f),
|
||||||
Z = 0,
|
Z = 0,
|
||||||
};
|
};
|
||||||
|
|
||||||
Vector3.TransformCoordinate(ref screenPos3D, ref viewProjectionMatrix, out var camPos);
|
SharpDX.Vector3.TransformCoordinate(ref screenPos3D, ref viewProjectionMatrix, out var camPos);
|
||||||
|
|
||||||
screenPos3D.Z = 1;
|
screenPos3D.Z = 1;
|
||||||
Vector3.TransformCoordinate(ref screenPos3D, ref viewProjectionMatrix, out var camPosOne);
|
SharpDX.Vector3.TransformCoordinate(ref screenPos3D, ref viewProjectionMatrix, out var camPosOne);
|
||||||
|
|
||||||
var clipPos = camPosOne - camPos;
|
var clipPos = camPosOne - camPos;
|
||||||
clipPos.Normalize();
|
clipPos.Normalize();
|
||||||
|
|
@ -343,7 +377,7 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
worldPos = new Vector3
|
worldPos = new SharpDX.Vector3
|
||||||
{
|
{
|
||||||
X = worldPosArray[0],
|
X = worldPosArray[0],
|
||||||
Y = worldPosArray[1],
|
Y = worldPosArray[1],
|
||||||
|
|
@ -354,6 +388,23 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
return isSuccess;
|
return isSuccess;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Converts screen coordinates to in-world coordinates via raycasting.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="screenPos">Screen coordinates.</param>
|
||||||
|
/// <param name="worldPos">Converted coordinates.</param>
|
||||||
|
/// <param name="rayDistance">How far to search for a collision.</param>
|
||||||
|
/// <returns>True if successful. On false, worldPos's contents are undefined.</returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// This overload requires a conversion to SharpDX vectors, however the penalty should be negligible.
|
||||||
|
/// </remarks>
|
||||||
|
public bool ScreenToWorld(Vector2 screenPos, out Vector3 worldPos, float rayDistance = 100000.0f)
|
||||||
|
{
|
||||||
|
var result = this.ScreenToWorld(screenPos.ToSharpDX(), out var sharpworldPos);
|
||||||
|
worldPos = sharpworldPos.ToSystem();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Gets a pointer to the game's UI module.
|
/// Gets a pointer to the game's UI module.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|
@ -381,12 +432,14 @@ namespace Dalamud.Game.Internal.Gui
|
||||||
/// <param name="name">The addon name.</param>
|
/// <param name="name">The addon name.</param>
|
||||||
/// <param name="index">The index of the addon, starting at 1.</param>
|
/// <param name="index">The index of the addon, starting at 1.</param>
|
||||||
/// <returns>The native memory representation of the addon, if it exists.</returns>
|
/// <returns>The native memory representation of the addon, if it exists.</returns>
|
||||||
public Addon.Addon GetAddonByName(string name, int index)
|
public Addon GetAddonByName(string name, int index)
|
||||||
{
|
{
|
||||||
var addonMem = this.GetUiObjectByName(name, index);
|
var address = this.GetUiObjectByName(name, index);
|
||||||
if (addonMem == IntPtr.Zero) return null;
|
|
||||||
var addonStruct = Marshal.PtrToStructure<Structs.Addon>(addonMem);
|
if (address == IntPtr.Zero)
|
||||||
return new Addon.Addon(addonMem, addonStruct);
|
return null;
|
||||||
|
|
||||||
|
return new Addon(address);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
|
|
||||||
namespace Dalamud.Game.Internal.Gui
|
namespace Dalamud.Game.Gui
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The address resolver for the <see cref="GameGui"/> class.
|
/// The address resolver for the <see cref="GameGui"/> class.
|
||||||
Loading…
Add table
Add a link
Reference in a new issue