refactor: update for net5

This commit is contained in:
Anna 2021-08-22 16:46:41 -04:00
parent 15d103c3e3
commit 11a41cd706
13 changed files with 92 additions and 81 deletions

View File

@ -1,8 +1,8 @@
using System;
using System.Runtime.InteropServices;
using Dalamud.Game;
using Dalamud.Game.ClientState;
using Dalamud.Game.ClientState.Actors.Types;
using Dalamud.Game.ClientState.Objects;
using Dalamud.Game.ClientState.Objects.Types;
using Dalamud.Game.Text.SeStringHandling;
using Dalamud.Hooking;
@ -16,12 +16,12 @@ namespace XivCommon.Functions {
internal const string ChatBubbleUpdate = "48 85 D2 0F 84 ?? ?? ?? ?? 48 89 5C 24 ?? 57 48 83 EC 20 8B 41 0C";
}
private ClientState ClientState { get; }
private ObjectTable ObjectTable { get; }
private SeStringManager SeStringManager { get; }
private delegate void OpenChatBubbleDelegate(IntPtr manager, IntPtr actor, IntPtr text, byte a4);
private delegate void OpenChatBubbleDelegate(IntPtr manager, IntPtr @object, IntPtr text, byte a4);
private delegate void UpdateChatBubbleDelegate(IntPtr bubblePtr, IntPtr actor);
private delegate void UpdateChatBubbleDelegate(IntPtr bubblePtr, IntPtr @object);
private Hook<OpenChatBubbleDelegate>? OpenChatBubbleHook { get; }
@ -30,12 +30,12 @@ namespace XivCommon.Functions {
/// <summary>
/// The delegate for chat bubble events.
/// </summary>
public delegate void OnChatBubbleDelegate(ref Actor actor, ref SeString text);
public delegate void OnChatBubbleDelegate(ref GameObject @object, ref SeString text);
/// <summary>
/// The delegate for chat bubble update events.
/// </summary>
public delegate void OnUpdateChatBubbleDelegate(ref Actor actor);
public delegate void OnUpdateChatBubbleDelegate(ref GameObject @object);
/// <summary>
/// <para>
@ -57,8 +57,8 @@ namespace XivCommon.Functions {
/// </summary>
public event OnUpdateChatBubbleDelegate? OnUpdateBubble;
internal ChatBubbles(ClientState clientState, SigScanner scanner, SeStringManager manager, bool hookEnabled) {
this.ClientState = clientState;
internal ChatBubbles(ObjectTable objectTable, SigScanner scanner, SeStringManager manager, bool hookEnabled) {
this.ObjectTable = objectTable;
this.SeStringManager = manager;
if (!hookEnabled) {
@ -82,22 +82,22 @@ namespace XivCommon.Functions {
this.UpdateChatBubbleHook?.Dispose();
}
private void OpenChatBubbleDetour(IntPtr manager, IntPtr actor, IntPtr text, byte a4) {
private void OpenChatBubbleDetour(IntPtr manager, IntPtr @object, IntPtr text, byte a4) {
try {
this.OpenChatBubbleDetourInner(manager, actor, text, a4);
this.OpenChatBubbleDetourInner(manager, @object, text, a4);
} catch (Exception ex) {
Logger.LogError(ex, "Exception in chat bubble detour");
this.OpenChatBubbleHook!.Original(manager, actor, text, a4);
this.OpenChatBubbleHook!.Original(manager, @object, text, a4);
}
}
private void OpenChatBubbleDetourInner(IntPtr manager, IntPtr actorPtr, IntPtr textPtr, byte a4) {
var actor = this.ClientState.Actors.CreateActorReference(actorPtr);
private void OpenChatBubbleDetourInner(IntPtr manager, IntPtr @objectPtr, IntPtr textPtr, byte a4) {
var @object = this.ObjectTable.CreateObjectReference(objectPtr);
var text = Util.ReadSeString(textPtr, this.SeStringManager);
try {
this.OnChatBubble?.Invoke(ref actor, ref text);
this.OnChatBubble?.Invoke(ref @object, ref text);
} catch (Exception ex) {
Logger.LogError(ex, "Exception in chat bubble event");
}
@ -106,31 +106,31 @@ namespace XivCommon.Functions {
unsafe {
fixed (byte* newTextPtr = newText) {
this.OpenChatBubbleHook!.Original(manager, actor.Address, (IntPtr) newTextPtr, a4);
this.OpenChatBubbleHook!.Original(manager, @object.Address, (IntPtr) newTextPtr, a4);
}
}
}
private void UpdateChatBubbleDetour(IntPtr bubblePtr, IntPtr actor) {
private void UpdateChatBubbleDetour(IntPtr bubblePtr, IntPtr @object) {
try {
this.UpdateChatBubbleDetourInner(bubblePtr, actor);
this.UpdateChatBubbleDetourInner(bubblePtr, @object);
} catch (Exception ex) {
Logger.LogError(ex, "Exception in update chat bubble detour");
this.UpdateChatBubbleHook!.Original(bubblePtr, actor);
this.UpdateChatBubbleHook!.Original(bubblePtr, @object);
}
}
private void UpdateChatBubbleDetourInner(IntPtr bubblePtr, IntPtr actorPtr) {
private void UpdateChatBubbleDetourInner(IntPtr bubblePtr, IntPtr objectPtr) {
// var bubble = (ChatBubble*) bubblePtr;
var actor = this.ClientState.Actors.CreateActorReference(actorPtr);
var @object = this.ObjectTable.CreateObjectReference(objectPtr);
try {
this.OnUpdateBubble?.Invoke(ref actor);
this.OnUpdateBubble?.Invoke(ref @object);
} catch (Exception ex) {
Logger.LogError(ex, "Exception in chat bubble update event");
}
this.UpdateChatBubbleHook!.Original(bubblePtr, actor.Address);
this.UpdateChatBubbleHook!.Original(bubblePtr, @object.Address);
}
}

View File

@ -22,33 +22,33 @@ namespace XivCommon.Functions.ContextMenu {
public string? ParentAddonName { get; }
/// <summary>
/// The actor ID for this context menu. May be invalid (0xE0000000).
/// The object ID for this context menu. May be invalid (0xE0000000).
/// </summary>
public uint ActorId { get; }
public uint ObjectId { get; }
/// <summary>
/// The lower half of the content ID of the actor for this context menu. May be zero.
/// The lower half of the content ID of the object for this context menu. May be zero.
/// </summary>
public uint ContentIdLower { get; }
/// <summary>
/// The text related to this context menu, usually an actor name.
/// The text related to this context menu, usually an object name.
/// </summary>
public SeString? Text { get; }
/// <summary>
/// The world of the actor this context menu is for, if any.
/// The world of the object this context menu is for, if any.
/// </summary>
public ushort ActorWorld { get; }
public ushort ObjectWorld { get; }
internal BaseContextMenuArgs(IntPtr addon, IntPtr agent, string? parentAddonName, uint actorId, uint contentIdLower, SeString? text, ushort actorWorld) {
internal BaseContextMenuArgs(IntPtr addon, IntPtr agent, string? parentAddonName, uint objectId, uint contentIdLower, SeString? text, ushort objectWorld) {
this.Addon = addon;
this.Agent = agent;
this.ParentAddonName = parentAddonName;
this.ActorId = actorId;
this.ObjectId = objectId;
this.ContentIdLower = contentIdLower;
this.Text = text;
this.ActorWorld = actorWorld;
this.ObjectWorld = objectWorld;
}
}
}

View File

@ -65,7 +65,7 @@ namespace XivCommon.Functions.ContextMenu {
/// </summary>
private const int InventoryMenuActionsOffset = 0x558;
private const int ActorIdOffset = 0xEF0;
private const int ObjectIdOffset = 0xEF0;
private const int ContentIdLowerOffset = 0xEE0;
private const int TextPointerOffset = 0xE08;
private const int WorldOffset = 0xF00;
@ -317,13 +317,13 @@ namespace XivCommon.Functions.ContextMenu {
return this._getAddonByInternalId((IntPtr) stage->RaptureAtkUnitManager, addonId);
}
private unsafe (uint actorId, uint contentIdLower, SeString? text, ushort actorWorld) GetAgentInfo(IntPtr agent) {
var actorId = *(uint*) (agent + ActorIdOffset);
private unsafe (uint objectId, uint contentIdLower, SeString? text, ushort objectWorld) GetAgentInfo(IntPtr agent) {
var objectId = *(uint*) (agent + ObjectIdOffset);
var contentIdLower = *(uint*) (agent + ContentIdLowerOffset);
var textBytes = Util.ReadTerminated(Marshal.ReadIntPtr(agent + TextPointerOffset));
var text = textBytes.Length == 0 ? null : this.SeStringManager.Parse(textBytes);
var actorWorld = *(ushort*) (agent + WorldOffset);
return (actorId, contentIdLower, text, actorWorld);
var objectWorld = *(ushort*) (agent + WorldOffset);
return (objectId, contentIdLower, text, objectWorld);
}
private static unsafe (uint itemId, uint itemAmount, bool itemHq) GetInventoryAgentInfo(IntPtr agent) {
@ -531,10 +531,10 @@ namespace XivCommon.Functions.ContextMenu {
addon,
agent,
parentAddonName,
info.actorId,
info.objectId,
info.contentIdLower,
info.text,
info.actorWorld
info.objectWorld
);
if (nativeItems != null) {
args.Items.AddRange(nativeItems);
@ -636,10 +636,10 @@ namespace XivCommon.Functions.ContextMenu {
addon,
custom.Agent,
addonName,
info.actorId,
info.objectId,
info.contentIdLower,
info.text,
info.actorWorld
info.objectWorld
);
try {

View File

@ -6,7 +6,7 @@ namespace XivCommon.Functions.ContextMenu {
/// Arguments for the context menu item selected delegate.
/// </summary>
public class ContextMenuItemSelectedArgs : BaseContextMenuArgs {
internal ContextMenuItemSelectedArgs(IntPtr addon, IntPtr agent, string? parentAddonName, uint actorId, uint contentIdLower, SeString? text, ushort actorWorld) : base(addon, agent, parentAddonName, actorId, contentIdLower, text, actorWorld) {
internal ContextMenuItemSelectedArgs(IntPtr addon, IntPtr agent, string? parentAddonName, uint objectId, uint contentIdLower, SeString? text, ushort objectWorld) : base(addon, agent, parentAddonName, objectId, contentIdLower, text, objectWorld) {
}
}
}

View File

@ -12,7 +12,7 @@ namespace XivCommon.Functions.ContextMenu {
/// </summary>
public List<BaseContextMenuItem> Items { get; } = new();
internal ContextMenuOpenArgs(IntPtr addon, IntPtr agent, string? parentAddonName, uint actorId, uint contentIdLower, SeString? text, ushort actorWorld) : base(addon, agent, parentAddonName, actorId, contentIdLower, text, actorWorld) {
internal ContextMenuOpenArgs(IntPtr addon, IntPtr agent, string? parentAddonName, uint objectId, uint contentIdLower, SeString? text, ushort objectWorld) : base(addon, agent, parentAddonName, objectId, contentIdLower, text, objectWorld) {
}
}
}

View File

@ -1,7 +1,7 @@
using System;
using System.Runtime.InteropServices;
using Dalamud.Game;
using Dalamud.Game.ClientState.Actors.Types;
using Dalamud.Game.ClientState.Objects.Types;
namespace XivCommon.Functions {
/// <summary>
@ -28,20 +28,20 @@ namespace XivCommon.Functions {
}
/// <summary>
/// Opens the Examine window for the specified actor.
/// Opens the Examine window for the specified object.
/// </summary>
/// <param name="actor">Actor to open window for</param>
/// <param name="object">Object to open window for</param>
/// <exception cref="InvalidOperationException">If the signature for this function could not be found</exception>
public void OpenExamineWindow(Actor actor) {
this.OpenExamineWindow(actor.ActorId);
public void OpenExamineWindow(GameObject @object) {
this.OpenExamineWindow(@object.ObjectId);
}
/// <summary>
/// Opens the Examine window for the actor with the specified ID.
/// Opens the Examine window for the object with the specified ID.
/// </summary>
/// <param name="actorId">Actor ID to open window for</param>
/// <param name="objectId">Object ID to open window for</param>
/// <exception cref="InvalidOperationException">If the signature for this function could not be found</exception>
public void OpenExamineWindow(uint actorId) {
public void OpenExamineWindow(uint objectId) {
if (this.RequestCharacterInfo == null) {
throw new InvalidOperationException("Could not find signature for Examine function");
}
@ -58,9 +58,9 @@ namespace XivCommon.Functions {
// offsets at sig E8 ?? ?? ?? ?? 33 C0 EB 4C
// this is called at the end of the 2c case
var raw = (uint*) rciData;
*(raw + 10) = actorId;
*(raw + 11) = actorId;
*(raw + 12) = actorId;
*(raw + 10) = objectId;
*(raw + 11) = objectId;
*(raw + 12) = objectId;
*(raw + 13) = 0xE0000000;
*(raw + 311) = 0;
}

View File

@ -7,9 +7,9 @@ namespace XivCommon.Functions.NamePlates {
/// </summary>
public class NamePlateUpdateEventArgs {
/// <summary>
/// The actor ID associated with this name plate.
/// The object ID associated with this name plate.
/// </summary>
public uint ActorId { get; }
public uint ObjectId { get; }
/// <summary>
/// The name string.
@ -71,8 +71,8 @@ namespace XivCommon.Functions.NamePlates {
/// </summary>
public int Flags { get; set; }
internal NamePlateUpdateEventArgs(uint actorId) {
this.ActorId = actorId;
internal NamePlateUpdateEventArgs(uint objectId) {
this.ObjectId = objectId;
}
}
}

View File

@ -2,8 +2,8 @@
using System.Collections.Generic;
using System.Runtime.InteropServices;
using Dalamud.Game;
using Dalamud.Game.Internal.Gui;
using Dalamud.Game.Internal.Gui.Structs;
using Dalamud.Game.Gui.PartyFinder;
using Dalamud.Game.Gui.PartyFinder.Types;
using Dalamud.Hooking;
namespace XivCommon.Functions {

View File

@ -1,8 +1,7 @@
using System;
using System.Runtime.InteropServices;
using Dalamud.Game;
using Dalamud.Game.Internal;
using Dalamud.Game.Internal.Gui;
using Dalamud.Game.Gui;
using Dalamud.Game.Text.SeStringHandling;
using Dalamud.Hooking;
@ -61,14 +60,12 @@ namespace XivCommon.Functions.Tooltips {
/// </summary>
public event ActionTooltipEventDelegate? OnActionTooltip;
private Framework Framework { get; }
private GameGui GameGui { get; }
private SeStringManager SeStringManager { get; }
private ItemTooltip? ItemTooltip { get; set; }
private ActionTooltip? ActionTooltip { get; set; }
internal Tooltips(SigScanner scanner, Framework framework, GameGui gui, SeStringManager manager, bool enabled) {
this.Framework = framework;
internal Tooltips(SigScanner scanner, GameGui gui, SeStringManager manager, bool enabled) {
this.GameGui = gui;
this.SeStringManager = manager;

View File

@ -1,7 +1,12 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using Dalamud.Plugin;
using Dalamud.Game;
using Dalamud.Game.ClientState;
using Dalamud.Game.ClientState.Objects;
using Dalamud.Game.Gui;
using Dalamud.Game.Gui.PartyFinder;
using Dalamud.Game.Text.SeStringHandling;
using XivCommon.Functions;
using XivCommon.Functions.ContextMenu;
using XivCommon.Functions.NamePlates;
@ -25,7 +30,7 @@ namespace XivCommon {
private delegate IntPtr GetAgentByInternalIdDelegate(IntPtr agentModule, uint id);
private DalamudPluginInterface Interface { get; }
private GameGui GameGui { get; }
private GetAgentByInternalIdDelegate? GetAgentByInternalIdInternal { get; }
@ -88,21 +93,24 @@ namespace XivCommon {
/// </summary>
public Journal Journal { get; }
internal GameFunctions(Hooks hooks, DalamudPluginInterface @interface) {
this.Interface = @interface;
internal GameFunctions(Hooks hooks) {
this.GameGui = Util.GetService<GameGui>();
var scanner = @interface.TargetModuleScanner;
var seStringManager = @interface.SeStringManager;
var clientState = Util.GetService<ClientState>();
var objectTable = Util.GetService<ObjectTable>();
var partyFinderGui = Util.GetService<PartyFinderGui>();
var scanner = Util.GetService<SigScanner>();
var seStringManager = Util.GetService<SeStringManager>();
this.UiAlloc = new UiAlloc(scanner);
this.Chat = new Chat(this, scanner);
this.PartyFinder = new PartyFinder(scanner, @interface.Framework.Gui.PartyFinder, hooks);
this.PartyFinder = new PartyFinder(scanner, partyFinderGui, hooks);
this.BattleTalk = new BattleTalk(this, scanner, seStringManager, hooks.HasFlag(Hooks.BattleTalk));
this.Examine = new Examine(this, scanner);
this.Talk = new Talk(scanner, seStringManager, hooks.HasFlag(Hooks.Talk));
this.ChatBubbles = new ChatBubbles(@interface.ClientState, scanner, seStringManager, hooks.HasFlag(Hooks.ChatBubbles));
this.ContextMenu = new ContextMenu(this, scanner, seStringManager, @interface.ClientState.ClientLanguage, hooks);
this.Tooltips = new Tooltips(scanner, @interface.Framework, @interface.Framework.Gui, seStringManager, hooks.HasFlag(Hooks.Tooltips));
this.ChatBubbles = new ChatBubbles(objectTable, scanner, seStringManager, hooks.HasFlag(Hooks.ChatBubbles));
this.ContextMenu = new ContextMenu(this, scanner, seStringManager, clientState.ClientLanguage, hooks);
this.Tooltips = new Tooltips(scanner, this.GameGui, seStringManager, hooks.HasFlag(Hooks.Tooltips));
this.NamePlates = new NamePlates(this, scanner, seStringManager, hooks.HasFlag(Hooks.NamePlates));
this.DutyFinder = new DutyFinder(this, scanner);
this.Journal = new Journal(this, scanner);
@ -132,7 +140,7 @@ namespace XivCommon {
/// </summary>
/// <returns>Pointer</returns>
public IntPtr GetUiModule() {
return this.Interface.Framework.Gui.GetUIModule();
return this.GameGui.GetUIModule();
}
/// <summary>

View File

@ -1,5 +1,5 @@
using System;
using Dalamud.Plugin;
using Dalamud.Logging;
namespace XivCommon {
internal static class Logger {

View File

@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
using System.Reflection;
using Dalamud.Game.Text.SeStringHandling;
namespace XivCommon {
@ -14,7 +15,7 @@ namespace XivCommon {
internal static unsafe byte[] ReadTerminated(IntPtr memory) {
if (memory == IntPtr.Zero) {
return new byte[0];
return Array.Empty<byte>();
}
var buf = new List<byte>();
@ -36,5 +37,11 @@ namespace XivCommon {
internal static void PrintMissingSig(string name) {
Logger.LogWarning($"Could not find signature for {name}. This functionality will be disabled.");
}
internal static T GetService<T>() {
var service = Type.GetType("Dalamud.Service")!.MakeGenericType(typeof(T));
var get = service.GetMethod("Get", BindingFlags.Public | BindingFlags.Static)!;
return (T) get.Invoke(null, null)!;
}
}
}

View File

@ -19,10 +19,9 @@ namespace XivCommon {
/// This will automatically enable hooks based on the hooks parameter.
/// </para>
/// </summary>
/// <param name="interface">The <see cref="DalamudPluginInterface"/> of the plugin constructing this base</param>
/// <param name="hooks">Flags indicating which hooks to enable</param>
public XivCommonBase(DalamudPluginInterface @interface, Hooks hooks = HooksExt.DefaultHooks) {
this.Functions = new GameFunctions(hooks, @interface);
public XivCommonBase(Hooks hooks = HooksExt.DefaultHooks) {
this.Functions = new GameFunctions(hooks);
}
/// <inheritdoc />