diff --git a/include/playerlist.hpp b/include/playerlist.hpp index cce8cc0f..707a4c52 100644 --- a/include/playerlist.hpp +++ b/include/playerlist.hpp @@ -22,7 +22,8 @@ enum class k_EState RAGE, IPC, DEVELOPER, - STATE_LAST = DEVELOPER + CAT, + STATE_LAST = CAT }; extern rgba_t k_Colors[]; diff --git a/res/idspec.png b/res/idspec.png new file mode 100644 index 00000000..036e300a Binary files /dev/null and b/res/idspec.png differ diff --git a/src/hacks/ESP.cpp b/src/hacks/ESP.cpp index 81766a5b..113c482d 100644 --- a/src/hacks/ESP.cpp +++ b/src/hacks/ESP.cpp @@ -378,6 +378,7 @@ void _FASTCALL emoji(CachedEntity *ent) { static glez_texture_t textur = glez_texture_load_png_rgba("/opt/cathook/data/res/atlas.png"); + static glez_texture_t idspecific; auto hit = hitboxcache[ent->m_IDX][0]; Vector hbm, hbx; if (draw::WorldToScreen(hit->min, hbm) && @@ -396,6 +397,59 @@ void _FASTCALL emoji(CachedEntity *ent) if (!textur) textur = glez_texture_load_png_rgba( "/opt/cathook/data/res/atlas.png"); + player_info_s info; + unsigned int steamID; + unsigned int steamidarray[32]{}; + steamidarray[0] = 263966176; + steamidarray[1] = 479487126; + steamidarray[2] = 840899897; + if (g_IEngine->GetPlayerInfo(ent->m_IDX, &info)) + { + steamID = info.friendsID; + } + if (!idspecific) + idspecific = glez_texture_load_png_rgba( + "/opt/cathook/data/res/idspec.png"); + if (idspecific && + playerlist::AccessData(steamID).state == + playerlist::k_EState::CAT) + glez_rect_textured( + head_scr.x - size / 2, head_scr.y - size / 2, size, + size, white, idspecific, 2 * 64, 1 * 64, 64, 64); + for (auto i : steamidarray) + { + if (steamID == i && + playerlist::AccessData(steamID).state == + playerlist::k_EState::CAT) + { + if (!idspecific) + { + idspecific = glez_texture_load_png_rgba( + "/opt/cathook/data/res/idspec.png"); + } + if (idspecific) + { + if (i == steamidarray[0]) + glez_rect_textured(head_scr.x - size / 2, + head_scr.y - size / 2, + size, size, white, + idspecific, 1 * 64, + 1 * 64, 64, 64); + else if (i == steamidarray[1]) + glez_rect_textured( + head_scr.x - size / 2, + head_scr.y - size / 2, size, size, + white, idspecific, 0, 1 * 64, 64, 64); + else if (i == steamidarray[2]) + glez_rect_textured(head_scr.x - size / 2, + head_scr.y - size / 2, + size, size, white, + idspecific, 2 * 64, + 1 * 64, 64, 64); + } + return; + } + } if (textur) { if (emoji_esp == 1) diff --git a/src/hooks/others.cpp b/src/hooks/others.cpp index 60ba300e..825666fa 100644 --- a/src/hooks/others.cpp +++ b/src/hooks/others.cpp @@ -17,7 +17,8 @@ static CatVar no_invisibility(CV_SWITCH, "no_invis", "0", "Remove Invisibility", "Useful with chams!"); -static CatVar medal_flip(CV_SWITCH, "medal_flip", "0", "Infinite Medal Flip", ""); +static CatVar medal_flip(CV_SWITCH, "medal_flip", "0", "Infinite Medal Flip", + ""); // This hook isn't used yet! int C_TFPlayer__DrawModel_hook(IClientEntity *_this, int flags) @@ -284,7 +285,7 @@ static CatVar newlines_msg(CV_INT, "chat_newlines", "0", "Prefix newlines", static CatVar airstuck(CV_KEY, "airstuck", "0", "Airstuck"); static CatVar crypt_chat( - CV_SWITCH, "chat_crypto", "0", "Crypto chat", + CV_SWITCH, "chat_crypto", "1", "Crypto chat", "Start message with !! and it will be only visible to cathook users"); static CatVar chat_filter(CV_STRING, "chat_censor", "", "Spam Chat with newlines if the chosen words are " @@ -658,7 +659,8 @@ static CatVar clean_chat(CV_SWITCH, "clean_chat", "0", "Clean chat", "Removes newlines from chat"); static CatVar dispatch_log(CV_SWITCH, "debug_log_usermessages", "0", "Log dispatched user messages"); -std::string clear = ""; +std::string clear = ""; +static bool firstcall = true; bool DispatchUserMessage_hook(void *_this, int type, bf_read &buf) { int loop_index, s, i, j; @@ -693,15 +695,18 @@ bool DispatchUserMessage_hook(void *_this, int type, bf_read &buf) message.push_back(c); } } - static const char *lastfilter; - static const char *lastname; - static bool retrun = false; - if (data[0] != LOCAL_E->m_IDX) { - if (retrun) - PrintChat("\x07%06X%s\x01: \x07%06X%s\x01", 0xe05938, lastname, - 0xefec1f, lastfilter); + static const char *lastfilter; + static const char *lastname; + static bool retrun = false; + if (data[0] != LOCAL_E->m_IDX) + { + if (retrun) + { + PrintChat("\x07%06X%s\x01: \x07%06X%s\x01", 0xe05938, + lastname, 0xefec1f, lastfilter); + retrun = false; + } } - retrun = false; if (chat_filter_enabled && data[0] != LOCAL_E->m_IDX) { if (!strcmp(chat_filter.GetString(), "")) @@ -860,10 +865,26 @@ bool DispatchUserMessage_hook(void *_this, int type, bf_read &buf) } if (crypt_chat) { + if (firstcall) + chat_stack::Say("!!meow", false); + firstcall = false; if (message.find("!!") == 0) { if (ucccccp::validate(message)) { + CachedEntity *entity = ENTITY(data[0]); + if (CE_GOOD(entity)) + { + if (boost::algorithm::contains( + ucccccp::decrypt(message), "meow")) + { + player_info_s info; + g_IEngine->GetPlayerInfo(data[0], &info); + unsigned steamid = info.friendsID; + playerlist::AccessData(steamid).state = + playerlist::k_EState::CAT; + } + } PrintChat("\x07%06X%s\x01: %s", 0xe05938, name.c_str(), ucccccp::decrypt(message).c_str()); } @@ -933,10 +954,11 @@ void LevelShutdown_hook(void *_this) int RandomInt_hook(void *_this, int iMinVal, int iMaxVal) { - static const RandomInt_t original = + static const RandomInt_t original = RandomInt_t(hooks::vstd.GetMethod(offsets::RandomInt())); - - if (medal_flip && iMinVal == 0 && iMaxVal == 9) return 0; + + if (medal_flip && iMinVal == 0 && iMaxVal == 9) + return 0; return original(_this, iMinVal, iMaxVal); -} \ No newline at end of file +} diff --git a/src/playerlist.cpp b/src/playerlist.cpp index 5e090a6b..71be8dea 100644 --- a/src/playerlist.cpp +++ b/src/playerlist.cpp @@ -1,225 +1,227 @@ -/* - * playerlist.cpp - * - * Created on: Apr 11, 2017 - * Author: nullifiedcat - */ + /* + * playerlist.cpp + * + * Created on: Apr 11, 2017 + * Author: nullifiedcat + */ -#include "playerlist.hpp" -#include "common.hpp" + #include "playerlist.hpp" + #include "common.hpp" -#include -#include -#include + #include + #include + #include -namespace playerlist -{ + namespace playerlist + { -std::unordered_map data{}; + std::unordered_map data{}; -const userdata null_data{}; + const userdata null_data{}; -rgba_t k_Colors[] = { colors::empty, colors::FromRGBA8(99, 226, 161, 255), - colors::FromRGBA8(226, 204, 99, 255), - colors::FromRGBA8(232, 134, 6, 255), colors::empty }; + rgba_t k_Colors[] = { colors::empty, colors::FromRGBA8(99, 226, 161, 255), + colors::FromRGBA8(226, 204, 99, 255), + colors::FromRGBA8(232, 134, 6, 255), colors::empty }; -bool ShouldSave(const userdata &data) -{ - return data.color || (data.state != k_EState::DEFAULT); -} + bool ShouldSave(const userdata &data) + { + return data.color || (data.state != k_EState::DEFAULT); + } -void Save() -{ - DIR *cathook_directory = opendir(DATA_PATH); - if (!cathook_directory) - { - logging::Info("[ERROR] cathook data directory doesn't exist! How did " - "the cheat even get injected?"); - return; - } - else - closedir(cathook_directory); - try - { - std::ofstream file(DATA_PATH "/plist", - std::ios::out | std::ios::binary); - file.write(reinterpret_cast(&SERIALIZE_VERSION), - sizeof(SERIALIZE_VERSION)); - int size = 0; - for (const auto &item : data) - { - if (ShouldSave(item.second)) - size++; - } - file.write(reinterpret_cast(&size), sizeof(size)); - for (const auto &item : data) - { - if (!ShouldSave(item.second)) - continue; - file.write(reinterpret_cast(&item.first), - sizeof(item.first)); - file.write(reinterpret_cast(&item.second), - sizeof(item.second)); - } - file.close(); - logging::Info("Writing successful"); - } - catch (std::exception &e) - { - logging::Info("Writing unsuccessful: %s", e.what()); - } -} + void Save() + { + DIR *cathook_directory = opendir(DATA_PATH); + if (!cathook_directory) + { + logging::Info("[ERROR] cathook data directory doesn't exist! How did " + "the cheat even get injected?"); + return; + } + else + closedir(cathook_directory); + try + { + std::ofstream file(DATA_PATH "/plist", + std::ios::out | std::ios::binary); + file.write(reinterpret_cast(&SERIALIZE_VERSION), + sizeof(SERIALIZE_VERSION)); + int size = 0; + for (const auto &item : data) + { + if (ShouldSave(item.second)) + size++; + } + file.write(reinterpret_cast(&size), sizeof(size)); + for (const auto &item : data) + { + if (!ShouldSave(item.second)) + continue; + file.write(reinterpret_cast(&item.first), + sizeof(item.first)); + file.write(reinterpret_cast(&item.second), + sizeof(item.second)); + } + file.close(); + logging::Info("Writing successful"); + } + catch (std::exception &e) + { + logging::Info("Writing unsuccessful: %s", e.what()); + } + } -void Load() -{ - data.clear(); - DIR *cathook_directory = opendir(DATA_PATH); - if (!cathook_directory) - { - logging::Info("[ERROR] cathook data directory doesn't exist! How did " - "the cheat even get injected?"); - return; - } - else - closedir(cathook_directory); - try - { - std::ifstream file(DATA_PATH "/plist", std::ios::in | std::ios::binary); - int file_serialize = 0; - file.read(reinterpret_cast(&file_serialize), - sizeof(file_serialize)); - if (file_serialize != SERIALIZE_VERSION) - { - logging::Info( - "Outdated/corrupted playerlist file! Cannot load this."); - file.close(); - return; - } - int count = 0; - file.read(reinterpret_cast(&count), sizeof(count)); - logging::Info("Reading %i entries...", count); - for (int i = 0; i < count; i++) - { - int steamid; - userdata udata; - file.read(reinterpret_cast(&steamid), sizeof(steamid)); - file.read(reinterpret_cast(&udata), sizeof(udata)); - data.emplace(steamid, udata); - } - file.close(); - logging::Info("Reading successful!"); - } - catch (std::exception &e) - { - logging::Info("Reading unsuccessful: %s", e.what()); - } -} + void Load() + { + data.clear(); + DIR *cathook_directory = opendir(DATA_PATH); + if (!cathook_directory) + { + logging::Info("[ERROR] cathook data directory doesn't exist! How did " + "the cheat even get injected?"); + return; + } + else + closedir(cathook_directory); + try + { + std::ifstream file(DATA_PATH "/plist", std::ios::in | std::ios::binary); + int file_serialize = 0; + file.read(reinterpret_cast(&file_serialize), + sizeof(file_serialize)); + if (file_serialize != SERIALIZE_VERSION) + { + logging::Info( + "Outdated/corrupted playerlist file! Cannot load this."); + file.close(); + return; + } + int count = 0; + file.read(reinterpret_cast(&count), sizeof(count)); + logging::Info("Reading %i entries...", count); + for (int i = 0; i < count; i++) + { + int steamid; + userdata udata; + file.read(reinterpret_cast(&steamid), sizeof(steamid)); + file.read(reinterpret_cast(&udata), sizeof(udata)); + data.emplace(steamid, udata); + } + file.close(); + logging::Info("Reading successful!"); + } + catch (std::exception &e) + { + logging::Info("Reading unsuccessful: %s", e.what()); + } + } -rgba_t Color(unsigned steamid) -{ - if (AccessData(steamid).state == k_EState::DEVELOPER) - return colors::RainbowCurrent(); - if (AccessData(steamid).color.a) - { - return AccessData(steamid).color; - } - else - { - return k_Colors[static_cast(AccessData(steamid).state)]; - } -} + rgba_t Color(unsigned steamid) + { + if (AccessData(steamid).state == k_EState::DEVELOPER) + return colors::RainbowCurrent(); + if (AccessData(steamid).state == k_EState::CAT) + return colors::RainbowCurrent(); + if (AccessData(steamid).color.a) + { + return AccessData(steamid).color; + } + else + { + return k_Colors[static_cast(AccessData(steamid).state)]; + } + } -rgba_t Color(CachedEntity *player) -{ - if (CE_GOOD(player)) - return Color(player->player_info.friendsID); - return colors::empty; -} + rgba_t Color(CachedEntity *player) + { + if (CE_GOOD(player)) + return Color(player->player_info.friendsID); + return colors::empty; + } -userdata &AccessData(unsigned steamid) -{ - try - { - return data.at(steamid); - } - catch (std::out_of_range &oor) - { - data.emplace(steamid, userdata{}); - return data.at(steamid); - } -} + userdata &AccessData(unsigned steamid) + { + try + { + return data.at(steamid); + } + catch (std::out_of_range &oor) + { + data.emplace(steamid, userdata{}); + return data.at(steamid); + } + } -// Assume player is non-null -userdata &AccessData(CachedEntity *player) -{ - if (CE_GOOD(player)) - return AccessData(player->player_info.friendsID); - return AccessData(0U); -} + // Assume player is non-null + userdata &AccessData(CachedEntity *player) + { + if (CE_GOOD(player)) + return AccessData(player->player_info.friendsID); + return AccessData(0U); + } -bool IsDefault(unsigned steamid) -{ - const userdata &data = AccessData(steamid); - return data.state == k_EState::DEFAULT && !data.color.a; -} + bool IsDefault(unsigned steamid) + { + const userdata &data = AccessData(steamid); + return data.state == k_EState::DEFAULT && !data.color.a; + } -bool IsDefault(CachedEntity *entity) -{ - if (CE_GOOD(entity)) - return IsDefault(entity->player_info.friendsID); - return true; -} + bool IsDefault(CachedEntity *entity) + { + if (CE_GOOD(entity)) + return IsDefault(entity->player_info.friendsID); + return true; + } -CatCommand pl_save("pl_save", "Save playerlist", Save); -CatCommand pl_load("pl_load", "Load playerlist", Load); + CatCommand pl_save("pl_save", "Save playerlist", Save); + CatCommand pl_load("pl_load", "Load playerlist", Load); -CatCommand pl_set_state( - "pl_set_state", - "pl_set_state uniqueid state\nfor example pl_set_state 306902159 0", - [](const CCommand &args) { - if (args.ArgC() < 3) - { - logging::Info("Invalid call"); - return; - } - unsigned steamid = strtoul(args.Arg(1), nullptr, 10); - k_EState state = - static_cast(strtol(args.Arg(2), nullptr, 10)); - if (state < k_EState::DEFAULT || state > k_EState::STATE_LAST) - state = k_EState::DEFAULT; - AccessData(steamid).state = state; - logging::Info("Set %d to %d", steamid, state); - }); + CatCommand pl_set_state( + "pl_set_state", + "pl_set_state uniqueid state\nfor example pl_set_state 306902159 0", + [](const CCommand &args) { + if (args.ArgC() < 3) + { + logging::Info("Invalid call"); + return; + } + unsigned steamid = strtoul(args.Arg(1), nullptr, 10); + k_EState state = + static_cast(strtol(args.Arg(2), nullptr, 10)); + if (state < k_EState::DEFAULT || state > k_EState::STATE_LAST) + state = k_EState::DEFAULT; + AccessData(steamid).state = state; + logging::Info("Set %d to %d", steamid, state); + }); -CatCommand pl_set_color("pl_set_color", "pl_set_color uniqueid r g b", - [](const CCommand &args) { - if (args.ArgC() < 5) - { - logging::Info("Invalid call"); - return; - } - unsigned steamid = - strtoul(args.Arg(1), nullptr, 10); - int r = strtol(args.Arg(2), nullptr, 10); - int g = strtol(args.Arg(3), nullptr, 10); - int b = strtol(args.Arg(4), nullptr, 10); - rgba_t color = colors::FromRGBA8(r, g, b, 255); - AccessData(steamid).color = color; - logging::Info("Changed %d's color", steamid); - }); + CatCommand pl_set_color("pl_set_color", "pl_set_color uniqueid r g b", + [](const CCommand &args) { + if (args.ArgC() < 5) + { + logging::Info("Invalid call"); + return; + } + unsigned steamid = + strtoul(args.Arg(1), nullptr, 10); + int r = strtol(args.Arg(2), nullptr, 10); + int g = strtol(args.Arg(3), nullptr, 10); + int b = strtol(args.Arg(4), nullptr, 10); + rgba_t color = colors::FromRGBA8(r, g, b, 255); + AccessData(steamid).color = color; + logging::Info("Changed %d's color", steamid); + }); -CatCommand pl_info("pl_info", "pl_info uniqueid", [](const CCommand &args) { - if (args.ArgC() < 2) - { - logging::Info("Invalid call"); - return; - } - unsigned steamid = strtoul(args.Arg(1), nullptr, 10); - logging::Info("Data for %i: ", steamid); - logging::Info(" State: %i", AccessData(steamid).state); - /*int clr = AccessData(steamid).color; - if (clr) { - ConColorMsg(*reinterpret_cast<::Color*>(&clr), "[CUSTOM COLOR]\n"); - }*/ -}); -} + CatCommand pl_info("pl_info", "pl_info uniqueid", [](const CCommand &args) { + if (args.ArgC() < 2) + { + logging::Info("Invalid call"); + return; + } + unsigned steamid = strtoul(args.Arg(1), nullptr, 10); + logging::Info("Data for %i: ", steamid); + logging::Info(" State: %i", AccessData(steamid).state); + /*int clr = AccessData(steamid).color; + if (clr) { + ConColorMsg(*reinterpret_cast<::Color*>(&clr), "[CUSTOM COLOR]\n"); + }*/ + }); + }