702 lines
		
	
	
		
			18 KiB
		
	
	
	
		
			SourcePawn
		
	
	
		
			Executable File
		
	
	
	
	
			
		
		
	
	
			702 lines
		
	
	
		
			18 KiB
		
	
	
	
		
			SourcePawn
		
	
	
		
			Executable File
		
	
	
	
	
#include <sourcemod>
 | 
						|
#include <sdktools>
 | 
						|
#include <zombiereloaded>
 | 
						|
#include <BotTargeting>
 | 
						|
#include <cstrike>
 | 
						|
 | 
						|
#pragma semicolon 1
 | 
						|
#pragma newdecls required
 | 
						|
 | 
						|
#define MAXNAMES 500
 | 
						|
ArrayList g_hNames;
 | 
						|
ArrayList g_hClanNames;
 | 
						|
 | 
						|
bool g_bFakePopulation[MAXPLAYERS + 1];
 | 
						|
bool g_bMapEnded;
 | 
						|
 | 
						|
int g_iBaseLatency[MAXPLAYERS + 1];
 | 
						|
int g_iLatency[MAXPLAYERS + 1];
 | 
						|
 | 
						|
int g_iAdminFakes;
 | 
						|
int g_iPopulation;
 | 
						|
 | 
						|
bool g_bCheckRequested;
 | 
						|
 | 
						|
bool g_bBlockInstantFakeConnects;
 | 
						|
 | 
						|
Database g_hDatabase;
 | 
						|
Database g_hDatabase_hlstats;
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public Plugin myinfo =
 | 
						|
{
 | 
						|
	name        = "ImprovedHitboxes", //camouflage
 | 
						|
	author      = "Neon + Dogan + Botox",
 | 
						|
	description = "Handle Hitboxes via Plugin",
 | 
						|
	version     = "5.3.1",
 | 
						|
	url         = "https://steamcommunity.com/id/n3ontm"
 | 
						|
};
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public void OnPluginStart()
 | 
						|
{
 | 
						|
	RegAdminCmd("sm_debugfakes", Command_DebugFakes, ADMFLAG_GENERIC, "Shows the amount of fake-clients on server");
 | 
						|
	RegAdminCmd("sm_fakes", Command_Fakes, ADMFLAG_GENERIC, "Shows the fake-clients on server");
 | 
						|
	RegAdminCmd("sm_setfakes", Command_SetFakes, ADMFLAG_RCON, "Manually sets the amount of fake-clients");
 | 
						|
 | 
						|
	int arraySize = ByteCountToCells(MAX_NAME_LENGTH);
 | 
						|
	g_hNames = CreateArray(arraySize);
 | 
						|
	g_hClanNames = CreateArray(arraySize);
 | 
						|
 | 
						|
	g_iAdminFakes = -1;
 | 
						|
	g_iPopulation = GetClientCount(false);
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if(IsClientConnected(i) && IsFakeClient(i))
 | 
						|
			g_iPopulation--;
 | 
						|
	}
 | 
						|
	g_bMapEnded = false;
 | 
						|
	g_bBlockInstantFakeConnects = false;
 | 
						|
	CreateTimer(40.0, BlockInstantFakeConnects, _, TIMER_REPEAT);
 | 
						|
	CreateTimer(3.0, RandomizePing, _, TIMER_REPEAT);
 | 
						|
	CreateTimer(150.0, RandomizeNames, _, TIMER_REPEAT);
 | 
						|
 | 
						|
	HookUserMessage(GetUserMessageId("SayText2"), UserMessage_SayText2, true);
 | 
						|
 | 
						|
	RequestFrame(CheckPopulation);
 | 
						|
 | 
						|
    if (!g_hDatabase)
 | 
						|
    {
 | 
						|
        Database.Connect(SQL_OnDatabaseConnect, "racetimercss");
 | 
						|
    }
 | 
						|
    if (!g_hDatabase_hlstats)
 | 
						|
    {
 | 
						|
        Database.Connect(SQL_OnDatabaseConnect_hlstats, "hlstatsx");
 | 
						|
    }
 | 
						|
}
 | 
						|
 | 
						|
