IOS-i mängude arendamine võib olla rikastav kogemus nii isikliku kui ka rahaline kasvu. Selle aasta alguses võtsin kasutusele Cocos2D-põhise mängu, Mesilaste võistlus , App Store'i. Selle mäng on lihtne: lõpmatu jooksja, kus mängijad (antud juhul mesilased) koguvad punkte ja väldivad takistusi. Vaata siin demo jaoks.
Selles õpetuses selgitan iOS-i mängude arendamise protsessi, alates Cocos2D-st kuni avaldamiseni. Siit leiate lühikese sisukorra:
Enne kui jõuame üksikasjadeni, on kasulik mõista nende vahet spritid ja füüsilised esemed.
Iga üksuse jaoks, mis kuvatakse lõputu jooksumängu ekraanil, nimetatakse selle üksuse graafilist kujutist kui spriit , samas kui selle üksuse hulknurkset kujutist füüsikamootoris nimetatakse a füüsiline objekt .
Niisiis joonistatakse sprite ekraanile, mille taga on vastav füüsiline objekt, mida seejärel haldab teie füüsikamootor. Seda seadistust saab siin visualiseerida, kus spritid kuvatakse ekraanil, nende füüsilised hulknurksed vasted on roheliselt välja toodud:
Füüsilised objektid pole vaikimisi nende vastavate spritidega ühendatud, mis tähendab, et teie olete iOS-i arendaja saab valida, millist füüsikamootorit kasutada ning kuidas ühendada spritid ja kehad. Kõige tavalisem viis on alamklassi vaikimisi spiteerida ja lisada sellele konkreetne füüsiline keha.
Seda silmas pidades ...
Cocos2D-iphone on iOS-i jaoks avatud lähtekoodiga raamistik, mis kasutab riistvaragraafika kiirendamiseks OpenGL-i ja toetab Burundit ja Kast2D füüsika mootorid.
Esiteks, miks me sellist raamistikku vajame? Alustuseks rakendavad raamistikud mängude arendamise sageli kasutatud komponente. Näiteks saab Cocos2D laadida spritte (eriti sprite lehed ( miks? )), käivitage või peatage füüsikamootor ning käsitsege ajastus ja animatsioon õigesti. Ja teeb seda kõike koodiga, mis on põhjalikult läbi vaadatud ja testitud. Miks peaksite pühendama oma aega tõenäoliselt halvema koodi uuesti kirjutamisele?
turvaprobleemid asjade internetis
Ehk kõige tähtsam - Cocos2D mängude arendamisel kasutatakse graafilise riistvara kiirendust . Ilma sellise kiirenduseta töötab iga iOS-i lõpmatu jooksumäng, millel on isegi mõõdukas spritide arv, eriti halva jõudlusega. Kui proovime teha keerulisemat rakendust, hakkame tõenäoliselt ekraanil nägema efekti „bullet-time”, st iga sprite'i mitu eksemplari, kui see üritab animeerida.
Lõpuks optimeerib Cocos2D mälukasutust sellest ajast peale vahemälud spritid . Seega vajavad kõik dubleeritud spritid minimaalselt lisamälu, mis on mängude jaoks ilmselgelt kasulik.
Pärast kõiki kiidusõnu, mida olen Cocos2D-le lappinud, võib see tunduda ebaloogiline soovitage kasutada klaviatuure . Miks mitte lihtsalt manipuleerida oma objektidega Cocos2D-ga jne? Noh, ausalt öeldes on staatiliste akende puhul sageli mugavam kasutada Xcode'i liidese ehitajat ja selle Storyboardi mehhanismi.
Esiteks võimaldab see mul hiirega lohistada ja paigutada kõik oma lõputu jooksumängu graafilised elemendid. Teiseks on Storyboardi API väga-väga kasulik. (Ja jah, ma tean umbes Cocos ehitaja ).
c ettevõtted pakuvad omanikele suuremat õiguskaitset kui ettevõtted.
Siin on kiire pilguheit minu storyboardi:
Mängu põhivaate kontroller sisaldab lihtsalt Cocos2D stseeni, mille peal on mõned HUD elemendid:
Pöörake tähelepanu valgele taustale: see on Cocos2D stseen, mis laadib käitamise ajal kõik vajalikud graafilised elemendid. Muud vaated (reaalajas indikaatorid, võililled, nupud jne) on kõik tavalised kakaovaated, mis on ekraanile lisatud Interface Builderi abil.
Ma ei peatu üksikasjades - kui olete huvitatud, leiate näiteid GitHubist.
(Rohkem motivatsiooni pakkumiseks tahaksin kirjeldada oma lõputut jooksumängu veidi üksikasjalikumalt. Kui soovite jätkata tehnilise aruteluga, jätke see jaotis vahele.)
Otseülekande ajal on mesilane liikumatu ja põld ise tõepoolest tormab kaasa, tuues endaga kaasa mitmesuguseid ohte (ämblikud ja mürgised lilled) ja perki (võililled ja nende seemned).
Cocos2D-l on kaameraobjekt, mis on loodud tegelase järgimiseks; praktikas oli mängumaailma sisaldava CCLayeriga manipuleerimine vähem keeruline.
Juhtelemendid on lihtsad: ekraani puudutamine liigutab mesilast üles ja teine puudutus - alla.
Maailmakihil endal on tegelikult kaks alamkihti. Kui mäng algab, täidetakse esimene alamkiht vahemikus 0 kuni BUF_LEN ja kuvatakse esialgu. Teine alamkiht täidetakse eelnevalt vahemikus BUF_LEN kuni 2 * BUF_LEN. Kui mesilane jõuab BUF_LEN-i, puhastatakse esimene alamkiht ja asustatakse see koheselt 2 * BUF_LEN-lt 3 * BUF_LEN-le ning esitatakse teine alamkiht. Nii vaheldume kihtide vahel, mitte kunagi ei hoia vananenud esemeid, mis on oluline osa mälulekete vältimisest.
Füüsikamootorite osas kasutasin Chipmunki kahel põhjusel:
Füüsikamootorit kasutati tegelikult ainult kokkupõrke tuvastamiseks. Mõnikord küsitakse minult: 'Miks te ei kirjutanud ise oma kokkupõrke tuvastamist?'. Tegelikult pole sellel eriti mõtet. Füüsikamootorid olid loodud just selleks: nad suudavad tuvastada keeruka kujuga kehade kokkupõrkeid ja optimeerida seda protsessi. Näiteks jagavad füüsikamootorid maailma sageli rakkudeks ja kontrollivad kokkupõrkeid ainult samas või külgnevas rakus olevate kehade suhtes.
Indie lõpmatu jooksja mängu arendamise põhikomponent on vältida komistamist väikeste probleemide üle. Aeg on rakenduse väljatöötamisel ülioluline ressurss ja automatiseerimine võib uskumatult aega kokku hoida.
Kuid mõnikord võib automatiseerimine olla ka kompromiss perfektsionismi ja tähtajast kinnipidamise vahel. Selles mõttes võib perfektsionism olla Angry Birdsi tapja.
Näiteks lõin mõnes teises praegu arendatavas iOS-i mängus raamistiku, et luua spetsiaalse tööriista (saadaval veebisaidil) paigutuste loomine GitHub ). Sellel raamistikul on oma piirangud (näiteks pole stseenide vahel toredaid üleminekuid), kuid selle kasutamine võimaldab mul oma stseenid teha kümnendiku ajast.
erinevus ja s corp ja c corp vahel
Nii et kuigi te ei saa spetsiaalsete supervahenditega oma superraami üles ehitada, saate ja peaksite siiski automatiseerima võimalikult palju neid väikeseid ülesandeid.
Perfektsionism võib olla Angry Birdsi tapja. Aeg on iOS-i mängude arendamisel ülioluline ressurss. PiiksumaSelle lõpmatu jooksja ehitamisel oli automaatika taas kord võtmetähtsusega. Näiteks saatis minu artist mulle kõrge eraldusvõimega graafika spetsiaalse Dropboxi kausta kaudu. Aja kokkuhoiuks kirjutasin mõned skriptid, et automaatselt ehitada failikomplektid App Store'i jaoks vajalikele erinevatele eraldusvõimetele, lisades ka -hd või @ 2x (nimetatud skriptid põhinevad ImageMagick ).
Lisatööriistade osas leidsin TexturePacker olla väga kasulik - see võib pakkida spritid sprite-lehtedele, nii et teie rakendus tarbib vähem mälu ja laadib kiiremini, kuna kõik teie spritid loetakse ühest failist. Samuti saab eksportida tekstuure peaaegu kõigis võimalikes raamistike vormingutes. (Pange tähele, et TexturePacker ei ole tasuta tööriist, kuid arvan, et see on oma hinda väärt. Võite vaadata ka selliseid tasuta alternatiive nagu Kingakarp .)
Peamine mängufüüsikaga seotud raskus on igale spraidile sobivate hulknurkade loomine. Teisisõnu, luues mõne ebaselge kujuga mesilase või lille hulknurkse kujutise. Ärge isegi proovige seda käsitsi teha - kasutage alati spetsiaalseid rakendusi, mida on palju. Mõned on isegi ... eksootilised - näiteks loovad Inkspace'iga vektormaske ja impordivad need seejärel mängu.
Enda lõputu jooksjamängu arendamiseks lõin tööriista selle protsessi automatiseerimiseks (vt siin õigeks kasutamiseks), mida ma kutsun Andengine Vertex Abimees . Nagu nimigi ütleb, oli see algselt mõeldud Andengine raamistik , kuigi see töötab tänapäeval paljude vormingutega sobivalt.
milline järgmistest ei ole sulgemise põhimõte?
Meie puhul peame kasutama plist-mustrit:
%.5f%.5f
Järgmisena loome plist-faili koos objektide kirjeldustega:
jet_ant vertices -0.182620.08277 -0.14786-0.22326 0.20242-0.55282 0.470470.41234 0.038230.41234
Ja objektilaadur:
- (void)createBodyAtLocation:(CGPoint)location{ float mass = 1.0; body = cpBodyNew(mass, cpMomentForBox(mass, self.sprite.contentSize.width*self.sprite.scale, self.sprite.contentSize.height*self.sprite.scale)); body->p = location; cpSpaceAddBody(space, body); NSString *path =[[NSBundle mainBundle] pathForResource:@'obj _descriptions' ofType:@'plist']; // e = 0.7; shape->u = 1.0; shape->collision_type = OBJ_COLLISION_TYPE; cpSpaceAddShape(space, shape); }
Selle kontrollimiseks, kuidas spritid vastavad nende füüsilisele kehale, vt siin .
Palju parem, eks?
Kokkuvõtvalt võib öelda, et automatiseeri alati, kui see on võimalik. Isegi lihtsad skriptid võivad säästa palju aega. Ja mis peamine, seda aega saab hiire klõpsamise asemel kasutada programmeerimiseks. (Lisamotivatsiooni huvides on siin a märk XKCD .)
Mängus kogutud õhupallid toimivad rakendusesisese valuutana, võimaldades kasutajatel oma mesilase jaoks uusi nahka osta. Kuid seda valuutat saab osta ka päris rahaga. Rakendusesisese arvelduse puhul on oluline märkida, kas peate ostu kehtivuse kontrollimiseks serveripoolseid kontrollima. Kuna kõik ostetavad kaubad on mängude osas sisuliselt võrdsed (lihtsalt muutes mesilase välimust), ei pea ostu kehtivust kontrollima server. Kuid paljudel juhtudel peate seda kindlasti tegema.
Ray Wenderlichil on ideaalne rakendusesisene arvelduse õpetus .
Mobiilsetes mängudes suhtlemine on midagi enamat kui lihtsalt Facebooki nupu „Like” lisamine või edetabelite seadistamine. Mängu põnevamaks muutmiseks rakendasin mitmikmängu versiooni.
millesse on windows programmeeritud
Kuidas see töötab? Esiteks ühendatakse iOS-i mängukeskuse reaalajas mängude tegemise abil kaks mängijat. Kuna mängijad mängivad tõesti sama lõpmatut jooksumängu, peab olema ainult üks komplekt mänguobjekte. See tähendab, et ühe mängija eksemplar peab objektid genereerima ja teine mängib need ette. Teisisõnu, kui mõlema mängija seadmed loovad mänguobjekte, oleks kogemuse sünkroonimine keeruline.
Seda silmas pidades saadavad mõlemad mängijad pärast ühenduse loomist üksteisele juhusliku arvu. Suurema numbriga mängija toimib 'serverina', luues mänguobjekte.
Kas mäletate arutelu maailmaparteide jagamise üle? Kus meil oli kaks alamkihti, üks 0-st BUF_LEN-i ja teine BUF_LEN-st 2 * BUF_LEN-i? Seda arhitektuuri ei kasutatud kogemata - see oli vajalik viivitatud võrkude kaudu sujuva graafika pakkumiseks. Kui osa objektidest on loodud, pakitakse see plisti ja saadetakse teisele mängijale. Puhver on piisavalt suur, et lasta teisel mängijal mängida isegi võrgu viivitusega. Mõlemad mängijad saadavad teineteisele oma praeguse positsiooni poole sekundi jooksul, saates ka kohe üles-alla liigutused. Kogemuse silumiseks korrigeeritakse sujuva animatsiooniga asukohta ja kiirust iga 0,5 sekundi järel, nii et praktikas tundub, et teine mängija liigub või kiirendab järk-järgult.
Kindlasti tuleb mitmikmängu lõputu jooksva mängimise osas veel kaaluda, kuid loodetavasti annab see mõistmise kaasnevate väljakutsete jaoks.
Mängud pole kunagi lõppenud. On tõsi, et on mitmeid valdkondi, kus tahaksin omaenda täiendada, nimelt:
Maailmakihti teisaldatakse CCMoveBy toimingu abil. See oli tore, kui maailmakihi kiirus oli püsiv, kuna CCMoveBy toimingut tsükeldati rakendusega CCRepeatForever:
-(void) infiniteMove{ id actionBy = [CCMoveBy actionWithDuration: BUFFER_DURATION position: ccp(-BUFFER_LENGTH, 0)]; id actionCallFunc = [CCCallFunc actionWithTarget:self selector:@selector(requestFillingNextBuffer)]; id actionSequence = [CCSequence actions: actionBy, actionCallFunc, nil]; id repeateForever = [CCRepeatForever actionWithAction:actionSequence]; [self.bufferContainer runAction:repeateForever]; }
Kuid hiljem lisasin kiiruse suurenemise maailmas, et mängu jätkuks veelgi raskemaks:
-(void) infiniteMoveWithAccel { float duration = BUFFER_DURATION-BUFFER_ACCEL*self.lastBufferNumber; duration = max(duration, MIN_BUFFER_DURATION); id actionBy = [CCMoveBy actionWithDuration: duration position: ccp(-BUFFER_LENGTH, 0)]; id restartMove = [CCCallFunc actionWithTarget:self selector:@selector(infiniteMoveWithAccel)]; id fillBuffer = [CCCallFunc actionWithTarget:self selector:@selector(requestFillingNextBuffer)]; id actionSequence = [CCSequence actions: actionBy, restartMove, fillBuffer, nil]; [self.bufferContainer runAction:actionSequence]; }
See muudatus põhjustas animatsiooni iga taaskäivitamise korral koputamise. Püüdsin probleemi lahendada, tulutult. Kuid minu beetatestijad ei märganud käitumist, mistõttu lükkasin paranduse edasi.
Oma indie lõpmatu jooksjamängu loomine võib olla suurepärane kogemus. Ja kui olete jõudnud protsessi avaldamisetapini, võib see olla suurepärane tunne, kui lasete oma looming vabasse loodusesse.
Ülevaatusprotsess võib ulatuda mitmest päevast mitme nädalani. Lisateabe saamiseks on olemas kasulik sait siin mis kasutab praeguse ülevaatuse aja hindamiseks rahvahulgast saadud andmeid.
Lisaks soovitan kasutada AppAnnie uurida mitmesugust teavet kõigi App Store'i rakenduste kohta ja registreeruda mõnedes analüüsiteenustes, näiteks Flurry Analytics võib olla ka kasulik.
Ja kui see mäng on teid huvitanud, kontrollige kindlasti seda Mesilaste võistlus poes.