Liikkuvat laatat

Home » Blogi » Liikkuvat laatat

Kokoontukaa, pojat ja tytöt, tänään aion kertoa teille pienen tarinan laattojen siirtämisestä. Jotkut teistä saattavat tuntea sen jo nimellä “liikkuva alusta”, älkää antako nimen hämätä, se on edelleen sama suloinen asia.

Kerran, kauan sitten, laattapohjaisten pelien maassa, asui nuori laatta. Hän oli onnellinen laatta. Eräänä kauniina päivänä sankari tuli hänen luokseen ja kysyi: “Nuori laatta, miksi et liiku?”

“En tiedä kuinka liikkua”, sanoi pieni laatta.

“Se on surullista”, sankari huokaisi, “koska haluaisin seistä sinun päälläsi ja muuttaa kanssasi paikkoihin, joihin en pääse omin käsin.”

Sinä päivänä nuori laatta tajusi, ettei hänen elämänsä ollut enää niin onnellista.

Mutta voimme auttaa häntä liikkumaan.

Ennen kuin aloitamme koodauksen, meidän on tehtävä joitain sääntöjä. Vaikka säännöt ovat ärsyttäviä, ne ovat erittäin hyödyllisiä. Mitä me teemme? minne mennä? Mikä on elämän tarkoitus? Vastaussäännöt:

* liikkuvat laatat ovat pilvityyppisiä (selvitys löytyy täältä)

* Liikkuvat laatat voivat liikkua vaaka- ja pystysuunnassa

* sankari voi laskeutua liikkuvalle laatalle vain ylhäältä

* Kun sankari seisoo liikkuvan laatan päällä, hän liikkuu laatan mukana

* liikkuvan laatan sankari ei silti voi mennä seinään

Liikkuvan laatan päälle astuminen

Joten kuinka sankari voi laskeutua liikkuvalle laatalle. Ensimmäinen ja yksinkertaisin tapa on hypätä.

Kuvassa sankari liikkuu alaspäin ja seuraavassa vaiheessa hän olisi liikkuvan laatan sisällä. Asetamme hänet seisomaan laatan päälle. Huomaa, että sankarin TÄYTYY olla liikkuvan laatan yläpuolella ja sankarin TÄYTYY liikkua alaspäin. Muussa tapauksessa sankari ei laskeudu liikkuvalle laatalle.

Mutta se ei ole ainoa tapa sankarille päästä liikkuvalle laatalle. Seuraavassa kuvassa sankari seisoo paikallaan seinän päällä eikä liiku mihinkään.

Mutta liikkuva laatta liikkuu ylöspäin ja seuraavassa vaiheessa sankari olisi liikkuvan laatan sisällä. Kyllä, meidän on jälleen varmistettava, että sankari jää kiinni liikkuvaan laattaan ja hän alkaa liikkua ylöspäin liikkuvan laatan mukana.

Pois astuminen

Kun sankari seisoo liikkuvan laatan päällä, meidän on myös luotava tapoja, joilla sankari pääsee pois. Ensinnäkin hän voi hypätä pois. Hän voi kävellä liikkuvan laatan reunan yli. Ja myös pari mahdollista tilannetta on olemassa seuraavissa kuvissa:

Kun sankari seisoo liikkuvan laatan päällä liikkuvan ylöspäin ja seuraavassa vaiheessa sankari osuisi yllä olevaan seinään, hänen tulee pudottaa liikkuva laatta tai hänet puristuisi. Kun sankari seisoo liikkuvan laatan päällä ja liikkuu vaakatasossa ja osuu seinään vasemmalle/oikealle seuraavassa vaiheessa, hänet tulee sijoittaa lähelle seinää ja jos liikkuva laatta jatkaa liikkeessä, sankarin tulee pudota.

Tässä kuvassa sankari liikkuu alas seisoessaan liikkuvan laatan päällä. Kun sankari osuu seinälaattaan, hänen tulee pysyä seinällä. Liikkuva laatta jatkaa laskuaan, mutta ilman sankaria.

Valmistellaan

Piirrä liikkuva laatta elokuvaleike. Sinulla voi olla monia erilaisia ​​liikkuvia laattoja, laita ne eri kehyksiin “liikkuvien” mc:n sisään. Varmista, että kirjaston mc on linkitetty nimellä “liikkuvat tiilet”.

Ilmoita liikkuvat objektit:

game.MovingTilep1= funktio () {};

game.MovingTilep1.prototype.speed=2;

game.MovingTilep1.prototype.dirx=0;

