diff --git a/PlayerTags/GameInterface/ContextMenus/ContextMenu.cs b/PlayerTags/GameInterface/ContextMenus/ContextMenu.cs index d14dc01..c76218e 100644 --- a/PlayerTags/GameInterface/ContextMenus/ContextMenu.cs +++ b/PlayerTags/GameInterface/ContextMenus/ContextMenu.cs @@ -148,7 +148,7 @@ namespace PlayerTags.GameInterface.ContextMenus private const int MaxContextMenuItemsPerContextMenu = 32; private IntPtr m_CurrentContextMenuAgent; - private IntPtr m_SubContextMenuTitle; + private IntPtr m_CurrentSubContextMenuTitle; private ContextMenuOpenedArgs? m_ContextMenuOpenedArgs; private OpenSubContextMenuItem? m_OpenSubContextMenuItem; @@ -390,20 +390,12 @@ namespace PlayerTags.GameInterface.ContextMenus m_OpenSubContextMenu(agent); // Free any sub context menu title we've already allocated - if (m_SubContextMenuTitle != IntPtr.Zero) - { - unsafe - { - IMemorySpace.Free((void*)m_SubContextMenuTitle, (ulong)IntPtr.Size); - } - - m_SubContextMenuTitle = IntPtr.Zero; - } + GameInterfaceHelper.GameFree(ref m_CurrentSubContextMenuTitle, (ulong)IntPtr.Size); // Allocate a new 1 byte title. Without this, a title won't be rendered. // The actual value doesn't matter at this point, we'll set it later. - m_SubContextMenuTitle = (IntPtr)IMemorySpace.GetUISpace()->Malloc(1, 0); - *(&agentContext->SubContextMenuTitle) = (byte*)m_SubContextMenuTitle; + m_CurrentSubContextMenuTitle = GameInterfaceHelper.GameUIAllocate(1); + *(&agentContext->SubContextMenuTitle) = (byte*)m_CurrentSubContextMenuTitle; } //*(&a->SelectedIndex) = s; diff --git a/PlayerTags/GameInterface/ContextMenus/ContextMenuReaderWriter.cs b/PlayerTags/GameInterface/ContextMenus/ContextMenuReaderWriter.cs index 74ead9b..dd9be79 100644 --- a/PlayerTags/GameInterface/ContextMenus/ContextMenuReaderWriter.cs +++ b/PlayerTags/GameInterface/ContextMenus/ContextMenuReaderWriter.cs @@ -287,7 +287,7 @@ namespace PlayerTags.GameInterface.ContextMenus // Allocate the new array. We have to do a little dance with the first 8 bytes which represents the array count const int arrayCountSize = 8; var newAtkValuesArraySize = arrayCountSize + Marshal.SizeOf() * newAtkValuesCount; - var newAtkValuesArray = (IntPtr)IMemorySpace.GetUISpace()->Malloc((ulong)newAtkValuesArraySize, 0); + var newAtkValuesArray = GameInterfaceHelper.GameUIAllocate((ulong)newAtkValuesArraySize); if (newAtkValuesArray == IntPtr.Zero) { return; diff --git a/PlayerTags/GameInterface/GameInterfaceHelper.cs b/PlayerTags/GameInterface/GameInterfaceHelper.cs index 4f87e1f..46568f1 100644 --- a/PlayerTags/GameInterface/GameInterfaceHelper.cs +++ b/PlayerTags/GameInterface/GameInterfaceHelper.cs @@ -1,4 +1,5 @@ using Dalamud.Game.Text.SeStringHandling; +using FFXIVClientStructs.FFXIV.Client.System.Memory; using System; using System.Runtime.InteropServices; using System.Text; @@ -73,7 +74,7 @@ namespace PlayerTags.GameInterface return true; } - public static IntPtr Allocate(SeString seString) + public static IntPtr PluginAllocate(SeString seString) { var bytes = seString.Encode(); @@ -84,7 +85,7 @@ namespace PlayerTags.GameInterface return pointer; } - public static void Free(ref IntPtr ptr) + public static void PluginFree(ref IntPtr ptr) { Marshal.FreeHGlobal(ptr); ptr = IntPtr.Zero; @@ -103,5 +104,20 @@ namespace PlayerTags.GameInterface return bytes; } + + public static unsafe IntPtr GameUIAllocate(ulong size) + { + return (IntPtr)IMemorySpace.GetUISpace()->Malloc(size, 0); + } + + public static unsafe void GameFree(ref IntPtr ptr, ulong size) + { + if (ptr == IntPtr.Zero) + { + return; + } + + IMemorySpace.Free((void*)ptr, size); + } } } diff --git a/PlayerTags/GameInterface/Nameplates/Nameplate.cs b/PlayerTags/GameInterface/Nameplates/Nameplate.cs index 8d60743..ff8f1cd 100644 --- a/PlayerTags/GameInterface/Nameplates/Nameplate.cs +++ b/PlayerTags/GameInterface/Nameplates/Nameplate.cs @@ -107,38 +107,38 @@ namespace PlayerTags.GameInterface.Nameplates bool hasNameChanged = beforeNameHashCode != playerNameplateUpdatedArgs.Name.GetHashCode(); if (hasNameChanged) { - newNamePtr = GameInterfaceHelper.Allocate(playerNameplateUpdatedArgs.Name); + newNamePtr = GameInterfaceHelper.PluginAllocate(playerNameplateUpdatedArgs.Name); } IntPtr newTitlePtr = titlePtr; bool hasTitleChanged = beforeTitleHashCode != playerNameplateUpdatedArgs.Title.GetHashCode(); if (hasTitleChanged) { - newTitlePtr = GameInterfaceHelper.Allocate(playerNameplateUpdatedArgs.Title); + newTitlePtr = GameInterfaceHelper.PluginAllocate(playerNameplateUpdatedArgs.Title); } IntPtr newFreeCompanyPtr = freeCompanyPtr; bool hasFreeCompanyChanged = beforeFreeCompanyHashCode != playerNameplateUpdatedArgs.FreeCompany.GetHashCode(); if (hasFreeCompanyChanged) { - newFreeCompanyPtr = GameInterfaceHelper.Allocate(playerNameplateUpdatedArgs.FreeCompany); + newFreeCompanyPtr = GameInterfaceHelper.PluginAllocate(playerNameplateUpdatedArgs.FreeCompany); } var result = m_SetPlayerNameplateHook.Original(playerNameplateObjectPtr, playerNameplateUpdatedArgs.IsTitleAboveName, playerNameplateUpdatedArgs.IsTitleVisible, newNamePtr, newTitlePtr, newFreeCompanyPtr, playerNameplateUpdatedArgs.IconId); if (hasNameChanged) { - GameInterfaceHelper.Free(ref newNamePtr); + GameInterfaceHelper.PluginFree(ref newNamePtr); } if (hasTitleChanged) { - GameInterfaceHelper.Free(ref newTitlePtr); + GameInterfaceHelper.PluginFree(ref newTitlePtr); } if (hasFreeCompanyChanged) { - GameInterfaceHelper.Free(ref newFreeCompanyPtr); + GameInterfaceHelper.PluginFree(ref newFreeCompanyPtr); } return result;