Таймер

Тема в разделе "Программирование / Скриптинг", создана пользователем /_Parlament_\, 8 июл 2015.

  1. /_Parlament_\

    /_Parlament_\

    Сообщения:
    135
    Симпатии:
    7
    Добрый день, как правильно делать таймер, а то у меня пишет только вы возродитесь через 2 сек и все
    как сделать чтобы когда я умер писало
    возрождение через 5
    возрождение через 4
    возрождение через 3
    возрождение через 2
    возрождение через 1
    возрождение через 0
    PHP:
    #include <sourcemod>
    #include <sdktools>
    #include <cstrike>

    #pragma semicolon 1

    new Handle:Enabled;
    new 
    Handle:RespawnEnabled;
    new 
    Handle:RespawnTime;


    public 
    OnPluginStart()
    {
        
    CreateConVar("st_version""1.6""Версия"FCVAR_PLUGIN|FCVAR_SPONLY|FCVAR_REPLICATED|FCVAR_NOTIFY);
        
        
    Enabled CreateConVar("st_enabled""1""0 = Plugin Disabled, 1 = Plugin Enabled");
        
    RespawnEnabled CreateConVar("st_respawn",    "1""enabled/disable respawn");
        
    RespawnTime CreateConVar("st_respawntime",     "5""Ammount of time to respawn after a user dies");
        
        
    HookEvent("player_death"PlayerDeath);
    }

    public 
    Action:PlayerDeath(Handle:event, const String:name[], bool:dontBroadcast)
    {
        if(
    GetConVarInt(RespawnEnabled) == 0)
            return 
    Plugin_Continue;
            
        new 
    client GetClientOfUserId(GetEventInt(event"userid"));
        
    RespawnClient(client);
        
        return 
    Plugin_Continue;
    }


    stock RespawnClient(client)

        new 
    Float:Timer float(GetConVarInt(RespawnTime));
        
        if(
    GetConVarInt(Enabled) == 1)
        {
            
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x041 \x01секунд"RoundToNearest(Timer));
        }
        else
        {
        
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x042 \x01секунд"RoundToNearest(Timer));
        }
        else
        {
        
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x043 \x01секунд"RoundToNearest(Timer));
        }
        else
        {
        
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x044 \x01секунд"RoundToNearest(Timer));
        }
        else
        {
        
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x045 \x01секунд"RoundToNearest(Timer));
        }
        
    CreateTimer(TimerRespawnclient);

        return;
    }

    public 
    Action:Respawn(Handle:Timerany:client)
    {
        if(!
    IsClientInGame(client) || IsPlayerAlive(client))
            return;
        
        new 
    Team GetClientTeam(client);
        if(
    Team == || Team == 1)
            return;
        
        
    CS_RespawnPlayer(client);
        
        return;
    }
     
  2. DarklSide

    DarklSide

    Сообщения:
    680
    Симпатии:
    173
  3. uhx

    uhx

    Сообщения:
    20
    Симпатии:
    0
    Используй это:
    CreateTimer(1.0, Respawn, client, TIMER_REPEAT);
    + счетчик в самом таймере. Правда, как его правильно организовать я не знаю, сам бы не прочь узнать :) Просто если объявлять через static внутри таймера, то он будет изменяться у ВСЕХ таймеров параллельно, что не есть хорошо :) Ну, в общем, как-то так:
    PHP:
    #include <sourcemod> 
    #include <sdktools> 
    #include <cstrike> 

    //new Handle:Enabled; 
    new Handle:RespawnEnabled
    new 
    Handle:RespawnTime

    new 
    Float:g_tClients[MAXPLAYERS+1];

    public 
    OnPluginStart() 

        
    CreateConVar("st_version""1.6""Версия"FCVAR_PLUGIN|FCVAR_SPONLY|FCVAR_REPLICATED|FCVAR_NOTIFY); 
        
    // А зачем тут два одинаковых квара ? :)
        //Enabled = CreateConVar("st_enabled", "1", "0 = Plugin Disabled, 1 = Plugin Enabled"); 
        
    RespawnEnabled CreateConVar("st_respawn",    "1""enabled/disable respawn"); 
        
    RespawnTime CreateConVar("st_respawntime",     "5""Ammount of time to respawn after a user dies"); 
         
        
    HookEvent("player_death"PlayerDeath); 


    public 
    Action:PlayerDeath(Handle:event, const String:name[], bool:dontBroadcast

        if(
    GetConVarInt(RespawnEnabled) == 0
            return 
    Plugin_Continue
             
        new 
    client GetClientOfUserId(GetEventInt(event"userid")); 
        
        
    g_tClients[client] = GetConVarFloat(RespawnTime);
        
    // Создаем повторяющийся таймер :)
        
    CreateTimer(1.0RespawnclientTIMER_REPEAT|TIMER_FLAG_NO_MAPCHANGE)
         
        return 
    Plugin_Continue


    public 
    Action:Respawn(Handle:Timerany:client
    {    
    // Клиент не в игре или уже живой? Останавливаемся!
        
    if(!IsClientInGame(client) && !IsPlayerAlive(client)) 
            return 
    Plugin_Stop
        
        if(--
    g_tClients[client] <= 0){
            
    CS_RespawnPlayer(client); 
            return 
    Plugin_Stop;
        }
        
        
    decl String:Hint[64];
        
    Format(Hintsizeof(Hint), "Вы будете возрождены через %2.f секунд."g_tClients[client]);
        
    PrintHintText(clientHint);

        return 
    Plugin_Continue;
    }  
    Писал на коленке, поэтому может не работать) Критика приветствуется: Сурспавн учу первую неделю, поэтому пока только привыкаю :)
     
  4. san911

    san911 Вообще короче нечего

    Сообщения:
    177
    Симпатии:
    37
    Разве что так...
    PHP:
    #include <sourcemod> 
    #include <cstrike> 

    new Handle:Enabled INVALID_HANDLE
    new 
    RespawnTime[MAXPLAYERS+1]; 

    public 
    OnPluginStart() 

        
    Enabled CreateConVar("st_enabled""1""0 = Plugin Disabled, 1 = Plugin Enabled");
        
    HookEvent("player_death"PlayerDeath); 


    public 
    PlayerDeath(Handle:event, const String:name[], bool:dontBroadcast

        if(
    GetConVarInt(Enabled) == 1)
        {   
            new 
    client GetClientOfUserId(GetEventInt(event"userid"));
            
    CreateTimer(1.0RespawnClientclientTIMER_REPEAT|TIMER_FLAG_NO_MAPCHANGE);
        }


    public 
    Action:RespawnClient(Handle:timerany:client
    {
        if(
    IsClientInGame(client) && !IsPlayerAlive(client)) 
        {
            
    RespawnTime[client]++;
            
            if (
    RespawnTime[client] == 1)
            {
                
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x045 \x01секунд"); 
            } 
            else if (
    RespawnTime[client] == 2)
            { 
                
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x044 \x01секунд"); 
            } 
            else if (
    RespawnTime[client] == 3)
            { 
                
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x043 \x01секунд"); 
            } 
            else if (
    RespawnTime[client] == 4)
            { 
                
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x042 \x01секунд"); 
            } 
            else if (
    RespawnTime[client] == 5)
            { 
                
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x041 \x01секунд"); 
            }
            else if (
    RespawnTime[client] == 6)
            { 
                
    Respawn(client);
                
    RespawnTime[client] = 0;
                return 
    Plugin_Stop;
            }
        }
        else return 
    Plugin_Stop;
        
        return 
    Plugin_Continue


    stock Respawn(client

        new 
    Team GetClientTeam(client); 
        if(
    Team == || Team == 3// 0 - Не существует, 1 - Наблюдатель, 2 - Террорист, 3 - Контер-Террорист.
        
    CS_RespawnPlayer(client); 
    }
     
    /_Parlament_\ нравится это.
  5. SenatoR

    SenatoR Модератор

    Сообщения:
    714
    Симпатии:
    270
  6. AlmazON

    AlmazON деревянный © yand3xmail

    Сообщения:
    4.515
    Симпатии:
    1.969
    [CS:GO/CS:S] Автовозрождение игрока с отображением оставшегося времени

    Оффтоп
    Без особой оптимизации, сам механизм:
    PHP:
    #include <sourcemod> 
    #include <cstrike> 

    #pragma semicolon 1 

    new bool:bEnable
    new 
    RespawnTime;
    new 
    iTimeClient[MAXPLAYERS+1] = {1};

    public 
    OnPluginStart() 

        
    CreateConVar("st_version""1.6""Версия"FCVAR_PLUGIN|FCVAR_SPONLY|FCVAR_REPLICATED|FCVAR_NOTIFY);
        
    decl Handle:convar;
        
    HookConVarChange(convar CreateConVar("st_enabled""1""0 = Plugin Disabled, 1 = Plugin Enabled"_true0.0true1.0), ChangeEnable);
        
    bEnable GetConVarBool(convar);
        
    HookConVarChange(convar CreateConVar("st_respawntime",     "5""Ammount of time to respawn after a user dies"_true0.0), ChangeTime); 
        
    RespawnTime GetConVarInt(convar);
        
    HookEvent("player_death"PlayerDeath); 
    }

    public 
    ChangeEnable(Handle:convar, const String:oldValue[], const String:newValue[]) bEnable GetConVarBool(convar);
    public 
    ChangeTime(Handle:convar, const String:oldValue[], const String:newValue[]) RespawnTime GetConVarInt(convar);

    public 
    PlayerDeath(Handle:event, const String:name[], bool:dontBroadcast

        if(
    bEnable)
        {
            new 
    client GetClientOfUserId(GetEventInt(event"userid"));
            if(
    iTimeClient[client] == 0)
            {
                
    iTimeClient[client] = RespawnTime;
                
    TriggerTimer(CreateTimer(1.0RespawnClientclientTIMER_REPEAT));
            }
        }
    }

    public 
    Action:RespawnClient(Handle:Timerany:client
    {
        if(
    IsClientInGame(client) && GetClientTeam(client) > && IsPlayerAlive(client) == false)
        {
            
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x04%i \x01секунд"iTimeClient[client]);
            if(
    iTimeClient[client]--) return Plugin_Continue;
            
    CS_RespawnPlayer(client);
        }
        
    iTimeClient[client] = 0;
        return 
    Plugin_Stop
    Могут быть нюансы - надеюсь, сам решишь.
     
    Последнее редактирование: 9 июл 2015
    neatek3, Hejter и /_Parlament_\ нравится это.
  7. /_Parlament_\

    /_Parlament_\

    Сообщения:
    135
    Симпатии:
    7
    AlmazON, Мда))
    Вы будете возрождены через 50 секунд
    Вы будете возрождены через 12846 секунд
    Вы будете возрождены через 3288631 секунд
    Вы будете возрождены через 841889582 секунд
    Вы будете возрождены через 775368241 секунд
     
  8. AlmazON

    AlmazON деревянный © yand3xmail

    Сообщения:
    4.515
    Симпатии:
    1.969
    Это какой-то баг форматирования PrintToChat, ибо, как ты заметил, возрождает то через 5 секунд, как и положено, а эта величина напрямую связано с чатом.
    Поправил, теперь можно устанавливать время возрождения, равное 0.
     
  9. White Wolf

    White Wolf [] (int _n) -> double { return (_n % 2) == 0;}); Супер-модератор

    Сообщения:
    1.189
    Симпатии:
    413
    /_Parlament_\, используй цикл for в handler'e таймера. И в таймер передавай клиента.
    Вот тебе как реализовать, только переменную подставь свою.
    PHP:
    for (int i 5>= 0; --i)
    {
      
    PrintToChat(client"Осталось %d"i);
      return 
    Plugin_Continue;
    }
    return 
    Plugin_Stop;
     
  10. AlmazON

    AlmazON деревянный © yand3xmail

    Сообщения:
    4.515
    Симпатии:
    1.969
    Это же цикл, здесь клиентов подставлять можно, но никак не время! Ты получишь несколько сообщений за долю секунды на каждую сработку таймера (до бесконечности) и только.
    Оффтоп
     
  11. /_Parlament_\

    /_Parlament_\

    Сообщения:
    135
    Симпатии:
    7
    AlmazON, У кого нибудь найдется Hammer Editor? Просто в стиме нельзя ничего делать, если кто поможет пишите servers.parlament
     
  12. Hejter

    Hejter Mapper Source Engine

    Сообщения:
    1.771
    Симпатии:
    259
    Что тебе нужно, напиши сюда.
     
  13. neatek3

    neatek3

    Сообщения:
    124
    Симпатии:
    127
    почему в Стиме нельзя ничего сделать?
    там есть hammer editor для игр... и весит мало.

    AlmazON, ну хоть ктото сделал адекватный вывод счётчика в чат хд
    правда создание квар и хук извращенский
    TIMER_FLAG_NO_MAPCHANGE забыл
     
  14. AlmazON

    AlmazON деревянный © yand3xmail

    Сообщения:
    4.515
    Симпатии:
    1.969
    Создание кваров, как это делает один из разработчиков SM.
    Сам пусть улучшает) Тут суть в таймере была - принцип показан.
    Нет. Иначе значения из массива не приравняет к нулю.
     
  15. Серый™

    Серый™ CS:S Server

    Сообщения:
    2.563
    Симпатии:
    1.149
    Код:
    int g_iTime[MAXPLAYERS+1] = 5; // время
    
    CreateTimer(1.0, Timer, iClient, TIMER_REPEAT);
    
    public Action Timer(Handle timer, any iClient)
    {
        if (g_iTime[iClient] > 0 && IsClientInGame(iClient) && IsPlayerAlive(iClient)) 
        {
            PrintHintText(iClient, "%T", "Time", iClient, g_iTime[iClient]);
            g_iTime[iClient]--;
            return Plugin_Continue; 
        }
        else
        {
            g_iTime[iClient] = 5;
            //код на исполнение на конец таймера
            return Plugin_Stop;
        }
    }
    
    
    
     
  16. AlmazON

    AlmazON деревянный © yand3xmail

    Сообщения:
    4.515
    Симпатии:
    1.969
    Серый™, требовалось:
    А у тебя такого сообщения уже не покажет. Оптимизация g_iTime[iClient] > 0 оказалась ни при делах.
    И, главная ошибка (неточность):
    Значение устанавливается после вызова функции таймера. А если квар изменят?! Таймер у всех ещё раз проработает по старому интервалу респавна.
     
  17. /_Parlament_\

    /_Parlament_\

    Сообщения:
    135
    Симпатии:
    7
    Вот как то так)) Будут обновы Оффтоп
     
  18. DarklSide

    DarklSide

    Сообщения:
    680
    Симпатии:
    173
    /_Parlament_\, добавил склонение:
    PHP:
    #include <sourcemod> 
    #include <cstrike> 
    #pragma semicolon 1 

    new bool:bEnable true;

    new 
    RespawnTime 0
    iTimeClient[MAXPLAYERS 1] =  { 0, ... };

    new const 
    String:sbs[][] =  { "у""ы""" };

    public 
    OnPluginStart()
    {
        
    CreateConVar("st_version""1.6""Версия"FCVAR_PLUGIN FCVAR_SPONLY FCVAR_REPLICATED FCVAR_NOTIFY);
        new 
    Handle:convar;
        
    HookConVarChange(convar CreateConVar("st_enabled""1""0 = Plugin Disabled, 1 = Plugin Enabled"_true0.0true1.0), ChangeEnable);
        
    bEnable GetConVarBool(convar);
        
    HookConVarChange(convar CreateConVar("st_respawntime""5""Ammount of time to respawn after a user dies"_true0.0), ChangeTime);
        
    RespawnTime GetConVarInt(convar);
        
    RespawnTime++;
        
    CloseHandle(convar);
        
    HookEvent("player_death"PlayerDeath);
    }

    public 
    ChangeEnable(Handle:convar, const String:oldValue[], const String:newValue[])
    {
        
    bEnable GetConVarBool(convar);
        if (
    bEnable)HookEvent("player_death"PlayerDeath);
        else 
    UnhookEvent("player_death"PlayerDeath);
    }

    public 
    ChangeTime(Handle:convar, const String:oldValue[], const String:newValue[])
    {
        
    RespawnTime GetConVarInt(convar);
        
    RespawnTime++;
    }

    public 
    PlayerDeath(Handle:event, const String:name[], bool:dontBroadcast)
    {
        new 
    client GetClientOfUserId(GetEventInt(event"userid"));
        
    iTimeClient[client] = RespawnTime;
        if (
    iTimeClient[client])
        {
            
    CreateTimer(1.0RespawnClientclientTIMER_REPEAT TIMER_FLAG_NO_MAPCHANGE);
        }
        else 
    CreateTimer(0.1RespawnClientclientTIMER_FLAG_NO_MAPCHANGE);
    }

    declin(time)
    {
        if (
    time 10 && time 20)return 2;
        new 
    timeo time 10;
        switch (
    timeo)
        {
            case 
    234:return 1;
            case 
    1:return 0;
        }
        return 
    2;
    }

    public 
    Action:RespawnClient(Handle:Timerany:client)
    {
        if (
    IsClientInGame(client) && GetClientTeam(client) > && !IsPlayerAlive(client))
        {
            if (--
    iTimeClient[client])
            {
                
    PrintToChat(client"\x01Вы будете \x04возрождены \x01через \x04%d \x01секунд%s"iTimeClient[client], sbs[declin(iTimeClient[client] % 100)]);
                return 
    Plugin_Continue;
            }
            else 
    CS_RespawnPlayer(client);
        }
        return 
    Plugin_Stop;
    }

    P.S.: возрождение через 0: (iTimeClient[client]--)
     
  19. Серый™

    Серый™ CS:S Server

    Сообщения:
    2.563
    Симпатии:
    1.149
    AlmazON, я скинул для примера и без учёта квара.
     
  20. AlmazON

    AlmazON деревянный © yand3xmail

    Сообщения:
    4.515
    Симпатии:
    1.969
    Серый™, ещё не учтено, что таким кодом можно запустить не один таймер, если за 1 секунду успеть возродиться и умереть.
    Это ещё что? Если нужно добавить единицу, так и добавь сразу.
    Квар закрывать необязательно, зря дописал.
    Ошибки в логах будут (у некоторых) + можно запустить 2 и более хука.