Заказать Сервер Заказать Плагин Контакты Поиск

[ вход ]
[ последние сообщения ]

Страница 1 из 11
Форум » SourceMod - Counter Strike Source && CS GO » Уроки SourceMod (SourcePawn) Скриптинга » Как создать голосование
Как создать голосование
_wS_ Дата: Вторник, 07.02.2012, 01:55:37 | Сообщение # 1
Даю примерик небольшого скрипта голосования за кик игрока в начале раунда.

Код
#pragma semicolon 1
#include <sourcemod>

new Handle:h_Menu, Handle:h_Timer;
new kick_vots[MAXPLAYERS + 1], timer_sec, all_votes;

public OnPluginStart()
{
     HookEvent("round_start", round_start, EventHookMode_PostNoCopy);
}

public round_start(Handle:event, const String:name[], bool:silent)
{
     // Если вдруг начался новый раунд, но наш таймер + меню активны, останавливаем их.
     // Например, раунд быстро закончился, или был рестарт.
     if (h_Timer != INVALID_HANDLE)
     {
         KillTimer(h_Timer);
         h_Timer = INVALID_HANDLE;
     }

     if (h_Menu != INVALID_HANDLE) CloseHandle(h_Menu);
     h_Menu = CreateMenu(Select_Func);
     SetMenuTitle(h_Menu, "Кого кикнуть?\n \n");
     SetMenuExitButton(h_Menu, false);
     decl String:StR_Id[15], String:StR_Name[MAX_NAME_LENGTH];
     new players = 0;
     for (new i = 1; i <= MaxClients; i++)
     {
         // очищаем кол-во голосов за кик игрока (i = его индекс)
         kick_vots[i] = 0;

         if (IsClientInGame(i) && GetClientName(i, StR_Name, MAX_NAME_LENGTH))
         {
             // получаем userid игрока и делаем его строкой, чтобы добавить в меню
             IntToString(GetClientUserId(i), StR_Id, sizeof(StR_Id));
             AddMenuItem(h_Menu, StR_Id, StR_Name);
             players++;
         }
     }

     // если игроков на сервере > 0
     if (players > 0)
     {
         // показываем игрокам созданное меню и запускаем таймер
         for (new i = 1; i <= MaxClients; i++)
         {
             if (IsClientInGame(i) && !IsFakeClient(i)) DisplayMenu(h_Menu, i, 10);
         }
         all_votes = 0;  // сколько всего было голосов
         timer_sec = 15; // время голосования в сек.
         h_Timer = CreateTimer(1.0, Timer_Func, _, TIMER_REPEAT);
     }
     else
     {
         // если нет игроков, удаляем созданное меню
         CloseHandle(h_Menu);
         h_Menu = INVALID_HANDLE;
     }
}

public Select_Func(Handle:menu, MenuAction:action, client, item)
{
     if (action != MenuAction_Select)
         return;

     decl String:StR_Id[15];
     if (!GetMenuItem(menu, item, StR_Id, sizeof(StR_Id)))
         return;

     new target = GetClientOfUserId(StringToInt(StR_Id));
     if (target > 0)
     {
         all_votes++;
         kick_vots[target]++;
         PrintToChatAll("%N выбрал игрока %N", client, target);
     }
     else
         PrintToChat(client, "Игрок не найден");
}

public Action:Timer_Func(Handle:timer)
{
     if (--timer_sec > 0)
     {
         PrintHintTextToAll("До завершения голосования:\n< %d сек >", timer_sec);
         return Plugin_Continue;
     }

     // Время истекло, голосование окончено
     h_Timer = INVALID_HANDLE;
     if (h_Menu != INVALID_HANDLE)
     {
         CloseHandle(h_Menu);
         h_Menu = INVALID_HANDLE;
     }
     PrintHintTextToAll("Голосование завершено (%d голосов)", all_votes);
     if (all_votes < 1)
         return Plugin_Stop;

     // Находим игрока, за которого больше всего проголосовали
     new vots = 0, target = 0;
     for (new i = 1; i <= MaxClients; i++)
     {
         if (kick_vots[i] > vots)
         {
             vots = kick_vots[i];
             target = i;
         }
     }
     if (target > 0 && IsClientInGame(target))
     {
         PrintToChatAll("Игрок %N кикнут", target);
         KickClient(target, "бб");
     }
     else
         PrintToChatAll("Игрок не найден");

     return Plugin_Stop;
}


#pragma semicolon 1 говорит компилятору, что в конце каждой строки будет символ ; (точка с запятой). Это не обязательно, можно убрать, просто кому как нравится.

