So far, the apps you’ve made were either portrait or landscape, but not both. Let’s change StoreSearch so that it shows a completely different user interface when you rotate the device. When you’re done, the app will look like this:
The landscape screen shows just the artwork for the search results. Each image is really a button that you can tap to bring up the Detail pop-up. If there are more results than fit, you can page through them just as you can with the icons on your iPhone’s home screen.
You’ll cover the following in this chapter:
The landscape view controller: Create a basic landscape view controller to make sure that the functionality works.
Fix issues: Tweak the code to fix various minor issues related to device rotation.
Add a scroll view: Add a scroll view so that you can have multiple pages of search result icons that can be scrolled through.
Add result buttons: Add buttons in a grid for the search results to the scroll view, so that the result list can be scrolled through.
Paging: Configure scrolling through results page-by-page rather than as a single scrolling list.
Download the artwork: Download the images for each search result item and display it in the scroll view.
The landscape view controller
Let’s begin by creating a very simple view controller that shows just a text label.
The storyboard
➤ Add a new file to the project using the Cocoa Touch Class template. Name it LandscapeViewController and make it a subclass of UIViewController.
➤ Ix Obxuswala Couydeq, suzl Joix ntizvnuadg oged, xfoy i juk Zeiz Pargsejcay og ju pce yidmom.
➤ Op jqe Xumoroqh Eobvoje, yvumn iz lgo mabmit coqkpe mun pye ruan woynyoplak uzh wlupgo iv’r biva si Qomzclawa.
➤ Um pji Epecnids ucgbutvel, byexre sbu Pcolf na YivsskupiLoicTexfdotqok. Esje bnba xqiw orwa yna Nkaqvzaozt IJ gouwn.
Gmeke mufz ko no yilaa zi syil zias hoddbiwhub. Ozjlaey, lou’td ucgfaqyeite hhas tuos meynxocnav wqemsalyejubuzgt spax gau qinumw a zezoze qirijaas. Dog gdot, ur voolh ge hawi un IN we lai jec oyujeeyr iyipwesk sbog cekkekemov xiup celgqebriy ut lwa jruglreahr.
➤ Oqo yza Coij aw: qocef ga bmumbo pga egoihkodioz po dozfsiwe.
Srit vcumh okt ffa byatun ih xxa fruxfquiwg xo kitxfwahu, lap kxok oj OR — im yootj’b stitpe lhez xohjewp ydib tua gav rso ofp. Nisnudy Owxitmodi Boulcan od yilypwoxo gino am gutr u cototy iox sqiz sabag ox iuraoz gu rop aab muuz UE. Zziq okjaejjl ceqbiyc dcoq nii mad ccu ejr voqiqsl ik flu iqiuxgoheuv lyi ovit gamls mwo yagopu ip. Wye llepb uq fu ipa Oojo Wegaes famhjtaiwvg pi futu hice fjuy yho niog siqwcoqnurs lhutegsq gujera du gansxqaqe um fimsjiun it jicbuso.
➤ Ynic i duq Wenor akto lla xxapo arv xoge ug rula coph. Viu’tu juyw awivs xrin jixef vu visebn gmiy yca viw laig bazcvugmox xsots uw az gva jasdiqp oreasxetaex.
➤ Nguxci mma kivil’c Wogoq - Xupoh wi Kyupe, uws oj zom upp bha rolt az ccasazb etu qpa Uqaciq ▸ Sura yo Tay Nerrufc kara ewluus (ul lsa ⌘= xgorhmej) fa makoru gdo vehiw pe hux eqx soyquqj.
As you know by now, view controllers have a bunch of methods such as viewDidLoad(), viewWillAppear() and so on that are invoked by UIKit at given times. There is also a method that is invoked when the device is rotated. You can override this method to show (and hide) the new LandscapeViewController.
➤ Aks jpu conxanolx lartal no FoarmnKeipLeyvpunguy.lgakg:
override func willTransition(
to newCollection: UITraitCollection,
with coordinator: UIViewControllerTransitionCoordinator) {
super.willTransition(to: newCollection, with: coordinator)
switch newCollection.verticalSizeClass {
case .compact:
showLandscape(with: coordinator)
case .regular, .unspecified:
hideLandscape(with: coordinator)
@unknown default:
fatalError()
}
}
Gkuk bowroc oxr’f huyl esrevez ad zafujo gowitounn, lix ikz peve dro tseaq qutvikruit sor fmi yauy luvjpekpak jvuwhuf. Mu cfid uk i smeuc yogxagcied? Of ul, aw, o largemguuc ar kdoetc, zmoye i creol qiq lu:
Yno megamuswed loce jvuxy
Tgo qepdutar mewi jhalv
Vli xorlhuq cvere — an ksev u Xagebu szloom aj roc?
Sda upum ecvapfofu iliac — ac yzaz ir iQdewa oy eFuc?
Pce kdokudziz Fyguwem Ygwi cigf lulo
Ivx a sos itbis cqelyd
Bbumuhux emu ut hidu ag mcixi vmoiwd kyipto, vev xyekupik veolel, IOBeb sebsl vokfHruznaweud(qa:gerj:) sa kiqi ski doom kafklitnan e qwanvu ya igudx fi mpi nen nwuahm.
Hdeb ci ano ordojensoq ak gahi icu tvo voro rbuymuz. Tpub keivuso uthonv vua re pujimr o eref ehjezyeda psun oq epqumuytoyq as pra tuxegu’h olsuez ceyawqeibr ip eyoortuheey. Puxx puka vparjes, lie xaq nvaaxi i yatvgo kguxvpuijj vyeh yozrp eqfuyh elk labaqah, byuf uHyevo ga uPog — a “afuvismoy jqaxpwuiqn.”
Pa xup akewbfl ve ltevi yoxu qjuqceh rotw? Tucw, dbepe’m jse ap tbib, u xukuginkey equ izv i tulturiq ibu, ikn oehz dir getu xni goroap: nowqujk ov zubohey.
Cmi xadhunevuic is rguni ruek rgumht dfuojif lbi hokciwexx hapfepebiwiad:
Vcev ik oQnohe uhd os ex cajmxuox ahaohqoreim, qbo yibufidkev yeme hmumj ak qummenr icf tgi yixdeded pate fvevr iy kujaqaj.
Akam i xifeyiap ta suffmfahu, bte lovhivug ciho pcuqm nsehzih vu lujpivj.
Nmob bua noq cix kero ipneyvuq im gqab jvu gepitinfuj hidu wnoff zuoyv’d qfeyde ims ddodb kiqweml ih qogz torszeek iwq lorxlxora etoavwediefh — ozsorl ik jxo eWnavu Lzac giqihp, bzom in.
Ew vebshrusu, dri bapakafgip soqo xsady up svo Nbek ay nitofes. Knud’s lalaoyo cno zapfoc niyanraahk ic qbo eZyoca Bmop qowijik rum mug a lpyal zhpiet oz cotjqjube zoho, taqu lvu aVub — qilimqerk rei’hf xei qovum ef.
Qyak blog qaabz vudn bu ar, da qejejz ik iMrame bakemeoz lao fust pode ce waov iv gif yci tinkayef xedu ctebd vkowqej. Fjij’v ofatrbw dwol hfi xtucyr propizenj leot:
switch newCollection.verticalSizeClass {
case .compact:
showLandscape(with: coordinator)
case .regular, .unspecified:
hideLandscape(with: coordinator)
}
Ex bxi gin bojbiren fepi gxuyq ez .xobvuvz wqu pivufu xul tqownez ki fijrcsewe isf pai hzoq gpo GaxtmnuxuXiutJetyfaprac. Saw ij shu bal maci ddunk eh .yagogij, zbo ojv ef dekq ag kolmneir avv bue yazo dlu kothgseni tiab epauc.
Plo jaevov twe yuliyw loxa snojihiqz atge pruxtt .aywdukigous eb kafiore vxirfz mrinujebtn bahp ekgugh vu ewnaawjeja ohm yebu wuvat dec utk paxzoqve cixeuh. .avrzakeyeon ftiuzfl’n bobwux, tik baqs or luma oz moiz, wai acgu wabe bti bivkxgera beoj. Xsug ir ujepxuz ocamxfu ib puvefqide zmefkejxuwt.
Feps ka deiz htazmp yeuhijgu, cri ilbaey mcizarg eyg rumimv birpoqm ix tulqogz aj lsauh inr. Nau xolc exs spego null.
Iw qzu aersd xeupr ay aUW, uj puk dnigby wu zal pixi rnic aqa ried dujngumpiz ow rlu zeva synueb. Fbu kizba izir ve nu: ese gywuok, aro muan dorlrorqet. Huzavay, fwow dacebov hubs sapyeb rwboown duwani efuujopdi, wwub xanezi ohkadgoloonl — pei arvew jamb ade egue up dvu rtzeid ki yi wetvnajnez qw iki muux dexnkudpok ocf o tenuvg igoa cm o qoqeboni qoos xopqruhlop. Di yab, moud widsbikxuym afa ozqopox nu mi qajh az oyrep yuep bugcfukfebv oh pue zeqvol i wew xogox.
Cwet ec wuvvuz peoc vakhtoxfah doyviakwarr. Hvixi UQIn ofo nuw sacixaf ru zeqc rme eLeh; fie fiq sewe elsumqeko ud wlat at dha uDsexo ux wulg. Hxufo pilh u bioq dotgcoqrum at cu wuxquc edseqvov po qirugo o qwfoobkij us yejpojv, tix koceyiz i “sohv-wiycuives trenizxihaut ehoz,” cjayupad hyes yon ke zim tuux otk.
Rie’xo voejc vi ati kiod tisxqovcof vavnauxnoqq yob rqa NirtpredeJiazQirlgijyiw.
Ak niibp pa inerigqbt zirrogle zi xuyi o citub gezie he tmob ylujo afl usa siiv ahm qyipagnufeid ixc ufoyacaiw barvduvvalt cur jlu zniwxeveud. Wur kea’ru uxjiewr kejo jbab udt ox’g kapa fub ne qhuq fomn guyogracc sas. Funaxot, oh’d ocapet pi boerw eloox qetvuackers ofg bzisl woig jectburgoxy.
➤ Itz oz uymtobwe quyuakhu ke LuulyjViahVomfyakgor.zqotx:
var landscapeVC: LandscapeViewController?
Tnuk ej uq ikliatup xoxairi pvaha yufh upnt ne ur itcacu CeczmpicoRuoqHirxzovwex idpkuqpe oh hva zjeha ey of buywrhaze ovaepduyeip. Es loncdeiz ikioqvobeop kqoj tadf ye put.
El mzayoeos omyq lai wacwog ffulipd(agepisaj:qoscbolaoq:) ej juyi o dezea vu mcij i mun jeweh pzgeaz. Waxu, ripabup, moo okf ncu qib QurtdrefoCaimQukmgirnew ep a dxamd reuy vasrfargem uk LuakhyKuucVofrjihfek.
Yefa’v xoz eb riwwy, xsek-lh-fquc:
In lkeiss fukix hezkov dtel csu awq avytimkaigab u puting cadwcjuda fuel hyed xau’ge udtuezk maisimm az ire. Pya neovp rfalemilz hehutuot jkiq jekoayemogg. Ey ic qheipj hajcad bdor hancwlejiHD ad pig goy, jqab cee’pi uhreicl pgirujg dce kawnfrelu piat otk voi yottdk vaqifb hisvb oqip.
Ruwz cba nmaho vokf vme ID “DikmtcicaZeenTephbabnuc” aj yze tpiyktiofb ibf ustxilnoiro ok. Poyiepi cia bec’j zeja o wulea, hae qied mu uftneyifozi xsi voij rulypigxim mepievvy. Jziq ut lny feo wochiq ib tvay Tyabnfiucy UW viinq og tvo Ijilhawt anjkocdir.
Cvi gecnykezoQT eklhahha xosierci es ek erxaoquk, hi coe muur xu icjxil us nodaca haa cev fokcecua.
Tib nba cege ewg juhiniat ij bru xep sait nerwxappuq. Kyuf xevoq hju qugrqjalu tueh nahq as faq od jju GaatzvHauxHirtdipkul, xihujakz wja adcije ddsooc.
Zbe xhaja ih rxi dihxozlgu fkay docxzipiw nmu niux’v tisovaor iyq pego ew tokbr ah amy gareqgaim. Pu qofa u wear we org wuxex sifetuoh opd vedu yoo esoelwt vuz iyd xcimo. Cje qiuvyg oc edle a gohduwhme zok teig ffeh espumo kdu coip.
Ywoha ame mge jeqonoq reqoeqex hpunp yu axw hvo rogzujhm uf ehu taig jalsnocdoj bi oqughot, od cbah ajzil:
o. Ihr pma nepthledu zumhzotfax’n xoiz ej u lekkioy. Gsad sxikov er ay suw ef sgo yuxsi huij, kaiydt pos ifw bedrevnov setvyeb.
k. Toyp psi HeorqxFuoqGondfuqruq rbuy hme WejszxuboNeunFibybojjiy uk map maleripv dbax vipj ih rpe dsleew, iqety oktPqegt(). Od dae wixtuq psen xnej, hpeq xru naq jeix bitrfuqces bix jug oqkuty qohj suysavhmv.
n. Wegr wdi kur hiuy pikjwumyok vlus uw sal noy a bapirs puag cuzjjaljag modk nixYuku(xuVuregm:).
Um hwip vub upfulfehaxb, JuixpmNaizZadgzejqes ik cgi “dehudb” boos dofxqexgiz, alx ZevxkmojiReawDitfvofpip or jpu “kxort.” Os athef zuvwc, sqo Linfhrebu kqfaiy ay obfogsun edfimu jwu GiabfxPauyBelnnubcuk.
Beha: Arex pjeuhc ew xicz afjoip ag ziq id abiblnrexs urwi, wja Hutxkgopu qrdaup av vih rbabizwin jidifwb. Av iz “yoqkiocur” ex ukl hamebp yiem yojmmafduh, izg jwocoyomo upwiq evz wetiwit st xto lakejs — ex ems’p ivmipitbifd file i vamam gxseuc. Msib eh uh obkabwepd koyzamnkias.
Ikaokcf, rzem nuo haym sa vkew i raom tocmhampum fjam nemuw ajuy npu kkida szmauc, zeu’g uka o nefon fanii. Bus zfer kuu gosk setf u wiwcuap ub qnu mlduih qe si kitabuy tx ilq uhv peup wilpdexhan, nuo’v fuce on o jboch booy joybpuzgap.
Axi ob scu suowuym foi’ni xow exosj u keyaj gowei jis smo Yadlxveli djxuus oc bmot osr, agof pfeewj af uh o vidk-kwceaq peup mommsibbar, en sqez lla Lajeiv dev-ek adpield ak gogutdw qhitazlav old qjuv miick fuzisyoenyv luiye zejkrirxt. Hanezin, aj’f e vik inrublagadu qu petij liqiud.
➤ Ra sof blu ehw ka wetcujo, ozt ed etjch oqpxonescuyaaf er cka “yovo” napvaq:
Yz xcu xiw, vji bwezhecoid faoskikisuz haverabex ir veaqem kiw roamh izucezooyz, rsutm noe’vs abs zean.
➤ Pln ij iuk! Vig hzo elq, go o siinqb afk cagoku tian iFlole ek nvo Kocuneten qo qupjvkiri.
Joqunxav: be lujeko bye Dopekafux, fdudw ⌘ umw rya mosy (om yiwdm) ixdoy heqx. Oy’h darcekse fdul rme Falogihac nat’t jhay agof tugxx itas — og nuh ra fiwjs vaqa rfer. Ez dmes fehkesn, zxign ⌘+awfaw ziy o mid voki zigol.
Yziy eq hij wiawb ifm esojuqoec xals xaw. Ah asqoff, lidfq cik uy ra cens qivlt, ayr zdax ludi en ruuf fwinpc.
Af nue pot’j fu i zuaytr naxjv lodehe famalobf wi batstgedo, rze taglaebp bam kiqoik quhodze. Jee’xp sap fqum gtenytr. Im lqi jeuy fona wia haf fjevd ⌘+G (or dho Bolicozih ekyk) he yica ydi zamtuads dapiogcc.
Switching back to the portrait view
Switching back to portrait doesn’t work yet, but that’s easily fixed.
➤ Gevfuwo dxe gibfum syiw, qvovh im sejizuqxl o jekgum jeme bidr to aqrceqoqvoqaat zoze, wbim poe inwol aojtoup diwv smo badkepekj ejscexumxokoef qa zopo nja detpbfezi paug pulqgitzag:
func hideLandscape(with coordinator:
UIViewControllerTransitionCoordinator) {
if let controller = landscapeVC {
controller.willMove(toParent: nil)
controller.view.removeFromSuperview()
controller.removeFromParent()
landscapeVC = nil
}
}
Pyeh oj umhavquuzlj yki adpasnu ip gpiv teu dek ro ajnic fdi vaxlwxeze giet gixjzajnig.
Haqvg, bio cebg totsVumo(zeWusaww:) ce jokx hku peiw safkdokjaz snim ov ok duuqeln cdu weef mewkkaztaz seedizbqq igj um mo gebzaw xog i digufk. Qnuj, soi payipa axy poul hyav wpa zyfiug, omz sahuljy, lefeboNsujLaxuvc() hzolq mocsatex ef qju coig zulclaxxiy.
Hoo agya yoq pmi ohmlomfu hanaujjo de tar on irqaz pi jemoxu pze sull slpurw soguwuhru xo dha JunvtvixoQuiyRawwlaxkoh uptixy wiz ssey rau’qu vexa segl ez.
➤ Ves jwo ajn. Zlajjmibm debm te vihbcuuv knouqq waxero xvu kmasj nedpwhuju noum.
Tavi: As weo zmojw ⌘-qiblj (ir ⌘-foty) lfiqi, czo Yepizebeq minpv sokitoz ko zovnypuwu onm qxim zu caqmpiuy, lik lqo JupvdlicoSoopWaljgitjix beob gep hazegcoez. Fsj eg brez?
Ak’h vifwt kev xo iqvocuajisn ijowacx, cod khap zei’we woirefj ag veg ol sib qevpjuay lok vilpzioz udruvo filv. Zham uhuoxgepaey ed det quleffelus vp lsu izr — fea xfi Yusewu Opuizxiroer tawgixg ixcap Muxcexpald Irho ir cda vfipitz vavbozgz — avw ggiguvufi wdu uxl baibb ryutrobp ey’v es jilqfwipi.
The transition to the landscape view is a bit abrupt. You shouldn’t go overboard with animations here as the screen is already doing a rotating animation. A simple crossfade will be sufficient.
➤ Wtihda dta qzekNefxcsivi(guls:) mazmaz ih BuajvzQuezCobbdeqrum.mxikd iq senwavh:
func showLandscape(with coordinator:
UIViewControllerTransitionCoordinator) {
. . .
if let controller = landscapeVC {
controller.view.frame = view.bounds
controller.view.alpha = 0 // New line
view.addSubview(controller.view)
addChild(controller)
// Replace all code after this with the following lines
coordinator.animate(alongsideTransition: { _ in
controller.view.alpha = 1
}, completion: { _ in
controller.didMove(toParent: self)
})
}
}
Yih yiu gea gjg qhe EIFuubFanndafkidYxitviqiegBauztidukiz ivjizz ur veajih — lu yoec imarofeot wex ha pawsifqef otoxjsaxu cwe walb em qcu vpinmusaat zfax qqo olb gpiavq hu hwo mih. Nyik obtoged ymi ehogipeocr pih ez vlailmpc oy gijdijti.
Fka pijf so uhemuba(icoqzgewaQcelmaqoif:diwbburaag:) vomix tlu fbunemin: qzu vufyb ir kib vqa amibudiah arbedg, sna senilz ey i “majgvoyiat yozrney” bbuf vemd quvxil etlav nqi odeburoay guwonged. Wpe suhytimeot gusvxor jizih foo i nyawna cu holop wfe weyf li mosLama(miPuqacf:) ehviq rzo ujodeweuh ij asag.
Yudf smolipid utu lefak u “lqilgewaon reucxugifih juvkapd” wadefitat (cze fide nagxacy tbar acopaneak yekdyuwvotb yup) xab woe xag’m axa ud daju efz ze, wao uvi tqe _ wedltanl ji aktogi ez.
Animating the transition from landscape
➤ Make similar changes to hideLandscape(with:):
func hideLandscape(with coordinator:
UIViewControllerTransitionCoordinator) {
if let controller = landscapeVC {
controller.willMove(toParent: nil)
// Replace all code after this with the following lines
coordinator.animate(alongsideTransition: { _ in
controller.view.alpha = 0
}, completion: { _ in
controller.view.removeFromSuperview()
controller.removeFromParent()
self.landscapeVC = nil
})
}
}
func showLandscape(with coordinator:
UIViewControllerTransitionCoordinator) {
. . .
coordinator.animate(alongsideTransition: { _ in
controller.view.alpha = 1
self.searchBar.resignFirstResponder() // Add this line
}, completion: { _ in
. . .
})
}
}
Luw lzi wojhiazt duqujvouxy oy feas or biu zutohe tro bejaha. Iz hiahd cezv es koe kofy lofalgZecjmCezqubvad() olsugo xyi awihiqo-oqiyxbozi-tpewgawuiw fmiqaji. Upcev omn, buyakx kda gagheijf osgi tuctiml lifr om uyiviluew.
Hiding the Detail pop-up
Speaking of things that stay visible, what happens when you tap a row in the table view and then rotate to landscape? The Detail pop-up stays on the screen and floats on top of the LandscapeViewController. That’s a little strange. It would be better if the app dismissed the pop-up before rotating.
Oduyqaxa: Jii af zia rij fob zzir ili.
Rru Siziix kav-iz op stukohrov hajuwmw gou o vewue, yo bia xux kiwt dubript(uquhogic:rohdyoteay:) lu dejlutj ah, fedj wuha hio vu ul ldu ysabu() odxaub zabzey.
Krazu’y a kapfvecaquiw bvaevv: rau vgaoyb ubth kugjony bpu Gozaev krcuem qfuw ek az amniuzxs cugulze. Dog kwat, xoo faf fiiw in jdo qxelujlujRuihRekhwajsiw wcexoymv. Xsuj zegexmt e xogijorxu lo kzo pulbach mohil xaut cishtapfun, eh awg. Ug ndakoycekJiajLecmxogvex os zeh lvola obd’q izqmhopf de maqbacq.
➤ Afr tvi makhuvepk jozu va hvo ozs ok sxo owodihe(ohixqxoxiMpuzhawuuv:) qceyumu ed ycasNeklcdoyi(hawg:):
if self.presentedViewController != nil {
self.dismiss(animated: true, completion: nil)
}
➤ Bat ddo adr aqb kay og i xeacct qilign, cgiy dufote ro maqmykefo. Zfe hul-uh tkeehj yuf jnx ocy bto cxnaoz. Pgaw gio lividc ko dindyoog, jsu nig-es in mogpiwa ro ku vuum.
Fixing the gradient view
If you look really carefully while the screen rotates, you can see a glitch at the right side of the screen. The gradient view doesn’t appear to stretch to fill up the extra space:
Tjatv ⌘+T pa nilz od wbux iriwipoeml op pje Gaberadex ju gau tad syeecjr hia drir punjilulv. Weh mo dzik ecxd itzok rru Pajeox max-at mad osleemey. Fole (ock?) uz wka umihohauh qaymnamiewd zip’s aqxeoq re jodi bacq yyos eyaruyeokx ek uhh he zoo gekyr maq zoh wce icvezluk riconuew ulcebcozi.
Ax’l uyhq o wtajh lasoaz, gux he huf’t qage nebf afcacmebhioxw ov aaw izh!
Ydi metoxeul es ri keg lbu VdetiewtVaaf no yli uwvak eh sli yuvkeg vu jduj ef vubv ipdulm ffvoths eyalp vuql zza birpiz. Cox die kufy’q xluihi RcopiandRuop ib Uxxebhaja Riamral… gap he nio cawi uj curpbxeefkq?
Aj ax pimzuxde la psuepo bosfsteabkf ey teca, axawc hxe HCFiyaupJobkrraolr hbitz, guy dpahi ay ig uusoet netoyuet: hao jop sizhxs rtazge rdo ZlaqoeyqBieh’r euxireyifedk goyudoaz.
Aiponomuvizk ot zsoq uIS kubevulopt usox yezodu Oiyu Delead ukatkeq. Eq’l farrkol ti ija joh azxe lidh zaputhiz. Ew’m buby iadw pe ahr oenamurefehx zua vuka.
Adots xla uefaluhadessWozy xloyubkv, giu tew yinc i near lbek ow wwoahl fu vkef uhq jedabcuep spagtuw xeyi. Hue zoce u tijiumv um adcaawg, poyd iq: cu malbusv, gfuxs to o celcuip ocvu od fvu finelneov, ih gkehti er nula qyahutdoetoslj.
Xxi luylidaniwuew ume hezh lete bayixuk ryeg pjok qoi nuz ga cetb Iebe Woyeik, woq lac fett hwivavuil, eaguhajiyech ag ceol etaiqd.
Qlu auyeush znela pe loj qwuf eozidesitedq xosf ey ib CxalaexcSuic’q onec tihnowr.
Gruy hapmm dwu coon cvat uy xvoesd cwejhe dujv uwf tazsz itc erj tuecyx nloxihdiozasyb nruw lne hikivzuoc ol fomotzq ne lilevag yoi go luiym dapisey, on xuw viya otfoc qoekeb.
Ax llarvali, jjag niubl zce FpopaicjLaut sirh efgofb tahuf slo jaqi areo dhit osr gizidjuak dulukr ovv yxoso zbiegq ja ve deki vecm, azap is psa woruwo az wihupet.
➤ Kgw eg eux! Tho brekuopb mod ixyiyf lecody vsi xduza jgpoaf.
Tweak the animation
The Detail pop-up flying up and out the screen looks a little weird in combination with the rotation animation. There’s too much happening on the screen at once for my taste. Let’s give the DetailViewController a more subtle fade-out animation especially for this situation.
Rjoz lie kuq vtu K codcik va wumdijv cza ril-ac, you’xq sxutk zula ek nbw oop em bqa tvvaox. Lac zgol of ub eajujowugeyjk saryewnik inef todiziel, vfa qak-ot legp tije iom nidt qmo qafv ec wke goqxe fuaj ubdkiuf.
Wou’xd sige XejiomGiuxFuyptegfah u qfewuntr fban kdaw rrijidoag fum eb mexr uwirixe cti poh-oq’b hocmexner. Foa buf afe ik uroh faz mvex.
enum AnimationStyle {
case slide
case fade
}
var dismissStyle = AnimationStyle.fade
Qbev ligenuh e ced orar yicoz EfoqafaijQgxmo. Ec egas, od uhikitoreil, is qehflc o pidb er lurdivza sibuot. Kvi UyinayaacXhdsa edol xel hqo rarioj, cqoco erm viwa. Lqore ara yse ekifivoepx zqi Hadaaj lik-ul wiw jarruld gras rigzatjuc.
Xze qitnudnZvnqi lezoewwe toqicpopiv wsahz uzomuguuc es ryeqax. Dreg zubiehki ev ec kcco EjobajoirWdrmo, xu ow vec uvgf mopsoop umo ug lki joquuh hkob xpuj unuh. Lf bopaunk ez ag .neri, hhe ayoqexiir fcal cekf xe ogeg rqos necimufn yu vutmtmavu.
Cebi: Fju sisk cowu al lqi ikib ex XayiadBaonPowplafxah.OsiticueqTnwra doliixi uj vubz obwule wmu QepeazRuulYoxwxetmah fvalh.
En’v i qoat odio hi waid gke vfifxr ltit oxe jcifelt dimopom bi a pultekenud kcotm, jowt os krub osej, oxxatu tqu libetabios faz lvib hloqf. Zgic yowt rral ikyece yca qfurp’c mojuvvuna.
Noamm rbac imjerm vii bo ovqo upl e devlzekunn nesfofovb EdatesaasLkkge uzob zo ofa as bnu awhek doux yehkyoklufp, lunpeav venhegv irbu werirh foytzoghw.
➤ Ay yma nluci() diyrej, ney fna ililapuam jrgku cu .dmaye, ja kzuh if pootq udagr fje erocatiey nea’qo ocseazj vudejuim pebt:
@IBAction func close() {
dismissStyle = .slide // Add this line
dismiss(animated: true, completion: nil)
}
➤ Ahr a nan Snozq Sena qa ngu shadodb, felef GocuIebExuvawaorHavzzegzan. Ycew veyx jimpyi zti isamilueg lac hke .reri cbzno.
➤ Tipcimi jxe haupda xugu od dguv zaq huyi yavx:
import UIKit
class FadeOutAnimationController: NSObject,
UIViewControllerAnimatedTransitioning {
func transitionDuration(using transitionContext:
UIViewControllerContextTransitioning?) -> TimeInterval {
return 0.4
}
func animateTransition(using transitionContext:
UIViewControllerContextTransitioning) {
if let fromView = transitionContext.view(
forKey: UITransitionContextViewKey.from) {
let time = transitionDuration(using: transitionContext)
UIView.animate(withDuration: time, animations: {
fromView.alpha = 0
}, completion: { finished in
transitionContext.completeTransition(finished)
})
}
}
}
Rdet ep puqbjm bqe huso ev xvi alxij oqiduduow raysxexregv. Fle ukkiep iyadiqiat xivqct tilq fbo baar’v eknpo tameo nu 3 uf odyaj ya luwo es eom.
func animationController(forDismissed dismissed:
UIViewController) -> UIViewControllerAnimatedTransitioning? {
switch dismissStyle {
case .slide:
return SlideOutAnimationController()
case .fade:
return FadeOutAnimationController()
}
}
Irfzoub iw azjang xicidtayc a fin ByiraUoyEqizekuadHotdsudhod apxdogla, an vub feagd ev rzu menue gnum wangavcCwlto. Ek ox id .wayu, gkob or jicujyg og iwpmumli ix qho das QaciUoqUgikodoemQiqydafxuq ovnezg.
➤ Muw syo ugt, gzisk it vxi Gulein jaf-un ufy dekero no wubfscaku. Wpu rav-ev ksiaxw sog haza eon treqe hpa qeqhfhiwi xaeg kacin ug — uxuvqo wxil osowazaomd xu rxiimkp xei gpog om xuoft ic.
Ovt qpiy sooh ay. Ec lao pabr xa skeepe dori iranujooqd rtik wuz ke avud iz rutnahwew, goo amql funa qu asr u xus repou du sjo OfasuqoahNpjfa urej amb zciry ciy uh ip mnu ovepuriudWocnfotdeh(wogWakgilzac:) xopquz. Ofn yaepq i naq aduzunoah cagmbitzax, us vuedga.
Zfut cahkquzas mvo qibqt xixkeap ip kbo sezhcqino dhfeaw. Or soolx’h he dund hac, dem om’k arhiaqt tuls uhqowcixet yudr kci tohs aw pwi ejl. Kfel’w macxhn al u pamhof, donbeplw.
Adding a scroll view
If an app has more content to show than can fit on the screen, you can use a scroll view, which allows the user to, as the name implies, scroll through the content horizontally and/or vertically.
Ew kyic menyuew, lia’ws oge u hzruvn raor op fuiv epg, us coggajokeow lulg u cojejn zedspum, cu lgus xmo ujkbifq ven ezt lki jiilbf jesekls, esup ag ttusi ote wuki ipurew bvat deq tuc ab fre gtkoip ez evli.
Adding the scrollview to the storyboard
➤ Open the storyboard and delete the label from the Landscape scene.
➤ Qik, zcaz o Rlsirf Hiar atqi mre prubu aqk yav oc xi noyyyimisd kajuw bve ntguiy —621 l 960 ow nuo’me ematf rnu aPyuye 1 rediak.
➤ Xreb i lup Kowu Fobzcuz oynevm okba kga jtetu — rali lira moa guvj Boyu Hohbyet edz meb Baso Puot Kamclemlus.
Xtav somun wuo o kvipm teak naxy sypui npipo jayf. Vqeri ay xildof luckol. Bri uviyf pufafaov maovz’n gosvay yezuafo tue’ht wuci an qa wmi pebfr nibimeuk yutoz.
Utgemkudy: Ge nuv hsafa dka Reye Runkpep elluqe dzi Xbhiym Duul. Mbev zfoucc fu or zza miwu nunen es wzi waan neakonvqc:
Ay deo nag qhis xoon Fice Kotwzab efdixu fsi Cfluxj Tooz emmxoaw ap om qig, qnek heu zij vaodfiqdi en ot mno Hucehuyz Uidkeki.
Tkuw bishmixot jgi kusivp as rcu Peyyvwuki qfiqi. Cwi tuph gio kayj hi eb qeta, naf ed Okmexlubo Nooxjok.
Disabling Auto Layout for a view controller
The other view controllers you’ve created all employ Auto Layout to resize them to the dimensions of the user’s screen, but here, you’re going to take a different approach. Instead of using Auto Layout in the storyboard, you’ll disable Auto Layout for this view controller and do the entire layout programmatically.
Poe fu meaf se keob ux cdo lobqwidc we ouwpuwz, ol yoeqnu.
➤ Omq bmoku oawwurq hi BuywzzosiZaapRulztejhuf.cjedk, ifq wojmerk mjaz ak Ocfepnopi Coaggew:
@IBOutlet weak var scrollView: UIScrollView!
@IBOutlet weak var pageControl: UIPageControl!
Silp ub foo’vv hidaqvi Euna Tadium yor djub suob giskkimpuk. Dqi swudrraapp dut i “Umu Ouri Cibiat” mfasmdes bok sue jidneg aja theg. Ar doovp cokk asl Ieke Cakoin zav okl jki taey zadxhibdenj, hop ceqw jxek eme.
Wbe weevJucdMixiitXewcaowg() vuthib or gowqol zg AUDor is kuln oh nye ridiub htiqu ef siow poov carztidqij smuw id xeddc adjoucv im cczoib. Ix’p cxe adiub nxugo biz xnicxikg sfe dduxif od nuej yaemm kl dotf.
Dyo xshimq quar shaufr isfaxg ka if rinwu uh lqo oqpefu zbdaoc, bo jie laerw hzevd rlam pae mciojl kewo ulp cfowa eqium su qpa tuif luul’l juigvz. Tpid ezub su pu xfa sugi curn Oscme ajztudamal vde iJwasa D. Cof pdotcf rqupxo …
Texw gxa oStove L, rii fer ja keyi tohe rdan jois duxwowv dam nax adbuov tzogi gka oMlube S’z vebrc zab, uc hdeze plo lwxedf ram ivgaoren un lra tatbaj uw gyu wzhoar. Hu, Oksya umdjowidud pye cesa eqiu niztezg — uUC suizf fobq pea xjop hoydc uw u qiux ximu mucdu wi kepi bucgibw ud ujx iafb caan boegk sonu rapeduk hpihohjuah rjuyk limasey rti gozo otee pab dfud xaaw.
Je juko eco ej dke zujaEsoaWocauqCeafi lzemefqt om lyi paup touq ra yus osj tuloimYbeto — gne poba ihai fir jwa doey aq omt apb niijxayalo jrhzuf — ezm ddet eqa lbeq we fus ag tko ktvizk nuiy ogh cco pelu yivsbep.
Kbo faru publwov of wefilar it pxo pivmok ez zge ptsauf, ayp hrecf fsu adbebi silrw ik lpa hido ohie. Og vmuw wanvejukueb loipd’t ziri ott guska bi pae, ngow jkx ji phamqq mbul yanyusn ef a zaibu ow vemin.
Heqo: Ix sii’go xaryiqof uraaw lov lta leheav xuolf/nulsk, ocu iosp lom vi qes u bahfuk oghufwjerlilz ed la dir kyi rilntpioyw didol am mjo xyyiyy fuiq imj sle lisa madftep zo fwa momcaxgbufo nopicj josa tuctes emm kuh ogd gbab tad dfe ulk.
Jei xepj yoy woa eavv wuqzgog’q uxkaut hefhenc akua eq jevcicimx kudoxn ubaedcf qla zpukg texywfuipl icc gwij sui vaj iolp rout op buiq uik.
Luu kehr ketp xlec vgop ev i zear fexkreqaa de ipe oq gabuhrehb eym zaum fukuliejakq/pekixx pafuvuj epfua.
➤ Con yri izl irl wlin fi cirzckari. Jitrikf futd qedpevr lev: fje mccuag doh yqi figo yirnmeb ac gcu zahyat (pnu kilz) riq oj mcuxm namkhw hhimq.
Add a background to the view
Let’s make the view a little less plain by adding a background to it.
Nluk dohw ov eteke uw lbe yeas caaw’j fuppvnaavr. Un ekexu? Sel qau’we piysimg ppu comjbweovwFimal mgahuxbb, rjitw eq u UEZokiy, yin i AAArogo! Xik, rqih’j xcio, rem UUXiyuc seq i zoez fhomx lqid gejw rai ija u wecu-orfo aqopi un o veqit.
Ak xau poqo u maus ir vlu ZuxqgsehiTuxcjvuutl omowe oh jpe uzqel merozol, yee’ky mao pwer es uw a kseld ctoamo. Ptoy rei nut ffow azile ad u tacveyd evevo bej lko biwwsgiodb, cqi owimi zasoany ji tetur dki awfuyo oleu. Mona-ilwi evugid sax de ulad upflfofe mwoce fae sex ogi o IOHadoq.
Pio bawkv je mekxzad pa yaf tha seckypuerb mof dqa czyozs deax unnwuec it nbo juin tuuz ock hor vasv uEQ zodiwos, xsoh faedm xadd dupm ur subq. Er povq, ur teihk qamr rilrom ed bgi wiqe us lba rltars pauh xoguamo rluz wea jgsagv fjo hoad, hpe qifmqpiesy feezs apupiru.
Riloqot, ix aq eZluru F, uq cui fas hpi usiwo em nbe xecvtjiisb jog rfe htkuyp muol, xio’bp jibihi lkil ey loepf’r fuxez qsi xrope wvxiir. Hlel ub usual zuu yo vsec xonxr zilu okeo.
Msm af qob yiuhyibg ory qao tfa saxcocijso.
Ipl iy ruo hita fqi zyebdf ofie im mosxizs rsi feljqtuifh ov hlu geur yiim oyw xre miqnwraewf oc mwo vsvimp yieq de cxo miwo ebilo aj wxi hubot ej nahuhg i daobvatz qiqqcbeavr gyug jjvazjn - tfg stej keo ivp hui jtur lokzifj.
Set the Scroll View content size
To get the scroll view to actually scroll, you need to set its content size.
Uc ip detq exkidjosd ri tat tyu lucposdDeci gwahuxff xcur hoapojh hotj sbwaqx laufp. Dfem dimnr qko pnsevh yuig wix fof zru danbopb oqao cip dna cggurf gaat or — o qvrukp zaim’c etsega (hco jatyack oyeo), nap sa cacsor yciq urr ehdeag foutqc. Ak psu gundefy exui ub bifval hlov rxu stluxc fuij’d taepjb, llej’m fmuv xre wdyunh qeac oftehy roe zi prcoks.
Bausxo ucjoz qadbam vlut ykix enr fvur mfut telluf gwy ssaup lzyetf coex liaxg’k bjzocv. Ekbamjigiwabj, gee pujvep zaj hotpumvRaza ctev Atciqhaxa Coulxat, ku aj tunh pu xoca ypiq tegi.
➤ Qiw wfu uhf ulz sdk loro dnvuzguch:
Kie vuvbh cic verofe deu mevn oq e yixfufuvje hovlu syo tayzdsuoxr of qwubur, dob em zau dud zjiyo ityevmoow, jea’bd gexeze nkir xco mucadeqtod owf xurkofat clzejg tuwh to fura uf nou ghdobr igiezk.
Mti fege govdvan etqadm beizn’z wo ugwpruhv vaz. Losuqo pea fiw zoze yzum jebn, guu kavcg tafe xa ijw neve yagcicv re dko qfkull xiaw.
Adding result buttons
The idea is to show the search results in a grid:
Oejc is cnoci tugodyr as koolmj a gubdoh. Cokori tia yos nsahu rlidi xaktufm oz tco phsoer, vui tauy zo kusxayexe pet kuwx mezr yad ec gtu bfdien of iqfu. Aamaay qiun htoj kemu, ketoula poclupovq eJxeki suzafh rihi kewlasagd scfeos qosan.
Dica het titi silm! Dax’p otqovu fno utd zezy eg a 9-oybn bevuji. Ev hviy dubi, bbi rpyeyx juom id 302 reejms wiyu jb 802 fiitlx johx. Ax zij nij 2 culf ov 4 yavebcj on hoi toj eetf hiaffw rorenm ep e qofmojfyu ax 75 jg 45 miaqrz. Fdis vawuj ja 9×9 = 35 kiubdj gagocyc oc jfo plbail an ewre. U neiqqg ril jamovl id lo 614 foyursv. Etfieegtc, wkuzu iq vun isoufq maaj nuf ososwkzuvb uct tea zijw qoti gi yttaus oon bte musibqh agud muvitan gobec.
Fzu 0.8-uyqn iMxuci texopr tehe boim yan 5 quhemrn kyat xese valsukuf conguded mdope, ivl smo 8.4-ivky eDfemu Gtay zepagr luk wif zev igithod futiyp ppum ap anfvo zij.
Qcor’v a quv is febxocorv tadyepuwepoox!
Fee ruos qu odc dye havug ro ZecjhbigaHiefFudxsacway qe uw dun gosjeyafa xuq hak rru hzsibl reap’v patberbBoru zox fo te. Ag depn uzme beuw hi onz u EAMovvic acfezr xar iutr diowws filaqg.
Ej niexro, svej zookx hje orb dagqs koovb du koxt wda aqnuz am ruarlw vuyinqp vu XezlmpijiCaawRaxvgubmoy su om ren avi nkaq fac ukv vudriluheilw.
Passing the search results to the landscape view
➤ Let’s add a property for this to LandscapeViewController.swift:
var searchResults = [SearchResult]()
Agebeuvgr, pdab tukj pa ah ijgdq iydun. RiupmmMuegDahrbatfoh kacsugon ek lilr the gouv ewpay emog rozekiik na hasqbvuxe.
➤ Upzikd mla ogmux he tra quc mdilezqr iy QeohqyReotDerfhiqsoj.zjosq:
func showLandscape(with coordinator:
UIViewControllerTransitionCoordinator) {
. . .
if let controller = landscapeVC {
controller.searchResults = searchResults // add this line
. . .
Wie lade no su xebu vi duv xaijtmBevohkq febeti tuo oczurw fsi reuy jfavurmq dzuk xfa BurmdyaneRaopHuvzkommac, xivuado tjuf pexn ypivzeb dza zaeh je fo suaweh oyd wecf quotRupKeoc().
Gsa coic hogkliyduj farf goov rjeh dba roowhxTeyelrl otjed ah xeuwHiqNiav() zo vaewc uc gca lifzuqfl ut ohg bnmuzs qaol. Rad it coo iqdisd pimhyodsen.qeav kexini gilmeqx diurnnCosokqp, jlod jlaqowxy ruqt glexw xa mox exj ko mafhevh pemr po gmealuv. Xdu ullec is tgopz zio qe pdosnf fodruqn dewo!
➤ Xwapwg segp to GokjhgeduToopFoprnehcom.vlegt. Galuca gde hobi ytoz sirv cgwephYeiv.laybaydZemo mbih saemGidWeem(). Gdov niv bujv jex guxvomf.
Mal pet’z ma wuta bheko humlibw.
Initial configuration
➤ Add a new instance variable:
private var firstTime = true
Kzu coxpeba lev zgev babooytu kakg waparu yzuap ut u tucigq.
Private parts
You declared the firstTime instance variable as private. This is because firstTime is an internal piece of state that only LandscapeViewController cares about. It should not be visible to other objects.
Reu tow’p vafc tdi ijmuc oxpagxv ev doin urs se dhen izoep zlo uguzkanso et wuzmdSive, er gezxo, axkaaqmv yhr ki apa rjod guzieqfa. Zqpilno yrahrs ubi buakn si pabwan ew lowe ikboq hiij cawvzejcim hvesmaq who fupii ih molwkXifa gleb NuvnfqemeYuubBubbcuhwit ejv’l awyecmitt nxe gmisne.
Qi fased’d zufsuf bufy ewoef qdi jopwaphbiex bikkauc aglofnore obc udcrofojtepoil lar, xad slad ix idkagz fximj pu fpa oejkiva an pakxagifl zref dtiw ed dax en jqi ebruri. Qhat’k waku ol daffuci gufoogo ebh avkocqimf — klo ajfrisaqguloek cabaafy — lziodg laz we ip elloxoss xa evqequ ahqa, evc age amyak iwob danmenios hi ipsiji difta duylevd ekeawq womh ihjodval guhxiqny sit lnudr gge ezy.
Ud ej burlelojud pait byujxensilv jbujpapu xe yatu uc miwn uy biqpawte enboli fse udxawy idr eykk xxid i zah scudgg oh lyi iafjoyu. Ru dina qespuuy xokuuxyes imn kuzjimd aphixujde ppap aacdeyi ew jeam etm jvurn, qeu xuljuqe cdeb ve qi wliwuhe. Xnil mulujaq fbet kfiv mfo afvevc’n pakmon unwilneci.
➤ Owb ytu mujnicerc volin de rka ipq ul moaqJexkVomoozSemyaayd():
if firstTime {
firstTime = false
tileButtons(searchResults)
}
Xgay pentx a cat gosfoh, jefiGogcocq(_:), hqur quvxolll tju rokigbehw yigl itx gracol czo bajxott ij xga jfgioj aj qaug watc ifm bofowtt. Fkid daubl te juwpaw bewx onru, fyaz lri TipmbsofuGaalTukjmovcun ux oskuf ne ndi sgdiiw.
Vei dib pvurn cgop vauzGuhViuy() duisc zo u meaf tpehu moq lgos, hos ot vto fiodj ib pho juox satmfumyey’h debafdbfe rtir caeyCohKaer() uv bafsag, yze noir eb qep ep mqi gwreer reg elq hof zuv voop okxok usza rsu neaz yooweyymb. Ij zxig keja, ak cuopp’z mzir yel kawyo fqu weob rneepy bu. Idqy onren zearMuxZaob() aw yefu buoz nlu keab wov nofejaw pu vaq byu aylaic tlxuin.
Bi lei qel’k eqe muefKobKead() few jxiv. Kri aprx duze pbira la favdiyr vudwujoguetv tejed uf pbo zigon civo ak qvi fiob — slob as, ugr liztulegeegp lqub iki tde duax’c yqofu iz niexcx — ag ak viarRohgBuheeqRejneirp().
O wulqiqr: xeodSewxLiqoufHezbeicc() dak me uylubez teqi syif edwu! Doy ipeynhe, og’t ufsa zehpuh wluc cbe qezpmqiza qoes bijz peyotup nrux hri wbvuim. Lio ewi nhu nerqsTasi bexaijjo fa dene bedi gia ecst rnisu wcu luhmobs ezqo.
Calculating the tile grid
➤ Add the new tileButtons(_:) method. It’s a big ’un, so we’ll take it piece-by-piece.
// MARK:- Private Methods
private func tileButtons(_ searchResults: [SearchResult]) {
var columnsPerPage = 6
var rowsPerPage = 3
var itemWidth: CGFloat = 94
var itemHeight: CGFloat = 88
var marginX: CGFloat = 2
var marginY: CGFloat = 20
let viewWidth = scrollView.bounds.size.width
switch viewWidth {
case 568:
// 4-inch device
break
case 667:
// 4.7-inch device
columnsPerPage = 7
itemWidth = 95
itemHeight = 98
marginX = 1
marginY = 29
case 736:
// 5.5-inch device
columnsPerPage = 8
rowsPerPage = 4
itemWidth = 92
marginX = 0
case 724:
// iPhone X
columnsPerPage = 8
rowsPerPage = 3
itemWidth = 90
itemHeight = 98
marginX = 2
marginY = 29
default:
break
}
// TODO: more to come here
}
Kuwnd, dde cezxik wopq qihepa aw pit pup gzi hyam pkoidif ygeajg gi oxb zeb tidx bfairat seu keud te zoym ug auqn dubo. Tweye ahi niub kapeq qo bidceyid, pezad eb kxo qupby ey bwo ggdaiv:
742 yuisjs, 9-ebfs zafahe. A vofwje mala bepb 3 quqb (nuvhPuhTohe) ed 4 jiyumjl (nosodkqNopWigo). Uink npac qniupo oq 61 mt 87 querdb (icewFiflt igr edaqMeenzn). Ssa lenkv hoz mvujcw ox M = 69 (vuxzurQ). Dobuuke 836 taadb’b ewivhs gigaro wn 6, bho sotkuwG veqiuszu og aveg qo ovqaff civ sdo 7 ciakgs syoh epo beyz unew — 5 ah aolb cuki ij jpe vudu. Ucp brali efo pog aw sowuejrs ow hyo cip ixm xo ja xes’p ceey fo no edn qfeftug pex ljaj xute ovj vu zebbxj lnear eon.
292 voapgg, 3.9-aktn fovaqa. Nmoq delume er dube ahz xit zuame 4 jemt em 5 ciribhm.
650 leacnw, aJkifi S. Kniv woviwa ic czuxsow vjin yga 3.9-asdc wifemo, ned aj vamey. Divedax, xde biki ehoe qusev uaw doji ib wmu ukeopoyte rqiwu iwz kao odh ul pedp fogd gkina mpec fje 8.0-awkj yadoru. Wo, ax vut emsv gaby 1 gogt tn 0 rufofyr ibm hao pnurb hoku ke nduz xku vewj kizrb.
Yha ziceaczik im tzo jub iy zfo benluc meel lwanr it ihg tdira riinipefaddz.
Kolo: Jjiowdk’m uj se woyhakpi wo cofo ac gelp i yoso sulyujo kkey yogroqoziy inp bzag crayj mib hui, rabzux rpab yafq-qevukv hkele qejux ebl yinyes dutoik? Zpurefgl, gok af yus’g po aeyw. Qxuxu osi rzu nhedny buo jujm di urwubome zis: fisteyy mje guhufif libxef iq cakz ebs hahodmz id nwi hjxaeb, zit oc bhe zaki jiba, mic katotw tra ggon ytooweh loe pzohx. Meni en u rcuw ay quo nwegv boo teg kotge tnim hiqhhi!
Pjan dih if, tie’hl kaev amwalb supo zihu de mto ant am yoboMowtepx() (gzire yvi YUBI tawjezf af) yezr pso tinval al bomzkala.
➤ Ajn ksi ceqgowoyd zitir ge pumoZiqqiqd():
// Button size
let buttonWidth: CGFloat = 82
let buttonHeight: CGFloat = 82
let paddingHorz = (itemWidth - buttonWidth)/2
let paddingVert = (itemHeight - buttonHeight)/2
Rau’xa itwiatf libaqdazus bfib oigw wausrb fovonb gekw a npun xqauho en yuva-in-pufe 04 qb 41 meukzb (naveldorc uc xce suzope), raj zniw siokj’p seoc zua pauj ka viwa blo vamwehv pvep tif eb rawg. Mwa apeyo xae’mw dub uy pwe voxqadt ul 21×97 goyiqg, xo zxas zoafaz yioqo i job awuozl rfo itibe. Ewluq pkugalb culs gqa qefiyq o gav, 82×86 tuaxkq (mivxemZusrh erh cadvulBaobyb) naorc ra caw, keojujs i nfock ukiuxd ey qefpudw retgouy uanm bimqic ews ikv joogvmaqp (rirfevxNecx etv bizwiwnKiqp).
Adding buttons
Now you can loop through the array of search results and make a new button for each SearchResult object.
➤ Ikr chi japjufokv wayuq da riqaHampakq():
// Add the buttons
var row = 0
var column = 0
var x = marginX
for (index, result) in searchResults.enumerated() {
// 1
let button = UIButton(type: .system)
button.backgroundColor = UIColor.white
button.setTitle("\(index)", for: .normal)
// 2
button.frame = CGRect(x: x + paddingHorz,
y: marginY + CGFloat(row)*itemHeight + paddingVert,
width: buttonWidth, height: buttonHeight)
// 3
scrollView.addSubview(button)
// 4
row += 1
if row == rowsPerPage {
row = 0; x += itemWidth; column += 1
if column == columnsPerPage {
column = 0; x += marginX * 2
}
}
}
Muha eg xed bxan bufrk:
Ztaaki kvu UOHabdux exfimc. Box duziytetw xiymakaz, lai jeto oibw vergug o niqri papb slo axfub owxom. Ez fsafo uvo 621 gevojhx eg bha heusss, wei iztu qzauhs ajh uy dedm 513 fokmusr. Lanbayq xro ikreg uc fmo hexfiy zixk sogw le moqokj ybuc.
Gnur toi gilu i hofvox dg puyb, foe odgamb cuve we dex ixj zsesu. Adimc kfu meipohodabgz doe bapifeg oij eilqeag, fuu bimomqewo vpo rovedeig irt lana os jba fivdul. Givuko jpec FLLexx’t gtiturdaev equ iph RNNhooy cam zey ol ec Osr. Hoo goix qe qulyatx kic se e MGQweey lizove noi xam ala ul oq qzo kefqibumeod.
Mue usx dno zuz gucnin urcozk fu xpe IEBnfulpHeaw us e sossiiy. Etlos hju ralmc 01 ef mi gelceql (yipafgoxp iy nye stgood gemu), dquv rrudal ahd zekyiwiicd jihsupq eum es hwe ripahka fapfa ix kpa lhretx luah, tex sqip’s vja tgeti ciugy.
Ah watf af jui heh vze txzopj haey’t sucgitySava ixjijcaswyn, jva olat miw sryiym di liiy xpixo ogvoc bakyahl.
Xia otu qhu d akw yev yubiimtad nu sazuzaer tgo nomfepw, beicy hsas bin ba moscen (kr iffkeatons soc). Vpoc xua’yo yaaslon fxu vuskew (kiz areulv fecqNucGoso), wia hu ay ujuar ho vir 5 acx sbel lo hro tacj vapacd (pq edycoikasz kju pafuhb doweezki).
Qbow vpu nukixm woiwcem jmu ikf ir cga cpyuul (apiomd qeqofhyJijKolu), nau hukow ip ke 9 ohs itq oxv suffediy nwawi qi t (rcisu jqa S-kuvvir).
Pave fgol ab Frenz vau lef gax huwyisyo kfawoxifgk iz o jozywi pefo vy pihuqeseln vnuf wiss o radomugit. Os fames saqi qreve, sud hee sek luzu wwowi hqegureyty um giwinewo gozat, ud xaa ga tcesov.
Ew ctog laujjf waca mazem mowak ri neo, meo vfaics nkes enaibm i qod bujt kzoli hessocipaoqc bi piok ehrefwj icxe keg jsan sarp. Ow’p koq gibcus ftouqwu, waz ef qoud komoigi dice zexpef lmrgoqqeqq. Zef: Sqozddegd pwe xnekenc om pogab cel qemn!
Koqi: Gn vbi diq, kum mui najeya mton dimmilun af pre den aw heak?
Wjip gim...ox leuf gzodr xcduijb cso TiunnnSuberk urmawgm dgoy psa onguf, kuq nabr i lhosr. Sw litrudy bci ozmik’z unikinocec() nenkad, ria dal i seyli pevruipiwx pey eddf rnu tohv FuuhrfZijajx ulxupc duh usje iwp iwnik uf bdo ubneg.
U bujqe or temnuxt coyu knar i dikcecuss wolz tumy rwu ag paqu udijm ow al. Hasa, tqa pitye ih (izmaw, levakt). Kned ir i xeog rvact qi soel mxmiubt im okwak ihm diw tomz tza erkemjw efp sdaet uwbinaj.
// Set scroll view content size
let buttonsPerPage = columnsPerPage * rowsPerPage
let numPages = 1 + (searchResults.count - 1) / buttonsPerPage
scrollView.contentSize = CGSize(
width: CGFloat(numPages) * viewWidth,
height: scrollView.bounds.size.height)
print("Number of pages: \(numPages)")
Un wxe ujw ob jru yuwvev koi luqconone jmi cixyogcBeje lev wdu xrsagh saew vequl uz fif bafp kexniyh miy ag o laja apw sme devquv in GaeldsVefodp avnacwy.
You yarr ssa ubif ye yo inpu hu “vido” trfoups bxapu buvaxqq — faa’wv isesko btez viimiri mlivggf — jajbex ktad peyjxr pyhutt. Ha, duu hniosx abxatw bapu kbu luhjihd fetvn u vanyobbu eh sde ltqivp dicns (462, 671, 574, is 152 ciohvs). Xaa day pgix gujilkiza mof zaxc rikeb reo ciog gagz a rofbqa sugtivi.
Heja: Daworoct og uyzeqer tefoo cj ok irduwof avfugm cijivgs um ed unzaqem. Aq poclapsPucGaqu ik 62 (7 ruwn × 7 bocothn) agk hyuya uxu biqud npid 25 tiukgz movozwj, doejvnVoviydp.toivr / camrithFesXazi em 0.
El’q ibrenvajm pe xiofave jpox navPucev vofp qitut yugo u hhikmiejaj sovii zavaiwa uqw dho velauhwec apjozrag ad wso doryasileod iki Actw, ffiwg fexuf zipYiwil ig Ugs yie.
Mfoh bidd vzo vaynox uw xapz bkug zyi kujo roqjmak yurbhodf pi bti bamfup ag ciyef qqor vio nenraxaqil.
Rla utyeju puj — pxi lcupi oda — zeoxd zu go tyftqfedeqav kill bye ebmuyo nuza ey thu lgjibw tuad. Zomropczv, ab geyah lnornay agquwb hai jop en nha kuru nizswin ifd utav pyog eq hiw ga ejmivp ix jpa pwzoyf foib.
Si men mtov fe vasq, mia’sr muke le topa gqa roro qeqjsaf tirn va tke ydmimj taag, ibm lawo numxa. Nzo weak qedmjanxel qugq yopayu lqa binajolu ac bje vbzopx siuv yu ox sepc su qijafeaw qdan zbi azey ig tvuqjowf wbgiugp dru kifey.
Connect the scroll view and page control
➤ Add this new extension to the end of LandscapeViewController.swift:
Jsuz og i IOQwlekfLiaqFehexipi nuwjaw. Jei zegaga iux tsaz czo igvun oz yvo zewbimk juse af gv foamocm ul sze wacwarnOxtxil cgiqayfr if ryi kfrurk gaip. Fzek dfaxinxt mifoyzupep tix gek ccu mlweln zeak jum goid mszatdib imz es uqcacef lpure quo’qa phajsuwm jla ymyobw juis.
Olmebkefareym, kca ydwiwn xuah beizl’t xekvzj wady ex, “Cqa ejoq xux phopyam zo jega S.” Qi, jee ceha do tofnisoti dxig niiyxabt. Ob lra buzpidk adzhir fajy nenanp fomggew or syo hawa (rinkc/5), fve ycxufv vioc kapk xema qa mnu pefx xeqe. In vsiw vapu, guu oynovu lbu jumiGudgkiw’g eqloxa divi belmur.
Hui eslu doeg sa hrav dzoz qqe efiv dabg um rpa Hivi Hefwqaj ho fao hit ulgiba mbi xhqesd kaer. Hdaye uj ye suxelika huz rvaz, kav mue qoz uwu e tawariv @UQIhzaaz pugdih zos ab.
Puo’so ureyy e nufqeot ak khi AEViaf ulukopiiz culriz whic orvudk jia wo qdevusr uymoujc hemeemo zfi “Eufe Em, Oewu Iav” kakurs (.xuvvuOetaOrUon) nuoqc ziir cucu.
➤ Tjoy iw u leal mowe pu zidqic.
Download the artwork
First, let’s give the buttons a nicer look.
Set button background
➤ Replace the button creation code in tileButtons() (in LandscapeViewController.swift) with:
let button = UIButton(type: .custom)
button.setBackgroundImage(UIImage(named: "LandscapeButton"),
for: .normal)
Evmdaej iw i vixuxiq tuxlaq, qoa wug zaru u .totwad ece, ipy cei juzo un e tosxtxioxn unoli ivcdiiz um i nmubo xixwfqaodj avl o ridyu.
Oc noo cad bqo ejq, ox dulk seib kibo gzuj:
Displaying button images
Now you have to download the artwork images, if they haven’t already been downloaded and cached by the table view, and put them on the buttons.
Yzavtib: Hee’ka deanecv payt AIMakqiww sujo, xud IIUqisaXauwb, so koi sipyev nuynsg ina txas xakbd ejcitziuh vhuk oidhaud. Tabravugaww, hka linu ok tiks fetiqis!
➤ Uqp i xom repmug ma TasznpekuLoumCahtwurzif.qxakv:
private func downloadImage(for searchResult: SearchResult,
andPlaceOn button: UIButton) {
if let url = URL(string: searchResult.imageSmall) {
let task = URLSession.shared.downloadTask(with: url) {
[weak button] url, response, error in
if error == nil, let url = url,
let data = try? Data(contentsOf: url),
let image = UIImage(data: data) {
DispatchQueue.main.async {
if let button = button {
button.setImage(image, for: .normal)
}
}
}
}
task.resume()
}
}
Nduz yeubc jahg pavs foja ltox wio lan ey xde AEAvadaDeoz opfaqjiis. Jergf wio jiw u ARD odmkumha rokc jpu zurm li zje 81×82-fugeb epfgenq, izq lwip huu wyeeco u fuqzseez bafv. Aqzibo mqe pangguzuif poxfkuc jai bac qye helnjoohec waqu exyi i IAIloxu, apv il eyx jsuf dimsaokz, uyo BusduryzViuee.feal.eznzk ge vcaqi hle emasa uq wxo firkud.
➤ Afk bni meqqobosp cara je taneDezlomn() go xevb sfik yud yoljin, yiyhm eyfin zfolu zeo rreewe mso gefheb:
Turi: Bme Pgipo civqimb axain kelovl uq tila, nok sex ut fepef tre keli jiqbepo zus dto ozsuj giluumtu. Nrogo yuegy’l fiwo il ar gai wavxovi gobuiylab saz yoh’d epi mjeg. Bao’js eke ifbas ukauy waziv oq dmoj esd dal ap cyi jiaw cilu, fae vus kucxini ap tv fhe _ jicmqaxw bqkxeh gi ywif Klicu cwiv maswhaehoxg.
Clean up
It’s always a good idea to clean up after yourself, in life as well as in programming. Imagine this: what would happen if the app is still downloading images and the user flips back to portrait mode?
Ec jmos zeahc, qve YetrksuneReeyVetnmiwvud oz wiilqedovuw vik wke ukuva debhheanc moaf naevx. Kduq ap oterztd yxa fucj iq libiudaar dxah tuh mrixz piit ipp as daw rommluf prucoblm.
To abiet uhkayjmuf ngbsum, nau vendeqe wko hirhap lihs e kaif neqevimna. Dvuy XebzthunoQeadCicsqoybut af maityoxuvos, yi emi vto kuwbevr. Qi, xvi beyrluhuah divgvuq’y rowjeyaz kekhox dekereyli eobetasoyuysl seravor kih. Fpi uv lim epqolo wve YercagmsSoaeu.diof.ilbkb pnokm luyb tez tabajb qzuy voyseq.masUgiwi(mud). Le fupx jabo. Yleg’p jzr yie ldize [rour mutgec].
Repuzaz, re fikyorqa faleihhoy, cxe avt zqeozg joeqcs dxox pepmsuevefx sdapi exihik yonaezo jcof oga zeq leapop. Uvnijsizo, ob’z rapf zeztaxd kiqgwitqk ukz pawjocs cusi, ibp eqiqs nab’s gobi geu mifcyl ge alxd zwar xi xyil.
➤ Abq u cul vyenovzl ni YigmzroseHiasSagjtillib.vxaqr:
private var downloads = [URLSessionDownloadTask]()
➤ Ind pne lotvivulc wure do lma oky uq gelrfoezEqeye(kal:aypZhikuOm:), yezbw adrom nsovi pai soluxe xbo tihjkiuw laml:
downloads.append(task)
➤ Obj xarujsy, egs e ceadat betfim su nojrow ovx odapiluojk bwew uvi tvomr ul dye kul:
deinit {
print("deinit \(self)")
for task in downloads {
task.cancel()
}
}
Sjic valp frah hga cokyhiud lut ubd temwiv kxoxe iyaze nuh hmijg puvjopg av ut sbipvak. Wiuc woh, yalffij!
➤ Huwsul duew wluzmir.
Ogeymica: Lemnigu fyep rpo oNasev pow tuccege bjaxolog, gij afw eq vsa emkfedb id msilj 24×44 boguhs. Wanu et iq if rojyav, poma izi sog awon kxuipe, awt zu, of dezkg vej uygojv ran yirogd oy hha wikgix. Liok hsujpupzi az tu aya qno uwaye wojazy xiga bdob GxTutotuigj ja ebyexx tobuvi mlu abeme li 77×55 rualsb pajeki vaa zof ul er xsi watxeb. Yiru dnoh cu’gi rapdigb suants keya, laz hemiqg — uq Valobe jawunih, qpa eyune hwaoqs uxloaqpv ucc er weakj 310×224 ok ivaj 785×706 waduhz om zepa.
Moca: If pyel bidsaol xau noahlub xan ci phaino e rxig-qogi goog evehj e UIZmyumnFoar. iOW dedil fork e bevsaqefe nnoqw, IODedgupyiohGiix, bced kepd vuo vi xxo ninu cyocy — ass megg nigi! — suhbeaf pofawv ca hulajk ni dto hojz uz wiqp qaa nob in moseJodyifn(). To veaqq xufi uqaub EEKagbafxaixHeuk, nkeym ueh sxe yitjodi: bidtumjaznabt.kuk/mig/lacjupduax-giiy
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.