Страница 1 из 1

smforcecam

Добавлено: 16 окт 2018, 08:23
Longipongeoos
Наблюдение за всеми игроками администратором.
Исходный код

Код: Выбрать все

#if 1 //####################################################### Headers #####################################################//
#pragma semicolon 1
#include <sourcemod>
#include <sdktools>

#define PLUGIN_VERSION "1.0"
#define DEBUG 0

public Plugin:myinfo = {
   name = "SM Forcecamera",
   author = "KawMAN",
   description = "Turn on mp_forcecamera 1 for non admins only",
   version = PLUGIN_VERSION,
   url = "http://wsciekle.pl/"
};
#endif //---------------------------------------------------- Headers End ---------------------------------------------------//

#if 1 //####################################################### GLOBALS #####################################################//

#define MAXADMGROUPS 8

new bool:AllowViewOpp[MAXPLAYERS+1]   = {false, ...};

new bool:g_sm_forcecam            = false;
new Handle:gCvar_sm_forcecam      = INVALID_HANDLE;
new String:g_sm_forcecam_flag[2]   = "";
new Handle:gCvar_sm_forcecam_flag   = INVALID_HANDLE;
new String:g_sm_forcecam_groups[MAXADMGROUPS+1][32];
new Handle:gCvar_sm_forcecam_groups   = INVALID_HANDLE;
new Handle:gCvar_mp_forcecamera      = INVALID_HANDLE;
new Handle:gCvar_sm_forcecam_ver      = INVALID_HANDLE;


#endif //---------------------------------------------------- GLOBALS END ---------------------------------------------------//

#if 1 //####################################################### SM Fwd #####################################################//
public OnPluginStart()
{
   //Load Languages
   LoadTranslations("common.phrases");
   
   gCvar_sm_forcecam = CreateConVar("sm_forcecamera", "1", "Enable SM Force Camera");
   gCvar_sm_forcecam_flag = CreateConVar("sm_forcecamera_flag", "a", "Admin Flag required for view opposite team players");
   gCvar_sm_forcecam_groups = CreateConVar("sm_forcecamera_groups", "Full Admins", "Allow this Groups to view opposite team players");
   gCvar_sm_forcecam_ver = CreateConVar("sm_forcecam_ver", PLUGIN_VERSION, "SM Force Camera Version", FCVAR_PLUGIN|FCVAR_SPONLY|FCVAR_REPLICATED|FCVAR_DONTRECORD|FCVAR_NOTIFY);
   
   gCvar_mp_forcecamera = FindConVar("mp_forcecamera");
   
   RefreshSetting();
   
   HookEvent("player_death", Ev_PlayerDeath);
   HookConVarChange(gCvar_sm_forcecam, MyCvarChange);
   HookConVarChange(gCvar_sm_forcecam_flag, MyCvarChange);
   HookConVarChange(gCvar_sm_forcecam_groups, MyCvarChange);
   HookConVarChange(gCvar_mp_forcecamera, MyCvarChange);
   
   #if DEBUG >= 1
   RegAdminCmd("sm_forcecam_table", Cmd_ForceCamTable, ADMFLAG_ROOT, "");
   #endif
}

public OnMapStart()
{
   CreateTimer(5.0, DelayedVersionRefresh);
}

public bool:OnClientConnect(client, String:rejectmsg[], maxlen)
{
   AllowViewOpp[client] = false;
   return true;
}

public OnClientPostAdminCheck(client)
{
   decl String:Flag[2];
   AllowViewOpp[client] = false;
   new AdminId:AdmId = GetUserAdmin(client);
   GetConVarString(gCvar_sm_forcecam_flag, Flag, sizeof(Flag));
   if(Flag[0]!='\0')
   {
      decl AdminFlag:Flag2;
      if(FindFlagByChar(Flag[0], Flag2))
      {
         if(GetAdminFlag(AdmId, Flag2))
         {
            #if DEBUG >= 2
            decl String:cname[128];
            GetClientName(client, cname, sizeof(cname));
            new team = GetClientTeam(client);
            PrintToServer("[SM_FORCECAM] %s(%d)[%d] authed by flag", cname, client,team);
            #endif
            AllowViewOpp[client]   = true;
            
         }
      }
   }
   
   new GroupsCount = GetAdminGroupCount(AdmId);
   if(AllowViewOpp[client] != true && GroupsCount>0)
   {
      decl String:GroupName[32];
      for(new i = 0; i<GroupsCount; i++)
      {
         if(AllowViewOpp[client] == true) break;
         
         GetAdminGroup(AdmId, i, GroupName, sizeof(GroupName));
         for(new j = 0; j <= MAXADMGROUPS; j++)
         {
            if(g_sm_forcecam_groups[j][0]!='\0' && strcmp(GroupName, g_sm_forcecam_groups[j], false) == 0)
            {
               #if DEBUG >= 2
               decl String:cname[128];
               GetClientName(client, cname, sizeof(cname));
               new team = GetClientTeam(client);
               PrintToServer("[SM_FORCECAM] %s(%d)[%d] authed by group", cname, client,team);
               #endif
               
               AllowViewOpp[client]   = true;
               break;
            }
         }
      }
   }
   
}

