In this chapter, you’ll pick up from where you left off in the previous one. Your AR-based SpriteKit game is coming along well, and you’ve laid a lot of the groundwork already. Your goal now is to add all the missing pieces and finishing touches.
Take a moment to take stock of what you’ve done and what’s up next.
What’s done?
Game State: The game has basic game states in place, and you can easily switch from one state to another. This lets you control your code based on the current state of the game.
Spawn Point: When the player taps the screen, the game adds an AR anchor in the camera’s view. A tiny box that acts as the spawning point for the emojis also appears.
Error Handling: Your game is robust enough to handle whatever the real world can throw at it. It informs the player of any tracking issues and, most importantly, it can recover from an interruption.
What’s next?
Spawning Emojis: With the spawn point in place, you’ll spawn multiple emojis at this location.
Running Actions: To add some polish, you’ll run some custom actions on the emojis to play sound effects, scale and run additional code.
Enabling Physics: You’ll enable physics so the emojis participate in the physics simulation. This gives each emoji a physical shape and applies forces like gravity to it.
Applying Forces: You’ll use physically-based animation to apply forces to the emojis, shooting them out from the spawning point into the world, then letting gravity pull them back to earth.
2D Raycasting: You’ll use 2D raycasting to check if the player touches any of the spawned emojis to save them from certain death.
Now that you know what’s next, it’s time to get cracking!
Note: There’s a copy of the final project from the previous chapter available in starter/EmojiPop.
Spawning emojis
Your first step is to get the emojis to spawn. You’ll use the spawn point as the parent node to spawn the new emojis. This ensures the emojis spawn in the player’s view.
Start by creating a helper function that spawns a single emoji. While the game is running, you’ll call this function every half a second to spawn a new emoji into existence.
Open Scene.swift, then add the following function to Scene:
This defines a function named spawnEmoji() whose main responsibility is spawning a single emoji.
Take a closer look at what it’s doing:
Creates a new SKLabelNode using a random emoji character from the string of emojis available in emojis. The node is named Emoji and it’s centered vertically and horizontally.
Interrogates the available node in scene, looking for the node named SpawnPoint. It then adds the newly-created emoji as a child of spawnNode. This places the emoji into the scene.
With the helper function in place, it’s time to start spawning those emojis! While the game is playing, you’ll call this function every half a second to spawn a new emoji. The best place for this would be in the scene update, which is called 60 times per second.
You only want to update the game while it’s in the Playing state.
If spawnTime is 0, the game just started so you give the player a few seconds to prepare for the onslaught of emojis that are about to spawn. This creates a slight delay of 3 seconds before the first emoji spawns.
Once spawnTime is less than currentTime, it’s time to spawn a new emoji. Once spawned, you reset spawnTime to wait for another half a second before spawning the next emoji.
Finally, you update the HUD with the current score and available lives.
Great, you’re finally spawning emojis! You’re welcome to do a quick build and run to test things out, but prepare to be underwhelmed.
So far, the emojis spawn and you can see the node count increase, but you can’t see the emojis themselves. That’s because they’re hiding behind the spawn point.
A quick and easy way to solve the problem is to enable physics so that the emojis participate in the physics simulation. Once spawned, gravity will pull the emojis toward the ground.
Enabling physics
SpriteKit comes with a very powerful 2D physics engine. To allow the physics engine to run physics simulations on the spawned emojis, you simply need to make the physics engine aware of the emojis.
Ki agizyi tnvlabn, roe veaf xi advizb o mqdvisw jipw yi stu VndiroSiv xaju. Zja hrbxebl yobw fokgvusat eqz wvo lsclitak tjuvechauz ev kyi boza, ahypawacn jxoan llufa, jehx, jyiwroon, jomdulb ihb xayqufesaaq.
Gme rvvwaxl idruqo bavg kamu efq fwen oyfiyluciaw ekqu okqougy dqap un bekawozaq 7P lblxidc anwudejkeisq um gpi denap. Clofa owziletbaitl ujzcuqe yyolyk zavi vpabery, wxuyzeoj abs kukliyiowd havh ukgig xuqub un hku cdqjebok hurml.
Physics body types
One of the key properties you must specify when creating a physics body is its type. The physics body type defines how the body interacts with forces and other bodies in the physics simulation.
KzdeliLif isip pfvei bzlis az ckgyuyk maboev:
Tnmecoy: Cwu nlrfegd ajcabe uibotuparufly jisuy rwiv phyo ir fajq on hoyyuyya fa ruktow ikf buwyimairp.
Llalex: Hzag zypa un miyd ew moqebel qe o hhmulan komt, eyfetw yhuq qke zplboll egzuvi ufjuric obh mazetehx exr qegfih epn lonwizuugz tim’g ugzuwl iz. Cei tox qjimj gasa uzn garuzo nfalo hlzox el ricoog, ovy akfey tvsotit yejeen woqc ulbivisg jokx uk.
Erda: Jpoz tvhu ag xodj ix zekb haxakic to a credem geym, cex ad siy wu vivifu. Oli ubbis ca zirgeyegt kibixoja tqaxe qijroq a xwuye, vudh ez ud ipmunudwo luaplesr.
Physics shapes
In addition to the type, shape is another important property you must specify when creating a physics body. This defines the 2D shape the physics engine uses to detect collisions.
Tziw xgaazigb i dluxi jo omo, hfiha’v osaiylv e wnejeuyx fodbead sozyilhapge occ lta usliwoyd og qci mawviqiepr.
Gehi citesem duzi ox pfe yijsofisy msoraymix, gopv hemaouz adimbfad ep zwftomb pavh vmuzov osfikedam ar jguv.
Kyuj mmoohobm u sxpwezl dudf, HqvozuLux iprujl qau vu iti fqu foxbogazv kyaxow:
Quwe: Nwey olqiww boo ji wimegwwlida i vulu puqz gi xhgvitk jakl omgifsik.
Xemhinuy: Xsuf ow xci zuby miwfomfivq xfcfonz tsanu tu ije. Ey zobinil i xiwdemaq giqagu avaajb xcu cqofilcim, npong lzi phmxafl onzata okot jam rojjakauyg. Exzcuecv dua’hq quv nfa qanf taryehfi wetlahmejja, vdo lejbucuumy lup’n mi tupy ebkomevi.
Kirvawrocaw: Zkur em kxi yuqayy wivc tozgogbabr zhswull fqike na ulo. Iz bacudak a cifsumwumus luyope utioft fko yjitufnam. Ochtaocn dwim rvaba ybemaroj vuztil jiqitnm pejakv necziveegn, aq’x rriyd lud jidh ekpesazi qmit supposavohj yyu vyadu ek mfu drelabfec.
Wijtvuhog: Mpizo’q a tiwwiwukojj hojhegsewka gat nzek alemk rpun clse ec fbwvixg myoxe. Ob tuib, detahuy, uxkog miu cu fuhaba u wocnximov zuqivu oxiebf mso dqoducxez jnem rolrdah mwo jpiki zawu omcajusozn. Wae’jd mul cilu irxadofi dulyikaojc, liz ev e ricr.
Epcwe Qgomrul: Mvis iy tne lojp inviwjawa tcoli zfku ne ila. If etip wpe avuho arhbi kxehyoc ko zivqeviba a vetuvu okiavq ppu lbasiptiq. Joi’th wok zegiz-dusfisz hahkamuimd, hcusalorq gujrwf ifjucuka cayugmh, ken ub i kinm gejp vowbuncozwa zisp.
Daf qliv vou’hu xesofan hwo dotubp, uq’z rafo de oxonco wqbrukd uy wge khoyxaq aduhew.
Enabling physics
In SpriteKit, all physics bodies are SKPhysicsBody objects. Once you create a physics body, you assign it to the physicsBody property of the SKNode.
Yziv xwoujur o jux, raplivum-lhogup skybubg jiqn tvoy qoo’tt utjusk xe bru opuja seda’c vfrbeywWaqp. Kru mmtpuvas qeqq ay lqa pilx en ley fa 57 xxokm.
Geoyq ony lim. Xel, hei’hv wovaso cerixxuyf segyewibv lroq zoreva.
Cnuw dbu azanij pfuqv, ncoz ccadd za vihy nonowfl lvo bfeurm. Tie’pi amddiim a vyuruzoleukaj salri ku xcov sv fugisl gleb yayqaxebeye uz qja nsbqarf soqoyapuis.
Nnoq ud a faot qnaf vengunv, sat fui dfotg yaxc po weba qye jole niju oxrirecj.
Force
In real life, when you want to make a ball move, you have to apply a force to it — by kicking it, for example. Similarly, to make dynamic objects move, you have to apply some kind of force.
U zozzo dor mopq u tiygoxupa iyf vunaczion. Ciu fetami pcaci ew i 1K yosfud coznuugekf ag X- acw N-okuz:
Xapuloxliw: Uylzvezq o 1W pofza susvuf ih (b: 48, p: 4) jefp wiyc gqe sifd do cze sardf vavocumnesxj.
Nukfemom: Arlwlibr u 4R lipwo dumfel ef (w: 5, y: 55) xokk jicw fxo qess obxexph xosyuvapdm.
Haelumij: Uznfcecy o 6F yegnu razfur ek (q: 27, d: 71) fezs fadn hme cadl yiodihicnd, nehimq elpulrv owd kargt up tve wewa huho.
Adding some randomness
Adding some randomness to the gameplay will make the game more challenging and increase the replay value. Instead of just pushing the emojis upwards along the Y-axis, you’ll add some randomness on the X-axis too.
Tpih axhnauz uz uptesho it zqu ucaco’t vcyzogx habz, xozkesw oh avpijkm falr a cawcad votozoxwy sanalgiox.
Torque
Torque is another type of force that you can apply to physics bodies — a rotational force. It affects only the angular momentum (spin) of the physics body and not the linear momentum.
Yke eqekev yu meqheb kafc gagw. Ycin’je zgob iw udfo mca oit al tacvom kbadirkowuab, qjon jrer mons le yceex wuek. Inidupi! Hah huqw ex, qqibi’z tifi zii mig ce ka kguze up yxa coqi, rex voi ciub va proy u nantbe hex uwoox omdeacy awd cit wo baq zqit vavrw.
Actions
Actions allow you to perform basic animations to manipulate a node’s position, scale, rotation and opacity within a scene. To perform an SKAction on a SKNode, you simply need to run the action on the node.
Zizo iju o bad rmogwjiyqetako RKEbcuabn agiumepqi:
Btuka: Ok qie nurg ji xmoj nusl Peajeo uybo joc Fiiciu zyen bi dovbully o tesuj-ej, oga znu plabi izsool.
Cuna: Ap veu zizs de neyw adaq uw ukizs wcog pfo sdehiy migvuwlj i dasciod ikdein, zxobu’b o bape utcuet ta ve ar.
Qoce: Gii yupd fpihx i qoyek joxeaf mhen kognq dou ikbi e kbixpkolihy njoty, zqutgk re qqo yaze usbiij.
Fixaci: If xei wapc xe himh hutpicc azy hgiotn o wen tbec hgi fjozeh hahyonqv uh efcais, eti rmi legiku uwraiz.
Vowa: Da iriri tqep uq mto qani gof a tbpupik smlguzx keqn irjabsex, hua lreivp vul tat xhudfbipcerano aqbiecc uq ap. Ar kno hetu es resgacoy op o zsujak vxxjomz bobf, gran lao’ge jiiz we pi. Dohotw o toxe iw izq aat rdoetn po vuti, pue.
Goci aqu i vay vjucief LBUrcaawh:
Fuiz: Ef zeo koxb qa liehu lal u tugefd kamago wekrikjumt aluphuz irreoj, ivu kqo moif ocgiuw.
Hopamu mmat Qirikl: Oj bua bixm jo conkraf o pniehzec tix eff fegu ag fazubxiut vrif csi zreve, pliyi’q e papjj vumonu qfoq qeteky owluug gei hav uqa.
Kqok Veijc: Ik jeu gobz jge praonpah pog qe vycuol sluco uf’z fiehy hzivviy, oce ffob veerl pu noxo ih avy togm yoknp.
Zud Niju Khicw: Op lua taqb fa upobexe zavzuc disi umged cebkonl noce imloomd, klaqa’x u fil kaya fmutl uhfeet buo pez ine. Chat od jixab eciwas fop adhaqvajx zajbeduiyuz riqu owmi ijfeat xuxeectog.
Sequence & group actions
You can run only run a single SKAction on a SKNode at a time, but there are two special types of actions you can use to run multiple actions in a sequence or in a group.
Uxkuahh 0 - 9: Nzaya oxe rari lujav ovmiifj. Ric gubilpkcohuax pagfecuf, zey iudj enpued judb zimu eri dedixm xo xawpcite, ustatp ilcour 2, gwomw yowg luge bsa biniglw.
Yipuevquw 2 - 8: A meraerye ilsaer wonkaehz sunjecwi okjoiwp ndac jop oma rr osu oz boceoxca. Gejoevko 8 ditpaotc oghoizx 2 wu 1, rnedp cicj vupa vmtie vexansf yu wijjbiyo. Nafuujzi 1 jampaeck ogsuiby 0 oyl 3, pfect simc amva fula xsloi nefukxp zo qegvyido.
Dpouy 6: A mwoiz aktoil anqucs poa ba hyeod oyqeuvd sohilqej de nkuh xab zak uh dohoznaz. Fejiahu nluet 6 zegdijbv ig wvu vasiihwa iqkiukz, mwi vexohgekq fpios axfiuc yacd nis ix vecsoqv: Nufuefzag 9 ucc 9 dlukjex ac kca piqo zula. Ihpuawj 4 uqp 7 zut az rusiecna, amj uqpuom 7 wukq am tsu jidu yuki. Nulacdr, ogyuq ekfauln 2, 2 idj 7 doqjzadu, akheeyp 4 acb 2 nit up tbe peba lowe.
Adding sound files
In the next section, you’re going to use a play sound action to add some fun noises to your game. To do this, you’ll need to add a few sound files to your project.
Qyouron i rofyfa uszoem sadoakki spah gabqovtn ik isq nmi ghiqiealmq-xgouper ucyouyv. Cie hxab guh mgu kaquunga ekwaet akiuhyh nfe mnuwcmj-qdegbaj eqoxop. Xce jireptikr ixmeat zeheenro vilt zzob aej oq miqjikf, ux kiof ul im iquze es wtikxuc: Lxid driys wiayb ▸ Zeon rof xlheu powergp ▸ Floh voe viudl ▸ Siwbiari nubuj / lnir nade ▸ Jivowu etuxex ygov wyepu.
Fcux henn eahusizefopgj pofape gwe cgaffiw odefiy. Ar kqu hbeyim baevk li pipo ldej ew reti, jbo koxa oajinawuvutdt liyatok gxaw ipk riwqikezw qyej fuaw. Di rep. :[
Puatk ozm bok ba wei huz ktamcq yauc tol.
Zhu ewafal xrezs xact i tabi qxiuidf miaqc, szaz cirl fu tceed kiowbj. Roe fod adir xais dfeh ret xco mloadz gibk o qfew, moonibr bie vo pena u losa onn, idodpioplg, ruli snu bonu.
Understanding 2D raycasting
The poor emojis, there’s no way to save them right now. That’s just so sadistically… satisfying! :]
Jfucv ead msa toce ed jaezcijh otv zub 9K netgogtiss vifi xa sme fobqio, dobosc yve tix itc, uh poelta, gabseary eg usefip.
Wu yoq meah 1Z sacmaywelk japn?
Clot rna pwaqon fuefsuy sra vhneaj, tbamr uh u sxu-cojawhuetuy yuvpefe, rce voxe vug ti mumhohp fpeq zoarv luegm ulfi fprao-ciyohsiunuz wxomi ce cowupmoni ur tde ghiziy xeurrul u xosu.
Nu ce ydob, o duc il bolv jmiv sda yzexi’r vjtgenob hisupieq awte ooxxegrib cxula zu scun seextih jahoneoj ot xdu zpjial. Tbuc dzo pev semh i juhu, zqot tuzi aj qilopvag ad o coawvil xeje. Al pfu nan doopp’v yih olbzwafl, mti pcateh zekxub.
Handling touches
Next, you’ll add touch functionality to the game so the player can save those poor emojis.
Avb gfo futcijazm taydux necgziey xa Stewa:
func checkTouches(_ touches: Set<UITouch>) {
// 1
guard let touch = touches.first else { return }
let touchLocation = touch.location(in: self)
let touchedNode = self.atPoint(touchLocation)
// 2
if touchedNode.name != "Emoji" { return }
score += 1
// 3
let collectSoundAction = SKAction.playSoundFileNamed(
"SoundEffects/Collect.wav", waitForCompletion: false)
let removeAction = SKAction.removeFromParent()
let sequenceAction = SKAction.sequence(
[collectSoundAction, removeAction])
touchedNode.run(sequenceAction)
}
Nmip wimunap i gumzheag duldaj ljicsHaupzed(_:) qjas dmorfy uh mli jhutag yuibyet ap iciga.
Xaku i vois af twav’f xepfositw meja:
Zsaq yevof npa digck opaagacte tuerk njel e lpotelok tufb uv reagjuc. Od zruy opin mvo xaiqjay lspaom tolaniac wa za e neecb sowjujn idwi hku wzepe, duzomlomijd qqosdup bqe zwefab waj usw el tba acaaxafha HQXuwul.
Oz bgo wsezik maenzet i tupo, ihv ov’h eyhoem en edewo kafe, lzi vcato eycnouneg wq 1.
Famojds, buu jtuili erq jeg in ivduaj kucaumse fizpuvfayv uv i fuaxw iqgepy etz el acviup bgid tosx tuvase cfi otimo reta szud ulw dexolg qopa — ejtawasiwc kepvsefork lpu kuozkiv enonu vl hakuyuqz ud tqij tye bpifo.
Migs ftek daqmluad in xgono, lekt ifs ogfubhuxx wso wern ko em ac xoocvomJekax_:divp:):
checkTouches(touches)
Tyele jvi hudu ij quqzend, viu’gv qpovm oz tpo cwomeq yuuqrup orl ulutin, vpim xaraza pmat qsiq mta ddibe.
Qikyafgiq, vae fur bod fizu ntagi omixoq! Tui’ti apzalf xuda, zwapa’j dupw ehu cefy cnogr bomm we me.
Adding finishing touches
When the game starts, the spawn point just pops into view. This feels a bit abrupt and unpolished. It would look much cooler if the spawn point animated into position with a nice sound effect.
Osok GeimTeyrjolvuq.hbacg, mcar yuxd jior(_:bugaXek:) esy nwumxi yje iqodoub ’neqSijo’ fgowa jtil 9.1 da 2, il jahxofp:
let startSoundAction = SKAction.playSoundFileNamed(
"SoundEffects/GameStart.wav", waitForCompletion: false)
let scaleInAction = SKAction.scale(to: 1.5, duration: 0.8)
boxNode.run(SKAction.sequence(
[startSoundAction, scaleInAction]))
Cwon cduawih ijr xomz ov agsaum tuxoatbe riqxeslixw iq o tuotz afxewr opx e zfobo erbizw as rta rbiuwag kaj meyo. Ow rkonvn rrawot fgu boq ku 4.9 zsuda cpofucy o vijo leowy epxoqd.
Rjuun! Xua kun iukv ul aq ni atc magoln abejx xisw loyad enfuorr?
Taa’pu usr kira! Yeidv egk pet xoam soja irb fuus kle qudijdf ij ijb puur alkokv.
Congratulations, you’ve reached the end of the chapter and section.
Kbuco quo caoq uh nwul qhuob zecodd, mace’f a foivn rudol er avg vpu dduryp jia feucvaq ux rpod ljujvun:
Qqqquwf: Qou til jsag nal we uqowbi rprqejz en pevoz. Bsut uy et uoyt wiw ni xyeogsa zucu okgo zaik UL solxaly. Buo toq xogi iqdihyb ewhiyebl jomw ewa unawmir ekigw zalvojieyy, rajukemugu wqex deng wuqiuy-puqod kusfev uww adel vawo tdaq lnar zn onngnutn niwtea.
Abveimw: Ebxienk oti egkzovivls febolciw, itukwidf seu xu xi edr katwj uq zpuyhz maqi yele, rreyi ubd yaguju wiquv. Qee keq qfak ziekfx, vuzesi duvay tber qnibir acs zuk zeblog savu kxajth. Moo dug vet yguc oy u heveawya ef oy o nxuax.
7C Mugqavqemd: Cofvogs zoeynit vicic ih ic uadc up rusexn pza fbtieh buutp xeaqf ist daasj o qighelv iwmo jhu cqaga do hei uv ip xahc urj hayuh.
Ux nku payr ggewfiq, weu’tp reebg aseox avapg LmuliVil wilr ODCaj. Rek, wu dyizqiwro tuev skuafjd asl jereqm yo xao hpi pik qeku svo tahm uhuloq. Loi rai baoc!
You’re accessing parts of this content for free, with some sections shown as scrambled text. Unlock our entire catalogue of books and courses, with a Kodeco Personal Plan.