game.MovingTilep1.prototype.diry=1;

peli.MovingTilep1.prototype.miny= 0;

game.MovingTilep1.prototype.maxy=2;

game.MovingTilep1.prototype.width=game.tileW/2;

peli.MovingTilep1.prototype.height=peli.tileH/2;

game.MovingTilep2= funktio () {};

game.MovingTilep2.prototype.speed=2;

game.MovingTilep2.prototype.dirx=1;

game.MovingTilep2.prototype.diry=0;

peli.MovingTilep2.prototype.minx= -2;

game.MovingTilep2.prototype.maxx=2;

game.MovingTilep2.prototype.width=game.tileW/2;

game.MovingTilep2.prototype.height=game.tileH/2;

Meillä on kahdenlaisia ​​liikkuvia laattoja: MovingTilep1 liikkuu pystysuunnassa (sen diry-ominaisuuden arvo on nollasta poikkeava) ja MovingTilep2 on vaakasuora liikkuja (koska sen dirx on asetettu niin). Nopeusominaisuus, kuten olet jo arvannut, määrittää kuinka monta pikseliä laatta liikkuu kussakin vaiheessa.

Miny/maxy/minx/maxx-ominaisuudet asettavat liikkeen rajat. Voisimme kirjoittaa myös joitain absoluuttisia arvoja, mutta silloin muutosten tekeminen on hämmentävää. Sen sijaan rajat on asetettu suhteessa liikkuvan laatan aloituspaikkaan. Voimme asettaa liikkuvan laatan mihin tahansa asentoon ja se liikkuu silti oikein rajojensa välillä. Muista, että siirrettävät laatat eivät tarkista seinälaattoja, ja sinun tehtäväsi on sijoittaa ne niin, etteivät ne liiku seinien läpi. Tai aseta ne niin, että ne liikkuvat seinien läpi, jos haluat niin. Teet peliä, joten olet jumala.

Katsotaanpa esimerkkiä. Movingtile alkaa paikasta x=2, y=5. Siinä on pystysuuntainen liike ja miny=-1, maxy=4. Kuinka pitkälle se sitten liikkuu? Alkaen y-miny=5+(-1)=4, joten minimipaikka, johon se menee, on x=2, y=4. Maksimipaikka on 5+4=9 tai asema x=2, y=9.

Liikkuvien laattojen aloitusasennon antamiseksi käytämme vihollisten taulukon kaltaista taulukkoa:

//liikkuvat laatat -taulukko on järjestyksessä [tile type, xtile, ytile]

myMovingTiles = [

[0],

[[1, 4, 2]],

[[2, 4, 4]]

];

Kartassa1 olemme ilmoittaneet 1 liikkuvan laatan. Sen tyyppi 1 (tehty mallista MovingTile1) ja se on sijoitettu alkuasentoon x=4, y=2. Map2:ssa on myös vain yksi liikkuva laatta. Voit laittaa enemmän kuin yhden liikkuvan laatan jokaiseen karttaan.

Seuraavaksi meidän on lisättävä liikkuvat laatat buildMap-toimintoon. Kirjoita vihollisen koodin jälkeen:

game.movingtiles = myMovingTiles[game.currentMap];

for (var i = 0; i<peli.movingtiles.length; ++i) {

var nimi = “liikkuva”+i;

peli[nimi]= uusi peli[“MovingTilep”+game.movingtiles[i][0]];

game.clip.attachMovie(“liikkuvat”, nimi, 12001+i);

peli[nimi].clip=peli.leike[nimi];

peli[nimi].clip.gotoAndStop(game.movingtiles[i][0]);

peli[nimi].xtile = peli.movingtiles[i][1];

peli[nimi].ytile = peli.movingtiles[i][2];

peli[nimi].x = peli[nimi].xtile *peli.tileW+peli.tileW/2;

peli[nimi].y = peli[nimi].ytile *peli.tileH+peli.tileH/2;

peli[nimi].leike._x = peli[nimi].x;

peli[nimi].leike._y = peli[nimi].y;

peli[nimi].minx=peli[nimi].minx+peli[nimi].xtile;

peli[nimi].maxx=peli[nimi].maxx+peli[nimi].xtile;

peli[nimi].miny=peli[nimi].miny+peli[nimi].ytile;

peli[nimi].maxy=peli[nimi].maxy+peli[nimi].ytile;

}

