[Friends] First version of working avatars
This commit is contained in:
parent
0a5161d956
commit
6cc4fa582a
@ -117,7 +117,11 @@ namespace Components
|
|||||||
int notify = Dvar::Var("cl_notifyFriendState").get<int>();
|
int notify = Dvar::Var("cl_notifyFriendState").get<int>();
|
||||||
if(gotOnline && (notify == -1 || (notify == 1 && !Game::CL_IsCgameInitialized())) && !Dvar::Var("ui_streamFriendly").get<bool>())
|
if(gotOnline && (notify == -1 || (notify == 1 && !Game::CL_IsCgameInitialized())) && !Dvar::Var("ui_streamFriendly").get<bool>())
|
||||||
{
|
{
|
||||||
Toast::Show("cardicon_joystick", entry->name, "is playing IW4x", 3000);
|
Game::Material* material = Friends::CreateAvatar(user);
|
||||||
|
Toast::Show(material, entry->name, "is playing IW4x", 3000, [material]()
|
||||||
|
{
|
||||||
|
Materials::Delete(material, true);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -530,6 +534,34 @@ namespace Components
|
|||||||
Utils::IO::WriteFile("players/friends.dat", list.SerializeAsString());
|
Utils::IO::WriteFile("players/friends.dat", list.SerializeAsString());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Game::Material* Friends::CreateAvatar(SteamID user)
|
||||||
|
{
|
||||||
|
if (!Steam::Proxy::SteamUtils || !Steam::Proxy::SteamFriends) return nullptr;
|
||||||
|
|
||||||
|
int index = Steam::Proxy::SteamFriends->GetMediumFriendAvatar(user);
|
||||||
|
|
||||||
|
unsigned int width, height;
|
||||||
|
Steam::Proxy::SteamUtils->GetImageSize(index, &width, &height);
|
||||||
|
|
||||||
|
Game::GfxImage* image = Materials::CreateImage(Utils::String::VA("texture_%llX", user.bits), width, height, 1, 0x1000003, D3DFMT_A8R8G8B8);
|
||||||
|
|
||||||
|
D3DLOCKED_RECT lockedRect;
|
||||||
|
image->map->LockRect(0, &lockedRect, nullptr, 0);
|
||||||
|
|
||||||
|
unsigned char* buffer = static_cast<unsigned char*>(lockedRect.pBits);
|
||||||
|
Steam::Proxy::SteamUtils->GetImageRGBA(index, buffer, width * height * 4);
|
||||||
|
|
||||||
|
// Swap red and blue channel
|
||||||
|
for (unsigned int i = 0; i < width * height * 4; i += 4)
|
||||||
|
{
|
||||||
|
std::swap(buffer[i + 0], buffer[i + 2]);
|
||||||
|
}
|
||||||
|
|
||||||
|
image->map->UnlockRect(0);
|
||||||
|
|
||||||
|
return Materials::Create(Utils::String::VA("avatar_%llX", user.bits), image);
|
||||||
|
}
|
||||||
|
|
||||||
Friends::Friends()
|
Friends::Friends()
|
||||||
{
|
{
|
||||||
Friends::LoggedOn = false;
|
Friends::LoggedOn = false;
|
||||||
@ -554,13 +586,6 @@ namespace Components
|
|||||||
Command::Execute("openmenu popup_friends", true);
|
Command::Execute("openmenu popup_friends", true);
|
||||||
}, HOOK_JUMP).install()->quick();
|
}, HOOK_JUMP).install()->quick();
|
||||||
|
|
||||||
// Avatar callback
|
|
||||||
// Steam::Proxy::RegisterCallback(333, [](void* data)
|
|
||||||
// {
|
|
||||||
// MessageBoxA(0, 0, 0, 0);
|
|
||||||
//
|
|
||||||
// });
|
|
||||||
|
|
||||||
// Callback to update user information
|
// Callback to update user information
|
||||||
Steam::Proxy::RegisterCallback(336, [](void* data)
|
Steam::Proxy::RegisterCallback(336, [](void* data)
|
||||||
{
|
{
|
||||||
@ -702,8 +727,7 @@ namespace Components
|
|||||||
for (auto user : Friends::FriendsList)
|
for (auto user : Friends::FriendsList)
|
||||||
{
|
{
|
||||||
Logger::Print("Fetching %s...\n", user.name.data());
|
Logger::Print("Fetching %s...\n", user.name.data());
|
||||||
int index = Steam::Proxy::SteamFriends->GetSmallFriendAvatar(user.userId);
|
int index = Steam::Proxy::SteamFriends->GetMediumFriendAvatar(user.userId);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
if (!Steam::Proxy::SteamUtils) return;
|
if (!Steam::Proxy::SteamUtils) return;
|
||||||
@ -715,25 +739,18 @@ namespace Components
|
|||||||
unsigned int width, height;
|
unsigned int width, height;
|
||||||
Steam::Proxy::SteamUtils->GetImageSize(index, &width, &height);
|
Steam::Proxy::SteamUtils->GetImageSize(index, &width, &height);
|
||||||
Game::Image_Setup(&image, static_cast<short>(width), static_cast<short>(height), 1, 0x1000003, D3DFMT_A8R8G8B8);
|
Game::Image_Setup(&image, static_cast<short>(width), static_cast<short>(height), 1, 0x1000003, D3DFMT_A8R8G8B8);
|
||||||
|
Logger::Print("%dx%d\n", width, height);
|
||||||
|
|
||||||
D3DLOCKED_RECT lockedRect;
|
D3DLOCKED_RECT lockedRect;
|
||||||
image.map->LockRect(0, &lockedRect, nullptr, 0);
|
image.map->LockRect(0, &lockedRect, nullptr, 0);
|
||||||
|
|
||||||
unsigned char* buffer = static_cast<unsigned char*>(lockedRect.pBits);
|
unsigned char* buffer = static_cast<unsigned char*>(lockedRect.pBits);
|
||||||
|
|
||||||
Steam::Proxy::SteamUtils->GetImageRGBA(index, buffer, width * height * 4);
|
Steam::Proxy::SteamUtils->GetImageRGBA(index, buffer, width * height * 4);
|
||||||
|
|
||||||
|
// Swap red and blue channel
|
||||||
for (unsigned int i = 0; i < width * height * 4; i += 4)
|
for (unsigned int i = 0; i < width * height * 4; i += 4)
|
||||||
{
|
{
|
||||||
unsigned char r = buffer[i + 0];
|
std::swap(buffer[i + 0], buffer[i + 2]);
|
||||||
unsigned char g = buffer[i + 1];
|
|
||||||
unsigned char b = buffer[i + 2];
|
|
||||||
unsigned char a = buffer[i + 3];
|
|
||||||
|
|
||||||
buffer[i + 0] = a;
|
|
||||||
buffer[i + 1] = r;
|
|
||||||
buffer[i + 2] = g;
|
|
||||||
buffer[i + 3] = b;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
image.map->UnlockRect(0);
|
image.map->UnlockRect(0);
|
||||||
@ -760,7 +777,6 @@ namespace Components
|
|||||||
|
|
||||||
Friends::StoreFriendsList();
|
Friends::StoreFriendsList();
|
||||||
|
|
||||||
//Steam::Proxy::UnregisterCallback(333);
|
|
||||||
Steam::Proxy::UnregisterCallback(336);
|
Steam::Proxy::UnregisterCallback(336);
|
||||||
Steam::Proxy::UnregisterCallback(304);
|
Steam::Proxy::UnregisterCallback(304);
|
||||||
|
|
||||||
|
@ -95,5 +95,7 @@ namespace Components
|
|||||||
|
|
||||||
static void SetRawPresence(const char* key, const char* value);
|
static void SetRawPresence(const char* key, const char* value);
|
||||||
static std::vector<int> GetAppIdList();
|
static std::vector<int> GetAppIdList();
|
||||||
|
|
||||||
|
static Game::Material* CreateAvatar(SteamID user);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
@ -47,7 +47,7 @@ namespace Components
|
|||||||
return material;
|
return material;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Materials::Delete(Game::Material* material)
|
void Materials::Delete(Game::Material* material, bool deleteImage)
|
||||||
{
|
{
|
||||||
if (!material) return;
|
if (!material) return;
|
||||||
|
|
||||||
@ -57,11 +57,39 @@ namespace Components
|
|||||||
Materials::MaterialTable.erase(mat);
|
Materials::MaterialTable.erase(mat);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (deleteImage)
|
||||||
|
{
|
||||||
|
for (char i = 0; i < material->textureCount; ++i)
|
||||||
|
{
|
||||||
|
Materials::DeleteImage(material->textureTable[i].info.image);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Utils::Memory::GetAllocator()->free(material->textureTable);
|
Utils::Memory::GetAllocator()->free(material->textureTable);
|
||||||
Utils::Memory::GetAllocator()->free(material->name);
|
Utils::Memory::GetAllocator()->free(material->name);
|
||||||
Utils::Memory::GetAllocator()->free(material);
|
Utils::Memory::GetAllocator()->free(material);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Game::GfxImage* Materials::CreateImage(std::string name, unsigned int width, unsigned int height, unsigned int depth, unsigned int flags, _D3DFORMAT format)
|
||||||
|
{
|
||||||
|
Game::GfxImage* image = Utils::Memory::GetAllocator()->allocate<Game::GfxImage>();
|
||||||
|
image->name = Utils::Memory::GetAllocator()->duplicateString(name);
|
||||||
|
|
||||||
|
Game::Image_Setup(image, width, height, depth, flags, format);
|
||||||
|
|
||||||
|
return image;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Materials::DeleteImage(Game::GfxImage* image)
|
||||||
|
{
|
||||||
|
if (!image) return;
|
||||||
|
|
||||||
|
Game::Image_Release(image);
|
||||||
|
|
||||||
|
Utils::Memory::GetAllocator()->free(image->name);
|
||||||
|
Utils::Memory::GetAllocator()->free(image);
|
||||||
|
}
|
||||||
|
|
||||||
void Materials::DeleteAll()
|
void Materials::DeleteAll()
|
||||||
{
|
{
|
||||||
std::vector<Game::Material*> materials;
|
std::vector<Game::Material*> materials;
|
||||||
|
@ -11,7 +11,10 @@ namespace Components
|
|||||||
static int FormatImagePath(char* buffer, size_t size, int, int, const char* image);
|
static int FormatImagePath(char* buffer, size_t size, int, int, const char* image);
|
||||||
|
|
||||||
static Game::Material* Create(std::string name, Game::GfxImage* image);
|
static Game::Material* Create(std::string name, Game::GfxImage* image);
|
||||||
static void Delete(Game::Material* material);
|
static void Delete(Game::Material* material, bool deleteImage = false);
|
||||||
|
|
||||||
|
static Game::GfxImage* CreateImage(std::string name, unsigned int width, unsigned int height, unsigned int depth, unsigned int flags, _D3DFORMAT format);
|
||||||
|
static void DeleteImage(Game::GfxImage* image);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
static std::vector<Game::Material*> MaterialTable;
|
static std::vector<Game::Material*> MaterialTable;
|
||||||
|
@ -7,10 +7,16 @@ namespace Components
|
|||||||
|
|
||||||
Toast::WinToastHandler* Toast::ToastHandler = nullptr;
|
Toast::WinToastHandler* Toast::ToastHandler = nullptr;
|
||||||
|
|
||||||
void Toast::Show(std::string image, std::string title, std::string description, int length)
|
void Toast::Show(std::string image, std::string title, std::string description, int length, Utils::Slot<void()> callback)
|
||||||
|
{
|
||||||
|
Game::Material* material = Game::DB_FindXAssetHeader(Game::XAssetType::ASSET_TYPE_MATERIAL, image.data()).material;
|
||||||
|
return Show(material, title, description, length, callback);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Toast::Show(Game::Material* material, std::string title, std::string description, int length, Utils::Slot<void()> callback)
|
||||||
{
|
{
|
||||||
Toast::Mutex.lock();
|
Toast::Mutex.lock();
|
||||||
Toast::Queue.push({ image, Utils::String::ToUpper(title), description, length, 0 });
|
Toast::Queue.push({ material, Utils::String::ToUpper(title), description, length, 0, callback });
|
||||||
Toast::Mutex.unlock();
|
Toast::Mutex.unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -54,7 +60,6 @@ namespace Components
|
|||||||
float descSize = 0.9f;
|
float descSize = 0.9f;
|
||||||
|
|
||||||
Game::Material* white = Game::DB_FindXAssetHeader(Game::XAssetType::ASSET_TYPE_MATERIAL, "white").material;
|
Game::Material* white = Game::DB_FindXAssetHeader(Game::XAssetType::ASSET_TYPE_MATERIAL, "white").material;
|
||||||
Game::Material* image = Game::DB_FindXAssetHeader(Game::XAssetType::ASSET_TYPE_MATERIAL, toast->image.data()).material;
|
|
||||||
Game::Font* font = Game::DB_FindXAssetHeader(Game::XAssetType::ASSET_TYPE_FONT, "fonts/objectiveFont").font;
|
Game::Font* font = Game::DB_FindXAssetHeader(Game::XAssetType::ASSET_TYPE_FONT, "fonts/objectiveFont").font;
|
||||||
Game::Font* descfont = Game::DB_FindXAssetHeader(Game::XAssetType::ASSET_TYPE_FONT, "fonts/normalFont").font;
|
Game::Font* descfont = Game::DB_FindXAssetHeader(Game::XAssetType::ASSET_TYPE_FONT, "fonts/normalFont").font;
|
||||||
Game::vec4_t wColor = { 1.0f, 1.0f, 1.0f, 1.0f };
|
Game::vec4_t wColor = { 1.0f, 1.0f, 1.0f, 1.0f };
|
||||||
@ -111,7 +116,7 @@ namespace Components
|
|||||||
Game::CL_DrawStretchPicPhysical(static_cast<float>(width / 2 - bWidth / 2), static_cast<float>(height + bHeight / 2), bWidth * 1.0f, border * 1.0f, 0, 0, 1.0f, 1.0f, borderColor, white); // Bottom
|
Game::CL_DrawStretchPicPhysical(static_cast<float>(width / 2 - bWidth / 2), static_cast<float>(height + bHeight / 2), bWidth * 1.0f, border * 1.0f, 0, 0, 1.0f, 1.0f, borderColor, white); // Bottom
|
||||||
|
|
||||||
// Image
|
// Image
|
||||||
Game::CL_DrawStretchPicPhysical(static_cast<float>(width / 2 - bWidth / 2 + iOffsetLeft), static_cast<float>(height - bHeight / 2 + iOffset), imgDim * 1.0f, imgDim * 1.0f, 0, 0, 1.0f, 1.0f, wColor, image);
|
Game::CL_DrawStretchPicPhysical(static_cast<float>(width / 2 - bWidth / 2 + iOffsetLeft), static_cast<float>(height - bHeight / 2 + iOffset), imgDim * 1.0f, imgDim * 1.0f, 0, 0, 1.0f, 1.0f, wColor, toast->image);
|
||||||
|
|
||||||
// Text
|
// Text
|
||||||
float leftText = width / 2 - bWidth / 2 - cornerSize + iOffsetLeft * 2 + imgDim;
|
float leftText = width / 2 - bWidth / 2 - cornerSize + iOffsetLeft * 2 + imgDim;
|
||||||
@ -136,6 +141,7 @@ namespace Components
|
|||||||
|
|
||||||
if ((toast->start + toast->length) < Game::Sys_Milliseconds())
|
if ((toast->start + toast->length) < Game::Sys_Milliseconds())
|
||||||
{
|
{
|
||||||
|
if(toast->callback) toast->callback();
|
||||||
Toast::Queue.pop();
|
Toast::Queue.pop();
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -11,7 +11,8 @@ namespace Components
|
|||||||
|
|
||||||
typedef WinToastLib::WinToastTemplate Template;
|
typedef WinToastLib::WinToastTemplate Template;
|
||||||
|
|
||||||
static void Show(std::string image, std::string title, std::string description, int length);
|
static void Show(std::string image, std::string title, std::string description, int length, Utils::Slot<void()> callback = Utils::Slot<void()>());
|
||||||
|
static void Show(Game::Material* material, std::string title, std::string description, int length, Utils::Slot<void()> callback = Utils::Slot<void()>());
|
||||||
static bool ShowNative(const WinToastLib::WinToastTemplate& toast);
|
static bool ShowNative(const WinToastLib::WinToastTemplate& toast);
|
||||||
|
|
||||||
static std::string GetIcon();
|
static std::string GetIcon();
|
||||||
@ -20,14 +21,16 @@ namespace Components
|
|||||||
class UIToast
|
class UIToast
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
std::string image;
|
Game::Material* image;
|
||||||
std::string title;
|
std::string title;
|
||||||
std::string desc;
|
std::string desc;
|
||||||
int length;
|
int length;
|
||||||
int start;
|
int start;
|
||||||
|
Utils::Slot<void()> callback;
|
||||||
};
|
};
|
||||||
|
|
||||||
class WinToastHandler: public WinToastLib::IWinToastHandler {
|
class WinToastHandler: public WinToastLib::IWinToastHandler
|
||||||
|
{
|
||||||
public:
|
public:
|
||||||
void toastActivated() const override {};
|
void toastActivated() const override {};
|
||||||
void toastDismissed(WinToastLib::IWinToastHandler::WinToastDismissalReason /*state*/) const override {};
|
void toastDismissed(WinToastLib::IWinToastHandler::WinToastDismissalReason /*state*/) const override {};
|
||||||
|
@ -394,19 +394,6 @@ namespace Game
|
|||||||
return poolEntry;
|
return poolEntry;
|
||||||
}
|
}
|
||||||
|
|
||||||
__declspec(naked) void Menu_FreeItemMemory(Game::itemDef_t* /*item*/)
|
|
||||||
{
|
|
||||||
__asm
|
|
||||||
{
|
|
||||||
pushad
|
|
||||||
mov edi, [esp + 24h]
|
|
||||||
mov eax, 63D880h
|
|
||||||
call eax
|
|
||||||
popad
|
|
||||||
retn
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const char* TableLookup(StringTable* stringtable, int row, int column)
|
const char* TableLookup(StringTable* stringtable, int row, int column)
|
||||||
{
|
{
|
||||||
if (!stringtable || !stringtable->values || row >= stringtable->rowCount || column >= stringtable->columnCount) return "";
|
if (!stringtable || !stringtable->values || row >= stringtable->rowCount || column >= stringtable->columnCount) return "";
|
||||||
@ -454,24 +441,6 @@ namespace Game
|
|||||||
return gameType;
|
return gameType;
|
||||||
}
|
}
|
||||||
|
|
||||||
__declspec(naked) float UI_GetScoreboardLeft(void* /*a1*/)
|
|
||||||
{
|
|
||||||
__asm
|
|
||||||
{
|
|
||||||
push eax
|
|
||||||
pushad
|
|
||||||
|
|
||||||
mov ecx, 590390h
|
|
||||||
mov eax, [esp + 28h]
|
|
||||||
call ecx
|
|
||||||
mov[esp + 20h], eax
|
|
||||||
popad
|
|
||||||
pop eax
|
|
||||||
|
|
||||||
retn
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const char *DB_GetXAssetName(XAsset *asset)
|
const char *DB_GetXAssetName(XAsset *asset)
|
||||||
{
|
{
|
||||||
if (!asset) return "";
|
if (!asset) return "";
|
||||||
@ -572,6 +541,219 @@ namespace Game
|
|||||||
if(lock) InterlockedDecrement(lockVar);
|
if(lock) InterlockedDecrement(lockVar);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// this cant be MessageBox because windows.h has a define that converts it to MessageBoxW. which is just stupid
|
||||||
|
void ShowMessageBox(std::string message, std::string title)
|
||||||
|
{
|
||||||
|
if (!Game::CL_IsCgameInitialized())
|
||||||
|
{
|
||||||
|
Dvar_SetStringByName("com_errorMessage", message.data());
|
||||||
|
Dvar_SetStringByName("com_errorTitle", title.data());
|
||||||
|
Cbuf_AddText(0, "openmenu error_popmenu_lobby");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned int R_HashString(const char* string)
|
||||||
|
{
|
||||||
|
unsigned int hash = 0;
|
||||||
|
|
||||||
|
while (*string)
|
||||||
|
{
|
||||||
|
hash = (*string | 0x20) ^ (33 * hash);
|
||||||
|
++string;
|
||||||
|
}
|
||||||
|
|
||||||
|
return hash;
|
||||||
|
}
|
||||||
|
|
||||||
|
void SV_KickClientError(client_t* client, std::string reason)
|
||||||
|
{
|
||||||
|
if (client->state < 5)
|
||||||
|
{
|
||||||
|
Components::Network::SendCommand(client->addr, "error", reason);
|
||||||
|
}
|
||||||
|
|
||||||
|
SV_KickClient(client, reason.data());
|
||||||
|
}
|
||||||
|
|
||||||
|
void Scr_iPrintLn(int clientNum, std::string message)
|
||||||
|
{
|
||||||
|
Game::SV_GameSendServerCommand(clientNum, 0, Utils::String::VA("%c \"%s\"", 0x66, message.data()));
|
||||||
|
}
|
||||||
|
|
||||||
|
void Scr_iPrintLnBold(int clientNum, std::string message)
|
||||||
|
{
|
||||||
|
Game::SV_GameSendServerCommand(clientNum, 0, Utils::String::VA("%c \"%s\"", 0x67, message.data()));
|
||||||
|
}
|
||||||
|
|
||||||
|
int FS_FOpenFileReadCurrentThread(const char* file, int* fh)
|
||||||
|
{
|
||||||
|
if (GetCurrentThreadId() == *reinterpret_cast<DWORD*>(0x1CDE7FC))
|
||||||
|
{
|
||||||
|
return FS_FOpenFileRead(file, fh);
|
||||||
|
}
|
||||||
|
else if (GetCurrentThreadId() == *reinterpret_cast<DWORD*>(0x1CDE814))
|
||||||
|
{
|
||||||
|
return FS_FOpenFileReadDatabase(file, fh);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
*fh = NULL;
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Load_IndexBuffer(void* data, IDirect3DIndexBuffer9** storeHere, int count)
|
||||||
|
{
|
||||||
|
if (Components::Dvar::Var("r_loadForRenderer").get<bool>())
|
||||||
|
{
|
||||||
|
void* buffer = R_AllocStaticIndexBuffer(storeHere, 2 * count);
|
||||||
|
std::memcpy(buffer, data, 2 * count);
|
||||||
|
|
||||||
|
if (storeHere && *storeHere)
|
||||||
|
{
|
||||||
|
(*storeHere)->Unlock();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
char* Com_GetParseThreadInfo()
|
||||||
|
{
|
||||||
|
if (Game::Sys_IsMainThread())
|
||||||
|
{
|
||||||
|
return reinterpret_cast<char*>(0x6466628);
|
||||||
|
}
|
||||||
|
else if (Game::Sys_IsRenderThread())
|
||||||
|
{
|
||||||
|
return reinterpret_cast<char*>(0x646AC34);
|
||||||
|
}
|
||||||
|
else if (Game::Sys_IsServerThread())
|
||||||
|
{
|
||||||
|
return reinterpret_cast<char*>(0x646F240);
|
||||||
|
}
|
||||||
|
else if(Game::Sys_IsDatabaseThread())
|
||||||
|
{
|
||||||
|
return reinterpret_cast<char*>(0x647384C);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Com_SetParseNegativeNumbers(int parse)
|
||||||
|
{
|
||||||
|
char* g_parse = Com_GetParseThreadInfo();
|
||||||
|
|
||||||
|
if (g_parse)
|
||||||
|
{
|
||||||
|
g_parse[1056 * *(reinterpret_cast<DWORD*>(g_parse) + 4224) + 1032] = parse != 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int CL_GetMaxXP()
|
||||||
|
{
|
||||||
|
StringTable* rankTable = DB_FindXAssetHeader(ASSET_TYPE_STRINGTABLE, "mp/rankTable.csv").stringTable;
|
||||||
|
const char* maxrank = StringTable_Lookup(rankTable, 0, "maxrank", 1);
|
||||||
|
return atoi(StringTable_Lookup(rankTable, 0, maxrank, 7));
|
||||||
|
}
|
||||||
|
|
||||||
|
void SortWorldSurfaces(GfxWorld* world)
|
||||||
|
{
|
||||||
|
DWORD* specular1 = reinterpret_cast<DWORD*>(0x69F105C);
|
||||||
|
DWORD* specular2 = reinterpret_cast<DWORD*>(0x69F92D4);
|
||||||
|
DWORD saveSpecular1 = *specular1;
|
||||||
|
DWORD saveSpecular2 = *specular2;
|
||||||
|
|
||||||
|
GfxWorld** gameWorld = reinterpret_cast<GfxWorld**>(0x66DEE94);
|
||||||
|
GfxWorld* saveWorld = *gameWorld;
|
||||||
|
|
||||||
|
*specular1 = 1;
|
||||||
|
*specular2 = 1;
|
||||||
|
*gameWorld = world;
|
||||||
|
|
||||||
|
R_SortWorldSurfaces();
|
||||||
|
|
||||||
|
*gameWorld = saveWorld;
|
||||||
|
*specular1 = saveSpecular1;
|
||||||
|
*specular2 = saveSpecular2;
|
||||||
|
}
|
||||||
|
|
||||||
|
void R_AddDebugBounds(float* color, Bounds* b)
|
||||||
|
{
|
||||||
|
Game::vec3_t v1, v2, v3, v4, v5, v6, v7, v8;
|
||||||
|
float* center = b->midPoint;
|
||||||
|
float* halfSize = b->halfSize;
|
||||||
|
|
||||||
|
v1[0] = center[0] - halfSize[0];
|
||||||
|
v1[1] = center[1] - halfSize[1];
|
||||||
|
v1[2] = center[2] - halfSize[2];
|
||||||
|
|
||||||
|
v2[0] = center[0] + halfSize[0];
|
||||||
|
v2[1] = center[1] - halfSize[1];
|
||||||
|
v2[2] = center[2] - halfSize[2];
|
||||||
|
|
||||||
|
v3[0] = center[0] - halfSize[0];
|
||||||
|
v3[1] = center[1] + halfSize[1];
|
||||||
|
v3[2] = center[2] - halfSize[2];
|
||||||
|
|
||||||
|
v4[0] = center[0] + halfSize[0];
|
||||||
|
v4[1] = center[1] + halfSize[1];
|
||||||
|
v4[2] = center[2] - halfSize[2];
|
||||||
|
|
||||||
|
v5[0] = center[0] - halfSize[0];
|
||||||
|
v5[1] = center[1] - halfSize[1];
|
||||||
|
v5[2] = center[2] + halfSize[2];
|
||||||
|
|
||||||
|
v6[0] = center[0] + halfSize[0];
|
||||||
|
v6[1] = center[1] - halfSize[1];
|
||||||
|
v6[2] = center[2] + halfSize[2];
|
||||||
|
|
||||||
|
v7[0] = center[0] - halfSize[0];
|
||||||
|
v7[1] = center[1] + halfSize[1];
|
||||||
|
v7[2] = center[2] + halfSize[2];
|
||||||
|
|
||||||
|
v8[0] = center[0] + halfSize[0];
|
||||||
|
v8[1] = center[1] + halfSize[1];
|
||||||
|
v8[2] = center[2] + halfSize[2];
|
||||||
|
|
||||||
|
// bottom
|
||||||
|
Game::R_AddDebugLine(color, v1, v2);
|
||||||
|
Game::R_AddDebugLine(color, v2, v4);
|
||||||
|
Game::R_AddDebugLine(color, v4, v3);
|
||||||
|
Game::R_AddDebugLine(color, v3, v1);
|
||||||
|
|
||||||
|
// top
|
||||||
|
Game::R_AddDebugLine(color, v5, v6);
|
||||||
|
Game::R_AddDebugLine(color, v6, v8);
|
||||||
|
Game::R_AddDebugLine(color, v8, v7);
|
||||||
|
Game::R_AddDebugLine(color, v7, v5);
|
||||||
|
|
||||||
|
// verticals
|
||||||
|
Game::R_AddDebugLine(color, v1, v5);
|
||||||
|
Game::R_AddDebugLine(color, v2, v6);
|
||||||
|
Game::R_AddDebugLine(color, v3, v7);
|
||||||
|
Game::R_AddDebugLine(color, v4, v8);
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma optimize("", off)
|
||||||
|
__declspec(naked) float UI_GetScoreboardLeft(void* /*a1*/)
|
||||||
|
{
|
||||||
|
__asm
|
||||||
|
{
|
||||||
|
push eax
|
||||||
|
pushad
|
||||||
|
|
||||||
|
mov ecx, 590390h
|
||||||
|
mov eax, [esp + 28h]
|
||||||
|
call ecx
|
||||||
|
mov[esp + 20h], eax
|
||||||
|
popad
|
||||||
|
pop eax
|
||||||
|
|
||||||
|
retn
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
__declspec(naked) XAssetHeader DB_FindXAssetDefaultHeaderInternal(XAssetType /*type*/)
|
__declspec(naked) XAssetHeader DB_FindXAssetDefaultHeaderInternal(XAssetType /*type*/)
|
||||||
{
|
{
|
||||||
__asm
|
__asm
|
||||||
@ -633,30 +815,6 @@ namespace Game
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// this cant be MessageBox because windows.h has a define that converts it to MessageBoxW. which is just stupid
|
|
||||||
void ShowMessageBox(std::string message, std::string title)
|
|
||||||
{
|
|
||||||
if (!Game::CL_IsCgameInitialized())
|
|
||||||
{
|
|
||||||
Dvar_SetStringByName("com_errorMessage", message.data());
|
|
||||||
Dvar_SetStringByName("com_errorTitle", title.data());
|
|
||||||
Cbuf_AddText(0, "openmenu error_popmenu_lobby");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
unsigned int R_HashString(const char* string)
|
|
||||||
{
|
|
||||||
unsigned int hash = 0;
|
|
||||||
|
|
||||||
while (*string)
|
|
||||||
{
|
|
||||||
hash = (*string | 0x20) ^ (33 * hash);
|
|
||||||
++string;
|
|
||||||
}
|
|
||||||
|
|
||||||
return hash;
|
|
||||||
}
|
|
||||||
|
|
||||||
__declspec(naked) void R_LoadSunThroughDvars(const char* /*mapname*/, sunflare_t* /*sun*/)
|
__declspec(naked) void R_LoadSunThroughDvars(const char* /*mapname*/, sunflare_t* /*sun*/)
|
||||||
{
|
{
|
||||||
__asm
|
__asm
|
||||||
@ -711,26 +869,6 @@ namespace Game
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void SV_KickClientError(client_t* client, std::string reason)
|
|
||||||
{
|
|
||||||
if (client->state < 5)
|
|
||||||
{
|
|
||||||
Components::Network::SendCommand(client->addr, "error", reason);
|
|
||||||
}
|
|
||||||
|
|
||||||
SV_KickClient(client, reason.data());
|
|
||||||
}
|
|
||||||
|
|
||||||
void Scr_iPrintLn(int clientNum, std::string message)
|
|
||||||
{
|
|
||||||
Game::SV_GameSendServerCommand(clientNum, 0, Utils::String::VA("%c \"%s\"", 0x66, message.data()));
|
|
||||||
}
|
|
||||||
|
|
||||||
void Scr_iPrintLnBold(int clientNum, std::string message)
|
|
||||||
{
|
|
||||||
Game::SV_GameSendServerCommand(clientNum, 0, Utils::String::VA("%c \"%s\"", 0x67, message.data()));
|
|
||||||
}
|
|
||||||
|
|
||||||
__declspec(naked) void Scr_NotifyId(unsigned int /*id*/, unsigned __int16 /*stringValue*/, unsigned int /*paramcount*/)
|
__declspec(naked) void Scr_NotifyId(unsigned int /*id*/, unsigned __int16 /*stringValue*/, unsigned int /*paramcount*/)
|
||||||
{
|
{
|
||||||
__asm
|
__asm
|
||||||
@ -778,37 +916,6 @@ namespace Game
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int FS_FOpenFileReadCurrentThread(const char* file, int* fh)
|
|
||||||
{
|
|
||||||
if (GetCurrentThreadId() == *reinterpret_cast<DWORD*>(0x1CDE7FC))
|
|
||||||
{
|
|
||||||
return FS_FOpenFileRead(file, fh);
|
|
||||||
}
|
|
||||||
else if (GetCurrentThreadId() == *reinterpret_cast<DWORD*>(0x1CDE814))
|
|
||||||
{
|
|
||||||
return FS_FOpenFileReadDatabase(file, fh);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
*fh = NULL;
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void Load_IndexBuffer(void* data, IDirect3DIndexBuffer9** storeHere, int count)
|
|
||||||
{
|
|
||||||
if (Components::Dvar::Var("r_loadForRenderer").get<bool>())
|
|
||||||
{
|
|
||||||
void* buffer = R_AllocStaticIndexBuffer(storeHere, 2 * count);
|
|
||||||
std::memcpy(buffer, data, 2 * count);
|
|
||||||
|
|
||||||
if (storeHere && *storeHere)
|
|
||||||
{
|
|
||||||
(*storeHere)->Unlock();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
__declspec(naked) void Load_VertexBuffer(void* /*data*/, IDirect3DVertexBuffer9** /*where*/, int /*len*/)
|
__declspec(naked) void Load_VertexBuffer(void* /*data*/, IDirect3DVertexBuffer9** /*where*/, int /*len*/)
|
||||||
{
|
{
|
||||||
__asm
|
__asm
|
||||||
@ -829,91 +936,40 @@ namespace Game
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
char* Com_GetParseThreadInfo()
|
__declspec(naked) void Image_Setup(GfxImage* /*image*/, unsigned int /*width*/, unsigned int /*height*/, unsigned int /*depth*/, unsigned int /*flags*/, _D3DFORMAT /*format*/)
|
||||||
{
|
|
||||||
if (Game::Sys_IsMainThread())
|
|
||||||
{
|
|
||||||
return reinterpret_cast<char*>(0x6466628);
|
|
||||||
}
|
|
||||||
else if (Game::Sys_IsRenderThread())
|
|
||||||
{
|
|
||||||
return reinterpret_cast<char*>(0x646AC34);
|
|
||||||
}
|
|
||||||
else if (Game::Sys_IsServerThread())
|
|
||||||
{
|
|
||||||
return reinterpret_cast<char*>(0x646F240);
|
|
||||||
}
|
|
||||||
else if(Game::Sys_IsDatabaseThread())
|
|
||||||
{
|
|
||||||
return reinterpret_cast<char*>(0x647384C);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void Com_SetParseNegativeNumbers(int parse)
|
|
||||||
{
|
|
||||||
char* g_parse = Com_GetParseThreadInfo();
|
|
||||||
|
|
||||||
if (g_parse)
|
|
||||||
{
|
|
||||||
g_parse[1056 * *(reinterpret_cast<DWORD*>(g_parse) + 4224) + 1032] = parse != 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int CL_GetMaxXP()
|
|
||||||
{
|
|
||||||
StringTable* rankTable = DB_FindXAssetHeader(ASSET_TYPE_STRINGTABLE, "mp/rankTable.csv").stringTable;
|
|
||||||
const char* maxrank = StringTable_Lookup(rankTable, 0, "maxrank", 1);
|
|
||||||
return atoi(StringTable_Lookup(rankTable, 0, maxrank, 7));
|
|
||||||
}
|
|
||||||
|
|
||||||
__declspec(naked) void Image_Setup(GfxImage* /*image*/, unsigned int /*width*/, unsigned int /*height*/, unsigned int /*depth*/, unsigned int /*flags*/, int /*format*/)
|
|
||||||
{
|
{
|
||||||
__asm
|
__asm
|
||||||
{
|
{
|
||||||
pushad
|
pushad
|
||||||
xor edi, edi
|
|
||||||
|
|
||||||
mov eax, [esp + 24h] // image
|
mov eax, [esp + 24h] // image
|
||||||
mov di, word ptr [esp + 28h] // width
|
mov edi, [esp + 28h] // width
|
||||||
push [esp + 38h] // format
|
push [esp + 38h] // format
|
||||||
push [esp + 38h] // flags
|
push [esp + 38h] // flags
|
||||||
push 0
|
push [esp + 38h] // depth
|
||||||
push [esp + 3Ch] // depth
|
push [esp + 38h] // height
|
||||||
push [esp + 3Ch] // height
|
|
||||||
|
|
||||||
mov ecx, 54AF50h
|
mov ecx, 54AF50h
|
||||||
call ecx
|
call ecx
|
||||||
|
|
||||||
add esp, 14h
|
add esp, 10h
|
||||||
|
|
||||||
popad
|
popad
|
||||||
retn
|
retn
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void SortWorldSurfaces(GfxWorld* world)
|
__declspec(naked) void Menu_FreeItemMemory(itemDef_t* /*item*/)
|
||||||
{
|
{
|
||||||
DWORD* specular1 = reinterpret_cast<DWORD*>(0x69F105C);
|
__asm
|
||||||
DWORD* specular2 = reinterpret_cast<DWORD*>(0x69F92D4);
|
{
|
||||||
DWORD saveSpecular1 = *specular1;
|
pushad
|
||||||
DWORD saveSpecular2 = *specular2;
|
mov edi, [esp + 24h]
|
||||||
|
mov eax, 63D880h
|
||||||
GfxWorld** gameWorld = reinterpret_cast<GfxWorld**>(0x66DEE94);
|
call eax
|
||||||
GfxWorld* saveWorld = *gameWorld;
|
popad
|
||||||
|
retn
|
||||||
*specular1 = 1;
|
}
|
||||||
*specular2 = 1;
|
|
||||||
*gameWorld = world;
|
|
||||||
|
|
||||||
R_SortWorldSurfaces();
|
|
||||||
|
|
||||||
*gameWorld = saveWorld;
|
|
||||||
*specular1 = saveSpecular1;
|
|
||||||
*specular2 = saveSpecular2;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
__declspec(naked) void R_AddDebugLine(float* /*color*/, float* /*v1*/, float* /*v2*/)
|
__declspec(naked) void R_AddDebugLine(float* /*color*/, float* /*v1*/, float* /*v2*/)
|
||||||
@ -975,61 +1031,5 @@ namespace Game
|
|||||||
retn
|
retn
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
#pragma optimize("", on)
|
||||||
void R_AddDebugBounds(float* color, Bounds* b)
|
|
||||||
{
|
|
||||||
Game::vec3_t v1, v2, v3, v4, v5, v6, v7, v8;
|
|
||||||
float* center = b->midPoint;
|
|
||||||
float* halfSize = b->halfSize;
|
|
||||||
|
|
||||||
v1[0] = center[0] - halfSize[0];
|
|
||||||
v1[1] = center[1] - halfSize[1];
|
|
||||||
v1[2] = center[2] - halfSize[2];
|
|
||||||
|
|
||||||
v2[0] = center[0] + halfSize[0];
|
|
||||||
v2[1] = center[1] - halfSize[1];
|
|
||||||
v2[2] = center[2] - halfSize[2];
|
|
||||||
|
|
||||||
v3[0] = center[0] - halfSize[0];
|
|
||||||
v3[1] = center[1] + halfSize[1];
|
|
||||||
v3[2] = center[2] - halfSize[2];
|
|
||||||
|
|
||||||
v4[0] = center[0] + halfSize[0];
|
|
||||||
v4[1] = center[1] + halfSize[1];
|
|
||||||
v4[2] = center[2] - halfSize[2];
|
|
||||||
|
|
||||||
v5[0] = center[0] - halfSize[0];
|
|
||||||
v5[1] = center[1] - halfSize[1];
|
|
||||||
v5[2] = center[2] + halfSize[2];
|
|
||||||
|
|
||||||
v6[0] = center[0] + halfSize[0];
|
|
||||||
v6[1] = center[1] - halfSize[1];
|
|
||||||
v6[2] = center[2] + halfSize[2];
|
|
||||||
|
|
||||||
v7[0] = center[0] - halfSize[0];
|
|
||||||
v7[1] = center[1] + halfSize[1];
|
|
||||||
v7[2] = center[2] + halfSize[2];
|
|
||||||
|
|
||||||
v8[0] = center[0] + halfSize[0];
|
|
||||||
v8[1] = center[1] + halfSize[1];
|
|
||||||
v8[2] = center[2] + halfSize[2];
|
|
||||||
|
|
||||||
// bottom
|
|
||||||
Game::R_AddDebugLine(color, v1, v2);
|
|
||||||
Game::R_AddDebugLine(color, v2, v4);
|
|
||||||
Game::R_AddDebugLine(color, v4, v3);
|
|
||||||
Game::R_AddDebugLine(color, v3, v1);
|
|
||||||
|
|
||||||
// top
|
|
||||||
Game::R_AddDebugLine(color, v5, v6);
|
|
||||||
Game::R_AddDebugLine(color, v6, v8);
|
|
||||||
Game::R_AddDebugLine(color, v8, v7);
|
|
||||||
Game::R_AddDebugLine(color, v7, v5);
|
|
||||||
|
|
||||||
// verticals
|
|
||||||
Game::R_AddDebugLine(color, v1, v5);
|
|
||||||
Game::R_AddDebugLine(color, v2, v6);
|
|
||||||
Game::R_AddDebugLine(color, v3, v7);
|
|
||||||
Game::R_AddDebugLine(color, v4, v8);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
@ -845,7 +845,7 @@ namespace Game
|
|||||||
|
|
||||||
int CL_GetMaxXP();
|
int CL_GetMaxXP();
|
||||||
|
|
||||||
void Image_Setup(GfxImage* image, unsigned int width, unsigned int height, unsigned int depth, unsigned int flags, int format);
|
void Image_Setup(GfxImage* image, unsigned int width, unsigned int height, unsigned int depth, unsigned int flags, _D3DFORMAT format);
|
||||||
|
|
||||||
void SortWorldSurfaces(GfxWorld* world);
|
void SortWorldSurfaces(GfxWorld* world);
|
||||||
void R_AddDebugLine(float* color, float* v1, float* v2);
|
void R_AddDebugLine(float* color, float* v1, float* v2);
|
||||||
|
Loading…
Reference in New Issue
Block a user