#endif //---------------------------------------------------- SM Fwd END ---------------------------------------------------//

#if 1 //####################################################### Settings #####################################################//

public MyCvarChange(Handle:convar, const String:oldValue[], const String:newValue[]) //----------- On plugins cvar change
{
   if(strcmp(oldValue, newValue)==0) return; //No change
   RefreshSetting(convar);
}

RefreshSetting(Handle:convar=INVALID_HANDLE) //---- Setting state refresh, INVALID_HANDLE == refresh all cvars and precache models
{
   
   if(convar == INVALID_HANDLE || convar == gCvar_sm_forcecam)
   {
      new bool:boolval = GetConVarBool(gCvar_sm_forcecam);
      if(boolval!=g_sm_forcecam)
      {
         if(boolval)
         {
            g_sm_forcecam = true;
            AddCommandListener(Cmd_spec_prev, "spec_prev");
            AddCommandListener(Cmd_spec_next, "spec_next");
            AddCommandListener(Cmd_spec_player, "spec_player");
            AddCommandListener(Cmd_spec_mode, "spec_mode");
            if(gCvar_mp_forcecamera!=INVALID_HANDLE) SetConVarBool(gCvar_mp_forcecamera, false);
         }
         else
         {
            g_sm_forcecam = false;
            RemoveCommandListener(Cmd_spec_prev, "spec_prev");
            RemoveCommandListener(Cmd_spec_next, "spec_next");
            RemoveCommandListener(Cmd_spec_player, "spec_player");
            RemoveCommandListener(Cmd_spec_mode, "spec_mode");
         }
      }
      if(convar != INVALID_HANDLE) return;
   }
   
   if(convar == INVALID_HANDLE || convar == gCvar_sm_forcecam_flag)
   {
      GetConVarString(gCvar_sm_forcecam_flag, g_sm_forcecam_flag, sizeof(g_sm_forcecam_flag));
      
      if(convar != INVALID_HANDLE) return;
   }
   if(convar == INVALID_HANDLE || convar == gCvar_mp_forcecamera)
   if(convar == INVALID_HANDLE || convar == gCvar_sm_forcecam_groups)
   {
      decl String:tmp[256];
      GetConVarString(gCvar_sm_forcecam_groups, tmp, sizeof(tmp));
      ExplodeString(tmp, ",", g_sm_forcecam_groups, sizeof(g_sm_forcecam_groups), sizeof(g_sm_forcecam_groups[]));
      if(convar != INVALID_HANDLE) return;
   }
   if(convar == INVALID_HANDLE || convar == gCvar_mp_forcecamera)
   {
      if(gCvar_mp_forcecamera!=INVALID_HANDLE && g_sm_forcecam) SetConVarBool(gCvar_mp_forcecamera, false);
   }
}

#endif //---------------------------------------------------- Settings END ---------------------------------------------------//

#if 1 //####################################################### Spec Commands #################################################//

public Action:Cmd_spec_mode(client, const String:command[], argc)
{
   if(client == 0 || IsPlayerAlive(client)) return Plugin_Handled;
   if( (!g_sm_forcecam) || AllowViewOpp[client]) return Plugin_Continue;
   
   SetEntProp(client, Prop_Send, "m_iObserverMode", 4); //Force First Person
   return Plugin_Handled;
}