Otamme nykyisen kartan taulukon liikkuvasta laattaryhmästä. Muuttuva game.movingtiles pitää sisällään tietoa kuinka monta liikkuvaa laattaa meillä on lavalla ja mistä ne alkavat. Sitten luomme uuden objektin, asetamme mc:n lavalle oikeaan asentoon ja lähetämme sen oikeassa kehyksessä. Huomaa, että tyyppi1 liikkuva ruutu lähetetään kehykseen 1, tyyppi2 kehykseen2. Koodin viimeinen osa laskee arvot kunkin liikkuvan laatan rajojen arvot. Vaikka nimet ovat jälleen miny/max/minx/maxx, ominaisuudet eivät ole enää suhteellisia. Jokaisella liikkuvalla laattaobjektilla on absoluuttiset arvot rajoilleen, joten meidän ei tarvitse laskea niitä jatkuvasti tarkistaaksemme, onko aika kääntyä takaisin.

MoveChar-funktiossa meidän on lisättävä 1 rivi alkuun tallentaaksemme nykyisen y-paikan:

ob.lasty=ob.y;

Meidän on myös kirjoitettava koodi uudelleen moveChar-funktiossa liikkuaksesi alaspäin

if (diry == 1) {

if (ob.downleft ja ob.downright ja !checkMovingTiles(speed*diry)) {

ob.y += nopeus*diry;

} muu {

ob.jump = false;

if(ob.onMovingTile){

ob.y=ob.onMovingTile.y-ob.onMovingTile.height-ob.height;

}muu{

ob.y = (ob.ytile+1)*game.tileH-ob.height;

}

}

}

Olemme lisänneet kutsun checkMovingTiles-funktiolle, joka palauttaa tosi, jos sankari laskeutuu liikkuvalle laatalle. Ja jos olemme laskeutuneet sen päälle, asetamme sankarin y-koordinaatin niin, että se on juuri laatan yläpuolella.

Onko sankari liikkuvassa laatassa?

Arvasit jo MoveChar-funktion lisäyksen perusteella, kyllä, nyt on aika tehdä uusi toiminto tarkastaakseen seisooko char liikkuvalla laatalla. checkMovingTiles-toiminto ei vain löydä vastausta, vaan se myös tallentaa eteenpäin liikkuvan laattasankarin nimen char-objektiin.

function checkMovingTiles (y) {

if(char.diry<>-1){

var heroymax=char.y+char.height+y;

var heroxmax=char.x+char.width;

var heroxmin=char.x-char.width;

foundit=false;

for (var i = 0; i<peli.movingtiles.length; i++) {

var ob=peli[“liikkuva”+i];

var tileymax=ob.y+ob.height;

var tileymin=ob.y-ob.height;

var tilexmax=ob.x+ob.width;

var tilexmin=ob.x-ob.width;

if(char.lasty+char.height<=tileymin){

if (heroymax<=tileymax ja heroymax>=tileymin) {

jos (heroxmax>tilexmin ja heroxmax<tilexmax) {

char.onMovingTile=ob;

löytyi = tosi;

tauko;

} else if (heroxmin>tilexmin ja heroxmin<tilexmax) {

char.onMovingTile=ob;

löytyi = tosi;

tauko;

}

}

}

}

paluu(foundit);

}

}

Katsotaan mitä täällä tapahtuu. Jos char ei liiku ylöspäin (diry ei ole -1), laskemme merkin rajat. Sitten alamme kiertää kaikki liikkuvat laatat. ob tulee siirtämään käsittelemäämme laattaobjektia. Laskemme myös rajat nykyiselle laatalle selvittääksemme, törmäävätkö ne toisiinsa:

“Lasty”-ominaisuuden omaava if-lause varmistaa, että merkin viimeinen sijainti oli liikkuvan ruudun yläpuolella ja muut if-lauseet löytävät törmäyksen merkin ja ruudun välillä. Jos olemme löytäneet liikkuvan ruudun, onMovingTile pitää viittauksen laattaobjektiin.

Se liikkuu

Ole valmis ihmiskunnan historian rumimpaan, suurimpaan, ilkeimpään tehtävään! Se on iso, koska se tekee monia asioita, ensin se liikkuu kaikkien liikkuvien laattojen ympäri, sitten tarkistaa, tarvitseeko laattojen liikesuuntaa päinvastaiseksi, ja jos se ei ole tarpeeksi kovaa työtä, tämä toiminto käsittelee myös sankarin liikkeet seisoo liikkuvan laatan päällä ja tarkistaa, putoaako sankari siltä.