public void SQL_OnDatabaseConnect_hlstats(Database db, const char[] error, any data)
 | 
						|
{
 | 
						|
    if(!db || strlen(error))
 | 
						|
    {
 | 
						|
        LogError("Database error: %s", error);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
    g_hDatabase_hlstats = db;
 | 
						|
    randomize_clantags();
 | 
						|
}
 | 
						|
 | 
						|
public void randomize_clantags()
 | 
						|
{
 | 
						|
    char sQuery[512];
 | 
						|
    Format(sQuery, sizeof(sQuery), "select DISTINCT tag from unloze_stats.hlstats_Clans ORDER BY RAND() limit 500");
 | 
						|
    g_hDatabase_hlstats.Query(SQL_OnQueryCompleted_hlstats, sQuery, DBPrio_High);
 | 
						|
}
 | 
						|
 | 
						|
public void SQL_OnDatabaseConnect(Database db, const char[] error, any data)
 | 
						|
{
 | 
						|
    if(!db || strlen(error))
 | 
						|
    {
 | 
						|
        LogError("Database error: %s", error);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
    g_hDatabase = db;
 | 
						|
    randomize_names();
 | 
						|
}
 | 
						|
 | 
						|
public void randomize_names()
 | 
						|
{
 | 
						|
    char sQuery[512];
 | 
						|
    Format(sQuery, sizeof(sQuery), "select name from unloze_racetimer_css.random_names ORDER BY RAND() limit 500");
 | 
						|
    g_hDatabase.Query(SQL_OnQueryCompleted, sQuery, DBPrio_High);
 | 
						|
}
 | 
						|
 | 
						|
public void SQL_OnQueryCompleted_hlstats(Database db, DBResultSet results, const char[] error, int iSerial)
 | 
						|
{
 | 
						|
    if (!db || strlen(error))
 | 
						|
    {
 | 
						|
        delete results;
 | 
						|
        LogError("Query error for hlstats: %s", error);
 | 
						|
        if (!g_hDatabase_hlstats)
 | 
						|
        {
 | 
						|
            Database.Connect(SQL_OnDatabaseConnect_hlstats, "hlstatsx");
 | 
						|
        }
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    while (results.RowCount && results.FetchRow())
 | 
						|
    {
 | 
						|
        char sName[MAX_NAME_LENGTH];
 | 
						|
        results.FetchString(0, sName, sizeof(sName));
 | 
						|
        g_hClanNames.PushString(sName);
 | 
						|
    }
 | 
						|
    delete results;
 | 
						|
}
 | 
						|
 | 
						|
public void SQL_OnQueryCompleted(Database db, DBResultSet results, const char[] error, int iSerial)
 | 
						|
{
 | 
						|
    if (!db || strlen(error))
 | 
						|
    {
 | 
						|
        delete results;
 | 
						|
        LogError("Query error for racetimer: %s", error);
 | 
						|
        if (!g_hDatabase)
 | 
						|
        {
 | 
						|
            Database.Connect(SQL_OnDatabaseConnect, "racetimercss");
 | 
						|
        }
 | 
						|
        return;
 | 
						|
    }
 | 
						|
 | 
						|
    while (results.RowCount && results.FetchRow())
 | 
						|
    {
 | 
						|
        char sName[MAX_NAME_LENGTH];
 | 
						|
        results.FetchString(0, sName, sizeof(sName));
 | 
						|
        g_hNames.PushString(sName);
 | 
						|
    }
 | 
						|
    delete results;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public void OnPluginEnd()
 | 
						|
{
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if(g_bFakePopulation[i])
 | 
						|
		{
 | 
						|
			g_bFakePopulation[i] = false;
 | 
						|
			g_iLatency[i] = 0;
 | 
						|
			KickClient(i, "Disconnect by user.");
 | 
						|
		}
 | 
						|
	}
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public void OnMapStart()
 | 
						|
{
 | 
						|
    g_hNames.Clear();
 | 
						|
    g_hClanNames.Clear();
 | 
						|
    if (!g_hDatabase)
 | 
						|
    {
 | 
						|
        Database.Connect(SQL_OnDatabaseConnect, "racetimercss");
 | 
						|
    }
 | 
						|
    else
 | 
						|
    {
 | 
						|
        randomize_names();
 | 
						|
    }
 | 
						|
 | 
						|
    if (!g_hDatabase_hlstats)
 | 
						|
    {
 | 
						|
        Database.Connect(SQL_OnDatabaseConnect_hlstats, "hlstatsx");
 | 
						|
    }
 | 
						|
    else
 | 
						|
    {
 | 
						|
        randomize_clantags();
 | 
						|
    }
 | 
						|
 | 
						|
 | 
						|
    /*
 | 
						|
	char sFile[PLATFORM_MAX_PATH];
 | 
						|
	char sLine[MAX_NAME_LENGTH];
 | 
						|
	BuildPath(Path_SM, sFile, sizeof(sFile), "configs/fakeclients_names.txt");
 | 
						|
	Handle hFile = OpenFile(sFile, "r");
 | 
						|
 | 
						|
	if(hFile != INVALID_HANDLE)
 | 
						|
	{
 | 
						|
		int iLine = 0;
 | 
						|
		g_hNames.Clear();
 | 
						|
		while (!IsEndOfFile(hFile))
 | 
						|
		{
 | 
						|
			if (!ReadFileLine(hFile, sLine, sizeof(sLine)) || iLine >= MAXNAMES)
 | 
						|
				break;
 | 
						|
 | 
						|
			TrimString(sLine);
 | 
						|
			g_hNames.PushString(sLine);
 | 
						|
			iLine++;
 | 
						|
		}
 | 
						|
		delete hFile;
 | 
						|
	}
 | 
						|
	else
 | 
						|
		SetFailState("Could not open file: configs/fakeclients_names.txt");
 | 
						|
    */
 | 
						|
 | 
						|
	g_bMapEnded = false;
 | 
						|
 | 
						|
	g_bBlockInstantFakeConnects = false;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public void OnMapEnd()
 | 
						|
{
 | 
						|
	g_bMapEnded = true;
 | 
						|
	g_iAdminFakes = -1;
 | 
						|
	g_iPopulation = GetClientCount(false);
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if(IsClientConnected(i) && IsFakeClient(i))
 | 
						|
			g_iPopulation--;
 | 
						|
	}
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public Action BlockInstantFakeConnects(Handle timer)
 | 
						|
{
 | 
						|
	g_bBlockInstantFakeConnects = false;
 | 
						|
	RequestFrame(CheckPopulation);
 | 
						|
 | 
						|
	return Plugin_Continue;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public Action RandomizePing(Handle timer)
 | 
						|
{
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if(g_bFakePopulation[i])
 | 
						|
			g_iLatency[i] = g_iBaseLatency[i] + GetRandomInt(-3, 3);
 | 
						|
	}
 | 
						|
	return Plugin_Continue;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public Action RandomizeNames(Handle timer)
 | 
						|
{
 | 
						|
    if (g_hNames.Length == 0 || g_hClanNames.Length == 0)
 | 
						|
    {
 | 
						|
        return Plugin_Handled;
 | 
						|
    }
 | 
						|
 | 
						|
    ArrayList hNames = g_hNames.Clone();
 | 
						|
    ArrayList hClanNames = g_hClanNames.Clone();
 | 
						|
    for(int i = 1; i <= MaxClients; i++)
 | 
						|
    {
 | 
						|
        if(g_bFakePopulation[i])
 | 
						|
        {
 | 
						|
            int iRand = GetRandomInt(0, hNames.Length - 1);
 | 
						|
            char sName[MAX_NAME_LENGTH];
 | 
						|
            hNames.GetString(iRand, sName, sizeof(sName));
 | 
						|
            hNames.Erase(iRand);
 | 
						|
            SetClientName(i, sName);
 | 
						|
 | 
						|
            if (GetRandomInt(0, 5) >= 3)
 | 
						|
            {
 | 
						|
                int iRandClans = GetRandomInt(0, hClanNames.Length - 1);
 | 
						|
                hClanNames.GetString(iRandClans, sName, sizeof(sName));
 | 
						|
                hClanNames.Erase(iRandClans);
 | 
						|
                CS_SetClientClanTag(i, sName);
 | 
						|
            }
 | 
						|
            else
 | 
						|
            {
 | 
						|
                CS_SetClientClanTag(i, "");
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
    delete hNames;
 | 
						|
    delete hClanNames;
 | 
						|
    return Plugin_Continue;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public Action UserMessage_SayText2(UserMsg msg_id, BfRead msg, const int[] players, int playersNum, bool reliable, bool init)
 | 
						|
{
 | 
						|
	if(!reliable)
 | 
						|
		return Plugin_Continue;
 | 
						|
 | 
						|
	int client;
 | 
						|
	char sMessage[32];
 | 
						|
 | 
						|
	if(GetUserMessageType() == UM_Protobuf) //fuck cs go but "ClEaN CoDe"
 | 
						|
	{
 | 
						|
		PbReadString(msg, "msg_name", sMessage, sizeof(sMessage));
 | 
						|
 | 
						|
		if(!(sMessage[0] == '#' && StrContains(sMessage, "Name_Change")))
 | 
						|
			return Plugin_Continue;
 | 
						|
 | 
						|
		client = PbReadInt(msg, "ent_idx");
 | 
						|
	}
 | 
						|
	else
 | 
						|
	{
 | 
						|
		client = BfReadByte(msg);
 | 
						|
		BfReadByte(msg);
 | 
						|
		BfReadString(msg, sMessage, sizeof(sMessage));
 | 
						|
 | 
						|
		if(!(sMessage[0] == '#' && StrContains(sMessage, "Name_Change")))
 | 
						|
			return Plugin_Continue;
 | 
						|
	}
 | 
						|
 | 
						|
	if(g_bFakePopulation[client])
 | 
						|
		return Plugin_Handled;
 | 
						|
 | 
						|
	return Plugin_Continue;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public Action Command_DebugFakes(int client, int argc)
 | 
						|
{
 | 
						|
	int iFakes = 0;
 | 
						|
	int iFakesInTeam = 0;
 | 
						|
	int iPlayers = GetClientCount(false);
 | 
						|
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if (g_bFakePopulation[i])
 | 
						|
			iFakes++;
 | 
						|
 | 
						|
		if (g_bFakePopulation[i] && GetClientTeam(i) > 0)
 | 
						|
			iFakesInTeam++;
 | 
						|
 | 
						|
		if(IsClientConnected(i) && IsFakeClient(i))
 | 
						|
			iPlayers--;
 | 
						|
	}
 | 
						|
 | 
						|
	ReplyToCommand(client, "[SM] There are currently %d Fake-Clients, from which %d are in Spectate.", iFakes, iFakes - iFakesInTeam);
 | 
						|
	ReplyToCommand(client, "[SM] Server Population at the end of the previous Map: %d.", g_iPopulation);
 | 
						|
	ReplyToCommand(client, "[SM] Current Server Population: %d. Difference: %d.", iPlayers, iPlayers - g_iPopulation);
 | 
						|
 | 
						|
	return Plugin_Handled;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public Action Command_SetFakes(int client, int argc)
 | 
						|
{
 | 
						|
	if (argc < 1)
 | 
						|
	{
 | 
						|
		ReplyToCommand(client, "[SM] Usage: sm_setfakes <amount of fakes>");
 | 
						|
		return Plugin_Handled;
 | 
						|
	}
 | 
						|
 | 
						|
	char sArgs[16];
 | 
						|
	GetCmdArg(1, sArgs, sizeof(sArgs));
 | 
						|
 | 
						|
	if (!StringToIntEx(sArgs, g_iAdminFakes))
 | 
						|
	{
 | 
						|
		ReplyToCommand(client, "[SM] Invalid value");
 | 
						|
		return Plugin_Handled;
 | 
						|
	}
 | 
						|
 | 
						|
	ReplyToCommand(client, "[SM] You set the amount of Fake-Clients to %d.", g_iAdminFakes);
 | 
						|
	CheckPopulation();
 | 
						|
	return Plugin_Handled;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public Action Command_Fakes(int client, int args)
 | 
						|
{
 | 
						|
	char aBuf[1024];
 | 
						|
	char aBuf2[MAX_NAME_LENGTH];
 | 
						|
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if(IsClientInGame(i))
 | 
						|
		{
 | 
						|
			if(g_bFakePopulation[i])
 | 
						|
			{
 | 
						|
				GetClientName(i, aBuf2, sizeof(aBuf2));
 | 
						|
				StrCat(aBuf, sizeof(aBuf), aBuf2);
 | 
						|
				StrCat(aBuf, sizeof(aBuf), ", ");
 | 
						|
			}
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
	if(strlen(aBuf))
 | 
						|
	{
 | 
						|
		aBuf[strlen(aBuf) - 2] = 0;
 | 
						|
		ReplyToCommand(client, "[SM] Fake-Clients online: %s", aBuf);
 | 
						|
	}
 | 
						|
	else
 | 
						|
		ReplyToCommand(client, "[SM] Fake-Clients online: none");
 | 
						|
 | 
						|
	return Plugin_Handled;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public void OnClientConnected(int client)
 | 
						|
{
 | 
						|
	if (!g_bCheckRequested && !IsFakeClient(client))
 | 
						|
	{
 | 
						|
		RequestFrame(CheckPopulation);
 | 
						|
		g_bCheckRequested = true;
 | 
						|
	}
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public void OnClientDisconnect(int client)
 | 
						|
{
 | 
						|
	if (client > 0)
 | 
						|
	{
 | 
						|
		if(g_bFakePopulation[client])
 | 
						|
		{
 | 
						|
			g_bFakePopulation[client] = false;
 | 
						|
			g_iLatency[client] = 0;
 | 
						|
		}
 | 
						|
 | 
						|
		if (!g_bCheckRequested && !IsFakeClient(client))
 | 
						|
		{
 | 
						|
			RequestFrame(CheckPopulation);
 | 
						|
			g_bCheckRequested = true;
 | 
						|
		}
 | 
						|
	}
 | 
						|
}
 | 
						|
 | 
						|
public Action repeatCheckPopulation(Handle timer)
 | 
						|
{
 | 
						|
    CheckPopulation();
 | 
						|
	return Plugin_Continue;
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public void CheckPopulation()
 | 
						|
{
 | 
						|
    if (g_hNames.Length == 0 || g_hClanNames.Length == 0)
 | 
						|
    {
 | 
						|
        CreateTimer(5.0, repeatCheckPopulation);
 | 
						|
        return;
 | 
						|
    }
 | 
						|
	g_bCheckRequested = false;
 | 
						|
 | 
						|
	if(g_bMapEnded)
 | 
						|
		return;
 | 
						|
 | 
						|
	int iPlayers = GetClientCount(false);
 | 
						|
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if(IsClientConnected(i) && IsFakeClient(i))
 | 
						|
			iPlayers--;
 | 
						|
	}
 | 
						|
 | 
						|
	int iFakes = 0;
 | 
						|
	int iFakesInTeam = 0;
 | 
						|
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if (g_bFakePopulation[i])
 | 
						|
			iFakes++;
 | 
						|
	}
 | 
						|
 | 
						|
	int iFakesNeeded = 0;
 | 
						|
	int iFakesInTeamNeeded = 0;
 | 
						|
 | 
						|
    int max = 2;
 | 
						|
    int min = 1;
 | 
						|
    
 | 
						|
    if (iPlayers == 1)
 | 
						|
    {
 | 
						|
        max = iPlayers * 5;
 | 
						|
        min = 3;
 | 
						|
    }
 | 
						|
    else if (iPlayers < 6)
 | 
						|
    {
 | 
						|
        max = iPlayers * 5;
 | 
						|
        min = iPlayers * 2;
 | 
						|
    }
 | 
						|
    else if (iPlayers < 11)
 | 
						|
    {
 | 
						|
        max = RoundToFloor(iPlayers * 1.5);
 | 
						|
        min = iPlayers;
 | 
						|
    }
 | 
						|
    else if (iPlayers < 20)
 | 
						|
    {
 | 
						|
        max = iPlayers;
 | 
						|
        min = RoundToFloor(iPlayers * 0.5);
 | 
						|
    }
 | 
						|
    else if (iPlayers < 26)
 | 
						|
    {
 | 
						|
        max = iPlayers;
 | 
						|
        min = RoundToFloor(iPlayers * 0.3);
 | 
						|
    }
 | 
						|
    else if (iPlayers < 36)
 | 
						|
    {
 | 
						|
        max = RoundToFloor(iPlayers * 0.5);
 | 
						|
        min = RoundToFloor(iPlayers * 0.3);
 | 
						|
    }
 | 
						|
    else
 | 
						|
    {
 | 
						|
        max = RoundToFloor(iPlayers * 0.3);
 | 
						|
        min = RoundToFloor(iPlayers * 0.1);
 | 
						|
    }
 | 
						|
 | 
						|
    iFakesNeeded = GetRandomInt(min, max);
 | 
						|
	//iFakesNeeded = randomAmount - iPlayers;
 | 
						|
	if (iFakesNeeded < 0 || iPlayers > 50)
 | 
						|
	{
 | 
						|
		iFakesNeeded = 0;
 | 
						|
		iFakesInTeamNeeded = 0;
 | 
						|
	}
 | 
						|
	else
 | 
						|
	{
 | 
						|
		iFakesInTeamNeeded = iFakesNeeded / 3;
 | 
						|
	}
 | 
						|
    if (iFakesInTeamNeeded < 0)
 | 
						|
    {
 | 
						|
        iFakesInTeamNeeded = 0;
 | 
						|
    }
 | 
						|
 | 
						|
	if(g_iAdminFakes != -1)
 | 
						|
		iFakesNeeded = g_iAdminFakes;
 | 
						|
 | 
						|
	if (iFakes != iFakesNeeded)
 | 
						|
	{
 | 
						|
		while (iFakes < iFakesNeeded && !g_bBlockInstantFakeConnects)
 | 
						|
		{
 | 
						|
			ArrayList hNames = g_hNames.Clone();
 | 
						|
			char sName[MAX_NAME_LENGTH];
 | 
						|
			for(int i = 1; i <= MaxClients; i++)
 | 
						|
			{
 | 
						|
				if(g_bFakePopulation[i])
 | 
						|
				{
 | 
						|
					GetClientName(i, sName, sizeof(sName));
 | 
						|
					int iPos = hNames.FindString(sName);
 | 
						|
					if (iPos > -1)
 | 
						|
						hNames.Erase(iPos);
 | 
						|
				}
 | 
						|
			}
 | 
						|
 | 
						|
			int iRand = GetRandomInt(0, hNames.Length - 1);
 | 
						|
			hNames.GetString(iRand, sName, sizeof(sName));
 | 
						|
			delete hNames;
 | 
						|
 | 
						|
			int iIndex = CreateFakeClient(sName);
 | 
						|
 | 
						|
			if(iIndex < 1 || iIndex > MaxClients)
 | 
						|
				return;
 | 
						|
 | 
						|
			SetEntityFlags(iIndex, FL_CLIENT);
 | 
						|
			DispatchKeyValue(iIndex, "classname", "player");
 | 
						|
			DispatchSpawn(iIndex);
 | 
						|
 | 
						|
			g_bFakePopulation[iIndex] = true;
 | 
						|
			g_iBaseLatency[iIndex] = GetRandomInt(20, 110);
 | 
						|
			g_iLatency[iIndex] = g_iBaseLatency[iIndex];
 | 
						|
 | 
						|
			AdminId FakeAdmin = CreateAdmin();
 | 
						|
			SetAdminFlag(FakeAdmin, Admin_Custom6, true);
 | 
						|
			SetUserAdmin(iIndex, FakeAdmin, true);
 | 
						|
 | 
						|
            if (GetRandomInt(0, 5) >= 3)
 | 
						|
            {
 | 
						|
                ArrayList hClanNames = g_hClanNames.Clone();
 | 
						|
                iRand = GetRandomInt(0, hClanNames.Length - 1);
 | 
						|
                hClanNames.GetString(iRand, sName, sizeof(sName));
 | 
						|
                delete hClanNames;
 | 
						|
                CS_SetClientClanTag(iIndex, sName);
 | 
						|
            }
 | 
						|
            else
 | 
						|
            {
 | 
						|
                CS_SetClientClanTag(iIndex, "");
 | 
						|
            }
 | 
						|
			iFakes++;
 | 
						|
 | 
						|
			g_bBlockInstantFakeConnects = true;
 | 
						|
		}
 | 
						|
 | 
						|
		while (iFakes > iFakesNeeded)
 | 
						|
		{
 | 
						|
			for(int i = 1; i <= MaxClients; i++)
 | 
						|
			{
 | 
						|
				if(g_bFakePopulation[i])
 | 
						|
				{
 | 
						|
					g_bFakePopulation[i] = false;
 | 
						|
					g_iLatency[i] = 0;
 | 
						|
					KickClient(i, "Disconnect by user.");
 | 
						|
					iFakes--;
 | 
						|
					break;
 | 
						|
				}
 | 
						|
			}
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if (g_bFakePopulation[i] && GetClientTeam(i) >= CS_TEAM_T)
 | 
						|
			iFakesInTeam++;
 | 
						|
	}
 | 
						|
 | 
						|
	if (iFakes == iFakesNeeded && iFakesInTeam != iFakesInTeamNeeded && g_iAdminFakes == -1)
 | 
						|
	{
 | 
						|
		while (iFakesInTeam < iFakesInTeamNeeded)
 | 
						|
		{
 | 
						|
			for(int i = 1; i <= MaxClients; i++)
 | 
						|
			{
 | 
						|
				if(g_bFakePopulation[i] && GetClientTeam(i) <= CS_TEAM_SPECTATOR)
 | 
						|
				{
 | 
						|
					ChangeClientTeam(i, CS_TEAM_CT);
 | 
						|
					FakeClientCommandEx(i, "joinclass");
 | 
						|
					iFakesInTeam++;
 | 
						|
					break;
 | 
						|
				}
 | 
						|
			}
 | 
						|
		}
 | 
						|
 | 
						|
		while (iFakesInTeam > iFakesInTeamNeeded)
 | 
						|
		{
 | 
						|
			for(int i = 1; i <= MaxClients; i++)
 | 
						|
			{
 | 
						|
				if(g_bFakePopulation[i] && GetClientTeam(i) >= CS_TEAM_T)
 | 
						|
				{
 | 
						|
					ChangeClientTeam(i, CS_TEAM_SPECTATOR);
 | 
						|
					iFakesInTeam--;
 | 
						|
					break;
 | 
						|
				}
 | 
						|
			}
 | 
						|
		}
 | 
						|
	}
 | 
						|
}
 | 
						|
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
// Purpose:
 | 
						|
//----------------------------------------------------------------------------------------------------
 | 
						|
public void OnGameFrame()
 | 
						|
{
 | 
						|
	for(int i = 1; i <= MaxClients; i++)
 | 
						|
	{
 | 
						|
		if(g_bFakePopulation[i])
 | 
						|
		{
 | 
						|
			int iResEnt = GetPlayerResourceEntity();
 | 
						|
 | 
						|
			if(iResEnt == -1)
 | 
						|
				return;
 | 
						|
 | 
						|
			SetEntProp(iResEnt, Prop_Send, "m_iPing", g_iLatency[i], _, i);
 | 
						|
		}
 | 
						|
	}
 | 
						|
}
 | 
						|
 | 
						|
/*
 | 
						|
public Action ZR_OnClientMotherZombieEligible(int client)
 | 
						|
{
 | 
						|
	if (g_bFakePopulation[client])
 | 
						|
		return Plugin_Handled;
 | 
						|
 | 
						|
	return Plugin_Continue;
 | 
						|
}
 | 
						|
*/
 |