public Action:Cmd_spec_player(client, const String:command[], argc)
{
   if(client == 0 || IsPlayerAlive(client)) return Plugin_Handled;
   if( (!g_sm_forcecam) || AllowViewOpp[client]) return Plugin_Continue;
   
   new team = GetClientTeam(client);
   if(team <= 1) return Plugin_Continue; //Spectator
   
   decl String:arg[128];
   GetCmdArg(1, arg, sizeof(arg));
   if(arg[0]!='\0')
   {
      decl String:target_name[MAX_TARGET_LENGTH];
      decl target_list[MAXPLAYERS], target_count, bool:tn_is_ml;
      
      if ((target_count = ProcessTargetString(
            arg,
            client,
            target_list,
            MAXPLAYERS,
            COMMAND_FILTER_CONNECTED,
            target_name,
            sizeof(target_name),
            tn_is_ml)) <= 0)
      {
         ReplyToTargetError(client, target_count);
         return Plugin_Handled;
      }
      
      if(target_count != 1 ) return Plugin_Handled;
      
      new observclient = target_list[0];
      new team2 = GetClientTeam(observclient);
      if(team == team2) return Plugin_Continue;
   }
   
   return Plugin_Handled;
}

public Action:Cmd_spec_next(client, const String:command[], argc)
{
   if(client == 0 || IsPlayerAlive(client)) return Plugin_Handled;
   if( (!g_sm_forcecam) || AllowViewOpp[client]) return Plugin_Continue;
   
   new team = GetClientTeam(client);
   if(team <= 1) return Plugin_Continue;  //Spectator
   
   new Observing = GetEntPropEnt(client, Prop_Send, "m_hObserverTarget");
   
   new NextObserv = NextPrevClient(Observing, true, team);
   
   if(NextObserv != -1 ) {
      #if DEBUG >= 2
      decl String:cname[128],String:cname2[128];
      GetClientName(client, cname, sizeof(cname));
      GetClientName(NextObserv, cname2, sizeof(cname2));
      new team2 = GetClientTeam(NextObserv);
      PrintToServer("C: %s(%d)[%d], used spec_next, %s(%d)[%d]", cname, client,team, cname2, NextObserv, team2);
      #endif
      
      SetEntPropEnt(client, Prop_Send, "m_hObserverTarget", NextObserv);
   }
   else return Plugin_Continue; //No more alive players
      
   return Plugin_Handled;
}

public Action:Cmd_spec_prev(client, const String:command[], argc)
{
   if(client == 0 || IsPlayerAlive(client)) return Plugin_Handled;
   if( (!g_sm_forcecam) || AllowViewOpp[client]) return Plugin_Continue;
   
   new team = GetClientTeam(client);
   if(team <= 1) return Plugin_Continue;  //Spectator
   
   new Observing = GetEntPropEnt(client, Prop_Send, "m_hObserverTarget");
   new PrevObserv = NextPrevClient(Observing, false, team);
   if(PrevObserv != -1 )
   {
      #if DEBUG >= 2
      decl String:cname[128],String:cname2[128];
      GetClientName(client, cname, sizeof(cname));
      GetClientName(PrevObserv, cname2, sizeof(cname2));
      new team2 = GetClientTeam(PrevObserv);
      PrintToServer("C: %s(%d)[%d], used spec_prev, %s(%d)[%d]", cname, client,team, cname2, PrevObserv, team2);
      #endif
   
      SetEntPropEnt(client, Prop_Send, "m_hObserverTarget", PrevObserv);
   }
   else return Plugin_Continue; //No more alive players
   
   return Plugin_Handled;
}

public Action:Ev_PlayerDeath(Handle:event, const String:name[], bool:dontBroadcast)
{
   new client = GetClientOfUserId(GetEventInt(event, "userid"));
   if(!AllowViewOpp[client])
   {
      CreateTimer(6.0, DelayedSetObserv, client);
   }
   
   //Check all players who was watching him
   CreateTimer(0.1, DelayedCheckDeath, client);
   
   return Plugin_Continue;
}

