12.05.2011, 12:17
What is so bad on it? It looks awesome! Take a look at the code
pawn Код:
////////////////////////////////////////////////////////////////////////////////
// Super Anti Cheat by Steve* "Steven Kelly" 2011.
// Please leave the credits.
////////////////////////////////////////////////////////////////////////////////
#if defined SAC_INCLUDED
#endinput
#else
#define SAC_INCLUDED
#endif
////////////////////////////////////////////////////////////////////////////////
#include <a_samp>
#include <dini>
////////////////////////////////////////////////////////////////////////////////
#define MAX_SAC_CHECKS 3 // If it detects a cheat the first time, it won't ban or kick, it will just ban or kick when it has detected it with the number you defined.
#define SAC_SendClientMessage(%0,%1,%2)\
format(SAC_MSG_STRING, sizeof(SAC_MSG_STRING), "{FB0000}(SAC){FFFFFF} %s", %2);\
SendClientMessage(%0,%1,SAC_MSG_STRING)
#define SAC_SendClientMessagef(%0,%1,%2,%3)\
format(SAC_MSG_STRING, sizeof(SAC_MSG_STRING), %2, %3);\
format(SAC_MSG_STRING, sizeof(SAC_MSG_STRING), "{FB0000}(SAC){FFFFFF} %s", SAC_MSG_STRING);\
SendClientMessage(%0,%1,SAC_MSG_STRING)
#define SAC_SendClientMessageToAll(%0,%1)\
format(SAC_MSG_STRING, sizeof(SAC_MSG_STRING), "{FB0000}(SAC){FFFFFF} %s", %1);\
SendClientMessageToAll(%0, SAC_MSG_STRING)
#define SAC_SendClientMessageToAllf(%0,%1,%2)\
format(SAC_MSG_STRING, sizeof(SAC_MSG_STRING), %1, %2);\
format(SAC_MSG_STRING, sizeof(SAC_MSG_STRING), "{FB0000}(SAC){FFFFFF} %s", SAC_MSG_STRING);\
SendClientMessageToAll(%0, SAC_MSG_STRING)
#define SAC_Kickf(%0,%1,%2) do{ new SAC_KICK_STRING[200]; format(SAC_KICK_STRING, sizeof(SAC_KICK_STRING), %1,%2); SAC_Kick(%0,SAC_KICK_STRING); } while(SAC_FALSE)
#define SAC_Banf(%0,%1,%2) do{ new SAC_BAN_STRING[200]; format(SAC_BAN_STRING, sizeof(SAC_BAN_STRING), %1,%2); SAC_Ban(%0,SAC_BAN_STRING); } while(SAC_FALSE)
#define SAC_Logf(%0,%1) do{ new SAC_LOG_STRING[200]; format(SAC_LOG_STRING, sizeof(SAC_LOG_STRING),%0,%1); SAC_Log(SAC_LOG_STRING); } while(SAC_FALSE)
#define MAX_SAC_PLAYERS 100
#pragma tabsize 0
//#define USE_FOREACH
#if !defined USE_FOREACH
#define SAC_foreach(%0) for(new idx_%0 = 0, %0 = foreach_ConnectedPlayerList[0]; idx_%0 < foreach_ConnectedPlayers; ++idx_%0, %0 = foreach_ConnectedPlayerList[idx_%0])
#endif
#define TIMER_MILISECONDS 5000
////////////////////////////////////////////////////////////////////////////////
enum SAC_PLAYER_INFOS
{
JETPACK_HACK,
WEAPON_HACK,
FULLY_CONNECTED,
SPAWNED,
FROZEN
};
enum SAC_SERVER_INFOS
{
FORBIDDEN_NAMES
}
enum SAC_CHEATZ
{
JETPACK,
WEAPONS,
BAN,
SINGLE_PLAYER_CHEATS,
UNFREEZE
};
////////////////////////////////////////////////////////////////////////////////
new SAC_MSG_STRING[200];
new SAC_PLAYER_INFO[MAX_SAC_PLAYERS][SAC_PLAYER_INFOS];
new SAC_SERVER_INFO[SAC_SERVER_INFOS];
new SAC_CONFIGURATION_FILE[] = "/SAC/Config.ini";
new SAC_LOG_FILE[] = "/SAC/SAC_log.log";
new SAC_CHEATS[SAC_CHEATZ];
new SAC_FALSE = false;
new SAC_Players[MAX_SAC_PLAYERS][MAX_PLAYER_NAME+1];
new foreach_ConnectedPlayers;
new foreach_ConnectedPlayerList[MAX_PLAYERS+1];
new SAC_TIMER;
new SAC_aWeaponNames[][32] =
{
{"Unarmed (Fist)"}, {"Brass Knuckles"}, {"Golf Club"}, {"Night Stick"}, {"Knife"}, {"Baseball Bat"},
{"Shovel"}, {"Pool Cue"}, {"Katana"}, {"Chainsaw"}, {"Purple Dildo"}, {"Big White Vibrator"},
{"Medium White Vibrator"}, {"Small White Vibrator"}, {"Flowers"}, {"Cane"}, {"Grenade"}, {"Teargas"},
{"Molotov"}, {"Empty Slot 1"}, {"Empty Slot 2"}, {"Empty Slot 3"}, {"Colt 45"}, {"Colt 45 (Silenced)"},
{"Desert Eagle"}, {"Normal Shotgun"}, {"Sawnoff Shotgun"}, {"Combat Shotgun"}, {"Micro Uzi (Mac 10)"},
{"MP5"}, {"AK47"}, {"M4"}, {"Tec9"}, {"Country Rifle"}, {"Sniper Rifle"}, {"Rocket Launcher"},
{"Heat-Seeking Rocket Launcher"}, {"Flamethrower"}, {"Minigun"}, {"Satchel Charge"}, {"Detonator"},
{"Spray Can"}, {"Fire Extinguisher"}, {"Camera"}, {"Night Vision Goggles"}, {"Infrared Vision Goggles"},
{"Parachute"}, {"Fake Pistol"}
};
new SinglePlayerCheats[][] =
{
// Weapons, Health and Armour
"BAGUVIX",
"HESOYAM",
"WANRLTW",
"NCSGDAG",
"OUIQDMW",
"LXGIWYL",
"KJKSZPJ",
"UZUMYMW",
"ROCKETMAN",
"AIYPWZQP",
// Cops, Statuses and Gangs
"OSRBLHH",
"ASNAEB",
"LJSPQK",
"AEZAKMI",
"MUNASEF",
"KANGAROO",
"IAVENJQ",
"AEDUWNV",
"CVWKXAM",
"BTCDBCB",
"KVGYZQK",
"JYSDSOD",
"OGXSDAG",
"EHIBXQS",
"MROEMZH",
"BIFBUZZ",
// Create cars
"AIWPRTON",
"CQZIJMB",
"JQNTDMH",
"PDNEJOH",
"VPJTQWV",
"AQTBCODX",
"KRIJEBR",
"UBHYZHQ",
"RZHSUEW",
"JUMPJET",
"KGGGDKP",
"OHDUDE",
"AKJJYGLC",
"AMOMHRER",
"EEGCYXT",
"URKQSRK",
"AGBDLCID",
// Car-Cheats
"CPKTNWT",
"XICWMD",
"PGGOMOY",
"ZEIIVG",
"YLTEICZ",
"LLQPFBN",
"IOWDLAC",
"AFSNMSMW",
"BGKGTJH",
"GUSNHDE",
"RIPAZHA",
"JHJOECW",
"JCNRUAD",
"COXEFGU",
"BSXSGGC",
"THGLOJ",
"FVTMNBZ",
"VKYPQCF",
"VQIMAHA",
// Gameplay-Cheats
"AJLOJYQY",
"BAGOWPG",
"FOOOXFT",
"SZCMAWO",
"BLUESUEDESHOES",
"BGLUAWML",
"CIKGCGX",
"AFPHULTL",
"BEKKNQV",
"IOJUFZN",
"PRIEBJ",
"SJMAHPE",
"BMTPWHR",
"ZSOXFSQ",
// Weather and Time cheats
"AFZLLQLL",
"ICIKPYH",
"ALNSFMZO",
"AUIFRVQS",
"CFVFGMJ",
"MGHXYRM",
"CWJXUOC",
"YSOHNUL",
"PPGWJHT",
"LIYOAAY",
"XJVSNAJ",
"OFVIAC",
"BOOOOORING",
"Onspeed",
"ASPIRINE",
"LEAVEMEALONE",
"NUTTERTOOLS",
"PROFESSIONALTOOLS",
"Thugstool",
"YOUWONTTAKEMEALIVE",
"ICANTTAKEITANYMORE"
};
new SAC_FORBIDDEN_NAMES[][MAX_PLAYER_NAME] =
{
"unnamed"
};
////////////////////////////////////////////////////////////////////////////////
forward SAC_OnPlayerConnect(playerid);
forward SAC_OnPlayerDisconnect(playerid, reason);
forward SAC_OnGameModeInit();
forward SAC_OnFilterScriptInit();
forward SAC_OnGameModeExit();
forward SAC_OnFilterScriptExit();
forward SAC_AfterPlayerConnect(playerid);
forward SAC_OnPlayerSpawn(playerid);
forward SAC_SetPlayerSpecialAction(playerid, actionid);
forward SAC();
forward OnSACBan(playerid, reason[]);
forward OnSACKick(playerid, reason[]);
forward SAC_OnPlayerText(playerid, text[]);
forward SAC_TogglePlayerControllable(playerid, toggle);
////////////////////////////////////////////////////////////////////////////////
// native SAC_SetPlayerSpecialAction(playerid, actionid);
// native SAC_TogglePlayerControllable(playerid, toggle);
// native OnSACBan(playerid, reason[]);
// native OnSACKick(playerid, reason[]);
////////////////////////////////////////////////////////////////////////////////
#if !defined FILTERSCRIPT
public OnGameModeInit()
#else
public OnFilterScriptInit()
#endif
{
if(!dini_Exists(SAC_CONFIGURATION_FILE))
{
dini_Create(SAC_CONFIGURATION_FILE);
dini_IntSet(SAC_CONFIGURATION_FILE, "Jetpack", 1); SAC_CHEATS[JETPACK] = 1;
dini_IntSet(SAC_CONFIGURATION_FILE, "Weapons", 1); SAC_CHEATS[WEAPONS] = 1;
dini_IntSet(SAC_CONFIGURATION_FILE, "BanCheaters", 1); SAC_CHEATS[BAN] = 1;
dini_IntSet(SAC_CONFIGURATION_FILE, "ForbidNames", 1); SAC_SERVER_INFO[FORBIDDEN_NAMES] = 1;
dini_IntSet(SAC_CONFIGURATION_FILE, "SinglePlayerCheats", 1); SAC_CHEATS[SINGLE_PLAYER_CHEATS] = 1;
dini_IntSet(SAC_CONFIGURATION_FILE, "Anti-Unfreeze", 1); SAC_CHEATS[UNFREEZE] = 1;
}
else
{
SAC_CHEATS[JETPACK] = dini_Int(SAC_CONFIGURATION_FILE, "Jetpack");
SAC_CHEATS[WEAPONS] = dini_Int(SAC_CONFIGURATION_FILE, "Weapons");
SAC_CHEATS[BAN] = dini_Int(SAC_CONFIGURATION_FILE, "BanCheaters");
SAC_SERVER_INFO[FORBIDDEN_NAMES] = dini_Int(SAC_CONFIGURATION_FILE, "ForbidNames");
SAC_CHEATS[SINGLE_PLAYER_CHEATS] = dini_Int(SAC_CONFIGURATION_FILE, "SinglePlayerCheats");
SAC_CHEATS[UNFREEZE] = dini_Int(SAC_CONFIGURATION_FILE, "Anti-Unfreeze");
SAC_TIMER = SetTimer("SAC", TIMER_MILISECONDS, 1);
new SAC_Jetpack[20];
new SAC_Weapon[20];
new SAC_FNames[20];
new SAC_SCheats[20];
new SAC_Unfreeze[20];
new KICKBAN[20];
if(SAC_CHEATS[JETPACK]) SAC_Jetpack = "Yes";
else SAC_Jetpack = "No";
if(SAC_CHEATS[WEAPONS]) SAC_Weapon = "Yes";
else SAC_Weapon = "No";
if(SAC_CHEATS[BAN]) KICKBAN = "Ban";
else KICKBAN = "Kick";
if(SAC_SERVER_INFO[FORBIDDEN_NAMES]) SAC_FNames = "Yes";
else SAC_FNames = "No";
if(SAC_CHEATS[SINGLE_PLAYER_CHEATS]) SAC_SCheats = "Yes";
else SAC_SCheats = "No";
if(SAC_CHEATS[UNFREEZE]) SAC_Unfreeze = "Yes";
else SAC_Unfreeze = "No";
print (" ======================");
print (" SAC:");
print (" Loaded successfully");
print (" ----------------------");
print (" Configuration:");
printf(" %s cheaters for Jetpack: %s", KICKBAN, SAC_Jetpack);
printf(" %s cheaters for Weapons: %s", KICKBAN, SAC_Weapon);
printf(" %s cheaters for singleplayer cheats: %s", KICKBAN, SAC_SCheats);
printf(" Kick players for a forbidden name: %s", SAC_FNames);
printf(" Freeze player which are unfreezing themself: %s", SAC_Unfreeze);
if(SAC_CHEATS[BAN]) KICKBAN = "Yes";
else KICKBAN = "No";
printf(" Ban Cheaters: %s", KICKBAN);
print (" ======================");
}
#if !defined FILTERSCRIPT
return CallLocalFunction("SAC_OnGameModeInit", " ", 0);
#else
return CallLocalFunction("SAC_OnFilterScriptInit", " ", 0);
#endif
}
#if !defined FILTERSCRIPT
public OnGameModeExit()
#else
public OnFilterScriptExit()
#endif
{
KillTimer(SAC_TIMER);
print (" ======================");
print (" SAC:");
print (" Unloaded successfully");
print (" ======================");
#if !defined FILTERSCRIPT
return CallLocalFunction("SAC_OnGameModeExit", " ", 0);
#else
return CallLocalFunction("SAC_OnFilterScriptExit", " ", 0);
#endif
}
public OnPlayerConnect(playerid)
{
foreach_AddPlayer(playerid);
GetPlayerName(playerid, SAC_Players[playerid], MAX_PLAYER_NAME);
new KICKBAN[100];
if(SAC_CHEATS[BAN]) KICKBAN = "ban";
else KICKBAN = "kick";
SAC_SendClientMessagef(playerid, 0xFFFFFFFF, "This server is protected by {00C2EC}SAC{FFFFFF}, cheating will result in a permanent %s.", KICKBAN);
SAC_ResetPlayerStatuses(playerid);
SetTimerEx("SAC_AfterPlayerConnect", 3000, 0, "d", playerid);
if(SAC_SERVER_INFO[FORBIDDEN_NAMES])
{
for(new i; i < sizeof(SAC_FORBIDDEN_NAMES); i++)
{
if(strcmp(SAC_pName(playerid), SAC_FORBIDDEN_NAMES[i], true) == 0)
{
SAC_SendClientMessage(playerid, 0xFFFFFFFF, "Your name is forbidden on our server");
SAC_SendClientMessage(playerid, 0xFFFFFFFF, "Please change your name if you want to come back");
SAC_Kickf(playerid, "Forbidden name (%s)", SAC_pName(playerid));
}
}
}
return CallLocalFunction("SAC_OnPlayerConnect", "d", playerid);
}
public SAC_AfterPlayerConnect(playerid)
{
SAC_PLAYER_INFO[playerid][FULLY_CONNECTED] = 1;
return 1;
}
public OnPlayerDisconnect(playerid, reason)
{
SAC_ResetPlayerStatuses(playerid);
foreach_RemovePlayer(playerid);
return CallLocalFunction("SAC_OnPlayerDisconnect", "dd", playerid, reason);
}
public OnPlayerSpawn(playerid)
{
if(!SAC_PLAYER_INFO[playerid][SPAWNED])
SAC_PLAYER_INFO[playerid][SPAWNED] = 1;
return CallLocalFunction("SAC_OnPlayerSpawn", "d", playerid);
}
public OnPlayerText(playerid, text[])
{
// Anti singleplayer cheat
if(SAC_CHEATS[SINGLE_PLAYER_CHEATS])
{
if((SinglePlayerCheatCheck(text)) && (!IsPlayerAdmin(playerid)))
{
if(!SAC_CHEATS[BAN])
SAC_Kick(playerid, "Singleplayer cheats");
else
SAC_Ban(playerid, "Singleplayer cheats");
}
}
return CallLocalFunction("SAC_OnPlayerText", "ds", playerid, text);
}
public SAC_SetPlayerSpecialAction(playerid, actionid)
{
if(IsPlayerConnected(playerid))
{
if((actionid == SPECIAL_ACTION_USEJETPACK) && (SAC_CHEATS[JETPACK]))
{
SAC_Logf("Could not give player %s a jetpack because of it is forbidden", SAC_pName(playerid));
return 0;
}
return SetPlayerSpecialAction(playerid, actionid);
}
return 1;
}
public SAC_TogglePlayerControllable(playerid, toggle)
{
if(IsPlayerConnected(playerid))
{
switch(toggle)
{
case 0: { TogglePlayerControllable(playerid, 0); SAC_PLAYER_INFO[playerid][FROZEN] = 1; }
case 1: { TogglePlayerControllable(playerid, 1); SAC_PLAYER_INFO[playerid][FROZEN] = 0; }
}
}
return 1;
}
public SAC() // Main function of the anti cheat
{
#if defined USE_FOREACH
foreach(Player, i)
#else
SAC_foreach(i)
#endif
{
if((!IsPlayerAdmin(i)) && (SAC_PLAYER_INFO[i][FULLY_CONNECTED]) && (SAC_IsPlayerSpawned(i)))
{
// Anti JetPack
if(SAC_CHEATS[JETPACK])
{
if(GetPlayerSpecialAction(i) == SPECIAL_ACTION_USEJETPACK)
{
SAC_PLAYER_INFO[i][JETPACK_HACK]++;
if(SAC_PLAYER_INFO[i][JETPACK_HACK] >= MAX_SAC_CHECKS)
{
if(SAC_CHEATS[BAN])
SAC_Ban(i, "Jetpack hack");
else
SAC_Kick(i, "Jetpack hack");
}
}
}
// Anti weapons
if(SAC_CHEATS[WEAPONS])
{
if((GetPlayerWeapon(i) == 35) || (GetPlayerWeapon(i) == 36) || (GetPlayerWeapon(i) == 37) || (GetPlayerWeapon(i) == 38))
{
SAC_PLAYER_INFO[i][WEAPON_HACK]++;
if(SAC_PLAYER_INFO[i][WEAPON_HACK] >= MAX_SAC_CHECKS)
{
if(SAC_CHEATS[BAN])
SAC_Banf(i, "Weapon hack (%s)", SAC_aWeaponNames[GetPlayerWeapon(i)]);
else
SAC_Kickf(i, "Weapon hack (%s)", SAC_aWeaponNames[GetPlayerWeapon(i)]);
}
}
}
// Anti Unfreeze
if(SAC_CHEATS[UNFREEZE])
{
if(SAC_PLAYER_INFO[i][FROZEN])
TogglePlayerControllable(i, 0);
}
}
}
return 1;
}
////////////////////////////////////////////////////////////////////////////////
stock SAC_ResetPlayerStatuses(playerid)
{
SAC_PLAYER_INFO[playerid][JETPACK_HACK] = 0;
SAC_PLAYER_INFO[playerid][WEAPON_HACK] = 0;
SAC_PLAYER_INFO[playerid][FULLY_CONNECTED] = 0;
SAC_PLAYER_INFO[playerid][SPAWNED] = 0;
SAC_PLAYER_INFO[playerid][FROZEN] = 0;
return 1;
}
stock SAC_pName(playerid)
{
return SAC_Players[playerid];
}
stock ReturnTime() // Double O Seven
{
new jb_time[16],jb_h,jb_m,jb_s;
gettime(jb_h,jb_m,jb_s);
format(jb_time,sizeof(jb_time),"%02d:%02d:%02d",jb_h,jb_m,jb_s);
return jb_time;
}
stock ReturnDate() // Double O Seven
{
new jb_date[32],jb_day,jb_month,jb_year;
getdate(jb_year,jb_month,jb_day);
format(jb_date,sizeof(jb_date),"%d. %s %d",jb_day,GetMonth(jb_month),jb_year);
return jb_date;
}
stock GetMonth(month) // Double O Seven
{
new string[32]; string="Unknown month";
switch(month)
{
case 1:string="January";
case 2:string="February";
case 3:string="March";
case 4:string="April";
case 5:string="May";
case 6:string="June";
case 7:string="July";
case 8:string="August";
case 9:string="Septembre";
case 10:string="Octobre";
case 11:string="Novembre";
case 12:string="Decembre";
}
return string;
}
stock SAC_Log(log[])
{
printf("(SAC) %s",log);
new string[256];
format(string,sizeof(string),"%s | %s | %s\r\n",ReturnDate(),ReturnTime(),log);
new File:f=fopen(SAC_LOG_FILE,io_append);
fwrite(f,string);
return fclose(f);
}
stock foreach_AddPlayer(playerid)
{
#if !defined USE_FOREACH
if(foreach_ConnectedPlayers >= MAX_PLAYERS) return 0;
foreach_ConnectedPlayerList[++foreach_ConnectedPlayers] = playerid;
#endif
return 1;
}
stock foreach_RemovePlayer(playerid)
{
#if !defined USE_FOREACH
for(new i; i < foreach_ConnectedPlayers; ++i)
{
if(foreach_ConnectedPlayerList[i] == playerid)
{
--foreach_ConnectedPlayers;
foreach_ConnectedPlayerList[i] = foreach_ConnectedPlayerList[foreach_ConnectedPlayers];
return 1;
}
}
return 0;
#endif
}
stock SAC_Kick(playerid, reason[])
{
SAC_SendClientMessageToAllf(0xFFFFFFFF, "Permanently kicked player {00C2EC}%s{FFFFFF} (reason: %s)", SAC_pName(playerid), reason);
SAC_Logf("%s has been kicked (reason: %s)", SAC_pName(playerid), reason);
CallLocalFunction("OnSACKick", "ds", playerid, reason);
TogglePlayerControllable(playerid, 0);
GameTextForPlayer(playerid, "~w~You have been kicked", 500000, 5);
return Kick(playerid);
}
stock SAC_Ban(playerid, reason[])
{
SAC_SendClientMessageToAllf(0xFFFFFFFF, "Permanently banned player {00C2EC}%s{FFFFFF} (reason: %s)", SAC_pName(playerid), reason);
SAC_Logf("%s has been banned (reason: %s)", SAC_pName(playerid), reason);
CallLocalFunction("OnSACBan", "ds", playerid, reason);
TogglePlayerControllable(playerid, 0);
GameTextForPlayer(playerid, "~w~You have been banned", 500000, 5);
return Ban(playerid);
}
stock SAC_IsPlayerSpawned(playerid)
{
return SAC_PLAYER_INFO[playerid][SPAWNED];
}
stock SinglePlayerCheatCheck(text[])
{
if(strlen(text) < 6)
return 0;
for(new i; i < sizeof(SinglePlayerCheats); i++)
if(strfind(text, SinglePlayerCheats[i], true) != -1)
return 1;
return 0;
}
////////////////////////////////////////////////////////////////////////////////
// OnPlayerConnect
#if defined _ALS_OnPlayerConnect
#undef OnPlayerConnect
#else
#define _ALS_OnPlayerConnect
#endif
#define OnPlayerConnect SAC_OnPlayerConnect
// OnPlayerDisconnect
#if defined _ALS_OnPlayerDisconnect
#undef OnPlayerDisconnect
#else
#define _ALS_OnPlayerDisconnect
#endif
#define OnPlayerDisconnect SAC_OnPlayerDisconnect
// OnGameModeInit
#if defined _ALS_OnGameModeInit
#undef OnGameModeInit
#else
#define _ALS_OnGameModeInit
#endif
#define OnGameModeInit SAC_OnGameModeInit
// OnFilterScriptInit
#if defined _ALS_OnFilterScriptInit
#undef OnFilterScriptInit
#else
#define _ALS_OnFilterScriptInit
#endif
#define OnFilterScriptInit SAC_OnFilterScriptInit
// OnGameModeExit
#if defined _ALS_OnGameModeExit
#undef OnGameModeExit
#else
#define _ALS_OnGameModeExit
#endif
#define OnGameModeExit SAC_OnGameModeExit
// OnFilterScriptExit
#if defined _ALS_OnFilterScriptExit
#undef OnFilterScriptExit
#else
#define _ALS_OnFilterScriptExit
#endif
#define OnFilterScriptExit SAC_OnFilterScriptExit
// OnPlayerSpawn
#if defined _ALS_OnPlayerSpawn
#undef OnPlayerSpawn
#else
#define _ALS_OnPlayerSpawn
#endif
#define OnPlayerSpawn SAC_OnPlayerSpawn
// OnPlayerText
#if defined _ALS_OnPlayerText
#undef OnPlayerText
#else
#define _ALS_OnPlayerText
#endif
#define OnPlayerText SAC_OnPlayerText
////////////////////////////////////////////////////////////////////////////////