Idõzítõk Mik azok az idõzítõk?Az idõzítõk( avagy
timer-ek ) olyan egységei a programnak, amiknek segítségével lehetõségünk van függvényeket meghívni
tetszõleges idõ múlva, vagy ezeket
ismételni opcionális idõközönként. Kezelésük nagyon egyszerû, és ugyanakkor nagyon fontos részei a kódunknak, biztosra veszem, hogy mindenki hasznlálja is õket. Nézzük meg õket részletesebben.
MûködéseAz idõzítõk kezelésére
3 függvény áll a rendelkezésünkre, ami bõven elegendõ a feladataink ütemezéséhez. Most mindegyiken végigmegyünk részletesen.
A \'SetTimer\' függvényA
SetTimer függvény segítségével
indíthatunk el idõzítõket.
Paraméterei:
funcname[ ]: Sztring típusú paraméter, a meghívni kívánt függvény nevét kell megadnunk.
interval: Integer( egész szám ) típusú paraméter, a meghívás és a lefutás közti idõt jelöli milimásodpercben(!).
repeating: Ugyan integer típusú paraméter ez is, de csak két érték a fontos; Ha 0( false ), akkor nem ismétlõdik, ha 1( true ), akkor ismétlõdni fog( amíg le nem állítjuk ).
Nézzünk pár példát! Elsõnek csinálunk egy idõzítõt, ami 5 másodpercenként ír egy x betût a konzolba.
#include < a_samp >
//Prototípus létrehozása
public myFunc( );
public OnFilterScriptInit( ) {
//Idõzítõ inicializálása
SetTimer( \"myFunc\", 5000, true );
return 1;
}
//A \'myFunc\' nevû függvény kiír egy x-et a konzolba( minden lefutásnál )
public myFunc( ) { print( \"x\" ); }
Ez a kis kód szépen elírogat magának a
végtelenségig. De mi van akkor, ha nekünk ismétlõdõ timer-re van szükségünk, de
nem akarjuk a végteleségig futtatni, csak mondjuk 10-szer? Fel kell címkéznünk az idõzítõnket:
#include < a_samp >
//Változó létrehozása az idõzítõnknek, és a számlálónak
new myTimer;
new myCounter;
//Prototípus létrehozása
public myFunc( );
public OnFilterScriptInit( ) {
//Idõzítõ inicializálása + felcímkézése
myTimer = SetTimer( \"myFunc\", 5000, true );
return 1;
}
//A \'myFunc\' nevû függvény kiír egy x-et a konzolba( minden lefutásnál ), és növeli a \'myCounter\' értékét
public myFunc( ) {
//Ha már 5-ször lefutott az eljárásunk, akkor leállítjuk az idõzítõnket
if( myCounter == 5 ) return KillTimer( myTimer );
//Ellenkezõ esetben folytatjuk a mûveletünket
print( \"x\" );
++myCounter;
return 1;
}
A \'KillTimer\' függvényAz elõzõ példában már szerepelt a
KillTimer függvény, a szerepe az idõzítõ
leállítása. Nyilván ebbõl világossá válik számunkra, hogy ezt csak
ismétlõdõ idõzítõknél használjuk.
Paramétere:
timerid: Integer típusú paraméter, a leállítani kívánt idõzítõnk azonosítóját kell megadni.
Nem írok erre külön példát, nézd át az elõzõt mégegyszer, és gondold végig a folyamatot!
A \'SetTimerEx\' függvényA
SetTimerEx függvény szerepe ugyanaz, mint a
SetTimer-é; Meghív egy eljárást. De itt rendelkezésünkre áll még egy paraméter, amivel tetszõleges értékeket( integer, float, sztring, ... ) adhatunk át a meghívott függvénynek.
Paraméterei:
funcname[ ]: Sztring típusú paraméter, a meghívni kívánt függvény nevét kell megadnunk.
interval: Integer( egész szám ) típusú paraméter, a meghívás és a lefutás közti idõt jelöli milimásodpercben(!).
repeating: Ugyan integer típusú paraméter ez is, de csak két érték a fontos; Ha 0( false ), akkor nem ismétlõdik, ha 1( true ), akkor ismétlõdni fog( amíg le nem állítjuk ).
format[ ]: Sztring típusú paraméter, az átadni kívánt adat típusának megfelelõ betûjelet kell megadnunk( lentebb ).
{Float,_}:...: Az elõzõ paraméterhez kapcsolódik, az átadni kívánt adatot kell megadni.
Nézzünk erre egy konkrét példát! Amikor egy játékos beér egy checkpoint-ba, akkor 3 másodperc múlva kap egy üzenetet( csak õ! ):
#include < a_samp >
#define COLOR_GREEN 0x00FF00AA
public OnPlayerEnterCheckpoint( playerid ) {
//Meghívjuk a \'checkpointMessage\' függvényt a játékos azonosítójával paraméterként( azaz CSAK NEKI küld üzenetet )
SetTimerEx( \"checkpointMessage\", 3000, false, \"i\", playerid );
return 1;
}
public checkpointMessage( id );
public checkpointMessage( id ) {
SendClientMessage( id, COLOR_GREEN, \"Gratulálok, hogy megértetted az idõzítõk mûködését!\" );
}
És végül, ahogy ígértem, a karakterek, amiket a SetTimerEx függvénynél használhatunk:
i,d: Integer/decimális, azaz egész típusú szám( PL: 1342453326945 )
f: Float( lebegõpontos ), azaz tört típusú szám( PL: 3.14 )
s: Sztring, azaz karakterlánc( PL: \"kutya\" )
a: Array, azaz tömb, aminek a következõ paramétere egész típusú kell legyen, ami a tömb méretét jelöli
b: Boolean, azaz logikai érték( 0/1 | true/false )
Ennyi lenne ez a leírás, ha valami kérdés van, tedd fel itt a témában, és igyekszem rá válaszolni.
Szép leírás, grat!
Ha jól tudom, az elsõ példát, mikor kiír egy \'x\' betût a konzolba sokkal könnyebben is meglehet oldani.
public OnFilterScriptInit()
{
SetTimer(\"print(\"x\")\",5000,true);
return 1;
}
Szép leírás Zero. :)
Szép leírás, grat!
Ha jól tudom, az elsõ példát, mikor kiír egy \'x\' betût a konzolba sokkal könnyebben is meglehet oldani.
public OnFilterScriptInit()
{
SetTimer(\"print(\"x\")\",5000,true);
return 1;
}
ilyent meg nem lehet
Akkor rosszul tudtam. :D
Köszönöm a dicséreteket.
Szép leírás barátom. :)
Szép leírás barátom. :)
Kösz. :angel:
Ezer köszönet :) Mégegy tökéletes leírás mostmár a settimerexet is vágom :P
Örülök, ha segített. :angel:
Egy kis félreírás: a prototípust forward statementtel hozod létre, nem public-cal.
(Egy kis félreírás: )a prototípust forward statementtel is létrehozhatod, de public-cal is.
Szép leírás!
És akkor mi van, ha csinálok egy olyan timert ami csak egyszer fut le és nem állítom le ? ( KillTimer-el )
Semmi, azt nem kell leállítani, mivel csak egyszer fut le, aztán automatikusan leállítja a futását. ;)
Egy éves bump.
Nemrég Slice készített egy scriptet, amivel pontosabbá teszi a timereket.
Szerintem ezt nagyon érdemes használni, mivel ittvan egy kép, hogy mennyire pontosak alapból a timerek.
http://www.nm-ss.tarhely.biz/SAMP/ServerUpdate/1.8/SetTimer_Pontos.jpg[/img]
http://forum.sa-mp.com/showthread.php?t=289675
Love it. Lehet hogy tévedek, de
[pawn]
#emit PUSH.S iArgCount
#emit SYSREQ.C CallLocalFunction
iArgCount += 4;
#emit LCTRL 4
#emit LOAD.S.alt iArgCount
#emit ADD
#emit SCTRL 4
// [ STK ] = PRI / ALT, STK = STK - Ez nem kéne?
#emit PUSH.PRI
[/pawn]
Én csak egyvalamit nem értek, hogy elõször meghívja a függvényt és és a timerber megadott idõtartaming azt csinálja ami a függvénybe van, vagy indít egy idõzítõd és az adott idõ után meghívja a függvényt?
forward probatimer(playerid);
CMD:proba(playerid, params[])
{
SetTimerEx(\"probatimer\", 9000, false, \"i\", playerid);
SendClientMessage(playerid, -1, \"A timer elindult\");
return 1;
}
public probatimer(playerid)
{
SendClientMessage(playerid, -1, \"A timer lefutott\");
return 1;
}
Tehát az utolsó meglátásod a helyes (indít egy idõzítõd és az adott idõ után meghívja a függvényt)
forward probatimer(playerid);
CMD:proba(playerid, params[])
{
SetTimerEx(\"probatimer\", 9000, false, \"i\", playerid);
SendClientMessage(playerid, -1, \"A timer elindult\");
return 1;
}
public probatimer(playerid)
{
SendClientMessage(playerid, -1, \"A timer lefutott\");
return 1;
}
Tehát az utolsó meglátásod a helyes (indít egy idõzítõd és az adott idõ után meghívja a függvényt)
Lefut. De timer által meghívott eljárásba nem kell visszatérés.
forward probatimer(playerid);
CMD:proba(playerid, params[])
{
SetTimerEx(\"probatimer\", 9000, false, \"i\", playerid);
SendClientMessage(playerid, -1, \"A timer elindult\");
return 1;
}
public probatimer(playerid)
{
SendClientMessage(playerid, -1, \"A timer lefutott\");
}
Igen, igazad van. Én néztem el.
Sziasztok! Nekem a timerrel kapcsolatban a következõ kérdésem lenne:
Szeretnék egy admin jail scriptet írni (már megírtam nagyjából), Egy Timerrel oldottam meg hogy ha beteszem 10 mpre akkor 10 mp után dobja ki vh elé.
A következõ lenne a probléma. Ha kilép az illetõ akkor a timert nem menti el. Azt tudom hogy egy adattározó programmal kell elmenteni, de nem tudom \"kinyerni\" a hátralévõ idõt. Erre kéne valami ötlet, hogy hogyan tudnám kinyerni a hátralévõ idõt?
Ha bárki tud bármit mondani azt nagyon megköszönném!
Üdv.Klmos