public Action:DelayedCheckDeath(Handle:timer, any:client)
{
   decl NextObserv, team, Observing;
   for(new i=1; i<=MaxClients; i++)
   {
      if(!AllowViewOpp[client] && IsClientInGame(i) && (!IsPlayerAlive(i)) )
      {
         team = GetClientTeam(i);
         if(team<=1)  continue; //Spec
         Observing = GetEntPropEnt(i, Prop_Send, "m_hObserverTarget");
         if(Observing == client)
         {
            NextObserv = NextPrevClient(client, true, team);
            if(NextObserv > 0) SetEntPropEnt(client, Prop_Send, "m_hObserverTarget", NextObserv);
         }
      }
   }
}
public Action:DelayedSetObserv(Handle:timer, any:client)
{
   if(IsClientInGame(client) && (!IsPlayerAlive(client)))
   {
      new team = GetClientTeam(client);
      
      new Observing = GetEntPropEnt(client, Prop_Send, "m_hObserverTarget");
      new NextObserv = NextPrevClient(Observing, true, team);
      if(NextObserv != -1 ) SetEntPropEnt(client, Prop_Send, "m_hObserverTarget", NextObserv);
      CreateTimer(1.0, DelayedSetMode, client);
   }
}


public Action:DelayedSetMode(Handle:timer, any:client)
{
   if(IsClientConnected(client) && IsClientInGame(client) && (!IsPlayerAlive(client)))
   {
      SetEntProp(client, Prop_Send, "m_iObserverMode", 4);
   }
}

#endif //---------------------------------------------------- Spec Commands End ------------------------------------------------//

#if 1 //####################################################### Helpers #################################################//
NextPrevClient(client, bool:Next = true,Team = -1, bool:Alive = true)
{
   if(client <=0 ) client = 1 ;
   if(client > MaxClients ) client = MaxClients ;
   new i = client;
   
   if(Next) i++;
   else i--;
   
   for(; ; )
   {
      if(IsClientConnected(i) && IsClientInGame(i) )
      {
         if(!Alive || ( Alive && IsPlayerAlive(i)) )
         {
            if(Team == -1)
            {
               break;
            }
            new Team2 = GetClientTeam(i);
            if(Team == Team2)
            {
               break;
            }
         }
      }
            
      if(i == MaxClients && Next) i = 0;
      if(i == 1 && !Next) i = MaxClients;
      
      if(i == client) return -1; // No clients
      if(Next) i++;
      else i--;
   }
   return i;
}

public Action:DelayedVersionRefresh(Handle:timer, any:client)
{
   SetConVarString(gCvar_sm_forcecam_ver, PLUGIN_VERSION, false, false);
}


#if DEBUG >= 1
public Action:Cmd_ForceCamTable(client, args)
{
   decl String:cname[64], String:cname2[64], team, team2, Observing;
   ReplyToCommand(client, "##### Observing Table #####");
   ReplyToCommand(client, "#ClientId-ClientName-Team observing ClientId-ClientName-Team#");
   for(new i=1; i<=MaxClients; i++)
   {
      if(IsClientInGame(i) && (!IsPlayerAlive(i)) )
      {
         GetClientName(i, cname, sizeof(cname));
         team = GetClientTeam(i);
         if(args>=1 && team<=1)  continue;
         Observing = GetEntPropEnt(i, Prop_Send, "m_hObserverTarget");
         
         if(Observing == -1 || !IsClientInGame(Observing) || !IsPlayerAlive(Observing)) continue;
         GetClientName(Observing, cname2, sizeof(cname2));
         team2 = GetClientTeam(Observing);
         
         ReplyToCommand(client, "%d#%d-%s-%d\t\tobserv\t\t%d-%s-%d", AllowViewOpp[i],i, cname,team, Observing ,cname2,team2);
      }
   }
}
#endif

#endif //---------------------------------------------------- Helpers End ------------------------------------------------//



CVARS:

Код: Выбрать все

sm_forcecamera - 1 - Включить плагин, 0 - Отключить (по умолчанию: 1)
sm_forcecamera_flag - флаг администратора, который позволяет наблюдать за игроками (по умолчанию: a)
sm_forcecamera_groups - Список групп, которые позволяют наблюдать за игроками в другой команде, (по умолчанию: «Полные админы», группы должны быть разделены запятой).
sm_forcecam_ver - версия SM Forcecamera

Необходимое значение в Sourcemod.cfg

Код: Выбрать все

mp_forcecamera 0


Установка:
1. Скомпилировать исходный код "sp"
2. Переместить плагин "smx" в папку plugins
3. Переместить файл "sp" в папку scripting
4. Значение "cvars" записать в файл server.cfg