Прикрепления: x_vote.sp(3Kb)
 
naykon4979 Дата: Среда, 08.02.2012, 16:58:35 | Сообщение # 2
Сообщений: 3
Репутация: 0 [ +/- ]
Поподробней об этом
Quote (_wS_)
new Handle:h_Menu, Handle:h_Timer, kick_vots[MAXPLAYERS+1], timer_sec, all_votes;


и этом

Quote (_wS_)
INVALID_HANDLE
 
_wS_ Дата: Среда, 08.02.2012, 17:37:25 | Сообщение # 3
У переменных есть значения по умолчанию, например:

Code
new x; // 0
new Float:x // 0.0
new Handle:x // INVALID_HANDLE


Handle:h_Menu - храним в этой переменной созданное меню
Handle:h_Timer - в этой таймер
kick_vots[MAXPLAYERS+1] - количество голосов

kick_vots[65]; // доступные индексы: с kick_vots[0] до kick_vots[64]. Каждый игрок это уникальный индекс (как userid). Поэтому, если индекс игрока 5 и за него голосуют, мы делаем kick_vots[5] += 1; MaxClients - максимальный индекс игрока (число равно максимальному количеству слотов на сервере).

timer_sec - время таймера в секундах. all_votes - сколько всего было голосов. Это глобальные переменные (так как созданы вверху, а не внутри какой-то функции). Такие переменные доступны внутри любой функции, т.е. их можно получать/менять.
 
Valeriks Дата: Среда, 12.02.2014, 01:20:22 | Сообщение # 4
Сообщений: 102
Репутация: 3 [ +/- ]
Интересно, а можно сделать совсем простое голосование ДА/НЕТ по выполнению серверной команды?
Как бы регистрируем команду чата, скажем !sv, появляется окошко с голосованием, и если 60% игроков на сервере проголосовали ЗА то выполняем серверную команду.. Или я малость загоняюсь? xaxa

п.с..или даже без окошка)) просто чтобы в чате появлялась надпись, там получено столько-то голосов и за это и то. как при запуске голосования по смене карты rtv, что-то типо того.


Сообщение отредактировал Valeriks - Среда, 12.02.2014, 01:25:58
 
Darkeneez Дата: Среда, 12.02.2014, 04:14:07 | Сообщение # 5
Сообщений: 222
Репутация: 18 [ +/- ]
Код

stock create_vote(client)
{
  if    (IsVoteInProgress())
  {
   PrintToChat(client, "\x04[GamesVote]\x01Голосование УЖЕ идет");
   return;
  }
   
  new i_Clients[32], i_Count;

  for (new i = 1; i <= MaxClients; i++)
  {
   if (!IsClientInGame(i) || !IsPlayerAlive(i) || GetClientTeam(i) != 2)
    continue;
     
   i_Clients[i_Count++] = i;
  }
   
  new    Handle:_menu    =    CreateMenu(Handle_VoteMenu);
  SetMenuTitle(_menu, "Во что хотите поиграть?");  
   
  if(KvGotoFirstSubKey(kv_one, false))
  {
   new    String:name_[70];
   new    p_max;  
   new    p_min;
    
   do
   {
    KvGetSectionName(kv_one,    name_,    sizeof    (name_));
    p_max    =    KvGetNum(kv_one,    "max_players");
    p_min    =    KvGetNum(kv_one,    "min_players");
    if    (i_Count > p_min && i_Count < p_max && GetRandomInt(1, 5) == 2 || 3)  
     AddMenuItem(_menu,    name_,    name_);
   }
   while    (KvGotoNextKey(kv_one, false));
  }
  KvRewind(kv_one);
   
  SetMenuExitButton(_menu, true);
  VoteMenu(_menu, i_Clients, i_Count, 15);
}

Разбирай.
 
Valeriks Дата: Среда, 12.02.2014, 15:08:54 | Сообщение # 6
Сообщений: 102
Репутация: 3 [ +/- ]
Цитата Darkeneez ()
Разбирай.

Темный лес...
 
Darkeneez Дата: Среда, 12.02.2014, 18:26:17 | Сообщение # 7
Сообщений: 222
Репутация: 18 [ +/- ]
Гм, попробуем еще раз.

