#include #include #include #include #include #define PLUGIN "Walk through walls" #define VERSION "1.1" #define AUTHOR "Xalus" new Float:g_flDelay[33]; new g_cvarDistance, g_cvarFalldistance, g_cvarButton, g_cvarDelay, g_cvarMessages; public plugin_init() { register_plugin(PLUGIN, VERSION, AUTHOR); // Register: Cvar g_cvarDistance = register_cvar("wtw_distance", "60"); // Maximum wall width wich player can go through. g_cvarFalldistance = register_cvar("wtw_fall_distance", "150"); // Maximum Fall distance behind the wall. (So you don't end up dead). g_cvarButton = register_cvar("wtw_button", "0"); // Button (USE) needed to go through walls (1) or automatically (0) g_cvarDelay = register_cvar("wtw_delay", "0.7"); // Delay after going through a wall, to go through the next one. g_cvarMessages = register_cvar("wtw_message", "0"); // Show a message to player if walking trough wall failed. // Register: Touch register_touch("worldspawn","player","Touch_Wall"); register_touch("func_brush","player","Touch_Wall"); register_touch("func_breakable","player","Touch_Wall"); } public Touch_Wall(entity, id) { if(is_user_alive(id)) { if(g_flDelay[id] < get_gametime()) { new intCvarButton; intCvarButton = get_pcvar_num(g_cvarButton); if(!intCvarButton || (intCvarButton && pev(id, pev_button) & IN_USE)) { set_player_behindwall(id); } } } } set_player_behindwall(id) { new Float:flOrigin[4][3], Float:flAngle[3] pev(id, pev_origin, flOrigin[0]) pev(id, pev_v_angle, flAngle) flAngle[0] = -10.0 origin_infront(flAngle, flOrigin[0], (get_pcvar_float(g_cvarDistance) + 40.0), flOrigin[1]); new iTraceHandle = create_tr2(); engfunc(EngFunc_TraceLine, flOrigin[0], flOrigin[1], DONT_IGNORE_MONSTERS, id, iTraceHandle); get_tr2(iTraceHandle, TR_vecEndPos, flOrigin[2]); if(get_distance_f(flOrigin[0], flOrigin[2]) > 17.0) { free_tr2(iTraceHandle); return 0; } g_flDelay[id] = (get_gametime() + get_pcvar_float(g_cvarDelay)); engfunc(EngFunc_TraceLine, flOrigin[1], flOrigin[0], DONT_IGNORE_MONSTERS, id, iTraceHandle); get_tr2(iTraceHandle, TR_vecEndPos, flOrigin[3]); origin_infront(flAngle, flOrigin[3], 16.55, flOrigin[3]); if(is_hull_vacant(flOrigin[3], pev(id, pev_flags) & FL_DUCKING ? HULL_HEAD : HULL_HUMAN)) { xs_vec_copy(flOrigin[3], flOrigin[1]); flOrigin[1][2] -= 1000.0; engfunc(EngFunc_TraceLine, flOrigin[3], flOrigin[1], IGNORE_MONSTERS, id, iTraceHandle); get_tr2(iTraceHandle, TR_vecEndPos, flOrigin[1]); if(get_distance_f(flOrigin[3], flOrigin[1]) > get_pcvar_float(g_cvarFalldistance)) { if(get_pcvar_num(g_cvarMessages)) { client_print(id, print_center, "Walking through wall failed, no solid ground behind wall."); } free_tr2(iTraceHandle); return 0; } engfunc(EngFunc_SetOrigin, id, flOrigin[3]); } else if(get_pcvar_num(g_cvarMessages)) { client_print(id, print_center, "Walking through wall failed, wall too big."); } free_tr2(iTraceHandle); return 1; } origin_infront( Float:vAngles[3], Float:vecOrigin[ 3 ], Float:flDistance, Float:vecOutput[ 3 ] ) // By Exolent { new Float:vecAngles[3]; xs_vec_copy(vAngles, vecAngles); engfunc(EngFunc_MakeVectors, vecAngles); global_get(glb_v_forward, vecAngles); xs_vec_mul_scalar(vecAngles, flDistance, vecAngles); xs_vec_add(vecOrigin, vecAngles, vecOutput); } bool:is_hull_vacant(const Float:origin[3], hull) { new tr; engfunc(EngFunc_TraceHull, origin, origin, IGNORE_MONSTERS, hull, 0, tr); return bool:(!get_tr2(tr, TR_StartSolid) && !get_tr2(tr, TR_AllSolid) && get_tr2(tr, TR_InOpen)) }