From 9f80a1c36507a4dabfc7f68b8a56593e98d37eec Mon Sep 17 00:00:00 2001 From: Stephen Date: Mon, 16 Jan 2023 05:05:30 -0500 Subject: [PATCH] Migrations fix --- class_dumping/generate-dynamic-header.js | 2 +- include/copypasted/Netvar.h | 2 +- include/hacks/Aimbot.hpp | 13 - include/hacks/AntiAntiAim.hpp | 2 +- include/hacks/ESP.hpp | 1 - include/hacks/SkinChanger.hpp | 4 +- include/hacks/ac/aimbot.hpp | 2 +- include/helpers.hpp | 31 +- include/itemtypes.hpp | 6 +- include/json.hpp | 8 +- include/playerlist.hpp | 2 +- include/settings/Manager.hpp | 2 +- include/visual/menu/menu/Menu.hpp | 2 +- src/PlayerTools.cpp | 2 +- src/classinfo/dynamic.gen.cpp | 2 +- src/crits.cpp | 2 +- src/hacks/Aimbot.cpp | 106 +- src/hacks/AntiAntiAim.cpp | 2 +- src/hacks/AutoItem.cpp | 2 +- src/hacks/CatBot.cpp | 2 +- src/hacks/ChatCommands.cpp | 2 +- src/hacks/CritSay.cpp | 2 +- src/hacks/ESP.cpp | 1510 +++++++++-------- src/hacks/KillSay.cpp | 2 +- src/hacks/Killstreak.cpp | 2 +- src/hacks/Misc.cpp | 8 +- src/hacks/MiscPlayerInfo.cpp | 4 +- src/hacks/NavBot.cpp | 8 +- src/hacks/SkinChanger.cpp | 4 +- src/hacks/SpellForcer.cpp | 16 +- src/hacks/ac/aimbot.cpp | 4 +- src/helpers.cpp | 8 +- src/hooks/CreateMove.cpp | 9 +- src/playerlist.cpp | 2 +- .../menu/menu/special/SettingsManagerList.cpp | 2 +- 35 files changed, 883 insertions(+), 895 deletions(-) diff --git a/class_dumping/generate-dynamic-header.js b/class_dumping/generate-dynamic-header.js index 57df6496..b03a0e1f 100755 --- a/class_dumping/generate-dynamic-header.js +++ b/class_dumping/generate-dynamic-header.js @@ -48,7 +48,7 @@ var source = ` namespace client_classes { -std::unordered_map classid_mapping {}; +boost::unordered_flat_map classid_mapping {}; dynamic::dynamic() { ${POPULATED_MAP} diff --git a/include/copypasted/Netvar.h b/include/copypasted/Netvar.h index c1974661..856b7881 100644 --- a/include/copypasted/Netvar.h +++ b/include/copypasted/Netvar.h @@ -38,7 +38,7 @@ public: class netvar_tree { struct node; - using map_type = std::unordered_map, hash_char, equal_char>; + using map_type = boost::unordered_flat_map, hash_char, equal_char>; struct node { diff --git a/include/hacks/Aimbot.hpp b/include/hacks/Aimbot.hpp index ba8f6d01..781e60f6 100644 --- a/include/hacks/Aimbot.hpp +++ b/include/hacks/Aimbot.hpp @@ -17,20 +17,8 @@ namespace hacks::shared::aimbot extern settings::Boolean ignore_cloak; extern unsigned last_target_ignore_timer; // Used to store aimbot data to prevent calculating it again -struct AimbotCalculatedData_s -{ - unsigned long predict_tick{ 0 }; - bool predict_type{ 0 }; - Vector aim_position{ 0 }; - unsigned long vcheck_tick{ 0 }; - bool visible{ false }; - float fov{ 0 }; - int hitbox{ 0 }; -}; - // Functions used to calculate aimbot data, and if already calculated use it Vector PredictEntity(CachedEntity *entity); -bool BacktrackVisCheck(CachedEntity *entity); // Functions called by other functions for when certian game calls are run void Reset(); @@ -54,5 +42,4 @@ bool isHitboxMedium(int hitbox); int ClosestHitbox(CachedEntity *target); void DoSlowAim(Vector &inputAngle); bool UpdateAimkey(); -float EffectiveTargetingRange(); } // namespace hacks::shared::aimbot diff --git a/include/hacks/AntiAntiAim.hpp b/include/hacks/AntiAntiAim.hpp index 24f3896a..29340512 100644 --- a/include/hacks/AntiAntiAim.hpp +++ b/include/hacks/AntiAntiAim.hpp @@ -19,7 +19,7 @@ struct brutedata namespace hacks::shared::anti_anti_aim { -extern std::unordered_map resolver_map; +extern boost::unordered_flat_map resolver_map; void increaseBruteNum(int idx); void frameStageNotify(ClientFrameStage_t stage); // void resolveEnt(int IDX, IClientEntity *entity = nullptr); diff --git a/include/hacks/ESP.hpp b/include/hacks/ESP.hpp index 7adaf647..35fb50b2 100644 --- a/include/hacks/ESP.hpp +++ b/include/hacks/ESP.hpp @@ -15,7 +15,6 @@ namespace hacks::shared::esp { // Init -void Init(); void Shutdown(); // Strings void SetEntityColor(CachedEntity *entity, const rgba_t &color); diff --git a/include/hacks/SkinChanger.hpp b/include/hacks/SkinChanger.hpp index 0879eafe..ff7a1c42 100644 --- a/include/hacks/SkinChanger.hpp +++ b/include/hacks/SkinChanger.hpp @@ -121,9 +121,9 @@ struct def_attribute_modifier std::vector modifiers{}; }; -extern std::unordered_map modifier_map; +extern boost::unordered_flat_map modifier_map; extern patched_weapon_cookie cookie; -// extern std::unordered_map cookie_map; +// extern boost::unordered_flat_map cookie_map; def_attribute_modifier &GetModifier(int idx); // patched_weapon_cookie& GetCookie(int idx); diff --git a/include/hacks/ac/aimbot.hpp b/include/hacks/ac/aimbot.hpp index 8e209bb1..a9f851b2 100644 --- a/include/hacks/ac/aimbot.hpp +++ b/include/hacks/ac/aimbot.hpp @@ -26,7 +26,7 @@ struct ac_data extern int amount[MAX_PLAYERS]; void ResetEverything(); -std::unordered_map &player_orgs(); +boost::unordered_flat_map &player_orgs(); void ResetPlayer(int idx); void Init(); diff --git a/include/helpers.hpp b/include/helpers.hpp index 72fec3df..e7618611 100644 --- a/include/helpers.hpp +++ b/include/helpers.hpp @@ -97,9 +97,22 @@ void VectorAngles(Vector &forward, Vector &angles); void AngleVectors2(const QAngle &angles, Vector *forward); void AngleVectors3(const QAngle &angles, Vector *forward, Vector *right, Vector *up); bool isRapidFire(IClientEntity *wep); +void fClampAngle(Vector &qaAng); + +inline Vector GetAimAtAngles(Vector origin, Vector target, CachedEntity *punch_correct = nullptr) +{ + Vector angles, tr; + tr = (target - origin); + VectorAngles(tr, angles); + // Apply punchangle correction + if (punch_correct) + angles -= CE_VECTOR(punch_correct, netvar.vecPunchAngle); + fClampAngle(angles); + return angles; +} extern std::mutex trace_lock; bool IsEntityVisible(CachedEntity *entity, int hb); -bool IsEntityVectorVisible(CachedEntity *entity, Vector endpos, bool use_weapon_offset = false, unsigned int mask = MASK_SHOT_HULL, trace_t *trace = nullptr); +bool IsEntityVectorVisible(CachedEntity *entity, Vector endpos, bool use_weapon_offset = false, unsigned int mask = MASK_SHOT_HULL, trace_t *trace = nullptr, bool hit = false); bool VisCheckEntFromEnt(CachedEntity *startEnt, CachedEntity *endEnt); bool VisCheckEntFromEntVector(Vector startVector, CachedEntity *startEnt, CachedEntity *endEnt); Vector VischeckCorner(CachedEntity *player, CachedEntity *target, float maxdist, bool checkWalkable); @@ -112,14 +125,14 @@ bool LineIntersectsBox(Vector &bmin, Vector &bmax, Vector &lmin, Vector &lmax); void GenerateBoxVertices(const Vector &vOrigin, const QAngle &angles, const Vector &vMins, const Vector &vMaxs, Vector pVerts[8]); float DistToSqr(CachedEntity *entity); -void fClampAngle(Vector &qaAng); + // const char* MakeInfoString(IClientEntity* player); bool GetProjectileData(CachedEntity *weapon, float &speed, float &gravity, float &start_velocity); bool IsVectorVisible(Vector a, Vector b, bool enviroment_only = false, CachedEntity *self = LOCAL_E, unsigned int mask = MASK_SHOT_HULL); // A Special function for navparser to check if a Vector is visible. bool IsVectorVisibleNavigation(Vector a, Vector b, unsigned int mask = MASK_SHOT_HULL); float ProjGravMult(int class_id, float x_speed); -bool didProjectileHit(Vector start_point, Vector end_point, CachedEntity *entity, float projectile_size); +bool didProjectileHit(Vector start_point, Vector end_point, CachedEntity *entity, float projectile_size, bool grav_comp); Vector getShootPos(Vector angle); Vector GetForwardVector(Vector origin, Vector viewangles, float distance, CachedEntity *punch_entity = nullptr); Vector GetForwardVector(float distance, CachedEntity *punch_entity = nullptr); @@ -162,18 +175,6 @@ void ChangeName(std::string name); void WhatIAmLookingAt(int *result_eindex, Vector *result_pos); -inline Vector GetAimAtAngles(Vector origin, Vector target, CachedEntity *punch_correct = nullptr) -{ - Vector angles, tr; - tr = (target - origin); - VectorAngles(tr, angles); - // Apply punchangle correction - if (punch_correct) - angles -= CE_VECTOR(punch_correct, netvar.vecPunchAngle); - fClampAngle(angles); - return angles; -} - void AimAt(Vector origin, Vector target, CUserCmd *cmd, bool compensate_punch = true); void FastStop(); void AimAtHitbox(CachedEntity *ent, int hitbox, CUserCmd *cmd, bool compensate_punch = true); diff --git a/include/itemtypes.hpp b/include/itemtypes.hpp index ecacfe25..e61e8e8d 100644 --- a/include/itemtypes.hpp +++ b/include/itemtypes.hpp @@ -159,8 +159,8 @@ public: void RegisterItem(std::string modelpath, k_EItemType type); k_EItemType GetItemType(CachedEntity *entity); - std::unordered_map models; - std::unordered_map map; + boost::unordered_flat_map models; + boost::unordered_flat_map map; }; class ItemManager @@ -171,7 +171,7 @@ public: void RegisterSpecialMapping(ItemCheckerFn fn, k_EItemType type); k_EItemType GetItemType(CachedEntity *ent); - std::unordered_map special_map; + boost::unordered_flat_map special_map; std::vector specials; ItemModelMapper mapper_special; ItemModelMapper mapper; diff --git a/include/json.hpp b/include/json.hpp index c5dc990d..529d9f6c 100644 --- a/include/json.hpp +++ b/include/json.hpp @@ -1034,7 +1034,7 @@ public: described below. @tparam ObjectType the container to store objects (e.g., `std::map` or - `std::unordered_map`) + `boost::unordered_flat_map`) @tparam StringType the type of the keys or names (e.g., `std::string`). The comparison function `std::less` is used to order elements inside the container. @@ -1791,7 +1791,7 @@ public: `unordered_multiset` with a `value_type` from which a @ref basic_json value can be constructed. - **objects**: @ref object_t and all kinds of compatible associative - containers such as `std::map`, `std::unordered_map`, `std::multimap`, + containers such as `std::map`, `boost::unordered_flat_map`, `std::multimap`, and `std::unordered_multimap` with a `key_type` compatible to @ref string_t and a `value_type` from which a @ref basic_json value can be constructed. @@ -3003,7 +3003,7 @@ public: to other types. There a few things to note: (1) Floating-point numbers can be converted to integers\, (2) A JSON array can be converted to a standard `std::vector`\, (3) A JSON object can be converted to C++ - associative containers such as `std::unordered_map`.,get__ValueType_const} @since version 2.1.0 @@ -3222,7 +3222,7 @@ public: to other types. There a few things to note: (1) Floating-point numbers can be converted to integers\, (2) A JSON array can be converted to a standard `std::vector`\, (3) A JSON object can be converted to C++ - associative containers such as `std::unordered_map`.,operator__ValueType} @since version 1.0.0 diff --git a/include/playerlist.hpp b/include/playerlist.hpp index d2262718..499a26c6 100644 --- a/include/playerlist.hpp +++ b/include/playerlist.hpp @@ -47,7 +47,7 @@ struct userdata unsigned kills{ 0 }; }; -extern std::unordered_map data; +extern boost::unordered_flat_map data; void Save(); void Load(); diff --git a/include/settings/Manager.hpp b/include/settings/Manager.hpp index 4a8f76dc..25e44e80 100644 --- a/include/settings/Manager.hpp +++ b/include/settings/Manager.hpp @@ -46,6 +46,6 @@ public: void applyDefaults(); IVariable *lookup(const std::string &string); - std::unordered_map registered{}; + boost::unordered_flat_map registered{}; }; } // namespace settings diff --git a/include/visual/menu/menu/Menu.hpp b/include/visual/menu/menu/Menu.hpp index b238bb90..0e84e30c 100644 --- a/include/visual/menu/menu/Menu.hpp +++ b/include/visual/menu/menu/Menu.hpp @@ -86,6 +86,6 @@ public: std::vector> modal_stack{}; Tooltip tooltip{}; tinyxml2::XMLDocument xml_source{}; - std::unordered_map prefabs{}; + boost::unordered_flat_map prefabs{}; }; } // namespace zerokernel diff --git a/src/PlayerTools.cpp b/src/PlayerTools.cpp index 95e02c03..9c0edf25 100644 --- a/src/PlayerTools.cpp +++ b/src/PlayerTools.cpp @@ -21,7 +21,7 @@ static settings::Boolean taunting{ "player-tools.ignore.taunting", "true" }; static settings::Boolean hoovy{ "player-tools.ignore.hoovy", "true" }; static settings::Boolean ignoreCathook{ "player-tools.ignore.cathook", "true" }; -static std::unordered_map betrayal_list{}; +static boost::unordered_flat_map betrayal_list{}; static CatCommand forgive_all("pt_forgive_all", "Clear betrayal list", []() { betrayal_list.clear(); }); diff --git a/src/classinfo/dynamic.gen.cpp b/src/classinfo/dynamic.gen.cpp index 3f9e8c19..e93c5525 100644 --- a/src/classinfo/dynamic.gen.cpp +++ b/src/classinfo/dynamic.gen.cpp @@ -6,7 +6,7 @@ namespace client_classes { -std::unordered_map classid_mapping{}; +boost::unordered_flat_map classid_mapping{}; dynamic::dynamic() { diff --git a/src/crits.cpp b/src/crits.cpp index a7520b34..2ef0ec8e 100644 --- a/src/crits.cpp +++ b/src/crits.cpp @@ -5,7 +5,7 @@ #include "netadr.h" #include "AntiCheatBypass.hpp" -std::unordered_map command_number_mod{}; +boost::unordered_flat_map command_number_mod{}; namespace criticals { diff --git a/src/hacks/Aimbot.cpp b/src/hacks/Aimbot.cpp index 563726ff..2a1dd472 100644 --- a/src/hacks/Aimbot.cpp +++ b/src/hacks/Aimbot.cpp @@ -89,7 +89,16 @@ static settings::Float specfov("aimbot.spectator.fov", "0"); static settings::Int specslow("aimbot.spectator.slow", "0"); settings::Boolean engine_projpred{ "aimbot.debug.engine-pp", "1" }; - +struct AimbotCalculatedData_s +{ + unsigned long predict_tick{ 0 }; + bool predict_type{ 0 }; + Vector aim_position{ 0 }; + unsigned long vcheck_tick{ 0 }; + bool visible{ false }; + float fov{ 0 }; + int hitbox{ 0 }; +} static cd; int slow_aim; float fov; bool enable; @@ -115,6 +124,18 @@ float cur_proj_grav{ 0.0f }; float cur_proj_start_vel{ 0.0f }; bool shouldbacktrack_cache = false; +// Func to find value of how far to target ents +inline float EffectiveTargetingRange() +{ + if (GetWeaponMode() == weapon_melee) + return (float) re::C_TFWeaponBaseMelee::GetSwingRange(RAW_ENT(LOCAL_W)); + else if (LOCAL_W->m_iClassID() == CL_CLASS(CTFFlameThrower)) + return 310.0f; // Pyros only have so much until their flames hit + else if (LOCAL_W->m_iClassID() == CL_CLASS(CTFWeaponFlameBall)) + return 512.0f; // Dragons Fury is fast but short range + + return (float) max_range; +} inline bool isHitboxMedium(int hitbox) { switch (hitbox) @@ -241,7 +262,6 @@ void spectatorUpdate() } } - #define GET_MIDDLE(c1, c2) (corners[c1] + corners[c2]) / 2.0f // Get all the valid aim positions @@ -253,15 +273,11 @@ std::vector getValidHitpoints(CachedEntity *ent, int hitbox) trace_t trace; - if (IsEntityVectorVisible(ent, hb->center, true, MASK_SHOT_HULL, &trace)) + if (IsEntityVectorVisible(ent, hb->center, true, MASK_SHOT_HULL, &trace, true)) { if (trace.hitbox == hitbox) hitpoints.push_back(hb->center); } - - if (!*multipoint) - return hitpoints; - // Multipoint auto bboxmin = hb->bbox->bbmin; auto bboxmax = hb->bbox->bbmax; @@ -302,7 +318,7 @@ std::vector getValidHitpoints(CachedEntity *ent, int hitbox) { trace_t trace; - if (IsEntityVectorVisible(ent, positions[i], true, MASK_SHOT_HULL, &trace)) + if (IsEntityVectorVisible(ent, positions[i], true, MASK_SHOT_HULL, &trace, true)) { if (trace.hitbox == hitbox) hitpoints.push_back(positions[i]); @@ -315,10 +331,14 @@ std::vector getValidHitpoints(CachedEntity *ent, int hitbox) return hitpoints; } int i = 0; - while (hitpoints.empty() && i <= 17) // Prevents returning empty at all costs. Loops through every hitbox + const u_int8_t max_box = ent->hitboxes.GetNumHitboxes(); + while (hitpoints.empty() && i < max_box ) // Prevents returning empty at all costs. Loops through every hitbox { if (hitbox == i) + { ++i; + continue; + } hitpoints = getHitpointsVischeck(ent, i); ++i; } @@ -329,12 +349,7 @@ std::vector getValidHitpoints(CachedEntity *ent, int hitbox) std::vector getHitpointsVischeck(CachedEntity *ent, int hitbox) { std::vector hitpoints; - auto hb = ent->hitboxes.GetHitbox(hitbox); - if (!*multipoint) - { - hitpoints.push_back(hb->center); - return hitpoints; - } + auto hb = ent->hitboxes.GetHitbox(hitbox); auto bboxmin = hb->bbox->bbmin; auto bboxmax = hb->bbox->bbmax; @@ -374,7 +389,7 @@ std::vector getHitpointsVischeck(CachedEntity *ent, int hitbox) { trace_t trace; - if (IsEntityVectorVisible(ent, positions[i], true, MASK_SHOT_HULL, &trace)) + if (IsEntityVectorVisible(ent, positions[i], true, MASK_SHOT_HULL, &trace, true)) { if (trace.hitbox == hitbox) hitpoints.push_back(positions[i]); @@ -390,7 +405,7 @@ std::optional getBestHitpoint(CachedEntity *ent, int hitbox) std::optional best_pos = std::nullopt; float max_score = FLT_MAX; - for (auto &position : positions) + for (auto const &position : positions) { float score = GetFov(g_pLocalPlayer->v_OrigViewangles, g_pLocalPlayer->v_Eye, position); if (score < max_score) @@ -403,10 +418,6 @@ std::optional getBestHitpoint(CachedEntity *ent, int hitbox) return best_pos; } - - - - // Reduce Backtrack lag by checking if the ticks hitboxes are within a reasonable FOV range bool validateTickFOV(tf2::backtrack::BacktrackData &tick) { @@ -428,7 +439,6 @@ bool validateTickFOV(tf2::backtrack::BacktrackData &tick) return true; } - void doAutoZoom(bool target_found) { bool isIdle = target_found ? false : hacks::shared::followbot::isIdle(); @@ -466,7 +476,7 @@ void doAutoZoom(bool target_found) CachedEntity *target_last = 0; bool aimed_this_tick = false; Vector viewangles_this_tick(0.0f); -AimbotCalculatedData_s cd; + // If slow aimbot allows autoshoot bool slow_can_shoot = false; bool projectileAimbotRequired; @@ -1014,7 +1024,7 @@ bool IsTargetStateGood(CachedEntity *entity) cd.hitbox = BestHitbox(entity); if (*vischeck_hitboxes && !*multipoint && is_player) { - if (*vischeck_hitboxes == 1 && playerlist::AccessData(entity).state != playerlist::k_EState::RAGE) + if (*vischeck_hitboxes == 1 && playerlist::AccessData(entity).state != playerlist::k_EState::RAGE || (projectileAimbotRequired && 0.01f < cur_proj_grav) ) { return true; } @@ -1024,17 +1034,22 @@ bool IsTargetStateGood(CachedEntity *entity) int i = 0; trace_t first_tracer; - if (IsEntityVectorVisible(entity, entity->hitboxes.GetHitbox(cd.hitbox)->center, true, MASK_SHOT_HULL, &first_tracer)) + if (IsEntityVectorVisible(entity, entity->hitboxes.GetHitbox(cd.hitbox)->center, true, MASK_SHOT_HULL, &first_tracer, true)) return true; - while (i <= 17) // Prevents returning empty at all costs. Loops through every hitbox + + const u_int8_t max_box = entity->hitboxes.GetNumHitboxes(); + while (i < max_box) // Prevents returning empty at all costs. Loops through every hitbox { - if (i == cd.hitbox && i != 17) + if (i == cd.hitbox) + { ++i; + continue; + } trace_t test_trace; - std::vector centered_hitbox = getHitpointsVischeck(entity, i); + Vector centered_hitbox = entity->hitboxes.GetHitbox(i)->center; - if (IsEntityVectorVisible(entity, centered_hitbox[0], true, MASK_SHOT_HULL, &test_trace)) + if (IsEntityVectorVisible(entity, centered_hitbox, true, MASK_SHOT_HULL, &test_trace, true)) { cd.hitbox = i; return true; @@ -1162,19 +1177,14 @@ bool Aim(CachedEntity *entity) // Get angles from eye to target Vector is_it_good = PredictEntity(entity); if (!projectileAimbotRequired) - { - if (!IsEntityVectorVisible(entity, is_it_good, false)) + if (!IsEntityVectorVisible(entity, is_it_good, true, MASK_SHOT_HULL, nullptr, true)) return false; - } Vector angles = GetAimAtAngles(g_pLocalPlayer->v_Eye, is_it_good, LOCAL_E); if (projectileAimbotRequired) // unfortunately you have to check this twice, otherwise you'd have to run GetAimAtAngles far too early - { - - if (!didProjectileHit(getShootPos(angles), is_it_good, entity, projectileHitboxSize(LOCAL_W->m_iClassID()))) + if (!didProjectileHit(getShootPos(angles), is_it_good, entity, projectileHitboxSize(LOCAL_W->m_iClassID()), (0.01f < cur_proj_grav))) return false; - } if (fov > 0 && cd.fov > fov) return false; // Slow aim @@ -1183,9 +1193,7 @@ bool Aim(CachedEntity *entity) #if ENABLE_VISUALS if (entity->m_Type() == ENTITY_PLAYER) - { hacks::shared::esp::SetEntityColor(entity, colors::target); - } #endif // Set angles current_user_cmd->viewangles = angles; @@ -1335,11 +1343,15 @@ Vector PredictEntity(CachedEntity *entity) else { // Allow multipoint logic to run + if (!*multipoint) + { + result = entity->hitboxes.GetHitbox(cd.hitbox)->center; + break; + } + std::optional best_pos = getBestHitpoint(entity, cd.hitbox); if (best_pos) result = *best_pos; - else - GetHitbox(entity, cd.hitbox, result); } } break; @@ -1471,7 +1483,6 @@ int autoHitbox(CachedEntity *target) return preferred; } - // Function to find the closesnt hitbox to the crosshair for a given ent int ClosestHitbox(CachedEntity *target) { @@ -1574,19 +1585,6 @@ bool UpdateAimkey() return allow_aimkey; } -// Func to find value of how far to target ents -float EffectiveTargetingRange() -{ - if (GetWeaponMode() == weapon_melee) - return (float) re::C_TFWeaponBaseMelee::GetSwingRange(RAW_ENT(LOCAL_W)); - else if (LOCAL_W->m_iClassID() == CL_CLASS(CTFFlameThrower)) - return 310.0f; // Pyros only have so much until their flames hit - else if (LOCAL_W->m_iClassID() == CL_CLASS(CTFWeaponFlameBall)) - return 512.0f; // Dragons Fury is fast but short range - - return (float) max_range; -} - // Used mostly by navbot to not accidentally look at path when aiming bool isAiming() { diff --git a/src/hacks/AntiAntiAim.cpp b/src/hacks/AntiAntiAim.cpp index ff6ac6f2..783df64d 100644 --- a/src/hacks/AntiAntiAim.cpp +++ b/src/hacks/AntiAntiAim.cpp @@ -11,7 +11,7 @@ namespace hacks::shared::anti_anti_aim static settings::Boolean enable{ "anti-anti-aim.enable", "false" }; static settings::Boolean debug{ "anti-anti-aim.debug.enable", "false" }; -std::unordered_map resolver_map; +boost::unordered_flat_map resolver_map; std::array sniperdot_array; static inline void modifyAngles() diff --git a/src/hacks/AutoItem.cpp b/src/hacks/AutoItem.cpp index 56b131d7..96908963 100644 --- a/src/hacks/AutoItem.cpp +++ b/src/hacks/AutoItem.cpp @@ -62,7 +62,7 @@ struct AchivementItem }; // A map that allows us to map item ids to achievement names and achievement ids -static std::unordered_map ach_items; +static boost::unordered_flat_map ach_items; static std::array, 3> craft_groups; bool checkAchMgr() diff --git a/src/hacks/CatBot.cpp b/src/hacks/CatBot.cpp index 3ecf50ee..d0a896db 100644 --- a/src/hacks/CatBot.cpp +++ b/src/hacks/CatBot.cpp @@ -65,7 +65,7 @@ struct catbot_user_state int treacherous_kills{ 0 }; }; -static std::unordered_map human_detecting_map{}; +static boost::unordered_flat_map human_detecting_map{}; int globerr(const char *path, int eerrno) { diff --git a/src/hacks/ChatCommands.cpp b/src/hacks/ChatCommands.cpp index f10d459e..523c3935 100644 --- a/src/hacks/ChatCommands.cpp +++ b/src/hacks/ChatCommands.cpp @@ -50,7 +50,7 @@ private: std::vector commands; }; -static std::unordered_map commands; +static boost::unordered_flat_map commands; void handleChatMessage(std::string message, int senderid) { diff --git a/src/hacks/CritSay.cpp b/src/hacks/CritSay.cpp index 21741fce..7f43bc53 100644 --- a/src/hacks/CritSay.cpp +++ b/src/hacks/CritSay.cpp @@ -19,7 +19,7 @@ struct CritsayStorage std::string message{}; }; -static std::unordered_map critsay_storage{}; +static boost::unordered_flat_map critsay_storage{}; // Thanks HellJustFroze for linking me http://daviseford.com/shittalk/ const std::vector builtin_default = { "Woops, i slipped", "*critical hit* -> %name%", "ok now let's do it again, %name%", "nice" }; diff --git a/src/hacks/ESP.cpp b/src/hacks/ESP.cpp index 78da4beb..1764f1d3 100644 --- a/src/hacks/ESP.cpp +++ b/src/hacks/ESP.cpp @@ -78,12 +78,64 @@ static settings::Boolean entity_model{ "esp.debug.model", "false" }; static settings::Boolean entity_id{ "esp.debug.id", "true" }; // Forward declarations +class ESPData +{ +public: + int string_count{ 0 }; + boost::unordered_flat_map strings{}; + rgba_t color{ colors::empty }; + bool needs_paint{ false }; + bool has_collide{ false }; + Vector collide_max{ 0, 0, 0 }; + Vector collide_min{ 0, 0, 0 }; + bool transparent{ false }; +}; + +boost::unordered_flat_map data; +inline void AddEntityString(CachedEntity *entity, const std::string &string, const rgba_t &color = colors::empty) +{ + ESPData &entity_data = data[entity]; + if (entity_data.strings.try_emplace(string, color).second) + ++(entity_data.string_count); + entity_data.needs_paint = true; +} +inline bool hitboxUpdate(CachedEntity *ent) +{ + + auto hit = ent->hitboxes.GetHitbox(0); + if (!hit) + return false; + Vector hbm, hbx; + if (!draw::WorldToScreen(hit->min, hbm) || !draw::WorldToScreen(hit->max, hbx)) + return false; +} +// Sets an entitys esp color +void SetEntityColor(CachedEntity *entity, const rgba_t &color) +{ + data[entity].color = color; +} +inline void repaintEnt(CachedEntity *ent, float distance) +{ + rgba_t color = colors::EntityF(ent); + if (RAW_ENT(ent)->IsDormant()) + { + color.r *= 0.5f; + color.g *= 0.5f; + color.b *= 0.5f; + } + // If show distance, add string here + if (show_distance) + AddEntityString(ent, format(int(distance / 64 * 1.22f), 'm')); + SetEntityColor(ent, color); +} + void ResetEntityStrings(bool full_clear); // Entity Processing void __attribute__((fastcall)) ProcessEntity(CachedEntity *ent); -void __attribute__((fastcall)) ProcessEntityPT(CachedEntity *ent); -void __attribute__((fastcall)) hitboxUpdate(CachedEntity *ent); +void ProcessEntityPT(); + +void _FASTCALL ShowConditions(CachedEntity *ent); // helper funcs void __attribute__((fastcall)) Draw3DBox(CachedEntity *ent, const rgba_t &clr); void __attribute__((fastcall)) DrawBox(CachedEntity *ent, const rgba_t &clr); @@ -91,7 +143,7 @@ void BoxCorners(int minx, int miny, int maxx, int maxy, const rgba_t &color, boo bool GetCollide(CachedEntity *ent); // Storage vars for entities that need to be re-drawn -std::vector> entities_need_repaint{}; +std::vector> entities_need_repaint{}; // :b:one stuff needs to be up here as puting it in the header for sorting would // be a pain. @@ -104,59 +156,24 @@ const std::string bonenames_spine[] = { "bip_pelvis", "bip_spine_0", "bip_spine const std::string bonenames_arm_r[] = { "bip_upperArm_R", "bip_lowerArm_R", "bip_hand_R" }; const std::string bonenames_arm_l[] = { "bip_upperArm_L", "bip_lowerArm_L", "bip_hand_L" }; const std::string bonenames_up[] = { "bip_upperArm_R", "bip_spine_3", "bip_upperArm_L" }; -class ESPString -{ -public: - std::string data; - rgba_t color{ colors::empty }; -}; -class ESPData -{ -public: - int string_count{ 0 }; - std::array strings{}; - rgba_t color{ colors::empty }; - bool needs_paint{ false }; - bool has_collide{ false }; - Vector collide_max{ 0, 0, 0 }; - Vector collide_min{ 0, 0, 0 }; - bool transparent{ false }; -}; -boost::unordered_flat_map data; -// Dont fully understand struct but a guess is a group of something. -// I will return once I have enough knowlage to reverse this. -// NOTE: No idea on why we cant just use gethitbox and use the displacement on -// that insted of having all this extra code. Shouldnt gethitbox use cached -// hitboxes, if so it should be nicer on performance -// Use to add a esp string to an entity -inline void AddEntityString(CachedEntity *entity, const std::string &string, const rgba_t &color = colors::empty) -{ - ESPData &entity_data = data[entity]; - if (entity_data.string_count >= 15) - return; - entity_data.strings[entity_data.string_count].data = string; - entity_data.strings[entity_data.string_count].color = color; - entity_data.string_count++; - entity_data.needs_paint = true; -} class bonelist_s { private: - bool setup{ false }; - bool success{ false }; - std::unordered_map bones{}; - int leg_r[3]{ 0 }; - int leg_l[3]{ 0 }; - int bottom[3]{ 0 }; - int spine[7]{ 0 }; - int arm_r[3]{ 0 }; - int arm_l[3]{ 0 }; - int up[3]{ 0 }; + boost::unordered_flat_map bones{}; + std::vector leg_r; + std::vector leg_l; + std::vector bottom; + std::vector spine; + std::vector arm_r; + std::vector arm_l; + std::vector up; public: + bool setup{ false }; + bool success{ false }; void Setup(const studiohdr_t *hdr); - void _FASTCALL DrawBoneList(const matrix3x4_t *bones, int *in, int size, const rgba_t &color); + void _FASTCALL DrawBoneList(const matrix3x4_t *bones, std::vector const &in, int size, const rgba_t &color); void _FASTCALL Draw(CachedEntity *ent, const rgba_t &color); }; @@ -168,25 +185,33 @@ void bonelist_s::Setup(const studiohdr_t *hdr) success = false; return; } + bones.clear(); for (int i = 0; i < hdr->numbones; ++i) bones.emplace(std::make_pair(std::string(hdr->pBone(i)->pszName()), i)); - for (int i = 0; i < 7; ++i) - spine[i] = bones.at(bonenames_spine[i]); + for (const auto &spine_str : bonenames_spine) + if (bones.contains(spine_str)) + spine.emplace_back(bones.at(spine_str)); for (int i = 0; i < 3; ++i) { - arm_l[i] = bones.at(bonenames_arm_l[i]); - up[i] = bones.at(bonenames_up[i]); - arm_r[i] = bones.at(bonenames_arm_r[i]); - bottom[i] = bones.at(bonenames_bottom[i]); - leg_l[i] = bones.at(bonenames_leg_l[i]); - leg_r[i] = bones.at(bonenames_leg_r[i]); + if (bones.contains(bonenames_arm_l[i])) + arm_l.emplace_back(bones.at(bonenames_arm_l[i])); + if (bones.contains(bonenames_up[i])) + up.emplace_back(bones.at(bonenames_up[i])); + if (bones.contains(bonenames_arm_r[i])) + arm_r.emplace_back(bones.at(bonenames_arm_r[i])); + if (bones.contains(bonenames_bottom[i])) + bottom.emplace_back(bones.at(bonenames_bottom[i])); + if (bones.contains(bonenames_leg_l[i])) + leg_l.emplace_back(bones.at(bonenames_leg_l[i])); + if (bones.contains(bonenames_leg_r[i])) + leg_r.emplace_back(bones.at(bonenames_leg_r[i])); } success = true; setup = true; } -void _FASTCALL bonelist_s::DrawBoneList(const matrix3x4_t *bones, int *in, int size, const rgba_t &color) +void _FASTCALL bonelist_s::DrawBoneList(const matrix3x4_t *bones, std::vector const &in, int size, const rgba_t &color) { Vector last_screen; Vector current_screen; @@ -215,13 +240,20 @@ void _FASTCALL bonelist_s::Draw(CachedEntity *ent, const rgba_t &color) if (!success) return; const auto &bones = ent->hitboxes.GetBones(); - DrawBoneList(bones, leg_r, 3, color); - DrawBoneList(bones, leg_l, 3, color); - DrawBoneList(bones, bottom, 3, color); - DrawBoneList(bones, spine, 7, color); - DrawBoneList(bones, arm_r, 3, color); - DrawBoneList(bones, arm_l, 3, color); - DrawBoneList(bones, up, 3, color); + DrawBoneList(bones, leg_r, leg_r.size(), color); + DrawBoneList(bones, leg_l, leg_l.size(), color); + DrawBoneList(bones, bottom, bottom.size(), color); + DrawBoneList(bones, spine, spine.size(), color); + DrawBoneList(bones, arm_r, arm_r.size(), color); + DrawBoneList(bones, arm_l, arm_l.size(), color); + DrawBoneList(bones, up, up.size(), color); + leg_r.clear(); + leg_l.clear(); + bottom.clear(); + spine.clear(); + arm_r.clear(); + arm_l.clear(); + up.clear(); } // These are strings that never change and should only be constructed once @@ -311,8 +343,7 @@ static void Draw() if (!enable) return; PROF_SECTION(DRAW_ESP_PERFORMANCE); - for (auto &i : entities_need_repaint) - ProcessEntityPT(ENTITY(i.first)); + ProcessEntityPT(); } // Function called on create move @@ -344,17 +375,17 @@ static void cm() for (auto const &ent : entity_cache::player_cache) { // Get an entity from the loop tick and process it + ProcessEntity(ent); hitboxUpdate(ent); - if (!data.contains(ent)) - data.emplace(ent, ESPData{}); + data.try_emplace(ent, ESPData{}); if (data[ent].needs_paint) { // Checking this every tick is a waste of nanoseconds if (vischeck_tick && vischeck) data[ent].transparent = !ent->IsVisible(); - entities_need_repaint.push_back({ ent->m_IDX, ent->m_vecOrigin().DistToSqr(g_pLocalPlayer->v_Origin) }); + entities_need_repaint.push_back({ ent, ent->m_vecOrigin().DistToSqr(g_pLocalPlayer->v_Origin) }); } } } @@ -370,7 +401,7 @@ static void cm() if (!ent_index->m_bAlivePlayer()) continue; - bool player = ent_index->m_IDX < max_clients; + bool player = ent_index->m_Type() == ENTITY_PLAYER; if (player) { @@ -378,57 +409,25 @@ static void cm() hitboxUpdate(ent_index); } else if (entity_tick) - { ProcessEntity(ent_index); - hitboxUpdate(ent_index); - } - if (!data.contains(ent_index)) - data.emplace(ent_index, ESPData{}); + data.try_emplace(ent_index, ESPData{}); if (data[ent_index].needs_paint) { // Checking this every tick is a waste of nanoseconds + // Get an entity from the loop tick and process iProcessEntityPT nanoseconds if (vischeck_tick && vischeck) data[ent_index].transparent = !ent_index->IsVisible(); - entities_need_repaint.push_back({ ent_index->m_IDX, ent_index->m_vecOrigin().DistToSqr(g_pLocalPlayer->v_Origin) }); + entities_need_repaint.push_back({ ent_index, ent_index->m_vecOrigin().DistToSqr(g_pLocalPlayer->v_Origin) }); } } } } // Render closer entities later in order to have their text in the foreground - std::sort(entities_need_repaint.begin(), entities_need_repaint.end(), [](std::pair &a, std::pair &b) { return a.second > b.second; }); + std::sort(entities_need_repaint.begin(), entities_need_repaint.end(), [](std::pair &a, std::pair &b) { return a.second > b.second; }); } // namespace hacks::shared::esp Timer retry{}; -void Init() -{ - /*esp_font_scale.InstallChangeCallback( - [](IConVar *var, const char *pszOldValue, float flOldValue) { - logging::Info("current font: %p %s %d", fonts::esp.get(), - fonts::esp->path.c_str(), fonts::esp->isLoaded()); - fonts::esp.reset(new fonts::font(DATA_PATH "/fonts/megasans.ttf", - esp_font_scale)); - });*/ -} - -// This is used to stop the bone ESP from lagging -void _FASTCALL hitboxUpdate(CachedEntity *ent) -{ - // Check to prevent crashes - if (CE_BAD(ent) || !ent->m_bAlivePlayer()) - return; - if (ent->m_Type() == ENTITY_PLAYER) - { - auto hit = ent->hitboxes.GetHitbox(0); - if (!hit) - return; - Vector hbm, hbx; - if (draw::WorldToScreen(hit->min, hbm) && draw::WorldToScreen(hit->max, hbx)) - { - Vector head_scr; - } - } -} void _FASTCALL Sightlines(CachedEntity *ent, rgba_t &fg) { @@ -649,15 +648,14 @@ void DrawStrings(EntityType &type, bool &transparent, Vector &draw_point, ESPDat } // Loop through strings - for (int j = 0; j < ent_data.string_count; j++) + for (const auto &[string, color_l] : ent_data.strings) { // Pull string from the entity's cached string array - const ESPString &string = ent_data.strings[j]; // If string has a color assined to it, apply that otherwise use // entities color - rgba_t color = string.color ? string.color : ent_data.color; + rgba_t color = color_l ? color_l : ent_data.color; if (transparent) color = colors::Transparent(color); // Apply transparency if needed @@ -669,10 +667,10 @@ void DrawStrings(EntityType &type, bool &transparent, Vector &draw_point, ESPDat if (*esp_text_position == 3 || *esp_text_position == 4) { float w, h; - fonts::esp->stringSize(string.data, &w, &h); + fonts::esp->stringSize(string, &w, &h); draw_pointx_tmp -= w / 2.0f; } - draw::String(draw_pointx_tmp, draw_point.y, color, string.data.c_str(), *fonts::esp); + draw::String(draw_pointx_tmp, draw_point.y, color, string.c_str(), *fonts::esp); } // Add to the y due to their being text in that spot @@ -759,94 +757,176 @@ void _FASTCALL BoxEsp(EntityType &type, bool &transparent, rgba_t &fg, CachedEnt break; } } -// Used when processing entitys with cached data from createmove in draw -void _FASTCALL ProcessEntityPT(CachedEntity *ent) +void _FASTCALL ShowConditions(CachedEntity *ent) { - PROF_SECTION(PT_esp_process_entity); - - // Check to prevent crashes - if (CE_INVALID(ent) || !ent->m_bAlivePlayer()) - return; - // Dormant - bool dormant = false; + auto clr = colors::EntityF(ent); if (RAW_ENT(ent)->IsDormant()) { - if (!ent->m_vecDormantOrigin()) - return; - dormant = true; + clr.r *= 0.5f; + clr.g *= 0.5f; + clr.b *= 0.5f; } - - int classid = ent->m_iClassID(); - EntityType type = ent->m_Type(); - // Grab esp data - ESPData &ent_data = data[ent]; - - // Get color of entity - // TODO, check if we can move this after world to screen check - rgba_t fg = ent_data.color; - if (!fg || fg.a == 0.0f) + // Invis + if (IsPlayerInvisible(ent)) { - fg = colors::EntityF(ent); - if (dormant) - { - fg.r *= 0.75f; - fg.g *= 0.75f; - fg.b *= 0.75f; - } - ent_data.color = fg; + if (HasCondition(ent)) + AddEntityString(ent, in_ringer_str, colors::FromRGBA8(178.0f, 0.0f, 255.0f, 255.0f)); + else + AddEntityString(ent, cloaked_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); } - - // Check if entity is on screen, then save screen position if true - auto position = ent->m_vecDormantOrigin(); - if (!position) - return; - - // Sightline esp - if (sightlines && type == ENTITY_PLAYER) - Sightlines(ent, fg); - - static Vector screen; - if (!draw::EntityCenterToScreen(ent, screen)) - return; - - // Reset the collide cache - ent_data.has_collide = false; - - // Get if ent should be transparent - bool transparent = vischeck && ent_data.transparent; - - // Box esp - if (box_esp || box_3d_player || box_3d_building) - BoxEsp(type, transparent, fg, ent); - - if (draw_bones) + if (CE_BYTE(ent, netvar.m_bFeignDeathReady)) + AddEntityString(ent, ready_ringer_str, colors::FromRGBA8(178.0f, 0.0f, 255.0f, 255.0f)); + if (HasCondition(ent)) + AddEntityString(ent, disguised_str, colors::FromRGBA8(220, 220, 220, 255)); + if (HasCondition(ent)) + AddEntityString(ent, gassed_str, colors::FromRGBA8(0, 128, 0, 255)); + // Uber/Bonk + if (IsPlayerInvulnerable(ent)) + AddEntityString(ent, invulnerable_str); + // Vaccinator + if (HasCondition(ent)) { - if (vischeck && !ent->IsVisible()) - transparent = true; - rgba_t bone_color = colors::EntityF(ent); - if (transparent) - bone_color = colors::Transparent(bone_color); - - static bonelist_s bl; - if (!CE_INVALID(ent) && ent->m_bAlivePlayer() && !RAW_ENT(ent)->IsDormant()) - { - if (bones_color) - bl.Draw(ent, bone_color); - else - bl.Draw(ent, colors::white); - } + AddEntityString(ent, bullet_a_str, colors::FromRGBA8(220, 220, 220, 255)); } + else if (HasCondition(ent)) + { + AddEntityString(ent, bullet_p_str); + } + if (HasCondition(ent)) + { + AddEntityString(ent, fire_a_str, colors::FromRGBA8(220, 220, 220, 255)); + } + else if (HasCondition(ent)) + { + AddEntityString(ent, fire_p_str); + } + if (HasCondition(ent)) + { + AddEntityString(ent, blast_a_str, colors::FromRGBA8(220, 220, 220, 255)); + } + else if (HasCondition(ent)) + { + AddEntityString(ent, blast_p_str); + } + // Crit + if (IsPlayerCritBoosted(ent)) + AddEntityString(ent, crit_str, colors::orange); - // Health bar - if (*healthbar != 0) - Healthbar(type, classid, fg, ent_data, ent); - // We only want health bars on players and buildings + // We want revving, zoomed and slowed to be mutually exclusive. Otherwise slowed and zoomed/revving will show at the same time. + // Revving + auto weapon_idx = HandleToIDX(CE_INT(ent, netvar.hActiveWeapon)); + CachedEntity *weapon = IDX_GOOD(weapon_idx) ? ENTITY(weapon_idx) : nullptr; + if (CE_GOOD(weapon) && weapon->m_iClassID() == CL_CLASS(CTFMinigun) && CE_INT(weapon, netvar.iWeaponState) != 0) + AddEntityString(ent, revving_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); + // Zoomed + else if (HasCondition(ent)) + AddEntityString(ent, zooming_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); + // Slowed + else if (HasCondition(ent)) + AddEntityString(ent, slowed_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); - // Check if entity has strings to draw - if (ent_data.string_count) - DrawStrings(type, transparent, screen, ent_data, ent); + // Jarated + if (HasCondition(ent)) + AddEntityString(ent, jarated_str, colors::yellow); + // Taunting + if (HasCondition(ent)) + AddEntityString(ent, taunting_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); + // Dormant + if (CE_VALID(ent) && RAW_ENT(ent)->IsDormant()) + AddEntityString(ent, dormant_str, colors::red); } +// Used when processing entitys with cached data from createmove in draw +void ProcessEntityPT() +{ + PROF_SECTION(PT_esp_process_entity); + for (auto const &[ent, distance] : entities_need_repaint) + { + // Check to prevent crashes + if (CE_INVALID(ent) || !ent->m_bAlivePlayer()) + continue; + // Dormant + bool dormant = false; + if (RAW_ENT(ent)->IsDormant()) + { + if (!ent->m_vecDormantOrigin()) + continue; + dormant = true; + } + int classid = ent->m_iClassID(); + EntityType type = ent->m_Type(); + // Grab esp data + ESPData &ent_data = data[ent]; + + // Get color of entity + // TODO, check if we can move this after world to screen check + rgba_t fg = ent_data.color; + if (!fg || fg.a == 0.0f) + { + fg = colors::EntityF(ent); + if (dormant) + { + fg.r *= 0.75f; + fg.g *= 0.75f; + fg.b *= 0.75f; + } + ent_data.color = fg; + } + + // Check if entity is on screen, then save screen position if true + auto position = ent->m_vecDormantOrigin(); + if (!position) + return; + + // Sightline esp + if (sightlines && type == ENTITY_PLAYER) + Sightlines(ent, fg); + + static Vector screen; + if (!draw::EntityCenterToScreen(ent, screen)) + continue; + + // Reset the collide cache + ent_data.has_collide = false; + + // Get if ent should be transparent + bool transparent = vischeck && ent_data.transparent; + + // Box esp + if (box_esp || box_3d_player || box_3d_building) + BoxEsp(type, transparent, fg, ent); + + if (draw_bones) + { + if (vischeck && !ent->IsVisible()) + transparent = true; + rgba_t bone_color = colors::EntityF(ent); + if (transparent) + bone_color = colors::Transparent(bone_color); + + static bonelist_s bl; + bl.success = false; + bl.setup = false; + if (!CE_INVALID(ent) && ent->m_bAlivePlayer() && !RAW_ENT(ent)->IsDormant()) + { + if (bones_color) + bl.Draw(ent, bone_color); + else + bl.Draw(ent, colors::white); + } + } + + // Health bar + if (*healthbar != 0) + Healthbar(type, classid, fg, ent_data, ent); + // We only want health bars on players and buildings + + // Check if entity has strings to draw + if (ent_data.string_count) + DrawStrings(type, transparent, screen, ent_data, ent); + } +} +static std::string write_str; // Used to process entities from CreateMove void _FASTCALL ProcessEntity(CachedEntity *ent) { @@ -882,604 +962,536 @@ void _FASTCALL ProcessEntity(CachedEntity *ent) AddEntityString(ent, std::string(g_IModelInfo->GetModelName(model))); } } - // Get esp data from current ent ESPData &espdata = data[ent]; - - // Projectile esp - if (ent->m_Type() == ENTITY_PROJECTILE && proj_esp && (ent->m_bEnemy() || (teammates && !proj_enemy))) + switch (ent->m_Type()) { - // Rockets - if (classid == CL_CLASS(CTFProjectile_Rocket) || classid == CL_CLASS(CTFProjectile_SentryRocket)) - { - if (proj_rockets) - { - if ((int) proj_rockets != 2 || ent->m_bCritProjectile()) - { - AddEntityString(ent, rocket_str); - } - } - - // Pills/Stickys - } - else if (classid == CL_CLASS(CTFGrenadePipebombProjectile)) - { - // Switch based on pills/stickys - switch (CE_INT(ent, netvar.iPipeType)) - { - case 0: // Pills - if (!proj_pipes) - break; - if ((int) proj_pipes == 2 && !ent->m_bCritProjectile()) - break; - AddEntityString(ent, pill_str); - break; - case 1: // Stickys - if (!proj_stickies) - break; - if ((int) proj_stickies == 2 && !ent->m_bCritProjectile()) - break; - AddEntityString(ent, sticky_str); - } - - // Huntsman - } - else if (classid == CL_CLASS(CTFProjectile_Arrow)) - { - if ((int) proj_arrows != 2 || ent->m_bCritProjectile()) - { - AddEntityString(ent, arrow_str); - } - } - } - int itemtype = ent->m_ItemType(); - // NPC esp - if (npc) + case ENTITY_PROJECTILE: { - // We can mark everything except the ghost like this - if (ent->m_Type() == ENTITY_NPC) + if (proj_esp && (ent->m_bEnemy() || (teammates && !proj_enemy))) { - switch (classid) + // Rockets + if (classid == CL_CLASS(CTFProjectile_Rocket) || classid == CL_CLASS(CTFProjectile_SentryRocket)) { - case CL_CLASS(CTFTankBoss): - AddEntityString(ent, tank_str, colors::FromRGBA8(0, 128, 0, 255)); - break; - case CL_CLASS(CMerasmus): - case CL_CLASS(CMerasmusDancer): - AddEntityString(ent, merasmus_str, colors::FromRGBA8(0, 128, 0, 255)); - break; - case CL_CLASS(CZombie): - AddEntityString(ent, skeleton_str, colors::FromRGBA8(0, 128, 0, 255)); - break; - case CL_CLASS(CEyeballBoss): - AddEntityString(ent, monoculus_str, colors::FromRGBA8(0, 128, 0, 255)); - break; - case CL_CLASS(CHeadlessHatman): - AddEntityString(ent, horsemann_str, colors::FromRGBA8(0, 128, 0, 255)); - break; - } - } - else if (itemtype == HALLOWEEN_GHOST) - AddEntityString(ent, ghost_str, colors::FromRGBA8(0, 128, 0, 255)); - } - if (item_esp) - { - // Dropped weapon esp - if (item_dropped_weapons && classid == CL_CLASS(CTFDroppedWeapon)) - { - AddEntityString(ent, "Dropped Weapon"); - } - // Gargoyle esp - else if (item_gargoyle && classid == CL_CLASS(CHalloweenGiftPickup)) - { - if (HandleToIDX(CE_INT(ent, netvar.m_hTargetPlayer)) == g_pLocalPlayer->entity_idx) - { - AddEntityString(ent, gargoyle_str, colors::FromRGBA8(98, 163, 213, 255)); - } - } - // Explosive/Environmental hazard esp - else if (item_explosive && (classid == CL_CLASS(CTFPumpkinBomb) || (itemtype >= BOMB_BALLOONBOMB && itemtype <= BOMB_WALKEREXPLODE))) - { - if (classid == CL_CLASS(CTFPumpkinBomb)) - AddEntityString(ent, pumpkinbomb_str, colors::FromRGBA8(255, 162, 0, 255)); - else - { - switch (itemtype) + if (proj_rockets) { - case BOMB_BALLOONBOMB: - AddEntityString(ent, balloonbomb_str, colors::FromRGBA8(255, 162, 0, 255)); - break; - case BOMB_WOODENBARREL: - AddEntityString(ent, woodenbarrel_str, colors::FromRGBA8(255, 162, 0, 255)); - break; - case BOMB_WALKEREXPLODE: - AddEntityString(ent, walkerexplode_str, colors::FromRGBA8(255, 162, 0, 255)); - break; - } - } - } - if (item_objectives && (classid == CL_CLASS(CCaptureFlag) || (itemtype >= FLAG_ATOMBOMB && itemtype <= CART_BOMBCART_RED))) - { - rgba_t color = ent->m_iTeam() == TEAM_BLU ? colors::blu : (ent->m_iTeam() == TEAM_RED ? colors::red : colors::white); - - switch (itemtype) - { - case FLAG_ATOMBOMB: - AddEntityString(ent, atombomb_str, color); - break; - case FLAG_SKULLPICKUP: - AddEntityString(ent, soulpickup_str, color); - break; - case FLAG_GIBBUCKET: - AddEntityString(ent, bodyparts_str, color); - break; - case FLAG_BOTTLEPICKUP: - AddEntityString(ent, beerbottle_str, color); - break; - case FLAG_GIFT: - if (classid == CL_CLASS(CCaptureFlag)) - AddEntityString(ent, gift_str, color); - break; - case FLAG_AUSSIECONTAINER: - AddEntityString(ent, aussiecontainer_str, color); - break; - case FLAG_TICKETCASE: - AddEntityString(ent, ticketcase_str, color); - break; - case CART_BOMBCART: - AddEntityString(ent, cart_str, colors::blu); - break; - case CART_BOMBCART_RED: - AddEntityString(ent, cart_str, colors::red); - break; - default: - AddEntityString(ent, intel_str, color); - break; - } - - auto resettime = CE_FLOAT(ent, netvar.m_flResetTime); - std::string time = std::to_string(int(resettime - g_GlobalVars->curtime)); - time.append("s"); - - if (resettime && classid == CL_CLASS(CCaptureFlag)) - AddEntityString(ent, time, colors::FromRGBA8(98, 163, 213, 255)); - } - // Other item esp - else if (itemtype != ITEM_NONE) - { - // Health pack esp - if (item_health_packs && ((itemtype >= ITEM_HEALTH_SMALL && itemtype <= EDIBLE_MEDIUM) || itemtype == ITEM_HL_BATTERY)) - { - switch (itemtype) - { - case ITEM_HEALTH_SMALL: - AddEntityString(ent, health_small_str); - break; - case ITEM_HEALTH_MEDIUM: - AddEntityString(ent, health_medium_str); - break; - case ITEM_HEALTH_LARGE: - AddEntityString(ent, health_big_str); - break; - case ITEM_HL_BATTERY: - AddEntityString(ent, hl_battery_str); - break; - case EDIBLE_MEDIUM: - AddEntityString(ent, mediumhealth_str, colors::green); - break; - case EDIBLE_SMALL: - AddEntityString(ent, smallhealth_str, colors::green); - break; - } - // TF2C Adrenaline esp - } - else if (item_adrenaline && itemtype == ITEM_TF2C_PILL) - { - AddEntityString(ent, pill_str); - - // Ammo pack esp - } - else if (item_ammo_packs && itemtype >= ITEM_AMMO_SMALL && itemtype <= ITEM_AMMO_LARGE) - { - switch (itemtype) - { - case ITEM_AMMO_SMALL: - AddEntityString(ent, ammo_small_str); - break; - case ITEM_AMMO_MEDIUM: - AddEntityString(ent, ammo_medium_str); - break; - case ITEM_AMMO_LARGE: - AddEntityString(ent, ammo_big_str); - break; - } - // Powerup esp - } - else if (item_powerups && itemtype >= ITEM_POWERUP_FIRST && itemtype <= ITEM_POWERUP_LAST) - { - AddEntityString(ent, powerups[itemtype - ITEM_POWERUP_FIRST]); - - // TF2C weapon spawner esp - } - else if (item_weapon_spawners && itemtype >= ITEM_TF2C_W_FIRST && itemtype <= ITEM_TF2C_W_LAST) - { - AddEntityString(ent, std::string(tf2c_weapon_names[itemtype - ITEM_TF2C_W_FIRST]) + " Spawner"); - if (CE_BYTE(ent, netvar.bRespawning)) - AddEntityString(ent, tf2c_spawner_respawn_str); - } - // Halloween spell esp - else if (item_spellbooks && (itemtype == ITEM_SPELL || itemtype == ITEM_SPELL_RARE)) - { - if (itemtype == ITEM_SPELL) - { - AddEntityString(ent, spell_str, colors::green); - } - else - { - AddEntityString(ent, rare_spell_str, colors::FromRGBA8(139, 31, 221, 255)); - } - } - // Crumpkin esp https://wiki.teamfortress.com/wiki/Halloween_pumpkin - else if (item_crumpkin && itemtype == ITEM_CRUMPKIN) - { - AddEntityString(ent, crumpkin_str, colors::FromRGBA8(253, 203, 88, 255)); - } - } - } - // MVM Money esp - if (classid == CL_CLASS(CCurrencyPack) && item_money) - { - if (CE_BYTE(ent, netvar.bDistributed)) - { - if (item_money_red) - { - AddEntityString(ent, mvm_red_money_str); - } - } - else - { - AddEntityString(ent, mvm_money_str); - } - } - // Building esp - else if (ent->m_Type() == ENTITY_BUILDING && buildings) - { - - // Check if enemy building - if (!ent->m_bEnemy() && !team_buildings) - return; - - // TODO maybe... - /*if (legit && ent->m_iTeam() != g_pLocalPlayer->team) { - if (ent->m_lLastSeen > v_iLegitSeenTicks->GetInt()) { - return; - } - }*/ - - // Make a name for the building based on the building type and level - if (show_name || show_class) - { - const std::string &name = (classid == CL_CLASS(CObjectTeleporter) ? teleporter_str : (classid == CL_CLASS(CObjectSentrygun) ? sentry_str : dispenser_str)); - int level = CE_INT(ent, netvar.iUpgradeLevel); - bool IsMini = CE_BYTE(ent, netvar.m_bMiniBuilding); - - if (!IsMini) - AddEntityString(ent, format(name, " (Level ", level, ")")); - else - AddEntityString(ent, std::string("Mini ") + name); - } - - // If text health is true, then add a string with the health - if (show_health) - { - AddEntityString(ent, format(ent->m_iHealth(), '/', ent->m_iMaxHealth(), " HP"), colors::Health(ent->m_iHealth(), ent->m_iMaxHealth())); - } - - if (show_conditions) - { - bool IsSapped = CE_BYTE(ent, netvar.m_bHasSapper); - bool IsDisabled = CE_BYTE(ent, netvar.m_bDisabled); - bool IsPlasmaDisabled = CE_BYTE(ent, netvar.m_bPlasmaDisable); - bool IsMini = CE_BYTE(ent, netvar.m_bMiniBuilding); - int required_metal = CE_INT(ent, netvar.m_iUpgradeMetalRequired); - int metal = CE_INT(ent, netvar.m_iUpgradeMetal); - - if (!IsMini && CE_INT(ent, netvar.iUpgradeLevel) != 3) - AddEntityString(ent, format("Upgrade: " + std::to_string(required_metal - metal), '/', std::to_string(required_metal))); - - switch (classid) - { - case CL_CLASS(CObjectSentrygun): - { - bool IsControlled = CE_BYTE(ent, netvar.m_bPlayerControlled); - int sentry_ammo = CE_INT(ent, netvar.m_iAmmoShells); - int sentry_rockets = CE_INT(ent, netvar.m_iAmmoRockets); - int max_ammo = 0; - - switch (CE_INT(ent, netvar.iUpgradeLevel)) - { - case 1: - max_ammo = 150; - break; - case 2: - case 3: - max_ammo = 200; - break; - } - - AddEntityString(ent, format(std::to_string(sentry_ammo), '/', max_ammo, " Ammo")); - - if (CE_INT(ent, netvar.iUpgradeLevel) == 3) - AddEntityString(ent, format(std::to_string(sentry_rockets), '/', "20 Rockets")); - - if (IsControlled) // Dispensers are also "controlled" when they're in use - AddEntityString(ent, controlled_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); - break; - } - case CL_CLASS(CObjectDispenser): - { - int AmmoMetal = CE_INT(ent, netvar.m_iAmmoMetal); - - AddEntityString(ent, format(std::to_string(AmmoMetal), '/', "400 Metal")); - break; - } - case CL_CLASS(CObjectTeleporter): - { - if (CE_INT(ent, netvar.m_iTeleState) > 1) - { - float next_teleport = CE_FLOAT(ent, netvar.m_flTeleRechargeTime); - float yaw_to_exit = CE_FLOAT(ent, netvar.m_flTeleYawToExit); - std::string time = std::to_string(int(next_teleport - g_GlobalVars->curtime)); - time.append("s"); - - if (yaw_to_exit) + if ((int) proj_rockets != 2 || ent->m_bCritProjectile()) { - if (next_teleport < g_GlobalVars->curtime) - AddEntityString(ent, tp_ready_str); - else - AddEntityString(ent, time); + AddEntityString(ent, rocket_str); } } - break; + + // Pills/Stickys } - } - - if (IsSapped) - AddEntityString(ent, sapped_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); - - else if ((classid == CL_CLASS(CObjectTeleporter) && CE_INT(ent, netvar.m_iTeleState) <= 1) || IsDisabled || IsPlasmaDisabled) - AddEntityString(ent, disabled_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); - } - - // Set the entity to repaint - espdata.needs_paint = true; - - // Player esp - } - else if (ent->m_Type() == ENTITY_PLAYER && ent->m_bAlivePlayer()) - { - // Local player handling - if (!(local_esp && g_IInput->CAM_IsThirdPerson()) && ent->m_IDX == g_IEngine->GetLocalPlayer()) - return; - if (hide_invis && IsPlayerInvisible(ent)) - return; - - // Get player class - int pclass = CE_INT(ent, netvar.iClass); - - // Attempt to get player info, and if cant, return - player_info_s info; - if (!GetPlayerInfo(ent->m_IDX, &info)) - return; - - // TODO, check if u can just use "ent->m_bEnemy()" instead of m_iTeam - // Legit mode handling - if (legit && ent->m_bEnemy() && playerlist::IsDefault(info.friendsID)) - { - if (IsPlayerInvisible(ent)) - return; // Invis check - if (vischeck && !ent->IsVisible()) - return; // Vis check - // TODO, maybe... - // if (ent->m_lLastSeen > - // (unsigned)v_iLegitSeenTicks->GetInt()) - // return; - } - - // Powerup handling - if (powerup_esp) - { - powerup_type power = GetPowerupOnPlayer(ent); - if (power != not_powerup) - AddEntityString(ent, std::string("^ ") + powerups[power] + " ^"); - } - - if (ent->m_bEnemy() || teammates || player_tools::shouldAlwaysRenderEsp(ent)) - { - // Playername - if (show_name) - AddEntityString(ent, std::string(info.name)); - - // Player class - if (show_class) + else if (classid == CL_CLASS(CTFGrenadePipebombProjectile)) { - if (pclass > 0 && pclass < 10) - AddEntityString(ent, classes[pclass - 1]); + // Switch based on pills/stickys + switch (CE_INT(ent, netvar.iPipeType)) + { + case 0: // Pills + if (!proj_pipes) + break; + if ((int) proj_pipes == 2 && !ent->m_bCritProjectile()) + break; + AddEntityString(ent, pill_str); + break; + case 1: // Stickys + if (!proj_stickies) + break; + if ((int) proj_stickies == 2 && !ent->m_bCritProjectile()) + break; + AddEntityString(ent, sticky_str); + } + + // Huntsman } + else if (classid == CL_CLASS(CTFProjectile_Arrow)) + { + if ((int) proj_arrows != 2 || ent->m_bCritProjectile()) + { + AddEntityString(ent, arrow_str); + } + } + } + break; + } + case ENTITY_PLAYER: + { + if (ent->m_bAlivePlayer()) + { + // Local player handling + if (!(local_esp && g_IInput->CAM_IsThirdPerson()) && ent->m_IDX == g_IEngine->GetLocalPlayer()) + return; + if (hide_invis && IsPlayerInvisible(ent)) + return; + + // Get player class + int pclass = CE_INT(ent, netvar.iClass); + + // Attempt to get player info, and if cant, return + player_info_s info; + if (!GetPlayerInfo(ent->m_IDX, &info)) + return; + + // TODO, check if u can just use "ent->m_bEnemy()" instead of m_iTeam + // Legit mode handling + if (legit && ent->m_bEnemy() && playerlist::IsDefault(info.friendsID)) + { + if (IsPlayerInvisible(ent)) + return; // Invis check + if (vischeck && !ent->IsVisible()) + return; // Vis check + // TODO, maybe... + // if (ent->m_lLastSeen > + // (unsigned)v_iLegitSeenTicks->GetInt()) + // return; + } + + // Powerup handling + if (powerup_esp) + { + powerup_type power = GetPowerupOnPlayer(ent); + if (power != not_powerup) + AddEntityString(ent, std::string("^ ") + powerups[power] + " ^"); + } + + if (ent->m_bEnemy() || teammates || player_tools::shouldAlwaysRenderEsp(ent)) + { + // Playername + if (show_name) + AddEntityString(ent, std::string(info.name)); + + // Player class + if (show_class) + { + if (pclass > 0 && pclass < 10) + AddEntityString(ent, classes[pclass - 1]); + } #if ENABLE_IPC - // ipc bot esp - if (show_bot_id && ipc::peer && ent != LOCAL_E) - { - for (unsigned i = 0; i < cat_ipc::max_peers; ++i) + // ipc bot esp + if (show_bot_id && ipc::peer && ent != LOCAL_E) { - if (!ipc::peer->memory->peer_data[i].free && ipc::peer->memory->peer_user_data[i].friendid == info.friendsID) + for (unsigned i = 0; i < cat_ipc::max_peers; ++i) { - AddEntityString(ent, botname_str + std::to_string(i)); - break; + if (!ipc::peer->memory->peer_data[i].free && ipc::peer->memory->peer_user_data[i].friendid == info.friendsID) + { + AddEntityString(ent, botname_str + std::to_string(i)); + break; + } } } - } #endif - // Health esp - if (show_health) - { - int health = g_pPlayerResource->GetHealth(ent); - int max_health = g_pPlayerResource->GetMaxHealth(ent); - AddEntityString(ent, format(health, '/', max_health, " HP"), colors::Health(health, max_health)); - } - IF_GAME(IsTF()) - { - // Medigun Ubercharge esp - if (show_ubercharge) + // Health esp + if (show_health) { - if (CE_INT(ent, netvar.iClass) == tf_medic) + int health = g_pPlayerResource->GetHealth(ent); + int max_health = g_pPlayerResource->GetMaxHealth(ent); + AddEntityString(ent, format(health, '/', max_health, " HP"), colors::Health(health, max_health)); + } + IF_GAME(IsTF()) + { + // Medigun Ubercharge esp + if (show_ubercharge) { - int *weapon_list = (int *) ((unsigned) (RAW_ENT(ent)) + netvar.hMyWeapons); - for (int i = 0; weapon_list[i]; ++i) + if (CE_INT(ent, netvar.iClass) == tf_medic) { - int handle = weapon_list[i]; - int eid = HandleToIDX(handle); - if (eid > MAX_PLAYERS && eid <= HIGHEST_ENTITY) + int *weapon_list = (int *) ((unsigned) (RAW_ENT(ent)) + netvar.hMyWeapons); + for (int i = 0; weapon_list[i]; ++i) { - CachedEntity *weapon = ENTITY(eid); - if (!CE_INVALID(weapon) && weapon->m_iClassID() == CL_CLASS(CWeaponMedigun) && weapon) + int handle = weapon_list[i]; + int eid = HandleToIDX(handle); + if (eid > MAX_PLAYERS && eid <= HIGHEST_ENTITY) { - std::string charge = std::to_string(int(CE_FLOAT(weapon, netvar.m_flChargeLevel) * 100)); - - if (CE_INT(weapon, netvar.iItemDefinitionIndex) != 998) + CachedEntity *weapon = ENTITY(eid); + if (!CE_INVALID(weapon) && weapon->m_iClassID() == CL_CLASS(CWeaponMedigun) && weapon) { - AddEntityString(ent, charge + "% Uber", colors::Health(CE_FLOAT(weapon, netvar.m_flChargeLevel) * 100, 100)); + std::string charge = std::to_string(int(CE_FLOAT(weapon, netvar.m_flChargeLevel) * 100)); + + if (CE_INT(weapon, netvar.iItemDefinitionIndex) != 998) + { + AddEntityString(ent, charge + "% Uber", colors::Health(CE_FLOAT(weapon, netvar.m_flChargeLevel) * 100, 100)); + } + else + AddEntityString(ent, charge + "% Uber | Charges: " + std::to_string(int(CE_FLOAT(weapon, netvar.m_flChargeLevel) / 0.25f)), colors::Health((CE_FLOAT(weapon, netvar.m_flChargeLevel) * 100), 100)); + break; } - else - AddEntityString(ent, charge + "% Uber | Charges: " + std::to_string(int(CE_FLOAT(weapon, netvar.m_flChargeLevel) / 0.25f)), colors::Health((CE_FLOAT(weapon, netvar.m_flChargeLevel) * 100), 100)); - break; } } } } + // Conditions esp + if (show_conditions) + ShowConditions(ent); } - // Conditions esp - if (show_conditions) + // Hoovy Esp + if (IsHoovy(ent)) + AddEntityString(ent, hoovy_str); + + // Active weapon esp + if (show_weapon) { - auto clr = colors::EntityF(ent); - if (RAW_ENT(ent)->IsDormant()) + int widx = HandleToIDX(CE_INT(ent, netvar.hActiveWeapon)); + if (IDX_GOOD(widx)) { - clr.r *= 0.5f; - clr.g *= 0.5f; - clr.b *= 0.5f; - } - // Invis - if (IsPlayerInvisible(ent)) - { - if (HasCondition(ent)) - AddEntityString(ent, in_ringer_str, colors::FromRGBA8(178.0f, 0.0f, 255.0f, 255.0f)); - else - AddEntityString(ent, cloaked_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); - } - if (CE_BYTE(ent, netvar.m_bFeignDeathReady)) - AddEntityString(ent, ready_ringer_str, colors::FromRGBA8(178.0f, 0.0f, 255.0f, 255.0f)); - if (HasCondition(ent)) - AddEntityString(ent, disguised_str, colors::FromRGBA8(220, 220, 220, 255)); - if (HasCondition(ent)) - AddEntityString(ent, gassed_str, colors::FromRGBA8(0, 128, 0, 255)); - // Uber/Bonk - if (IsPlayerInvulnerable(ent)) - AddEntityString(ent, invulnerable_str); - // Vaccinator - if (HasCondition(ent)) - { - AddEntityString(ent, bullet_a_str, colors::FromRGBA8(220, 220, 220, 255)); - } - else if (HasCondition(ent)) - { - AddEntityString(ent, bullet_p_str); - } - if (HasCondition(ent)) - { - AddEntityString(ent, fire_a_str, colors::FromRGBA8(220, 220, 220, 255)); - } - else if (HasCondition(ent)) - { - AddEntityString(ent, fire_p_str); - } - if (HasCondition(ent)) - { - AddEntityString(ent, blast_a_str, colors::FromRGBA8(220, 220, 220, 255)); - } - else if (HasCondition(ent)) - { - AddEntityString(ent, blast_p_str); - } - // Crit - if (IsPlayerCritBoosted(ent)) - AddEntityString(ent, crit_str, colors::orange); - - // We want revving, zoomed and slowed to be mutually exclusive. Otherwise slowed and zoomed/revving will show at the same time. - // Revving - auto weapon_idx = HandleToIDX(CE_INT(ent, netvar.hActiveWeapon)); - CachedEntity *weapon = IDX_GOOD(weapon_idx) ? ENTITY(weapon_idx) : nullptr; - if (CE_GOOD(weapon) && weapon->m_iClassID() == CL_CLASS(CTFMinigun) && CE_INT(weapon, netvar.iWeaponState) != 0) - AddEntityString(ent, revving_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); - // Zoomed - else if (HasCondition(ent)) - AddEntityString(ent, zooming_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); - // Slowed - else if (HasCondition(ent)) - AddEntityString(ent, slowed_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); - - // Jarated - if (HasCondition(ent)) - AddEntityString(ent, jarated_str, colors::yellow); - // Taunting - if (HasCondition(ent)) - AddEntityString(ent, taunting_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); - // Dormant - if (CE_VALID(ent) && RAW_ENT(ent)->IsDormant()) - AddEntityString(ent, dormant_str, colors::red); - } - } - // Hoovy Esp - if (IsHoovy(ent)) - AddEntityString(ent, hoovy_str); - - // Active weapon esp - if (show_weapon) - { - int widx = HandleToIDX(CE_INT(ent, netvar.hActiveWeapon)); - if (IDX_GOOD(widx)) - { - CachedEntity *weapon = ENTITY(widx); - if (CE_VALID(weapon) && re::C_BaseCombatWeapon::IsBaseCombatWeapon(RAW_ENT(weapon))) - { - const char *weapon_name = g_ILocalize->FindAsUTF8(re::C_BaseCombatWeapon::GetPrintName(RAW_ENT(weapon))); - if (weapon_name) - AddEntityString(ent, std::string(weapon_name)); + CachedEntity *weapon = ENTITY(widx); + if (CE_VALID(weapon) && re::C_BaseCombatWeapon::IsBaseCombatWeapon(RAW_ENT(weapon))) + { + const char *weapon_name = g_ILocalize->FindAsUTF8(re::C_BaseCombatWeapon::GetPrintName(RAW_ENT(weapon))); + if (weapon_name) + AddEntityString(ent, std::string(weapon_name)); + } } } - } - // Notify esp to repaint - espdata.needs_paint = true; + // Notify esp to repaint + repaintEnt(ent, distance); + } } + break; } - - if (espdata.needs_paint) + case ENTITY_NPC: { - // Set entity color - rgba_t color = colors::EntityF(ent); - if (RAW_ENT(ent)->IsDormant()) + if (npc) { - color.r *= 0.5f; - color.g *= 0.5f; - color.b *= 0.5f; + // We can mark everything except the ghost like this + if (ent->m_Type() == ENTITY_NPC) + { + switch (classid) + { + case CL_CLASS(CTFTankBoss): + write_str = tank_str; + break; + case CL_CLASS(CMerasmus): + case CL_CLASS(CMerasmusDancer): + write_str = merasmus_str; + break; + case CL_CLASS(CZombie): + write_str = skeleton_str; + break; + case CL_CLASS(CEyeballBoss): + write_str = monoculus_str; + break; + case CL_CLASS(CHeadlessHatman): + write_str = horsemann_str; + break; + } + AddEntityString(ent, write_str, colors::FromRGBA8(0, 128, 0, 255)); + } + if (ent->m_ItemType() == HALLOWEEN_GHOST) + AddEntityString(ent, ghost_str, colors::FromRGBA8(0, 128, 0, 255)); } - // If show distance, add string here - if (show_distance) + break; + } + case ENTITY_BUILDING: + { + if (buildings) { - AddEntityString(ent, format(int(distance / 64 * 1.22f), 'm')); + + // Check if enemy building + if (!ent->m_bEnemy() && !team_buildings) + return; + + // TODO maybe... + /*if (legit && ent->m_iTeam() != g_pLocalPlayer->team) { + if (ent->m_lLastSeen > v_iLegitSeenTicks->GetInt()) { + return; + } + }*/ + + // Make a name for the building based on the building type and level + if (show_name || show_class) + { + const std::string &name = (classid == CL_CLASS(CObjectTeleporter) ? teleporter_str : (classid == CL_CLASS(CObjectSentrygun) ? sentry_str : dispenser_str)); + int level = CE_INT(ent, netvar.iUpgradeLevel); + bool IsMini = CE_BYTE(ent, netvar.m_bMiniBuilding); + + if (!IsMini) + AddEntityString(ent, format(name, " (Level ", level, ")")); + else + AddEntityString(ent, std::string("Mini ") + name); + } + + // If text health is true, then add a string with the health + if (show_health) + { + AddEntityString(ent, format(ent->m_iHealth(), '/', ent->m_iMaxHealth(), " HP"), colors::Health(ent->m_iHealth(), ent->m_iMaxHealth())); + } + + if (show_conditions) + { + bool IsSapped = CE_BYTE(ent, netvar.m_bHasSapper); + bool IsDisabled = CE_BYTE(ent, netvar.m_bDisabled); + bool IsPlasmaDisabled = CE_BYTE(ent, netvar.m_bPlasmaDisable); + bool IsMini = CE_BYTE(ent, netvar.m_bMiniBuilding); + int required_metal = CE_INT(ent, netvar.m_iUpgradeMetalRequired); + int metal = CE_INT(ent, netvar.m_iUpgradeMetal); + + if (!IsMini && CE_INT(ent, netvar.iUpgradeLevel) != 3) + AddEntityString(ent, format("Upgrade: " + std::to_string(required_metal - metal), '/', std::to_string(required_metal))); + + switch (classid) + { + case CL_CLASS(CObjectSentrygun): + { + bool IsControlled = CE_BYTE(ent, netvar.m_bPlayerControlled); + int sentry_ammo = CE_INT(ent, netvar.m_iAmmoShells); + int sentry_rockets = CE_INT(ent, netvar.m_iAmmoRockets); + int max_ammo = 0; + + switch (CE_INT(ent, netvar.iUpgradeLevel)) + { + case 1: + max_ammo = 150; + break; + case 2: + case 3: + max_ammo = 200; + break; + } + + AddEntityString(ent, format(std::to_string(sentry_ammo), '/', max_ammo, " Ammo")); + + if (CE_INT(ent, netvar.iUpgradeLevel) == 3) + AddEntityString(ent, format(std::to_string(sentry_rockets), '/', "20 Rockets")); + + if (IsControlled) // Dispensers are also "controlled" when they're in use + AddEntityString(ent, controlled_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); + break; + } + case CL_CLASS(CObjectDispenser): + { + int AmmoMetal = CE_INT(ent, netvar.m_iAmmoMetal); + + AddEntityString(ent, format(std::to_string(AmmoMetal), '/', "400 Metal")); + break; + } + case CL_CLASS(CObjectTeleporter): + { + if (CE_INT(ent, netvar.m_iTeleState) > 1) + { + float next_teleport = CE_FLOAT(ent, netvar.m_flTeleRechargeTime); + float yaw_to_exit = CE_FLOAT(ent, netvar.m_flTeleYawToExit); + std::string time = std::to_string(int(next_teleport - g_GlobalVars->curtime)); + time.append("s"); + + if (yaw_to_exit) + { + if (next_teleport < g_GlobalVars->curtime) + AddEntityString(ent, tp_ready_str); + else + AddEntityString(ent, time); + } + } + break; + } + } + + if (IsSapped) + AddEntityString(ent, sapped_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); + + else if ((classid == CL_CLASS(CObjectTeleporter) && CE_INT(ent, netvar.m_iTeleState) <= 1) || IsDisabled || IsPlasmaDisabled) + AddEntityString(ent, disabled_str, colors::FromRGBA8(220.0f, 220.0f, 220.0f, 255.0f)); + } + + // Set the entity to repaint + repaintEnt(ent, distance); + + // Player esp + } + break; + } + default: + if (item_esp) + { + int itemtype = ent->m_ItemType(); + // Dropped weapon esp + if (item_dropped_weapons && classid == CL_CLASS(CTFDroppedWeapon)) + { + AddEntityString(ent, "Dropped Weapon"); + } + // Gargoyle esp + else if (item_gargoyle && classid == CL_CLASS(CHalloweenGiftPickup)) + { + if (HandleToIDX(CE_INT(ent, netvar.m_hTargetPlayer)) == g_pLocalPlayer->entity_idx) + { + AddEntityString(ent, gargoyle_str, colors::FromRGBA8(98, 163, 213, 255)); + } + } + // Explosive/Environmental hazard esp + else if (item_explosive && (classid == CL_CLASS(CTFPumpkinBomb) || (itemtype >= BOMB_BALLOONBOMB && itemtype <= BOMB_WALKEREXPLODE))) + { + if (classid == CL_CLASS(CTFPumpkinBomb)) + AddEntityString(ent, pumpkinbomb_str, colors::FromRGBA8(255, 162, 0, 255)); + else + { + switch (itemtype) + { + case BOMB_BALLOONBOMB: + write_str = balloonbomb_str; + break; + case BOMB_WOODENBARREL: + write_str = woodenbarrel_str; + break; + case BOMB_WALKEREXPLODE: + write_str = walkerexplode_str; + break; + } + AddEntityString(ent, write_str, colors::FromRGBA8(255, 162, 0, 255)); + } + } + if (item_objectives && (classid == CL_CLASS(CCaptureFlag) || (itemtype >= FLAG_ATOMBOMB && itemtype <= CART_BOMBCART_RED))) + { + rgba_t color = ent->m_iTeam() == TEAM_BLU ? colors::blu : (ent->m_iTeam() == TEAM_RED ? colors::red : colors::white); + + switch (itemtype) + { + case FLAG_ATOMBOMB: + write_str = atombomb_str; + break; + case FLAG_SKULLPICKUP: + write_str = soulpickup_str; + break; + case FLAG_GIBBUCKET: + write_str = bodyparts_str; + break; + case FLAG_BOTTLEPICKUP: + write_str = beerbottle_str; + break; + case FLAG_GIFT: + if (classid == CL_CLASS(CCaptureFlag)) + write_str = gift_str; + break; + case FLAG_AUSSIECONTAINER: + write_str = aussiecontainer_str; + break; + case FLAG_TICKETCASE: + write_str = ticketcase_str; + break; + case CART_BOMBCART: + color = colors::blu; + write_str = cart_str; + break; + case CART_BOMBCART_RED: + color = colors::red; + write_str = cart_str; + break; + default: + write_str = intel_str; + break; + } + AddEntityString(ent, write_str, color); + + auto resettime = CE_FLOAT(ent, netvar.m_flResetTime); + std::string time = std::to_string(int(resettime - g_GlobalVars->curtime)); + time.append("s"); + + if (resettime && classid == CL_CLASS(CCaptureFlag)) + AddEntityString(ent, time, colors::FromRGBA8(98, 163, 213, 255)); + } + // Other item esp + else if (itemtype != ITEM_NONE) + { + rgba_t color = colors::empty; + // Health pack esp + if (item_health_packs && ((itemtype >= ITEM_HEALTH_SMALL && itemtype <= EDIBLE_MEDIUM) || itemtype == ITEM_HL_BATTERY)) + { + switch (itemtype) + { + case ITEM_HEALTH_SMALL: + write_str = health_small_str; + break; + case ITEM_HEALTH_MEDIUM: + write_str = health_medium_str; + break; + case ITEM_HEALTH_LARGE: + write_str = health_big_str; + break; + case ITEM_HL_BATTERY: + write_str = hl_battery_str; + break; + case EDIBLE_MEDIUM: + write_str = mediumhealth_str; + color = colors::green; + break; + case EDIBLE_SMALL: + write_str = smallhealth_str; + color = colors::green; + break; + } + // TF2C Adrenaline esp + } + else if (item_adrenaline && itemtype == ITEM_TF2C_PILL) + { + write_str = pill_str; + + // Ammo pack esp + } + else if (item_ammo_packs && itemtype >= ITEM_AMMO_SMALL && itemtype <= ITEM_AMMO_LARGE) + { + switch (itemtype) + { + case ITEM_AMMO_SMALL: + write_str = ammo_small_str; + break; + case ITEM_AMMO_MEDIUM: + write_str = ammo_medium_str; + break; + case ITEM_AMMO_LARGE: + write_str = ammo_big_str; + break; + } + // Powerup esp + } + else if (item_powerups && itemtype >= ITEM_POWERUP_FIRST && itemtype <= ITEM_POWERUP_LAST) + { + write_str = powerups[itemtype - ITEM_POWERUP_FIRST]; + + // TF2C weapon spawner esp + } + else if (item_weapon_spawners && itemtype >= ITEM_TF2C_W_FIRST && itemtype <= ITEM_TF2C_W_LAST) + { + write_str = std::string(tf2c_weapon_names[itemtype - ITEM_TF2C_W_FIRST]) + " Spawner"; + if (CE_BYTE(ent, netvar.bRespawning)) + AddEntityString(ent, tf2c_spawner_respawn_str); + } + // Halloween spell esp + else if (item_spellbooks && (itemtype == ITEM_SPELL || itemtype == ITEM_SPELL_RARE)) + { + if (itemtype == ITEM_SPELL) + { + write_str = spell_str; + color = colors::green; + } + else + { + write_str = rare_spell_str; + color = colors::FromRGBA8(139, 31, 221, 255); + } + } + // Crumpkin esp https://wiki.teamfortress.com/wiki/Halloween_pumpkin + else if (item_crumpkin && itemtype == ITEM_CRUMPKIN) + { + write_str = crumpkin_str; + color = colors::FromRGBA8(253, 203, 88, 255); + } + AddEntityString(ent, write_str, color); + } + } + if (item_money && classid == CL_CLASS(CCurrencyPack)) + { + if (CE_BYTE(ent, netvar.bDistributed)) + { + if (item_money_red) + { + AddEntityString(ent, mvm_red_money_str); + } + } + else + { + AddEntityString(ent, mvm_money_str); + } } - SetEntityColor(ent, color); } } @@ -1710,15 +1722,18 @@ bool GetCollide(CachedEntity *ent) // Impossible error, return false return false; } + // Function to reset entitys strings void ResetEntityStrings(bool full_clear) { if (full_clear) for (auto &[key, val] : data) { + val.string_count = 0; val.color = colors::empty; val.needs_paint = false; + val.strings.clear(); } else for (int i = 1; i < g_GlobalVars->maxClients; ++i) @@ -1727,24 +1742,15 @@ void ResetEntityStrings(bool full_clear) element.string_count = 0; element.color = colors::empty; element.needs_paint = false; + element.strings.clear(); } } - -// Sets an entitys esp color -inline void SetEntityColor(CachedEntity *entity, const rgba_t &color) -{ - if (entity->m_IDX > 2047 || entity->m_IDX < 0) - return; - data[entity].color = color; -} - static InitRoutine init( []() { EC::Register(EC::CreateMove, cm, "cm_esp", EC::average); #if ENABLE_VISUALS EC::Register(EC::Draw, Draw, "draw_esp", EC::average); - Init(); #endif }); diff --git a/src/hacks/KillSay.cpp b/src/hacks/KillSay.cpp index 9dc63257..6a741452 100644 --- a/src/hacks/KillSay.cpp +++ b/src/hacks/KillSay.cpp @@ -21,7 +21,7 @@ struct KillsayStorage std::string message{}; }; -static std::unordered_map killsay_storage{}; +static boost::unordered_flat_map killsay_storage{}; // Thanks HellJustFroze for linking me http://daviseford.com/shittalk/ const std::vector builtin_default = { "Don't worry guys, I'm a garbage collector. I'm used to carrying trash.", "%name% is the human equivalent of a participation award.", "I would insult %name%, but nature did a better job.", "%name%, perhaps your strategy should include trying.", "Some people get paid to suck, you do it for free, %name%.", "You must really like that respawn timer, %name%.", "If your main is %class%, you should give up.", "Hey %name%, i see you can't play %class%. Try quitting the game.", "%name%@gmail.com to vacreview@valvesoftware.com\nFOUND CHEATER", "\n☐ Not rekt\n ā˜‘ Rekt\n ā˜‘ Really Rekt\n ā˜‘ Tyrannosaurus Rekt" }; diff --git a/src/hacks/Killstreak.cpp b/src/hacks/Killstreak.cpp index 53a73dda..f4f45b00 100644 --- a/src/hacks/Killstreak.cpp +++ b/src/hacks/Killstreak.cpp @@ -13,7 +13,7 @@ namespace hacks::tf2::killstreak { static settings::Boolean enable{ "killstreak.enable", "false" }; -static std::unordered_map ks_map; +static boost::unordered_flat_map ks_map; int killstreak{ 0 }; void reset() diff --git a/src/hacks/Misc.cpp b/src/hacks/Misc.cpp index 43e5c8d9..221cc567 100644 --- a/src/hacks/Misc.cpp +++ b/src/hacks/Misc.cpp @@ -783,10 +783,12 @@ static CatCommand debug_print_weaponid("debug_weaponid", "Print the weapon IDs o #if ENABLE_VISUALS && !ENFORCE_STREAM_SAFETY // This makes us able to see enemy class and status in scoreboard and player panel +/* static std::unique_ptr patch_playerpanel; static std::unique_ptr patch_scoreboard1; static std::unique_ptr patch_scoreboard2; static std::unique_ptr patch_scoreboard3; +*/ // Credits to UNKN0WN namespace ScoreboardColoring @@ -1005,10 +1007,12 @@ void Shutdown() #if ENABLE_VISUALS && !ENFORCE_STREAM_SAFETY // unpatching local player render_zoomed = false; + /* patch_playerpanel->Shutdown(); patch_scoreboard1->Shutdown(); patch_scoreboard2->Shutdown(); patch_scoreboard3->Shutdown(); + */ if (ScoreboardColoring::addr1 == 3 || ScoreboardColoring::addr2 == 2) return; @@ -1081,7 +1085,7 @@ static InitRoutine init( #if !ENFORCE_STREAM_SAFETY if (render_zoomed) tryPatchLocalPlayerShouldDraw(true); - render_zoomed.installChangeCallback([](settings::VariableBase &, bool after) { tryPatchLocalPlayerShouldDraw(after); }); + /*render_zoomed.installChangeCallback([](settings::VariableBase &, bool after) { tryPatchLocalPlayerShouldDraw(after); }); patch_playerpanel = std::make_unique(gSignatures.GetClientSignature, "0F 94 45 ? 85 C0 0F 8E", 0x0, std::vector{ 0xC6, 0x45, 0xDF, 0x01 }); uintptr_t addr_scrbrd = gSignatures.GetClientSignature("8B 10 89 74 24 04 89 04 24 FF 92 ? ? ? ? 83 F8 02 75 09"); @@ -1096,7 +1100,7 @@ static InitRoutine init( patch_scoreboard1->Patch(); patch_scoreboard2->Patch(); patch_scoreboard3->Patch(); - + */ static BytePatch stealth_kill{ gSignatures.GetClientSignature, "84 C0 75 28 A1", 2, { 0x90, 0x90 } }; // stealth kill patch stealth_kill.Patch(); static BytePatch cyoa_patch{ gSignatures.GetClientSignature, "75 ? 80 BB ? ? ? ? 00 74 ? A1 ? ? ? ? 8B 10 C7 44 24", 0, { 0xEB } }; diff --git a/src/hacks/MiscPlayerInfo.cpp b/src/hacks/MiscPlayerInfo.cpp index e6ed9dfd..d06e614d 100644 --- a/src/hacks/MiscPlayerInfo.cpp +++ b/src/hacks/MiscPlayerInfo.cpp @@ -22,8 +22,8 @@ struct LevelInfo static std::array mafia_levels{ LevelInfo(0, 9, "Crook"), LevelInfo(50, 50, "Crook"), LevelInfo(10, 10, "Bad Cop"), LevelInfo(0, 10, "Hoody"), LevelInfo(0, 5, "Gangster"), LevelInfo(1, 1, "Poor Man"), LevelInfo(10, 10, "Rich Man"), LevelInfo(10, 34, "Hitman"), LevelInfo(15, 99, "Boss"), LevelInfo(60, 100, "God Father") }; #if ENABLE_VISUALS -std::unordered_map> choosen_entry{}; -std::unordered_map previous_entry_amount{}; +boost::unordered_flat_map> choosen_entry{}; +boost::unordered_flat_map previous_entry_amount{}; std::string random_mafia_entry(int level, unsigned steamid) { std::vector store; diff --git a/src/hacks/NavBot.cpp b/src/hacks/NavBot.cpp index 3aade17e..2f0d3ee8 100644 --- a/src/hacks/NavBot.cpp +++ b/src/hacks/NavBot.cpp @@ -483,12 +483,12 @@ void updateEnemyBlacklist(int slot) return; // Store the danger of the invidual nav areas - std::unordered_map dormant_slight_danger; - std::unordered_map normal_slight_danger; + boost::unordered_flat_map dormant_slight_danger; + boost::unordered_flat_map normal_slight_danger; // This is used to cache Dangerous areas between ents - std::unordered_map> ent_marked_dormant_slight_danger; - std::unordered_map> ent_marked_normal_slight_danger; + boost::unordered_flat_map> ent_marked_dormant_slight_danger; + boost::unordered_flat_map> ent_marked_normal_slight_danger; std::vector> checked_origins; for (auto const &ent: entity_cache::player_cache) diff --git a/src/hacks/SkinChanger.cpp b/src/hacks/SkinChanger.cpp index ff80e252..fd15b451 100644 --- a/src/hacks/SkinChanger.cpp +++ b/src/hacks/SkinChanger.cpp @@ -561,8 +561,8 @@ def_attribute_modifier &GetModifier(int idx) } } // A map that maps an Item Definition Index to a modifier -std::unordered_map modifier_map{}; +boost::unordered_flat_map modifier_map{}; // A map that maps an Entity Index to a cookie -// std::unordered_map cookie_map {}; +// boost::unordered_flat_map cookie_map {}; patched_weapon_cookie cookie{ 0 }; } // namespace hacks::tf2::skinchanger diff --git a/src/hacks/SpellForcer.cpp b/src/hacks/SpellForcer.cpp index fd150b5e..e774c2c1 100644 --- a/src/hacks/SpellForcer.cpp +++ b/src/hacks/SpellForcer.cpp @@ -62,20 +62,20 @@ spelltypes getSpellMode() // Too much random noise on these maps to force spells // static std::array noisy_maps{ "" }; -static std::unordered_map spellmap_normal({ { 0, 4206970 }, { 1, 4206969 }, { 2, 4206972 }, { 3, 4206997 }, { 4, 4206971 }, { 5, 4206977 }, { 7, 4206973 }, { 8, 4206982 }, { 9, 4206976 } }); -static std::unordered_map spellmap_normal_rare({ { 7, 4206987 }, { 8, 4206982 }, { 9, 4207006 }, { 10, 4206983 }, { 11, 4206984 } }); +static boost::unordered_flat_map spellmap_normal({ { 0, 4206970 }, { 1, 4206969 }, { 2, 4206972 }, { 3, 4206997 }, { 4, 4206971 }, { 5, 4206977 }, { 7, 4206973 }, { 8, 4206982 }, { 9, 4206976 } }); +static boost::unordered_flat_map spellmap_normal_rare({ { 7, 4206987 }, { 8, 4206982 }, { 9, 4207006 }, { 10, 4206983 }, { 11, 4206984 } }); -static std::unordered_map spellmap_helltower({ { 0, 4206998 }, { 1, 4206984 }, { 2, 4206985 }, { 3, 4206986 }, { 4, 4206987 }, { 5, 4206982 }, { 6, 4206983 } }); +static boost::unordered_flat_map spellmap_helltower({ { 0, 4206998 }, { 1, 4206984 }, { 2, 4206985 }, { 3, 4206986 }, { 4, 4206987 }, { 5, 4206982 }, { 6, 4206983 } }); -static std::unordered_map spellmap_doomsday_normal({ { 0, 4206982 }, { 2, 4207006 }, { 4, 4206983 }, { 5, 4206984 } }); -static std::unordered_map spellmap_doomsday_rare({ { 7, 4207009 }, { 8, 4207014 }, { 9, 4207008 }, { 10, 4207007 } }); +static boost::unordered_flat_map spellmap_doomsday_normal({ { 0, 4206982 }, { 2, 4207006 }, { 4, 4206983 }, { 5, 4206984 } }); +static boost::unordered_flat_map spellmap_doomsday_rare({ { 7, 4207009 }, { 8, 4207014 }, { 9, 4207008 }, { 10, 4207007 } }); -static std::unordered_map spellmap_bumpercar({ { 12, 4206982 }, { 13, 4206983 }, { 14, 4206987 }, { 15, 4206988 } }); -// static std::unordered_map hasslecastle_normal({ { 0, 4206990 }, { 1, 4206989 }, { 2, 4206986 }, { 3, 4206997 }, { 4, 4206984 }, { 5, 4206983 }, { 7, 4207000 }, { 8, 4206982 }, { 9, 4207027 } }); +static boost::unordered_flat_map spellmap_bumpercar({ { 12, 4206982 }, { 13, 4206983 }, { 14, 4206987 }, { 15, 4206988 } }); +// static boost::unordered_flat_map hasslecastle_normal({ { 0, 4206990 }, { 1, 4206989 }, { 2, 4206986 }, { 3, 4206997 }, { 4, 4206984 }, { 5, 4206983 }, { 7, 4207000 }, { 8, 4206982 }, { 9, 4207027 } }); int getCommandForSpellID(int spellidx, int spelltype) { - std::unordered_map spellmap; + boost::unordered_flat_map spellmap; // if (levelname.find("koth_slasher") != levelname.npos || levelname.find("pl_bloodwater") != levelname.npos || levelname.find("pl_rumble_event") != levelname.npos) diff --git a/src/hacks/ac/aimbot.cpp b/src/hacks/ac/aimbot.cpp index 0e7b3812..8100e214 100644 --- a/src/hacks/ac/aimbot.cpp +++ b/src/hacks/ac/aimbot.cpp @@ -19,9 +19,9 @@ static settings::Int detections_warning{ "find-cheaters.aimbot.detections", "3" ac_data data_table[MAX_PLAYERS]; int amount[MAX_PLAYERS]; -std::unordered_map Player_origs{}; +boost::unordered_flat_map Player_origs{}; -std::unordered_map &player_orgs() +boost::unordered_flat_map &player_orgs() { return Player_origs; } diff --git a/src/helpers.cpp b/src/helpers.cpp index cbb23b8c..3246ba64 100644 --- a/src/helpers.cpp +++ b/src/helpers.cpp @@ -651,7 +651,7 @@ powerup_type GetPowerupOnPlayer(CachedEntity *player) return powerup_type::supernova; return powerup_type::not_powerup; } -bool didProjectileHit(Vector start_point, Vector end_point, CachedEntity *entity, float projectile_size) +bool didProjectileHit(Vector start_point, Vector end_point, CachedEntity *entity, float projectile_size, bool grav_comp) { trace::filter_default.SetSelf(RAW_ENT(g_pLocalPlayer->entity)); @@ -659,7 +659,7 @@ bool didProjectileHit(Vector start_point, Vector end_point, CachedEntity *entity trace_t trace_obj; ray.Init(start_point, end_point, Vector(0, -projectile_size, -projectile_size), Vector(0, projectile_size, projectile_size)); g_ITrace->TraceRay(ray, MASK_SHOT_HULL, &trace::filter_default, &trace_obj); - return (((IClientEntity *) trace_obj.m_pEnt) == RAW_ENT(entity) || !trace_obj.DidHit()); + return (((IClientEntity *) trace_obj.m_pEnt) == RAW_ENT(entity) || (grav_comp ? !trace_obj.DidHit(): false)); } // A function to find a weapon by WeaponID @@ -1024,7 +1024,7 @@ bool IsEntityVisible(CachedEntity *entity, int hb) return entity->hitboxes.VisibilityCheck(hb); } -bool IsEntityVectorVisible(CachedEntity *entity, Vector endpos, bool use_weapon_offset, unsigned int mask, trace_t *trace) +bool IsEntityVectorVisible(CachedEntity *entity, Vector endpos, bool use_weapon_offset, unsigned int mask, trace_t *trace, bool hit) { trace_t trace_object; @@ -1046,7 +1046,7 @@ bool IsEntityVectorVisible(CachedEntity *entity, Vector endpos, bool use_weapon_ g_ITrace->TraceRay(ray, mask, &trace::filter_default, trace); } - return (((IClientEntity *) trace->m_pEnt) == RAW_ENT(entity) || !trace->DidHit()); + return (((IClientEntity *) trace->m_pEnt) == RAW_ENT(entity) || (hit ? false: !trace->DidHit()) ); } // Get all the corners of a box. Taken from sauce engine. diff --git a/src/hooks/CreateMove.cpp b/src/hooks/CreateMove.cpp index 96ed7e01..84d4566a 100644 --- a/src/hooks/CreateMove.cpp +++ b/src/hooks/CreateMove.cpp @@ -243,14 +243,7 @@ DEFINE_HOOKED_METHOD(CreateMove, bool, void *this_, float input_sample_time, CUs time_replaced = false; curtime_old = g_GlobalVars->curtime; - - if (*fuckmode) - { - static int prevbuttons = 0; - current_user_cmd->buttons |= prevbuttons; - prevbuttons |= current_user_cmd->buttons; - } - + if (!g_Settings.bInvalid && CE_GOOD(g_pLocalPlayer->entity)) { servertime = (float) CE_INT(g_pLocalPlayer->entity, netvar.nTickBase) * g_GlobalVars->interval_per_tick; diff --git a/src/playerlist.cpp b/src/playerlist.cpp index 3008443a..ae656d2d 100644 --- a/src/playerlist.cpp +++ b/src/playerlist.cpp @@ -16,7 +16,7 @@ namespace playerlist { -std::unordered_map data{}; +boost::unordered_flat_map data{}; const std::string k_Names[] = { "DEFAULT", "FRIEND", "RAGE", "IPC", "TEXTMODE", "CAT", "PARTY" }; const char *const k_pszNames[] = { "DEFAULT", "FRIEND", "RAGE", "IPC", "TEXTMODE", "CAT", "PARTY" }; diff --git a/src/visual/menu/menu/special/SettingsManagerList.cpp b/src/visual/menu/menu/special/SettingsManagerList.cpp index 3d669b27..0774b8e2 100644 --- a/src/visual/menu/menu/special/SettingsManagerList.cpp +++ b/src/visual/menu/menu/special/SettingsManagerList.cpp @@ -110,7 +110,7 @@ void zerokernel::special::SettingsManagerList::addCollapsible(std::string name, list.addObject(std::move(entry)); } -static std::unordered_map marks{}; +static boost::unordered_flat_map marks{}; void zerokernel::special::SettingsManagerList::markVariable(std::string name) {