Még egy számítgatós lecke tõlem...
A lecke lényege: Egy játékos (de lehet akár pont is) körül egy kör formának a pozícióit kiszámolgatjuk.
Feltétlennül szükséges függvények:
- floatsin
- floatcos
Rövid lesz.
Elõször is lekérjük a játékos nézetét. Ha pontról van szó, és nem játékosról, akkor csak szimplán megadjuk ezt 0-nak.
new Float:a;
GetPlayerFacingAngle(playerid,a);
Pont esetén csak: new Float:a = 0;
Lekérjük a játékos pozícióját. Pont esetében a pozíció adott.
new Float:P[3]; //Lebegõpontos tömb a pozícióhoz
GetPlayerPos(playerid,P[0],P[1],P[2]); //Lekérés
Pontnál csak tudni kell a koordinátákat, és belehelyezni egy ugyanilyen tömbbe, de nem muszály.
Most jön a lényeg. Az X pozíciónak a Szinuszát kiszámítjuk a játékos nézetével. Az Y pozíciónak pedig a Kosziniszát számoljuk ki, szintén a játékos nézetének segítségével. Ezzel megkapjuk a játékos elõtti pozíciót. Esetleg megszorozhatjuk valamennyivel, hogy távolabb legyen. Ezt függvénybe helyezzük. Példának most a játékost a körbe fogjuk mozgatni, a kezdõ pozíciójától kezdve.
SetPlayerPos(playerid,P[0] - 2 * floatsin(-a,degrees), P[1] - 2 * floatcos(-a,degrees), P[2]);
A struktúra a következõ: Pozíció (változó) - távolság * szögfüggvény(a nézet ellentetje, számolási módszer)
FIGYELMEZTETÉS: Mivel most kivonunk, így minél nagyobb számmal szorzod a számítást, annál KÖZELEBB lesz a távolság!
Magyarul elõször megszorozzuk a távolsággal a kiszámolt pozíciót, ami a nézethez képest elõl van, majd a játékos koordinátájának egy elemébõl (tehát X, és aztán Y) kivonjuk ezt.
És ezt mind egy timerrel kell csinálni, vagy akár ciklussal, mikor hogy. Már a pozíció beállítását is abban kell.
A pozíció beállítása után úgymond megváltoztatjuk a játékos nézetét, de mégsem. Csak a VÁLTOZÓJÁNAK az értékét fogjuk. (ugyanabban a ciklusban, timerben)
FIGYELMEZTETÉS: Mint mondtam, NEM KÉRJÜK LE ÚJRA, csak a változó értékét megváltoztatjuk, a játékosnak meg NEM változtatjuk a nézetét, csak a VÁLTOZÓÉT (tehát csak egyszer kellett lekérni, azt eltároltuk már).
a += 1;
A nézet változójához hozzáadtunk egyet. 0.5-el sokkal simább a kör, de több idõt is igényel, ráadásul most egész számmal számoljunk inkább.
És ezután újra beállítjuk, de ezt egy ciklus, timer segítségével. Tehát, NEM írjuk be újra a SetPlayerPos -t, hanem csak lefuttatjuk újra a ciklust amibe már beleírtuk (vagy esetleg timer).
Ha ciklust használunk, és 1-el növeljük mindig a nézetünk értékét, akkor célszerû a ciklus feltétel értékét 360-ra állítani, mivel ugyebár 360 fokos egy kör, és 360 pont kell gyakorlatilag, tehát 360x kell számolnunk
.
for(new f=0; f < 360; f++) //Ciklus létrehozása
{
//a nemrég említett SetPlayerPos, ugyanazokkal a számításokkal
SetPlayerPos(playerid,P[0] - 2 * floatsin(-a,degrees), P[1] - 2 * floatcos(-a,degrees), P[2]);
a += 1; //hozzá adunk egyet a nézet változójához, így \"félig\" megadtuk a következõ pozíciót
}
Timernél szinte ugyanez, csak ott az idõt is meg kell adnunk, és meg kell néznünk, hogy 360-at elérte-e már a változónk.
public MovePlayer(playerid)
{
//a nemrég említett SetPlayerPos, ugyanazokkal a számításokkal
SetPlayerPos(playerid,P[0] - 2 * floatsin(-a,degrees), P[1] - 2 * floatcos(-a,degrees), P[2]);
//ha 360-at elérte a változó, megszakítjuk a timert, hogy ne számoljon feleslegesen tovább
if(a >= 360) return KillTimer(timer),0;
a += 1; //hozzá adunk egyet a nézet változójához, így \"félig\" megadtuk a következõ pozíciót
És persze be kell állítanunk az idõzítõt, de fontos hogy adjunk neki azonosítót, hogy ki tudjuk iktatni, ha már nem kell. A timer idejét annyira állítsátok, amilyen gyakran akarjátok, hogy lépegessen.
timer = SetTimerEx(\"MovePlayer\",1000,1,\"i\",playerid);
Ennyi lenne errõl, szerintem eléggé érthetõ.