function moveTiles () {

for (var i = 0; i<peli.movingtiles.length; i++) {

var ob=peli[“liikkuva”+i];

getMyCorners (ob.x + ob.speed*ob.dirx, ob.y + ob.speed*ob.diry, ob)

if (ob.miny>ob.upY tai ob.maxy<ob.downY) {

ob.diry=-ob.diry;}

if (ob.minx>ob.leftX tai ob.maxx<ob.rightX) {

ob.dirx=-ob.dirx;

}

ob.x = ob.x + ob.speed*ob.dirx;

ob.y = ob.y + ob.speed*ob.diry;

ob.xtile = Math.floor(ob.x/peli.tileW);

ob.ytile = Math.floor(ob.y/peli.tileH);

ob.clip._x = ob.x;

ob.clip._y = ob.y;

if(ob.diry==-1){

checkMovingTiles(0);

}

}

//tarkista, onko sankari liikkuvassa ruudussa

if(char.onMovingTile){

getMyCorners (char.x, char.y+char.onMovingTile.speed*char.onMovingTile.diry, char);

if (char.onMovingTile.diry == -1) {

if (char.upleft ja char.upright) {

char.y=char.onMovingTile.y-char.onMovingTile.height-char.height;

} muu {

char.y = char.ytile*game.tileH+char.height;

char.jumpspeed = 0;

char.jump = tosi;

char.onMovingTile=false;

}

}

if (char.onMovingTile.diry == 1) {

if (char.downleft ja char.downright) {

char.y=char.onMovingTile.y-char.onMovingTile.height-char.height;

} muu {

char.onMovingTile=false;

char.y = (char.ytile+1)*game.tileH-char.height;

}

}

getMyCorners (char.x+char.onMovingTile.speed*char.onMovingTile.dirx, char.y, char);

if (char.onMovingTile.dirx == -1) {

if (char.downleft ja char.upleft) {

char.x += char.onMovingTile.speed*char.onMovingTile.dirx;

} muu {

char.x = char.xtile*game.tileW+char.width;

pudota (char);

}

}

if (char.onMovingTile.dirx == 1) {

if (char.upright ja char.downright) {

char.x += char.onMovingTile.speed*char.onMovingTile.dirx;

} muu {

pudota (char);

char.x = (char.xtile+1)*game.tileW-char.width;

}

}

updateChar (char);

}

}

No, kuten aiemmin kerrottiin, ensimmäinen osa siirtää liikkuvia laattoja. Se käy läpi kaikki liikkuvat laatat ja vertaa niiden seuraavaa sijaintia miny/maxy/minx/maxx-ominaisuuksiin. Jos liikkuva laatta on siirtynyt liian pitkälle, sen liike käännetään.

Seuraavalla koodilla:

if(ob.diry==-1){

checkMovingTiles(0);

}

tarkistamme, olemmeko saaneet sankarin. Huomaa, että tämä on mahdollista vain, jos sankari seisoo paikallaan seinän reunalla ja laatta liikkuu ylöspäin (diry on -1).

Funktion osa riviltä:

if(char.onMovingTile){

käsittelee sankaria. Kun onMovingTile-ominaisuus ei ole epätosi, se tarkoittaa, että char seisoo yhdellä niistä ja sen onMovingTile viittaa oikeaan liikkuvaan laattaobjektiin. Tässä oleva koodi on hyvin samanlainen kuin MoveChar-toiminnon koodi. Laskemme kulmat sankarin seuraavalle paikalle getMyCorners-funktiolla, jos emme ole törmänneet mihinkään seinään, siirrämme sankaria laatalla, mutta jos kova seinä on löydetty, sankari ei pääse liikkumaan sinne.

Käärien sen

DetectKeys-funktiossa lisää rivi alkuun siirtääksesi kaikki laatat ennen kuin sankarikin saa mahdollisuuden liikkua:

moveTiles();

ja jos sankari hyppää, meidän on asetettava sen onMovingTile-ominaisuus arvoon false:

ob.onMovingTile=false;

Ja kun sankari liikkuu vasemmalle tai oikealle näppäintä painettaessa, tarkista liikkuvat laatat:

if (!checkMovingTiles(1)) {

char.onMovingTile = false;

}

Bugikorjaus

Duncan löysi vian vaakatasossa liikkuvasta laattasta. Kun kävelit siitä suoraan seinälaatan päällä, hiilty ei havainnut olevansa pois liikkuvalta laatalta ja jatkoi liikkumista laatan mukana. Tarkista liikkuvat laatat, kun painat vasenta tai oikeaa näppäintä tämän välttämiseksi.