Код
stock create_vote(client)  
{  
  if    (IsVoteInProgress()) //Проверяем, имеются ли запущенные голосования (Любые)
  {  
  PrintToChat(client, "\x04[GamesVote]\x01Голосование УЖЕ идет");  
  return;  
  }  
   
  //Считаем и записываем нужное число игроков по условиям  
  new i_Clients[32], i_Count;  

  for (new i = 1; i <= MaxClients; i++)  
  {  
   if (!IsClientInGame(i) || !IsPlayerAlive(i) || GetClientTeam(i) != 2)  
   continue;  
       
   i_Clients[i_Count++] = i;  
  }  
     
  //Создаем меню
  new    Handle:_menu    =    CreateMenu(Handle_VoteMenu);  
  SetMenuTitle(_menu, "Во что хотите поиграть?");   
     
  AddMenuItem(_menu,    "0",    "Ляля");  
  AddMenuItem(_menu,    "1",    "Ляля");  
     
     //Добавляем кнопку выхода
  SetMenuExitButton(_menu, true);  
  //Показываем меню голосования нужным игрокам (Число и ID которых, ранее записали в цикле)
  VoteMenu(_menu, i_Clients, i_Count, 15);  
}
 
Valeriks Дата: Среда, 12.02.2014, 20:42:16 | Сообщение # 8
Сообщений: 102
Репутация: 3 [ +/- ]
Хорошо. Теперь приблизительно понятно. Начала кода я попробую собрать сам.
Не понятно следующее. Мы проверили нет ли голосования, посчитали игроков, создали меню и показали его игрокам.. А какая функция будет дергать выполнение если большинство проголосовало за?
 
Darkeneez Дата: Четверг, 13.02.2014, 05:06:09 | Сообщение # 9
Сообщений: 222
Репутация: 18 [ +/- ]
Код
public Handle_VoteMenu(Handle:menu, MenuAction:action, param1, param2)
{
         //param1 - клиент (Голосование при этом еще не закончено!!) param2- пункт голосования
  if    (param1 > 0)
  {
   new String:map[64];
   GetMenuItem(menu, param2, map, sizeof(map));
   if    (!StrEqual(map, ""))
    PrintToChatAll("\x04[GamesVote]\x03%N \x01Хочет играть в \x03\"%s\"", param1, map);
  }
   
  if (action == MenuAction_End)
  {
   CloseHandle(menu);
  }  
  //param1 - победивший пункт голосования (Голосование закончилось)
  else if (action == MenuAction_VoteEnd)  
  {
   new String:map[64];
   GetMenuItem(menu, param1, map, sizeof(map));
   PrintToChatAll("\x04[GamesVote]\x01Играем в \x03\"%s\"", map);
   PrintCenterTextAll("Играем в %s", map);
   PrintHintTextToAll("Играем в %s", map);
    
   if(KvJumpToKey(kv_one, map))
   {
    new String:rules_[256];
    KvGetString(kv_one,    "rules", rules_, sizeof(rules_));
    if    (!StrEqual(rules_,    ""))
     PrintToChatAll("\x04[GamesVote]\x03Правила игры в \x04%s:\x03\n%s", map, rules_);
   }
  }
}
 
dimoncheg Дата: Суббота, 21.03.2015, 21:45:50 | Сообщение # 10
Сообщений: 12
Репутация: 1 [ +/- ]
Реально создать такое меню голосования, по типу плагина maprate( рейтинг карт) Потому что я этот плагин уже даавно ищу, найти никак не магу( а если и нахожу, он нерабочий!
 
iEx Дата: Суббота, 21.03.2015, 22:54:53 | Сообщение # 11
Сообщений: 305
Репутация: 23 [ +/- ]
Все возможно,руки нужны да знания.
Создание меню+Запись данных фаил(kv) и его считывание сойдет,но лучше подключить базу данных...
 
dimoncheg Дата: Суббота, 21.03.2015, 23:30:28 | Сообщение # 12
Сообщений: 12
Репутация: 1 [ +/- ]
iEx, Во, братан, слушай, если тебя не затруднит, я нашел подобный плагин голоания за карту, называется map rate, я его ставил, он не рабтает, мне написали на вашем форуме, что лагин уже несколько лет с ошибкой лежит, и никто не исправляет, ну так вот, к чему я это говорю: Если тебе время позволяет, пожалуйста перейди по ссылочке:
, там исходник этого плагина, ты одним глазком глянь что там не так, и отпиши мне пожалуйсто, если и ошибку исправишь, буду очень благодарен)! За ранее спасибо!
Ссылка, откуда я скачивал сам плагин!
 
Форум » SourceMod - Counter Strike Source && CS GO » Уроки SourceMod (SourcePawn) Скриптинга » Как создать голосование
Страница 1 из 11
Поиск: