Skip to content

Instantly share code, notes, and snippets.

@Nukem9
Last active August 21, 2019 22:28
Show Gist options
  • Save Nukem9/be036cc899dd5197bd9092b0ae2205b6 to your computer and use it in GitHub Desktop.
Save Nukem9/be036cc899dd5197bd9092b0ae2205b6 to your computer and use it in GitHub Desktop.
std::unordered_map<uint32_t, const char *> g_EditorNameMap;
std::mutex g_NameMapLock;
// TESForm::GetName() is the vfunc at +0x130
// TESForm::GetId() returns the form id
class TESForm : public BaseFormComponent
{
public:
uint32_t GetId() const
{
return *(uint32_t *)((uintptr_t)this + 0xC);
}
uint8_t GetType() const
{
return *(uint8_t *)((uintptr_t)this + 0x4);
}
void hk_GetFullTypeName(char *Buffer, uint32_t BufferSize);
const char *hk_GetName();
bool hk_SetEditorId(const char *Name);
};
// vftable + 0x90
void TESForm::hk_GetFullTypeName(char *Buffer, uint32_t BufferSize)
{
const char *typeName = ((const char *(__thiscall *)(void *))(0x00440E30))(this);
_snprintf_s(Buffer, _TRUNCATE, BufferSize, "%s Form '%s' (%08X)", typeName, GetName(), GetId());
}
// vftable + 0x130
const char *TESForm::hk_GetName()
{
std::lock_guard<std::mutex> lock(g_NameMapLock);
auto itr = g_EditorNameMap.find(GetId());
if (itr != g_EditorNameMap.end())
return itr->second;
// By default the game returns an empty string
return "";
}
// vftable + 0x134
bool TESForm::hk_SetEditorId(const char *Name)
{
std::lock_guard<std::mutex> lock(g_NameMapLock);
g_EditorNameMap.insert(std::make_pair(GetId(), _strdup(Name)));
return true;
}
// 0x0055D480
const char *TESObjectREFR::hk_GetName()
{
if (!*(bool *)0x11C40C8)
{
*(bool *)0x11C40C8 = true;
const char *name = GetName();
*(bool *)0x11C40C8 = false;
if (name && strlen(name) > 0)
return name;
}
TESForm *base = GetBaseObject();
// TESDataHandler::IsInitDone - omitted because I don't care
if (!base)
return "";
const char *name = base->GetName();
if (name && strlen(name) > 0)
return name;
// Now it tries fetching any ExtraData - omitted because I don't care
return "";
}
// Example with TESWeather
WriteDword(0x0103168C + 0x90, &TESForm::hk_GetFullTypeName);
WriteDword(0x0103168C + 0x130, &TESForm::hk_GetName);
WriteDword(0x0103168C + 0x134, &TESForm::hk_SetEditorId);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment