Vous êtes sur la page 1sur 731

)    *+ , -.

//012 34 2 56
78910: 94 ;< = ->?@

9
 8       

5   

80 1 1 0 234 567

  !" #$ "  % &'(

The Busy Coder's Guide to Android Development

by Mark L. Murphy

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The Busy Coder's Guide to Android Development by Mark L. Murphy Copyright 2008-2011 CommonsWare, LLC. All ights eser!e". #rinte" in the $nite" %tates o& Ameri'a. CommonsWare books may be pur'hase" in printe" (bulk) or "igital &orm &or e"u'ational or business use. *or more in&ormation, 'onta't direct@commonsware.com. #rinting +istory, Mar 2011,-ersion ../ 0%12, 348-0-381/480-0-3

5he CommonsWare name an" logo, 61usy Co"er7s 8ui"e9, an" relate" tra"e "ress are tra"emarks o& CommonsWare, LLC. All other tra"emarks re&eren'e" in this book are tra"emarks o& their respe'ti!e &irms. 5he publisher an" author(s) assume no responsibility &or errors or omissions or &or "amages resulting &rom the use o& the in&ormation 'ontaine" herein.

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Table of Contents

Welcome to the Warescription!........................................................xxiii Preface.................................................................................................xxv Wel'ome to the 1ook:..............................................................................;;! Wares'ription............................................................................................;;! 1ook 1ug 1ounty.....................................................................................;;!i %our'e Co"e An" 0ts Li'ense.................................................................;;!ii Creati!e Commons an" the *our-to-*ree (<2*) 8uarantee...............;;!iii A'kno=le"gments...................................................................................;;i; The Bi Picture.........................................................................................! What An"roi"s Are Ma"e >&........................................................................ A'ti!ities.................................................................................................. %er!i'es...................................................................................................< Content #ro!i"ers..................................................................................< 0ntents.....................................................................................................< %tu&& At ?our @isposal..................................................................................A %torage.....................................................................................................A 2et=ork...................................................................................................A Multime"ia.............................................................................................A 8#%..........................................................................................................A
iii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

#hone %er!i'es......................................................................................../ 5he 1ig #i'ture...>& 5his 1ook..................................................................../ "o# To Get $tarted.................................................................................% %tep B1, Ca!a...................................................................................................4 0nstall the C@D........................................................................................4 Learn Ca!a...............................................................................................8 %tep B2, 0nstall the An"roi" %@D................................................................3 0nstall the 1ase 5ools.............................................................................3 0nstall the %@Ds an" A""->ns..............................................................3 %tep B., 0nstall the A@5 &or E'lipse...........................................................1. %tep B<, 0nstall Apa'he Ant........................................................................1A %tep BA, %et $p the Emulator.....................................................................1/ %tep B/, %et $p the @e!i'e.........................................................................2. Win"o=s...............................................................................................2< >% F an" Linu;.....................................................................................2A &our 'irst Android Pro(ect....................................................................)% %tep B1, Create the 2e= #roGe't.................................................................24 E'lipse...................................................................................................24 Comman" Line.......................................................................................1 %tep B2, 1uil", 0nstall, an" un the Appli'ation in ?our Emulator or @e!i'e...........................................................................................................2 E'lipse.....................................................................................................2 Comman" Line....................................................................................... *xaminin &our 'irst Pro(ect................................................................+% #roGe't %tru'ture..........................................................................................4 oot Contents........................................................................................4 5he %=eat >&& ?our 1ro=.....................................................................8
iv
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

An" 2o=, 5he est o& the %tory...........................................................3 What ?ou 8et >ut >& 0t......................................................................<0 0nsi"e ?our Mani&est..................................................................................<0 0n 5he 1eginning, 5here Was the oot, An" 0t Was 8oo"...............<1 An Appli'ation *or ?our Appli'ation.................................................<2 A Bit A,out *clipse................................................................................-. What the A@5 8i!es ?ou...........................................................................<A Coping =ith E'lipse....................................................................................</ +o= to 0mport a 2on-E'lipse #roGe't................................................</ +o= to 8et 5o @@M%...........................................................................A1 +o= to Create an Emulator.................................................................A. +o= to un a #roGe't...........................................................................A< +o= 2ot to un ?our #roGe't.............................................................AA Alternati!e 0@Es..........................................................................................AA More on the 5ools......................................................................................A/ 0@Es...An" 5his 1ook.................................................................................A4 *nhancin &our 'irst Pro(ect................................................................./ %upporting Multiple %'reens.....................................................................A3 %pe'i&ying -ersions..................................................................................../0 0e#ritin &our 'irst Pro(ect.................................................................1. 5he A'ti!ity................................................................................................./A @isse'ting the A'ti!ity...............................................................................// 1uil"ing an" unning the A'ti!ity.........................................................../8 About the emaining E;amples................................................................/3 2sin 3456Based 5ayouts.....................................................................%! What 0s an FML-1ase" LayoutH.................................................................41 Why $se FML-1ase" LayoutsH..................................................................42
v
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

>D, %o What @oes 0t Look LikeH...............................................................4. What7s With the I %ignsH.........................................................................4< An" We Atta'h 5hese to the Ca!a...+o=H................................................4< 5he est o& the %tory..................................................................................4A *mployin Basic Wid ets......................................................................%/ Assigning Labels.........................................................................................43 1utton, 1utton, Who7s 8ot the 1uttonH...................................................80 *leeting 0mages...........................................................................................81 *iel"s o& 8reen. >r >ther Colors..............................................................8. Cust Another 1o; to Che'k.........................................................................8A 5urn the a"io $p......................................................................................88 0t7s Juite a -ie=.........................................................................................30 #a""ing.................................................................................................30 >ther $se&ul #roperties......................................................................30 $se&ul Metho"s.....................................................................................31 Colors.....................................................................................................31 Wor7in #ith Containers....................................................................../+ 5hinking Linearly.......................................................................................3< Con'epts an" #roperties.....................................................................3< E;ample.................................................................................................34 5he 1o; Mo"el....................................................................................102 All 5hings Are elati!e.............................................................................10< Con'epts an" #roperties....................................................................10< E;ample...............................................................................................104 >!erlap................................................................................................103 5abula asa.................................................................................................111 Con'epts an" #roperties.....................................................................112
vi
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

E;ample................................................................................................11< %'roll=ork...................................................................................................11A The 8nput 4ethod 'rame#or7............................................................!!/ Deyboar"s, +ar" an" %o&t.........................................................................113 5ailore" 5o ?our 2ee"s............................................................................120 5ell An"roi" Where 0t Can 8o.................................................................12< *itting 0n.....................................................................................................124 Cane, %top 5his CraKy 5hing:....................................................................128 2sin $election Wid ets.......................................................................!+! A"apting to the Cir'umstan'es.................................................................1.1 $sing ArrayA"apter............................................................................1.2 Lists o& 2aughty an" 2i'e.........................................................................1.. %ele'tion Mo"es..................................................................................1.A %pin Control...............................................................................................1.4 8ri" ?our Lions (>r %omething Like 5hat...)..........................................1<1 *iel"s, 2o= With .AL Less 5yping:.........................................................1<A 8alleries, 8i!e >r 5ake 5he Art...............................................................1<3 Gettin 'ancy With 5ists......................................................................!.! 8etting 5o *irst 1ase..................................................................................1A1 A @ynami' #resentation...........................................................................1A< 0n&lating o=s >ursel!es..........................................................................1A/ A %i"ebar About 0n&lation..................................................................1A/ An" 2o=, 1a'k 5o >ur %tory............................................................1A8 1etter. %tronger. *aster.............................................................................1A3 $sing 'on!ert-ie=..............................................................................1A3 $sing the +ol"er #attern....................................................................1/1 0ntera'ti!e o=s........................................................................................1/<
vii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

$till 4ore Wid ets and Containers......................................................!%! #i'k an" Choose.........................................................................................141 5ime Deeps *lo=ing Like a i!er.............................................................14/ %eeking esolution....................................................................................148 #utting 0t >n My 5ab................................................................................143 5he #ie'es............................................................................................180 Wiring 0t 5ogether..............................................................................181 A""ing 5hem $p................................................................................18< *lipping 5hem >&&.....................................................................................188 8etting 0n %omebo"y7s @ra=er................................................................13. >ther 8oo" %tu&&.......................................................................................134 *m,eddin the We,9it Bro#ser.........................................................!// A 1ro=ser, Writ %mall..............................................................................133 Loa"ing 0t $p............................................................................................202 2a!igating the Waters..............................................................................20. Entertaining the Client............................................................................20< %ettings, #re&eren'es, an" >ptions (>h, My:).......................................20/ Applyin 4enus...................................................................................):/ *la!ors o& Menu........................................................................................203 Menus o& >ptions......................................................................................210 Menus in Conte;t......................................................................................212 5aking a #eek.............................................................................................21. ?et More 0n&lation.....................................................................................218 Menu FML %tru'ture..........................................................................213 Menu >ptions an" FML....................................................................213 0n&lating the Menu..............................................................................221 0n the Lan" o& Menus an" +oney............................................................22.
viii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

$ho#in Pop62p 4essa es..................................................................)). aising 5oasts............................................................................................22A Alert: Alert:................................................................................................22/ Che'king 5hem >ut.................................................................................224 "andlin Activity 5ifecycle *vents......................................................)+! %'hroe"inger7s A'ti!ity..............................................................................2.1 Li&e, @eath, an" ?our A'ti!ity.................................................................2.2 onCreate() an" on@estroy()..............................................................2.2 on%tart(), on estart(), an" on%top()................................................2.. on#ause() an" on esume()...............................................................2.< 5he 8ra'e o& %tate.....................................................................................2.< "andlin 0otation...............................................................................)+% A #hilosophy o& @estru'tion....................................................................2.4 0t7s All 5he %ame, Cust @i&&erent..............................................................2.8 #i'king an" -ie=ing a Conta't.........................................................2<0 %a!ing ?our %tate...............................................................................2<2 2o= With More %a!ings:.........................................................................2<A @0? otation.............................................................................................2<4 ...1ut 8oogle @oes 2ot e'ommen" 5his........................................2A0 *or'ing the 0ssue........................................................................................2A1 Making %ense o& it All...............................................................................2A. Dealin #ith Threads...........................................................................).. 5he Main Appli'ation 5hrea"..................................................................2AA Making #rogress =ith #rogress1ars........................................................2A4 8etting 5hrough the +an"lers................................................................2A8 Messages.............................................................................................2A8 unnables...........................................................................................2/2
ix
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Where, >h Where +as My $0 5hrea" 8oneH........................................2/2 Asyn'ing *eeling.......................................................................................2/2 5he 5heory..........................................................................................2/. Asyn'5ask, 8eneri's, an" -arargs....................................................2/< 5he %tages o& Asyn'5ask...................................................................2/< A %ample 5ask....................................................................................2/A 5hrea"s an" otation...............................................................................240 Manual A'ti!ity Asso'iation..............................................................241 *lo= o& E!ents....................................................................................24< Why 5his Works.................................................................................24A An" 2o=, 5he Ca!eats.............................................................................24/ Creatin 8ntent 'ilters.........................................................................)%% What7s ?our 0ntentH.................................................................................248 #ie'es o& 0ntents.................................................................................248 0ntent outing....................................................................................243 %tating ?our 0ntent(ions).........................................................................280 2arro= e'ei!ers......................................................................................282 5he #ause Ca!eat......................................................................................28. 5aunchin Activities and $u,6Activities.............................................);. #eers an" %ubs..........................................................................................28/ %tart 7Em $p..............................................................................................28/ Make an 0ntent...................................................................................28/ Make the Call......................................................................................284 5abbe" 1ro=sing, %ort >&........................................................................231 Wor7in #ith 0esources.....................................................................)/% 5he esour'e Lineup................................................................................234 %tring 5heory............................................................................................238
x
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

#lain %trings........................................................................................238 %tring *ormats....................................................................................233 %tyle" 5e;t...........................................................................................00 %tyle" 5e;t an" *ormats.....................................................................00 8ot the #i'tureH.........................................................................................0< FML, 5he esour'e Way..........................................................................0/ Mis'ellaneous -alues................................................................................03 @imensions..........................................................................................03 Colors....................................................................................................10 Arrays.....................................................................................................11 @i&&erent %trokes &or @i&&erent *olks........................................................12 5L Languages, 8oing 1oth Ways............................................................14 Definin and 2sin $tyles....................................................................+!/ %tyles, @0? @ ?..........................................................................................13 Elements o& %tyle........................................................................................21 Where to Apply a %tyle.......................................................................22 5he A!ailable Attributes.....................................................................22 0nheriting a %tyle.................................................................................2. 5he #ossible -alues.............................................................................2< 5hemes, Woul" a %tyle 1y Any >ther 2ame..........................................2A "andlin 4ultiple $creen $i<es..........................................................+)% 5aking the @e&ault.....................................................................................28 Whole in >ne.............................................................................................23 @on7t 5hink About #ositions, 5hink About ules.............................0 Consi"er #hysi'al @imensions.............................................................1 A!oi" M ealM #i;els................................................................................1 Choose %'alable @ra=ables.................................................................2
xi
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

5ailor Ma"e, Cust *or ?ou (An" ?ou, An" ?ou, An"...)...........................2 Nsupports-s'reensO................................................................................ esour'es an" esour'e %ets...............................................................< *in"ing ?our %iKe..................................................................................A Ain7t 2othing Like the eal 5hing............................................................/ @ensity @i&&ers....................................................................................../ A"Gusting the @ensity...........................................................................4 uthlessly E;ploiting the %ituation...........................................................8 epla'e Menus =ith 1uttons...............................................................3 epla'e 5abs =ith a %imple A'ti!ity...................................................3 Consoli"ate Multiple A'ti!ities.........................................................<0 E;ample, E$<?ou......................................................................................<0 5he *irst Cut.........................................................................................<1 *i;ing the *onts...................................................................................<4 *i;ing the 0'ons...................................................................................A0 $sing the %pa'e...................................................................................A0 What 0& 0t 0s 2ot a 1ro=serH...............................................................A. 8ntroducin the "oneycom, 28..........................................................+.% Why +oney'ombH.....................................................................................A4 What the $ser %ees....................................................................................A8 5he +olographi' 5heme.........................................................................../. @ealing =ith the est o& the @e!i'es......................................................./< 2sin the Action Bar............................................................................+1% Enabling the A'tion 1ar............................................................................/4 #romoting Menu 0tems to the A'tion 1ar.............................................../8 espon"ing to the Logo............................................................................/3 A""ing Custom -ie=s to the A'tion 1ar.................................................40
xii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

@e&ining the Layout............................................................................40 #utting the Layout in the MMenuM......................................................42 8etting Control o& $ser 0nput............................................................4. @on7t *orget the #hones:...........................................................................4A 'ra ments.............................................................................................+%% 0ntro"u'ing *ragments..............................................................................44 5he #roblem........................................................................................48 5he *ragments %olution.....................................................................48 5he An"roi" Compatibility Library...................................................80 Creating *ragment Classes........................................................................81 8eneral *ragments...............................................................................81 List*ragment........................................................................................8. >ther *ragment 1ase Classes.............................................................88 *ragments, Layouts, A'ti!ities, an" Multiple %'reen %iKes....................83 E$<?ou................................................................................................30 @etailsA'ti!ity.....................................................................................3A *ragments an" Con&iguration Changes...................................................3/ @esigning &or *ragments...........................................................................34 "andlin Platform Chan es...............................................................+// 5hings 5hat Make ?ou 8o M1oomM..........................................................33 -ie= +ierar'hy..................................................................................<00 Changing esour'es..........................................................................<00 +an"ling A#0 Changes..............................................................................<01 Minimum, Ma;imum, 5arget, an" 1uil" -ersions..........................<01 @ete'ting the -ersion........................................................................<0< Wrapping the A#0..............................................................................<0< #atterns &or +oney'omb..........................................................................<04
xiii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

5he A'tion 1ar...................................................................................<04 Writing 5ablet->nly Apps................................................................<03 Accessin 'iles......................................................................................-!+ ?ou An" 5he +orse ?ou o"e 0n >n.......................................................<1. ea"in7 7n Writin7.......................................................................................<14 E;ternal %torage, 8iant E'onomy-%iKe %pa'e.........................................<21 Where to Write..................................................................................<22 When to Write....................................................................................<22 %tri'tMo"e, A!oi"ing Canky Co"e...........................................................<2. %etting up %tri't Mo"e.......................................................................<2< %eeing 0t 0n A'tion.............................................................................<2< @e!elopment >nly, #lease:...............................................................<2A Con"itionally 1eing %tri't.................................................................<2A Linu; *ilesystems, ?ou %yn', ?ou Win...................................................<28 2sin Preferences................................................................................-+! 8etting What ?ou Want...........................................................................<.1 %tating ?our #re&eren'e............................................................................<.2 0ntro"u'ing #re&eren'eA'ti!ity...............................................................<.. Letting $sers +a!e 5heir %ay..................................................................<.< A""ing a Wee 1it >7 %tru'ture................................................................<.3 5he Din" >& #op-$ps ?ou Like...............................................................<<2 #re&eren'es !ia *ragments.......................................................................<</ 5he +oney'omb Way........................................................................<<4 A""ing 1a'k=ar"s Compatibility.....................................................<A2 4ana in and Accessin 5ocal Data,ases.........................................-.. A Jui'k %JLite #rimer............................................................................<A4 %tart at the 1eginning...............................................................................<A4
xiv
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

%etting the 5able.......................................................................................</1 Makin7 @ata...............................................................................................</2 What 8oes Aroun", Comes Aroun".......................................................</. a= Jueries........................................................................................</. egular Jueries.................................................................................</< $sing Cursors.....................................................................................</A Custom CursorA"apters....................................................................<// Making ?our >=n Cursors................................................................</4 *lash, %oun"s *aster 5han 0t 0s...............................................................</4 @ata, @ata, E!ery=here...........................................................................</8 5evera in =ava 5i,raries.....................................................................-%! Ants an" Cars..............................................................................................<41 5he >uter Limits......................................................................................<42 *ollo=ing the %'ript.................................................................................<4. e!ie=ing the %'ript.................................................................................<48 Communicatin via the 8nternet........................................................-;! E%5 an" ela;ation.................................................................................<81 +55# >perations !ia Apa'he +ttpClient........................................<82 #arsing esponses..............................................................................<8< %tu&& 5o Consi"er...............................................................................<8/ An"roi"+ttpClient.............................................................................<84 Le!eraging 0nternet-A=are An"roi" Components................................<88 @o=nloa"ing *iles.............................................................................<88 Continuing >ur Es'ape *rom Canky Co"e.............................................A00 $ervices> The Theory.............................................................................:+ Why %er!i'esH...........................................................................................A0. %etting $p a %er!i'e.................................................................................A0<
xv
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

5he %er!i'e Class................................................................................A0< Li&e'y'le Metho"s..............................................................................A0A Mani&est Entry....................................................................................A0A Communi'ating 5o %er!i'es....................................................................A0/ %en"ing Comman"s =ith start%er!i'e()..........................................A0/ 1in"ing =ith bin"%er!i'e()...............................................................A08 Communi'ating *rom %er!i'es...............................................................A03 Callba'kPListener >bGe'ts.................................................................A03 1roa"'ast 0ntents................................................................................A10 #en"ing esults....................................................................................A11 Messenger.............................................................................................A11 2oti&i'ations........................................................................................A12 Basic $ervice Patterns...........................................................................!+ 5he @o=nloa"er........................................................................................A1. 5he @esign...........................................................................................A1< 5he %er!i'e 0mplementation..............................................................A1< $sing the %er!i'e.................................................................................A14 5he Musi' #layer.......................................................................................A18 5he @esign...........................................................................................A13 5he %er!i'e 0mplementation..............................................................A13 $sing the %er!i'e.................................................................................A21 5he Web %er!i'e 0nter&a'e.......................................................................A22 5he @esign..........................................................................................A2. 5he otation Challenge.....................................................................A2. 5he %er!i'e 0mplementation.............................................................A2< $sing the %er!i'e................................................................................A23

xvi
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Alertin 2sers ?ia @otifications...........................................................+% 2oti&i'ation Con&iguration.......................................................................A.4 +ar"=are 2oti&i'ations.....................................................................A.8 0'ons....................................................................................................A.3 2oti&i'ations in A'tion.............................................................................A<0 %taying in the *oregroun".......................................................................A<A *ake#layer, e"u;..............................................................................A</ 2oti&i'ations an" +oney'omb................................................................A<8 0eAuestin and 0eAuirin Permissions...............................................+ Mother, May 0H..........................................................................................AA< +alt: Who 8oes 5hereH............................................................................AAA En&or'ing #ermissions !ia the Mani&est...........................................AA/ En&or'ing #ermissions Else=here.....................................................AA4 May 0 %ee ?our @o'umentsH....................................................................AA4 2e= #ermissions in >l" Appli'ations....................................................AA8 #ermissions, $p *ront >r 2ot At All......................................................AA8 Accessin 5ocation6Based $ervices......................................................1+ Lo'ation #ro!i"ers, 5hey Dno= Where ?ou7re +i"ing.........................A/< *in"ing ?oursel&.......................................................................................A/< >n the Mo!e.............................................................................................A// Are We 5here ?etH Are We 5here ?etH Are We 5here ?etH.................A/8 5esting...5esting.......................................................................................A/3 4appin #ith 4ap?ie# and 4apActivity............................................%! 5erms, 2ot o& En"earment.......................................................................A41 #iling >n....................................................................................................A42 5he Dey 5o 0t All.......................................................................................A42 5he 1are 1ones.........................................................................................A4<
xvii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

>ptional Maps....................................................................................A4/ E;er'ising ?our Control...........................................................................A4/ Qoom....................................................................................................A44 Center..................................................................................................A44 Layers $pon Layers..................................................................................A48 >!erlay Classes...................................................................................A48 @ra=ing the 0temiKe">!erlay...........................................................A48 +an"ling %'reen 5aps........................................................................A80 My, Mysel&, an" MyLo'ation>!erlay.......................................................A81 ugge" 5errain.........................................................................................A82 Maps an" *ragments................................................................................A8< Limit ?oursel& to An"roi" ..0...........................................................A8< $se onCreate-ie=() an" onA'ti!ityCreate"().................................A8A +ost the *ragment in a MapA'ti!ity................................................A8/ "andlin Telephone Calls...................................................................;/ eport 5o 5he Manager...........................................................................A30 ?ou Make the Call:...................................................................................A30 2o, eally, ?ou Make the Call:................................................................A3. 'onts....................................................................................................../. Lo!e 5he >ne ?ou7re With......................................................................A3A +ere a 8lyph, 5here a 8lyph...................................................................A33 4ore Development Tools....................................................................1:! +ierar'hy -ie=er, +o= @eep 0s ?our Co"eH........................................../01 @@M%, $n"er An"roi"7s +oo".............................................................../0/ Logging.............................................................................................../08 *ile #ush an" #ull............................................................................../03 %'reenshots........................................................................................./10
xviii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Lo'ation $p"ates................................................................................./11 #la'ing Calls an" Messages................................................................/12 Memory Management......................................................................../1/ a"b, Like @@M%, With More 5yping......................................................./14 The 0ole of Alternative *nvironments...............................................1)! 0n the 1eginning, 5here Was Ca!a.........................................................../22 ...An" 0t Was >D......................................................................................./22 1u'king the 5ren"..................................................................................../2. %upport, %tru'ture..................................................................................../2< Ca!eat @e!eloper....................................................................................../2< "T45...................................................................................................1)% >&&line Appli'ations................................................................................./24 What @oes 0t MeanH........................................................................../24 +o= @o ?ou $se 0tH........................................................................../28 Web %torage............................................................................................../.< What @oes 0t MeanH........................................................................../.A +o= @o ?ou $se 0tH..........................................................................././ Web %JL @atabase............................................................................/.4 8oing 5o #ro"u'tion................................................................................/.8 5esting................................................................................................./.8 %igning an" @istribution.................................................................../.8 $p"ates.............................................................................................../.3 0ssues ?ou May En'ounter......................................................................./.3 An"roi" @e!i'e -ersions.................................................................../.3 %'reen %iKes an" @ensities................................................................/<0 Limite" #lat&orm 0ntegration............................................................/<0 #er&orman'e an" 1attery.................................................................../<1
xix
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Look an" *eel...................................................................................../<2 @istribution......................................................................................../<2 +5MLA an" Alternati!e An"roi" 1ro=sers............................................/<. *ire&o; Mobile..................................................................................../<. >pera Mobile....................................................................................../<. @olphin 1ro=ser +@ <.0.................................................................../<. +5MLA, 5he 1aseline.............................................................................../<. PhoneGap.............................................................................................1-. What 0s #hone8apH................................................................................../<A What @o ?ou Write 0nH...................................................................../<A What *eatures @o ?ou 8etH............................................................./</ What @o Apps Look LikeH................................................................/<4 +o= @oes @istribution WorkH........................................................./<4 What About >ther #lat&ormsH........................................................./<8 $sing #hone8ap......................................................................................./<8 0nstallation........................................................................................./<3 Creating an" 0nstalling ?our #roGe't................................................/<3 #hone8apP1uil"................................................................................./A0 #hone8ap an" the Che'klist %ample....................................................../A< %ti'king to the %tan"ar"s................................................................../A< A""ing #hone8ap A#0s...................................................................../A4 0ssues ?ou May En'ounter......................................................................//0 %e'urity...............................................................................................//0 %'reen %iKes an" @ensities.................................................................//1 Look an" *eel.....................................................................................//2 *or More 0n&ormation..............................................................................//.

xx
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Bther Alternative *nvironments........................................................11. ho"es.......................................................................................................//A *lash, *le;, an" A0 ................................................................................./// C uby an" uboto..................................................................................../// Mono@roi"...............................................................................................//4 App 0n!entor.............................................................................................//4 5itanium Mobile......................................................................................//3 >ther C-M Compile" Languages............................................................/40 Dealin With Devices..........................................................................1%+ 5his App Contains E;pli'it... 0nstru'tions............................................../4. 0mplie" *eature eRuests................................................................../4A A 8uarantee" Market.............................................................................../4/ >ther %tu&& 5hat -aries............................................................................/44 1ugs, 1ugs, 1ugs......................................................................................./48 @e!i'e 5esting........................................................................................../48 Where Do We Go 'rom "ereC.............................................................1;! Juestions. %ometimes, With Ans=ers..................................................../81 +ea"ing to the %our'e............................................................................./82 8etting ?our 2e=s *i;............................................................................./8.

xxi
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Welcome to the Warescription!

We hope you enGoy this ebook an" its up"ates S subs'ribe to the Wares'ription ne=sletter on the Wares'ription site to learn =hen ne= e"itions o& this book, or other books, are a!ailable. All e"itions o& CommonsWare titles, print an" ebook, &ollo= a so&t=arestyle numbering system. MaGor releases (1.0, 2.0, et'.) are a!ailable in both print an" ebookT minor releases (0.1, 0.3, et'.) are a!ailable in ebook &orm &or Wares'ription subs'ribers only. eleases en"ing in .3 are Mrelease 'an"i"atesM &or the ne;t maGor release, la'king perhaps an in"e; but other=ise being 'omplete. Ea'h Wares'ription ebook is li'ense" &or the e;'lusi!e use o& its subs'riber an" is tagge" =ith the subs'riber7s name. We ask that you not "istribute these books. 0& you =ork &or a &irm an" =ish to ha!e se!eral employees ha!e a''ess, enterprise Wares'riptions are a!ailable. Cust 'onta't us at enterpriseI'ommons=are.'om. Also, bear in min" that e!entually this e"ition o& this title =ill be release" un"er a Creati!e Commons li'ense S more on this in the pre&a'e. emember that the CommonsWare Web site has errata an" resour'es (e.g., sour'e 'o"e) &or ea'h o& our titles. Cust !isit the Web page &or the book you are intereste" in an" &ollo= the links. ?ou 'an sear'h through the #@* using most #@* rea"ers (e.g., A"obe ea"er). 0& you =ish to sear'h all o& the CommonsWare books at on'e, an"
xxiii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

your operating system "oes not support that "ire'tly, you 'an al=ays 'ombine the #@*s into one, using tools like #@* %plit-An"-Merge or the Linu; 'omman" pdftk *.pdf cat output combined.pdf.

xxiv
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Preface

Welcome to the Book!


5hanks: 5hanks &or your interest in "e!eloping appli'ations &or An"roi": 0n'reasingly, people =ill a''ess 0nternet-base" ser!i'es using so-'alle" Mnon-tra"itionalM means, su'h as mobile "e!i'es. 5he more =e "o in that spa'e no=, the more that people =ill help in!est in that spa'e to make it easier to buil" more po=er&ul mobile appli'ations in the &uture. An"roi" is ne= S An"roi"-po=ere" "e!i'es appeare" on the s'ene &irst in late 2008 S but it likely =ill rapi"ly gro= in importan'e "ue to the siKe an" s'ope o& the >pen +an"set Allian'e. An", most o& all, thanks &or your interest in this book: 0 sin'erely hope you &in" it use&ul an" at least o''asionally entertaining.

Warescription
5his book =ill be publishe" both in print an" in "igital (ebook) &orm. 5he ebook !ersions o& all CommonsWare titles are a!ailable !ia an annual subs'ription S the Wares'ription. 5he Wares'ription entitles you, &or the "uration o& your subs'ription, to ebook &orms o& all CommonsWare titles, not Gust the one you are rea"ing.

xxv
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

#resently, CommonsWare o&&ers #@* an" Din"leT other ebook &ormats =ill be a""e" base" on interest an" the openness o& the &ormat. Ea'h subs'riber gets personaliKe" e"itions o& all e"itions o& ea'h title, both those mirroring printe" e"itions an" in-bet=een up"ates that are only a!ailable in ebook &orm. 5hat =ay, your ebooks are ne!er out o& "ate &or long, an" you 'an take a"!antage o& ne= material as it is ma"e a!ailable instea" o& ha!ing to =ait &or a =hole ne= print e"ition. *or e;ample, =hen ne= releases o& the An"roi" %@D are ma"e a!ailable, this book =ill be Rui'kly up"ate" to be a''urate =ith 'hanges in the A#0s. *rom time to time, subs'ribers =ill also re'ei!e a''ess to subs'riber-only online material, both short arti'les an" not-yet-publishe" ne= titles. Also, i& you o=n a print 'opy o& a CommonsWare book, an" it is in goo" 'lean 'on"ition =ith no marks or sti'kers, you 'an e;'hange that 'opy &or a "is'ount o&& the Wares'ription pri'e. 0& you are intereste" in a Wares'ription, !isit the Wares'ription se'tion o& the CommonsWare Web site. ?ou 'an &in" out =hen ne= releases o& this book are a!ailable !ia,

5he '=-an"roi" 8oogle 8roup, =hi'h is also a great pla'e to ask Ruestions about the book an" its e;amples 5he 'ommonsguy 5=itter &ee" 5he Wares'ription ne=sletter, =hi'h you 'an subs'ribe to o&& o& your Wares'ription page

Book Bug Bounty


*in" a problem in one o& our booksH Let us kno=: 1e the &irst to report a uniRue 'on'rete problem in the 'urrent "igital e"ition, an" =e7ll gi!e you a 'oupon &or a si;-month Wares'ription as a bounty &or helping us "eli!er a better pro"u't. ?ou 'an use that 'oupon to get a ne= Wares'ription, rene= an e;isting Wares'ription, or gi!e the
xxvi
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

'oupon to a &rien", 'olleague, or some ran"om person you meet on the sub=ay. 1y M'on'reteM problem, =e mean things like,

5ypographi'al errors %ample appli'ations that "o not =ork as a"!ertise", in the en!ironment "es'ribe" in the book *a'tual errors that 'annot be open to interpretation

1y MuniRueM, =e mean ones not yet reporte". Ea'h book has an errata page on the CommonsWare Web siteT most kno=n problems =ill be liste" there. >ne 'oupon is gi!en per email 'ontaining !ali" bug reports. We appre'iate hearing about Mso&terM issues as =ell, su'h as,

#la'es =here you think =e are in error, but =here =e &eel our interpretation is reasonable #la'es =here you think =e 'oul" a"" sample appli'ations, or e;pan" upon the e;isting material %amples that "o not =ork "ue to Mshi&ting san"sM o& the un"erlying en!ironment (e.g., 'hange" A#0s =ith ne= releases o& an %@D)

+o=e!er, those Mso&terM issues "o not Ruali&y &or the &ormal bounty program. 1e sure to 'he'k the book7s errata page, though, to see i& your issue has alrea"y been reporte". Juestions about the bug bounty, or problems you =ish to report &or bounty 'onsi"eration, shoul" be sent to bountyI'ommons=are.'om.

Source Code And ts !icense


5he sour'e 'o"e samples sho=n in this book are a!ailable &or "o=nloa" &rom the book7s 8it+ub repository. All o& the An"roi" proGe'ts are li'ense" un"er the Apa'he 2.0 Li'ense, in 'ase you ha!e the "esire to reuse any o& it.
xxvii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

0& you =ish to use the sour'e 'o"e &rom the CommonsWare Web site, bear in min" a &e= things, 1. 5he proGe'ts are set up to be built by Ant, not by E'lipse. 0& you =ish to use the 'o"e =ith E'lipse, you =ill nee" to 'reate a suitable An"roi" E'lipse proGe't an" import the 'o"e an" other assets.

2. ?ou shoul" "elete buil".;ml, then run android update project -p ... (=here ... is the path to a proGe't o& interest) on those proGe'ts you =ish to use, so the buil" &iles are up"ate" &or your An"roi" %@D !ersion.

Creative Commons and the "our#to#"ree $%&"' (uarantee


Ea'h CommonsWare book e"ition =ill be a!ailable &or use un"er the Creati!e Commons Attribution-2on'ommer'ial-%hareAlike ..0 li'ense as o& the &ourth anni!ersary o& its publi'ation "ate, or =hen <,000 'opies o& the e"ition ha!e been sol", =hi'he!er 'omes &irst. 5hat means that, on'e &our years ha!e elapse" (perhaps sooner:), you 'an use this prose &or non'ommer'ial purposes. 5hat is our *our-to-*ree 8uarantee to our rea"ers an" the broa"er 'ommunity. *or the purposes o& this guarantee, ne= Wares'riptions an" rene=als =ill be 'ounte" as sales o& this e"ition, starting &rom the time the e"ition is publishe". 5his e"ition o& this book =ill be a!ailable un"er the a&orementione" Creati!e Commons li'ense on ! 4arch ):!.. >& 'ourse, =at'h the CommonsWare Web site, as this e"ition might be reli'ense" sooner base" on sales. *or more "etails on the Creati!e Commons Attribution-2on'ommer'ial%hareAlike ..0 li'ense, !isit the Creati!e Commons Web site. 2ote that &uture e"itions o& this book =ill be'ome &ree on later "ates, ea'h &our years &rom the publi'ation o& that e"ition or base" on sales o& that spe'i&i' e"ition. eleasing one e"ition un"er the Creati!e Commons li'ense "oes not automati'ally release all e"itions un"er that li'ense.

xxviii
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Ackno)ledgments
0 =oul" like to thank the An"roi" team, not only &or putting out a goo" pro"u't, but &or in!aluable assistan'e on the An"roi" 8oogle 8roups. %ome o& the i'ons use" in the sample 'o"e =ere pro!i"e" by the 2u!ola i'on set.

xxix
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

PART I Core Concepts

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1

The Big Picture

An"roi" is e!ery=here. #hones. 5ablets. 5-s an" set-top bo;es po=ere" by 8oogle 5-. %oon, An"roi" =ill be in 'ars an" all sort o& other pla'es as =ell. +o=e!er, the general theme o& An"roi" "e!i'es =ill be smaller s'reens an"Por no har"=are keyboar". An", by the numbers, An"roi" =ill probably be most asso'iate" =ith smartphones &or the &oreseeable &uture. *or "e!elopers, this has bene&its an" "ra=ba'ks. >n the plus si"e, An"roi"-style smartphones are se;y. >&&ering 0nternet ser!i'es o!er mobile "e!i'es "ates ba'k to the mi"-13307s an" the +an"hel" @e!i'e Markup Language (+@ML). +o=e!er, only in re'ent years ha!e phones 'apable o& 0nternet a''ess taken o&&. 2o=, thanks to tren"s like te;t messaging an" to pro"u'ts like Apple7s i#hone, phones that 'an ser!e as 0nternet a''ess "e!i'es are rapi"ly gaining popularity. %o, =orking on An"roi" appli'ations gi!es you e;perien'e =ith an interesting te'hnology (An"roi") in a &ast-mo!ing market segment (0nternet-enable" phones), =hi'h is al=ays a goo" thing. 5he problem 'omes =hen you a'tually ha!e to program the "arn things. Anyone =ith e;perien'e in programming &or #@As or phones has &elt the pain o& phones simply being small in all sorts o& "imensions,

*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

The Big Picture

%'reens are small (you =ill not get 'omments like, Mis that a 2<-in'h LC@ in your po'ket, or...HM) Deyboar"s, i& they e;ist, are small #ointing "e!i'es, i& they e;ist, are annoying (as anyone =ho has lost their stylus =ill tell you) or ine;a't (large &ingers an" Mmulti-tou'hM LC@s 'an sometimes be...problemati') C#$ spee" an" memory are tight 'ompare" to "esktops an" ser!ers you may be use" to An" so on

Moreo!er, appli'ations running on a phone ha!e to "eal =ith the &a't that they7re on a phone. #eople =ith mobile phones ten" to get !ery irritate" =hen those phones "o not =ork. %imilarly, those same people =ill get irritate" at you i& your program MbreaksM their phones,

...by tying up the C#$ su'h that 'alls 'an7t be re'ei!e" ...by not =orking properly =ith the rest o& the phone7s >%, su'h that your appli'ation "oes not Ruietly &a"e to the ba'kgroun" =hen a 'all 'omes in or nee"s to be pla'e" ...by 'rashing the phone7s operating system, su'h as by leaking memory like a sie!e

+en'e, "e!eloping programs &or a phone is a "i&&erent e;perien'e than "e!eloping "esktop appli'ations, Web sites, or ba'k-en" ser!er pro'esses. ?ou =in" up =ith "i&&erent-looking tools, "i&&erent-beha!ing &rame=orks, an" M"i&&erent than you are use" toM limitations on =hat you 'an "o =ith your program. What An"roi" tries to "o is meet you hal&=ay,

?ou get a 'ommonly-use" programming language (Ca!a) =ith some 'ommonly use" libraries (e.g., some Apa'he Commons A#0s), =ith support &or tools you may be use" to (E'lipse)

&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The Big Picture

?ou get a &airly rigi" an" un'ommon &rame=ork in =hi'h your programs nee" to run so they 'an be Mgoo" 'itiKensM on the phone an" not inter&ere =ith other programs or the operation o& the phone itsel&

As you might e;pe't, mu'h o& this book "eals =ith that &rame=ork an" ho= you =rite programs that =ork =ithin its 'on&ines an" take a"!antage o& its 'apabilities.

What Androids Are +ade ,f


When you =rite a "esktop appli'ation, you are Mmaster o& your o=n "omainM. ?ou laun'h your main =in"o= an" any 'hil" =in"o=s S like "ialog bo;es S that are nee"e". *rom your stan"point, you are your o=n =orl", le!eraging &eatures supporte" by the operating system, but largely ignorant o& any other program that may be running on the 'omputer at the same time. 0& you "o intera't =ith other programs, it is typi'ally through an A#0, su'h as using C@1C (or &rame=orks atop it) to 'ommuni'ate =ith My%JL or another "atabase. An"roi" has similar 'on'epts, but pa'kage" "i&&erently, an" stru'ture" to make phones more 'rash-resistant.

Activities
5he buil"ing blo'k o& the user inter&a'e is the activity. ?ou 'an think o& an a'ti!ity as being the An"roi" analogue &or the =in"o= or "ialog in a "esktop appli'ation, or the page in a 'lassi' Web app. An"roi" is "esigne" to support lots o& 'heap a'ti!ities, so you 'an allo= users to keep 'li'king to bring up ne= a'ti!ities an" tapping the 1ACD button to ba'k up, Gust like they "o in a Web bro=ser.

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The Big Picture

Services
A'ti!ities are short-li!e" an" 'an be shut "o=n at any time. %er!i'es, on the other han", are "esigne" to keep running, i& nee"e", in"epen"ent o& any a'ti!ity. ?ou might use a ser!i'e &or 'he'king &or up"ates to an %% &ee", or to play ba'k musi' e!en i& the 'ontrolling a'ti!ity is no longer operating. ?ou =ill also use ser!i'es &or s'he"ule" tasks (M'ron GobsM) an" &or e;posing 'ustom A#0s to other appli'ations on the "e!i'e, though those are relati!ely a"!an'e" 'apabilities.

Content Providers
Content pro!i"ers pro!i"e a le!el o& abstra'tion &or any "ata store" on the "e!i'e that is a''essible by multiple appli'ations. 5he An"roi" "e!elopment mo"el en'ourages you to make your o=n "ata a!ailable to other appli'ations, as =ell as your o=n S buil"ing a 'ontent pro!i"er lets you "o that, =hile maintaining 'omplete 'ontrol o!er ho= your "ata gets a''esse".

Intents
0ntents are system messages, running aroun" the insi"e o& the "e!i'e, noti&ying appli'ations o& !arious e!ents, &rom har"=are state 'hanges (e.g., an %@ 'ar" =as inserte"), to in'oming "ata (e.g., an %M% message arri!e"), to appli'ation e!ents (e.g., your a'ti!ity =as laun'he" &rom the "e!i'e7s main menu). 2ot only 'an you respon" to an Intent, but you 'an 'reate your o=n, to laun'h other a'ti!ities, or to let you kno= =hen spe'i&i' situations arise (e.g., raise su'h-an"-so Intent =hen the user gets =ithin 100 meters o& this-an"-su'h lo'ation).

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The Big Picture

Stuff At .our /isposal


Stor !e
?ou 'an pa'kage "ata &iles =ith your appli'ation, &or things that "o not 'hange, su'h as i'ons or help &iles. ?ou also 'an 'ar!e out a small bit o& spa'e on the "e!i'e itsel&, &or "atabases or &iles 'ontaining user-entere" or retrie!e" "ata nee"e" by your appli'ation. An", i& the user supplies bulk storage, like an %@ 'ar", you 'an rea" an" =rite &iles on there as nee"e".

"et#or$
An"roi" "e!i'es =ill generally be 0nternet-rea"y, through one 'ommuni'ations me"ium or another. ?ou 'an take a"!antage o& the 0nternet a''ess at any le!el you =ish, &rom ra= Ca!a so'kets all the =ay up to a built-in WebDit-base" Web bro=ser =i"get you 'an embe" in your appli'ation.

%ultimedi
An"roi" "e!i'es ha!e the ability to play ba'k an" re'or" au"io an" !i"eo. While the spe'i&i's may !ary &rom "e!i'e to "e!i'e, you 'an Ruery the "e!i'e to learn its 'apabilities an" then take a"!antage o& the multime"ia 'apabilities as you see &it, =hether that is to play ba'k musi', take pi'tures =ith the 'amera, or use the mi'rophone &or au"io note-taking.

GPS
An"roi" "e!i'es =ill &reRuently ha!e a''ess to lo'ation pro!i"ers, su'h as 8#%, that 'an tell your appli'ations =here the "e!i'e is on the &a'e o& the Earth. 0n turn, you 'an "isplay maps or other=ise take a"!antage o& the lo'ation "ata, su'h as tra'king a "e!i'e7s mo!ements i& the "e!i'e has been stolen.

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The Big Picture

Phone Services
An", o& 'ourse, An"roi" "e!i'es are typi'ally phones, allo=ing your so&t=are to initiate 'alls, sen" an" re'ei!e %M% messages, an" e!erything else you e;pe't &rom a mo"ern bit o& telephony te'hnology.

The Big Picture111,f This Book


+ere is =hat7s 'oming in the rest o& this book, 5he ne;t t=o 'hapters are "esigne" to get you going Rui'kly =ith the An"roi" en!ironment, through a series o& step-by-step, tutorial-style instru'tions &or setting up the tools you nee", 'reating your &irst proGe't, an" getting that &irst proGe't running on the An"roi" emulator. 5he three 'hapters that &ollo= try to e;plain a bit more about =hat Gust happene" in those &irst t=o 'hapters. We e;amine the An"roi" proGe't that =e 'reate", talk a bit more about E'lipse, an" "is'uss some things =e 'oul" a"" to the proGe't to help it run on more "e!i'es an" su'h. 5he bulk o& the book is e;ploring !arious 'apabilities o& the An"roi" A#0s S ho= to 'reate 'omponents like a'ti!ities, ho= to a''ess the 0nternet an" lo'al "atabases, ho= to get your lo'ation an" sho= it on a map, an" so &orth.

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &

3o) To (et Started

Without &urther a"o, let us get you set up =ith the pie'es an" parts ne'essary to buil" an An"roi" app. @BT*, the instru'tions presente" here are a''urate as o& the time o& this =riting. +o=e!er, the tools 'hange rapi"ly, an" so these instru'tions may be out o& "ate by the time you rea" this. #lease re&er to the An"roi" @e!elopers Web site &or 'urrent instru'tions, using this as a base gui"eline o& =hat to e;pe't.

Step 4*5 6ava


When you =rite An"roi" appli'ations, you typi'ally =rite them in Ca!a sour'e 'o"e. 5hat Ca!a sour'e 'o"e is then turne" into the stu&& that An"roi" a'tually runs (@al!ik byte'o"e in an A#D &ile). +en'e, the &irst thing you nee" to "o is get set up =ith a Ca!a "e!elopment en!ironment an" be rea"y to start =riting Ca!a 'lasses.

Inst ll the 'D(


?ou nee" to obtain an" install the o&&i'ial %unP>ra'le Ca!a %E %@D (C@D). ?ou 'an obtain this &rom the >ra'le Ca!a Web site &or Win"o=s an" Linu;, an" presumably &rom Apple &or >% F. 5he plain C@D (sans any Mbun"lesM)

7
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

shoul" su&&i'e. *ollo= the instru'tions supplie" by >ra'le or Apple &or installing it on your ma'hine. At the time o& this =riting, An"roi" supports Ca!a A an" Ca!a /, the latter being the no=-'urrent e"ition.

Altern tive ' v Compilers


0n prin'iple, you are suppose" to use the o&&i'ial %unP>ra'le Ca!a %E %@D. 0n pra'ti'e, it appears that >penC@D also =orks, at least on $buntu. +o=e!er, the &urther remo!e" you get &rom the o&&i'ial %unP>ra'le implementation, the less likely it is that it =ill =ork. *or e;ample, the 82$ Compiler &or Ca!a (8CC) may not =ork =ith An"roi".

)e rn ' v
5his book, like most books an" "o'umentation on An"roi", assumes that you ha!e basi' Ca!a programming e;perien'e. 0& you la'k this, you really shoul" 'onsi"er spen"ing a bit o& time on Ca!a &un"amentals, be&ore you "i!e into An"roi". >ther=ise, you may &in" the e;perien'e to be &rustrating. 0& you are in nee" o& a 'rash 'ourse in Ca!a to get in!ol!e" in An"roi" "e!elopment, here are the 'on'epts you nee" to su''ee", presente" in no parti'ular or"er,

Language &un"amentals (&lo= 'ontrol, et'.) Classes an" obGe'ts Metho"s an" "ata members #ubli', pri!ate, an" prote'te" %tati' an" instan'e s'ope E;'eptions 5hrea"s an" 'on'urren'y 'ontrol Colle'tions 8eneri's
8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

*ile 0P> e&le'tion 0nter&a'es

Step 4&5 nstall the Android S/9


5he An"roi" %@D gi!es you all the tools you nee" to 'reate an" test An"roi" appli'ations. 0t 'omes in t=o parts, the base tools, plus !ersionspe'i&i' %@Ds an" relate" a""-ons.

Inst ll the B se Tools


5he An"roi" "e!eloper tools 'an be &oun" on the An"roi" @e!elopers Web site. @o=nloa" the Q0# &ile appropriate &or your plat&orm an" unQ0# it in some likely spot S there is no spe'i&i' path that is reRuire". Win"o=s users also ha!e the option o& running a sel&-installing EFE &ile.

Inst ll the SD(s nd Add*+ns


0nsi"e the tools/ "ire'tory o& your An"roi" %@D installation &rom the pre!ious step, you =ill see an android bat'h &ile or shell s'ript. 0& you run that, you =ill be presente" =ith the An"roi" %@D an" A-@ Manager,

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

"igure *1 Android S/9 and A;/ +anager

At this point, =hile you ha!e some o& the buil" tools, you la'k the Ca!a &iles ne'essary to 'ompile an An"roi" appli'ation. ?ou also la'k a &e= a""itional buil" tools, plus the &iles ne'essary to run an An"roi" emulator. 5o a""ress this, 'li'k on the A!ailable #a'kages option on the le&t. 5his brings up a tree,

"igure &1 Android S/9 and A;/ +anager Available Packages

*<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

>pen the An"roi" epository bran'h o& the tree. A&ter a short pause, you =ill see a s'reen similar to this,

"igure -1 Android S/9 and A;/ +anager Available Android Packages

?ou =ill =ant to 'he'k the &ollo=ing items,

M%@D #lat&ormM &or all An"roi" %@D releases you =ant to test against M@o'umentation &or An"roi" %@DM &or the latest An"roi" %@D release M%amples &or %@DM &or the latest An"roi" %@D release, an" perhaps &or ol"er releases i& you =ish

5hen, open the 5hir"-#arty A""->ns bran'h o& the tree. A&ter a short pause, you =ill see a s'reen similar to this,

**

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

"igure %1 Android S/9 and A;/ +anager Available Third#Party Add#,ns

*ol" open the M8oogle 0n'. a""-onsM bran'h, =hi'h =ill "isplay something like this,

"igure 01 Android S/9 and A;/ +anager Available (oogle Add#,ns

Most likely, you =ill =ant to 'he'k the M8oogle A#0s by 8oogle 0n'.M items that mat'h up =ith the %@D !ersions you sele'te" in the An"roi" epository bran'h. 5he M8oogle A#0sM in'lu"e support &or 8oogle Maps, both &rom your 'o"e an" in the An"roi" emulator.

*&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

When you ha!e 'he'ke" all o& the items you =ant to "o=nloa", 'li'k the 0nstall %ele'te" button, =hi'h brings up a li'ense 'on&irmation "ialog,

"igure 21 Android S/9 and A;/ +anger nstalling Packages

e!ie= an" a''ept the li'enses, then 'li'k the 0nstall button. At this point, this is a &ine time to go get lun'h. >r, perhaps "inner. $nless you ha!e a substantial 0nternet 'onne'tion, "o=nloa"ing all o& this "ata an" unpa'king it =ill take a &air bit o& time. When the "o=nloa" is 'omplete, you 'an 'lose up the %@D an" A-@ Manager i& you =ish, though =e =ill use it to set up the emulator in a later step o& this 'hapter.

Step 4-5 nstall the A/T for =clipse


0& you =ill not be using E'lipse &or your An"roi" "e!elopment, you 'an skip to the ne;t se'tion. 0& you ha!e not yet installe" E'lipse, you =ill nee" to "o that &irst. E'lipse 'an be "o=nloa"e" &rom the E'lipse Web site. 5he ME'lipse 0@E &or Ca!a @e!elopersM pa'kage =ill =ork &ine.

*-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

2e;t, you nee" to install the An"roi" @e!eloper 5ools (A@5) plug-in. 5o "o this, go to +elp U 0nstall 2e= %o&t=are... in the E'lipse main menu. 5hen, 'li'k the A"" button to a"" a ne= sour'e o& plug-ins. 8i!e it some name (e.g., An"roi") an" supply the &ollo=ing $ L, https://dlssl.google.com/android/eclipse/. 5hat shoul" trigger E'lipse to "o=nloa" the roster o& plug-ins a!ailable &rom that site,

"igure 71 =clipse A/T plug#in installation

Che'k the 'he'kbo; to the le&t o& M@e!eloper 5oolsM an" 'li'k the 2e;t button. *ollo= the rest o& the =iKar" to re!ie= the tools to be "o=nloa"e" an" their respe'ti!e li'ense agreements. When the *inish button is enable", 'li'k it, an" E'lipse =ill "o=nloa" an" install the plug-ins. When "one, E'lipse =ill ask to restart S please let it. 5hen, you nee" to tea'h A@5 =here your An"roi" %@D installation is &rom the pre'e"ing se'tion. 5o "o this, 'hoose Win"o= U #re&eren'es &rom the

*%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

E'lipse main menu (or the eRui!alent #re&eren'es option &or >% F). Cli'k on the An"roi" entry in the list on the le&t,

"igure 81 =clipse A/T configuration

5hen, 'li'k the 1ro=se... button to &in" the "ire'tory =here you installe" the %@D. A&ter 'hoosing it, 'li'k Apply on the #re&eren'es =in"o=, an" you shoul" see the An"roi" %@D !ersions you installe" pre!iously. 5hen, 'li'k >D, an" the A@5 =ill be rea"y &or use.

Step 4%5 nstall Apache Ant


0& you =ill be "oing all o& your "e!elopment &rom E'lipse, you 'an skip to the ne;t se'tion. 0& you =ish to "e!elop using 'omman"-line buil" tools, you =ill nee" to install Apa'he Ant. ?ou may ha!e this alrea"y &rom pre!ious Ca!a "e!elopment =ork, as it is &airly 'ommon in Ca!a proGe'ts. +o=e!er, you
*0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

=ill nee" Ant !ersion 1.8.1, so "ouble-'he'k your 'urrent 'opy (e.g., ant -version) to ensure you are on the proper e"ition. 0& you "o not ha!e Ant, you 'an obtain it &rom the Apa'he Ant Web site. 5hey ha!e &ull installation instru'tions in the Ant manual, but the basi' steps are, 1. $npa'k the Q0# ar'hi!e =here!er it may make sense on your ma'hine

2. A"" a JAVA !"#$ en!ironment !ariable, pointing to =here your C@D is installe", i& you "o not ha!e one alrea"y .. A"" an A%& !"#$ en!ironment !ariable, pointing to the "ire'tory =here you unpa'ke" Ant in the &irst step abo!e <. A"" 'JAVA !"#$/bin an" 'A%& !"#$/bin to your (A&! A. un ant -version to 'on&irm that Ant is installe" properly

Step 405 Set >p the =mulator


5he An"roi" tools in'lu"e an emulator, a pie'e o& so&t=are that preten"s to be an An"roi" "e!i'e. 5his is !ery use&ul &or "e!elopment S not only "oes it mean you 'an get starte" on An"roi" =ithout a "e!i'e, but the emulator 'an help test "e!i'e 'on&igurations that you "o not o=n. 5he An"roi" emulator 'an emulate one or se!eral An"roi" "e!i'es. Ea'h 'on&iguration you =ant is store" in an MAn"roi" -irtual @e!i'eM, or A-@. 5he %@D an" A-@ Manager, =hi'h you use" to "o=nloa" the %@D 'omponents earlier in this 'hapter, is =here you 'reate these A-@s. 0& you "o not ha!e the %@D an" A-@ Manager running, you 'an run it !ia the an"roi" 'omman" &rom your %@D7s tools/ "ire'tory, or !ia Win"o= U %@D an" A-@ Manager &rom E'lipse. 0t starts up on a s'reen listing the A-@s you ha!e a!ailable S initially, the list =ill be empty,

*2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

"igure :1 Android S/9 and A;/ +anager

Cli'k the 2e=... button to 'reate a ne= A-@ &ile. 5his brings up a "ialog =here you 'an 'on&igure =hat this A-@ shoul" look an" =ork like,

"igure *<1 Adding a ?e) A;/

*7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

?ou nee" to pro!i"e the &ollo=ing,

A name &or the A-@. %in'e the name goes into &iles on your "e!elopment ma'hine, you =ill be limite" by &ilename 'on!entions &or your operating system (e.g., no ba'kslashes on Win"o=s). 5he An"roi" !ersion you =ant the emulator to run (a.k.a., the MtargetM). Choose one o& the %@Ds you installe" !ia the "rop-"o=n list. 2ote that in a""ition to MpureM An"roi" en!ironments, you =ill ha!e options base" on the thir"-party a""-ons you sele'te". *or e;ample, you probably ha!e some options &or setting up A-@s 'ontaining the 8oogle A#0s, an" you =ill nee" su'h an A-@ &or testing an appli'ation that uses 8oogle Maps. @etails about the %@ 'ar" the emulator shoul" emulate. %in'e An"roi" "e!i'es in!ariably ha!e some &orm o& Me;ternal storageM, you probably =ant to set up an %@ 'ar", by supplying a siKe in the asso'iate" &iel". +o=e!er, sin'e a &ile =ill be 'reate" on your "e!elopment ma'hine o& =hate!er siKe you spe'i&y &or the 'ar", you probably "o not =ant to 'reate a 281 emulate" %@ 'ar". .2M1 is a ni'e starting point, though you 'an go larger i& nee"e". 5he MskinM or resolution the emulator shoul" run in. 5he skin options you ha!e =ill "epen" upon =hat target you 'hose. 5he skins let you 'hoose a typi'al An"roi" s'reen resolution (e.g., W-8A800 &or 800;<80). ?ou 'an also manually spe'i&y a resolution =hen you =ant to test a non-stan"ar" 'on&iguration.

?ou 'an skip the M+ar"=areM se'tion &or no=, as 'hanging those settings is usually only reRuire" &or a"!an'e" 'on&igurations. 5he resulting "ialog might look something like this,

*8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

"igure **1 Adding a ?e) A;/ $continued'

Cli'k the Create A-@ button, an" your A-@ stub =ill be 'reate". 5o start the emulator, highlight it in the list an" 'li'k %tart... ?ou 'an skip the laun'h options &or no= an" Gust 'li'k Laun'h. 5he &irst time you laun'h a ne= A-@, it =ill take a long time to start up. 5he se'on" an" subseRuent times you start the A-@, it =ill 'ome up a bit &aster, an" usually you only nee" to start it up on'e per "ay (e.g., =hen you start "e!elopment). ?ou "o not nee" to stop an" restart the emulator e!ery time you =ant to test your appli'ation, in most 'ases. 5he emulator =ill go through a &e= startup phases, &irst =ith a plain-te;t MA2@ >0@M label,

*:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

"igure *&1 Android emulator@ initial startup segment

...then a graphi'al An"roi" logo,

&<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

"igure *-1 Android emulator@ secondary startup segment

be&ore e!entually lan"ing at the home s'reen (the &irst time you run the A-@, sho=n belo=) or the keyguar",

&*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

"igure *%1 Android home screen

0& you get the keyguar" (sho=n belo=), press the ME2$ button, or sli"e the green lo'k on the s'reen to the right, to get to the emulator7s home s'reen,

&&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

"igure *01 Android keyguard

Step 425 Set >p the /evice


?ou "o not nee" an An"roi" "e!i'e to get starte" in An"roi" appli'ation "e!elopment. +a!ing one is a goo" i"ea be&ore you try to ship an appli'ation (e.g., uploa" it to the An"roi" Market). An", perhaps you alrea"y ha!e a "e!i'e S maybe that is =hat is spurring your interest in "e!eloping &or An"roi". 5he &irst step to make your "e!i'e rea"y &or use =ith "e!elopment is to go into the %ettings appli'ation on the "e!i'e. *rom there, 'hoose Appli'ations, then @e!elopment. 5hat shoul" gi!e you a set o& 'he'kbo;es o& "e!elopment-relate" options to 'onsi"er,

&-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

"igure *21 Android device development settings

8enerally, you =ill =ant to enable $%1 "ebugging, so you 'an use your "e!i'e =ith the An"roi" buil" tools. ?ou 'an lea!e the other settings alone &or no= i& you =ish, though you may &in" the M%tay a=akeM option to be han"y, as it sa!es you &rom ha!ing to unlo'k your phone all o& the time =hile it is plugge" into $%1. 2e;t, you nee" to get your "e!elopment ma'hine set up to talk to your "e!i'e. 5hat pro'ess !aries by the operating system o& your "e!elopment ma'hine, as is 'o!ere" in the &ollo=ing se'tions.

,indo#s
When you &irst plug in your An"roi" "e!i'e, Win"o=s =ill attempt to &in" a "ri!er &or it. 0t is possible that, by !irtue o& other so&t=are you ha!e installe", that the "ri!er is rea"y &or use. 0& it &in"s a "ri!er, you are probably rea"y to go.

&%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

0& the "ri!er is not &oun", here are some options &or getting one.

,indo#s -pd te
%ome !ersions o& Win"o=s (e.g., -ista) =ill prompt you to sear'h Win"o=s $p"ate &or "ri!ers. 5his is 'ertainly =orth a shot, though not e!ery "e!i'e =ill ha!e supplie" its "ri!er to Mi'roso&t.

St nd rd Android Driver
0n your An"roi" %@D installation, you =ill &in" a google-usb driver "ire'tory, 'ontaining a generi' Win"o=s "ri!er &or An"roi" "e!i'es. ?ou 'an try pointing the "ri!er =iKar" at this "ire'tory to see i& it thinks this "ri!er is suitable &or your "e!i'e.

% nu. cturer*Supplied Driver


0& you still "o not ha!e a "ri!er, sear'h the C@ that 'ame =ith the "e!i'e (i& any) or sear'h the Web site o& the "e!i'e manu&a'turer. Motorola, &or e;ample, has "ri!ers a!ailable &or all o& their "e!i'es in one spot &or "o=nloa".

+S / nd )inu0
>""s are "e'ent that simply plugging in your "e!i'e =ill MGust =orkM. ?ou 'an see i& An"roi" re'ogniKes your "e!i'e !ia running adb devices in a shell (e.g., >% F 5erminal), =here adb is in your platform-tools/ "ire'tory o& your %@D. 0& you get output similar to the &ollo=ing, An"roi" "ete'te" your "e!i'e,
)ist of devices attached !&*+((,-*./0 device

0& you are running $buntu (or perhaps other Linu; !ariants), an" this 'omman" "i" not =ork, you may nee" to a"" some udev rules. *or e;ample,

&0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3o) To (et Started

here is a .1-android.rules &ile that =ill han"le the "e!i'es &rom a han"&ul o& manu&a'turers,
234252&$#667usb78 25292:idVendor;667-bb<78 #"=$67-0007 234252&$#667usb78 25292:idVendor;667>>b,78 #"=$67-0007 234252&$#667usb78 25292:idVendor;6671,d178 #"=$67-0007 234252&$#2667usb78 A&&?2:idVendor;6671,d178 A&&?2:id(roduct;667-c-178 #"=$67-00078 "@%$?67AmeB7 234252&$#667usb78 25292:idVendor;6671*d>78 25292:id(roduct;6671C.<78 #"=$67-0007 234252&$#667usb78 25292:idVendor;667-<e,78 25292:id(roduct;6670,1c78 #"=$67-0007

@rop that in your /etc/udev/rules.d "ire'tory on $buntu, then either reboot the 'omputer or other=ise reloa" the udev rules (e.g., sudo service udev reload). 5hen, unplug an" re-plug in the "e!i'e an" see i& it is "ete'te".

&2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1

.our "irst Android ProAect

2o= that you ha!e the An"roi" %@D, it is time to make your &irst An"roi" proGe't. 5he goo" ne=s is that this reRuires Kero lines o& 'o"e S An"roi"7s tools 'reate a M+ello, =orl":M appli'ation &or you as part o& 'reating a ne= proGe't. All you nee" to "o is buil" it, install it, an" see it 'ome up on your emulator or "e!i'e.

Step 4*5 Create the ?e) ProAect


An"roi"7s tools 'an 'reate a 'omplete skeleton proGe't &or you, =ith e!erything you nee" &or a 'omplete (albeit !ery tri!ial) An"roi" appli'ation. 5he only real "i&&eren'e 'omes &rom =hether you are using E'lipse or the 'omman" line.

Eclipse
*rom the E'lipse main menu, 'hoose *ile U 2e= U #roGe't..., an" this =ill bring up a list o& proGe't types to 'hoose &rom. *ol" open the An"roi" option an" 'li'k on An"roi" #roGe't,

&7
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

.our "irst Android ProAect

"igure *71 =clipse ?e) ProAect WiBard

#ress 2e;t to a"!an'e the =iKar" to the main An"roi" proGe't page,

&8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

.our "irst Android ProAect

"igure *81 =clipse ?e) ProAect WiBard@ Android ProAect

*ill in the &ollo=ing,


5he name o& the proGe't (e.g., 2o=) 5he An"roi" %@D you =ish to 'ompile against (e.g., 8oogle A#0s &or An"roi" 2....) 5he name o& the Ca!a pa'kage in =hi'h this proGe't goes (e.g., 'om.'ommons=are.an"roi".skeleton)
&:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

.our "irst Android ProAect

5he name o& the initial a'ti!ity to 'reate (e.g., 2o=)

"igure *:1 =clipse ?e) ProAect WiBard@ Android ProAect $continued'

At this point, 'li'king *inish =ill 'reate your E'lipse proGe't.

-<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

.our "irst Android ProAect

Comm nd )ine
+ere is a sample 'omman" that 'reates an An"roi" proGe't &rom the 'omman" line,
android create project --target 7Doogle Inc.:Doogle A(Is:/7 --path 2keleton/%oE --activitF %oE --package com.commonsEare.android.skeleton

5his =ill 'reate an appli'ation skeleton &or you, 'omplete =ith e!erything you nee" to buil" your &irst An"roi" appli'ation, Ca!a sour'e 'o"e, buil" instru'tions, et'. +o=e!er, you are probably going to nee" to 'ustomiKe this some=hat. +ere are =hat those 'omman"-line s=it'hes mean,

in"i'ates =hat !ersion o& An"roi" you are MtargetingM in terms o& your buil" pro'ess. ?ou nee" to supply the 0@ o& a target that is installe" on your "e!elopment ma'hine, one you "o=nloa"e" !ia the %@D an" A-@ Manager. ?ou 'an &in" out =hat targets are a!ailable !ia the android list targets 'omman". 5ypi'ally, your buil" pro'ess =ill target the ne=est !ersion o& An"roi" that you ha!e a!ailable.
--target

in"i'ates =here you =ant the proGe't &iles to be generate". An"roi" =ill 'reate a "ire'tory i& the one you name "oes not e;ist. *or e;ample, in the 'omman" sho=n abo!e, a 2keleton/%oE/ "ire'tory =ill be 'reate" (or use" i& it e;ists) un"erneath the 'urrent =orking "ire'tory, an" the proGe't &iles =ill be store" there.
--path

in"i'ates the Ca!a 'lass name o& your &irst a'ti!ity &or this proGe't. @o not in'lu"e a pa'kage name, an" the name has to meet Ca!a 'lass naming 'on!entions.
--activitF

in"i'ates the Ca!a pa'kage in =hi'h your &irst a'ti!ity =ill be lo'ate". 5his pa'kage also uniRuely i"enti&ies your proGe't on any "e!i'e on =hi'h you install it, an" this pa'kage also nee"s to be uniRue on the An"roi" Market i& you plan on "istributing your appli'ation there. +en'e, typi'ally, you 'onstru't your pa'kage base" on a "omain name you o=n (e.g., com.commonsEare.android.skeleton), to re"u'e the o""s o& an a''i"ental pa'kage name 'ollision =ith somebo"y else.
--package

-*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

.our "irst Android ProAect

*or your "e!elopment ma'hine, you =ill nee" to pi'k a suitable target, an" you may =ish to 'hange the path. 5he a'ti!ity an" pa'kage you 'an lea!e alone &or no=.

Step 4&5 Build@ nstall@ and Cun the Application in .our =mulator or /evice
+a!ing a proGe't is ni'e an" all, but it =oul" be e!en better i& =e 'oul" buil" an" run it, =hether on the An"roi" emulator or your An"roi" "e!i'e. >n'e again, the pro'ess "i&&ers some=hat "epen"ing on =hether you are using E'lipse or not.

Eclipse
With your proGe't sele'te" in the #a'kage E;plorer pane, 'li'k the green MplayM button in the E'lipse toolbar to run your proGe't. 5he &irst time you "o this, you =ill ha!e to go through a &e= steps to set up a Mrun 'on&igurationM, so E'lipse kno=s =hat you =ant to "o. *irst, in the M un AsM list, 'hoose MAn"roi" Appli'ationM,

"igure &<1 =clipse DCun AsD !ist -&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

.our "irst Android ProAect

0& you ha!e more than one emulator A-@ or "e!i'e a!ailable, you =ill then get an option to 'hoose =hi'h you =ish to run the appli'ation on. >ther=ise, i& you "o not ha!e a "e!i'e plugge" in, the emulator =ill start up =ith the A-@ you 'reate" earlier. 5hen, E'lipse =ill install the appli'ation on your "e!i'e or emulator an" start it up.

Comm nd )ine
*or "e!elopers not using E'lipse, in your terminal, 'hange into the 2keleton/%oE "ire'tory, then run the &ollo=ing 'omman",
ant clean install

5he Ant-base" buil" shoul" emit a list o& steps in!ol!e" in the installation pro'ess, =hi'h look like this,
4uildfile: /home/some-balding-guF/projects/2keleton/%oE/build.Gml AsetupB Android 2=H &ools ?evision , AsetupB (roject &arget: Doogle A(Is AsetupB Vendor: Doogle Inc. AsetupB (latform Version: >.1-update1 AsetupB A(I level: / AsetupB AsetupB -----------------AsetupB ?esolving librarF dependencies: AsetupB %o librarF dependencies. AsetupB AsetupB -----------------AsetupB AsetupB @A?%I%D: %o min2dkVersion value set. Application Eill install on all Android versions. AsetupB AsetupB Importing rules file: tools/ant/main rules.Gml clean: AdeleteB =eleting directorF /home/some-balding-guF/projects/2keleton/%oE/bin -debug-obfuscation-check: -set-debug-mode: -compile-tested-if-test: -dirs: AechoB +reating output directories if needed... AmkdirB +reated dir: /home/some-balding-guF/projects/2keleton/%oE/bin

--

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

.our "irst Android ProAect

AmkdirB +reated dir: /home/some-balding-guF/projects/2keleton/%oE/gen AmkdirB +reated dir: /home/some-balding-guF/projects/2keleton/%oE/bin/classes -pre-build: -resource-src: AechoB Denerating ?.java / #anifest.java from the resources... -aidl: AechoB +ompiling aidl files into Java classes... -pre-compile: compile: AjavacB /opt/android-sdk-linuG/tools/ant/main rules.Gml:C01: Earning: IincludeantruntimeI Eas not set8 defaulting to build.sFsclasspath6lastJ set to false for repeatable builds AjavacB +ompiling > source files to /home/some-baldingguF/projects/2keleton/%oE/bin/classes -post-compile: -obfuscate: -deG: AechoB +onverting compiled files and eGternal libraries into /home/somebalding-guF/projects/2keleton/%oE/bin/classes.deG... -package-resources: AechoB (ackaging resources AaaptB +reating full resource package... -package-debug-sign: AapkbuilderB +reating %oE-debug-unaligned.apk and signing it Eith a debug keF... debug: AechoB ?unning Kip align on final apk... AechoB =ebug (ackage: /home/some-balding-guF/projects/2keleton/%oE/bin/%oEdebug.apk 43I)= 23++$2293) &otal time: < seconds

2ote the 43I)= 23++$2293) at the bottom S that is ho= you kno= the appli'ation 'ompile" su''ess&ully. When you ha!e a 'lean buil", in your emulator or "e!i'e, open up the appli'ation laun'her, typi'ally &oun" at the bottom o& the home s'reen,

-%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

.our "irst Android ProAect

"igure &*1 Android emulator application launcher

2oti'e there is an i'on &or your %oE appli'ation. Cli'k on it to open it an" see your &irst a'ti!ity in a'tion. 5o lea!e the appli'ation an" return to the laun'her, press the M1ACD buttonM, lo'ate" to the right o& the VME2$W button, an" looks like an arro= pointing to the le&t.

-0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 2

=xamining .our "irst ProAect

5he pre!ious 'hapter steppe" you through 'reating a stub proGe't. 2o=, let us take a peek at =hat is insi"e o& this proGe't, so you un"erstan" =hat An"roi" gi!es you at the outset an" =hat the roles are &or the !arious "ire'tories an" &iles.

ProAect Structure
5he An"roi" buil" system is organiKe" aroun" a spe'i&i' "ire'tory tree stru'ture &or your An"roi" proGe't, mu'h like any other Ca!a proGe't. 5he spe'i&i's, though, are &airly uniRue to An"roi" S the An"roi" buil" tools "o a &e= e;tra things to prepare the a'tual appli'ation that =ill run on the "e!i'e or emulator. +ere7s a Rui'k primer on the proGe't stru'ture, to help you make sense o& it all, parti'ularly &or the sample 'o"e re&eren'e" in this book.

Root Contents
When you 'reate a ne= An"roi" proGe't (e.g., !ia android create project), you get se!eral items in the proGe't7s root "ire'tory, in'lu"ing,
Android#anifest.Gml, =hi'h

is an FML &ile "es'ribing the appli'ation being built an" =hat 'omponents S a'ti!ities, ser!i'es, et'. S are being supplie" by that appli'ation
bin/, =hi'h

hol"s the appli'ation on'e it is 'ompile"


-7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=xamining .our "irst ProAect

libs/, res/,

=hi'h hol"s any thir"-party Ca!a CA s your appli'ation reRuires =hi'h hol"s Mresour'esM, su'h as i'ons, 8$0 layouts, an" the like, that get pa'kage" =ith the 'ompile" Ca!a in the appli'ation
src/, =hi'h

hol"s the Ca!a sour'e 'o"e &or the appli'ation

0n a""ition to the &iles an" "ire'tories sho=n abo!e, you may &in" any o& the &ollo=ing in An"roi" proGe'ts,
assets/, =hi'h hol" other stati' &iles you =ish pa'kage" =ith the appli'ation &or "eployment onto the "e!i'e gen/,

=here An"roi"7s buil" tools =ill pla'e sour'e 'o"e that they generate
build.Gml an" *.properties, =hi'h are use" as part o& the Ant-base" 'omman"-line buil" pro'ess, i& you are not using E'lipse proguard.cfg,

=hi'h is use" &or integration =ith #ro8uar" &or ob&us'ating your An"roi" 'o"e

The S#e t +.. 3our Bro#


When you 'reate" the proGe't (e.g., !ia android create project), you supplie" the &ully-Ruali&ie" 'lass name o& the MmainM a'ti!ity &or the appli'ation (e.g., com.commonsEare.android.2ome=emo). ?ou =ill then &in" that your proGe't7s src/ tree alrea"y has the namespa'e "ire'tory tree in pla'e, plus a stub ActivitF sub'lass representing your main a'ti!ity (e.g., src/com/commonsEare/android/2ome=emo.java). ?ou are =el'ome to mo"i&y this &ile an" a"" others to the src/ tree as nee"e" to implement your appli'ation. 5he &irst time you 'ompile the proGe't (e.g., !ia ant), out in the MmainM a'ti!ity7s namespa'e "ire'tory, the An"roi" buil" 'hain =ill 'reate ?.java. 5his 'ontains a number o& 'onstants tie" to the !arious resour'es you pla'e" out in the res/ "ire'tory tree. ?ou shoul" not mo"i&y ?.java yoursel&, letting the An"roi" tools han"le it &or you. ?ou =ill see throughout many o&

-8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=xamining .our "irst ProAect

the samples =here =e re&eren'e things in ?.java (e.g., re&erring to a layout7s i"enti&ier !ia ?.laFout.main).

And "o#4 The Rest o. the Story


?ou =ill also &in" that your proGe't has a res/ "ire'tory tree. 5his hol"s Mresour'esM S stati' &iles that are pa'kage" along =ith your appli'ation, either in their original &orm or, o''asionally, in a prepro'esse" &orm. %ome o& the sub"ire'tories you =ill &in" or 'reate un"er res/ in'lu"e,
res/draEable/ res/laFout/ res/menu/

&or images (#28, C#E8, et'.)

&or FML-base" $0 layout spe'i&i'ations

&or FML-base" menu spe'i&i'ations

res/raE/ &or general-purpose &iles (e.g,. an au"io 'lip, a C%- &ile o& a''ount in&ormation) res/values/

&or strings, "imensions, an" the like

res/Gml/ &or other general-purpose FML &iles you =ish to ship

%ome o& the "ire'tory names may ha!e su&&i;es, like res/draEable-hdpi/. 5his in"i'ates that the "ire'tory o& resour'es shoul" only be use" in 'ertain 'ir'umstan'es S in this 'ase, the "ra=able resour'es shoul" only be use" on "e!i'es =ith high-"ensity s'reens. We =ill 'o!er all o& these, an" more, in later 'hapters o& this book. 0n your initial proGe't, you =ill &in",
res/draEable-hdpi/icon.png, res/draEable-mdpi/icon.png, res/draEable-ldpi/icon.png, an" =hi'h are three ren"itions o& a pla'ehol"er i'on &or your appli'ation &or high-, lo=-, an" me"ium"ensity s'reens, respe'ti!ely res/laFout/main.Gml,

=hi'h 'ontains an FML &ile that "es'ribes the !ery simple layout o& your user inter&a'e

-:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=xamining .our "irst ProAect

res/values/strings.Gml, =hi'h 'ontains e;ternaliKe" strings,

notably

the pla'ehol"er name o& your appli'ation

,h t 3ou Get +ut +. It


When you 'ompile your proGe't (!ia ant or the 0@E), bin/ "ire'tory un"er your proGe't root. %pe'i&i'ally,
bin/classes/

the results go into the

hol"s the 'ompile" Ca!a 'lasses hol"s the e;e'utable 'reate" &rom those 'ompile"

bin/classes.deG

Ca!a 'lasses

hol"s your appli'ation7s resour'es, pa'kage" as a Q0# &ile (=here Fourapp is the name o& your appli'ation)
bin/Fourapp.ap bin/Fourapp-*.apk

is the a'tual An"roi" appli'ation (=here * !aries)

5he .apk &ile is a Q0# ar'hi!e 'ontaining the .deG &ile, the 'ompile" e"ition o& your resour'es (resources.arsc), any un-'ompile" resour'es (su'h as =hat you put in res/raE/) an" the Android#anifest.Gml &ile. 0& you buil" a "ebug !ersion o& the appli'ation S =hi'h is the "e&ault S you =ill ha!e Fourapp-debug.apk an" Fourapp-debug-aligned.apk as t=o !ersions o& your A#D. 5he latter has been optimiKe" =ith the Kipalign utility to make it run &aster.

nside .our +anifest


5he &oun"ation &or any An"roi" appli'ation is the mani&est &ile, Android#anifest.Gml in the root o& your proGe't. +ere is =here you "e'lare =hat is insi"e your appli'ation S the a'ti!ities, the ser!i'es, an" so on. ?ou also in"i'ate ho= these pie'es atta'h themsel!es to the o!erall An"roi" systemT &or e;ample, you in"i'ate =hi'h a'ti!ity (or a'ti!ities) shoul" appear on the "e!i'e7s main menu (a.k.a., laun'her). When you 'reate your appli'ation, you =ill get a starter mani&est generate" &or you. *or a simple appli'ation, o&&ering a single a'ti!ity an" nothing else, the auto-generate" mani&est =ill probably =ork out &ine, or perhaps reRuire
%<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=xamining .our "irst ProAect

a &e= minor mo"i&i'ations. >n the other en" o& the spe'trum, the mani&est &ile &or the An"roi" A#0 "emo suite is o!er 1,000 lines long. ?our pro"u'tion An"roi" appli'ations =ill probably &all some=here in the mi""le.

In The Be!innin!4 There , s the Root4 And It , s Good


5he root o& all mani&est &iles is, not surprisingly, a manifest element,
Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.search7M ... L/manifestM

2ote the namespa'e "e'laration. Curiously, the generate" mani&ests only apply it on the attributes, not the elements (e.g., manifest, not android:manifest). +o=e!er, that pattern =orks, so unless An"roi" 'hanges, sti'k =ith their pattern. 5he biggest pie'e o& in&ormation you nee" to supply on the manifest element is the package attribute (also 'uriously not-namespa'e"). +ere, you 'an pro!i"e the name o& the Ca!a pa'kage that =ill be 'onsi"ere" the MbaseM o& your appli'ation. 5hen, e!ery=here else in the mani&est &ile that nee"s a 'lass name, you 'an Gust substitute a lea"ing "ot as shorthan" &or the pa'kage. *or e;ample, i& you nee"e" to re&er to com.commonsEare.android.search.2nicklefritK in this mani&est sho=n abo!e, you 'oul" Gust use .2nicklefritK, sin'e com.commonsEare.android.search is "e&ine" as the appli'ation7s pa'kage. As note" in the pre!ious 'hapter, your pa'kage also is a uniRue i"enti&ier &or your appli'ation. A "e!i'e 'an only ha!e one appli'ation installe" =ith a gi!en pa'kage, an" the An"roi" Market =ill only list one proGe't =ith a gi!en pa'kage. ?our mani&est also spe'i&ies android:version%ame an" android:version+ode attributes. 5hese represent the !ersions o& your appli'ation. 5he android:version%ame !alue is =hat the user =ill see in the Appli'ations list in
%*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=xamining .our "irst ProAect

their %ettings appli'ation. Also, the !ersion name is use" by the An"roi" Market listing, i& you are "istributing your appli'ation that =ay. 5he !ersion name 'an be any string !alue you =ant. 5he android:version+ode, on the other han", must be an integer, an" ne=er !ersions must ha!e higher !ersion 'o"es than "o ol"er !ersions. An"roi" an" the An"roi" Market =ill 'ompare the !ersion 'o"e o& a ne= A#D to the !ersion 'o"e o& an installe" appli'ation to "etermine i& the ne= A#D is in"ee" an up"ate. 5he typi'al approa'h is to start the !ersion 'o"e at 1 an" in'rement it =ith ea'h pro"u'tion release o& your appli'ation, though you 'an 'hoose another 'on!ention i& you =ish.

An Applic tion 5or 3our Applic tion


0n your initial proGe't7s mani&est, the only 'hil" o& the LmanifestM element is an LapplicationM element. 5he 'hil"ren o& the LapplicationM element represent the 'ore o& the mani&est &ile. >ne attribute o& the LapplicationM element that you may nee" in sele't 'ir'umstan'es is the android:debuggable attribute. 5his nee"s to be set to true i& you are installing the appli'ation on an a'tual "e!i'e an" you are using E'lipse (or another "ebugger) an" i& your "e!i'e pre'lu"es "ebugging =ithout this &lag. *or e;ample, the 2e;us >ne reRuires android:debuggable 6 7true7, a''or"ing to some reports. 1y "e&ault, =hen you 'reate a ne= An"roi" proGe't, you get a single LactivitFM element insi"e the LapplicationM element,
LNGml version671.-7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.skeleton7M LapplicationM LactivitF android:name67.%oE7 android:label67%oE7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM L/manifestM

%&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=xamining .our "irst ProAect

5his element supplies android:name &or the 'lass implementing the a'ti!ity, android:label &or the "isplay name o& the a'ti!ity, an" (&reRuently) an Lintent-filterM 'hil" element "es'ribing un"er =hat 'on"itions this a'ti!ity =ill be "isplaye". 5he sto'k LactivitFM element sets up your a'ti!ity to appear in the laun'her, so users 'an 'hoose to run it. As =e7ll see later in this book, you 'an ha!e se!eral a'ti!ities in one proGe't, i& you so 'hoose.

%-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 6

A Bit About =clipse

E'lipse is an e;tremely popular 0@E, parti'ularly &or Ca!a "e!elopment. 0t is also "esigne" to be e;tensible !ia an a""-in system. 5o top it o&&, E'lipse is open sour'e. 5hat 'ombination ma"e it an i"eal 'hoi'e o& 0@E to get attention &rom the 'ore An"roi" "e!eloper team. %pe'i&i'ally, to go alongsi"e the An"roi" %@D, 8oogle has publishe" some a""-ins &or the E'lipse en!ironment. #rimary among these is the An"roi" @e!eloper 5ools (A@5) a""-in, =hi'h gi!es the 'ore o& E'lipse a=areness o& An"roi".

What the A/T (ives .ou


5he A@5 a""-in, in essen'e, takes regular E'lipse operations an" e;ten"s them to =ork =ith An"roi" proGe'ts. *or e;ample, =ith E'lipse, you get,

2e= proGe't =iKar"s to 'reate regular An"roi" proGe'ts, An"roi" test proGe'ts, et'. 5he ability to run an An"roi" proGe't Gust like you might run a regular Ca!a appli'ation S !ia the green un button in the toolbar S "espite the &a't that this really in!ol!es pushing the An"roi" appli'ation o!er to an emulator or "e!i'e, possibly e!en starting up the emulator i& it is not running 5ooltip support &or An"roi" 'lasses an" metho"s An" so on
%0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

0n a""ition, the latest !ersion o& the A@5 pro!i"es you =ith preliminary support &or "rag-an"-"rop 8$0 e"iting. While this book =ill &o'us on the FML &iles that E'lipse =ill generate, E'lipse no= lets you assemble those FML &iles by "ragging $0 'omponents aroun" on the s'reen, a"Gusting properties as you go. @rag-an"-"rop 8$0 e"iting is &airly ne=, an" so there may be a &e= rough e"ges &or a =hile as the 'ommunity an" 8oogle i"enti&y the problems an" limitations =ith the 'urrent implementation.

Coping )ith =clipse


E'lipse is a po=er&ul tool. Like many po=er&ul tools, E'lipse is sometimes 'on&oun"ing. @etermining ho= to sol!e some spe'i&i' "e!elopment problem 'an be a 'hallenge, e;a'erbate" by the ne=-ness o& An"roi" itsel&. 5his se'tion o&&ers some tips &or han"ling some 'ommon issues in using E'lipse =ith An"roi".

Ho# to Import

"on*Eclipse Pro7ect

2ot all An"roi" proGe'ts ship =ith E'lipse proGe't &iles, su'h as the sample proGe'ts asso'iate" =ith this book. +o=e!er, these 'an still be easily a""e" to your E'lipse =orkspa'e, i& you =ish. +ere is ho= to "o it: *irst, 'hoose *ile O 2e= O #roGe't... &rom the E'lipse main menu,

%2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

"igure &&1 "ile menu in =clipse

5hen, 'hoose An"roi" O An"roi" #roGe't &rom the tree o& a!ailable proGe't types,

%7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

"igure &-1 ?e) proAect )iBard in =clipse

2ote, i& you "o not see this option, you ha!e not installe" the An"roi" @e!eloper 5ools. 5hen, in the ne;t page o& the proGe't 'reation =iKar", 'hoose the MCreate proGe't &rom e;isting sour'eM ra"io button, 'li'k the V1ro=se...W button, an" open the "ire'tory 'ontaining your proGe't7s An"roi"Mani&est.;ml &ile. 5his =ill populate most o& the rest o& this s'reen, though you may nee" to also spe'i&y a buil" target &rom the table,

%8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

"igure &%1 Android proAect )iBard in =clipse

5hen, 'li'k V*inishW. 5his =ill return you to E'lipse, =ith the importe" proGe't in your =orkspa'e,

%:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

"igure &01 Android proAect tree in =clipse

2e;t, right-'li'k o!er the proGe't name, an" 'hoose 1uil" #ath O Con&igure 1uil" #ath &rom the 'onte;t menu,

"igure &21 ProAect context menu in =clipse 0<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

5his brings up the buil" path portion o& the proGe't properties =in"o=,

"igure &71 ProAect properties )indo) in =clipse

0& the An"roi" CA is not 'he'ke" (see the An"roi" 2.2 entry in the abo!e image), 'he'k it, then 'lose the properties =in"o=. At this point, your proGe't shoul" be rea"y &or use.

Ho# to Get To DD%S


Many times, you =ill be tol" to take a look at something in @@M%, su'h as the LogCat tab to e;amine Ca!a sta'k tra'es. 0n E'lipse, @@M% is a perspe'ti!e. 5o open this perspe'ti!e in your =orkspa'e, 'hoose Win"o= O >pen #erspe'ti!e O >ther... &rom the main menu,

0*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

"igure &81 Perspective menu in =clipse

5hen, in the list o& perspe'ti!es, 'hoose @@M%,

0&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

"igure &:1 Perspective roster in =clipse

5his =ill a"" the @@M% perspe'ti!e to your =orkspa'e an" open it in your E'lipse 0@E. @@M% is 'o!ere" in greater "etail in a later 'hapter o& this book.

Ho# to Cre te n Emul tor


1y "e&ault, your E'lipse en!ironment has no An"roi" emulators set up. ?ou =ill nee" one be&ore you 'an run your proGe't su''ess&ully. 5o "o this, &irst 'hoose Win"o= O An"roi" %@D an" A-@ Manager &rom the main menu,

0-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

"igure -<1 Android A;/ +anager menu option in =clipse

5hat brings up the same =in"o= as you 'an get by running android &rom the 'omman" line.

Ho# to Run

Pro7ect

8i!en that you ha!e an A-@ "e&ine", or that you ha!e a "e!i'e set up &or "ebugging an" 'onne'te" to your "e!elopment ma'hine, you 'an run your proGe't in the emulator. *irst, 'li'k the un toolbar button, or 'hoose #roGe't O un &rom the main menu. 5his =ill bring up the M un AsM "ialog the &irst time you run the proGe't,

0%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

"igure -*1 Android A;/ +anager menu option in =clipse

Choose An"roi" Appli'ation an" 'li'k >D. 0& you ha!e more than one A-@ or "e!i'e a!ailable, you =ill be presente" =ith a =in"o= =here you 'hoose the "esire" target en!ironment. 5hen, the emulator =ill start up to run your appli'ation. 2ote that you =ill nee" to unlo'k the lo'k s'reen on the emulator (or "e!i'e) i& it is lo'ke".

Ho# "ot to Run 3our Pro7ect


When you go to run your proGe't, be sure to not ha!e an FML &ile be the a'ti!e tab in the e"itor. Attempting to MrunM this =ill result in a .out &ile being 'reate" in =hate!er "ire'tory the FML &ile li!es in (e.g., res/laFout/main.Gml.out). 5o re'o!er, simply "elete the o&&en"ing .out &ile an" try running again, this time =ith a Ca!a &ile as the a'ti!e tab.

Alternative /=s
0& you really like E'lipse an" the A@5, you may =ant to 'onsi"er M>5>@E- %tu"io &or An"roi". 5his is another set o& a""-ins &or E'lipse,

00

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

augmenting the A@5 an" o&&ering a number o& other An"roi"-relate" "e!elopment &eatures, in'lu"ing,

More =iKar"s &or helping you 'reate An"roi" 'lasses 0ntegrate" %JLite bro=sing, so you 'an manipulate a %JLite "atabase in your emulator right &rom your 0@E More !ali"ators to 'he'k &or 'ommon bugs, an" a library o& 'o"e snippets to ha!e &e=er bugs at the outset Assistan'e =ith translating your appli'ation to multiple languages An" mu'h more

While M>5>@E- %tu"io &or An"roi" is publishe" by Motorola, you 'an use it to buil" appli'ations &or all An"roi" "e!i'es, not only those manu&a'ture" by Motorola themsel!es. >ther 0@Es are slo=ly getting their eRui!alents o& the A@5, albeit =ith minimal assistan'e &rom 8oogle. *or e;ample, 0ntelliC7s 0@EA has a mo"ule &or An"roi" S originally 'ommer'ial, it is part o& the open sour'e 'ommunity e"ition o& 0@EA as o& !ersion 10. An", o& 'ourse, you "o not nee" to use an 0@E at all. While this may soun" sa'rilegious to some, 0@Es are not the only =ay to buil" appli'ations. Mu'h o& =hat is a''omplishe" !ia the A@5 'an be a''omplishe" through 'omman"-line eRui!alents, meaning a shell an" an e"itor is all you truly nee". *or e;ample, the author o& this book "oes not presently use an 0@E an" has no intention o& a"opting E'lipse any time soon.

+ore on the Tools


More 'o!erage o& @@M%, +ierar'hy -ie=, an" other tools 'an be &oun" later in this book.

02

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

A Bit About =clipse

/=s111And This Book


?ou are =el'ome to use E'lipse as you =ork through this book. ?ou are =el'ome to use another 0@E i& you =ish. ?ou are e!en =el'ome to skip the 0@E outright an" Gust use an e"itor. 5his book is &o'use" on "emonstrating An"roi" 'apabilities an" the A#0s &or e;ploiting those 'apabilities. 0t is not aime" at tea'hing the use o& any one 0@E. As su'h, the sample 'o"e sho=n shoul" =ork in any 0@E, parti'ularly i& you &ollo= the instru'tions &or importing non-E'lipse proGe'ts into E'lipse supplie" abo!e.

07

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 8

=nhancing .our "irst ProAect

5he An"roi"Mani&est.;ml &ile that An"roi" generate" &or your &irst proGe't gets the Gob "one. +o=e!er, &or a pro"u'tion appli'ation, you may =ish to 'onsi"er a""ing a &e= attributes an" elements, su'h as those "es'ribe" in this 'hapter.

Supporting +ultiple Screens


An"roi" "e!i'es 'ome =ith a =i"e range o& s'reen siKes, &rom 2.8M tiny smartphones to </M 8oogle 5-s. An"roi" "i!i"es these into &our bu'kets, base" on physi'al siKe an" the "istan'e at =hi'h they are usually !ie=e",

%mall (un"er .M) 2ormal (.M to aroun" <.AM) Large (<.AM to aroun" 10M) E;tra-large (o!er 10M)

1y "e&ault, your appli'ation =ill not support small s'reens, =ill support normal s'reens, an" may support large an" e;tra-large s'reens !ia some automate" 'on!ersion 'o"e built into An"roi". 5o truly support all the s'reen siKes you =ant, you shoul" 'onsi"er a""ing a Lsupports-screensM element. 5his enumerates the s'reen siKes you ha!e e;pli'it support &or. *or e;ample, i& you =ant to support small s'reens, you

0:
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

=nhancing .our "irst ProAect

=ill nee" the Lsupports-screensM element. %imilarly, i& you are pro!i"ing 'ustom $0 support &or large or e;tra-large s'reens, you =ill =ant to ha!e the Lsupports-screensM element. %o, =hile the starting mani&est &ile =orks, han"ling multiple s'reen siKes is something you =ill =ant to think about. Mu'h more in&ormation about pro!i"ing soli" support &or all s'reen siKes 'an be &oun" later in this book.

Specifying ;ersions
As =as note" in the pre!ious 'hapter, your mani&est alrea"y 'ontains some !ersion in&ormation, about your o=n appli'ation7s !ersion. +o=e!er, you probably =ant to a"" a Luses-sdkM element as a 'hil" o& the LmanifestM element to your Android#anifest.Gml &ile, to spe'i&y =hat !ersions o& An"roi" you are supporting. 1y "e&ault, your appli'ation is assume" to support e!ery An"roi" !ersion &rom 1.0 to the 'urrent ..0 an" on=ar" to any !ersion in the &uture. Most likely, that is not =hat you =ant. 5he important attribute &or your Luses-sdkM element is android:min2dkVersion. 5his in"i'ates =hat is the ol"est !ersion o& An"roi" you are testing =ith your appli'ation. 5he !alue o& the attribute is an integer representing the An"roi" %@D !ersion,

most

An"roi" 1.0 X 1 An"roi" 1.1 X 2 An"roi" 1.A X . An"roi" 1./ X < An"roi" 2.0 X A An"roi" 2.0.1 X / An"roi" 2.1 X 4 An"roi" 2.2 X 8 An"roi" 2.. X 3 An"roi" 2.... X 10
2<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=nhancing .our "irst ProAect

An"roi" ..0 X 11

%o, i& you are only testing your appli'ation on An"roi" 2.1 an" ne=er !ersions o& An"roi", you =oul" set your android:min2dkVersion to be /. ?ou may also =ish to spe'i&y an android:target2dkVersion attribute. 5his in"i'ates =hat !ersion o& An"roi" you are thinking o& as you are =riting your 'o"e. 0& your appli'ation is run on a ne=er !ersion o& An"roi", An"roi" may "o some things to try to impro!e 'ompatibility o& your 'o"e =ith respe't to 'hanges ma"e in the ne=er An"roi". %o, right no=, you might spe'i&y android:target2dkVersion671-7, in"i'ating you are =riting your appli'ation =ith An"roi" 2.... in min" S i& your app some"ay is run on an An"roi" ..0 "e!i'e, An"roi" may take some e;tra steps to make sure your 2....-'entri' 'o"e runs 'orre'tly on the ..0 "e!i'e. 0n parti'ular, to get the ne= M+oney'ombM look-an"-&eel =hen running on an An"roi" ..0 (or higher) tablet, you nee" to spe'i&y a target %@D !ersion o& 11 S this =ill be 'o!ere" in more "etail later in the book.

2*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

PART II Activities

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 9

Ce)riting .our "irst ProAect

5he proGe't you 'reate" in a pre!ious 'hapter =as Gust the "e&ault &iles generate" by the An"roi" buil" tools S you "i" not =rite any Ca!a 'o"e yoursel&. 0n this 'hapter, =e =ill mo"i&y that proGe't to ha!e a some=hat more intera'ti!e sample. Along the =ay, =e =ill e;amine the basi' Ca!a 'o"e that makes up an An"roi" a'ti!ity. 2>5E, 5he instru'tions in this 'hapter assume you &ollo=e" the original instru'tions in terms o& the names o& pa'kages an" &iles. 0& you use" "i&&erent names ba'k then, you =ill nee" to a"Gust the &ollo=ing steps to mat'h.

The Activity
?our proGe't7s src/ "ire'tory 'ontains the stan"ar" Ca!a-style tree o& "ire'tories base" upon the Ca!a pa'kage you 'hose =hen you 'reate" the proGe't (e.g., com.commonsEare.android results in src/com/commonsEare/android/). 0nsi"e the innermost "ire'tory you shoul" &in" a pre-generate" sour'e &ile name" %oE.java, =hi'h is =here your &irst a'ti!ity =ill go. >pen %oE.java in your e"itor an" paste in the &ollo=ing 'o"e,
package com.commonsEare.android.skeletonJ import android.app.ActivitFJ

20
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Ce)riting .our "irst ProAect

import import import import

android.os.4undleJ android.vieE.VieEJ android.Eidget.4uttonJ java.util.=ateJ

public class %oE eGtends ActivitF implements VieE."n+lick)istener : 4utton btnJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ btn6neE ButtonPthisQJ btn.setOnClickListenerPthisQJ updateTimePQJ setContentViewPbtnQJ

public void onClickPVieE vieEQ : updateTimePQJ ; private void updateTimePQ : btn.setTextPneE DatePQ.toStringPQQJ ; ;

>r, i& you "o=nloa" the sour'e &iles o&& the Web site, you 'an Gust use the 2keleton/%oE proGe't "ire'tly.

/issecting the Activity


Let7s e;amine this Ca!a 'o"e pie'e by pie'e,
package com.commonsEare.android.skeletonJ import import import import import android.app.ActivitFJ android.os.4undleJ android.vieE.VieEJ android.Eidget.4uttonJ java.util.=ateJ

5he pa'kage "e'laration nee"s to be the same as the one you use" =hen 'reating the proGe't. An", like any other Ca!a proGe't, you nee" to import any 'lasses you re&eren'e. Most o& the An"roi"-spe'i&i' 'lasses are in the android pa'kage.

22

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Ce)riting .our "irst ProAect

emember that not e!ery Ca!a %E 'lass is a!ailable to An"roi" programs: -isit the An"roi" 'lass re&eren'e to see =hat is an" is not a!ailable.
public class %oE eGtends ActivitF implements VieE."n+lick)istener : 4utton btnJ

A'ti!ities are publi' 'lasses, inheriting &rom the android.app.ActivitF base 'lass. 0n this 'ase, the a'ti!ity hol"s a button ( btn). %in'e, &or simpli'ity, =e =ant to trap all button 'li'ks Gust =ithin the a'ti!ity itsel&, =e also ha!e the a'ti!ity 'lass implement "n+lick)istener.
O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ btn6neE ButtonPthisQJ btn.setOnClickListenerPthisQJ updateTimePQJ setContentViewPbtnQJ ;

5he on+reatePQ metho" is in!oke" =hen the a'ti!ity is starte". 5he &irst thing you shoul" "o is 'hain up=ar" to the super'lass, so the sto'k An"roi" a'ti!ity initialiKation 'an be "one. 0n our implementation, =e then 'reate the button instan'e (neE 4uttonPthisQ), tell it to sen" all button 'li'ks to the a'ti!ity instan'e itsel& (!ia set"n+lick)istenerPQ), 'all a pri!ate update&imePQ metho" (see belo=), an" then set the a'ti!ity7s 'ontent !ie= to be the button itsel& (!ia set+ontentVieEPQ). We =ill "is'uss that magi'al 4undle icicle in a later 'hapter. *or the moment, 'onsi"er it an opaRue han"le that all a'ti!ities re'ei!e upon 'reation.
public void onClickPVieE vieEQ : updateTimePQJ ;

0n %=ing, a J4utton 'li'k raises Action)istener 'on&igure" &or the

an Action$vent, =hi'h is passe" to the button. 0n An"roi", a button 'li'k 'auses


27

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Ce)riting .our "irst ProAect

on+lickPQ

to be in!oke" in the "n+lick)istener instan'e 'on&igure" &or the button. 5he listener is pro!i"e" the !ie= that triggere" the 'li'k (in this 'ase, the button). All =e "o here is 'all that pri!ate update&imePQ metho",
private void updateTimePQ : btn.setTextPneE DatePQ.toStringPQQJ ;

When =e open the a'ti!ity (on+reatePQ) or =hen the button is 'li'ke" (on+lickPQ), =e up"ate the button7s label to be the 'urrent time !ia set&eGtPQ, =hi'h &un'tions mu'h the same as the J4utton eRui!alent.

Building and Cunning the Activity


5o buil" the a'ti!ity, either use your 0@E7s built-in An"roi" pa'kaging tool, or run ant clean install in the base "ire'tory o& your proGe't, as =as "es'ribe" in a pre!ious 'hapter. 5hen, run the a'ti!ity S it shoul" be automati'ally laun'he" &or you i& you are using E'lipse, else &in" the a'ti!ity in the home s'reen laun'her. ?ou shoul" see an a'ti!ity akin to,

"igure -&1 The ?o) demonstration activity

28

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Ce)riting .our "irst ProAect

Cli'king the button S in other =or"s, pretty mu'h any=here on the phone7s s'reen S =ill up"ate the time sho=n in the button7s label. 2ote that the label is 'entere" horiKontally an" !erti'ally, as those are the "e&ault styles applie" to button 'aptions. We 'an 'ontrol that &ormatting, =hi'h =ill be 'o!ere" in a later 'hapter. A&ter you are "one gaKing at the a=esomeness o& A"!an'e" #ush-1utton 5e'hnologyY, you 'an 'li'k the ba'k button on the emulator to return to the laun'her.

About the Cemaining =xamples


5he 'hapters so &ar ha!e gi!en you some steps to =ork through yoursel&. 0& you like that style o& learning, you may =ish to rea" An"roi" #rogramming 5utorials, by the author o& this book. 5hat book 'ontains o!er <0 tutorials =ith step-by-step instru'tions, so you 'an learn by "oing. 0& you obtaine" this book on the Wares'ription plan, you alrea"y ha!e a''ess to Android Programming Tutorials S Gust "o=nloa" that book an" go: 5he rest o& the 'hapters in this book present e;isting sample 'o"e, =hi'h you 'an "o=nloa" i& you =ish. ?ou are also =el'ome to key or paste in the sample 'o"e &rom the book, though that is not the e;pe'tation.

2:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER :

>sing E+!#Based !ayouts

While it is te'hni'ally possible to 'reate an" atta'h =i"gets to our a'ti!ity purely through Ca!a 'o"e, the =ay =e "i" in the pre'e"ing 'hapter, the more 'ommon approa'h is to use an FML-base" layout &ile. @ynami' instantiation o& =i"gets is reser!e" &or more 'ompli'ate" s'enarios, =here the =i"gets are not kno=n at 'ompile-time (e.g., populating a 'olumn o& ra"io buttons base" on "ata retrie!e" o&& the 0nternet). With that in min", it7s time to break out the FML an" learn ho= to lay out An"roi" a'ti!ity !ie=s that =ay.

What s an E+!#Based !ayoutF


As the name suggests, an FML-base" layout is a spe'i&i'ation o& =i"gets7 relationships to ea'h other S an" to 'ontainers S en'o"e" in FML &ormat. %pe'i&i'ally, An"roi" 'onsi"ers FML-base" layouts to be resour'es, an" as su'h layout &iles are store" in the res/laFout "ire'tory insi"e your An"roi" proGe't. Ea'h FML &ile 'ontains a tree o& elements spe'i&ying a layout o& =i"gets an" 'ontainers that make up one VieE. 5he attributes o& the FML elements are properties, "es'ribing ho= a =i"get shoul" look or ho= a 'ontainer shoul" beha!e. *or e;ample, i& a 4utton element has an attribute !alue o& android:teGt2tFle 6 7bold7, that means that the te;t appearing on the &a'e o& the button shoul" be ren"ere" in a bol"&a'e &ont style.
7*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

>sing E+!#Based !ayouts

An"roi"7s %@D ships =ith a tool (aapt) =hi'h uses the layouts. 5his tool shoul" be automati'ally in!oke" by your An"roi" tool 'hain (e.g., E'lipse, Ant7s build.Gml). >& parti'ular importan'e to you as a "e!eloper is that aapt generates the ?.java sour'e &ile =ithin your proGe't7s gen/ "ire'tory, allo=ing you to a''ess layouts an" =i"gets =ithin those layouts "ire'tly &rom your Ca!a 'o"e, as =ill be "emonstrate" later in this 'hapter.

Why >se E+!#Based !ayoutsF


Most e!erything you "o using FML layout &iles 'an be a'hie!e" through Ca!a 'o"e. *or e;ample, you 'oul" use set&FpefacePQ to ha!e a button ren"er its te;t in bol", instea" o& using a property in an FML layout. %in'e FML layouts are yet another &ile &or you to keep tra'k o&, =e nee" goo" reasons &or using su'h &iles. #erhaps the biggest reason is to assist in the 'reation o& tools &or !ie= "e&inition, su'h as a 8$0 buil"er in an 0@E like E'lipse or a "e"i'ate" An"roi" 8$0 "esigner like @roi"@ra=. %u'h 8$0 buil"ers 'oul", in prin'iple, generate Ca!a 'o"e instea" o& FML. 5he 'hallenge is re-rea"ing the "e&inition in to support e"its S that is &ar simpler i& the "ata is in a stru'ture" &ormat like FML than in a programming language. Moreo!er, keeping the generate" bits separate" out &rom han"-=ritten 'o"e makes it less likely that somebo"y7s 'ustom-'ra&te" sour'e =ill get 'lobbere" by a''i"ent =hen the generate" bits get re-generate". FML &orms a ni'e mi""le groun" bet=een something that is easy &or tool-=riters to use an" easy &or programmers to =ork =ith by han" as nee"e". Also, FML as a 8$0 "e&inition &ormat is be'oming more 'ommonpla'e. Mi'roso&t7s FAML, A"obe7s *le;, 8oogle7s 8W5, an" MoKilla7s F$L all take a similar approa'h to that o& An"roi", put layout "etails in an FML &ile an" put programming smarts in sour'e &iles (e.g., Ca!as'ript &or F$L). Many less-=ell-kno=n 8$0 &rame=orks, su'h as QD, also use FML &or !ie= "e&inition. While M&ollo=ing the her"M is not ne'essarily the best poli'y, it "oes ha!e the a"!antage o& helping to ease the transition into An"roi" &rom any other FML-'entere" !ie= "es'ription language.

7&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing E+!#Based !ayouts

,9@ So What /oes t !ook !ikeF


+ere is the 4utton &rom the pre!ious 'hapter7s sample appli'ation, 'on!erte" into an FML layout &ile, &oun" in the )aFouts/%oE?eduG sample proGe't,
LNGml version671.-7 encoding67utf-,7NM L4utton Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/button7 android:teGt677 android:laFout Eidth67fill parent7 android:laFout height67fill parent7/M

5he 'lass name o& the =i"get S 4utton S &orms the name o& the FML element. %in'e 4utton is an An"roi"-supplie" =i"get, =e 'an Gust use the bare 'lass name. 0& you 'reate your o=n =i"gets as sub'lasses o& android.vieE.VieE, you =oul" nee" to pro!i"e a &ull pa'kage "e'laration as =ell (e.g., com.commonsEare.android.#F@idget). 5he root element nee"s to "e'lare the An"roi" FML namespa'e,
Gmlns:android67http://schemas.android.com/apk/res/android7

All other elements =ill be 'hil"ren o& the root an" =ill inherit that namespa'e "e'laration. 1e'ause =e =ant to re&eren'e this button &rom our Ca!a 'o"e, =e nee" to gi!e it an i"enti&ier !ia the android:id attribute. We =ill 'o!er this 'on'ept in greater "etail later in this 'hapter. 5he remaining attributes are properties o& this 4utton instan'e,

in"i'ates the initial te;t to be "isplaye" on the button &a'e (in this 'ase, an empty string)
android:teGt android:laFout Eidth an" android:laFout height

tell An"roi" to ha!e the button7s =i"th an" height &ill the MparentM, in this 'ase the entire s'reen S these attributes =ill be 'o!ere" in greater "etail in a later 'hapter

7-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing E+!#Based !ayouts

%in'e this single =i"get is the only 'ontent in our a'ti!ity7s !ie=, =e only nee" this single element. Comple; !ie=s =ill reRuire a =hole tree o& elements, representing the =i"gets an" 'ontainers that 'ontrol their positioning. All the remaining 'hapters o& this book =ill use the FML layout &orm =hene!er pra'ti'al, so there are "oKens o& other e;amples o& more 'omple; layouts &or you to peruse.

WhatGs With the H SignsF


Many =i"gets an" 'ontainers only nee" to appear in the FML layout &ile an" "o not nee" to be re&eren'e" in your Ca!a 'o"e. *or e;ample, a stati' label (&eGtVieE) &reRuently only nee"s to be in the layout &ile to in"i'ate =here it shoul" appear. 5hese sorts o& elements in the FML &ile "o not nee" to ha!e the android:id attribute to gi!e them a name. Anything you do =ant to use in your Ca!a sour'e, though, nee"s an android:id. 5he 'on!ention is to use ORid/... as the id !alue, =here the ... represents your lo'ally-uniRue name &or the =i"get in Ruestion, &or the &irst o''urren'e o& a gi!en id !alue in your layout &ile. 5he se'on" an" subseRuent o''urren'es in the same layout &ile shoul" "rop the R sign S a &eature =e =ill use in an up'oming 'hapter. 0n the FML layout e;ample in the pre'e"ing se'tion, ORid/button is the i"enti&ier &or the 4utton =i"get. An"roi" pro!i"es a &e= spe'ial android:id !alues, o& the &orm Oandroid:id/... S =e =ill see some o& these in !arious 'hapters o& this book.

And We Attach These to the 6ava1113o)F


8i!en that you ha!e painstakingly set up the =i"gets an" 'ontainers &or your !ie= in an FML layout &ile name" main.Gml store" in res/laFout, all you nee" is one statement in your a'ti!ity7s on+reatePQ 'allba'k to use that layout,
setContentViewP?.laFout.mainQJ 7%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing E+!#Based !ayouts

5his is the same set+ontentVieEPQ =e use" earlier, passing it an instan'e o& a VieE sub'lass (in that 'ase, a 4utton). 5he An"roi"-built VieE, 'onstru'te" &rom our layout, is a''esse" &rom that 'o"e-generate" ? 'lass. All o& the layouts are a''essible un"er ?.laFout, keye" by the base name o& the layout &ile S res/laFout/main.Gml results in ?.laFout.main. 5o a''ess our i"enti&ie" =i"gets, use findVieE4FIdPQ, passing it the numeri' i"enti&ier o& the =i"get in Ruestion. 5hat numeri' i"enti&ier =as generate" by An"roi" in the ? 'lass as ?.id.something (=here something is the spe'i&i' =i"get you are seeking). 5hose =i"gets are simply sub'lasses o& VieE, Gust like the 4utton instan'e =e 'reate" in the pre!ious 'hapter.

The Cest of the Story


0n the original %oE "emo, the button7s &a'e =oul" sho= the 'urrent time, =hi'h =oul" re&le't =hen the button =as last pushe" (or =hen the a'ti!ity =as &irst sho=n, i& the button ha" not yet been pushe"). Most o& that logi' still =orks, e!en in this re!ise" "emo ( %oE?eduG). +o=e!er, rather than instantiating the 4utton in our a'ti!ity7s on+reatePQ 'allba'k, =e 'an re&eren'e the one &rom the FML layout,
package com.commonsEare.android.laFoutsJ import import import import import android.app.ActivitFJ android.os.4undleJ android.vieE.VieEJ android.Eidget.4uttonJ java.util.=ateJ

public class %oE?eduG eGtends ActivitF implements VieE."n+lick)istener : 4utton btnJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ btn6P4uttonQfindViewByIdP?.id.buttonQJ btn.setOnClickListenerPthisQJ updateTimePQJ

70

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing E+!#Based !ayouts

; public void onClickPVieE vieEQ : updateTimePQJ ; private void updateTimePQ : btn.setTextPneE DatePQ.toStringPQQJ ; ;

5he &irst "i&&eren'e is that rather than setting the 'ontent !ie= to be a !ie= =e 'reate" in Ca!a 'o"e, =e set it to re&eren'e the FML layout (set+ontentVieEP?.laFout.mainQ). 5he ?.java sour'e &ile =ill be up"ate" =hen =e rebuil" this proGe't to in'lu"e a re&eren'e to our layout &ile (store" as main.Gml in our proGe't7s res/laFout "ire'tory). 5he other "i&&eren'e is that =e nee" to get our han"s on our 4utton instan'e, &or =hi'h =e use the findVieE4FIdPQ 'all. %in'e =e i"enti&ie" our button as ORid/button, =e 'an re&eren'e the button7s i"enti&ier as ?.id.button. 2o=, =ith the 4utton instan'e in han", =e 'an set the 'allba'k an" set the label as nee"e". 5he results look the same as =ith the original %oE "emo,

72

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing E+!#Based !ayouts

"igure --1 The ?o)Cedux sample activity

77

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER ;

=mploying Basic Widgets

E!ery 8$0 toolkit has some basi' =i"gets, &iel"s, labels, buttons, et'. An"roi"7s toolkit is no "i&&erent in s'ope, an" the basi' =i"gets =ill pro!i"e a goo" intro"u'tion as to ho= =i"gets =ork in An"roi" a'ti!ities.

Assigning !abels
5he simplest =i"get is the label, re&erre" to in An"roi" as a &eGtVieE. Like in most 8$0 toolkits, labels are bits o& te;t not e"itable "ire'tly by users. 5ypi'ally, they are use" to i"enti&y a"Ga'ent =i"gets (e.g., a M2ame,M label be&ore a &iel" =here one &ills in a name). 0n Ca!a, you 'an 'reate a label by 'reating a &eGtVieE instan'e. More 'ommonly, though, you =ill 'reate labels in FML layout &iles by a""ing a &eGtVieE element to the layout, =ith an android:teGt property to set the !alue o& the label itsel&. 0& you nee" to s=ap labels base" on 'ertain 'riteria, su'h as internationaliKation, you may =ish to use a string resour'e re&eren'e in the FML instea", as =ill be "es'ribe" later in this book.
&eGtVieE

has numerous other properties o& rele!an'e &or labels, su'h as, to set the type&a'e to use &or the label (e.g., be ma"e bol"

android:tFpeface monospace)

android:teGt2tFle to in"i'ate that the type&a'e shoul" (bold), itali' (italic), or bol" an" itali' (bold italic)

7:
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

android:teGt+olor to set the &ormat (e.g., S99---- &or re")

'olor o& the label7s te;t, in

81 he;

*or e;ample, in the 4asic/)abel proGe't, you =ill &in" the &ollo=ing layout &ile,
LNGml version671.-7 encoding67utf-,7NM L&eGtVieE Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:teGt675ou Eere eGpecting something profoundN7 /M

Cust that layout alone, =ith the stub Ca!a sour'e pro!i"e" by An"roi"7s proGe't buil"er (e.g., android create project), gi!es you,

"igure -%1 The !abel/emo sample application

Button@ Button@ WhoGs (ot the ButtonF


We7!e alrea"y seen the use o& the 4utton =i"get in the pre!ious t=o 'hapters. As it turns out, 4utton is a sub'lass o& &eGtVieE, so e!erything

8<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

"is'usse" in the pre'e"ing se'tion in terms o& &ormatting the &a'e o& the button still hol"s. +o=e!er, An"roi" 1./ a""e" a ne= &eature &or the "e'laration o& the Mon'li'kM listener &or a 4utton. 0n a""ition to the 'lassi' approa'h o& "e&ining some obGe't (su'h as the a'ti!ity) as implementing the VieE."n+lick)istener inter&a'e, you 'an no= take a some=hat simpler approa'h,

@e&ine some metho" on your ActivitF that hol"s the button that takes a single VieE parameter, has a void return !alue, an" is public 0n your layout FML, on the 4utton element, in'lu"e the android:on+lick attribute =ith the name o& the metho" you "e&ine" in the pre!ious step

*or e;ample, =e might ha!e a metho" on our ActivitF that looks like,
public void someMethodPVieE the4uttonQ : // do something useful here ;

5hen, =e 'oul" use this FML "e'laration &or the 4utton itsel&, in'lu"ing android:on+lick,
L4utton android:on+lick67some#ethod7 ... /M

5his is enough &or An"roi" to M=ire togetherM the 4utton =ith the 'li'k han"ler.

"leeting mages
An"roi" has t=o =i"gets to help you embe" images in your a'ti!ities, ImageVieE an" Image4utton. As the names suggest, they are image-base" analogues to &eGtVieE an" 4utton, respe'ti!ely.

8*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

Ea'h =i"get takes an android:src attribute (in an FML layout) to spe'i&y =hat pi'ture to use. 5hese usually re&eren'e a "ra=able resour'e, "es'ribe" in greater "etail in the 'hapter on resour'es.
Image4utton, a sub'lass o& ImageVieE, mi;es in the stan"ar" 4utton beha!iors, &or respon"ing to 'li'ks an" =hatnot.

*or e;ample, take a peek at the main.Gml layout &rom the 4asic/ImageVieE sample proGe't,
LNGml version671.-7 encoding67utf-,7NM LImageVieE Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/icon7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:adjustVieE4ounds67true7 android:src67OdraEable/molecule7 /M

5he result, Gust using the 'o"e-generate" a'ti!ity, is simply the image,

"igure -01 The mage;ie)/emo sample application

8&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

"ields of (reen1 ,r ,ther Colors1


Along =ith buttons an" labels, &iel"s are the thir" Man'horM o& most 8$0 toolkits. 0n An"roi", they are implemente" !ia the $dit&eGt =i"get, =hi'h is a sub'lass o& the &eGtVieE use" &or labels. Along =ith the stan"ar" &eGtVieE properties (e.g., android:teGt2tFle), $dit&eGt has many others that =ill be use&ul &or you in 'onstru'ting &iel"s, in'lu"ing,
android:auto&eGt,

to 'ontrol i& the &iel" shoul" pro!i"e automati' spelling assistan'e


android:capitaliKe,

to 'ontrol i& the &iel" shoul" automati'ally 'apitaliKe the &irst letter o& entere" te;t (e.g., &irst name, 'ity)
android:digits, to 'on&igure

the &iel" to a''ept only 'ertain "igits

android:single)ine, to 'ontrol i& the &iel" is &or single-line input or multiple-line input (e.g., "oes NEnterO mo!e you to the ne;t =i"get or a"" a ne=lineH)

Most o& those are also a!ailable &rom the ne= android:input&Fpe attribute, a""e" in An"roi" 1.A as part o& a""ing Mso&t keyboar"sM to An"roi" S this =ill be "is'usse" in an up'oming 'hapter. *or e;ample, &rom the 4asic/9ield proGe't, here is an FML layout &ile sho=ing an $dit&eGt,
LNGml version671.-7 encoding67utf-,7NM L$dit&eGt Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/field7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:single)ine67false7 /M

2ote that android:single)ine is &alse, so users =ill be able to enter in se!eral lines o& te;t.

8-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

*or this proGe't, the 9ield=emo.java &ile populates the input &iel" =ith some prose,
package com.commonsEare.android.fieldJ import android.app.ActivitFJ import android.os.4undleJ import android.Eidget.$dit&eGtJ public class 9ield=emo eGtends ActivitF : O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ $dit&eGt fld6P$dit&eGtQfindViewByIdP?.id.fieldQJ fld.setTextP7)icensed under the Apache )icense8 Version >.- 7 R 7Pthe T7)icenseT7QJ Fou maF not use this file 7 R 7eGcept in compliance Eith the )icense. 5ou maF 7 R 7obtain a copF of the )icense at 7 R 7http://EEE.apache.org/licenses/)I+$%2$->.-7QJ ; ;

5he result, on'e built an" installe" into the emulator, is,

"igure -21 The "ield/emo sample application

8%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

Another &la!or o& &iel" is one that o&&ers auto-'ompletion, to help users supply a !alue =ithout typing in the =hole te;t. 5hat is pro!i"e" in An"roi" as the Auto+omplete&eGtVieE =i"get, "is'usse" in greater "etail later in this book.

6ust Another Box to Check


5he 'lassi' 'he'kbo; has t=o states, 'he'ke" an" un'he'ke". Cli'king the 'he'kbo; toggles bet=een those states to in"i'ate a 'hoi'e (e.g., MA"" rush "eli!ery to my or"erM). 0n An"roi", there is a +heck4oG =i"get to meet this nee". 0t has &eGtVieE as an an'estor, so you 'an use &eGtVieE properties like android:teGt+olor to &ormat the =i"get. Within Ca!a, you 'an in!oke,
is+heckedPQ to "etermine set+heckedPQ

i& the 'he'kbo; has been 'he'ke"

to &or'e the 'he'kbo; into a 'he'ke" or un'he'ke" the 'he'kbo; as i& the user 'he'ke" it

state
togglePQ to toggle

Also, you 'an register a listener obGe't (in this 'ase, an instan'e o& "n+hecked+hange)istener) to be noti&ie" =hen the state o& the 'he'kbo; 'hanges. *or e;ample, &rom the 4asic/+heck4oG proGe't, here is a simple 'he'kbo; layout,
LNGml version671.-7 encoding67utf-,7NM L+heck4oG Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/check7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGt67&his checkboG is: unchecked7 /M

80

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

5he 'orrespon"ing +heck4oG=emo.java retrie!es an" 'on&igures the beha!ior o& the 'he'kbo;,
public class +heck4oG=emo eGtends ActivitF implements +ompound4utton."n+hecked+hange)istener : +heck4oG cbJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ cb6P+heck4oGQfindViewByIdP?.id.checkQJ cb.setOnCheckedChangeListenerPthisQJ

public void onCheckedChangedP+ompound4utton buttonVieE8 boolean is+heckedQ : if Pis+heckedQ : cb.setTextP7&his checkboG is: checked7QJ ; else : cb.setTextP7&his checkboG is: unchecked7QJ ; ; ;

2ote that the a'ti!ity ser!es as its o=n listener &or 'he'kbo; state 'hanges sin'e it implements the "n+hecked+hange)istener inter&a'e (!ia cb.set"n+hecked+hange)istenerPthisQ). 5he 'allba'k &or the listener is on+hecked+hangedPQ, =hi'h re'ei!es the 'he'kbo; =hose state has 'hange" an" =hat the ne= state is. 0n this 'ase, =e up"ate the te;t o& the 'he'kbo; to re&le't =hat the a'tual bo; 'ontains. 5he resultH Cli'king the 'he'kbo; imme"iately up"ates its te;t, as sho=n belo=,

82

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

"igure -71 The CheckBox/emo sample application@ )ith the checkbox unchecked

"igure -81 The same application@ no) )ith the checkbox checked

87

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

Turn the Cadio >p


As =ith other implementations o& ra"io buttons in other toolkits, An"roi"7s ra"io buttons are t=o-state, like 'he'kbo;es, but 'an be groupe" su'h that only one ra"io button in the group 'an be 'he'ke" at any time. Like +heck4oG, ?adio4utton inherits &rom +ompound4utton, =hi'h in turn inherits &rom &eGtVieE. +en'e, all the stan"ar" &eGtVieE properties &or &ont &a'e, style, 'olor, et'. are a!ailable &or 'ontrolling the look o& ra"io buttons. %imilarly, you 'an 'all is+heckedPQ on a ?adio4utton to see i& it is sele'te", togglePQ to sele't it, an" so on, like you 'an =ith a +heck4oG. Most times, you =ill =ant to put your ?adio4utton =i"gets insi"e o& a ?adioDroup. 5he ?adioDroup in"i'ates a set o& ra"io buttons =hose state is tie", meaning only one button out o& the group 'an be sele'te" at any time. 0& you assign an android:id to your ?adioDroup in your FML layout, you 'an a''ess the group &rom your Ca!a 'o"e an" in!oke,
checkPQ to 'he'k a spe'i&i' group.checkP?.id.radio1Q) clear+heckPQ

ra"io button !ia its 0@ (e.g.,

to 'lear all ra"io buttons, so none in the group are o& the 'urrently-'he'ke"

'he'ke"
get+hecked?adio4uttonIdPQ to get the 0@ ra"io button (or -1 i& none are 'he'ke")

2ote that the mutual-e;'lusion &eature o& ?adioDroup only applies to ?adio4utton =i"gets that are imme"iate 'hil"ren o& the ?adioDroup. ?ou 'annot ha!e other 'ontainers S "is'usse" in the ne;t 'hapter S bet=een the ?adioDroup an" its ?adio4utton =i"gets. *or e;ample, &rom the 4asic/?adio4utton sample appli'ation, here is an FML layout sho=ing a ?adioDroup =rapping a set o& ?adio4utton =i"gets,
LNGml version671.-7 encoding67utf-,7NM L?adioDroup Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 88

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

android:laFout height67fill parent7 M L?adio4utton android:id67ORid/radio17 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGt67?ock7 /M L?adio4utton android:id67ORid/radio>7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGt672cissors7 /M L?adio4utton android:id67ORid/radioC7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGt67(aper7 /M L/?adioDroupM

$sing the sto'k An"roi"-generate" Ca!a &or the proGe't an" this layout, you get,

"igure -:1 The CadioButton/emo sample application

2ote that the ra"io button group is initially set to be 'ompletely un'he'ke" at the outset. 5o preset one o& the ra"io buttons to be 'he'ke", use either set+heckedPQ on the ?adio4utton or checkPQ on the ?adioDroup &rom =ithin your on+reatePQ 'allba'k in your a'ti!ity.
8:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

tGs Iuite a ;ie)


All =i"gets, in'lu"ing the ones sho=n abo!e, e;ten" VieE, an" as su'h gi!e all =i"gets an array o& use&ul properties an" metho"s beyon" those alrea"y "es'ribe".

P ddin!
Wi"gets ha!e a minimum siKe, one that may be in&luen'e" by =hat is insi"e o& them. %o, &or e;ample, a 4utton =ill e;pan" to a''ommo"ate the siKe o& its 'aption. ?ou 'an 'ontrol this siKe using pa""ing. A""ing pa""ing =ill in'rease the spa'e bet=een the 'ontents (e.g., the 'aption o& a 4utton) an" the e"ges o& the =i"get. #a""ing 'an be set on'e in FML &or all &our si"es ( android:padding) or on a per-si"e basis (android:padding)eft, et'.). #a""ing 'an also be set in Ca!a !ia the set(addingPQ metho". 5he !alue o& any o& these is a "imension S a 'ombination o& a unit o& measure an" a 'ount. %o, .pG is A pi;els, 1-dip is 10 "ensity-in"epen"ent pi;els, or >mm is 2 millimeters. We =ill e;amine "imension in greater "etail in an up'oming 'hapter.

+ther -se.ul Properties


0n a""ition to those presente" in this 'hapter an" in the ne;t 'hapter, some o& the properties on VieE most likely to be use" in'lu"e,
android:visibilitF,

!isible

=hi'h 'ontrols =hether the =i"get is initially


android:neGt9ocus)eft, android:neGt9ocus3p, =hi'h 'ontrol the

android:neGt9ocus=oEn, android:neGt9ocus?ight,

an" &o'us or"er i& the user uses the @-pa", tra'kball, or similar pointing "e!i'e

:<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

android:content=escription, =hi'h is roughly eRui!alent to the alt attribute on an +5ML LimgM tag, an" is use" by a''essibility tools to

help people =ho 'annot see the s'reen na!igate the appli'ation

-se.ul %ethods
?ou 'an toggle =hether or not a =i"get is enable" !ia set$nabledPQ an" see i& it is enable" !ia is$nabledPQ. >ne 'ommon use pattern &or this is to "isable some =i"gets base" on a +heck4oG or ?adio4utton sele'tion. ?ou 'an gi!e a =i"get &o'us !ia reUuest9ocusPQ an" see i& it is &o'use" !ia is9ocusedPQ. ?ou might use this in 'on'ert =ith "isabling =i"gets as mentione" abo!e, to ensure the proper =i"get has the &o'us on'e your "isabling operation is 'omplete. 5o help na!igate the tree o& =i"gets an" 'ontainers that make up an a'ti!ity7s o!erall !ie=, you 'an use,
get(arentPQ to findVieE4FIdPQ get?ootVieEPQ

&in" the parent =i"get or 'ontainer to &in" a 'hil" =i"get =ith a 'ertain 0@

to get the root o& the tree (e.g., =hat you pro!i"e" to the a'ti!ity !ia set+ontentVieEPQ)

Colors
5here are t=o types o& 'olor attributes in An"roi" =i"gets. %ome, like take a single 'olor (or a graphi' image to ser!e as the ba'kgroun"). >thers, like android:teGt+olor on &eGtVieE (an" sub'lasses) 'an take a +olor2tate)ist, in'lu"ing !ia the Ca!a setter (in this 'ase, set&eGt+olorPQ).
android:background,

A +olor2tate)ist allo=s you to spe'i&y "i&&erent 'olors &or "i&&erent 'on"itions. *or e;ample, =hen you get to sele'tion =i"gets in an up'oming 'hapter, you =ill see ho= a &eGtVieE has a "i&&erent te;t 'olor =hen it is the sele'te" item in a list 'ompare" to =hen it is in the list but not sele'te". 5his is han"le" !ia the "e&ault +olor2tate)ist asso'iate" =ith &eGtVieE.
:*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mploying Basic Widgets

0& you =ish to 'hange the 'olor o& a &eGtVieE =i"get in Ca!a 'o"e, you ha!e t=o main 'hoi'es, 1. $se +olor2tate)ist.value"fPQ, =hi'h returns a +olor2tate)ist in =hi'h all states are 'onsi"ere" to ha!e the same 'olor, =hi'h you supply as the parameter to the value"fPQ metho". 5his is the Ca!a eRui!alent o& the android:teGt+olor approa'h, to make the &eGtVieE al=ays a spe'i&i' 'olor regar"less o& 'ir'umstan'es.

2. Create a +olor2tate)ist =ith "i&&erent !alues &or "i&&erent states, either !ia the 'onstru'tor or !ia an FML "ra=able resour'e, a 'on'ept "is'usse" in a later 'hapter

:&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1<

Working )ith Containers

Containers pour a 'olle'tion o& =i"gets (an" possibly 'hil" 'ontainers) into spe'i&i' stru'tures you like. 0& you =ant a &orm =ith labels on the le&t an" &iel"s on the right, you =ill nee" a 'ontainer. 0& you =ant >D an" Can'el buttons to be beneath the rest o& the &orm, ne;t to one another, an" &lush to right si"e o& the s'reen, you =ill nee" a 'ontainer. Cust &rom a pure FML perspe'ti!e, i& you ha!e multiple =i"gets (beyon" ?adio4utton =i"gets in a ?adioDroup), you =ill nee" a 'ontainer Gust to ha!e a root element to pla'e the =i"gets insi"e. Most 8$0 toolkits ha!e some notion o& layout management, &reRuently organiKe" into 'ontainers. 0n Ca!aP%=ing, &or e;ample, you ha!e layout managers like 4oG)aFout an" 'ontainers that use them (e.g., 4oG). %ome toolkits sti'k stri'tly to the bo; mo"el, su'h as F$L an" *le;, &iguring that any "esire" layout 'an be a'hie!e" through the right 'ombination o& neste" bo;es. An"roi", through )inear)aFout, also o&&ers a Mbo;M mo"el, but in a""ition supports a range o& 'ontainers pro!i"ing "i&&erent layout rules. 0n this 'hapter, =e =ill look at three 'ommonly-use" 'ontainers, )inear)aFout (the bo; mo"el), ?elative)aFout (a rule-base" mo"el), an" &able)aFout (the gri" mo"el), along =ith 2crollVieE, a 'ontainer "esigne" to assist =ith implementing s'rolling 'ontainers.

:Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

Thinking !inearly
As note" abo!e, )inear)aFout is a bo; mo"el S =i"gets or 'hil" 'ontainers are line" up in a 'olumn or ro=, one a&ter the ne;t. 5his =orks similarly to 9loE)aFout in Ca!aP%=ing, vboG an" hboG in *le; an" F$L, et'. *le; an" F$L use the bo; as their primary unit o& layout. 0& you =ant, you 'an use )inear)aFout in mu'h the same =ay, es'he=ing some o& the other 'ontainers. 8etting the !isual representation you =ant is mostly a matter o& i"enti&ying =here bo;es shoul" nest an" =hat properties those bo;es shoul" ha!e, su'h as alignment vis--vis other bo;es.

Concepts nd Properties
5o 'on&igure a )inear)aFout, you ha!e &i!e main areas o& 'ontrol besi"es the 'ontainer7s 'ontents, the orientation, the &ill mo"el, the =eight, the gra!ity, an" the pa""ing.

+rient tion
>rientation in"i'ates =hether the )inear)aFout represents a ro= or a 'olumn. Cust a"" the android:orientation property to your )inear)aFout element in your FML layout, setting the !alue to be horiKontal &or a ro= or vertical &or a 'olumn. 5he orientation 'an be mo"i&ie" at runtime by in!oking set"rientationPQ on the )inear)aFout, supplying it either !"?IV"%&A) or V$?&I+A).

5ill %odel
Let7s imagine a ro= o& =i"gets, su'h as a pair o& ra"io buttons. 5hese =i"gets ha!e a MnaturalM siKe base" on their te;t. 5heir 'ombine" siKes probably "o not e;a'tly mat'h the =i"th o& the An"roi" "e!i'e7s s'reen S parti'ularly sin'e s'reens 'ome in !arious siKes. We then ha!e the issue o& =hat to "o =ith the remaining spa'e.
:%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

All =i"gets insi"e a )inear)aFout must supply android:laFout Eidth an" android:laFout height properties to help a""ress this issue. 5hese properties7 !alues ha!e three &la!ors,

?ou 'an pro!i"e a spe'i&i' "imension, su'h as 1>.dip to in"i'ate the =i"get shoul" take up e;a'tly a 'ertain siKe ?ou 'an pro!i"e Erap content, =hi'h means the =i"get shoul" &ill up its natural spa'e, unless that is too big, in =hi'h 'ase An"roi" 'an use =or"-=rap as nee"e" to make it &it ?ou 'an pro!i"e fill parent, =hi'h means the =i"get shoul" &ill up all a!ailable spa'e in its en'losing 'ontainer, a&ter all other =i"gets are taken 'are o&

5he latter t=o &la!ors are the most 'ommon, as they are in"epen"ent o& s'reen siKe, allo=ing An"roi" to a"Gust your !ie= to &it the a!ailable spa'e. @BT*, 0n A#0 le!el 8 (An"roi" 2.2), fill parent =as rename" to match parent, &or unkno=n reasons. ?ou 'an still use fill parent, as it =ill be supporte" &or the &oreseeable &uture. +o=e!er, at su'h point in time as you are only supporting A#0 le!el 8 or higher (e.g., android:min2dkVersion67,7 in your mani&est), you shoul" probably s=it'h o!er to match parent.

,ei!ht
1ut, =hat happens i& =e ha!e t=o =i"gets that shoul" split the a!ailable &ree spa'eH *or e;ample, suppose =e ha!e t=o multi-line &iel"s in a 'olumn, an" =e =ant them to take up the remaining spa'e in the 'olumn a&ter all other =i"gets ha!e been allo'ate" their spa'e. 5o make this =ork, in a""ition to setting android:laFout Eidth (&or ro=s) or android:laFout height (&or 'olumns) to fill parent, you must also set android:laFout Eeight. 5his property in"i'ates =hat proportion o& the &ree spa'e shoul" go to that =i"get. 0& you set android:laFout Eeight to be the same non-Kero !alue &or a pair o& =i"gets (e.g., 1), the &ree spa'e =ill be split e!enly bet=een them. 0& you set it to be 1 &or one =i"get an" > &or
:0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

another =i"get, the se'on" =i"get =ill use up t=i'e the &ree spa'e that the &irst =i"get "oes. An" so on. 5he =eight &or a =i"get is Kero by "e&ault. Another pattern &or using =eights is i& you =ant to allo'ate siKes on a per'entage basis. 5o use this te'hniRue &or, say, a horiKontal layout,

%et all the android:laFout Eidth !alues to be - &or the =i"gets in the layout %et the android:laFout Eeight !alues to be the "esire" per'entage siKe &or ea'h =i"get in the layout Make sure all those =eights a"" up to 1--

Gr vity
1y "e&ault, e!erything in a )inear)aFout is le&t- an" top-aligne". %o, i& you 'reate a ro= o& =i"gets !ia a horiKontal )inear)aFout, the ro= =ill start &lush on the le&t si"e o& the s'reen. 0& that is not =hat you =ant, you nee" to spe'i&y a gra!ity. $sing android:laFout gravitF on a =i"get (or 'alling setDravitFPQ at runtime on the =i"get7s Ca!a obGe't), you 'an tell the =i"get an" its 'ontainer ho= to align it vis--vis the s'reen. *or o& =i"gets, 'ommon gra!ity !alues are left, center horiKontal, an" right &or le&t-aligne", 'entere", an" right-aligne" =i"gets respe'ti!ely. *or a ro= o& =i"gets, the "e&ault is &or them to be aligne" so their te;ts are aligne" on the baseline (the in!isible line that letters seem to Msit onM), though you may =ish to spe'i&y a gra!ity o& center vertical to 'enter the =i"gets along the ro=7s !erti'al mi"point. a 'olumn

:2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

% r!ins
1y "e&ault, =i"gets are tightly pa'ke", one ne;t to the other. ?ou 'an 'ontrol this !ia the use o& margins, a 'on'ept that is reminis'ent o& the pa""ing "es'ribe" in a pre!ious 'hapter. 5he "i&&eren'e bet=een pa""ing an" margins 'omes in terms o& the ba'kgroun". Wi"gets =ith a transparent ba'kgroun" S like the "e&ault look o& a &eGtVieE S pa""ing an" margins ha!e similar !isual e&&e't, in'reasing the spa'e bet=een the =i"get an" a"Ga'ent =i"gets. +o=e!er, =i"gets =ith a non-transparent ba'kgroun" S like a 4utton S pa""ing is 'onsi"ere" insi"e the ba'kgroun" =hile margins are outsi"e. 0n other =or"s, a""ing pa""ing =ill in'rease the spa'e bet=een the 'ontents (e.g., the 'aption o& a 4utton) an" the e"ges, =hile a""ing margin in'reases the empty spa'e bet=een the e"ges an" a"Ga'ent =i"gets. Margins 'an be set in FML, either on a per-si"e basis (e.g., android:laFout margin&op) or on all si"es !ia android:laFout margin. >n'e again, the !alue o& any o& these is a "imension S a 'ombination o& a unit o& measure an" a 'ount, su'h as .pG &or A pi;els.

E0 mple
Let7s look at an e;ample ( +ontainers/)inear) that sho=s )inear)aFout properties set both in the FML layout &ile an" at runtime. +ere is the layout,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L?adioDroup android:id67ORid/orientation7 android:orientation67horiKontal7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:padding67.dip7M

:7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

L?adio4utton android:id67ORid/horiKontal7 android:teGt67horiKontal7 /M L?adio4utton android:id67ORid/vertical7 android:teGt67vertical7 /M L/?adioDroupM L?adioDroup android:id67ORid/gravitF7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:padding67.dip7M L?adio4utton android:id67ORid/left7 android:teGt67left7 /M L?adio4utton android:id67ORid/center7 android:teGt67center7 /M L?adio4utton android:id67ORid/right7 android:teGt67right7 /M L/?adioDroupM L/)inear)aFoutM

2ote that =e ha!e a )inear)aFout =rapping t=o ?adioDroup sets. ?adioDroup is a sub'lass o& )inear)aFout, so our e;ample "emonstrates neste" bo;es as i& they =ere all )inear)aFout 'ontainers. 5he top ?adioDroup sets up a ro= (android:orientation 6 7horiKontal7) o& ?adio4utton =i"gets. 5he ?adioDroup has .dip o& pa""ing on all si"es, separating it &rom the other ?adioDroup, =here dip stan"s &or "ensityin"epen"ent pi;els (think o& them as or"inary pi;els &or no= S =e =ill get into the "istin'tion later in the book). 5he =i"th an" height are both set to Erap content, so the ra"io buttons =ill only take up the spa'e that they nee". 5he bottom ?adioDroup is a 'olumn (android:orientation 6 7vertical7) o& three ?adio4utton =i"gets. Again, =e ha!e .dip o& pa""ing on all si"es an" a MnaturalM height (android:laFout height 6 7Erap content7). +o=e!er, =e ha!e set android:laFout Eidth to be fill parent, meaning the 'olumn o& ra"io buttons M'laimsM the entire =i"th o& the s'reen. 5o a"Gust these settings at runtime base" on user input, =e nee" some Ca!a 'o"e,
:8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

package com.commonsEare.android.linearJ import import import import import import import android.app.ActivitFJ android.os.4undleJ android.vieE.DravitFJ android.teGt.&eGt@atcherJ android.Eidget.)inear)aFoutJ android.Eidget.?adioDroupJ android.Eidget.$dit&eGtJ )inear)aFout=emo eGtends ActivitF ?adioDroup."n+hecked+hange)istener : orientationJ gravitFJ

public class implements ?adioDroup ?adioDroup

O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ orientation6P?adioDroupQfindViewByIdP?.id.orientationQJ orientation.setOnCheckedChangeListenerPthisQJ gravitF6P?adioDroupQfindViewByIdP?.id.gravitFQJ gravitF.setOnCheckedChangeListenerPthisQJ

public void onCheckedChangedP?adioDroup group8 int checkedIdQ : sEitch PcheckedIdQ : case ?.id.horiKontal: orientation.setOrientationP)inear)aFout.!"?IV"%&A)QJ breakJ case ?.id.vertical: orientation.setOrientationP)inear)aFout.V$?&I+A)QJ breakJ case ?.id.left: gravitF.set ra!ityPDravitF.)$9&QJ breakJ case ?.id.center: gravitF.set ra!ityPDravitF.+$%&$? !"?IV"%&A)QJ breakJ case ?.id.right: gravitF.set ra!ityPDravitF.?ID!&QJ breakJ ; ; ;

0n on+reatePQ, =e look up our t=o ?adioDroup 'ontainers an" register a listener on ea'h, so =e are noti&ie" =hen the ra"io buttons 'hange state
::

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

(set"n+hecked+hange)istenerPthisQ). %in'e the a'ti!ity "n+hecked+hange)istener, the a'ti!ity itsel& is the listener.

implements

0n on+hecked+hangedPQ (the 'allba'k &or the listener), =e see =hi'h ?adio4utton ha" a state 'hange. 1ase" on the 'li'ke"-upon item, =e a"Gust either the orientation o& the &irst )inear)aFout or the gra!ity o& the se'on" )inear)aFout. +ere is the result =hen it is &irst laun'he" insi"e the emulator,

"igure %<1 The !inear!ayout/emo sample application@ as initially launched

0& =e toggle on the M!erti'alM ra"io button, the top ?adioDroup a"Gusts to mat'h,

*<<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

"igure %*1 The same application@ )ith the vertical radio button selected

0& =e toggle the M'enterM or MrightM ra"io buttons, the bottom ?adioDroup a"Gusts to mat'h,

"igure %&1 The same application@ )ith the vertical and center radio buttons selected *<*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

"igure %-1 The same application@ )ith the vertical and right radio buttons selected

The Bo0 %odel


As note" earlier in this 'hapter, some 8$0 &rame=orks treat e!erything as bo;es S =hat An"roi" 'alls )inear)aFout 'ontainers. 0n *le; an" F$L, &or e;ample, you 'reate bo;es an" in"i'ate ho= big they shoul" be, as a per'entage o& the a!ailable spa'e, then you put =i"gets in the bo;es. A similar pattern e;ists in An"roi" &or )inear)aFout, as is "emonstrate" in the +ontainersT)inear(ercent proGe't. +ere, =e ha!e a layout FML &ile that 'ontains a !erti'al )inear)aFout =rapping three 4utton =i"gets,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L4utton android:teGt679iftF (ercent7 android:laFout Eidth67fill parent7 *<&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

/M L4utton android:teGt67&hirtF (ercent7 android:laFout Eidth67fill parent7 android:laFout height67-dip7 android:laFout Eeight67C-7 /M L4utton android:teGt67&EentF (ercent7 android:laFout Eidth67fill parent7 android:laFout height67-dip7 android:laFout Eeight67>-7 /M L/)inear)aFoutM

android:laFout height67-dip7 android:laFout Eeight67.-7

Ea'h o& the three =i"gets =ill take up a 'ertain per'entage o& the !erti'al spa'e &or the )inear)aFout. %in'e the )inear)aFout is set to &ill the s'reen, this means that the three =i"gets =ill "i!i"e up the s'reen base" upon their reRueste" per'entages. 5o reRuest a per'entage, ea'h 4utton,

%ets its android:laFout height to be -dip (note, =e use height here be'ause it is a !erti'al )inear)aFout =e are sub-"i!i"ing) %ets its android:laFout Eeight to be the "esire" per'entage (e.g., android:laFout Eeight67.-7)

%o long as the =eights sum to 1--, as they "o in this 'ase, you =ill get your "esire" break"o=n by per'entage,

*<-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

"igure %%1 A !inear!ayout split among three Buttons by percentage

All Things Are Celative


?elative)aFout, as the name suggests, lays out =i"gets base" upon their relationship to other =i"gets in the 'ontainer an" the parent 'ontainer. ?ou 'an pla'e Wi"get F belo= an" to the le&t o& Wi"get ?, or ha!e Wi"get Q7s bottom e"ge align =ith the bottom o& the 'ontainer, an" so on.

5his is reminis'ent o& Cames Elliot7s elati!eLayout &or use =ith Ca!aP%=ing.

Concepts nd Properties
5o make all this =ork, =e nee" =ays to re&eren'e other =i"gets =ithin an FML layout &ile, plus =ays to in"i'ate the relati!e positions o& those =i"gets.

*<%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

Positions Rel tive to Cont iner


5he easiest relations to set up are tying a =i"get7s position to that o& its 'ontainer,
android:laFout align(arent&op

says the =i"get7s top shoul" align

=ith the top o& the 'ontainer

says the =i"get7s bottom shoul" align =ith the bottom o& the 'ontainer
android:laFout align(arent4ottom

says the =i"get7s le&t si"e shoul" align =ith the le&t si"e o& the 'ontainer
android:laFout align(arent)eft

says the =i"get7s right si"e shoul" align =ith the right si"e o& the 'ontainer
android:laFout align(arent?ight android:laFout center!oriKontal says the =i"get positione" horiKontally at the 'enter o& the 'ontainer android:laFout centerVertical android:laFout centerIn(arent

shoul"

be

says the =i"get shoul" be positione" !erti'ally at the 'enter o& the 'ontainer says the =i"get shoul" be positione" both horiKontally an" !erti'ally at the 'enter o& the 'ontainer

All o& these properties take a simple boolean !alue (true or false). 2ote that the pa""ing o& the =i"get is taken into a''ount =hen per&orming these !arious alignments. 5he alignments are base" on the =i"get7s o!erall 'ell ('ombination o& its natural spa'e plus the pa""ing).

Rel tive "ot tion in Properties


5he remaining properties o& rele!an'e to ?elative)aFout take as a !alue the i"entity o& a =i"get in the 'ontainer. 5o "o this, 1. 2. #ut i"enti&iers (android:id attributes) on all elements that you =ill nee" to a""ress e&eren'e other =i"gets using the same i"enti&ier !alue

*<0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

5he &irst o''urren'e o& an id !alue shoul" ha!e the plus sign (ORid/Eidget a)T the se'on" an" subseRuent times that id !alue is use" in the layout &ile shoul" "rop the plus sign ( Oid/Eidget a). 5his allo=s the buil" tools to better help you 'at'h typos in your =i"get id !alues S i& you "o not ha!e a plus sign &or a =i"get id !alue that has not been seen be&ore, that =ill be 'aught at 'ompile time. *or e;ample, i& Wi"get A is i"enti&ie" as ORid/Eidget a, Wi"get 1 'an re&er to Wi"get A in one o& its o=n properties !ia the i"enti&ier Oid/Eidget a.

Positions Rel tive to +ther ,id!ets


5here are &our properties that 'ontrol position o& a =i"get !is a !is other =i"gets,

in"i'ates that the =i"get shoul" be pla'e" abo!e the =i"get re&eren'e" in the property
android:laFout above android:laFout beloE

in"i'ates that the =i"get shoul" be pla'e" belo= the =i"get re&eren'e" in the property in"i'ates that the =i"get shoul" be pla'e" to the le&t o& the =i"get re&eren'e" in the property
android:laFout to)eft"f

in"i'ates that the =i"get shoul" be pla'e" to the right o& the =i"get re&eren'e" in the property
android:laFout to?ight"f

1eyon" those &our, there are &i!e a""itional properties that 'an 'ontrol one =i"get7s alignment relati!e to another,

in"i'ates that the =i"get7s top shoul" be aligne" =ith the top o& the =i"get re&eren'e" in the property
android:laFout align&op

in"i'ates that the =i"get7s bottom shoul" be aligne" =ith the bottom o& the =i"get re&eren'e" in the property
android:laFout align4ottom

in"i'ates that the =i"get7s le&t shoul" be aligne" =ith the le&t o& the =i"get re&eren'e" in the property
android:laFout align)eft

*<2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

android:laFout align?ight

in"i'ates that the =i"get7s right shoul" be aligne" =ith the right o& the =i"get re&eren'e" in the property in"i'ates that the baselines o& the t=o =i"gets shoul" be aligne" (=here the MbaselineM is that in!isible line that te;t appears to sit on)
android:laFout align4aseline

5he last one is use&ul &or aligning labels an" &iel"s so that the te;t appears MnaturalM. %in'e &iel"s ha!e a bo; aroun" them an" labels "o not, android:laFout align&op =oul" align the top o& the &iel"7s bo; =ith the top o& the label, =hi'h =ill 'ause the te;t o& the label to be higher on-s'reen than the te;t entere" into the &iel". %o, i& =e =ant Wi"get 1 to be positione" to the right o& Wi"get A, in the FML element &or Wi"get 1, =e nee" to in'lu"e android:laFout to?ight"f 6 7Oid/Eidget a7 (assuming Oid/Eidget a is the i"entity o& Wi"get A).

+rder o. Ev lu tion
0t use" to be that An"roi" =oul" use a single pass to pro'ess ?elative)aFout-"e&ine" rules. 5hat meant you 'oul" not re&eren'e a =i"get (e.g., !ia android:laFout above) until it ha" been "e'lare" in the FML. 5his ma"e "e&ining some layouts a bit 'ompli'ate". %tarting in An"roi" 1./, An"roi" uses t=o passes to pro'ess the rules, so you 'an no= sa&ely ha!e &or=ar" re&eren'es to as-yet-un"e&ine" =i"gets.

E0 mple
With all that in min", let7s e;amine a typi'al M&ormM =ith a &iel", a label, plus a pair o& buttons labele" M>DM an" MCan'elM. +ere is the FML layout, pulle" &rom the +ontainers/?elative sample proGe't,
LNGml version671.-7 encoding67utf-,7NM L?elative)aFout Gmlns:android67http://schemas.android.com/apk/res/android7

*<7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

android:laFout Eidth67fill parent7 android:laFout height67Erap content7M L&eGtVieE android:id67ORid/label7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGt673?):7 android:laFout align4aseline67ORid/entrF7 android:laFout align(arent)eft67true7/M L$dit&eGt android:id67Oid/entrF7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:laFout to?ight"f67Oid/label7 android:laFout align(arent&op67true7/M L4utton android:id67ORid/ok7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:laFout beloE67Oid/entrF7 android:laFout align?ight67Oid/entrF7 android:teGt67"H7 /M L4utton android:id67ORid/cancel7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:laFout to)eft"f67Oid/ok7 android:laFout align&op67Oid/ok7 android:teGt67+ancel7 /M L/?elative)aFoutM

*irst, =e open up the ?elative)aFout. 0n this 'ase, =e =ant to use the &ull =i"th o& the s'reen (android:laFout Eidth 6 7fill parent7) an" only as mu'h height as =e nee" (android:laFout height 6 7Erap content7). 2e;t, =e "e&ine the label as a &eGtVieE. We in"i'ate that =e =ant its le&t e"ge aligne" =ith the le&t e"ge o& the ?elative)aFout (android:laFout align(arent)eft67true7) an" that =e =ant its baseline aligne" =ith the baseline o& the yet-to-be-"e&ine" $dit&eGt. %in'e the $dit&eGt has not been "e'lare" yet, =e use the R sign in the 0@ (android:laFout align4aseline67ORid/entrF7). A&ter that, =e a"" in the &iel" as an $dit&eGt. We =ant the &iel" to be to the right o& the label, ha!e the &iel" be aligne" =ith the top o& the ?elative)aFout, an" &or the &iel" to take up the rest o& this Mro=M in the layout. 5hose are han"le" by three properties,
android:laFout to?ight"f 6 7Oid/label7
*<8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

android:laFout align(arent&op 6 7true7 android:laFout Eidth 6 7fill parent7

5hen, the >D button is set to be belo= the &iel" ( android:laFout beloE 6 7Oid/entrF7) an" ha!e its right si"e align =ith the right si"e o& the &iel" (android:laFout align?ight 6 7Oid/entrF7). 5he Can'el button is set to be to the le&t o& the >D button (android:laFout to)eft 6 7Oid/ok7) an" ha!e its top aligne" =ith the >D button (android:laFout align&op 6 7Oid/ok7). With no 'hanges to the auto-generate" Ca!a 'o"e, the emulator gi!es us,

"igure %01 The Celative!ayout/emo sample application

+verl p
?elative)aFout also has a &eature that )inear)aFout la'ks S the ability to ha!e =i"gets o!erlap one another. Later 'hil"ren o& a ?elative)aFout are Mhigher in the Q a;isM than are earlier 'hil"ren, meaning that later 'hil"ren =ill o!erlap earlier 'hil"ren i& they are set up to o''upy the same spa'e in the layout.

*<:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

5his =ill be 'learer =ith an e;ample. +ere is a layout, &rom +ontainers/?elative"verlap, =ith a ?elative)aFout hol"ing t=o 4utton =i"gets,
LNGml version671.-7 encoding67utf-,7NM L?elative)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L4utton android:teGt67I A# 4ID7 android:teGt2iKe671>-dip7 android:teGt2tFle67bold7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 /M L4utton android:teGt67I am small7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:laFout centerIn(arent67true7 /M L/?elative)aFoutM

5he &irst 4utton is set to &ill the s'reen. 5he se'on" 4utton is set to be 'entere" insi"e the parent, but only take up as mu'h spa'e as is nee"e" &or its 'aption. +en'e, the se'on" 4utton =ill appear to M&loatM o!er the &irst 4utton,

**<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

"igure %21 The Celative,verlap sample application

1oth 4utton =i"gets 'an still be 'li'ke", though 'li'king on the smaller 4utton "oes not also 'li'k the bigger 4utton. ?our 'li'ks =ill be han"le" by the =i"get on top in the 'ase o& an o!erlap like this.

Tabula Casa
0& you like +5ML tables, sprea"sheet gri"s, an" the like, you =ill like An"roi"7s &able)aFout S it allo=s you to position your =i"gets in a gri" to your spe'i&i'ations. ?ou 'ontrol the number o& ro=s an" 'olumns, =hi'h 'olumns might shrink or stret'h to a''ommo"ate their 'ontents, an" so on.
&able)aFout

=orks in 'onGun'tion =ith &able?oE. &able)aFout 'ontrols the o!erall beha!ior o& the 'ontainer, =ith the =i"gets themsel!es poure" into one or more &able?oE 'ontainers, one per ro= in the gri".

***

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

Concepts nd Properties
*or all this to =ork, =e nee" to &igure out ho= =i"gets =ork =ith ro=s an" 'olumns, plus ho= to han"le =i"gets that li!e outsi"e o& ro=s.

Puttin! Cells in Ro#s


o=s are "e'lare" by you, the "e!eloper, by putting =i"gets as 'hil"ren o& a insi"e the o!erall &able)aFout. ?ou, there&ore, 'ontrol "ire'tly ho= many ro=s appear in the table.
&able?oE

5he number o& 'olumns are "etermine" by An"roi"T you 'ontrol the number o& 'olumns in an in"ire't &ashion. *irst, there =ill be at least one 'olumn per =i"get in your longest ro=. %o i& you ha!e three ro=s, one =ith t=o =i"gets, one =ith three =i"gets, an" one =ith &our =i"gets, there =ill be at least &our 'olumns. +o=e!er, a =i"get 'an take up more than one 'olumn by in'lu"ing the android:laFout span property, in"i'ating the number o& 'olumns the =i"get spans. 5his is akin to the colspan attribute one &in"s in table 'ells in +5ML,
L&able?oEM L&eGtVieE android:teGt673?):7 /M L$dit&eGt android:id67ORid/entrF7 android:laFout span67C7/M L/&able?oEM

0n the abo!e FML layout &ragment, the &iel" spans three 'olumns. >r"inarily, =i"gets are put into the &irst a!ailable 'olumn. 0n the abo!e &ragment, the label =oul" go in the &irst 'olumn ('olumn -, as 'olumns are 'ounte" starting &rom -), an" the &iel" =oul" go into a spanne" set o& three 'olumns ('olumns 1 through C). +o=e!er, you 'an put a =i"get into a "i&&erent 'olumn !ia the android:laFout column property, spe'i&ying the -base" 'olumn the =i"get belongs to,

**&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

L&able?oEM L4utton android:id67ORid/cancel7 android:laFout column67>7 android:teGt67+ancel7 /M L4utton android:id67ORid/ok7 android:teGt67"H7 /M L/&able?oEM

0n the pre'e"ing FML layout &ragment, the Can'el button goes in the thir" 'olumn ('olumn >). 5he >D button then goes into the ne;t a!ailable 'olumn, =hi'h is the &ourth 'olumn.

"on*Ro# Children o. T =le) yout


2ormally, &able)aFout 'ontains only &able?oE elements as imme"iate 'hil"ren. +o=e!er, it is possible to put other =i"gets in bet=een ro=s. *or those =i"gets, &able)aFout beha!es a bit like )inear)aFout =ith !erti'al orientation. 5he =i"gets automati'ally ha!e their =i"th set to fill parent, so they =ill &ill the same spa'e that the longest ro= "oes. >ne pattern &or this is to use a plain VieE as a "i!i"er (e.g., LVieE android:laFout height 6 7>dip7 android:background 6 7S----997 /M as a t=o-pi;el-high blue bar a'ross the =i"th o& the table).

Stretch4 Shrin$4 nd Coll pse


1y "e&ault, ea'h 'olumn =ill be siKe" a''or"ing to the MnaturalM siKe o& the =i"est =i"get in that 'olumn (taking spanne" 'olumns into a''ount). %ometimes, though, that "oes not =ork out !ery =ell, an" you nee" more 'ontrol o!er 'olumn beha!ior. ?ou 'an pla'e an android:stretch+olumns property on the &able)aFout. 5he !alue shoul" be a single 'olumn number (again, --base") or a 'omma"elimite" list o& 'olumn numbers. 5hose 'olumns =ill be stret'he" to take up any a!ailable spa'e yet on the ro=. 5his helps i& your 'ontent is narro=er than the a!ailable spa'e.

**-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

Con!ersely, you 'an pla'e a android:shrink+olumns property on the &able)aFout. Again, this shoul" be a single 'olumn number or a 'omma"elimite" list o& 'olumn numbers. 5he 'olumns liste" in this property =ill try to =or"-=rap their 'ontents to re"u'e the e&&e'ti!e =i"th o& the 'olumn S by "e&ault, =i"gets are not =or"-=rappe". 5his helps i& you ha!e 'olumns =ith potentially =or"y 'ontent that might 'ause some 'olumns to be pushe" o&& the right si"e o& the s'reen. ?ou 'an also le!erage an android:collapse+olumns property on the &able)aFout, again =ith a 'olumn number or 'omma-"elimite" list o& 'olumn numbers. 5hese 'olumns =ill start out M'ollapse"M, meaning they =ill be part o& the table in&ormation but =ill be in!isible. #rogrammati'ally, you 'an 'ollapse an" un-'ollapse 'olumns by 'alling set+olumn+ollapsedPQ on the &able)aFout. ?ou might use this to allo= users to 'ontrol =hi'h 'olumns are o& importan'e to them an" shoul" be sho=n !ersus =hi'h ones are less important an" 'an be hi""en. ?ou 'an also 'ontrol stret'hing an" shrinking at runtime !ia set+olumn2tretchablePQ an" set+olumn2hrinkablePQ.

E0 mple
5he FML layout &ragments sho=n abo!e, =hen 'ombine", gi!e us a ren"ition o& the M&ormM =e 'reate" &or ?elative)aFout, =ith the a""ition o& a "i!i"er line bet=een the labelP&iel" an" the t=o buttons (&oun" in the +ontainers/&able "emo),
&able)aFout
LNGml version671.-7 encoding67utf-,7NM L&able)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:stretch+olumns6717M L&able?oEM L&eGtVieE android:teGt673?):7 /M L$dit&eGt android:id67ORid/entrF7 android:laFout span67C7/M L/&able?oEM LVieE android:laFout height67>dip7

**%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

android:background67S----997 /M L&able?oEM L4utton android:id67ORid/cancel7 android:laFout column67>7 android:teGt67+ancel7 /M L4utton android:id67ORid/ok7 android:teGt67"H7 /M L/&able?oEM L/&able)aFoutM

When 'ompile" against the generate" Ca!a 'o"e an" run on the emulator, =e get,

"igure %71 The Table!ayout/emo sample application

Scroll)ork
#hone s'reens ten" to be small, =hi'h reRuires "e!elopers to use some tri'ks to present a lot o& in&ormation in the limite" a!ailable spa'e. >ne tri'k &or "oing this is to use s'rolling, so only part o& the in&ormation is !isible at one time, the rest a!ailable !ia s'rolling up or "o=n. is a 'ontainer that pro!i"es s'rolling &or its 'ontents. ?ou 'an take a layout that might be too big &or some s'reens, =rap it in a 2crollVieE,
2crollVieE
**0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

an" still use your e;isting layout logi'. 0t Gust so happens that the user 'an only see part o& your layout at one time, the rest a!ailable !ia s'rolling. *or e;ample, here is a 2crollVieE use" in an FML layout &ile (&rom the +ontainers/2croll "emo),
LNGml version671.-7 encoding67utf-,7NM L2crollVieE Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7M L&able)aFout android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:stretch+olumns67-7M L&able?oEM LVieE android:laFout height67,-dip7 android:background67S------7/M L&eGtVieE android:teGt67S------7 android:padding)eft67<dip7 android:laFout gravitF67center vertical7 /M L/&able?oEM L&able?oEM LVieE android:laFout height67,-dip7 android:background67S<<----7 /M L&eGtVieE android:teGt67S<<----7 android:padding)eft67<dip7 android:laFout gravitF67center vertical7 /M L/&able?oEM L&able?oEM LVieE android:laFout height67,-dip7 android:background67S,,<<--7 /M L&eGtVieE android:teGt67S,,<<--7 android:padding)eft67<dip7 android:laFout gravitF67center vertical7 /M L/&able?oEM L&able?oEM LVieE android:laFout height67,-dip7 android:background67Saa,,<<7 /M L&eGtVieE android:teGt67Saa,,<<7 android:padding)eft67<dip7 android:laFout gravitF67center vertical7 /M L/&able?oEM L&able?oEM LVieE android:laFout height67,-dip7 android:background67Sffaa,,7 /M

**2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

L&eGtVieE android:teGt67Sffaa,,7 android:padding)eft67<dip7 android:laFout gravitF67center vertical7 /M L/&able?oEM L&able?oEM LVieE android:laFout height67,-dip7 android:background67Sffffaa7 /M L&eGtVieE android:teGt67Sffffaa7 android:padding)eft67<dip7 android:laFout gravitF67center vertical7 /M L/&able?oEM L&able?oEM LVieE android:laFout height67,-dip7 android:background67Sffffff7 /M L&eGtVieE android:teGt67Sffffff7 android:padding)eft67<dip7 android:laFout gravitF67center vertical7 /M L/&able?oEM L/&able)aFoutM L/2crollVieEM

Without the 2crollVieE, the table =oul" take up at least A/0 pi;els (4 ro=s at 80 pi;els ea'h, base" on the VieE "e'larations). 5here may be some "e!i'es =ith s'reens 'apable o& sho=ing that mu'h in&ormation, but many =ill be smaller. 5he 2crollVieE lets us keep the table as-is, but only present part o& it at a time. >n the sto'k An"roi" emulator, =hen the a'ti!ity is &irst !ie=e", you see,

**7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Containers

"igure %81 The Scroll;ie)/emo sample application

2oti'e ho= only &i!e ro=s an" part o& the si;th are !isible. 1y pressing the upP"o=n buttons on the "ire'tional pa", you 'an s'roll up an" "o=n to see the remaining ro=s. Also note ho= the right si"e o& the 'ontent gets 'lippe" by the s'rollbar S be sure to put some pa""ing on that si"e or other=ise ensure your o=n 'ontent "oes not get 'lippe" in that &ashion. An"roi" 1.A intro"u'e" !oriKontal2crollVieE, =hi'h =orks like 2crollVieE... Gust horiKontally. 5his =oul" be goo" &or &orms that might be too =i"e rather than too tall. 2ote that neither 2crollVieE nor !oriKontal2crollVieE =ill gi!e you bi-"ire'tional s'rolling S you ha!e to 'hoose !erti'al or horiKontal. Also, note that you 'annot put s'rollable items into a 2crollVieE. *or e;ample, a )istVieE =i"get S =hi'h =e =ill see in an up'oming 'hapter S alrea"y kno=s ho= to s'roll. ?ou "o not nee" to put a )istVieE in a 2crollVieE, an" i& you =ere to try, it =oul" not =ork !ery =ell.

**8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 11

The nput +ethod "rame)ork

An"roi" 1.A intro"u'e" the input metho" &rame=ork (0M*), =hi'h is 'ommonly re&erre" to as Mso&t keyboar"sM. +o=e!er, the Mso&t keyboar"M term is not ne'essarily a''urate, as 0M* 'oul" be use" &or han"=riting re'ognition or other means o& a''epting te;t input !ia the s'reen.

9eyboards@ 3ard and Soft


%ome An"roi" "e!i'es ha!e a har"=are keyboar" that is !isible some o& the time (=hen it is sli" out). A &e= An"roi" "e!i'es ha!e a har"=are keyboar" that is al=ays !isible (so-'alle" MbarM or MslabM phones). Most An"roi" "e!i'es, though, ha!e no har"=are keyboar" at all. 5he 0M* han"les all o& these s'enarios. 0n short, i& there is no har"=are keyboar", an input metho" e"itor (0ME) =ill be a!ailable to the user =hen they tap on an enable" $dit&eGt. 5his reRuires no 'o"e 'hanges to your appli'ation...i& the "e&ault &un'tionality o& the 0ME is =hat you =ant. *ortunately, An"roi" is &airly smart about guessing =hat you =ant, so it may be you 'an Gust test =ith the 0ME but other=ise make no spe'i&i' 'o"e 'hanges. >& 'ourse, the keyboar" may not Ruite beha!e ho= you =oul" like. *or e;ample, in the 4asic/9ield sample proGe't, the 9ield=emo a'ti!ity has the 0ME o!erlaying the multiple-line $dit&eGt,
**:
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

"igure %:1 The input method editor@ as seen in the "ield/emo sample application

0t =oul" be ni'e to ha!e more 'ontrol o!er ho= this appears, an" &or other beha!ior o& the 0ME. *ortunately, the &rame=ork as a =hole gi!es you many options &or this, as is "es'ribe" o!er the bulk o& this 'hapter.

Tailored To .our ?eeds


An"roi" 1.1 an" earlier o&&ere" many attributes on $dit&eGt =i"gets to 'ontrol their style o& input, su'h as android:passEord to in"i'ate a &iel" shoul" be &or pass=or" entry (shrou"ing the pass=or" keystrokes &rom prying eyes). %tarting in An"roi" 1.A, =ith the 0M*, many o& these ha!e been 'ombine" into a single android:input&Fpe attribute. 5he android:input&Fpe attribute takes a 'lass plus mo"i&iers, in a pipe"elimite" list (=here W is the pipe 'hara'ter). 5he 'lass generally "es'ribes =hat the user is allo=e" to input, an" this "etermines the basi' set o& keys a!ailable on the so&t keyboar". 5he a!ailable 'lasses are,
teGt

(the "e&ault)

number
*&<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

phone datetime date time

Many o& these 'lasses o&&er one or more mo"i&iers, to &urther re&ine =hat the user =ill be entering. 5o help e;plain those, take a look at the res/laFout/main.Gml &ile &rom the Input#ethod/I#$=emo1 proGe't,
LNGml version671.-7 encoding67utf-,7NM L&able)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:stretch+olumns6717 M L&able?oEM L&eGtVieE android:teGt67%o special rules:7 /M L$dit&eGt /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67$mail address:7 /M L$dit&eGt android:input&Fpe67teGtWteGt$mailAddress7 /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt672igned decimal number:7 /M L$dit&eGt android:input&Fpe67numberWnumber2ignedWnumber=ecimal7 /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67=ate:7 /M L$dit&eGt android:input&Fpe67date7 /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67#ulti-line teGt:7 /M

*&*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

L$dit&eGt android:input&Fpe67teGtWteGt#ulti)ineWteGtAuto+orrect7 android:min)ines67C7 android:gravitF67top7 /M L/&able?oEM L/&able)aFoutM

+ere, you =ill see a &able)aFout 'ontaining &i!e ro=s, ea'h "emonstrating a slightly "i&&erent &la!or o& $dit&eGt, 1. >ne has no attributes at all on the $dit&eGt, meaning you get a plain te;t entry &iel"

2. >ne has android:input&Fpe 6 7teGtWteGt$mailAddress7, meaning it is te;t entry, but spe'i&i'ally seeks an email a""ress .. >ne allo=s &or signe" "e'imal numeri' input, !ia android:input&Fpe
6 7numberWnumber2ignedWnumber=ecimal7

<. >ne is set up to allo= &or "ata entry o& a "ate ( android:input&Fpe 6 7date7) A. 5he last allo=s &or multi-line input =ith auto-'orre'tion o& probable spelling errors (android:input&Fpe 6 7teGtWteGt#ulti)ineW teGtAuto+orrect7) 5he 'lass an" mo"i&iers tailor the keyboar". %o, a plain te;t entry &iel" results in a plain so&t keyboar",

*&&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

"igure 0<1 A standard input method editor $a1k1a1@ soft keyboard'

An email a""ress &iel" might put the O symbol on the so&t keyboar", at the 'ost o& a smaller spa'ebar,

"igure 0*1 The input method editor for email addresses

*&-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

2ote, though, that this beha!ior is spe'i&i' to the input metho" e"itor. %ome e"itors might put an I sign on the primary keyboar" &or an email &iel". %ome might put a M.'omM button on the primary keyboar". %ome might not rea't at all. 0t is up to the implementation o& the input metho" e"itor S all you 'an "o is supply the hint. 2umbers an" "ates restri't the keys to numeri' keys, plus a set o& symbols that may or may not be !ali" on a gi!en &iel",

"igure 0&1 The input method editor for signed decimal numbers

An" so on. 1y 'hoosing the appropriate android:input&Fpe, you 'an gi!e the user a so&t keyboar" that best suits =hat it is they shoul" be entering.

Tell Android Where t Can (o


?ou may ha!e noti'e" a subtle "i&&eren'e bet=een the &irst an" se'on" input metho" e"itors, beyon" the a""ition o& the O key. 0& you look in the

*&%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

lo=er-right 'orner o& the so&t keyboar", the se'on" &iel"7s e"itor has a M2e;tM button, =hile the &irst &iel"7s e"itor has a ne=line button. 5his points out t=o things, 1.
$dit&eGt =i"gets android:input&Fpe

are multi-line by "e&ault i& you "o not spe'i&y

2. ?ou 'an 'ontrol =hat goes on =ith that lo=er-right-han" button, 'alle" the a''essory button 1y "e&ault, on an $dit&eGt =here you ha!e spe'i&ie" android:input&Fpe, the a''essory button =ill be M2e;tM, mo!ing you to the ne;t $dit&eGt in seRuen'e, or M@oneM, i& you are on the last $dit&eGt on the s'reen. ?ou 'an manually stipulate =hat the a''essory button =ill be labele" !ia the android:ime"ptions attribute. *or e;ample, in the res/laFout/main.Gml &rom Input#ethod/I#$=emo>, you =ill see an augmente" !ersion o& the pre!ious e;ample, =here t=o input &iel"s spe'i&y =hat their a''essory button shoul" look like,
LNGml version671.-7 encoding67utf-,7NM L2crollVieE Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&able)aFout android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:stretch+olumns6717 M L&able?oEM L&eGtVieE android:teGt67%o special rules:7 /M L$dit&eGt /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67$mail address:7 /M L$dit&eGt android:input&Fpe67teGtWteGt$mailAddress7 android:ime"ptions67action2end7 /M L/&able?oEM L&able?oEM

*&0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

L&eGtVieE android:teGt672igned decimal number:7 /M L$dit&eGt android:input&Fpe67numberWnumber2ignedWnumber=ecimal7 android:ime"ptions67action=one7 /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67=ate:7 /M L$dit&eGt android:input&Fpe67date7 /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67#ulti-line teGt:7 /M L$dit&eGt android:input&Fpe67teGtWteGt#ulti)ineWteGtAuto+orrect7 android:min)ines67C7 android:gravitF67top7 /M L/&able?oEM L/&able)aFoutM L/2crollVieEM

+ere, =e atta'h a M%en"M a'tion to the a''essory button &or the email a""ress (android:ime"ptions 6 7action2end7), an" the M@oneM a'tion on the mi""le &iel" (android:ime"ptions 6 7action=one7). 1y "e&ault, M2e;tM =ill mo!e the &o'us to the ne;t $dit&eGt an" M@oneM =ill 'lose up the input metho" e"itor. +o=e!er, &or those, or &or any other ones like M%en"M, you 'an use set"n$ditorAction)istenerPQ on $dit&eGt (te'hni'ally, on the &eGtVieE super'lass) to get 'ontrol =hen the a''essory button is 'li'ke" or the user presses the L$nterM key. ?ou are pro!i"e" =ith a &lag in"i'ating the "esire" a'tion (e.g., I#$ A+&I"% 2$%=), an" you 'an then "o something to han"le that reRuest (e.g., sen" an email to the supplie" email a""ress).

*&2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

"itting n
?ou =ill noti'e that the I#$=emo> layout sho=n abo!e has another "i&&eren'e &rom its I#$=emo1 pre"e'essor, the use o& a 2crollVieE 'ontainer =rapping the &able)aFout. 5his ties into another le!el o& 'ontrol you ha!e o!er the input metho" e"itors, =hat happens to your a'ti!ity7s o=n layout =hen the input metho" e"itor appearsH 5here are three possibilities, "epen"ing on 'ir'umstan'es,

An"roi" 'an MpanM your a'ti!ity, e&&e'ti!ely sli"ing the =hole layout up to a''ommo"ate the input metho" e"itor, or o!erlaying your layout, "epen"ing on =hether the $dit&eGt being e"ite" is at the top or bottom. 5his has the e&&e't o& hi"ing some portion o& your $0. An"roi" 'an resiKe your a'ti!ity, e&&e'ti!ely 'ausing it to shrink to a smaller s'reen "imension, allo=ing the input metho" e"itor to sit belo= the a'ti!ity itsel&. 5his is great =hen the layout 'an rea"ily be shrunk (e.g., it is "ominate" by a list or multi-line input &iel" that "oes not nee" the =hole s'reen to be &un'tional). 0n lan"s'ape mo"e, An"roi" may "isplay the input metho" e"itor &ull-s'reen, obs'uring your entire a'ti!ity. 5his allo=s &or a bigger keyboar" an" generally easier "ata entry.

An"roi" 'ontrols the &ull-s'reen option purely on its o=n. An", by "e&ault, An"roi" =ill 'hoose bet=een pan an" resiKe mo"es "epen"ing on =hat your layout looks like. 0& you =ant to spe'i&i'ally 'hoose bet=een pan an" resiKe, you 'an "o so !ia an android:EindoE2oftInput#ode attribute on the LactivitFM element in your Android#anifest.Gml &ile. *or e;ample, here is the mani&est &rom I#$=emo>,
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.imf.tEo7 android:version+ode6717 android:version%ame671.-7M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67.I#$=emo>7 android:label67Ostring/app name7 android:EindoE2oftInput#ode67adjust?esiKe7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M *&7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

L/intent-filterM L/activitFM L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

1e'ause =e spe'i&ie" resiKe, An"roi" =ill shrink our layout to a''ommo"ate the input metho" e"itor. With the 2crollVieE in pla'e, this means the s'roll bar =ill appear as nee"e",

"igure 0-1 The shrunken@ scrollable layout

6ane@ Stop This CraBy Thing!


%ometimes, you nee" the input metho" e"itor to Gust go a=ay. *or e;ample, i& you make the a'tion button be M%ear'hM, the user tapping that button =ill not automati'ally hi"e the e"itor. 5o hi"e the e"itor, you =ill nee" to make a 'all to the Input#ethod#anager, a system ser!i'e that 'ontrols these input metho" e"itors,

*&8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The nput +ethod "rame)ork

Input#ethod#anager mgr6PInput#ethod#anagerQgetSystemSer!icePI%(3& #$&!"= 2$?VI+$QJ mgr.hideSoftInput"rom#indowPfld.get#indowTokenPQ8 -QJ

(=here fld is the $dit&eGt =hose input metho" e"itor you =ant to hi"e) 5his =ill al=ays 'lose the input metho" e"itor. +o=e!er, bear in min" that there are t=o =ays &or a user to ha!e opene" that input metho" e"itor in the &irst pla'e, 1. 0& their "e!i'e "oes not ha!e a har"=are keyboar" e;pose", an" they tap on the $dit&eGt, the input metho" e"itor shoul" appear

2. 0& they pre!iously "ismisse" the e"itor, or i& they are using the e"itor &or a =i"get that "oes not normally pop one up (e.g., )istVieE), an" they long-tap on the ME2$ button, the input metho" e"itor shoul" appear 0& you only =ant to 'lose the input metho" e"itor &or the &irst s'enario, but not the se'on", use Input#ethod#anager.!I=$ I#()I+I& "%)5 as a &lag &or the se'on" parameter to your 'all to hide2oftInput9rom@indoEPQ, instea" o& the sho=n in the pre!ious e;ample.

*&:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1&

>sing Selection Widgets

1a'k in the 'hapter on input metho" e"itors, you sa= ho= &iel"s 'oul" ha!e 'onstraints pla'e" upon them to limit possible input, su'h as numeri'-only or phone-number-only. 5hese sorts o& 'onstraints help users Mget it rightM =hen entering in&ormation, parti'ularly on a mobile "e!i'e =ith 'rampe" keyboar"s. >& 'ourse, the ultimate in 'onstraine" input is to sele't a 'hoi'e &rom a set o& items, su'h as the ra"io buttons seen earlier. Classi' $0 toolkits ha!e listbo;es, 'ombobo;es, "rop-"o=n lists, an" the like &or that !ery purpose. An"roi" has many o& the same sorts o& =i"gets, plus others o& parti'ular interest &or mobile "e!i'es (e.g., the DallerF &or e;amining sa!e" photos). Moreo!er, An"roi" o&&ers a &le;ible &rame=ork &or "etermining =hat 'hoi'es are a!ailable in these =i"gets. %pe'i&i'ally, An"roi" o&&ers a &rame=ork o& "ata a"apters that pro!i"e a 'ommon inter&a'e to sele'tion lists ranging &rom stati' arrays to "atabase 'ontents. %ele'tion !ie=s S =i"gets &or presenting lists o& 'hoi'es S are han"e" an a"apter to supply the a'tual 'hoi'es.

Adapting to the Circumstances


0n the abstra't, a"apters pro!i"e a 'ommon inter&a'e to multiple "isparate A#0s. More spe'i&i'ally, in An"roi"7s 'ase, a"apters pro!i"e a 'ommon inter&a'e to the "ata mo"el behin" a sele'tion-style =i"get, su'h as a
*-*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

listbo;. 5his use o& Ca!a inter&a'es is &airly 'ommon (e.g., Ca!aP%=ing7s mo"el a"apters &or J&able), an" Ca!a is &ar &rom the only en!ironment o&&ering this sort o& abstra'tion (e.g., *le;7s FML "ata-bin"ing &rame=ork a''epts FML inline" as stati' "ata or retrie!e" &rom the 0nternet). An"roi"7s a"apters are responsible &or pro!i"ing the roster o& "ata &or a sele'tion =i"get plus 'on!erting in"i!i"ual elements o& "ata into spe'i&i' !ie=s to be "isplaye" insi"e the sele'tion =i"get. 5he latter &a'et o& the a"apter system may soun" a little o"", but in reality it is not that "i&&erent &rom other 8$0 toolkits7 =ays o& o!erri"ing "e&ault "isplay beha!ior. *or e;ample, in Ca!aP%=ing, i& you =ant a J)ist-ba'ke" listbo; to a'tually be a 'he'klist (=here in"i!i"ual ro=s are a 'he'kbo; plus label, an" 'li'ks a"Gust the state o& the 'he'kbo;), you ine!itably =in" up 'alling set+ell?endererPQ to supply your o=n )ist+ell?enderer, =hi'h in turn 'on!erts strings &or the list into J+heck4oG-plus-J)abel 'omposite =i"gets.

-sin! Arr yAd pter


5he easiest a"apter to use is ArraFAdapter S all you nee" to "o is =rap one o& these aroun" a Ca!a array or java.util.)ist instan'e, an" you ha!e a &ully&un'tioning a"apter,
2tringAB items6:7this78 7is78 7a78 7reallF78 7sillF78 7list7;J neE ArraFAdapterL2tringMPthis8 android.?.laFout.simple list item 18 itemsQJ

>ne &la!or o& the ArraFAdapter 'onstru'tor takes three parameters,


5he +onteGt to use (typi'ally this =ill be your a'ti!ity instan'e) 5he resour'e 0@ o& a !ie= to use (su'h as a built-in system resour'e 0@, as sho=n abo!e) 5he a'tual array or list o& items to sho=

1y "e&ault, the ArraFAdapter =ill in!oke to2tringPQ on the obGe'ts in the list an" =rap ea'h o& those strings in the !ie= "esignate" by the supplie" resour'e. android.?.laFout.simple list item 1 simply turns those strings
*-&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

into &eGtVieE obGe'ts. 5hose &eGtVieE =i"gets, in turn, =ill be sho=n in the list or spinner or =hate!er =i"get uses this ArraFAdapter. 0& you =ant to see =hat android.?.laFout.simple list item 1 looks like, you 'an &in" a 'opy o& it in your %@D installation S Gust sear'h &or simple list item 1.Gml. We =ill see in a later 'hapter ho= to sub'lass an Adapter an" o!erri"e ro= 'reation, to gi!e you greater 'ontrol o!er ho= ro=s appear.

!ists of ?aughty and ?ice


5he 'lassi' listbo; =i"get in An"roi" is kno=n as )istVieE. 0n'lu"e one o& these in your layout, in!oke setAdapterPQ to supply your "ata an" 'hil" !ie=s, an" atta'h a listener !ia set"nItem2elected)istenerPQ to &in" out =hen the sele'tion has 'hange". With that, you ha!e a &ully-&un'tioning listbo;. +o=e!er, i& your a'ti!ity is "ominate" by a single list, you might =ell 'onsi"er 'reating your a'ti!ity as a sub'lass o& )istActivitF, rather than the regular ActivitF base 'lass. 0& your main !ie= is Gust the list, you "o not e!en nee" to supply a layout S )istActivitF =ill 'onstru't a &ull-s'reen list &or you. 0& you "o =ant to 'ustomiKe the layout, you 'an, so long as you i"enti&y your )istVieE as Oandroid:id/list, so )istActivitF kno=s =hi'h =i"get is the main list &or the a'ti!ity. *or e;ample, here is a layout pulle" &rom the 2election/)ist sample proGe't,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&eGtVieE android:id67ORid/selection7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7/M L)istVieE android:id67Oandroid:id/list7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:draE2elector"n&op67false7

*--

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

/M L/)inear)aFoutM

0t is Gust a list =ith a label on top to sho= the 'urrent sele'tion. 5he Ca!a 'o"e to 'on&igure the list an" 'onne't the list =ith the label is,
public class )istVieE=emo eGtends )istActivitF : private &eGtVieE selectionJ private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ setList$dapterPneE ArraFAdapterL2tringMPthis8 android.?.laFout.simple list item 18 itemsQQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ ; public void onListItemClickP)istVieE parent8 VieE v8 int position8 long idQ : selection.setTextPitemsApositionBQJ ; ;

With )istActivitF, you 'an set the list a"apter !ia set)istAdapterPQ S in this 'ase, pro!i"ing an ArraFAdapter =rapping an array o& nonsense strings. 5o &in" out =hen the list sele'tion 'hanges, o!erri"e on)istItem+lickPQ an" take appropriate steps base" on the supplie" 'hil" !ie= an" position (in this 'ase, up"ating the label =ith the te;t &or that position). 5he resultsH

*-%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

"igure 0%1 The !ist;ie)/emo sample application

5he

to our ArraFAdapter S android.?.laFout.simple list item 1 S 'ontrols =hat the ro=s look like. 5he !alue use" in the pre'e"ing e;ample pro!i"es the stan"ar" An"roi" list ro=, big &ont, lots o& pa""ing, =hite te;t.

se'on"

parameter

Selection %odes
1y "e&ault, )istVieE is set up simply to 'olle't 'li'ks on list entries. %ometimes, though, you =ant a list that tra'ks a user7s sele'tion, or possibly multiple sele'tions. )istVieE 'an han"le that as =ell, but it reRuires a &e= 'hanges. *irst, you =ill nee" to 'all set+hoice#odePQ on the )istVieE in Ca!a 'o"e to set the 'hoi'e mo"e, supplying either +!"I+$ #"=$ 2I%D)$ or +!"I+$ #"=$ #3)&I()$ as the !alue. ?ou 'an get your )istVieE &rom a )istActivitF !ia get)istVieEPQ. ?ou 'an also "e'lare this !ia the android:choice#ode attribute in your layout FML.

*-0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

5hen, rather than use android.?.laFout.simple list item 1 as the layout &or the list ro=s in your ArraFAdapter 'onstru'tor, you =ill nee" to use either android.?.laFout.simple list item single choice or android.?.laFout.simple list item multiple choice &or single-'hoi'e or multiple-'hoi'e lists, respe'ti!ely. *or e;ample, here is an a'ti!ity layout &rom the 2election/+hecklist sample proGe't,
LNGml version671.-7 encoding67utf-,7NM L)istVieE Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67Oandroid:id/list7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:draE2elector"n&op67false7 android:choice#ode67multiple+hoice7 /M

0t is a &ull-s'reen )istVieE, =ith the android:choice#ode67multiple+hoice7 attribute to in"i'ate that =e =ant multiple 'hoi'e support. >ur a'ti!ity Gust uses a stan"ar" ArraFAdapter on our list o& nonsense =or"s, but uses android.?.laFout.simple list item multiple choice as the ro= layout,
package com.commonsEare.android.checklistJ import import import import android.os.4undleJ android.app.)istActivitFJ android.Eidget.ArraFAdapterJ android.Eidget.)istVieEJ

public class +hecklist=emo eGtends )istActivitF : private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ setList$dapterPneE ArraFAdapterL2tringMPthis8

*-2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

; ;

android.?.laFout.simple list item multiple choice8 itemsQQJ

What the user sees is the list o& =or"s =ith 'he'kbo;es "o=n the right e"ge,

"igure 001 +ultiple#select mode

0& =e =ante", =e 'oul" 'all metho"s like get+heckedItem(ositionsPQ on our )istVieE to &in" out =hi'h items the user 'he'ke", or setItem+heckedPQ i& =e =ante" to 'he'k (or un-'he'k) a spe'i&i' entry oursel!es.

Spin Control
0n An"roi", the 2pinner is the eRui!alent o& the "rop-"o=n sele'tor you might &in" in other toolkits (e.g., J+ombo4oG in Ca!aP%=ing). #ressing the 'enter button on the @-pa" pops up a sele'tion "ialog &or the user to 'hoose an item &rom. ?ou basi'ally get the ability to sele't &rom a list

*-7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

=ithout taking up all the s'reen spa'e o& a )istVieE, at the 'ost o& an e;tra 'li'k or s'reen tap to make a 'hange. As =ith )istVieE, you pro!i"e the a"apter &or "ata an" 'hil" !ie=s !ia setAdapterPQ an" hook in a listener obGe't &or sele'tions !ia set"nItem2elected)istenerPQ. 0& you =ant to tailor the !ie= use" =hen "isplaying the "rop-"o=n perspe'ti!e, you nee" to 'on&igure the a"apter, not the 2pinner =i"get. $se the set=rop=oEnVieE?esourcePQ metho" to supply the resour'e 0@ o& the !ie= to use. *or e;ample, 'ulle" &rom the 2election/2pinner sample proGe't, here is an FML layout &or a simple !ie= =ith a 2pinner,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&eGtVieE android:id67ORid/selection7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L2pinner android:id67ORid/spinner7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:draE2elector"n&op67true7 /M L/)inear)aFoutM

5his is the same !ie= as sho=n in the pre!ious se'tion, Gust =ith a 2pinner instea" o& a )istVieE. 5he 2pinner property android:draE2elector"n&op 'ontrols =hether the arro=s are "ra=n on the sele'tor button on the right si"e o& the 2pinner $0. 5o populate an" use the 2pinner, =e nee" some Ca!a 'o"e,

*-8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

public class 2pinner=emo eGtends ActivitF implements AdapterVieE."nItem2elected)istener : private &eGtVieE selectionJ private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ 2pinner spin6P2pinnerQfindViewByIdP?.id.spinnerQJ spin.setOnItemSelectedListenerPthisQJ ArraFAdapterL2tringM aa6neE ArraFAdapterL2tringMPthis8 android.?.laFout.simple spinner item8 itemsQJ aa.setDropDownView%esourceP android.?.laFout.simple spinner dropdoEn itemQJ spin.set$dapterPaaQJ

public void onItemSelectedPAdapterVieELNM parent8 VieE v8 int position8 long idQ : selection.setTextPitemsApositionBQJ ; public void on&othingSelectedPAdapterVieELNM parentQ : selection.setTextP77QJ ;

+ere, =e atta'h the a'ti!ity itsel& as the sele'tion listener (spin.set"nItem2elected)istenerPthisQ). 5his =orks be'ause the a'ti!ity implements the "nItem2elected)istener inter&a'e. We 'on&igure the a"apter not only =ith the list o& &ake =or"s, but also =ith a spe'i&i' resour'e to use &or the "rop-"o=n !ie= (!ia aa.set=rop=oEnVieE?esourcePQ). Also note the use o& android.?.laFout.simple spinner item as the built-in VieE &or sho=ing items in the spinner itsel&. *inally, =e implement the 'allba'ks reRuire" by "nItem2elected)istener to a"Gust the sele'tion label base" on user input. What =e get is,

*-:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

"igure 021 The Spinner/emo sample application@ as initially launched

"igure 071 The same application@ )ith the spinner drop#do)n list displayed

*%<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

(rid .our !ions $,r Something !ike That111'


As the name suggests, DridVieE gi!es you a t=o-"imensional gri" o& items to 'hoose &rom. ?ou ha!e mo"erate 'ontrol o!er the number an" siKe o& the 'olumnsT the number o& ro=s is "ynami'ally "etermine" base" on the number o& items the supplie" a"apter says are a!ailable &or !ie=ing. 5here are a &e= properties =hi'h, =hen 'ombine", "etermine the number o& 'olumns an" their siKes,

spells out ho= many 'olumns there are, or, i& you supply a !alue o& auto fit, An"roi" =ill 'ompute the number o& 'olumns base" on a!ailable spa'e an" the properties liste" belo=.
android:num+olumns

an" android:horiKontal2pacing in"i'ate ho= mu'h =hitespa'e there shoul" be bet=een items in the gri".
android:vertical2pacing android:column@idth

shoul" be.

in"i'ates ho= many pi;els =i"e ea'h 'olumn

&or gri"s =ith auto fit &or happen &or any a!ailable spa'e not taken up by 'olumns or spa'ing S this shoul" be column@idth to ha!e the 'olumns take up a!ailable spa'e or spacing@idth to ha!e the =hitespa'e bet=een 'olumns absorb e;tra spa'e.

android:stretch#ode in"i'ates, android:num+olumns, =hat shoul"

>ther=ise, the DridVieE =orks mu'h like any other sele'tion =i"get S use setAdapterPQ to pro!i"e the "ata an" 'hil" !ie=s, in!oke set"nItem2elected)istenerPQ to register a sele'tion listener, et'. *or e;ample, here is an FML layout &rom the 2election/Drid sample proGe't, sho=ing a DridVieE 'on&iguration,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&eGtVieE android:id67ORid/selection7 *%*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M LDridVieE android:id67ORid/grid7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:vertical2pacing67<-dip7 android:horiKontal2pacing67.dip7 android:num+olumns67auto fit7 android:column@idth671--dip7 android:stretch#ode67column@idth7 android:gravitF67center7 /M L/)inear)aFoutM

*or this gri", =e take up the entire s'reen e;'ept &or =hat our sele'tion label reRuires. 5he number o& 'olumns is 'ompute" by An"roi" (android:num+olumns 6 7auto fit7) base" on our horiKontal spa'ing (android:horiKontal2pacing 6 7.dip7) an" 'olumns =i"th (android:column@idth 6 71--dip7), =ith the 'olumns absorbing any MslopM =i"th le&t o!er (android:stretch#ode 6 7column@idth7). 5he Ca!a 'o"e to 'on&igure the DridVieE is,
package com.commonsEare.android.gridJ import import import import import import import import android.app.ActivitFJ android.content.+onteGtJ android.os.4undleJ android.vieE.VieEJ android.Eidget.AdapterVieEJ android.Eidget.ArraFAdapterJ android.Eidget.DridVieEJ android.Eidget.&eGtVieEJ

public class Drid=emo eGtends ActivitF implements AdapterVieE."nItem2elected)istener : private &eGtVieE selectionJ private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ

*%&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

setContentViewP?.laFout.mainQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ DridVieE g6PDridVieEQ findViewByIdP?.id.gridQJ g.set$dapterPneE ArraFAdapterL2tringMPthis8 ?.laFout.cell8 itemsQQJ g.setOnItemSelectedListenerPthisQJ

public void onItemSelectedPAdapterVieELNM parent8 VieE v8 int position8 long idQ : selection.setTextPitemsApositionBQJ ; public void on&othingSelectedPAdapterVieELNM parentQ : selection.setTextP77QJ ;

5he gri" 'ells are "e&ine" by a separate res/laFout/cell.Gml &ile, re&eren'e" in our ArraFAdapter as ?.laFout.cell,
LNGml version671.-7 encoding67utf-,7NM L&eGtVieE Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGt2iKe671<dip7 /M

With the !erti'al spa'ing &rom the FML layout ( android:vertical2pacing 6 7<-dip7), the gri" o!er&lo=s the boun"aries o& the emulator7s s'reen,

*%-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

"igure 081 The (rid/emo sample application@ as initially launched

"igure 0:1 The same application@ scrolled to the bottom of the grid

*%%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

"ields5 ?o) With -0J !ess Typing!


5he Auto+omplete&eGtVieE is sort o& a hybri" bet=een the $dit&eGt (&iel") an" the 2pinner. With auto-'ompletion, as the user types, the te;t is treate" as a pre&i; &ilter, 'omparing the entere" te;t as a pre&i; against a list o& 'an"i"ates. Mat'hes are sho=n in a sele'tion list that &ol"s "o=n &rom the &iel". 5he user 'an either type out an entry (e.g., something not in the list) or 'hoose an entry &rom the list to be the !alue o& the &iel". sub'lasses $dit&eGt, so you 'an 'on&igure all the stan"ar" look-an"-&eel aspe'ts, su'h as &ont &a'e an" 'olor.
Auto+omplete&eGtVieE

0n a""ition, Auto+omplete&eGtVieE has a android:completion&hreshold property, to in"i'ate the minimum number o& 'hara'ters a user must enter be&ore the list &iltering begins. ?ou 'an gi!e Auto+omplete&eGtVieE an a"apter 'ontaining the list o& 'an"i"ate !alues !ia setAdapterPQ. +o=e!er, sin'e the user 'oul" type something not in the list, Auto+omplete&eGtVieE "oes not support sele'tion listeners. 0nstea", you 'an register a &eGt@atcher, like you 'an =ith any $dit&eGt, to be noti&ie" =hen the te;t 'hanges. 5hese e!ents =ill o''ur either be'ause o& manual typing or &rom a sele'tion &rom the "rop-"o=n list. 1elo= =e ha!e a &amiliar-looking FML layout, this time 'ontaining an Auto+omplete&eGtVieE (pulle" &rom the 2election/Auto+omplete sample appli'ation),
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&eGtVieE android:id67ORid/selection7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M

*%0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

LAuto+omplete&eGtVieE android:id67ORid/edit7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:completion&hreshold67C7/M L/)inear)aFoutM

5he 'orrespon"ing Ca!a 'o"e is,


package com.commonsEare.android.autoJ import import import import import import import import import android.app.ActivitFJ android.os.4undleJ android.teGt.$ditableJ android.teGt.&eGt@atcherJ android.vieE.VieEJ android.Eidget.AdapterVieEJ android.Eidget.ArraFAdapterJ android.Eidget.Auto+omplete&eGtVieEJ android.Eidget.&eGtVieEJ

public class Auto+omplete=emo eGtends ActivitF implements &eGt@atcher : private &eGtVieE selectionJ private Auto+omplete&eGtVieE editJ private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ edit6PAuto+omplete&eGtVieEQfindViewByIdP?.id.editQJ edit.addTextChangedListenerPthisQJ edit.set$dapterPneE ArraFAdapterL2tringMPthis8 android.?.laFout.simple dropdoEn item 1line8 itemsQQJ

public void onTextChangedP+har2eUuence s8 int start8 int before8 int countQ : selection.setTextPedit.getTextPQQJ ; public void 'eforeTextChangedP+har2eUuence s8 int start8 int count8 int afterQ : // needed for interface8 but not used ;

*%2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

public void afterTextChangedP$ditable sQ : // needed for interface8 but not used ;

5his time, our a'ti!ity implements &eGt@atcher, =hi'h means our 'allba'ks are on&eGt+hangedPQ, before&eGt+hangedPQ, an" after&eGt+hangedPQ. 0n this 'ase, =e are only intereste" in the &ormer, an" =e up"ate the sele'tion label to mat'h the Auto+omplete&eGtVieE7s 'urrent 'ontents. +ere =e ha!e the results,

"igure 2<1 The AutoComplete/emo sample application@ as initially launched

*%7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

"igure 2*1 The same application@ after a fe) matching letters )ere entered@ sho)ing the auto#complete drop#do)n

"igure 2&1 The same application@ after the auto#complete value )as selected

*%8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Selection Widgets

(alleries@ (ive ,r Take The Art


5he DallerF =i"get is not one or"inarily &oun" in 8$0 toolkits. 0t is, in e&&e't, a horiKontally-lai"-out listbo;. >ne 'hoi'e &ollo=s the ne;t a'ross the horiKontal plane, =ith the 'urrently-sele'te" item highlighte". >n an An"roi" "e!i'e, one rotates through the options through the le&t an" right @-pa" buttons. Compare" to the )istVieE, the DallerF takes up less s'reen spa'e =hile still sho=ing multiple 'hoi'es at one time (assuming they are short enough). Compare" to the 2pinner, the DallerF al=ays sho=s more than one 'hoi'e at a time. 5he Ruintessential e;ample use &or the DallerF is image pre!ie= S gi!en a 'olle'tion o& photos or i'ons, the DallerF lets people pre!ie= the pi'tures in the pro'ess o& 'hoosing one. Co"e-=ise, the DallerF =orks mu'h like a 2pinner or DridVieE. 0n your FML layout, you ha!e a &e= properties at your "isposal,
android:spacing

'ontrols the number o& pi;els bet=een entries in

the list

'ontrols =hat is use" to in"i'ate a sele'tion S this 'an either be a re&eren'e to a =raEable (see the resour'es 'hapter) or an 81 !alue in SAA??DD44 or similar notation
android:spinner2elector android:draE2elector"n&op in"i'ates i& the sele'tion bar (or =raEable) shoul" be "ra=n be&ore (false) or a&ter (true) "ra=ing the sele'te" 'hil" S i& you 'hoose true, be sure that your sele'tor has su&&i'ient

transparen'y to sho= the 'hil" through the sele'tor, other=ise users =ill not be able to rea" the sele'tion

*%:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 11

(etting "ancy With !ists

5he humble )istVieE is one o& the most important =i"gets in all o& An"roi", simply be'ause it is use" so &reRuently. Whether 'hoosing a 'onta't to 'all or an email message to &or=ar" or an ebook to rea", )istVieE =i"gets are employe" in a =i"e range o& a'ti!ities. >& 'ourse, it =oul" be ni'e i& they =ere more than Gust plain te;t. 5he goo" ne=s is that they 'an be as &an'y as you =ant, =ithin the limitations o& a mobile "e!i'e7s s'reen, o& 'ourse. +o=e!er, making them &an'y takes some =ork an" some &eatures o& An"roi" that =e =ill 'o!er in this 'hapter.

(etting To "irst Base


5he 'lassi' An"roi" )istVieE is a plain list o& te;t Z soli" but uninspiring. 5his is be'ause all =e ha!e han"e" to the )istVieE is a bun'h o& =or"s in an array, an" tol" An"roi" to use a simple built-in layout &or pouring those =or"s into a list. +o=e!er, you 'an ha!e a list =hose ro=s are ma"e up o& i'ons, or i'ons an" te;t, or 'he'kbo;es an" te;t, or =hate!er you =ant. 0t is merely a matter o& supplying enough "ata to the a"apter an" helping the a"apter to 'reate a ri'her set o& VieE obGe'ts &or ea'h ro=.

*0*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

*or e;ample, suppose you =ant a )istVieE =hose entries are ma"e up o& an i'on, &ollo=e" by some te;t. ?ou 'oul" 'onstru't a layout &or the ro= that looks like this, &oun" in res/laFout/roE.Gml in the 9ancF)ists/2tatic sample proGe't,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:orientation67horiKontal7 M LImageVieE android:id67ORid/icon7 android:padding67>dip7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:src67OdraEable/ok7 /M L&eGtVieE android:id67ORid/label7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGt2iKe67<-sp7 /M L/)inear)aFoutM

5his layout uses a )inear)aFout to set up a ro=, =ith the i'on on the le&t an" the te;t (in a ni'e big &ont) on the right. 1y "e&ault, though, An"roi" has no i"ea that you =ant to use this layout =ith your )istVieE. 5o make the 'onne'tion, you nee" to supply your Adapter =ith the resour'e 0@ o& the 'ustom layout sho=n abo!e,
public class 2tatic=emo eGtends )istActivitF : private &eGtVieE selectionJ private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ setList$dapterPneE ArraFAdapterL2tringMPthis8 ?.laFout.roE8 ?.id.label8

*0&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

itemsQQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ

public void onListItemClickP)istVieE parent8 VieE v8 int position8 long idQ : selection.setTextPitemsApositionBQJ ;

5his &ollo=s the general stru'ture &or the pre!ious List-ie= sample. 5he key in this e;ample is that you ha!e tol" ArraFAdapter that you =ant to use your 'ustom layout (?.laFout.roE) an" that the &eGtVieE =here the =or" shoul" go is kno=n as ?.id.label =ithin that 'ustom layout. emember, to re&eren'e a layout ( roE.Gml), use ?.laFout as a pre&i; on the base name o& the layout FML &ile (?.laFout.roE). 5he result is a )istVieE =ith i'ons "o=n the le&t si"e. 0n parti'ular, all the i'ons are the same,

"igure 2-1 The Static/emo application

*0-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

A /ynamic Presentation
5his te'hniRue S supplying an alternate layout to use &or ro=s S han"les simple 'ases !ery ni'ely. +o=e!er, =hat happens =hen =e =ant the i'on to 'hange base" on the ro= "ataH *or e;ample, perhaps =e =ant to use one i'on &or small =or"s an" a "i&&erent i'on &or large =or"s. 0n the 'ase o& ArraFAdapter, you =ill nee" to e;ten" it, 'reating your o=n 'ustom sub'lass (e.g., IconicAdapter) that in'orporates your business logi'. 0n parti'ular, it =ill nee" to o!erri"e getVieEPQ. 5he getVieEPQ metho" o& an Adapter is =hat an AdapterVieE (like )istVieE or 2pinner) 'alls =hen it nee"s the VieE asso'iate" =ith a gi!en pie'e o& "ata the Adapter is managing. 0n the 'ase o& an ArraFAdapter, getVieEPQ is 'alle" as nee"e" &or ea'h position in the array S Mget me the VieE &or the &irst ro=M, Mget me the VieE &or the se'on" ro=M, et'. *or e;ample, let us re=ork the abo!e 'o"e to use getVieEPQ, so =e 'an ha!e "i&&erent i'ons &or "i&&erent ro=s S in this 'ase, one i'on &or short =or"s an" one &or long =or"s (&rom the 9ancF)ists/=Fnamic sample proGe't),
public class =Fnamic=emo eGtends )istActivitF : &eGtVieE selectionJ private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ setList$dapterPneE Iconic$dapterPQQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ ; public void onListItemClickP)istVieE parent8 VieE v8 int position8 long idQ :

*0%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

selection.setTextPitemsApositionBQJ ; class IconicAdapter eGtends ArraFAdapterL2tringM : Iconic$dapterPQ : superP=Fnamic=emo.this8 ?.laFout.roE8 ?.id.label8 itemsQJ ; public VieE getViewPint position8 VieE convertVieE8 VieEDroup parentQ : VieE roE6super.getViewPposition8 convertVieE8 parentQJ ImageVieE icon6PImageVieEQroE.findViewByIdP?.id.iconQJ if PitemsApositionB.lengthPQM<Q : icon.setImage%esourceP?.draEable.deleteQJ ; else : icon.setImage%esourceP?.draEable.okQJ ; returnProEQJ ; ; ;

>ur IconicAdapter S an inner 'lass o& the a'ti!ity S has t=o metho"s. *irst, it has the 'onstru'tor, =hi'h Gust passes to ArraFAdapter the same "ata =e use" in the ArraFAdapter 'onstru'tor in 2tatic=emo. %e'on", it has our getVieEPQ implementation, =hi'h "oes t=o things, 1. 0t 'hains to the super'lass7 implementation o& getVieEPQ, =hi'h returns to us an instan'e o& our ro= VieE, as prepare" by ArraFAdapter. 0n parti'ular, our =or" has alrea"y been put into the &eGtVieE, sin'e ArraFAdapter "oes that normally.

2. 0t &in"s our ImageVieE an" applies a business rule to set =hi'h i'on shoul" be use", re&eren'ing one o& t=o "ra=able resour'es (?.draEable.ok an" ?.draEable.delete). 5his gi!es us,

*00

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

"igure 2%1 The /ynamic/emo application

nflating Co)s ,urselves


5he solution sho=n in this !ersion o& the =Fnamic=emo =orks &ine. +o=e!er, there =ill be times =hen ArraFAdapter 'annot e!en be use" &or setting up the basi's o& our ro=. *or e;ample, it is possible to ha!e a )istVieE =here the ro=s are materially "i&&erent, su'h as 'ategory hea"ers intersperse" among MregularM ro=s. 0n that 'ase, =e may nee" to "o all o& the =ork oursel!es, starting =ith in&lating our ro=s.

A Side= r A=out In.l tion


0n this 'ase, 6in&lation9 means the a't o& 'on!erting an FML layout spe'i&i'ation into the a'tual tree o& VieE obGe'ts the FML represents. 5his is un"oubte"ly a te"ious bit o& 'o"e, take an element, 'reate an instan'e o& the spe'i&ie" VieE 'lass, =alk the attributes, 'on!ert those into property setter 'alls, iterate o!er all 'hil" elements, lather, rinse, repeat.

*02

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

5he goo" ne=s is that the &ine &olk on the An"roi" team =rappe" all that up into a 'lass 'alle" )aFoutInflater that =e 'an use oursel!es. When it 'omes to &an'y lists, &or e;ample, =e =ill =ant to in&late VieEs &or ea'h ro= sho=n in the list, so =e 'an use the 'on!enient shorthan" o& the FML layout to "es'ribe =hat the ro=s are suppose" to look like. *or e;ample, let us look at a slightly "i&&erent implementation o& the =Fnamic=emo 'lass, &rom the 9ancF)ists/=Fnamic$G proGe't,
public class =Fnamic=emo eGtends )istActivitF : &eGtVieE selectionJ private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ setList$dapterPneE Iconic$dapterPQQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ ; public void onListItemClickP)istVieE parent8 VieE v8 int position8 long idQ : selection.setTextPitemsApositionBQJ ; class IconicAdapter eGtends ArraFAdapterL2tringM : Iconic$dapterPQ : superP=Fnamic=emo.this8 ?.laFout.roE8 itemsQJ ; public VieE getViewPint position8 VieE convertVieE8 VieEDroup parentQ : )aFoutInflater inflater6getLayoutInflaterPQJ VieE roE6inflater.inflateP?.laFout.roE8 parent8 falseQJ &eGtVieE label6P&eGtVieEQroE.findViewByIdP?.id.labelQJ label.setTextPitemsApositionBQJ ImageVieE icon6PImageVieEQroE.findViewByIdP?.id.iconQJ if PitemsApositionB.lengthPQM<Q : icon.setImage%esourceP?.draEable.deleteQJ ; else :

*07

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

icon.setImage%esourceP?.draEable.okQJ ; ; ; ; returnProEQJ

+ere =e in&late our ?.laFout.roE layout by use o& a )aFoutInflater obGe't, obtaine" &rom our ActivitF !ia get)aFoutInflaterPQ. 5his gi!es us a VieE obGe't ba'k =hi'h, in reality, is our )inear)aFout =ith an ImageVieE an" a &eGtVieE, Gust as ?.laFout.roE spe'i&ies. +o=e!er, rather than ha!ing to 'reate all those obGe'ts oursel!es an" =ire them together, the FML an" )aFoutInflater han"le the Mhea!y li&tingM &or us.

And "o#4 B c$ To +ur Story


%o =e ha!e use" )aFoutInflater to gi!e us a VieE representing the ro=. 5his ro= is MemptyM, sin'e the stati' layout &ile has no i"ea =hat a'tual "ata goes into the ro=. 0t is our Gob to 'ustomiKe an" populate the ro= as =e see &it be&ore returning it. %o, =e,

*ill in the te;t label into our label =i"get, using the =or" at the supplie" position %ee i& the =or" is longer than &our 'hara'ters an", i& so, =e &in" our ImageVieE i'on =i"get an" repla'e the sto'k resour'e =ith a "i&&erent one

5he user sees nothing "i&&erent S =e ha!e simply 'hange" ho= those ro=s are being 'reate". >b!iously, this =as a &airly 'ontri!e" e;ample, but you 'an see =here this te'hniRue 'oul" be use" to 'ustomiKe ro=s base" on any sort o& 'riteria.

*08

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

Better1 Stronger1 "aster1


5he getVieEPQ implementation sho=n in the 9ancF)ists/=Fnamic$G proGe't =orks, but is ine&&i'ient. E!ery time the user s'rolls, =e ha!e to 'reate a bun'h o& ne= VieE obGe'ts to a''ommo"ate the ne=ly-sho=n ro=s. 5his is ba". 0t might be ba" &or the imme"iate user e;perien'e, i& the list appears to be sluggish. More likely, though, it =ill be ba" "ue to battery usage S e!ery bit o& C#$ that is use" eats up the battery. 5his is 'ompoun"e" by the e;tra =ork the garbage 'olle'tor nee"s to "o to get ri" o& all those e;tra obGe'ts you 'reate. %o the less e&&i'ient your 'o"e, the more Rui'kly the phone7s battery =ill be "raine", an" the less happy the user =ill be. An" you =ant happy users, rightH %o, let us take a look at a &e= tri'ks to make your &an'y )istVieE =i"gets more e&&i'ient.

-sin! convert>ie#
5he getVieEPQ metho" re'ei!es, as one o& its parameters, a VieE name", by 'on!ention, convertVieE. %ometimes, convertVieE =ill be null. 0n those 'ases, you ha!e to 'reate a ne= ro= VieE &rom s'rat'h (e.g., !ia in&lation), Gust as =e "i" be&ore. +o=e!er, i& convertVieE is not null, then it is a'tually one o& your pre!iously-'reate" VieE obGe'ts: 5his =ill happen primarily =hen the user s'rolls the )istVieE S as ne= ro=s appear, An"roi" =ill attempt to re'y'le the !ie=s o& the ro=s that s'rolle" o&& the other en" o& the list, to sa!e you ha!ing to rebuil" them &rom s'rat'h. Assuming that ea'h o& your ro=s has the same basi' stru'ture, you 'an use findVieE4FIdPQ to get at the in"i!i"ual =i"gets that make up your ro= an"
*0:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

'hange their 'ontents, then return convertVieE &rom getVieEPQ, rather than 'reate a =hole ne= ro=. *or e;ample, here is the getVieEPQ implementation &rom last time, no= optimiKe" !ia convertVieE (&rom the 9ancF)ists/?ecFcling proGe't),
public class ?ecFcling=emo eGtends )istActivitF : private &eGtVieE selectionJ private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ setList$dapterPneE Iconic$dapterPQQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ ; public void onListItemClickP)istVieE parent8 VieE v8 int position8 long idQ : selection.setTextPitemsApositionBQJ ; class IconicAdapter eGtends ArraFAdapterL2tringM : Iconic$dapterPQ : superP?ecFcling=emo.this8 ?.laFout.roE8 itemsQJ ; public VieE getViewPint position8 VieE convertVieE8 VieEDroup parentQ : VieE roE6convertVieEJ if ProE66nullQ : )aFoutInflater inflater6getLayoutInflaterPQJ ; roE6inflater.inflateP?.laFout.roE8 parent8 falseQJ

&eGtVieE label6P&eGtVieEQroE.findViewByIdP?.id.labelQJ label.setTextPitemsApositionBQJ ImageVieE icon6PImageVieEQroE.findViewByIdP?.id.iconQJ if PitemsApositionB.lengthPQM<Q : icon.setImage%esourceP?.draEable.deleteQJ

*2<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

; else : icon.setImage%esourceP?.draEable.okQJ ; ; ; ; returnProEQJ

+ere, =e 'he'k to see i& the convertVieE is null an", i& so, =e then in&late our ro= S but i& it is not-null, =e Gust reuse it. 5he =ork to &ill in the 'ontents (i'on image, te;t) is the same in either 'ase. 5he a"!antage is that =e a!oi" the potentially-e;pensi!e in&lation step. 0n &a't, a''or"ing to statisti's 'ite" by 8oogle at the 2010 8oogle 0U> 'on&eren'e, a )istVieE that uses a re'y'ling )istAdapter =ill per&orm 1A0L &aster than one that "oes not. 0n &a't, &or 'omple; ro=s, that might un"erstate the bene&it. 2ot only is this &aster, but it uses mu'h less memory. Ea'h =i"get or 'ontainer S in other =or"s, ea'h sub'lass o& VieE S hol"s onto up to 2D1 o& "ata, not 'ounting things like images in ImageVieE =i"gets. Ea'h o& our ro=s, there&ore, might be as big as /D1. *or our list o& 2A nonsense =or"s, 'onsuming as mu'h as 1A0D1 &or a non-re'y'ling list (2A ro=s at /D1 ea'h) =oul" be ine&&i'ient but not a huge problem. A list o& 1,000 nonsense =or"s, though, 'onsuming as mu'h as /M1 o& AM, =oul" be a mu'h bigger issue. 1ear in min" that your appli'ation may only ha!e 1/M1 o& Ca!a heap memory to =ork =ith. e'y'ling allo=s us to han"le arbitrary list lengths =ith only as mu'h VieE memory 'onsume" as is nee"e" &or the ro=s !isible on s'reen. 2ote that ro= re'y'ling is only an issue i& =e are 'reating the ro=s oursel&. 0& =e let ArraFAdapter 'reate the ro=s, by le!eraging its implementation o& getVieEPQ as sho=n in the 9ancF)ists/=Fnamic proGe't, then it "eals =ith the re'y'ling.

-sin! the Holder P ttern


Another some=hat e;pensi!e operation =e "o a lot =ith &an'y !ie=s is 'all findVieE4FIdPQ. 5his "i!es into our in&late" ro= an" pulls out =i"gets by
*2*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

their assigne" i"enti&iers, so =e 'an 'ustomiKe the =i"get 'ontents (e.g., 'hange the te;t o& a &eGtVieE, 'hange the i'on in an ImageVieE). %in'e findVieE4FIdPQ 'an &in" =i"gets any=here in the tree o& 'hil"ren o& the ro=7s root VieE, this 'oul" take a &air number o& instru'tions to e;e'ute, parti'ularly i& =e keep ha!ing to re-&in" =i"gets =e ha" &oun" on'e be&ore. 0n some 8$0 toolkits, this problem is a!oi"e" by ha!ing the 'omposite VieE obGe'ts, like our ro=s, be "e'lare" totally in program 'o"e (in this 'ase, Ca!a). 5hen, a''essing in"i!i"ual =i"gets is merely the matter o& 'alling a getter or a''essing a &iel". An" you 'an 'ertainly "o that =ith An"roi", but the 'o"e gets rather !erbose. What =oul" be ni'e is a =ay =here =e 'an still use the layout FML yet 'a'he our ro=7s key 'hil" =i"gets so =e only ha!e to &in" them on'e. 5hat7s =here the hol"er pattern 'omes into play, in a 'lass =e7ll 'all VieE!older. All VieE obGe'ts ha!e get&agPQ an" set&agPQ metho"s. 5hese allo= you to asso'iate an arbitrary obGe't =ith the =i"get. What the hol"er pattern "oes is use that MtagM to hol" an obGe't that, in turn, hol"s ea'h o& the 'hil" =i"gets o& interest. 1y atta'hing that hol"er to the ro= VieE, e!ery time =e use the ro=, =e alrea"y ha!e a''ess to the 'hil" =i"gets =e 'are about, =ithout ha!ing to 'all findVieE4FIdPQ again. %o, let[s take a look at one o& these hol"er 'lasses (taken &rom the 9ancF)ists/VieE!older sample proGe't),
package com.commonsEare.android.fancFlists.fiveJ import android.vieE.VieEJ import android.Eidget.ImageVieEJ class VieE!older : ImageVieE icon6nullJ View(olderPVieE baseQ : this.icon6PImageVieEQbase.findViewByIdP?.id.iconQJ ;

*2&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

VieE!older

hol"s onto the 'hil" =i"gets, initialiKe" !ia findVieE4FIdPQ in its 'onstru'tor. 5he =i"gets are simply pa'kage-prote'te" "ata members, a''essible &rom other 'lasses in this proGe't...su'h as a VieE!older=emo a'ti!ity. 0n this 'ase, =e are only hol"ing onto one =i"get S the i'on S sin'e =e =ill let ArrayA"apter han"le our label &or us. $sing VieE!older is a matter o& 'reating an instan'e =hene!er =e in&late a ro= an" atta'hing sai" instan'e to the ro= VieE !ia set&agPQ, as sho=n in this re=rite o& getVieEPQ, &oun" in VieE!older=emo,
public VieE getViewPint position8 VieE convertVieE8 VieEDroup parentQ : VieE roE6super.getViewPposition8 convertVieE8 parentQJ VieE!older holder6PVieE!olderQroE.getTagPQJ if Pholder66nullQ : holder6neE View(olderProEQJ roE.setTagPholderQJ ; if PgetModelPpositionQ.lengthPQM<Q : holder.icon.setImage%esourceP?.draEable.deleteQJ ; else : holder.icon.setImage%esourceP?.draEable.okQJ ; returnProEQJ ;

+ere, =e go ba'k to allo=ing ArraFAdapter to han"le our ro= in&lation an" re'y'ling &or us. 0& the 'all to get&agPQ on the ro= returns null, =e kno= =e nee" to 'reate a ne= VieE!older, =hi'h =e then atta'h to the ro= !ia set&agPQ &or later reuse. 5hen, a''essing the 'hil" =i"gets is merely a matter o& a''essing the "ata members on the hol"er. 5he &irst time the )istVieE is "isplaye", all ne= ro=s nee" to be in&late", an" =e =in" up 'reating a VieE!older &or ea'h. As the user s'rolls, ro=s get re'y'le", an" =e 'an reuse their 'orrespon"ing VieE!older =i"get 'a'hes. $sing a hol"er helps per&orman'e, but the e&&e't is not as "ramati'. Whereas re'y'ling 'an gi!e you a 1A0L per&orman'e impro!ement, a""ing in a hol"er in'reases the impro!ement to 14AL. +en'e, =hile you may =ish to implement re'y'ling up &ront =hen you 'reate your a"apter, a""ing in a
*2-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

hol"er might be something you "eal =ith later, =hen you are =orking spe'i&i'ally on per&orman'e tuning. 0n this parti'ular 'ase, =e 'ertainly 'oul" simpli&y all o& this, by skipping VieE!older an" using get&agPQ an" set&agPQ =ith the ImageVieE "ire'tly. 5his e;ample is =ritten as it is to "emonstrate ho= to han"le a more 'omple; s'enario, =here you might ha!e se!eral =i"gets that =oul" nee" to be 'a'he" !ia the hol"er pattern.

nteractive Co)s
Lists =ith pretty i'ons ne;t to them are all &ine an" =ell. 1ut, 'an =e 'reate )istVieE =i"gets =hose ro=s 'ontain intera'ti!e 'hil" =i"gets instea" o& Gust passi!e =i"gets like &eGtVieE an" ImageVieEH *or e;ample, there is a ?ating4ar =i"get that allo=s users to assign a rating by 'li'king on a set o& star i'ons. Coul" =e 'ombine the ?ating4ar =ith te;t in or"er to allo= people to s'roll a list o&, say, songs an" rate them right insi"e the listH 5here is goo" ne=s an" ba" ne=s. 5he goo" ne=s is that intera'ti!e =i"gets in ro=s =ork Gust &ine. 5he ba" ne=s is that it is a little tri'ky, spe'i&i'ally =hen it 'omes to taking a'tion =hen the intera'ti!e =i"get7s state 'hanges (e.g., a !alue is type" into a &iel"). We nee" to store that state some=here, sin'e our ?ating4ar =i"get =ill be re'y'le" =hen the )istVieE is s'rolle". We nee" to be able to set the ?ating4ar state base" upon the a'tual =or" =e are !ie=ing as the ?ating4ar is re'y'le", an" =e nee" to sa!e the state =hen it 'hanges so it 'an be restore" =hen this parti'ular ro= is s'rolle" ba'k into !ie=. What makes this interesting is that, by "e&ault, the ?ating4ar has absolutely no i"ea =hat item in the ArraFAdapter it represents. A&ter all, the ?ating4ar is Gust a =i"get, use" in a ro= o& a )istVieE. We nee" to tea'h the ro=s =hi'h item in the ArraFAdapter they are 'urrently "isplaying, so =hen their ?ating4ar is 'he'ke", they kno= =hi'h item7s state to mo"i&y.

*2%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

%o, let7s see ho= this is "one, using the a'ti!ity in the 9ancF)ists/?ate)ist sample proGe't. We =ill use the same basi' 'lasses as our pre!ious "emo S =e are sho=ing a list o& nonsense =or"s, =hi'h you 'an then rate. 0n a""ition, =or"s gi!en a top rating are put in all 'aps,
package com.commonsEare.android.fancFlists.siGJ import import import import import import import import import import import import import android.app.ActivitFJ android.os.4undleJ android.app.)istActivitFJ android.vieE.VieEJ android.vieE.VieEDroupJ android.vieE.)aFoutInflaterJ android.Eidget.AdapterVieEJ android.Eidget.ArraFAdapterJ android.Eidget.?ating4arJ android.Eidget.)inear)aFoutJ android.Eidget.)istVieEJ android.Eidget.&eGtVieEJ java.util.ArraF)istJ

public class ?ate)ist=emo eGtends )istActivitF : private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ ArraF)istL?oE#odelM list6neE ArraF)istL?oE#odelMPQJ for P2tring s : itemsQ : list.addPneE %owModelPsQQJ ; ; setList$dapterPneE %ating$dapterPlistQQJ

private ?oE#odel getModelPint positionQ : returnPPP?atingAdapterQgetList$dapterPQQ.getItemPpositionQQJ ; class ?atingAdapter eGtends ArraFAdapterL?oE#odelM : %ating$dapterPArraF)istL?oE#odelM listQ : superP?ate)ist=emo.this8 ?.laFout.roE8 ?.id.label8 listQJ ; public VieE getViewPint position8 VieE convertVieE8

*20

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

VieEDroup parentQ : VieE roE6super.getViewPposition8 convertVieE8 parentQJ VieE!older holder6PVieE!olderQroE.getTagPQJ if Pholder66nullQ : holder6neE View(olderProEQJ roE.setTagPholderQJ ?ating4ar."n?ating4ar+hange)istener l6 neE ?ating4ar.On%atingBarChangeListenerPQ : public void on%atingChangedP?ating4ar rating4ar8 float rating8 boolean from&ouchQ : Integer mF(osition6PIntegerQrating4ar.getTagPQJ ?oE#odel model6getModelPmF(ositionQJ model.rating6ratingJ )inear)aFout parent6P)inear)aFoutQrating4ar.get)arentPQJ &eGtVieE label6P&eGtVieEQparent.findViewByIdP?.id.labelQJ ; ;J ; holder.rate.setOn%atingBarChangeListenerPlQJ label.setTextPmodel.toStringPQQJ

?oE#odel model6getModelPpositionQJ holder.rate.setTagPneE IntegerPpositionQQJ holder.rate.set%atingPmodel.ratingQJ ; ; class ?oE#odel : 2tring labelJ float rating6>.-fJ %owModelP2tring labelQ : this.label6labelJ ; public 2tring toStringPQ : if PratingM6C.-Q : returnPlabel.to*pperCasePQQJ ; returnPlabelQJ ; ; ; returnProEQJ

*22

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

+ere is =hat is "i&&erent in this a'ti!ity an" getVieEPQ implementation than be&ore, 1. While =e are still using 2tringVW items as the list o& nonsense =or"s, rather than pour that 2tring array straight into an ArraFAdapter, =e turn it into a list o& ?oE#odel obGe'ts. ?oE#odel is the mutable mo"el, it hol"s the nonsense =or" plus the 'urrent 'he'ke" state. 0n a real system, these might be obGe'ts populate" &rom a "atabase, an" the properties =oul" ha!e more business meaning.

2. $tility metho"s like on)istItem+lickPQ ha" to be up"ate" to re&le't the 'hange &rom a pure-2tring mo"el to use a ?oE#odel. .. 5he ArraFAdapter sub'lass (?atingAdapter), in getVieEPQ, lets ArraFAdapter in&late an" re'y'le the ro=, then 'he'ks to see i& =e ha!e a VieE!older in the ro=7s tag. 0& not, =e 'reate a ne= VieE!older an" asso'iate it =ith the ro=. *or the ro=7s ?ating4ar, =e a"" an anonymous on?ating+hangedPQ listener that looks at the ro=7s tag (get&agPQ) an" 'on!erts that into an Integer, representing the position =ithin the ArraFAdapter that this ro= is "isplaying. $sing that, the rating bar 'an get the a'tual ?oE#odel &or the ro= an" up"ate the mo"el base" upon the ne= state o& the rating bar. 0t also up"ates the te;t a"Ga'ent to the ?ating4ar =hen 'he'ke" to mat'h the rating bar state. <. We al=ays make sure that the ?ating4ar has the proper 'ontents an" has a tag (!ia set&agPQ) pointing to the position in the a"apter the ro= is "isplaying. 5he ro= layout is !ery simple, Gust a ?ating4ar an" a &eGtVieE insi"e a )inear)aFout,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:orientation67horiKontal7 M L?ating4ar android:id67ORid/rate7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:num2tars67C7

*27

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

android:step2iKe6717 android:rating67>7 /M L&eGtVieE android:id67ORid/label7 android:padding67>dip7 android:teGt2iKe671,sp7 android:laFout gravitF67leftWcenter vertical7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7/M L/)inear)aFoutM

5he VieE!older is similarly simple, Gust e;tra'ting the ?ating4ar out o& the ro= VieE &or 'a'hing purposes,
package com.commonsEare.android.fancFlists.siGJ import android.vieE.VieEJ import android.Eidget.?ating4arJ class VieE!older : ?ating4ar rate6nullJ View(olderPVieE baseQ : this.rate6P?ating4arQbase.findViewByIdP?.id.rateQJ ; ;

An" the result is =hat you =oul" e;pe't, !isually,

*28

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

(etting "ancy With !ists

"igure 201 The Cate!ist/emo application@ as initially launched

5his in'lu"es the toggle" rating bars turning their =or"s into all 'aps,

"igure 221 The same application@ sho)ing a top#rated )ord

*2:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 12

Still +ore Widgets and Containers

5his book has 'o!ere" a number o& =i"gets an" 'ontainers so &ar. 5his 'hapter is the last that &o'uses e;'lusi!ely on =i"gets an" 'ontainers, 'o!ering a number o& popular options, &rom "ate an" time =i"gets to tabs. A&ter this 'hapter, =e =ill still intro"u'e the o''asional ne= =i"get, but in the 'onte;t o& some other topi', su'h as intro"u'ing the (rogress4ar in the 'hapter on threa"s.

Pick and Choose


With limite"-input "e!i'es like phones, ha!ing =i"gets an" "ialogs that are a=are o& the type o& stu&& somebo"y is suppose" to be entering is !ery help&ul. 0t minimiKes keystrokes an" s'reen taps, plus re"u'es the 'han'e o& making some sort o& error (e.g., entering a letter somepla'e =here only numbers are e;pe'te"). As sho=n pre!iously, $dit&eGt has 'ontent-a=are &la!ors &or entering in numbers, phone numbers, et'. An"roi" also supports =i"gets ( =ate(icker, &ime(icker) an" "ialogs (=ate(icker=ialog, &ime(icker=ialog) &or helping users enter "ates an" times. 5he =ate(icker an" =ate(icker=ialog allo= you to set the starting "ate &or the sele'tion, in the &orm o& a year, month, an" "ay o& month !alue. 2ote

*7*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

that the month runs &rom - &or Canuary through 11 &or @e'ember. Most importantly, both let you pro!i"e a 'allba'k obGe't ( "n=ate+hanged)istener or "n=ate2et)istener) =here you are in&orme" o& a ne= "ate sele'te" by the user. 0t is up to you to store that "ate somepla'e, parti'ularly i& you are using the "ialog, sin'e there is no other =ay &or you to get at the 'hosen "ate later on. %imilarly, &ime(icker an" &ime(icker=ialog let you,

set the initial time the user 'an a"Gust, in the &orm o& an hour ( through >C) an" a minute (- through .*) in"i'ate i& the sele'tion shoul" be in 12-hour mo"e =ith an AMP#M toggle, or in 2<-hour mo"e (=hat in the $% is thought o& as Mmilitary timeM an" mu'h o& the rest o& the =orl" is thought o& as Mthe =ay times are suppose" to beM) pro!i"e 'allba'k obGe't ("n&ime+hanged)istener or "n&ime2et)istener) to be noti&ie" o& =hen the user has 'hosen a ne= time, =hi'h is supplie" to you in the &orm o& an hour an" minute a

*or e;ample, &rom the 9ancF/+hrono sample proGe't, here7s a tri!ial layout 'ontaining a label an" t=o buttons S the buttons =ill pop up the "ialog &la!ors o& the "ate an" time pi'kers,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&eGtVieE android:id67ORid/dateAnd&ime7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L4utton android:id67ORid/date4tn7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:teGt672et the =ate7 android:on+lick67choose=ate7 /M L4utton android:id67ORid/time4tn7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7

*7&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

android:teGt672et the &ime7 android:on+lick67choose&ime7 /M L/)inear)aFoutM

5he more interesting stu&& 'omes in the Ca!a sour'e,


package com.commonsEare.android.chronoJ import import import import import import import import import import android.app.ActivitFJ android.os.4undleJ android.app.=ate(icker=ialogJ android.app.&ime(icker=ialogJ android.vieE.VieEJ android.Eidget.=ate(ickerJ android.Eidget.&ime(ickerJ android.Eidget.&eGtVieEJ java.teGt.=ate9ormatJ java.util.+alendarJ

public class +hrono=emo eGtends ActivitF : =ate9ormat fmt=ateAnd&ime6=ate9ormat.getDateTimeInstancePQJ &eGtVieE dateAnd&ime)abelJ +alendar dateAnd&ime6+alendar.getInstancePQJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ dateAnd&ime)abel6P&eGtVieEQfindViewByIdP?.id.dateAnd&imeQJ updateLa'elPQJ ; public void chooseDatePVieE vQ : neE Date)ickerDialogP+hrono=emo.this8 d8 dateAnd&ime.getP+alendar.5$A?Q8 dateAnd&ime.getP+alendar.#"%&!Q8 dateAnd&ime.getP+alendar.=A5 "9 #"%&!QQ .showPQJ ; public void chooseTimePVieE vQ : neE Time)ickerDialogP+hrono=emo.this8 t8 dateAnd&ime.getP+alendar.!"3? "9 =A5Q8 dateAnd&ime.getP+alendar.#I%3&$Q8 trueQ .showPQJ ; private void updateLa'elPQ : dateAnd&ime)abel.setTextPfmt=ateAnd&ime

*7-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

.formatPdateAnd&ime.getTimePQQQJ ; : =ate(icker=ialog."n=ate2et)istener d6neE =ate(icker=ialog.OnDateSetListenerPQ public void onDateSetP=ate(icker vieE8 int Fear8 int month"f5ear8 int daF"f#onthQ : dateAnd&ime.setP+alendar.5$A?8 FearQJ dateAnd&ime.setP+alendar.#"%&!8 month"f5earQJ dateAnd&ime.setP+alendar.=A5 "9 #"%&!8 daF"f#onthQJ updateLa'elPQJ ;

;J :

&ime(icker=ialog."n&ime2et)istener t6neE &ime(icker=ialog.OnTimeSetListenerPQ public void onTimeSetP&ime(icker vieE8 int hour"f=aF8 int minuteQ : dateAnd&ime.setP+alendar.!"3? "9 =A58 hour"f=aFQJ dateAnd&ime.setP+alendar.#I%3&$8 minuteQJ updateLa'elPQJ ;

;J ;

5he Mmo"elM &or this a'ti!ity is Gust a +alendar instan'e, initially set to be the 'urrent "ate an" time. We pour it into the !ie= !ia a =ate9ormat &ormatter. 0n the update)abelPQ metho", =e take the 'urrent +alendar, &ormat it, an" put it in the &eGtVieE. Ea'h button has a 'orrespon"ing metho" that =ill get 'ontrol =hen the user 'li'ks it (choose=atePQ an" choose&imePQ). When the button is 'li'ke", either a =ate(icker=ialog or a &ime(icker=ialog is sho=n. 0n the 'ase o& the =ate(icker=ialog, =e gi!e it a "n=ate2et)istener 'allba'k that up"ates the +alendar =ith the ne= "ate (year, month, "ay o& month). We also gi!e the "ialog the last-sele'te" "ate, getting the !alues out o& the +alendar. 0n the 'ase o& the &ime(icker=ialog, it gets a "n&ime2et)istener 'allba'k to up"ate the time portion o& the +alendar, the last-sele'te" time, an" a true in"i'ating =e =ant 2<-hour mo"e on the time sele'tor. With all this =ire" together, the resulting a'ti!ity looks like this,

*7%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

"igure 271 The Chrono/emo sample application@ as initially launched

"igure 281 The same application@ sho)ing the date picker dialog

*70

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

"igure 2:1 The same application@ sho)ing the time picker dialog

Time 9eeps "lo)ing !ike a Civer


0& you =ant to "isplay the time, rather than ha!e users enter the time, you may =ish to use the =igital+lock or Analog+lock =i"gets. 5hese are e;tremely easy to use, as they automati'ally up"ate =ith the passage o& time. All you nee" to "o is put them in your layout an" let them "o their thing. *or e;ample, &rom the 9ancF/+locks sample appli'ation, here is an FML layout 'ontaining both =igital+lock an" Analog+lock,
LNGml version671.-7 encoding67utf-,7NM L?elative)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M LAnalog+lock android:id67ORid/analog7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:laFout center!oriKontal67true7 android:laFout align(arent&op67true7 /M L=igital+lock android:id67ORid/digital7

*72

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

android:laFout android:laFout android:laFout android:laFout /M L/?elative)aFoutM

Eidth67Erap content7 height67Erap content7 center!oriKontal67true7 beloE67Oid/analog7

Without any Ca!a 'o"e other than the generate" stub, =e 'an buil" this proGe't an" get the &ollo=ing a'ti!ity,

"igure 7<1 The Clocks/emo sample application

0& you are looking &or more o& a timer, +hronometer may be o& interest. With a +hronometer, you 'an tra'k elapse" time &rom a starting point. ?ou simply tell it =hen to startPQ an" stopPQ, an" possibly o!erri"e the &ormat string that "isplays the te;t,

*77

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

"igure 7*1 The ;ie)sKChronometer AP /emo from the Android &1< S/9

Seeking Cesolution
5he 2eek4ar is an input =i"get, allo=ing the user to sele't a !alue along a range o& possible !alues,

*78

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

"igure 7&1 The ;ie)sKSeekBar AP /emo from the Android &1< S/9

5he user 'an either "rag the MthumbM or 'li'k on either si"e o& it to reposition the thumb. 5he thumb then points to a parti'ular !alue along a range. 5hat range =ill be - to some ma;imum !alue, 1-- by "e&ault, that you 'ontrol !ia a 'all to set#aGPQ. ?ou 'an &in" out =hat the 'urrent position is !ia get(rogressPQ, or &in" out =hen the user makes a 'hange to the thumb7s position by registering a listener !ia set"n2eek4ar+hange)istenerPQ. We sa= another !ariation on this theme =ith the ?ating4ar in the pre!ious 'hapter.

Putting t ,n +y Tab
5he general An"roi" philosophy is to keep a'ti!ities short an" s=eet. 0& there is more in&ormation than 'an reasonably &it on one s'reen, albeit perhaps =ith s'rolling, then it perhaps belongs in another a'ti!ity ki'ke" o&& !ia an Intent, as =ill be "es'ribe" later in this book. +o=e!er, that 'an be 'ompli'ate" to set up. Moreo!er, sometimes there legitimately is a lot o& in&ormation that nee"s to be 'olle'te" to be pro'esse" as an atomi' operation.
*7:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

0n a tra"itional $0, you might use tabs to a''omplish this en", su'h as a J&abbed(ane in Ca!aP%=ing. 0n An"roi", you no= ha!e an option o& using a &ab!ost 'ontainer in mu'h the same =ay S a portion o& your a'ti!ity7s s'reen is taken up =ith tabs =hi'h, =hen 'li'ke", s=ap out part o& the !ie= an" repla'e it =ith something else. *or e;ample, you might ha!e an a'ti!ity =ith a tab &or entering a lo'ation an" a se'on" tab &or sho=ing a map o& that lo'ation. %ome 8$0 toolkits re&er to MtabsM as being Gust the things a user 'li'ks on to toggle &rom one !ie= to another. %ome toolkits re&er to MtabsM as being the 'ombination o& the 'li'kable button-ish element an" the 'ontent that appears =hen that tab is 'hosen. An"roi" treats the tab buttons an" 'ontents as "is'rete entities, so =e =ill 'all them Mtab buttonsM an" Mtab 'ontentsM in this se'tion.

The Pieces
5here are a &e= =i"gets an" 'ontainers you nee" to use in or"er to set up a tabbe" portion o& a !ie=,
&ab!ost is the o!erar'hing 'ontainer &or the tab buttons an" tab 'ontents &ab@idget implements the ro= o& tab buttons, =hi'h 'ontain te;t labels an" optionally 'ontain i'ons

is the 'ontainer &or the tab 'ontentsT ea'h tab 'ontent is a 'hil" o& the 9rame)aFout
9rame)aFout

5his is similar to the approa'h that MoKilla7s F$L takes. 0n F$L7s 'ase, the tabboG element 'orrespon"s to An"roi"7s &ab!ost, the tabs element 'orrespon"s to &ab@idget, an" tabpanels 'orrespon"s to the 9rame)aFout. *or e;ample, here is a layout "e&inition &or a tabbe" a'ti!ity, &rom 9ancF/&ab,
LNGml version671.-7 encoding67utf-,7NM L&ab!ost Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/tabhost7

*8<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

android:laFout Eidth67fill parent7 android:laFout height67fill parent7M L)inear)aFout android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7M L&ab@idget android:id67Oandroid:id/tabs7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L9rame)aFout android:id67Oandroid:id/tabcontent7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7M LAnalog+lock android:id67ORid/tab17 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 /M L4utton android:id67ORid/tab>7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:teGt67A semi-random button7 /M L/9rame)aFoutM L/)inear)aFoutM L/&ab!ostM

2ote that the &ab@idget an" 9rame)aFout are in"ire't 'hil"ren o& the &ab!ost, an" the 9rame)aFout itsel& has 'hil"ren representing the !arious tabs. 0n this 'ase, there are t=o tabs, a 'lo'k an" a button. 0n a more 'ompli'ate" s'enario, the tabs are probably some &orm o& 'ontainer (e.g., )inear)aFout) =ith their o=n 'ontents.

,irin! It To!ether
?ou 'an put these =i"gets in a regular ActivitF or a &abActivitF. &abActivitF, like )istActivitF, =raps a 'ommon $0 pattern (a'ti!ity ma"e up entirely o& tabs) into a pattern-a=are a'ti!ity sub'lass. 0& you =ish to use the &abActivitF, you must gi!e the &ab!ost an android:id o& Oandroid:id/tabhost. Con!ersely, i& you "o not =ish to use &abActivitF, you nee" to get your &ab!ost !ia findVieE4FIdPQ, then 'all setupPQ on the &ab!ost, be&ore you "o anything else. 5he rest o& the Ca!a 'o"e nee"s to tell the &ab!ost =hat !ie=s represent the tab 'ontents an" =hat the tab buttons shoul" look like. 5his is all =rappe"
*8*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

up in &ab2pec obGe'ts. ?ou get a &ab2pec instan'e &rom the host !ia neE&ab2pecPQ, &ill it out, then a"" it to the host in the proper seRuen'e. 5he t=o key metho"s on &ab2pec are,
set+ontentPQ, =here you in"i'ate =hat goes in the tab 'ontent &or this tab, typi'ally the android:id o& the !ie= you =ant sho=n =hen this tab is sele'te" setIndicatorPQ,

=here you pro!i"e the 'aption &or the tab button an", in some &la!ors o& this metho", supply a =raEable to represent the i'on &or the tab

2ote that tab Min"i'atorsM 'an a'tually be !ie=s in their o=n right, i& you nee" more 'ontrol than a simple label an" optional i'on. Also note that you must 'all setupPQ on the &ab!ost be&ore 'on&iguring any o& these &ab2pec obGe'ts. 5he 'all to setupPQ is not nee"e" i& you are using the &abActivitF base 'lass &or your a'ti!ity. *or e;ample, here is the Ca!a 'o"e to =ire together the tabs &rom the pre'e"ing layout e;ample,
package com.commonsEare.android.fancFJ import android.app.ActivitFJ import android.os.4undleJ import android.Eidget.&ab!ostJ public class &ab=emo eGtends ActivitF : O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ &ab!ost tabs6P&ab!ostQfindViewByIdP?.id.tabhostQJ tabs.setupPQJ &ab!ost.&ab2pec spec6tabs.newTa'SpecP7tag17QJ spec.setContentP?.id.tab1QJ spec.setIndicatorP7+lock7QJ tabs.addTa'PspecQJ

*8&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

spec6tabs.newTa'SpecP7tag>7QJ spec.setContentP?.id.tab>QJ spec.setIndicatorP74utton7QJ tabs.addTa'PspecQJ ; ;

We &in" our &ab!ost !ia the &amiliar findVieE4FIdPQ metho", then ha!e it setupPQ. A&ter that, =e get a &ab2pec !ia neE&ab2pecPQ, supplying a tag =hose purpose is unkno=n at this time. 8i!en the spe', you 'all set+ontentPQ an" setIndicatorPQ, then 'all add&abPQ ba'k on the &ab!ost to register the tab as a!ailable &or use. *inally, you 'an 'hoose =hi'h tab is the one to sho= !ia set+urrent&abPQ, pro!i"ing the --base" in"e; o& the tab. 5he resultH

"igure 7-1 The Tab/emo sample application@ sho)ing the first tab

*8-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

"igure 7%1 The same application@ sho)ing the second tab

Addin! Them -p
&ab@idget

is set up to allo= you to easily "e&ine tabs at 'ompile time. +o=e!er, sometimes, you =ant to a"" tabs to your a'ti!ity "uring runtime. *or e;ample, imagine an email 'lient =here in"i!i"ual email messages get opene" in their o=n tab, &or easy toggling bet=een messages. 0n this 'ase, you "o not kno= ho= many tabs or =hat their 'ontents =ill be until runtime, =hen the user 'hooses to open a message. *ortunately, An"roi" also supports a""ing tabs "ynami'ally at runtime.

A""ing tabs "ynami'ally at runtime =orks mu'h like the 'ompile-time tabs sho=n abo!e, e;'ept you use a "i&&erent &la!or o& set+ontentPQ, one that takes a &ab!ost.&ab+ontent9actorF instan'e. 5his is Gust a 'allba'k that =ill be in!oke" S you pro!i"e an implementation o& create&ab+ontentPQ an" use it to buil" an" return the VieE that be'omes the 'ontent o& the tab. Let us take a look at an e;ample (9ancF/=Fnamic&ab).

*8%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

*irst, here is some layout FML &or an a'ti!ity that sets up the tabs an" "e&ines one tab, 'ontaining a single button,
LNGml version671.-7 encoding67utf-,7NM L&ab!ost Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/tabhost7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7M L)inear)aFout android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7M L&ab@idget android:id67Oandroid:id/tabs7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L9rame)aFout android:id67Oandroid:id/tabcontent7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7M L4utton android:id67ORid/buttontab7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:teGt67A semi-random button7 android:on+lick67add&ab7 /M L/9rame)aFoutM L/)inear)aFoutM L/&ab!ostM

What =e =ant to "o is a"" ne= tabs =hene!er the button is 'li'ke". 5hat 'an be a''omplishe" in Gust a &e= lines o& 'o"e,
package com.commonsEare.android.dFnamictabJ import import import import import android.app.ActivitFJ android.os.4undleJ android.vieE.VieEJ android.Eidget.Analog+lockJ android.Eidget.&ab!ostJ

public class =Fnamic&ab=emo eGtends ActivitF : private &ab!ost tabs6nullJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ tabs6P&ab!ostQfindViewByIdP?.id.tabhostQJ tabs.setupPQJ

*80

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

&ab!ost.&ab2pec spec6tabs.newTa'SpecP7buttontab7QJ spec.setContentP?.id.buttontabQJ spec.setIndicatorP74utton7QJ tabs.addTa'PspecQJ ; public void addTa'PVieE vQ : &ab!ost.&ab2pec spec6tabs.newTa'SpecP7tag17QJ spec.setContentPneE &ab!ost.Ta'Content"actoryPQ : public VieE createTa'ContentP2tring tagQ : returnPneE $nalogClockP=Fnamic&ab=emo.thisQQJ ; ;QJ spec.setIndicatorP7+lock7QJ tabs.addTa'PspecQJ

; ;

0n our button7s add&abPQ 'allba'k, =e 'reate a &ab!ost.&ab2pec obGe't an" gi!e it an anonymous &ab!ost.&ab+ontent9actorF. 5he &a'tory, in turn, returns the VieE to be use" &or the tab S in this 'ase, Gust an Analog+lock. 5he logi' &or 'onstru'ting the tab[s VieE 'oul" be mu'h more elaborate, su'h as using )aFoutInflater to 'onstru't a !ie= &rom layout FML. 0nitially, =hen the a'ti!ity is laun'he", =e Gust ha!e the one tab,

*82

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

"igure 701 The /ynamicTab application@ )ith the single initial tab

"igure 721 The /ynamicTab application@ )ith three dynamically#created tabs

*87

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

"lipping Them ,ff


%ometimes, you =ant the o!erall e&&e't o& tabs (only some VieEs !isible at a time), but you "o not =ant the a'tual $0 implementation o& tabs. Maybe the tabs take up too mu'h s'reen spa'e. Maybe you =ant to s=it'h bet=een perspe'ti!es base" on a gesture or a "e!i'e shake. >r maybe you Gust like being "i&&erent. 5he goo" ne=s is that the guts o& the !ie=-&lipping logi' &rom tabs 'an be &oun" in the VieE9lipper 'ontainer, =hi'h 'an be use" in other =ays than the tra"itional tab. inherits &rom 9rame)aFout, Gust like =e use" to "es'ribe the innar"s o& a &ab@idget. +o=e!er, initially, it Gust sho=s the &irst 'hil" !ie=. 0t is up to you to arrange &or the !ie=s to &lip, either manually by user intera'tion, or automati'ally !ia a timer.
VieE9lipper

*or e;ample, here is a layout &or a simple a'ti!ity (9ancF/9lipper1) using a 4utton an" a VieE9lipper,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L4utton android:id67ORid/flip me7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:teGt679lip #eX7 android:on+lick67flip7 /M LVieE9lipper android:id67ORid/details7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&eGtVieE android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:teGt2tFle67bold7 android:teGt+olor67S99--99--7 android:teGt67&his is the first panel7 /M L&eGtVieE

*88

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:teGt2tFle67bold7 android:teGt+olor67S9999----7 android:teGt67&his is the second panel7 /M L&eGtVieE android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:teGt2tFle67bold7 android:teGt+olor67S999999--7 android:teGt67&his is the third panel7 /M L/VieE9lipperM L/)inear)aFoutM

2oti'e that the layout "e&ines three 'hil" !ie=s &or the VieE9lipper, ea'h a &eGtVieE =ith a simple message. >& 'ourse, you 'oul" ha!e !ery 'ompli'ate" 'hil" !ie=s, i& you so 'hose. 5o manually &lip the !ie=s, =e nee" to hook into the 4utton an" &lip them oursel!es =hen the button is 'li'ke",
package com.commonsEare.android.flipper1J import import import import android.app.ActivitFJ android.os.4undleJ android.vieE.VieEJ android.Eidget.VieE9lipperJ

public class 9lipper=emo eGtends ActivitF : VieE9lipper flipperJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ ; flipper6PVieE9lipperQfindViewByIdP?.id.detailsQJ

public void flipPVieE vQ : flipper.show&extPQJ ; ;

5his is Gust a matter o& 'alling shoE%eGtPQ on the VieE9lipper, like you 'an on any VieEAnimator 'lass.

*8:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

5he result is a tri!ial a'ti!ity, 'li'k the button, an" the ne;t &eGtVieE in seRuen'e is "isplaye", =rapping aroun" to the &irst a&ter !ie=ing the last,

"igure 771 The "lipper* application@ sho)ing the first panel

"igure 781 The same application@ after s)itching to the second panel

*:<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

5his, o& 'ourse, 'oul" be han"le" more simply by ha!ing a single &eGtVieE an" 'hanging the te;t an" 'olor on ea'h 'li'k. +o=e!er, you 'an imagine that the VieE9lipper 'ontents 'oul" be mu'h more 'ompli'ate", like the 'ontents you might put into a &abVieE. As =ith the &ab@idget, sometimes, your VieE9lipper 'ontents may not be kno=n at 'ompile time. As =ith &ab@idget, though, you 'an a"" ne= 'ontents on the &ly =ith ease. *or e;ample, let us look at another sample a'ti!ity ( 9ancF/9lipper>), using this layout,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M LVieE9lipper android:id67ORid/details7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L/VieE9lipperM L/)inear)aFoutM

2oti'e that the VieE9lipper has no 'ontents at 'ompile time. Also note that there is no 4utton &or &lipping bet=een the 'ontents S more on this in a moment. *or the VieE9lipper 'ontents, =e =ill 'reate large 4utton =i"gets, ea'h 'ontaining one o& the ran"om =or"s use" in many 'hapters in this book. An", =e =ill set up the VieE9lipper to automati'ally rotate bet=een the 4utton =i"gets,
package com.commonsEare.android.flipper>J import import import import import import android.app.ActivitFJ android.os.4undleJ android.vieE.VieEJ android.vieE.VieEDroupJ android.Eidget.4uttonJ android.Eidget.VieE9lipperJ

*:*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

public class 9lipper=emo> eGtends ActivitF : static 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J VieE9lipper flipperJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ flipper6PVieE9lipperQfindViewByIdP?.id.detailsQJ for P2tring item : itemsQ : 4utton btn6neE ButtonPthisQJ btn.setTextPitemQJ flipper.addViewPbtn8 neE VieEDroup.Layout)aramsP VieEDroup.)aFout(arams.9I)) (A?$%&8 VieEDroup.)aFout(arams.9I)) (A?$%&QQJ

; ;

flipper.set"lipInter!alP>---QJ flipper.start"lippingPQJ

A&ter iterating o!er the &unky =or"s, turning ea'h into a 4utton, an" a""ing the 4utton as a 'hil" o& the VieE9lipper, =e set up the &lipper to automati'ally &lip bet=een 'hil"ren ( flipper.set9lipIntervalP>---QJ) an" to start &lipping (flipper.start9lippingPQJ). 5he result is an en"less series o& buttons, ea'h appearing, then being repla'e" by the ne;t button in seRuen'e a&ter 2 se'on"s, =rapping aroun" to the &irst a&ter the last has been sho=n,

*:&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

"igure 7:1 The "lipper& application

5he auto-&lipping VieE9lipper is use&ul &or status panels or other situations =here you ha!e a lot o& in&ormation to "isplay, but not mu'h room. 5he key is that, sin'e it automati'ally &lips bet=een !ie=s, e;pe'ting users to intera't =ith in"i!i"ual !ie=s is "i'ey S the !ie= might s=it'h a=ay part=ay through their intera'tion.

(etting n SomebodyGs /ra)er


*or a long time, An"roi" "e!elopers yearne" &or a sli"ing "ra=er 'ontainer that =orke" like the one on the home s'reen, 'ontaining the i'ons &or laun'hing appli'ations. 5he o&&i'ial implementation =as in the open sour'e 'o"e but =as not part o& the %@D...until An"roi" 1.A, =hen they release" 2liding=raEer &or others to use. $nlike most other An"roi" 'ontainers, 2liding=raEer mo!es, s=it'hing &rom a 'lose" to an open position. 5his puts some restri'tions on =hat 'ontainer the 2liding=raEer itsel& 'an be in. 0t nee"s to be a 'ontainer that
*:-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

allo=s multiple =i"gets to sit atop ea'h other. ?elative)aFout an" 9rame)aFout satis&y this reRuirement, =here 9rame)aFout is a 'ontainer purely &or sta'king =i"gets atop one another. >n the &lip si"e, )inear)aFout "oes not allo= =i"gets to sta'k (they &all one a&ter another in a ro= or 'olumn), an" so you shoul" not ha!e a 2liding=raEer as an imme"iate 'hil" o& a )inear)aFout. +ere is a layout, sho=ing a 2liding=raEer in a 9rame)aFout, &rom the
9ancF/=raEer=emo proGe't,
LNGml version671.-7 encoding67utf-,7NM L9rame)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:background67S99<<<<++7 M L2liding=raEer android:id67ORid/draEer7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:handle67ORid/handle7 android:content67ORid/content7M LImageVieE android:id67Oid/handle7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:src67OdraEable/traF handle normal7 /M L4utton android:id67Oid/content7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:teGt67IIm in hereX7 /M L/2liding=raEerM L/9rame)aFoutM

5he 2liding=raEer shoul" 'ontain t=o things, 1. A han"le, &reRuently an ImageVieE or something along those lines, su'h as the one use" here, pulle" &rom the An"roi" open sour'e proGe't

2. 5he 'ontents o& the "ra=er itsel&, usually some sort o& 'ontainer, though in this 'ase =e are using a 4utton

*:%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

Moreo!er, 2liding=raEer nee"s to kno= the android:id !alues o& the han"le an" 'ontents, !ia the android:handle an" android:content attributes, respe'ti!ely. 5his tells the "ra=er ho= to animate itsel& as it sli"es open an" 'lose". +ere is =hat the 2liding=raEer looks like 'lose", using the supplie" han"le,

"igure 8<1 A Sliding/ra)er@ closed

An" here it is open, sho=ing its 'ontents,

*:0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

"igure 8*1 A Sliding/ra)er@ open

As one might e;pe't, you 'an open an" 'lose the "ra=er &rom Ca!a 'o"e as =ell as !ia user tou'h e!ents. +o=e!er, you ha!e t=o sets o& these metho"s, ones that take pla'e instantaneously (openPQ, closePQ, an" togglePQ) an" ones that use the animation ( animate"penPQ, animate+losePQ, animate&ogglePQ). ?ou 'an also lockPQ an" unlockPQ the "ra=erT =hile lo'ke", the "ra=er =ill not respon" to tou'h e!ents. ?ou 'an also register three types o& 'allba'ks i& you =ish, 1. A listener to be in!oke" =hen the "ra=er is opene"

2. A listener to be in!oke" =hen the "ra=er is 'lose" .. A listener to be in!oke" =hen the "ra=er is Ms'rolle"M (i.e., the user "rags or &lings the han"le) *or e;ample, the Laun'her7s 2liding=raEer toggles the i'on on the han"le &rom open to 'lose" to M"eleteM (i& you long-tap something on the "esktop). 0t a''omplishes this, in part, through 'allba'ks like these.

*:2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

2liding=raEer

'an be !erti'al or horiKontal. 2ote, though, that it keeps its orientation "espite the s'reen orientation. 0n other =or"s, i& you rotate the An"roi" "e!i'e or emulator running =raEer=emo, the "ra=er al=ays opens &rom the bottom S it "oes not al=ays Msti'kM to the original si"e it opene" &rom. 5his means that i& you =ant the "ra=er to al=ays open &rom the same si"e, like the Laun'her "oes, you =ill nee" separate layouts &or portrait !ersus lan"s'ape, a topi' =e "is'uss in the 'hapter on resour'es.

,ther (ood Stuff


An"roi" o&&ers Absolute)aFout, =here the 'ontents are lai" out base" on spe'i&i' 'oor"inate positions. ?ou tell Absolute)aFout =here to pla'e a 'hil" in pre'ise F,? 'oor"inates, an" An"roi" puts it there, no Ruestions aske". >n the plus si"e, this gi!es you pre'ise positioning. >n the minus si"e, it means your !ie=s =ill only look MrightM on s'reens o& a 'ertain "imension, or it reRuires you to =rite a bun'h o& 'o"e to a"Gust the 'oor"inates base" on s'reen siKe. %in'e An"roi" s'reens might run the gamut o& siKes, plus ha!e ne= siKes 'rop up perio"i'ally, using Absolute)aFout 'oul" get Ruite annoying. Also, note that Absolute)aFout is o&&i'ially "epre'ate", meaning that =hile it is a!ailable to you, its use is "is'ourage". An"roi" also has the $Gpandable)istVieE. 5his pro!i"es a simpli&ie" tree representation, supporting t=o le!els o& "epth, groups an" 'hil"ren. 8roups 'ontain 'hil"renT 'hil"ren are Mlea!esM o& the tree. 5his reRuires a ne= set o& a"apters, sin'e the )istAdapter &amily "oes not pro!i"e any sort o& group in&ormation &or the items in the list. +ere are some other =i"gets a!ailable in An"roi" beyon" those 'o!ere" so &ar in this book,
+hecked&eGtVieE,

a &eGtVieE that 'an either ha!e a 'he'kbo; or a ra"io button ne;t to it, use" =ith single-'hoi'e an" multi-'hoi'e lists
+hronometer, a stop=at'h-style 'ount"o=n timer DallerF,

a horiKontal s'rolling sele'tion =i"get, "esigne" &or thumbnail pre!ie=s o& images (e.g., 'amera photos, album 'o!ers)
*:7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Still +ore Widgets and Containers

#ultiAuto+omplete&eGtVieE,

like an Auto+omplete&eGtVieE, e;'ept that the user 'an make multiple 'hoi'es &rom the "rop-"o=n list, rather than Gust one
Yuick+ontact4adge,

gi!en the i"entity o& a 'onta't &rom the user7s 'onta'ts "atabase, "isplays a roster o& i'ons representing a'tions to be per&orme" on that 'onta't (pla'e a 'all, sen" a te;t message, sen" an email, et'.)
&oggle4utton, VieE2Eitcher

a t=o-state button =here the states are in"i'ate" by a MlightM an" prose (M>2M, M>**M) instea" o& a 'he'kmark (an" the Image2Eitcher an" &eGt2Eitcher sub'lasses), like a simpli&ie" VieE9lipper &or toggling bet=een t=o !ie=s

*:8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 16

=mbedding the Web9it Bro)ser

>ther 8$0 toolkits let you use +5ML &or presenting in&ormation, &rom limite" +5ML ren"erers (e.g., Ca!aP%=ing, =;Wi"gets) to embe""ing 0nternet E;plorer into .2E5 appli'ations. An"roi" is mu'h the same, in that you 'an embe" the built-in Web bro=ser as a =i"get in your o=n a'ti!ities, &or "isplaying +5ML or &ull-&le"ge" bro=sing. 5he An"roi" bro=ser is base" on WebDit, the same engine that po=ers Apple7s %a&ari Web bro=ser. 5he An"roi" bro=ser is su&&i'iently 'omple; that it gets its o=n Ca!a pa'kage (android.Eebkit), though using the @ebVieE =i"get itsel& 'an be simple or po=er&ul, base" upon your reRuirements.

A Bro)ser@ Writ Small


*or simple stu&&, @ebVieE is not signi&i'antly "i&&erent than any other =i"get in An"roi" S pop it into a layout, tell it =hat $ L to na!igate to !ia Ca!a 'o"e, an" you are "one. *or e;ample (@ebHit/4roEser1), here is a simple layout =ith a @ebVieE,
LNGml version671.-7 encoding67utf-,7NM L@ebVieE Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/Eebkit7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 /M

*::
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

=mbedding the Web9it Bro)ser

As =ith any other =i"get, you nee" to tell it ho= it shoul" &ill up the spa'e in the layout (in this 'ase, it &ills all remaining spa'e). 5he Ca!a 'o"e is eRually simple,
package com.commonsEare.android.broEser1J import android.app.ActivitFJ import android.os.4undleJ import android.Eebkit.@ebVieEJ public class 4roEser=emo1 eGtends ActivitF : @ebVieE broEserJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ broEser6P@ebVieEQfindViewByIdP?.id.EebkitQJ ; ; broEser.load*rlP7http://commonsEare.com7QJ

5he only thing unusual =ith this e"ition o& on+reatePQ is that =e in!oke load3rlPQ on the @ebVieE =i"get, to tell it to loa" a Web page (in this 'ase, the home page o& some ran"om &irm). +o=e!er, =e also ha!e to make one 'hange to Android#anifest.Gml, reRuesting permission to a''ess the 0nternet,
LNGml version671.-7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.broEser17M Luses-permission android:name67android.permission.I%&$?%$&7/M Lapplication android:icon67OdraEable/cE7M LactivitF android:name67.4roEser=emo17 android:label674roEser=emo17M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

&<<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mbedding the Web9it Bro)ser

0& =e &ail to a"" this permission, the bro=ser =ill re&use to loa" pages. #ermissions =ill be 'o!ere" in greater "etail in a later 'hapter. 5he resulting a'ti!ity looks like a Web bro=ser, Gust =ith hi""en s'rollbars,

"igure 8&1 The Bro)ser* sample application

As =ith the regular An"roi" bro=ser, you 'an pan aroun" the page by "ragging it, =hile the "ire'tional pa" mo!es you aroun" all the &o'usable elements on the page. What is missing is all the e;tra stu&& that make up a Web bro=ser, su'h as a na!igational toolbar. 2o=, you may be tempte" to repla'e the $ L in that sour'e 'o"e =ith something else, su'h as 8oogle7s home page or something else that relies upon Ca!as'ript. 1y "e&ault Ca!as'ript is turne" o&& in @ebVieE =i"gets. 0& you =ant to enable Ca!as'ript, 'all get2ettingsPQ.setJava2cript$nabledPtrueQJ on the @ebVieE instan'e. 5his notion =ill be 'o!ere" in a bit more "etail later in this 'hapter.

&<*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mbedding the Web9it Bro)ser

!oading t >p
5here are t=o main =ays to get 'ontent into the @ebVieE. >ne, sho=n abo!e, is to pro!i"e the bro=ser =ith a $ L an" ha!e the bro=ser "isplay that page !ia load3rlPQ. 5he bro=ser =ill a''ess the 0nternet through =hate!er means are a!ailable to that spe'i&i' "e!i'e at the present time (Wi*i, 28, .8, WiMa;, =ell-traine" tiny 'arrier pigeons, et'.). 5he alternati!e is to use load=ataPQ. +ere, you supply the +5ML &or the bro=ser to !ie=. ?ou might use this to,

"isplay a manual that =as installe" as a &ile =ith your appli'ation pa'kage "isplay snippets o& +5ML you retrie!e" as part o& other pro'essing, su'h as the "es'ription o& an entry in an Atom &ee" generate a =hole user inter&a'e using +5ML, instea" o& using the An"roi" =i"get set

5here are t=o &la!ors o& load=ataPQ. 5he simpler one allo=s you to pro!i"e the 'ontent, the M0ME type, an" the en'o"ing, all as strings. 5ypi'ally, your M0ME type =ill be teGt/html an" your en'o"ing =ill be 3&9-, &or or"inary +5ML. *or e;ample, i& you repla'e the load3rlPQ in!o'ation in the pre!ious e;ample =ith the &ollo=ing,
broEser.loadDataP7LhtmlMLbodFM!ello8 EorldXL/bodFML/htmlM78 7teGt/html78 73&9-,7QJ

?ou get,

&<&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mbedding the Web9it Bro)ser

"igure 8-1 The Bro)ser& sample application

5his is also a!ailable as a &ully-buil"able sample, as @ebHit/4roEser>.

?avigating the Waters


As =as mentione" abo!e, there is no na!igation toolbar =ith the @ebVieE =i"get. 5his allo=s you to use it in pla'es =here su'h a toolbar =oul" be pointless an" a =aste o& s'reen real estate. 5hat being sai", i& you =ant to o&&er na!igational 'apabilities, you 'an, but you ha!e to supply the $0. o&&ers =ays to per&orm gar"en-!ariety bro=ser na!igation, in'lu"ing,
@ebVieE reloadPQ to re&resh go4ackPQ

the 'urrently-!ie=e" Web page

to go ba'k one step in the bro=ser history, an" canDo4ackPQ to "etermine i& there is any history to go ba'k to
go9orEardPQ to go &or=ar" one step in the bro=ser history, an" canDo9orEardPQ to "etermine i& there is any history to go &or=ar" to

&<-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mbedding the Web9it Bro)ser

go4ack"r9orEardPQ

to go ba'k=ar"s or &or=ar"s in the bro=ser history, =here negati!e numbers represent a 'ount o& steps to go ba'k=ar"s, an" positi!e numbers represent ho= many steps to go &or=ar"s to see i& the bro=ser 'an go ba'k=ar"s or &or=ar"s the state" number o& steps (&ollo=ing the same positi!ePnegati!e 'on!ention as go4ack"r9orEardPQ)
canDo4ack"r9orEardPQ

to 'lear the bro=ser resour'e 'a'he an" clear!istorFPQ to 'lear the bro=sing history
clear+achePQ

=ntertaining the Client


#arti'ularly i& you are going to use the @ebVieE as a lo'al user inter&a'e (!s. bro=sing the Web), you =ill =ant to be able to get 'ontrol at key times, parti'ularly =hen users 'li'k on links. ?ou =ill =ant to make sure those links are han"le" properly, either by loa"ing your o=n 'ontent ba'k into the @ebVieE, by submitting an Intent to An"roi" to open the $ L in a &ull bro=ser, or by some other means (see the 'hapter on laun'hing a'ti!ities). ?our hook into the @ebVieE a'ti!ity is !ia set@ebVieE+lientPQ, =hi'h takes an instan'e o& a @ebVieE+lient implementation as a parameter. 5he supplie" 'allba'k obGe't =ill be noti&ie" o& a =i"e range o& e!ents, ranging &rom =hen parts o& a page ha!e been retrie!e" ( on(age2tartedPQ, et'.) to =hen you, as the host appli'ation, nee" to han"le 'ertain user- or 'ir'umstan'einitiate" e!ents, su'h as,
on&oo#anF?edirectsPQ on?eceived!ttpAuth?eUuestPQ

et'.

A 'ommon hook =ill be should"verride3rl)oadingPQ, =here your 'allba'k is passe" a $ L (plus the @ebVieE itsel&) an" you return true i& you =ill han"le the reRuest or false i& you =ant "e&ault han"ling (e.g., a'tually &et'h the Web page re&eren'e" by the $ L). 0n the 'ase o& a &ee" rea"er appli'ation, &or e;ample, you =ill probably not ha!e a &ull bro=ser =ith na!igation built into your rea"er, so i& the user 'li'ks a $ L, you probably =ant to use an
&<%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mbedding the Web9it Bro)ser

Intent

to ask An"roi" to loa" that page in a &ull bro=ser. 1ut, i& you ha!e inserte" a M&akeM $ L into the +5ML, representing a link to some a'ti!itypro!i"e" 'ontent, you 'an up"ate the @ebVieE yoursel&. *or e;ample, let7s amen" the &irst bro=ser e;ample to be a bro=ser-base" eRui!alent o& our original e;ample, an appli'ation that, upon a 'li'k, sho=s the 'urrent time. *rom @ebHit/4roEserC, here is the re!ise" Ca!a,
public class 4roEser=emoC eGtends ActivitF : @ebVieE broEserJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ broEser6P@ebVieEQfindViewByIdP?.id.EebkitQJ broEser.set#e'ViewClientPneE Call'ackPQQJ loadTimePQJ ; void loadTimePQ : 2tring page67LhtmlMLbodFMLa href6T7clockT7M7 RneE DatePQ.toStringPQ R7L/aML/bodFML/htmlM7J broEser.loadDataPpage8 7teGt/html78 73&9-,7QJ ; private class +allback eGtends @ebVieE+lient : public boolean shouldO!erride*rlLoadingP@ebVieE vieE8 2tring urlQ : loadTimePQJ ; ; ; returnPtrueQJ

+ere, =e loa" a simple Web page into the bro=ser ( load&imePQ) that 'onsists o& the 'urrent time, ma"e into a hyperlink to the /clock $ L. We also atta'h an instan'e o& a @ebVieE+lient sub'lass, pro!i"ing our implementation o& should"verride3rl)oadingPQ. 0n this 'ase, no matter =hat the $ L, =e =ant to Gust reloa" the @ebVieE !ia load&imePQ.

&<0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mbedding the Web9it Bro)ser

unning this a'ti!ity gi!es us,

"igure 8%1 The Bro)ser- sample application

%ele'ting the link an" 'li'king the @-pa" 'enter button =ill M'li'kM the link, 'ausing us to rebuil" the page =ith the ne= time.

Settings@ Preferences@ and ,ptions $,h@ +y!'


With your &a!orite "esktop Web bro=ser, you ha!e some sort o& MsettingsM or Mpre&eren'esM or MoptionsM =in"o=. 1et=een that an" the toolbar 'ontrols, you 'an t=eak an" t=i""le the beha!ior o& your bro=ser, &rom pre&erre" &onts to the beha!ior o& Ca!as'ript. %imilarly, you 'an a"Gust the settings o& your @ebVieE =i"get as you see &it, !ia the @eb2ettings instan'e returne" &rom 'alling the =i"get7s get2ettingsPQ metho". 5here are lots o& options on @eb2ettings to play =ith. Most appear &airly esoteri' (e.g., set9antasF9ont9amilFPQ). +o=e!er, here are some that you may &in" more use&ul,
&<2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

=mbedding the Web9it Bro)ser

Control the &ont siKing !ia set=efault9ont2iKePQ (to use a point siKe) or set&eGt2iKePQ (to use 'onstants in"i'ating relati!e siKes like )A?D$? an" 2#A))$2&) Control Ca!as'ript !ia setJava2cript$nabledPQ (to "isable it outright) an" setJava2cript+an"pen@indoEsAutomaticallFPQ (to merely stop it &rom opening pop-up =in"o=s) Control Web site ren"ering !ia set3serAgentPQ, so you 'an supply your o=n user agent string to make the Web ser!er think you are a "esktop bro=ser, another mobile "e!i'e (e.g., i#hone), or =hate!er

5he settings you 'hange are not persistent, so you shoul" store them some=here (su'h as !ia the An"roi" pre&eren'es engine) i& you are allo=ing your users to "etermine the settings, !ersus har"-=iring the settings in your appli'ation.

&<7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 18

Applying +enus

Like appli'ations &or the "esktop an" some mobile operating systems, An"roi" supports a'ti!ities =ith Mappli'ationM menus. Most An"roi" phones =ill ha!e a "e"i'ate" menu key &or popping up the menuT other "e!i'es =ill o&&er alternate means &or triggering the menu to appear, su'h as the on-s'reen button use" by the A C+>% A An"roi" tablet. Also, as =ith many 8$0 toolkits, you 'an 'reate M'onte;t menusM. >n a tra"itional 8$0, this might be triggere" by the right-mouse button. >n mobile "e!i'es, 'onte;t menus typi'ally appear =hen the user Mtaps-an"hol"sM o!er a parti'ular =i"get. *or e;ample, i& a &eGtVieE ha" a 'onte;t menu, an" the "e!i'e =as "esigne" &or &inger-base" tou'h input, you 'oul" push the &eGtVieE =ith your &inger, hol" it &or a se'on" or t=o, an" a popup menu =ill appear &or the user to 'hoose &rom.

"lavors of +enu
An"roi" 'onsi"ers the t=o types o& menu "es'ribe" abo!e as being the Moptions menuM an" M'onte;t menuM. 5he options menu is triggere" by pressing the har"=are MMenu button on the "e!i'e, =hile the 'onte;t menu is raise" by a tap-an"-hol" on the =i"get sporting the menu. 0n a""ition, the options menu operates in one o& t=o mo"es, i'on an" e;pan"e". When the user &irst presses the MMenu button, the i'on mo"e =ill appear, sho=ing up to the &irst si; menu 'hoi'es as large, &inger&<:
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

&rien"ly buttons in a gri" at the bottom o& the s'reen. 0& the menu has more than si; 'hoi'es, the si;th button =ill be'ome MMoreM S 'li'king that option =ill bring up the e;pan"e" mo"e, sho=ing the remaining 'hoi'es not !isible in the regular menu. 5he menu is s'rollable, so the user 'an get to any o& the menu 'hoi'es.

+enus of ,ptions
ather than buil"ing your a'ti!ity7s options menu "uring on+reatePQ, the =ay you =ire up the rest o& your $0, you instea" nee" to implement on+reate"ptions#enuPQ. 5his 'allba'k re'ei!es an instan'e o& #enu. 5he &irst thing you shoul" "o is 'hain up=ar" to the super'lass (super.on+reate"ptions#enuPmenuQ), so the An"roi" &rame=ork 'an a"" in any menu 'hoi'es it &eels are ne'essary. 5hen, you 'an go about a""ing your o=n options, "es'ribe" belo=. 0& you =ill nee" to a"Gust the menu "uring your a'ti!ity7s use (e.g., "isable a no=-in!ali" menu 'hoi'e), Gust hol" onto the #enu instan'e you re'ei!e in on+reate"ptions#enuPQ. >r, implement on(repare"ptions#enuPQ, =hi'h is 'alle" Gust be&ore "isplaying the menu ea'h time it is reRueste". 8i!en that you ha!e re'ei!e" a #enu obGe't !ia on+reate"ptions#enuPQ, you a"" menu 'hoi'es by 'alling addPQ. 5here are many &la!ors o& this metho", =hi'h reRuire some 'ombination o& the &ollo=ing parameters,

A group i"enti&ier (int), =hi'h shoul" be %"%$ unless you are 'reating a spe'i&i' groupe" set o& menu 'hoi'es &or use =ith setDroup+heckablePQ (see belo=) A 'hoi'e i"enti&ier (also an int), &or use in i"enti&ying this 'hoi'e in the on"ptionsItem2electedPQ 'allba'k =hen a menu 'hoi'e is 'hosen An or"er i"enti&ier (yet another int), &or in"i'ating =here this menu 'hoi'e shoul" be slotte" i& the menu has An"roi"-supplie" 'hoi'es alongsi"e your o=n S &or no=, Gust use %"%$ 5he te;t o& the menu 'hoi'e, as a %tring or a resour'e 0@

&*<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

5he addPQ &amily o& metho"s all return an instan'e o& #enuItem, =here you 'an a"Gust any o& the menu item settings you ha!e alrea"y set (e.g., the te;t o& the menu 'hoi'e). ?ou 'an also set the short'uts &or the menu 'hoi'e S single-'hara'ter mnemoni's that 'hoose that menu 'hoi'e =hen the menu is !isible. An"roi" supports both an alphabeti' (or MR=ertyM) set o& short'uts an" a numeri' set o& short'uts. 5hese are set in"i!i"ually by 'alling setAlphabetic2hortcutPQ an" set%umeric2hortcutPQ respe'ti!ely. 5he menu is pla'e" into alphabeti' short'ut mo"e by 'alling setYEertF#odePQ on the menu =ith a true parameter. 5he 'hoi'e an" group i"enti&iers are keys use" to unlo'k a""itional menu &eatures, su'h as,

Calling #enuItemSset+heckablePQ =ith a 'hoi'e i"enti&ier, to 'ontrol i& the menu 'hoi'e has a t=o-state 'he'kbo; alongsi"e the title, =here the 'he'kbo; !alue gets toggle" =hen the user 'hooses that menu 'hoi'e Calling #enuSsetDroup+heckablePQ =ith a group i"enti&ier, to turn a set o& menu 'hoi'es into ones =ith a mutual-e;'lusion ra"io button bet=een them, so one out o& the group 'an be in the M'he'ke"M state at any time

*inally, you 'an 'reate &ly-out sub-menus by 'alling add2ub#enuPQ, supplying the same parameters as add#enuPQ. An"roi" =ill e!entually 'all on+reate(anel#enuPQ, passing it the 'hoi'e i"enti&ier o& your sub-menu, along =ith another #enu instan'e representing the sub-menu itsel&. As =ith on+reate"ptions#enuPQ, you shoul" 'hain up=ar" to the super'lass, then a"" menu 'hoi'es to the sub-menu. >ne limitation is that you 'annot in"e&initely nest sub-menus S a menu 'an ha!e a sub-menu, but a submenu 'annot ha!e a sub-sub-menu. 0& the user makes a menu 'hoi'e, your a'ti!ity =ill be noti&ie" !ia the on"ptionsItem2electedPQ 'allba'k that a menu 'hoi'e =as sele'te". ?ou are gi!en the #enuItem obGe't 'orrespon"ing to the sele'te" menu 'hoi'e. A typi'al pattern is to sEitchPQ on the menu 0@ (item.getItemIdPQ) an" take appropriate beha!ior. 2ote that on"ptionsItem2electedPQ is use" regar"less o& =hether the 'hosen menu item =as in the base menu or in a submenu.
&**

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

+enus in Context
1y an" large, 'onte;t menus use the same guts as options menus. 5he t=o main "i&&eren'es are ho= you populate the menu an" ho= you are in&orme" o& menu 'hoi'es. *irst, you nee" to in"i'ate =hi'h =i"get(s) on your a'ti!ity ha!e 'onte;t menus. 5o "o this, 'all register9or+onteGt#enuPQ &rom your a'ti!ity, supplying the VieE that is the =i"get nee"ing a 'onte;t menu. 2e;t, you nee" to implement on+reate+onteGt#enuPQ, =hi'h, among other things, is passe" the VieE you supplie" in register9or+onteGt#enuPQ. ?ou 'an use that to "etermine =hi'h menu to buil", assuming your a'ti!ity has more than one. 5he on+reate+onteGt#enuPQ metho" gets the +onteGt#enu itsel&, the VieE the 'onte;t menu is asso'iate" =ith, an" a +onteGt#enu.+onteGt#enuInfo, =hi'h tells you =hi'h item in the list the user "i" the tap-an"-hol" o!er, in 'ase you =ant to 'ustomiKe the 'onte;t menu base" on that in&ormation. *or e;ample, you 'oul" toggle a 'he'kable menu 'hoi'e base" upon the 'urrent state o& the item. 0t is also important to note that on+reate+onteGt#enuPQ gets 'alle" &or ea'h time the 'onte;t menu is reRueste". $nlike the options menu (=hi'h is only built on'e per a'ti!ity), 'onte;t menus are "is'ar"e" on'e they are use" or "ismisse". +en'e, you "o not =ant to hol" onto the supplie" +onteGt#enu obGe'tT Gust rely on getting the 'han'e to rebuil" the menu to suit your a'ti!ity7s nee"s on an on-"eman" basis base" on user a'tions. 5o &in" out =hen a 'onte;t menu 'hoi'e =as 'hosen, implement on+onteGtItem2electedPQ on the a'ti!ity. 2ote that you only get the #enuItem instan'e that =as 'hosen in this 'allba'k. As a result, i& your a'ti!ity has t=o or more 'onte;t menus, you may =ant to ensure they ha!e uniRue menu item i"enti&iers &or all their 'hoi'es, so you 'an tell them apart in this 'allba'k. Also, you 'an 'all get#enuInfoPQ on the #enuItem to get the +onteGt#enu.+onteGt#enuInfo you re'ei!e" in on+reate+onteGt#enuPQ.
&*&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

>ther=ise, this 'allba'k beha!es the same as on"ptionsItem2electedPQ as is "es'ribe" abo!e.

Taking a Peek
0n the sample proGe't #enus/#enus, you =ill &in" an amen"e" !ersion o& the sample ()ist) =ith asso'iate" menus. %in'e the menus "o not a&&e't the layout, the FML layout &ile nee"s not 'hange an" is not reprinte" here.
)istVieE

+o=e!er, the Ca!a 'o"e has a &e= ne= beha!iors,


package com.commonsEare.android.menusJ import import import import import import import import import import import import import import android.app.Alert=ialogJ android.app.)istActivitFJ android.content.=ialogInterfaceJ android.os.4undleJ android.vieE.+onteGt#enuJ android.vieE.#enuJ android.vieE.#enuItemJ android.vieE.VieEJ android.Eidget.AdapterVieEJ android.Eidget.ArraFAdapterJ android.Eidget.$dit&eGtJ android.Eidget.)istVieEJ android.Eidget.&eGtVieEJ java.util.ArraF)istJ

public class #enu=emo eGtends )istActivitF : private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J public static final int #$%3 A== 6 #enu.9I?2&R1J public static final int #$%3 ?$2$& 6 #enu.9I?2&R>J public static final int #$%3 +A( 6 #enu.9I?2&RCJ public static final int #$%3 ?$#"V$ 6 #enu.9I?2&R<J private ArraF)istL2tringM Eords6nullJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ init$dapterPQJ register"orContextMenuPgetListViewPQQJ ; &*-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

O"verride public boolean onCreateOptionsMenuP#enu menuQ : menu .addP#enu.%"%$8 #$%3 A==8 #enu.%"%$8 7Add7Q .setIconP?.draEable.ic menu addQJ menu .addP#enu.%"%$8 #$%3 ?$2$&8 #enu.%"%$8 7?eset7Q .setIconP?.draEable.ic menu refreshQJ returnPsuper.onCreateOptionsMenuPmenuQQJ ; O"verride public void onCreateContextMenuP+onteGt#enu menu8 VieE v8 +onteGt#enu.+onteGt#enuInfo menuInfoQ : menu.addP#enu.%"%$8 #$%3 +A(8 #enu.%"%$8 7+apitaliKe7QJ menu.addP#enu.%"%$8 #$%3 ?$#"V$8 #enu.%"%$8 7?emove7QJ ; O"verride public boolean onOptionsItemSelectedP#enuItem itemQ : sEitch Pitem.getItemIdPQQ : case #$%3 A==: addPQJ returnPtrueQJ case #$%3 ?$2$&: init$dapterPQJ returnPtrueQJ

; ;

returnPsuper.onOptionsItemSelectedPitemQQJ O"verride public boolean onContextItemSelectedP#enuItem itemQ : AdapterVieE.Adapter+onteGt#enuInfo info6 PAdapterVieE.Adapter+onteGt#enuInfoQitem.getMenuInfoPQJ ArraFAdapterL2tringM adapter6PArraFAdapterL2tringMQgetList$dapterPQJ sEitch Pitem.getItemIdPQQ : case #$%3 +A(: 2tring Eord6Eords.getPinfo.positionQJ Eord6Eord.to*pperCasePQJ adapter.remo!ePEords.getPinfo.positionQQJ adapter.insertPEord8 info.positionQJ returnPtrueQJ case #$%3 ?$#"V$: adapter.remo!ePEords.getPinfo.positionQQJ

&*%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

; ;

returnPtrueQJ

returnPsuper.onContextItemSelectedPitemQQJ private void init$dapterPQ : Eords6neE ArraF)istL2tringMPQJ for P2tring s : itemsQ : Eords.addPsQJ ; setList$dapterPneE ArraFAdapterL2tringMPthis8 android.?.laFout.simple list item 18 EordsQQJ

private void addPQ : final VieE addVieE6getLayoutInflaterPQ.inflateP?.laFout.add8 nullQJ neE Alert=ialog.BuilderPthisQ .setTitleP7Add a @ord7Q .setViewPaddVieEQ .set)ositi!eButtonP7"H78 neE =ialogInterface.OnClickListenerPQ : public void onClickP=ialogInterface dialog8 int Ehich4uttonQ : ArraFAdapterL2tringM adapter6PArraFAdapterL2tringMQgetList$dapterPQJ $dit&eGt title6P$dit&eGtQaddVieE.findViewByIdP?.id.titleQJ ; adapter.addPtitle.getTextPQ.toStringPQQJ

; ;

;Q .set&egati!eButtonP7+ancel78 nullQ .showPQJ

0n on+reatePQ, =e register our )istVieE =i"get as ha!ing a 'onte;t menu. We also "elegate loa"ing the a"apter to an initAdapterPQ pri!ate metho", one that 'opies the "ata out o& our stati' 2tring array an" pours it into an ArraF)ist, using the ArraF)ist &or the ArraFAdapter. 5he reason, =e =ant to be able to 'hange the 'ontents o& the list on the &ly, an" that is mu'h easier i& you use an ArraF)ist rather than an or"inary 2tring array. *or the options menu, =e o!erri"e on+reate"ptions#enuPQ an" a"" t=o menu items, one to a"" a ne= =or" to the list an" one to reset the =or"s to their initial state. 5hese menu items ha!e 0@s "e&ine" lo'ally as stati' "ata
&*0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

members (#$%3 A== an" #$%3 ?$2$&), an" they also sport i'ons 'opie" out o& the An"roi" open sour'e proGe't. 0& the user "isplays the menu, it looks like this,

"igure 801 The +enu/emo sample application and its options menu

We also o!erri"e on"ptionsItem2electedPQ, =hi'h =ill be 'alle" i& the user makes a 'hoi'e &rom the menu. 5he supplie" #enuItem has a getItemIdPQ metho" that shoul" map to either #$%3 A== or #$%3 ?$2$&. 0n the 'ase o& #$%3 A==, =e 'all a pri!ate addPQ metho" that "isplays an Alert=ialog =ith a 'ustom -ie= as its 'ontents, in&late" &rom res/laFout/add.Gml,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67horiKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 M L&eGtVieE android:teGt67@ord:7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 /M L$dit&eGt

&*2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

android:id67ORid/title7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:laFout margin)eft67<dip7 /M L/)inear)aFoutM

5hat gi!es us a "ialog like this one,

"igure 821 The same application@ sho)ing the add#)ord dialog

0& the user 'li'ks the >D button, =e get our ArraFAdapter an" 'all addPQ on it, a""ing the entere" =or" to the en" o& the list. 0& the user 'hooses #$%3 ?$2$&, =e 'all initAdapterPQ again, setting up a ne= ArraFAdapter an" atta'hing the ne= one to our )istActivitF. *or the 'onte;t menu, =e o!erri"e on+reate+onteGt#enuPQ. >n'e again, =e "e&ine a pair o& menu items =ith lo'al 0@s, #$%3 +A( (to 'apitaliKe the longtappe"-upon =or") an" #$%3 ?$#"V$ (to remo!e the =or"). %in'e 'onte;t

&*7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

menus ha!e no i'ons, =e 'an skip that part. 5hat gi!es the user a 'onte;t menu i& they long tap on a =or",

"igure 871 The same application@ sho)ing the context menu

We also o!erri"e on+onteGt#enu2electedPQ. %in'e this is a 'onte;t menu &or a our #enuItem has some e;tra in&ormation &or us S spe'i&i'ally, =hi'h item =as long-tappe"-upon in the list. 5o "o that, =e 'all get#enuInfoPQ on the #enuItem an" 'ast the result to be an AdapterVieE.Adapter+onteGt#enuInfo. 5hat obGe't, in turn, has a position "ata member, =hi'h is the in"e; into our array o& the =or" the user 'hose. *rom there, =e =ork =ith our ArraFAdapter to 'apitaliKe or remo!e the =or", as reRueste".
)istVieE,

.et +ore nflation


We sa= earlier in this book that you 'an "es'ribe VieEs !ia FML &iles an" Min&lateM them into a'tual VieE obGe'ts at runtime. An"roi" also allo=s you to "es'ribe menus !ia FML &iles an" Min&lateM them =hen a menu is 'alle" &or. 5his helps you keep your menu stru'ture separate &rom the
&*8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

implementation o& menu-han"ling logi', an" it pro!i"es easier =ays to "e!elop menu-authoring tools.

%enu /%) Structure


Menu FML goes in res/menu/ in your proGe't tree, alongsi"e the other types o& resour'es that your proGe't might employ. As =ith layouts, you 'an ha!e se!eral menu FML &iles in your proGe't, ea'h =ith their o=n &ilename an" the .Gml e;tension. *or e;ample, &rom the #enus/Inflation sample proGe't, here is a menu 'alle" option.Gml,
LNGml version671.-7 encoding67utf-,7NM Lmenu Gmlns:android67http://schemas.android.com/apk/res/android7M Litem android:id67ORid/add7 android:title67Add7 android:icon67OdraEable/ic menu add7 /M Litem android:id67ORid/reset7 android:title67?eset7 android:icon67OdraEable/ic menu refresh7 /M L/menuM

?ou must start =ith a menu root element 0nsi"e a menu are item elements an" group elements, the latter representing a 'olle'tion o& menu items that 'an be operate" upon as a group %ubmenus are spe'i&ie" by a""ing a menu element as a 'hil" o& an item element, using this ne= menu element to "es'ribe the 'ontents o& the submenu 0& you =ant to "ete't =hen an item is 'hosen, or to re&eren'e an item or group &rom your Ca!a 'o"e, be sure to apply an android:id, Gust as you "o =ith VieE layout FML

%enu +ptions nd /%)


0nsi"e the item an" group elements you 'an spe'i&y !arious options, mat'hing up =ith 'orrespon"ing metho"s on #enu or #enuItem.
&*:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

Title
5he title o& a menu item is pro!i"e" !ia the android:title attribute on an item element. 5his 'an be either a literal string or a re&eren'e to a string resour'e (e.g., Ostring/foo).

Icon
Menu items optionally ha!e i'ons. 5o pro!i"e an i'on S in the &orm o& a re&eren'e to a "ra=able resour'e (e.g., OdraEable/eject), use the android:icon attribute on the item element.

+rder
1y "e&ault, the or"er o& the items in the menu is "etermine" by the or"er they appear in the menu FML. 0& you =ant, you 'an 'hange that, by spe'i&ying the android:orderIn+ategorF attribute on item element. 5his is a --base" in"e; o& the or"er &or the items asso'iate" =ith the 'urrent 'ategory. 5here is an impli'it "e&ault 'ategoryT groups 'an pro!i"e an android:menu+ategorF attribute to spe'i&y a "i&&erent 'ategory to use &or items in that group. 8enerally, though, it is simplest Gust to put the items in the FML in the or"er you =ant them to appear.

En =led
0tems an" groups 'an be enable" or "isable", 'ontrolle" in the FML !ia the android:enabled attribute on the item or group element. 1y "e&ault, items an" groups are enable". @isable" items an" groups appear in the menu but 'annot be sele'te". ?ou 'an 'hange an item7s status at runtime !ia the set$nabledPQ metho" on #enuItem, or 'hange a group7s status !ia setDroup$nabledPQ on #enu.

&&<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

>isi=le
%imilarly, items an" groups 'an be !isible or in!isible, 'ontrolle" in the FML !ia the android:visible attribute on the item or group element. 1y "e&ault, items an" groups are !isible. 0n!isible items an" groups "o not appear in the menu at all. ?ou 'an 'hange an item7s status at runtime !ia the setVisiblePQ metho" on #enuItem, or 'hange a group7s status !ia setDroupVisiblePQ on #enu.

Shortcut
0tems 'an ha!e short'uts S single letters ( android:alphabetic2hortcut) or numbers (android:numeric2hortcut) that 'an be presse" to 'hoose the item =ithout ha!ing to use the tou'hs'reen, @-pa", or tra'kball to na!igate the &ull menu.

In.l tin! the %enu


A'tually using the menu, on'e "e&ine" in FML, is easy. Cust 'reate a #enuInflater an" tell it to in&late your menu. 5he #enus/Inflation proGe't is a 'lone o& the #enus/#enus proGe't, =ith the menu 'reation 'on!erte" to use menu FML resour'es an" #enuInflater. 5he options menu =as 'on!erte" to the FML sho=n pre!iously in this se'tionT here is the 'onte;t menu,
LNGml version671.-7 encoding67utf-,7NM Lmenu Gmlns:android67http://schemas.android.com/apk/res/android7M Litem android:id67ORid/cap7 android:title67+apitaliKe7 /M Litem android:id67ORid/remove7 android:title67?emove7 /M L/menuM

5he Ca!a 'o"e is nearly i"enti'al, 'hanging mostly in the implementation o& on+reate"ptions#enuPQ an" on+reate+onteGt#enuPQ,

&&*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

O"verride public boolean onCreateOptionsMenuP#enu menuQ : neE MenuInflaterPthisQ.inflateP?.menu.option8 menuQJ returnPsuper.onCreateOptionsMenuPmenuQQJ ; O"verride public void onCreateContextMenuP+onteGt#enu menu8 VieE v8 +onteGt#enu.+onteGt#enuInfo menuInfoQ : neE MenuInflaterPthisQ.inflateP?.menu.conteGt8 menuQJ ;

+ere, =e see ho= #enuInflater Mpours inM the menu items spe'i&ie" in the menu resour'e (e.g., ?.menu.option) into the supplie" #enu or +onteGt#enu obGe't. We also nee" to 'hange on"ptionsItem2electedPQ an" to use the android:id !alues spe'i&ie" in the FML,

on+onteGtItem2electedPQ

O"verride public boolean onOptionsItemSelectedP#enuItem itemQ : sEitch Pitem.getItemIdPQQ : case ?.id.add: addPQJ returnPtrueQJ case ?.id.reset: init$dapterPQJ returnPtrueQJ ; ; returnPsuper.onOptionsItemSelectedPitemQQJ

O"verride public boolean onContextItemSelectedP#enuItem itemQ : AdapterVieE.Adapter+onteGt#enuInfo info6 PAdapterVieE.Adapter+onteGt#enuInfoQitem.getMenuInfoPQJ ArraFAdapterL2tringM adapter6PArraFAdapterL2tringMQgetList$dapterPQJ sEitch Pitem.getItemIdPQQ : case ?.id.cap: 2tring Eord6Eords.getPinfo.positionQJ Eord6Eord.to*pperCasePQJ adapter.remo!ePEords.getPinfo.positionQQJ adapter.insertPEord8 info.positionQJ

&&&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Applying +enus

returnPtrueQJ case ?.id.remove: adapter.remo!ePEords.getPinfo.positionQQJ ; ; returnPtrueQJ

returnPsuper.onContextItemSelectedPitemQQJ

n the !and of +enus and 3oney


An"roi" ..0 (a.k.a., +oney'omb) intro"u'e" a ne= look-an"-&eel &or An"roi" appli'ations, parti'ularly on tablets. >ptions menus in parti'ular 'hange &rom being something triggere" by some ME2$ button to a "rop"o=n menu &rom the Ma'tion barM. *ortunately, this is ba'k=ar"s'ompatible, so your e;isting menus =ill not nee" to 'hange to a"opt this ne= look. 5he 'on'ept o& the ne= +oney'omb look is 'o!ere" later in this book, an" the a'tion bar itsel& is also 'o!ere" later in this book.

&&-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 19

Sho)ing Pop#>p +essages

%ometimes, your a'ti!ity (or other pie'e o& An"roi" 'o"e) =ill nee" to speak up. 2ot e!ery intera'tion =ith An"roi" users =ill be neat, ti"y, an" 'ontainable in a'ti!ities 'ompose" o& !ie=s. Errors =ill 'rop up. 1a'kgroun" tasks may take =ay longer than e;pe'te". %omething asyn'hronous may o''ur, su'h as an in'oming message. 0n these an" other 'ases, you may nee" to 'ommuni'ate =ith the user outsi"e the boun"s o& the tra"itional user inter&a'e. >& 'ourse, this is nothing ne=. Error messages in the &orm o& "ialog bo;es ha!e been aroun" &or a !ery long time. More subtle in"i'ators also e;ist, &rom task tray i'ons to boun'ing "o'k i'ons to a !ibrating 'ell phone. An"roi" has Ruite a &e= systems &or letting you alert your users outsi"e the boun"s o& an ActivitF-base" $0. >ne, noti&i'ations, is tie" hea!ily into intents an" ser!i'es an", as su'h, is 'o!ere" in a later 'hapter. 0n this 'hapter, you =ill see t=o means o& raising pop-up messages, toasts an" alerts.

Caising Toasts
A &oast is a transient message, meaning that it "isplays an" "isappears on its o=n =ithout user intera'tion. Moreo!er, it "oes not take &o'us a=ay
&&0
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Sho)ing Pop#>p +essages

&rom the 'urrently-a'ti!e ActivitF, so i& the user is busy =riting the ne;t 8reat #rogramming 8ui"e, they =ill not ha!e keystrokes be MeatenM by the message. %in'e a &oast is transient, you ha!e no =ay o& kno=ing i& the user e!en noti'es it. ?ou get no a'kno=le"gment &rom them, nor "oes the message sti'k aroun" &or a long time to pester the user. +en'e, the &oast is mostly &or a"!isory messages, su'h as in"i'ating a long-running ba'kgroun" task is 'omplete", the battery has "roppe" to a lo=-but-not-too-lo= le!el, et'. Making a &oast is &airly easy. 5he &oast 'lass o&&ers a stati' make&eGtPQ that a''epts a 2tring (or string resour'e 0@) an" returns a &oast instan'e. 5he make&eGtPQ metho" also nee"s the ActivitF (or other +onteGt) plus a "uration. 5he "uration is e;presse" in the &orm o& the )$%D&! 2!"?& or )$%D&! )"%D 'onstants to in"i'ate, on a relati!e basis, ho= long the message shoul" remain !isible. 0& you =oul" pre&er your &oast be ma"e out o& some other VieE, rather than be a boring ol" pie'e o& te;t, simply 'reate a ne= &oast instan'e !ia the 'onstru'tor (=hi'h takes a +onteGt), then 'all setVieEPQ to supply it =ith the !ie= to use an" set=urationPQ to set the "uration. >n'e your &oast is 'on&igure", 'all its shoEPQ metho", an" the message =ill be "isplaye". We =ill see an e;ample o& this in a'tion later in this 'hapter.

Alert! Alert!
0& you =oul" pre&er something in the more 'lassi' "ialog bo; style, =hat you =ant is an Alert=ialog. As =ith any other mo"al "ialog bo;, an Alert=ialog pops up, grabs the &o'us, an" stays there until 'lose" by the user. ?ou might use this &or a 'riti'al error, a !ali"ation message that 'annot be e&&e'ti!ely "isplaye" in the base a'ti!ity $0, or something else =here you are sure that the user nee"s to see the message an" nee"s to see it no=. 5he simplest =ay to 'onstru't an Alert=ialog is to use the 4uilder 'lass. *ollo=ing in true buil"er style, 4uilder o&&ers a series o& metho"s to
&&2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Sho)ing Pop#>p +essages

'on&igure an Alert=ialog, ea'h metho" returning the 4uilder &or easy 'haining. At the en", you 'all shoEPQ on the buil"er to "isplay the "ialog bo;. Commonly-use" 'on&iguration metho"s on 4uilder in'lu"e,

i& you =ant the Mbo"yM o& the "ialog to be a simple te;tual message, &rom either a supplie" 2tring or a supplie" string resour'e 0@.
set#essagePQ

an" setIconPQ, to 'on&igure the te;t an"Por i'on to appear in the title bar o& the "ialog bo;.
set&itlePQ set(ositive4uttonPQ, set%eutral4uttonPQ, an" set%egative4uttonPQ, to in"i'ate =hi'h button(s) shoul" appear a'ross the bottom o& the "ialog, =here they shoul" be positione" (le&t, 'enter, or right, respe'ti!ely), =hat their 'aptions shoul" be, an" =hat logi' shoul" be in!oke" =hen the button is 'li'ke" (besi"es "ismissing the "ialog).

0& you nee" to 'on&igure the Alert=ialog beyon" =hat the buil"er allo=s, instea" o& 'alling shoEPQ, 'all createPQ to get the partially-built Alert=ialog instan'e, 'on&igure it the rest o& the =ay, then 'all one o& the &la!ors o& shoEPQ on the Alert=ialog itsel&. >n'e shoEPQ is 'alle", the "ialog bo; =ill appear an" a=ait user input. 2ote that pressing any o& the buttons =ill 'lose the "ialog, e!en i& you ha!e registere" a listener &or the button in Ruestion. +en'e, i& all you nee" a button to "o is 'lose the "ialog, gi!e it a 'aption an" a null listener. 5here is no option, =ith Alert=ialog, to ha!e a button at the bottom in!oke a listener yet not 'lose the "ialog.

Checking Them ,ut


5o see ho= these =ork in pra'ti'e, take a peek at #essages/#essage, 'ontaining the &ollo=ing layout...,

&&7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Sho)ing Pop#>p +essages

LNGml version671.-7 encoding67utf-,7NM L4utton Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/alert7 android:teGt67?aise an alert7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:on+lick67shoEAlert7 /M

...an" Ca!a 'o"e,


public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ ; public void show$lertPVieE vieEQ : neE Alert=ialog.BuilderPthisQ .setTitleP7#essage=emo7Q .setMessageP7)etIs raise a toastX7Q .set&eutralButtonP7!ere8 hereX78 neE =ialogInterface.OnClickListenerPQ : public void onClickP=ialogInterface dlg8 int sumthinQ : &oast .makeTextP#essage=emo.this8 7Lclink8 clinkM78 &oast.)$%D&! 2!"?&Q .showPQJ ; ;Q .showPQJ ; ;

5he layout is unremarkable S Gust a really large 4utton to sho= the Alert=ialog. When you 'li'k the 4utton, =e use a buil"er (neE 4uilderPthisQ) to set the title (set&itleP7#essage=emo7Q), message (set#essageP7)etIs raise a toastX7Q), an" Mneutral buttonM (set%eutral4uttonP7!ere8 hereX78 neE "n+lick)istenerPQ ...) be&ore sho=ing the "ialog. When the button is 'li'ke", the "n+lick)istener 'allba'k triggers the &oast 'lass to make us a te;t-base" toast (make&eGtPthis8 7Lclink8 clinkM78 )$%D&! 2!"?&Q), =hi'h =e then shoEPQ. 5he result is a typi'al "ialog bo;,

&&8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Sho)ing Pop#>p +essages

"igure 881 The +essage/emo sample application@ after clicking the DCaise an alertD button

When you 'lose the "ialog !ia the button, it raises the toast,

&&:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Sho)ing Pop#>p +essages

"igure 8:1 The same application@ after clicking the D+ake a toastD button

&-<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1:

3andling Activity !ifecycle =vents

While this may soun" like a broken re'or"...please remember that An"roi" "e!i'es, by an" large, are phones. As su'h, some a'ti!ities are more important than others S taking a 'all is probably more important to users than is playing %u"oku. An", sin'e it is a phone, it probably has less AM than "oes your 'urrent "esktop or notebook. As a result, your a'ti!ity may &in" itsel& being kille" o&& be'ause other a'ti!ities are going on an" the system nee"s your a'ti!ity7s memory. 5hink o& it as the An"roi" eRui!alent o& the M'ir'le o& li&eM S your a'ti!ity "ies so others may li!e, an" so on. ?ou 'annot assume that your a'ti!ity =ill run until you think it is 'omplete, or e!en until the user thinks it is 'omplete. 5his is one e;ample S perhaps the most important e;ample S o& ho= an a'ti!ity7s li&e'y'le =ill a&&e't your o=n appli'ation logi'. 5his 'hapter 'o!ers the !arious states an" 'allba'ks that make up an a'ti!ity7s li&e'y'le an" ho= you 'an hook into them appropriately.

SchroedingerGs Activity
An a'ti!ity, generally speaking, is in one o& &our states at any point in time,

&-*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Activity !ifecycle =vents

Active, the a'ti!ity =as starte" by the user, is running, an" is in the &oregroun". 5his is =hat you are use" to thinking o& in terms o& your a'ti!ity7s operation. Paused, the a'ti!ity =as starte" by the user, is running, an" is !isible, but a noti&i'ation or something is o!erlaying part o& the s'reen. @uring this time, the user 'an see your a'ti!ity but may not be able to intera't =ith it. *or e;ample, i& a 'all 'omes in, the user =ill get the opportunity to take the 'all or ignore it. $topped, the a'ti!ity =as starte" by the user, is running, but it is hi""en by other a'ti!ities that ha!e been laun'he" or s=it'he" to. ?our appli'ation =ill not be able to present anything meaning&ul to the user "ire'tly, only by =ay o& a 2oti&i'ation. Dead, either the a'ti!ity =as ne!er starte" (e.g., Gust a&ter a phone reset) or the a'ti!ity =as terminate", perhaps "ue to la'k o& a!ailable memory.

!ife@ /eath@ and .our Activity


An"roi" =ill 'all into your a'ti!ity as the a'ti!ity transitions bet=een the &our states liste" abo!e. %ome transitions may result in multiple 'alls to your a'ti!ity, an" sometimes An"roi" =ill kill your appli'ation =ithout 'alling it. 5his =hole area is rather murky an" probably subGe't to 'hange, so pay 'lose attention to the o&&i'ial An"roi" "o'umentation as =ell as this se'tion =hen "e'i"ing =hi'h e!ents to pay attention to an" =hi'h you 'an sa&ely ignore. 2ote that &or all o& these, you shoul" 'hain up=ar" an" in!oke the super'lass7 e"ition o& the metho", or An"roi" may raise an e;'eption.

onCre te?@ nd onDestroy?@


We ha!e been implementing on+reatePQ in all o& our ActivitF sub'lasses in all the e;amples. 5his =ill get 'alle" in three situations,

&-&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Activity !ifecycle =vents

1.

When the a'ti!ity is &irst starte" (e.g., sin'e a system restart), on+reatePQ =ill be in!oke" =ith a null parameter.

2. 0& the a'ti!ity ha" been running, then sometime later =as kille" o&&, on+reatePQ =ill be in!oke" =ith the 4undle &rom on2aveInstance2tatePQ as a parameter (see belo=). .. 0& the a'ti!ity ha" been running an" you ha!e set up your a'ti!ity to ha!e "i&&erent resour'es base" on "i&&erent "e!i'e states (e.g., lan"s'ape !ersus portrait), your a'ti!ity =ill be re-'reate" an" on+reatePQ =ill be 'alle". +ere is =here you initialiKe your user inter&a'e an" set up anything that nee"s to be "one on'e, regar"less o& ho= the a'ti!ity gets use". >n the other en" o& the li&e'y'le, on=estroFPQ may be 'alle" =hen the a'ti!ity is shutting "o=n, either be'ause the a'ti!ity 'alle" finishPQ (=hi'h M&inishesM the a'ti!ity) or be'ause An"roi" nee"s AM an" is 'losing the a'ti!ity prematurely. 2ote that on=estroFPQ may not get 'alle" i& the nee" &or AM is urgent (e.g., in'oming phone 'all) an" that the a'ti!ity =ill Gust get shut "o=n regar"less. +en'e, on=estroFPQ is mostly &or 'leanly releasing resour'es you obtaine" in on+reatePQ (i& any).

onSt rt?@4 onRest rt?@4 nd onStop?@


An a'ti!ity 'an 'ome to the &oregroun" either be'ause it is &irst being laun'he", or be'ause it is being brought ba'k to the &oregroun" a&ter ha!ing been hi""en (e.g., by another a'ti!ity, by an in'oming phone 'all). 5he on2tartPQ metho" is 'alle" in either o& those 'ases. 5he on?estartPQ metho" is 'alle" in the 'ase =here the a'ti!ity ha" been stoppe" an" is no= restarting. Con!ersely, on2topPQ is 'alle" =hen the a'ti!ity is about to be stoppe".

&--

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Activity !ifecycle =vents

onP use?@ nd onResume?@


5he on?esumePQ metho" is 'alle" Gust be&ore your a'ti!ity 'omes to the &oregroun", either a&ter being initially laun'he", being restarte" &rom a stoppe" state, or a&ter a pop-up "ialog (e.g., in'oming 'all) is 'leare". 5his is a great pla'e to re&resh the $0 base" on things that may ha!e o''urre" sin'e the user last =as looking at your a'ti!ity. *or e;ample, i& you are polling a ser!i'e &or 'hanges to some in&ormation (e.g., ne= entries &or a &ee"), on?esumePQ is a &ine time to both re&resh the 'urrent !ie= an", i& appli'able, ki'k o&& a ba'kgroun" threa" to up"ate the !ie= (e.g., !ia a !andler). Con!ersely, anything that steals your user a=ay &rom your a'ti!ity S mostly, the a'ti!ation o& another a'ti!ity S =ill result in your on(ausePQ being 'alle". +ere, you shoul" un"o anything you "i" in on?esumePQ, su'h as stopping ba'kgroun" threa"s, releasing any e;'lusi!e-a''ess resour'es you may ha!e a'Ruire" (e.g., 'amera), an" the like. >n'e on(ausePQ is 'alle", An"roi" reser!es the right to kill o&& your a'ti!ity7s pro'ess at any point. +en'e, you shoul" not be relying upon re'ei!ing any &urther e!ents.

The (race of State


Mostly, the a&orementione" metho"s are &or "ealing =ith things at the appli'ation-general le!el (e.g., =iring together the last pie'es o& your $0 in on+reatePQ, 'losing "o=n ba'kgroun" threa"s in on(ausePQ). +o=e!er, a large part o& the goal o& An"roi" is to ha!e a patina o& seamlessness. A'ti!ities may 'ome an" go as "i'tate" by memory reRuirements, but users are, i"eally, una=are that this is going on. 0&, &or e;ample, they =ere using a 'al'ulator, an" 'ome ba'k to that 'al'ulator a&ter an absen'e, they shoul" see =hate!er number(s) they =ere =orking on originally S unless they themsel!es took some a'tion to 'lose "o=n the 'al'ulator (e.g., presse" the 1ACD button to e;it it).

&-%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Activity !ifecycle =vents

5o make all this =ork, a'ti!ities nee" to be able to sa!e their appli'ationinstan'e state, an" to "o so Rui'kly an" 'heaply. %in'e a'ti!ities 'oul" get kille" o&& at any time, a'ti!ities may nee" to sa!e their state more &reRuently than one might e;pe't. 5hen, =hen the a'ti!ity restarts, the a'ti!ity shoul" get its &ormer state ba'k, so it 'an restore the a'ti!ity to the =ay it appeare" pre!iously. 5hink o& it as establishing a bookmark, su'h that =hen the user returns to that bookmark, you 'an return the appli'ation to the same state as =hen they le&t it. %a!ing instan'e state is han"le" by on2aveInstance2tatePQ. 5his supplies a 4undle, into =hi'h a'ti!ities 'an pour =hate!er "ata they nee" (e.g., the number sho=ing on the 'al'ulator7s "isplay). 5his metho" implementation nee"s to be spee"y, so "o not try to "o too mu'h &an'y S Gust put your "ata in the 4undle an" e;it the metho". 5hat instan'e state is pro!i"e" to you again in t=o pla'es, 1. 0n on+reatePQ

2. 0n on?estoreInstance2tatePQ 0t is your 'hoi'e =hen you =ish to re-apply the state "ata to your a'ti!ity S either 'allba'k is a reasonable option. 5he built-in implementation o& on2aveInstance2tatePQ =ill sa!e likely mutable state &rom a subset o& =i"gets. *or e;ample, it =ill sa!e the te;t in an $dit&eGt, but it =ill not sa!e =hether or not a 4utton is enable" or "isable". 5his =orks so long as the =i"gets are uniRuely i"enti&ie" !ia their android:id attributes. +en'e, i& you implement on2aveInstance2tatePQ, you 'an ele't to either 'hain up=ar" an" le!erage the inherite" implementation or not an" o!erri"e the inherite" implementation. %imilarly, some a'ti!ities may not nee" on2aveInstance2tatePQ to be implemente" at all, as the built-in one han"les e!erything that is nee"e".

&-0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1;

3andling Cotation

%ome An"roi" han"sets o&&er a sli"e-out keyboar" that triggers rotating the s'reen &rom portrait to lan"s'ape. >ther han"sets use a''elerometers to "etermine =hen the s'reen rotates. As a result, it is reasonable to assume that s=it'hing &rom portrait to lan"s'ape an" ba'k again may be something your users =ill look to "o. An"roi" has a number o& =ays &or you to han"le s'reen rotation, so your appli'ation 'an properly han"le either orientation. All these &a'ilities "o is help you "ete't an" manage the rotation pro'ess S you are still reRuire" to make sure you ha!e layouts that look "e'ent on ea'h orientation.

A Philosophy of /estruction
1y "e&ault, =hen there is a 'hange in the phone 'on&iguration that might a&&e't resour'e sele'tion, An"roi" =ill "estroy an" re-'reate any running or pause" a'ti!ities the ne;t time they are to be !ie=e". While this 'oul" happen &or a !ariety o& "i&&erent 'on&iguration 'hanges (e.g., 'hange o& language sele'tion), it =ill most likely trip you up mostly &or rotations, sin'e a 'hange in orientation 'an 'ause you to loa" a "i&&erent set o& resour'es (e.g., layouts). 5he types o& 'on&iguration 'hanges that trigger this "estroy-an"-re'reate beha!ior in'lu"e,

>rientation 'hanges (i.e., rotating the s'reen)


&-7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

E;ten"ing or hi"ing a physi'al keyboar", &or "e!i'es that ha!e su'h sli"ing keyboar"s #utting the "e!i'e in a 'ar or "esk "o'k, or remo!ing it &rom a "o'k Changing the lo'ale, an" thereby 'hanging the pre&erre" language

5he key here is that this is the "e&ault beha!ior. 0t is probably the beha!ior that is best &or most o& your a'ti!ities. ?ou "o ha!e some 'ontrol o!er the matter, though, an" 'an tailor ho= your a'ti!ities respon" to orientation 'hanges or similar 'on&iguration s=it'hes.

tGs All The Same@ 6ust /ifferent


%in'e, by "e&ault, An"roi" "estroys an" re-'reates your a'ti!ity on a rotation, you may only nee" to hook into the same on2aveInstance2tatePQ that you =oul" i& your a'ti!ity =ere "estroye" &or any other reason (e.g., lo= memory). 0mplement that metho" in your a'ti!ity an" &ill in the supplie" 4undle =ith enough in&ormation to get you ba'k to your 'urrent state. 5hen, in on+reatePQ (or on?estoreInstance2tatePQ, i& you pre&er), pi'k the "ata out o& the 4undle an" use it to bring your a'ti!ity ba'k to the =ay it =as. 5o "emonstrate this, let7s take a look at the ?otation/?otation"ne proGe't. 0t, an" the other sample proGe'ts use" in this 'hapter, use a pair o& main.Gml layouts, one in res/laFout/ an" one in res/laFout-land/ &or use in lan"s'ape mo"e. +ere is the portrait layout,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L4utton android:id67ORid/pick7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 android:teGt67(ick7 android:enabled67true7 android:on+lick67pick+ontact7 /M

&-8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

L4utton android:id67ORid/vieE7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 android:teGt67VieE7 android:enabled67false7 android:on+lick67vieE+ontact7 /M L/)inear)aFoutM

While here is the similar lan"s'ape layout,


LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67horiKontal7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L4utton android:id67ORid/pick7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 android:teGt67(ick7 android:enabled67true7 android:on+lick67pick+ontact7 /M L4utton android:id67ORid/vieE7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 android:teGt67VieE7 android:enabled67false7 android:on+lick67vieE+ontact7 /M L/)inear)aFoutM

1asi'ally, it is a pair o& buttons, ea'h taking up hal& the s'reen. 0n portrait mo"e, the buttons are sta'ke"T in lan"s'ape mo"e, they are si"e-by-si"e. 0& you =ere to simply 'reate a proGe't, put in those t=o layouts, an" 'ompile it, the appli'ation =oul" appear to =ork Gust &ine S a rotation ( L+trlM-L91>M in the emulator) =ill 'ause the layout to 'hange. An" =hile buttons la'k state, i& you =ere using other =i"gets (e.g., $dit&eGt), you =oul" e!en &in" that An"roi" hangs onto some o& the =i"get state &or you (e.g., the te;t entere" in the $dit&eGt).

&-:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

What An"roi" 'annot automati'ally help you =ith is anything hel" outsi"e the =i"gets.

Pic$in! nd >ie#in!

Cont ct

5his appli'ation lets you pi'k a 'onta't, then !ie= the 'onta't, !ia separate buttons, =ith the M-ie=M button only enable" =hen =e a'tually ha!e a 'onta't. Let us take a 'loser look at ho= this &eat is a''omplishe". When the user 'li'ks the #i'k button, =e 'all startActivitF9or?esultPQ. 5his is a !ariation on startActivitFPQ, "esigne" &or a'ti!ities that are set up to return some sort o& result S a user7s 'hoi'e o& &ile, or 'onta't, or =hate!er. elati!ely &e= a'ti!ities are set up this =ay, so you 'annot e;pe't to 'all startActivitF9or?esultPQ an" get ans=ers &rom any a'ti!ity you 'hoose. 0n this 'ase, =e =ant to pi'k a 'onta't. 5here is an A+&I"% (I+H Intent a'tion a!ailable in An"roi", "esigne" &or this sort o& s'enario. An A+&I"% (I+H Intent in"i'ates to An"roi" that =e =ant to pi'k...something. 5he MsomethingM is "etermine" by the 3ri =e put in the 0ntent. 0n our 'ase, it turns out that =e 'an use an A+&I"% (I+H Intent &or 'ertain system-"e&ine" 3ri !alues to let the user pi'k a 'onta't out o& the "e!i'e7s 'onta'ts. 0n parti'ular, on An"roi" 2.0 an" higher, =e 'an use android.provider.+ontacts+ontract.+ontacts.+"%&$%& 3?I &or this purpose,
public void pickContactPVieE vQ : Intent i6neE IntentPIntent.A+&I"% (I+H8 +ontacts.+"%&$%& 3?IQJ start$cti!ity"or%esultPi8 (I+H ?$Y3$2&QJ ;

*or

An"roi"

1./

an"

android.provider.+ontacts.+"%&$%& 3?I

ol"er, there is that =e 'oul" use.

separate

5he se'on" parameter to startActivitF9or?esultPQ is an i"enti&ying number, to help us "istinguish this 'all to startActivitF9or?esultPQ &rom any others =e might make.
&%<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

Calling startActivitF9or?esultPQ =ith an A+&I"% (I+H Intent &or the +ontacts.+"%&$%& 3?I =ill bring up a 'onta't-pi'ker a'ti!ity, supplie" by An"roi". When the user taps a 'onta't, the pi'ker a'ti!ity en"s (e.g., !ia finishPQ), an" 'ontrol returns to our a'ti!ity. At that point, our a'ti!ity is 'alle" =ith onActivitF?esultPQ. An"roi" supplies us =ith three pie'es o& in&ormation, 1. 5he i"enti&ying number =e supplie" to startActivitF9or?esultPQ, so =e 'an mat'h this result to its original reRuest

2. A result status, either ?$23)& "H or ?$23)& +A%+$)$=, to in"i'ate i& the user ma"e a positi!e sele'tion or i& the user aban"one" the pi'ker (e.g., by 'li'king the 1ACD button) .. An 0ntent that represents the result "ata itsel&, &or a ?$23)& "H response 5he "etails o& =hat is in the Intent =ill nee" to be "o'umente" by the a'ti!ity that you 'alle". 0n the 'ase o& an A+&I"% (I+H Intent &or the +ontacts.+"%&$%& 3?I, the returne" Intent has its o=n 3ri (!ia get=ataPQ) that represents the 'hosen 'onta't. 0n the ?otation"ne e;ample, =e sti'k that in a "ata member o& the a'ti!ity an" enable the -ie= button,
O"verride protected void on$cti!ity%esultPint reUuest+ode8 int result+ode8 Intent dataQ : if PreUuest+ode66(I+H ?$Y3$2&Q : if Presult+ode66?$23)& "HQ : contact6data.getDataPQJ vieE4utton.set+na'ledPtrueQJ ; ; ;

0& the user 'li'ks the no=-enable" -ie= button, =e 'reate an A+&I"% VI$@ Intent on the 'onta't7s 3ri, an" 'all startActivitFPQ on that Intent,
public void !iewContactPVieE vQ : start$cti!ityPneE IntentPIntent.A+&I"% VI$@8 contactQQJ ;

&%*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

5his =ill bring up an An"roi"-supplie" a'ti!ity to !ie= "etails o& that 'onta't.

S vin! 3our St te
8i!en that =e ha!e use" startActivitF9or?esultPQ to pi'k a 'onta't, no= =e nee" to hang onto that 'onta't =hen the s'reen orientation 'hanges. 0n the ?otation"ne e;ample, =e "o this !ia on2aveInstance2tatePQ,
package com.commonsEare.android.rotation.oneJ import import import import import import import import android.app.ActivitFJ android.content.IntentJ android.net.3riJ android.os.4undleJ android.provider.+ontacts+ontract.+ontactsJ android.vieE.VieEJ android.Eidget.4uttonJ android.util.)ogJ

public class ?otation"ne=emo eGtends ActivitF : static final int (I+H ?$Y3$2&61CC/J 4utton vieE4utton6nullJ 3ri contact6nullJ O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ vieE4utton6P4uttonQfindViewByIdP?.id.vieEQJ restoreMePsavedInstance2tateQJ ; vieE4utton.set+na'ledPcontactX6nullQJ

O"verride protected void on$cti!ity%esultPint reUuest+ode8 int result+ode8 Intent dataQ : if PreUuest+ode66(I+H ?$Y3$2&Q : if Presult+ode66?$23)& "HQ : contact6data.getDataPQJ vieE4utton.set+na'ledPtrueQJ ; ; ; public void pickContactPVieE vQ : Intent i6neE IntentPIntent.A+&I"% (I+H8 +ontacts.+"%&$%& 3?IQJ &%&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

start$cti!ity"or%esultPi8 (I+H ?$Y3$2&QJ

public void !iewContactPVieE vQ : start$cti!ityPneE IntentPIntent.A+&I"% VI$@8 contactQQJ ; O"verride protected void onSa!eInstanceStateP4undle out2tateQ : super.onSa!eInstanceStatePout2tateQJ if PcontactX6nullQ : out2tate.putStringP7contact78 contact.toStringPQQJ ; ; private void restoreMeP4undle stateQ : contact6nullJ if PstateX6nullQ : 2tring contact3ri6state.getStringP7contact7QJ if Pcontact3riX6nullQ : contact63ri.parsePcontact3riQJ ;

; ; ;

1y an" large, it looks like a normal a'ti!ity...be'ause it is. 0nitially, the Mmo"elM S a 3ri name" contact S is null. 0t is set as the result o& spa=ning the A+&I"% (I+H sub-a'ti!ity. 0ts string representation is sa!e" in on2aveInstance2tatePQ an" restore" in restore#ePQ ('alle" &rom on+reatePQ). 0& the 'onta't is not null, the M-ie=M button is enable" an" 'an be use" to !ie= the 'hosen 'onta't. -isually, it looks pretty mu'h as one =oul" e;pe't,

&%-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

"igure :<1 The Cotation,ne application@ in portrait mode

"igure :*1 The Cotation,ne application@ in landscape mode

5he bene&it to this implementation is that it han"les a number o& system e!ents beyon" mere rotation, su'h as being 'lose" by An"roi" "ue to lo= memory. *or &un, 'omment out the restore#ePQ 'all in on+reatePQ an" try running the appli'ation. ?ou =ill see that the appli'ation M&orgetsM a 'onta't sele'te" in one orientation =hen you rotate the emulator or "e!i'e.

&%%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

?o) With +ore Savings!


5he problem =ith on2aveInstance2tatePQ is that you are limite" to a 4undle. 5hat7s be'ause this 'allba'k is also use" in 'ases =here your =hole pro'ess might be terminate" (e.g., lo= memory), so the "ata to be sa!e" has to be something that 'an be serialiKe" an" has no "epen"en'ies upon your running pro'ess. *or some a'ti!ities, that limitation is not a problem. *or others, though, it is more annoying. 5ake an online 'hat, &or e;ample. ?ou ha!e no means o& storing a so'ket in a 4undle, so by "e&ault, you =ill ha!e to "rop your 'onne'tion to the 'hat ser!er an" re-establish it. 5hat not only may be a per&orman'e hit, but it might also a&&e't the 'hat itsel&, su'h as you appearing in the 'hat logs as "is'onne'ting an" re'onne'ting. >ne =ay to get past this is to use on?etain%on+onfigurationInstancePQ instea" o& on2aveInstance2tatePQ &or MlightM 'hanges like a rotation. ?our a'ti!ity7s on?etain%on+onfigurationInstancePQ 'allba'k 'an return an "bject, =hi'h you 'an retrie!e later !ia get)ast%on+onfigurationInstancePQ. 5he "bject 'an be Gust about anything you =ant S typi'ally, it =ill be some kin" o& M'onte;tM obGe't hol"ing a'ti!ity state, su'h as running threa"s, open so'kets, an" the like. ?our a'ti!ity7s on+reatePQ 'an 'all get)ast%on+onfigurationInstancePQ S i& you get a non-null response, you no= ha!e your so'kets an" threa"s an" =hatnot. 5he biggest limitation is that you "o not =ant to put in the sa!e" 'onte;t anything that might re&eren'e a resour'e that =ill get s=appe" out, su'h as a =raEable loa"e" &rom a resour'e. Let7s take a look at the ?otation/?otation&Eo sample proGe't, =hi'h uses this approa'h to han"ling rotations. 5he layouts, an" hen'e the !isual appearan'e, is the same as =ith ?otation/?otation"ne. Where things "i&&er slightly is in the Ca!a 'o"e,
package com.commonsEare.android.rotation.tEoJ import android.app.ActivitFJ import android.content.IntentJ import android.net.3riJ

&%0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

import import import import import

android.os.4undleJ android.provider.+ontacts+ontract.+ontactsJ android.vieE.VieEJ android.Eidget.4uttonJ android.util.)ogJ

public class ?otation&Eo=emo eGtends ActivitF : static final int (I+H ?$Y3$2&61CC/J 4utton vieE4utton6nullJ 3ri contact6nullJ O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ vieE4utton6P4uttonQfindViewByIdP?.id.vieEQJ restoreMePQJ ; vieE4utton.set+na'ledPcontactX6nullQJ

O"verride protected void on$cti!ity%esultPint reUuest+ode8 int result+ode8 Intent dataQ : if PreUuest+ode66(I+H ?$Y3$2&Q : if Presult+ode66?$23)& "HQ : contact6data.getDataPQJ vieE4utton.set+na'ledPtrueQJ ; ; ; public void pickContactPVieE vQ : Intent i6neE IntentPIntent.A+&I"% (I+H8 +ontacts.+"%&$%& 3?IQJ ; start$cti!ity"or%esultPi8 (I+H ?$Y3$2&QJ

public void !iewContactPVieE vQ : start$cti!ityPneE IntentPIntent.A+&I"% VI$@8 contactQQJ ; O"verride public "bject on%etain&onConfigurationInstance PQ : returnPcontactQJ ; private void restoreMePQ : contact6nullJ if PgetLast&onConfigurationInstance PQX6nullQ : contact6P3riQgetLast&onConfigurationInstance PQJ

&%2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

; ; ;

0n this 'ase, =e o!erri"e on?etain%on+onfigurationInstancePQ, returning the a'tual 3ri &or our 'onta't, rather than a string representation o& it. 0n turn, restore#ePQ 'alls get)ast%on+onfigurationInstancePQ, an" i& it is not null, =e hol" onto it as our 'onta't an" enable the M-ie=M button. 5he a"!antage here is that =e are passing aroun" the 3ri rather than a string representation. 0n this 'ase, that is not a big sa!ings. 1ut our state 'oul" be mu'h more 'ompli'ate", in'lu"ing threa"s an" so'kets an" other things =e 'annot pa'k into a 4undle.

/ . Cotation
E!en this, though, may still be too intrusi!e to your appli'ation. %uppose, &or e;ample, you are 'reating a real-time game, su'h as a &irst-person shooter. 5he Mhi''upM your users e;perien'e as your a'ti!ity is "estroye" an" re-'reate" might be enough to get them shot, =hi'h they may not appre'iate. While this =oul" be less o& an issue on the 5-Mobile 81, sin'e a rotation reRuires sli"ing open the keyboar" an" there&ore is unlikely to be "one mi"-game, other "e!i'es might rotate base" solely upon the "e!i'e7s position as "etermine" by a''elerometers. 5he thir" possibility &or han"ling rotations, there&ore, is to tell An"roi" that you =ill han"le them 'ompletely yoursel& an" that you "o not =ant assistan'e &rom the &rame=ork. 5o "o this, 1. #ut an android:config+hanges entry in your Android#anifest.Gml &ile, listing the 'on&iguration 'hanges you =ant to han"le yoursel& !ersus allo=ing An"roi" to han"le &or you

2. 0mplement on+onfiguration+hangedPQ in your ActivitF, =hi'h =ill be 'alle" =hen one o& the 'on&iguration 'hanges you liste" in android:config+hanges o''urs

&%7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

2o=, &or any 'on&iguration 'hange you =ant, you 'an bypass the =hole a'ti!ity-"estru'tion pro'ess an" simply get a 'allba'k letting you kno= o& the 'hange. 5o see this in a'tion, turn to the ?otation/?otation&hree sample appli'ation. >n'e again, our layouts are the same, so the appli'ation looks the same as the pre'e"ing t=o samples. +o=e!er, the Ca!a 'o"e is signi&i'antly "i&&erent, be'ause =e are no longer 'on'erne" =ith sa!ing our state, but rather =ith up"ating our $0 to "eal =ith the layout. 1ut &irst, =e nee" to make a small 'hange to our mani&est,
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.rotation.three7 android:version+ode6717 android:version%ame671.-.-7M Luses-sdk android:min2dkVersion67.7 android:target2dkVersion6707/M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67.?otation&hree=emo7 android:label67Ostring/app name7 android:config+hanges67keFboard!iddenW orientation7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

+ere, =e state that =e =ill han"le keFboard!idden an" orientation 'on&iguration 'hanges oursel!es. 5his 'o!ers us &or any 'ause o& the MrotationM S =hether it is a sli"ing keyboar" or a physi'al rotation. 2ote that this is set on the a'ti!ity, not the appli'ation S i& you ha!e se!eral a'ti!ities, you =ill nee" to "e'i"e &or ea'h =hi'h o& the ta'ti's outline" in this 'hapter you =ish to use. 0n a""ition, =e nee" to a"" an android:id to our )inear)aFout 'ontainers, su'h as,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7

&%8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

android:id67ORid/container7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L4utton android:id67ORid/pick7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 android:teGt67(ick7 android:enabled67true7 android:on+lick67pick+ontact7 /M L4utton android:id67ORid/vieE7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 android:teGt67VieE7 android:enabled67false7 android:on+lick67vieE+ontact7 /M L/)inear)aFoutM

5he Ca!a 'o"e &or this proGe't is sho=n belo=,


package com.commonsEare.android.rotation.threeJ import import import import import import import import import android.app.ActivitFJ android.content.IntentJ android.content.res.+onfigurationJ android.net.3riJ android.os.4undleJ android.provider.+ontacts+ontract.+ontactsJ android.vieE.VieEJ android.Eidget.4uttonJ android.Eidget.)inear)aFoutJ

public class ?otation&hree=emo eGtends ActivitF : static final int (I+H ?$Y3$2&61CC/J 4utton vieE4utton6nullJ 3ri contact6nullJ O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ vieE4utton6P4uttonQfindViewByIdP?.id.vieEQJ vieE4utton.set+na'ledPcontactX6nullQJ ; O"verride protected void on$cti!ity%esultPint reUuest+ode8 int result+ode8

&%:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

Intent dataQ : if PreUuest+ode66(I+H ?$Y3$2&Q : if Presult+ode66?$23)& "HQ : contact6data.getDataPQJ vieE4utton.set+na'ledPtrueQJ ; ; ; public void pickContactPVieE vQ : Intent i6neE IntentPIntent.A+&I"% (I+H8 +ontacts.+"%&$%& 3?IQJ ; start$cti!ity"or%esultPi8 (I+H ?$Y3$2&QJ

public void !iewContactPVieE vQ : start$cti!ityPneE IntentPIntent.A+&I"% VI$@8 contactQQJ ; public void onConfigurationChangedP+onfiguration neE+onfigQ : super.onConfigurationChangedPneE+onfigQJ )inear)aFout container6P)inear)aFoutQfindViewByIdP?.id.containerQJ if PneE+onfig.orientation66+onfiguration."?I$%&A&I"% )A%=2+A($Q : container.setOrientationP)inear)aFout.!"?IV"%&A)QJ ; else : container.setOrientationP)inear)aFout.V$?&I+A)QJ ; ; ;

>ur on+onfiguration+hangedPQ nee"s to up"ate the $0 to re&le't the orientation 'hange. +ere, =e &in" our )inear)aFout an" tell it to 'hange its orientation to mat'h that o& the "e!i'e. 5he orientation &iel" on the +onfiguration obGe't =ill tell us ho= the "e!i'e is oriente".

AAABut Goo!le Does "ot Recommend This


?ou might think that on+onfiguration+hangedPQ an" android:config+hanges =oul" be the ultimate solution. A&ter all, =e no longer ha!e to =orry about all that messy passing o& "ata to the ne= a'ti!ity as the ol" one is being "estroye". 5he on+onfiguration+hangedPQ approa'h is !ery se;y. +o=e!er, 8oogle "oes not re'ommen" it.
&0<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

5he

is &orgetting about resour'es. With the on+onfiguration+hangedPQ approa'h, you must take steps to ensure that ea'h an" e!ery resour'e that might possibly ha!e 'hange" as a result o& this 'on&iguration 'hange gets up"ate". 5hat in'lu"es strings, layouts, "ra=ables, menus, animations, pre&eren'es, "imensions, 'olors, an" all the others. 0& you are in'omplete, your app =ill ha!e a =hole series o& little (or not so little) bugs as a result. Allo=ing An"roi" to "estroy an" re'reate your a'ti!ity guarantees you =ill get the proper resour'es. All you nee" to "o is arrange to pass the proper "ata &rom the ol" to the ne= a'ti!ity. 5he on+onfiguration+hangedPQ approa'h is there =here the user =oul" be "ire'tly a&&e'te" by a "estroy-an"-'reate 'y'le. *or e;ample, imagine a !i"eo player appli'ation, playing a streaming !i"eo. @estroying an" re'reating the a'ti!ity =oul" ne'essarily 'ause us to ha!e to re'onne't to the stream, losing our bu&&ere" "ata. $sers =ill get &rustrate" i& an a''i"ental mo!ement 'auses the "e!i'e to 'hange orientation an" interrupt their !i"eo playba'k. 0n this 'ase, sin'e the user =ill per'ei!e problems =ith a "estroy-an"-'reate 'y'le, on+onfiguration+hangedPQ is an appropriate 'hoi'e.

primary

'on'ern

"orcing the ssue


%ome a'ti!ities simply are not really meant to 'hange orientation. 8ames, 'amera pre!ie=s, !i"eo players, an" the like may only make sense in lan"s'ape, &or e;ample. While most a'ti!ities shoul" allo= the user to =ork in any "esire" orientation, &or a'ti!ities =here this makes no sense, you 'an 'ontrol it. 5o blo'k An"roi" &rom rotating your a'ti!ity, all you nee" to "o is a"" android:screen"rientation 6 7portrait7 (or 7landscape7, as you pre&er) to your Android#anifest.Gml &ile, as sho=n belo= (&rom the ?otation/?otation9our sample proGe't),
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7

&0*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

package67com.commonsEare.android.rotation.four7 android:version+ode6717 android:version%ame671.-.-7M Luses-sdk android:min2dkVersion67.7 android:target2dkVersion6707/M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67.?otation9our=emo7 android:screen"rientation67portrait7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

%in'e this is applie" on a per-a'ti!ity basis, you =ill nee" to "e'i"e =hi'h o& your a'ti!ities may nee" this turne" on. At this point, your a'ti!ity is lo'ke" into =hate!er orientation you spe'i&ie", regar"less o& =hat you "o. 5he &ollo=ing s'reen shots sho= the same a'ti!ity as in the pre!ious three se'tions, but using the abo!e mani&est an" =ith the emulator set &or both portrait an" lan"s'ape orientation. 2ote that the $0 "oes not mo!e a bit, but remains in portrait mo"e.

"igure :&1 The Cotation"our application@ in portrait mode

&0&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

"igure :-1 The Cotation"our application@ in landscape mode

2ote that An"roi" =ill still "estroy an" re'reate your a'ti!ity, e!en i& you ha!e the orientation set to a spe'i&i' !alue as sho=n here. 0& you =ish to a!oi" that, you =ill also nee" to set android:config+hanges in the mani&est, as "es'ribe" earlier in this 'hapter. >r, you 'an still use on2aveInstance2tatePQ or on?etain%on+onfigurationInstancePQ to sa!e your a'ti!ity7s mutable state.

+aking Sense of it All


As note" at the top o& this 'hapter, "e!i'es =ith si"e-sli"er keyboar"s (5Mobile 81, Motorola @ >0@PMilestone, et'.) 'hange s'reen orientation =hen the keyboar" is e;pose" or hi""en, =hereas other "e!i'es 'hange s'reen orientation base" upon the a''elerometer.

&0-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Cotation

0& you ha!e an a'ti!ity that shoul" 'hange orientation base" on the a''elerometer, e!en i& the "e!i'e has a si"e-sli"er keyboar", Gust a"" android:screen"rientation 6 7sensor7 to your Android#anifest.Gml &ile (as seen in the ?otation/?otation9ive sample proGe't),
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.rotation.five7 android:version+ode6717 android:version%ame671.-.-7M Luses-sdk android:min2dkVersion67.7 android:target2dkVersion6707/M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67.?otation9ive=emo7 android:screen"rientation67sensor7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

5he 6sensor9, in this 'ase, tells An"roi" you =ant the a''elerometers to 'ontrol the s'reen orientation, so the physi'al shi&t in the "e!i'e orientation 'ontrols the s'reen orientation. An"roi" 2.. a""s a number o& other possible !alues &or android:orientation, in'lu"ing,

an" reverse(ortrait, in"i'ating that you =ant the s'reen to be in lan"s'ape or portrait, respe'ti!ely, but Mupsi"e "o=nM 'ompare" to the normal lan"s'ape an" portrait orientations
reverse)andscape

an" sensor(ortrait, in"i'ating you =ant to be lo'ke" to lan"s'ape or portrait, respe'ti!ely, but the sensors 'an be use" to "etermine =hi'h si"e is MupM
sensor)andscape full2ensor,

=hi'h allo=s the sensors to put the s'reen in any o& the &our possible orientations (portrait, re!erse portrait, lan"s'ape, re!erse lan"s'ape), =hereas sensor only toggles bet=een portrait an" lan"s'ape

&0%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &<

/ealing )ith Threads

$sers like snappy appli'ations. $sers "o not like appli'ations that &eel sluggish. 5he =ay to help your appli'ation &eel snappy is to use the stan"ar" threa"ing 'apabilities built into An"roi". 5his 'hapter =ill go through the issues in!ol!e" =ith threa" management in An"roi" an" =ill =alk you through some o& the options &or keeping the user inter&a'e 'risp an" responsi!e.

The +ain Application Thread


When you 'all set&eGtPQ on a &eGtVieE, you probably think that the s'reen is up"ate" =ith the te;t you supply, right then an" there. ?ou =oul" be mistaken. ather, e!erything that mo"i&ies the =i"get-base" $0 goes through a message Rueue. Calls to set&eGtPQ "o not up"ate the s'reen S they Gust pop a message on a Rueue telling the operating system to up"ate the s'reen. 5he operating system pops these messages o&& o& this Rueue an" "oes =hat the messages reRuire. 5he Rueue is pro'esse" by one threa", !ariously 'alle" the Mmain appli'ation threa"M an" the M$0 threa"M. %o long as that threa" 'an keep
&00
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

pro'essing messages, the s'reen =ill up"ate, user input =ill be han"le", an" so on. +o=e!er, the main appli'ation threa" is also use" &or nearly all 'allba'ks into your a'ti!ity. ?our on+reatePQ, on+lickPQ, on)istItem+lickPQ, an" similar metho"s are all 'alle" on the main appli'ation threa". While your 'o"e is e;e'uting in these metho"s, An"roi" is not pro'essing messages on the Rueue, an" so the s'reen "oes not up"ate, user input is not han"le", an" so on. 5his, o& 'ourse, is ba". %o ba", that i& you take more than a &e= se'on"s to "o =ork on the main appli'ation threa", An"roi" may "isplay the "rea"e" MAppli'ation 2ot espon"ingM "ialog (A2 &or short), an" your a'ti!ity may be kille" o&&. +en'e, you =ant to make sure that all o& your =ork on the main appli'ation threa" happens Rui'kly. 5his means that anything slo= shoul" be "one in a ba'kgroun" threa", so as not to tie up the main appli'ation threa". 5his in'lu"es things like,

0nternet a''ess, su'h as sen"ing "ata to a Web ser!i'e or "o=nloa"ing an image %igni&i'ant &ile operations, sin'e &lash storage 'an be remarkably slo= at times Any sort o& 'omple; 'al'ulations

*ortunately, An"roi" supports threa"s using the stan"ar" &hread 'lass &rom Ca!a, plus all o& the =rappers an" 'ontrol stru'tures you =oul" e;pe't, su'h as the java.util.concurrent 'lass pa'kage. +o=e!er, there is one big limitation, you 'annot mo"i&y the $0 &rom a ba'kgroun" threa". ?ou 'an only mo"i&y the $0 &rom the main appli'ation threa". +en'e, you nee" to get long-running =ork mo!e" into ba'kgroun" threa"s, but those threa"s nee" to "o something to arrange to up"ate the $0 using
&02

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

the main appli'ation threa". *ortunately, An"roi" pro!i"es a =i"e range o& tools to "o Gust that, an" these tools are the primary &o'us o& this 'hapter.

+aking Progress )ith ProgressBars


0& you are going to &ork ba'kgroun" threa"s to "o =ork on behal& o& the user, you =ill =ant to think about keeping the user in&orme" that =ork is going on. 5his is parti'ularly true i& the user is e&&e'ti!ely =aiting &or that ba'kgroun" =ork to 'omplete. 5he typi'al approa'h to keeping users in&orme" o& progress is some &orm o& progress bar, like you see =hen you 'opy a bun'h o& &iles &rom pla'e to pla'e in many "esktop operating systems. An"roi" supports this through the (rogress4ar =i"get. A (rogress4ar keeps tra'k o& progress, "e&ine" as an integer, =ith in"i'ating no progress has been ma"e. ?ou 'an "e&ine the ma;imum en" o& the range S =hat !alue in"i'ates progress is 'omplete S !ia set#aGPQ. 1y "e&ault, a (rogress4ar starts =ith a progress o& -, though you 'an start &rom some other position !ia set(rogressPQ. 0& you pre&er your progress bar to be in"eterminate, use setIndeterminatePQ, setting it to true. 0n your Ca!a 'o"e, you 'an either positi!ely set the amount o& progress that has been ma"e (!ia set(rogressPQ) or in'rement the progress &rom its 'urrent amount (!ia increment(rogress4FPQ). ?ou 'an &in" out ho= mu'h progress has been ma"e !ia get(rogressPQ. 5here are other alternati!es S (rogress=ialog, progress in"i'ator in the a'ti!ity7s title bar, et'. S but a (rogress4ar is a goo" pla'e to start.

&07

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

(etting Through the 3andlers


5he most &le;ible means o& making an An"roi"-&rien"ly ba'kgroun" threa" is to 'reate an instan'e o& a !andler sub'lass. ?ou only nee" one !andler obGe't per a'ti!ity, an" you "o not nee" to manually register it or anything S merely 'reating the instan'e is su&&i'ient to register it =ith the An"roi" threa"ing subsystem. ?our ba'kgroun" threa" 'an 'ommuni'ate =ith the !andler, =hi'h =ill "o all o& its =ork on the a'ti!ity7s $0 threa". 5his is important, as $0 'hanges, su'h as up"ating =i"gets, shoul" only o''ur on the a'ti!ity7s $0 threa". ?ou ha!e t=o options &or 'ommuni'ating =ith the !andler, messages an" ?unnable obGe'ts.

%ess !es
5o sen" a #essage to a !andler, &irst in!oke obtain#essagePQ to get the obGe't out o& the pool. 5here are a &e= &la!ors o& obtain#essagePQ, allo=ing you to Gust 'reate empty #essage obGe'ts, or ones populate" =ith message i"enti&iers an" arguments. 5he more 'ompli'ate" your !andler pro'essing nee"s to be, the more likely it is you =ill nee" to put "ata into the #essage to help the !andler "istinguish "i&&erent e!ents.
#essage

5hen, you sen" the #essage to the !andler !ia its message Rueue, using one o& the send#essage...PQ &amily o& metho"s, su'h as,
send#essagePQ

puts the message on the Rueue imme"iately

puts the message on the Rueue imme"iately, an" moreo!er puts it at the &ront o& the message Rueue (!ersus the ba'k, as is the "e&ault), so your message takes priority o!er all others
send#essageAt9ront"fYueuePQ

puts the message on the Rueue at the state" time, e;presse" in the &orm o& millise'on"s base" on system uptime (2Fstem+lock.uptime#illisPQ)
send#essageAt&imePQ

&08

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

send#essage=elaFedPQ send$mptF#essagePQ,

puts the message on the Rueue a&ter a "elay, e;presse" in millise'on"s =hi'h sen"s an empty #essage obGe't to the Rueue, allo=ing you to skip the obtain#essagePQ step i& you =ere planning on lea!ing it empty any=ay

5o

these messages, your !andler nee"s to implement handle#essagePQ, =hi'h =ill be 'alle" =ith ea'h message that appears on the message Rueue. 5here, the han"ler 'an up"ate the $0 as nee"e". +o=e!er, it shoul" still "o that =ork Rui'kly, as other $0 =ork is suspen"e" until the !andler is "one. *or e;ample, let7s 'reate a (rogress4ar an" up"ate it !ia a !andler. +ere is the layout &rom the &hreads/!andler sample proGe't,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L(rogress4ar android:id67ORid/progress7 stFle67Nandroid:attr/progress4ar2tFle!oriKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L/)inear)aFoutM

pro'ess

5he (rogress4ar, in a""ition to setting the =i"th an" height as normal, also employs the stFle property. 5his parti'ular style in"i'ates this (rogress4ar shoul" be "ra=n as the tra"itional horiKontal bar sho=ing the amount o& =ork that has been 'omplete". An" here is the Ca!a,
package com.commonsEare.android.threadsJ import import import import import import android.app.ActivitFJ android.os.4undleJ android.os.!andlerJ android.os.#essageJ android.Eidget.(rogress4arJ java.util.concurrent.atomic.Atomic4ooleanJ

&0:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

public class !andler=emo eGtends ActivitF : (rogress4ar barJ !andler handler6neE (andlerPQ : O"verride public void handleMessageP#essage msgQ : bar.increment)rogressByP.QJ ; ;J Atomic4oolean is?unning6neE $tomicBooleanPfalseQJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ bar6P(rogress4arQfindViewByIdP?.id.progressQJ ; public void onStartPQ : super.onStartPQJ bar.set)rogressP-QJ &hread background6neE ThreadPneE %unna'lePQ : public void runPQ : trF : for Pint i6-JiL>- ZZ is?unning.getPQJiRRQ : &hread.sleepP1---QJ handler.sendMessagePhandler.o'tainMessagePQQJ ; ; catch P&hroEable tQ : // just end the background thread ; ; ;QJ is?unning.setPtrueQJ background.startPQJ

public void onStopPQ : super.onStopPQJ is?unning.setPfalseQJ ;

As part o& 'onstru'ting the ActivitF, =e 'reate an instan'e o& !andler, =ith our implementation o& handle#essagePQ. 1asi'ally, &or any message re'ei!e", =e up"ate the (rogress4ar by . points, then e;it the message han"ler.

&2<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

We then take a"!antage o& on2tartPQ an" on2topPQ. 0n on2tartPQ, =e set up a ba'kgroun" threa". 0n a real system, this threa" =oul" "o something meaning&ul. +ere, =e Gust sleep one se'on", post a #essage to the !andler, an" repeat &or a total o& >- passes. 5his, 'ombine" =ith the A-point in'rease in the (rogress4ar position, =ill mar'h the bar 'lear a'ross the s'reen, as the "e&ault ma;imum !alue &or (rogress4ar is 1--. ?ou 'an a"Gust that ma;imum !ia set#aGPQ, su'h as setting the ma;imum to be the number o& "atabase ro=s you are pro'essing, an" up"ating on'e per ro=. 2ote that =e then leave on2tartPQ. 5his is 'ru'ial. 5he on2tartPQ metho" is in!oke" on the a'ti!ity $0 threa", so it 'an up"ate =i"gets an" su'h. +o=e!er, that means =e nee" to get out o& on2tartPQ, both to let the !andler get its =ork "one, an" also so An"roi" "oes not think our a'ti!ity is stu'k. 5he resulting a'ti!ity is simply a horiKontal progress bar,

"igure :%1 The 3andler/emo sample application

2ote, though, that =hile (rogress4ar samples like this one sho= your 'o"e arranging to up"ate the progress on the $0 threa", &or this spe'i&i' =i"get, that is not ne'essary. At least as o& An"roi" 1.A, (rogress4ar is no= M$0
&2*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

threa" sa&eM, in that you 'an up"ate it &rom any threa", an" it =ill han"le the "etails o& per&orming the a'tual $0 up"ate on the $0 threa".

Runn =les
0& you =oul" rather not &uss =ith #essage obGe'ts, you 'an also pass ?unnable obGe'ts to the !andler, =hi'h =ill run those ?unnable obGe'ts on the a'ti!ity $0 threa". !andler o&&ers a set o& post...PQ metho"s &or passing ?unnable obGe'ts in &or e!entual pro'essing. Cust as !andler supports postPQ an" post=elaFedPQ to a"" ?unnable obGe'ts to the e!ent Rueue, you 'an use those same metho"s on any VieE (i.e., any =i"get or 'ontainer). 5his slightly simpli&ies your 'o"e, in that you 'an then skip the !andler obGe't.

Where@ ,h Where 3as +y > Thread (oneF


%ometimes, you may not kno= i& you are 'urrently e;e'uting on the $0 threa" o& your appli'ation. *or e;ample, i& you pa'kage some o& your 'o"e in a CA &or others to reuse, you might not kno= =hether your 'o"e is being e;e'ute" on the $0 threa" or &rom a ba'kgroun" threa". 5o help 'ombat this problem, ActivitF o&&ers run"n3i&hreadPQ. 5his =orks similarly to the postPQ metho"s on !andler an" VieE, in that it Rueues up a ?unnable to run on the $0 threa"...i& you are not on the $0 threa" right no=. 0& you alrea"y are on the $0 threa", it in!okes the ?unnable imme"iately. 5his gi!es you the best o& both =orl"s, no "elay i& you are on the $0 threa", yet sa&ety in 'ase you are not.

Asyncing "eeling
An"roi" 1.A intro"u'e" a ne= =ay o& thinking about ba'kgroun" operations, AsFnc&ask. 0n one (reasonably) 'on!enient 'lass, An"roi" =ill han"le all o& the 'hores o& "oing =ork on the $0 threa" !ersus on a ba'kgroun" threa". Moreo!er, An"roi" itsel& allo'ates an" remo!es that
&2&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

ba'kgroun" threa". An", it maintains a small =ork Rueue, &urther a''entuating the M&ire an" &orgetM &eel to AsFnc&ask.

The Theory
5here is a saying, popular in marketing 'ir'les, MWhen a man buys a 1P<M "rill bit at a har"=are store, he "oes not =ant a 1P<M "rill bit S he =ants 1P<M holesM. +ar"=are stores 'annot sell holes, so they sell the ne;t-best thing, "e!i'es ("rills an" "rill bits) that make 'reating holes easy. %imilarly, An"roi" "e!elopers =ho ha!e struggle" =ith ba'kgroun" threa" management "o not stri'tly =ant ba'kgroun" threa"s S they =ant =ork to be "one o&& the $0 threa", so users are not stu'k =aiting an" a'ti!ities "o not get the "rea"e" Mappli'ation not respon"ingM (A2 ) error. An" =hile An"roi" 'annot magi'ally 'ause =ork to not 'onsume $0 threa" time, An"roi" 'an o&&er things that make su'h ba'kgroun" operations easier an" more transparent. AsFnc&ask is one su'h e;ample. 5o use AsFnc&ask, you must,

Create a sub'lass o& AsFnc&ask, 'ommonly as a pri!ate inner 'lass o& something that uses the task (e.g., an a'ti!ity) >!erri"e one or more AsFnc&ask metho"s to a''omplish the ba'kgroun" =ork, plus =hate!er =ork asso'iate" =ith the task that nee"s to be "one on the $0 threa" (e.g., up"ate progress) When nee"e", 'reate an instan'e o& the AsFnc&ask sub'lass an" 'all eGecutePQ to ha!e it begin "oing its =ork

What you "o not ha!e to "o is,


Create your o=n ba'kgroun" threa" 5erminate that ba'kgroun" threa" at an appropriate time Call all sorts o& metho"s to arrange &or bits o& pro'essing to be "one on the $0 threa"

&2-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

AsyncT s$4 Generics4 nd > r r!s


Creating a sub'lass o& AsFnc&ask is not Ruite as easy as, say, implementing the ?unnable inter&a'e. AsFnc&ask uses generi's, an" so you nee" to spe'i&y three "ata types,

5he type o& in&ormation that is nee"e" to pro'ess the task (e.g., $ Ls to "o=nloa") 5he type o& in&ormation that is passe" =ithin the task to in"i'ate progress 5he type o& in&ormation that is passe" =hen the task is 'omplete" to the post-task 'o"e

What makes this all the more 'on&using is that the &irst t=o "ata types are a'tually use" as !arargs, meaning that an array o& these types is use" =ithin your AsFnc&ask sub'lass. 5his shoul" be'ome 'learer as =e =ork our =ay to=ar"s an e;ample.

The St !es o. AsyncT s$


5here are &our metho"s you 'an o!erri"e in AsFnc&ask to a''omplish your en"s. 5he one you must o!erri"e, &or the task 'lass to be use&ul, is doIn4ackgroundPQ. 5his =ill be 'alle" by AsFnc&ask on a ba'kgroun" threa". 0t 'an run as long as it nee"s to in or"er to a''omplish =hate!er =ork nee"s to be "one &or this spe'i&i' task. 2ote, though, that tasks are meant to be &inite S using AsFnc&ask &or an in&inite loop is not re'ommen"e". 5he doIn4ackgroundPQ metho" =ill re'ei!e, as parameters, a !arargs array o& the &irst o& the three "ata types liste" abo!e S the "ata nee"e" to pro'ess the task. %o, i& your task7s mission is to "o=nloa" a 'olle'tion o& $ Ls, doIn4ackgroundPQ =ill re'ei!e those $ Ls to pro'ess.

&2%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

5he doIn4ackgroundPQ metho" must return a !alue o& the thir" "ata type liste" abo!e S the result o& the ba'kgroun" =ork. ?ou may =ish to o!erri"e on(re$GecutePQ. 5his metho" is 'alle", &rom the $0 threa", be&ore the ba'kgroun" threa" e;e'utes doIn4ackgroundPQ. +ere, you might initialiKe a (rogress4ar or other=ise in"i'ate that ba'kgroun" =ork is 'ommen'ing. Also, you may =ish to o!erri"e on(ost$GecutePQ. 5his metho" is 'alle", &rom the $0 threa", a&ter doIn4ackgroundPQ 'ompletes. 0t re'ei!es, as a parameter, the !alue returne" by doIn4ackgroundPQ (e.g., su''ess or &ailure &lag). +ere, you might "ismiss the (rogress4ar an" make use o& the =ork "one in the ba'kgroun", su'h as up"ating the 'ontents o& a list. you may =ish to o!erri"e on(rogress3pdatePQ. 0& doIn4ackgroundPQ 'alls the task7s publish(rogressPQ metho", the obGe't(s) passe" to that metho" are pro!i"e" to on(rogress3pdatePQ, but in the $0 threa". 5hat =ay, on(rogress3pdatePQ 'an alert the user as to the progress that has been ma"e on the ba'kgroun" =ork, su'h as up"ating a (rogress4ar or 'ontinuing an animation. 5he on(rogress3pdatePQ metho" =ill re'ei!e a !arargs o& the se'on" "ata type &rom the abo!e list S the "ata publishe" by doIn4ackgroundPQ !ia publish(rogressPQ. 0n a""ition,

A S mple T s$
As mentione" earlier, implementing an AsFnc&ask is not Ruite as easy as implementing a ?unnable. +o=e!er, on'e you get past the generi's an" !arargs, it is not too ba". *or e;ample, belo= you =ill &in" an implementation o& a )istActivitF that uses an AsFnc&ask, &rom the 5hrea"sPAsyn'er sample proGe't,
package com.commonsEare.android.asFncJ import import import import android.app.)istActivitFJ android.os.AsFnc&askJ android.os.4undleJ android.os.2Fstem+lockJ

&20

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

import android.Eidget.ArraFAdapterJ import android.Eidget.&oastJ import java.util.ArraF)istJ public class AsFnc=emo eGtends )istActivitF : private static final 2tringAB items6:7lorem78 7ipsum78 7dolor78 7sit78 7amet78 7consectetuer78 7adipiscing78 7elit78 7morbi78 7vel78 7ligula78 7vitae78 7arcu78 7aliUuet78 7mollis78 7etiam78 7vel78 7erat78 7placerat78 7ante78 7porttitor78 7sodales78 7pellentesUue78 7augue78 7purus7;J O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ setList$dapterPneE ArraFAdapterL2tringMPthis8 android.?.laFout.simple list item 18 neE $rrayListPQQQJ neE $ddStringTaskPQ.executePQJ ; class Add2tring&ask eGtends AsFnc&askLVoid8 2tring8 VoidM : O"verride protected Void doInBackgroundPVoid... unusedQ : for P2tring item : itemsQ : pu'lish)rogressPitemQJ 2Fstem+lock.sleepP>--QJ ; ; returnPnullQJ

O"verride protected void on)rogress*pdateP2tring... itemQ : PPArraFAdapterQgetList$dapterPQQ.addPitemA-BQJ ; O"verride protected void on)ost+xecutePVoid unusedQ : &oast .makeTextPAsFnc=emo.this8 7=oneX78 &oast.)$%D&! 2!"?&Q .showPQJ ; ; ;

&22

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

5his is another !ariation on the lorem ipsum list o& =or"s, use" &reRuently throughout this book. 5his time, rather than simply han" the list o& =or"s to an ArraFAdapter, =e simulate ha!ing to =ork to 'reate these =or"s in the ba'kgroun" using Add2tring&ask, our AsFnc&ask implementation. Let7s e;amine this pie'e by pie'e,

The AddStrin!T s$ Decl r tion


class Add2tring&ask eGtends AsFnc&askLVoid8 2tring8 VoidM :

+ere, =e use the generi's to set up the spe'i&i' types o& "ata =e are going to le!erage in Add2tring&ask. %pe'i&i'ally,

We "o not nee" any 'on&iguration in&ormation in this 'ase, so our &irst type is Void We =ant to pass ea'h string Mgenerate"M by our ba'kgroun" task to on(rogress3pdatePQ, so =e 'an a"" it to our list, so our se'on" type is
2tring

We "o not ha!e any results, stri'tly speaking (beyon" the up"ates), so our thir" type is Void

The doInB c$!round?@ %ethod


O"verride protected Void doInBackgroundPVoid... unusedQ : for P2tring item : itemsQ : pu'lish)rogressPitemQJ 2Fstem+lock.sleepP>--QJ ; returnPnullQJ ;

5he doIn4ackgroundPQ metho" is in!oke" in a ba'kgroun" threa". +en'e, =e 'an take as long as =e like. 0n a pro"u'tion appli'ation, =e =oul" be, perhaps, iterating o!er a list o& $ Ls an" "o=nloa"ing ea'h. +ere, =e iterate o!er our stati' list o& lorem ipsum =or"s, 'all publish(rogressPQ &or ea'h, an" then sleep 200 millise'on"s to simulate real =ork being "one.

&27

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

%in'e =e ele'te" to ha!e no 'on&iguration in&ormation, =e shoul" not nee" parameters to doIn4ackgroundPQ. +o=e!er, the 'ontra't =ith AsFnc&ask says =e nee" to a''ept a !arargs o& the &irst "ata type, =hi'h is =hy our metho" parameter is Void... unused. %in'e =e ele'te" to ha!e no results, =e shoul" not nee" to return anything. Again, though, the 'ontra't =ith AsFnc&ask says =e ha!e to return an obGe't o& the thir" "ata type. %in'e that "ata type is Void, our returne" obGe't is null.

The onPro!ress-pd te?@ %ethod


O"verride protected void on)rogress*pdateP2tring... itemQ : PPArraFAdapterQgetList$dapterPQQ.addPitemA-BQJ ;

5he on(rogress3pdatePQ metho" is 'alle" on the $0 threa", an" =e =ant to "o something to let the user kno= =e are progressing on loa"ing up these strings. 0n this 'ase, =e simply a"" the string to the ArraFAdapter, so it gets appen"e" to the en" o& the list. 5he on(rogress3pdatePQ metho" re'ei!es a 2tring... !arargs be'ause that is the se'on" "ata type in our 'lass "e'laration. %in'e =e are only passing one string per 'all to publish(rogressPQ, =e only nee" to e;amine the &irst entry in the !arargs array.

The onPostE0ecute?@ %ethod


O"verride protected void on)ost+xecutePVoid unusedQ : &oast .makeTextPAsFnc=emo.this8 7=oneX78 &oast.)$%D&! 2!"?&Q .showPQJ ;

5he on(ost$GecutePQ metho" is 'alle" on the $0 threa", an" =e =ant to "o something to in"i'ate that the ba'kgroun" =ork is 'omplete. 0n a real

&28

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

system, there may be some (rogress4ar to "ismiss or some animation to stop. +ere, =e simply raise a &oast. %in'e =e ele'te" to ha!e no results, =e shoul" not nee" any parameters. 5he 'ontra't =ith AsFnc&ask says =e ha!e to a''ept a single !alue o& the thir" "ata type. %in'e that "ata type is Void, our metho" parameter is Void unused.

The Activity
neE $ddStringTaskPQ.executePQJ

5o use Add2tring&ask, =e simply 'reate an instan'e an" 'all eGecutePQ on it. 5hat starts the 'hain o& e!ents e!entually lea"ing to the ba'kgroun" threa" "oing its =ork. 0& Add2trings&ask reRuire" 'on&iguration parameters, =e =oul" ha!e not use" Void as our &irst "ata type, an" the 'onstru'tor =oul" a''ept Kero or more parameters o& the "e&ine" type. 5hose !alues =oul" e!entually be passe" to doIn4ackgroundPQ.

The Results
0& you buil", install, an" run this proGe't, you =ill see the list being populate" in Mreal timeM o!er a &e= se'on"s, &ollo=e" by a &oast in"i'ating 'ompletion.

&2:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

"igure :01 The Async/emo@ part)ay through loading the list of )ords

Threads and Cotation


>ne problem =ith the "e&ault "estroy-an"-'reate 'y'le that a'ti!ities go through on an orientation 'hange 'omes &rom ba'kgroun" threa"s. 0& the a'ti!ity has starte" some ba'kgroun" =ork S through an AsFnc&ask, &or e;ample S an" then the a'ti!ity is "estroye" an" re-'reate", someho= the AsFnc&ask nee"s to kno= about this. >ther=ise, the AsFnc&ask might =ell sen" up"ates an" &inal results to the old a'ti!ity, =ith the ne= a'ti!ity none the =iser. 0n &a't, the ne= a'ti!ity might start up the ba'kgroun" =ork again, =asting resour'es. >ne =ay to "eal =ith this is to "isable the "estroy-an"-'reate 'y'le, by taking o!er 'on&iguration 'hanges, as "es'ribe" in a pre!ious se'tion. Another alternati!e is to ha!e a smarter a'ti!ity an" AsFnc&ask. ?ou 'an see an e;ample o& that in the ?otation/?otationAsFnc sample proGe't. 5his proGe't uses a (rogress4ar, mu'h like the !andler "emo &rom earlier in this 'hapter. 0t also has a &eGtVieE to in"i'ate =hen the ba'kgroun" =ork is 'omplete", initially in!isible,

&7<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L(rogress4ar android:id67ORid/progress7 stFle67Nandroid:attr/progress4ar2tFle!oriKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L&eGtVieE android:id67ORid/completed7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:teGt67@ork completedX7 android:visibilitF67invisible7 /M L/)inear)aFoutM

5he Mbusiness logi'M is &or an AsFnc&ask to "o some (&ake) =ork in the ba'kgroun", up"ating the (rogress4ar along the =ay, an" making the &eGtVieE !isible =hen it is &inishe". More importantly, it nee"s to "o this in su'h a =ay as to beha!e properly i& the s'reen is rotate",

We 'annot MloseM our AsFnc&ask, ha!ing it 'ontinue "oing =ork an" up"ating the =rong a'ti!ity We 'annot start a se'on" AsFnc&ask, thereby "oubling our =orkloa" We nee" to ha!e the $0 'orre'tly re&le't our =ork7s progress or 'ompletion

% nu l Activity Associ tion


Earlier in this 'hapter, =e sho=e" the use o& an AsFnc&ask that =as implemente" as a regular inner 'lass o& the ActivitF 'lass. 5hat =orks =ell =hen you are not 'on'erne" about rotation. *or e;ample, i& the AsFnc&ask is not a&&e'ting the user inter&a'e S su'h as uploa"ing a photo S rotation =ill not be an issue &or you. +a!ing the AsFnc&ask as an inner 'lass o& the ActivitF means you get rea"y a''ess to the A'ti!ity &or any pla'e =here you nee" a +onteGt. +o=e!er, &or the rotation s'enario, a regular inner 'lass =ill =ork poorly. 5he AsFnc&ask =ill think it kno=s the ActivitF it is suppose" to =ork =ith,
&7*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

but in reality it =ill be hol"ing onto an impli'it re&eren'e to the ol" a'ti!ity, not one a&ter an orientation 'hange. %o, in ?otationAsFnc, the ?otationAEare&ask 'lass is a stati' inner 'lass. 5his means ?otationAEare&ask "oes not ha!e any impli'it re&eren'e to any ?otationAsFnc ActivitF (ol" or ne=),
import import import import import import import android.app.ActivitFJ android.os.AsFnc&askJ android.os.4undleJ android.os.2Fstem+lockJ android.util.)ogJ android.vieE.VieEJ android.Eidget.(rogress4arJ

public class ?otationAsFnc eGtends ActivitF : private (rogress4ar bar6nullJ private ?otationAEare&ask task6nullJ O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ bar6P(rogress4arQfindViewByIdP?.id.progressQJ task6P?otationAEare&askQgetLast&onConfigurationInstance PQJ if Ptask66nullQ : task6neE %otation$wareTaskPthisQJ task.executePQJ ; else : task.attachPthisQJ update)rogressPtask.get)rogressPQQJ if Ptask.get)rogressPQM61--Q : mark$sDonePQJ ; ; ;

O"verride public "bject on%etain&onConfigurationInstance PQ : task.detachPQJ returnPtaskQJ ; void update)rogressPint progressQ :

&7&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

bar.set)rogressPprogressQJ ; void mark$sDonePQ : findViewByIdP?.id.completedQ.setVisi'ilityPVieE.VI2I4)$QJ ; static class ?otationAEare&ask eGtends AsFnc&askLVoid8 Void8 VoidM : ?otationAsFnc activitF6nullJ int progress6-J %otation$wareTaskP?otationAsFnc activitFQ : attachPactivitFQJ ; O"verride protected Void doInBackgroundPVoid... unusedQ : for Pint i6-JiL>-JiRRQ : 2Fstem+lock.sleepP.--QJ pu'lish)rogressPQJ ; returnPnullQJ ; O"verride protected void on)rogress*pdatePVoid... unusedQ : if PactivitF66nullQ : )og.wP7?otationAsFnc78 7on(rogress3pdatePQ skipped [ no activitF7QJ ; else : progressR6.J activitF.update)rogressPprogressQJ ; ; O"verride protected void on)ost+xecutePVoid unusedQ : if PactivitF66nullQ : )og.wP7?otationAsFnc78 7on(ost$GecutePQ skipped [ no activitF7QJ ; else : activitF.mark$sDonePQJ ; ; void detachPQ : activitF6nullJ ; void attachP?otationAsFnc activitFQ : this.activitF6activitFJ ;

&7-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

int get)rogressPQ : returnPprogressQJ ; ; ;

%in'e =e =ant ?otationAEare&ask to up"ate the 'urrent ?otationAsFnc ActivitF, =e supply that ActivitF =hen =e 'reate the task, !ia the 'onstru'tor. ?otationAEare&ask also has attachPQ an" detachPQ metho"s to 'hange =hat ActivitF the task kno=s about, as =e =ill see shortly.

5lo# o. Events
When ?otationAsFnc starts up &or the &irst time, it 'reates a ne= instan'e o& the ?otationAEare&ask 'lass an" e;e'utes it. At this point, the task has a re&eren'e to the ?otationAsFnc ActivitF an" 'an "o its (&ake) =ork, telling ?otationAsFnc to up"ate the progress along the =ay. 2o=, suppose that "uring the mi""le o& the doIn4ackgroundPQ pro'essing, the user rotates the s'reen. >ur ActivitF =ill be 'alle" =ith on?etain%on+onfigurationInstancePQ. +ere, =e =ant to "o t=o things, 1. %in'e this ActivitF instan'e is being "estroye", =e nee" to make sure the task no longer hol"s onto a re&eren'e to it. +en'e, =e 'all detachPQ, 'ausing the task to set its ?otationAsFnc "ata member (activitF) to null.

2. We return the ?otationAEare&ask obGe't, so that our ne= ?otationAsFnc instan'e 'an get a''ess to it E!entually, the ne= ?otationAsFnc instan'e =ill be 'reate". 0n on+reatePQ, =e try to get a''ess to any 'urrent ?otationAEare&ask instan'e !ia get)ast%on+onfigurationInstancePQ. 0& that =as null, then =e kno= that this is a ne=ly-'reate" a'ti!ity, an" so =e 'reate a ne= task. 0&, ho=e!er, get)ast%on+onfigurationInstancePQ returne" the task obGe't &rom the ol" ?otationAsFnc instan'e, =e hol" onto it an" up"ate our $0 to re&le't the 'urrent progress that has been ma"e. We also attachPQ the ne=
&7%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

?otationAsFnc

to the ?otationAEare&ask, so as &urther progress is ma"e, the task 'an noti&y the proper a'ti!ity. 5he net result is that our (rogress4ar smoothly progresses &rom 0 to 100, e!en =hile rotations are going on.

,hy This ,or$s


Most 'allba'k metho"s in An"roi" are "ri!en by messages on the message Rueue being pro'esse" by the main appli'ation threa". 2ormally, this Rueue is being pro'esse" =hene!er the main appli'ation threa" is not other=ise busy, su'h as running our 'o"e. +o=e!er, =hen a 'on&iguration 'hange o''urs, like a s'reen rotation, that no longer hol"s true. 0n bet=een the 'all to on?etain%on+onfigurationInstancePQ instan'e o& the ol" a'ti!ity an" the 'ompletion o& on+reatePQ o& the ne= a'ti!ity, the message Rueue is le&t alone. %o, let us suppose that, in bet=een on?etain%on+onfigurationInstancePQ a'ti!ity an" the subseRuent on+reatePQ, our AsFnc&ask7s ba'kgroun" =ork 'ompletes. 5his =ill trigger on(ost$GecutePQ to be 'alle"...e!entually. +o=e!er, sin'e on(ost$GecutePQ is a'tually laun'he" &rom a message on the message Rueue, on(ost$GecutePQ =ill not be 'alle" until a&ter our on+reatePQ has 'omplete". +en'e, our AsFnc&ask 'an keep running "uring the 'on&iguration 'hange, so long as =e "o t=o things, 1. 0n on+reatePQ o& the ne= a'ti!ity instan'e, =e up"ate the AsFnc&ask to ha!e it =ork =ith our ne= a'ti!ity, rather than the ol" one

2. We "o not attempt to use the a'ti!ity &rom doIn4ackgroundPQ

&70

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing )ith Threads

And ?o)@ The Caveats


1a'kgroun" threa"s, =hile eminently possible using the An"roi" !andler system, are not all happiness an" =arm puppies. 1a'kgroun" threa"s not only a"" 'omple;ity, but they ha!e real-=orl" 'osts in terms o& a!ailable memory, C#$, an" battery li&e. 5o that en", there is a =i"e range o& s'enarios you nee" to a''ount &or =ith your ba'kgroun" threa", in'lu"ing,

5he possibility that users =ill intera't =ith your a'ti!ity7s $0 =hile the ba'kgroun" threa" is 'hugging along. 0& the =ork that the ba'kgroun" threa" is "oing is altere" or in!ali"ate" by the user input, you =ill nee" to 'ommuni'ate this to the ba'kgroun" threa". An"roi" in'lu"es many 'lasses in the java.util.concurrent pa'kage that =ill help you 'ommuni'ate sa&ely =ith your ba'kgroun" threa". 5he possibility that the a'ti!ity =ill be kille" o&& =hile ba'kgroun" =ork is going on. *or e;ample, a&ter starting your a'ti!ity, the user might ha!e a 'all 'ome in, &ollo=e" by a te;t message, &ollo=e" by a nee" to look up a 'onta't...all o& =hi'h might be su&&i'ient to ki'k your a'ti!ity out o& memory. 5he ne;t 'hapter =ill 'o!er the !arious e!ents An"roi" =ill take your a'ti!ity throughT hook the proper ones an" be sure to shut "o=n your ba'kgroun" threa" 'leanly =hen you ha!e the 'han'e. 5he possibility that your user =ill get irritate" i& you 'he= up a lot o& C#$ time an" battery li&e =ithout gi!ing any payba'k. 5a'ti'ally, this means using (rogress4ar or other means o& letting the user kno= that something is happening. %trategi'ally, this means you still nee" to be e&&i'ient at =hat you "o S ba'kgroun" threa"s are no pana'ea &or sluggish or pointless 'o"e. 5he possibility that you =ill en'ounter an error "uring ba'kgroun" pro'essing. *or e;ample, i& you are gathering in&ormation o&& the 0nternet, the "e!i'e might lose 'onne'ti!ity. Alerting the user o& the problem !ia a 2oti&i'ation an" shutting "o=n the ba'kgroun" threa" may be your best option.

&72

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &1

Creating ntent "ilters

$p to no=, the &o'us o& this book has been on a'ti!ities opene" "ire'tly by the user &rom the "e!i'e7s laun'her. 5his, o& 'ourse, is the most ob!ious 'ase &or getting your a'ti!ity up an" !isible to the user. An", in many 'ases it is the primary =ay the user =ill start using your appli'ation. +o=e!er, remember that the An"roi" system is base" upon lots o& loosely'ouple" 'omponents. What you might a''omplish in a "esktop 8$0 !ia "ialog bo;es, 'hil" =in"o=s, an" the like are mostly suppose" to be in"epen"ent a'ti!ities. While one a'ti!ity =ill be Mspe'ialM, in that it sho=s up in the laun'her, the other a'ti!ities all nee" to be rea'he"...someho=. 5he Mho=M is !ia intents. An intent is basi'ally a message that you pass to An"roi" saying, M?o: 0 =ant to "o...er...something: ?eah:M +o= spe'i&i' the MsomethingM is "epen"s on the situation S sometimes you kno= e;a'tly =hat you =ant to "o (e.g., open up one o& your other a'ti!ities), an" sometimes you "o not. 0n the abstra't, An"roi" is all about intents an" re'ei!ers o& those intents. %o, no= that =e are =ell-!erse" in 'reating a'ti!ities, let7s "i!e into intents, so =e 'an 'reate more 'omple; appli'ations =hile simultaneously being Mgoo" An"roi" 'itiKensM.

&77
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Creating ntent "ilters

WhatGs .our ntentF


When %ir 5im 1erners-Lee 'ooke" up the +yperte;t 5rans&er #roto'ol S +55# S he set up a system o& !erbs plus a""resses in the &orm o& $ Ls. 5he a""ress in"i'ate" a resour'e, su'h as a Web page, graphi', or ser!er-si"e program. 5he !erb in"i'ate" =hat shoul" be "one, 8E5 to retrie!e it, #>%5 to sen" &orm "ata to it &or pro'essing, et'. 0ntents are similar, in that they represent an a'tion plus 'onte;t. 5here are more a'tions an" more 'omponents to the 'onte;t =ith An"roi" intents than there are =ith +55# !erbs an" resour'es, but the 'on'ept is still the same. Cust as a Web bro=ser kno=s ho= to pro'ess a !erb\$ L pair, An"roi" kno=s ho= to &in" a'ti!ities or other appli'ation logi' that =ill han"le a gi!en intent.

Pieces o. Intents
5he t=o most important pie'es o& an intent are the a'tion an" =hat An"roi" re&ers to as the M"ataM. 5hese are almost e;a'tly analogous to +55# !erbs an" $ Ls S the a'tion is the !erb, an" the M"ataM is a 3ri, su'h as content://contacts/people/1 representing a 'onta't in the 'onta'ts "atabase. A'tions are 'onstants, su'h as A+&I"% VI$@ (to bring up a !ie=er &or the resour'e), A+&I"% $=I& (to e"it the resour'e), or A+&I"% (I+H (to 'hoose an a!ailable item gi!en a 3ri representing a 'olle'tion, su'h as content://contacts/people). 0& you =ere to 'reate an intent 'ombining A+&I"% VI$@ =ith a 'ontent $ri o& an" pass that intent to An"roi", An"roi" =oul" kno= to &in" an" open an a'ti!ity 'apable o& !ie=ing that resour'e.
content://contacts/people/1,

5here are other 'riteria you 'an pla'e insi"e an intent (represente" as an 0ntent obGe't), besi"es the a'tion an" M"ataM 3ri, su'h as,

&78

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Creating ntent "ilters

A 'ategory. ?our MmainM a'ti!ity =ill be in the )A3%+!$? 'ategory, in"i'ating it shoul" sho= up on the laun'her menu. >ther a'ti!ities =ill probably be in the =$9A3)& or A)&$?%A&IV$ 'ategories. A M0ME type, in"i'ating the type o& resour'e you =ant to operate on, i& you "o not kno= a 'olle'tion 3ri. A 'omponent, =hi'h is to say, the 'lass o& the a'ti!ity that is suppose" to re'ei!e this intent. $sing 'omponents this =ay ob!iates the nee" &or the other properties o& the intent. +o=e!er, it "oes make the intent more &ragile, as it assumes spe'i&i' implementations. ME;trasM, =hi'h is a 4undle o& other in&ormation you =ant to pass along to the re'ei!er =ith the intent, that the re'ei!er might =ant to take a"!antage o&. What pie'es o& in&ormation a gi!en re'ei!er 'an use is up to the re'ei!er an" (hope&ully) is =ell-"o'umente".

?ou =ill &in" rosters o& the stan"ar" a'tions an" 'ategories in the An"roi" %@D "o'umentation &or the Intent 'lass.

Intent Routin!
As note" abo!e, i& you spe'i&y the target 'omponent in your intent, An"roi" has no "oubt =here the intent is suppose" to be route" to S it =ill laun'h the name" a'ti!ity. 5his might be >D i& the target intent is in your appli'ation. 0t "e&initely is not re'ommen"e" &or sen"ing intents to other appli'ations. Component names, by an" large, are 'onsi"ere" pri!ate to the appli'ation an" are subGe't to 'hange. Content 3ri templates an" M0ME types are the pre&erre" =ays o& i"enti&ying ser!i'es you =ish thir"-party 'o"e to supply. 0& you "o not spe'i&y the target 'omponent, then An"roi" has to &igure out =hat a'ti!ities (or other re'ei!ers) are eligible to re'ei!e the intent. 2ote the use o& the plural Ma'ti!itiesM, as a broa"ly-=ritten intent might =ell resol!e to se!eral a'ti!ities. 5hat is the...ummm...intent (par"on the pun), as you =ill see later in this 'hapter. 5his routing approa'h is re&erre" to as impli'it routing.

&7:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Creating ntent "ilters

1asi'ally, there are three rules, all o& =hi'h must be true &or a gi!en a'ti!ity to be eligible &or a gi!en intent, 1. 5he a'ti!ity must support the spe'i&ie" a'tion

2. 5he a'ti!ity must support the state" M0ME type (i& supplie") .. 5he a'ti!ity must support all o& the 'ategories name" in the intent 5he upshot is that you =ant to make your intents spe'i&i' enough to &in" the right re'ei!er(s), an" no more spe'i&i' than that. 5his =ill be'ome 'learer as =e =ork through some e;amples later in this 'hapter.

Stating .our ntent$ions'


All An"roi" 'omponents that =ish to be noti&ie" !ia intents must "e'lare intent &ilters, so An"roi" kno=s =hi'h intents shoul" go to that 'omponent. 5o "o this, you nee" to a"" intent-filter elements to your Android#anifest.Gml &ile. All o& the e;ample proGe'ts ha!e intent &ilters "e&ine", 'ourtesy o& the An"roi" appli'ation-buil"ing s'ript (android create project or the 0@E eRui!alent). 5hey look something like this,
LNGml version671.-7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.skeleton7M LapplicationM LactivitF android:name67.%oE7 android:label67%oE7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM L/manifestM

2ote the intent-filter element un"er the a'ti!ity element. +ere, =e "e'lare that this a'ti!ity,

&8<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Creating ntent "ilters

0s the main a'ti!ity &or this appli'ation 0t is in the )A3%+!$? 'ategory, meaning it gets an i'on in the An"roi" main menu

1e'ause this a'ti!ity is the main one &or the appli'ation, An"roi" kno=s this is the 'omponent it shoul" laun'h =hen somebo"y 'hooses the appli'ation &rom the main menu. ?ou are =el'ome to ha!e more than one a'tion or more than one 'ategory in your intent &ilters. 5hat in"i'ates that the asso'iate" 'omponent (e.g., a'ti!ity) han"les multiple "i&&erent sorts o& intents. More than likely, you =ill also =ant to ha!e your se'on"ary (non- #AI%) a'ti!ities spe'i&y the M0ME type o& "ata they =ork on. 5hen, i& an intent is targete" &or that M0ME type S either "ire'tly, or in"ire'tly by the 3ri re&eren'ing something o& that type S An"roi" =ill kno= that the 'omponent han"les su'h "ata. *or e;ample, you 'oul" ha!e an a'ti!ity "e'lare" like this,
LactivitF android:name67.&ourVieEActivitF7M Lintent-filterM Laction android:name67android.intent.action.VI$@7 /M LcategorF android:name67android.intent.categorF.=$9A3)&7 /M Ldata android:mime&Fpe67vnd.android.cursor.item/vnd.commonsEare.tour7 /M L/intent-filterM L/activitFM

5his a'ti!ity =ill get laun'he" by an intent reRuesting to !ie= a 3ri representing a vnd.android.cursor.item/vnd.commonsEare.tour pie'e o& 'ontent. 5hat Intent 'oul" 'ome &rom another a'ti!ity in the same appli'ation (e.g., the MA02 a'ti!ity &or this appli'ation) or &rom another a'ti!ity in another An"roi" appli'ation that happens to kno= a 3ri that this a'ti!ity han"les.

&8*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Creating ntent "ilters

?arro) Ceceivers
0n the e;amples sho=n abo!e, the intent &ilters =ere set up on a'ti!ities. %ometimes, tying intents to a'ti!ities is not e;a'tly =hat =e =ant,

%ome system e!ents might 'ause us to =ant to trigger something in a ser!i'e rather than an a'ti!ity %ome e!ents might nee" to laun'h "i&&erent a'ti!ities in "i&&erent 'ir'umstan'es, =here the 'riteria are not solely base" on the intent itsel&, but some other state (e.g., i& =e get intent F an" the "atabase has a ?, then laun'h a'ti!ity MT i& the "atabase "oes not ha!e a ?, then laun'h a'ti!ity 2)

*or these 'ases, An"roi" o&&ers the re'ei!er, "e&ine" as a 'lass implementing the 4roadcast?eceiver inter&a'e. 1roa"'ast re'ei!ers are "isposable obGe'ts "esigne" to re'ei!e intents S spe'i&i'ally, broa"'ast intents S an" take a'tion. 5he 4roadcast?eceiver inter&a'e has only one metho", on?eceivePQ. e'ei!ers implement that metho", =here they "o =hate!er it is they =ish to "o upon an in'oming intent. 5o "e'lare an re'ei!er, a"" a receiver element to your Android#anifest.Gml &ile,
Lreceiver android:name67.#FIntent?eceiver+lass%ame7 /M

An re'ei!er is only ali!e &or as long as it takes to pro'ess on?eceivePQ S as soon as that metho" returns, the re'ei!er instan'e is subGe't to garbage 'olle'tion an" =ill not be reuse". 5his means re'ei!ers are some=hat limite" in =hat they 'an "o, mostly to a!oi" anything that in!ol!es any sort o& 'allba'k. *or e;ample, they 'annot bin" to a ser!i'e, an" they 'annot open a "ialog bo;. 5he e;'eption is i& the 4roadcast?eceiver is implemente" on some longerli!e" 'omponent, su'h as an a'ti!ity or ser!i'e S in that 'ase, the re'ei!er li!es as long as its MhostM "oes (e.g., until the a'ti!ity is &roKen). +o=e!er, in this 'ase, you 'annot "e'lare the re'ei!er !ia Android#anifest.Gml. 0nstea", you nee" to 'all register?eceiverPQ on your ActivitF7s on?esumePQ 'allba'k
&8&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Creating ntent "ilters

to "e'lare interest in an intent, then 'all unregister?eceiverPQ &rom your ActivitF7s on(ausePQ =hen you no longer nee" those intents.

The Pause Caveat


5here is one hi''up =ith using 0ntent obGe'ts to pass arbitrary messages aroun", it only =orks =hen the re'ei!er is a'ti!e. 5o Ruote &rom the "o'umentation &or 4roadcast?eceiver, ! registering a receiver in your Activity.onResume() implementation" you should unregister it in Activity.onPause(). #$ou will not receive intents when paused" and this will cut down on unnecessary system overhead%. &o not unregister in Activity.onSaveInstanceState()" because this will not be called i! the user moves back in the history stack. +en'e, you 'an only really use the Intent &rame=ork as an arbitrary message bus i&,

?our re'ei!er "oes not 'are i& it misses messages be'ause it =as not a'ti!e, or ?ou pro!i"e some means o& getting the re'ei!er M'aught upM on messages it misse" =hile it =as ina'ti!e, or ?our re'ei!er is registere" in the mani&est

&8-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &&

!aunching Activities and Sub# Activities

5he theory behin" the An"roi" $0 ar'hite'ture is that "e!elopers shoul" "e'ompose their appli'ation into "istin't a'ti!ities. *or e;ample, a 'alen"ar appli'ation 'oul" ha!e a'ti!ities &or !ie=ing the 'alen"ar, !ie=ing a single e!ent, e"iting an e!ent (in'lu"ing a""ing a ne= one), an" so &orth. 5his, o& 'ourse, implies that one o& your a'ti!ities has the means to start up another a'ti!ity. *or e;ample, i& somebo"y 'li'ks on an e!ent &rom the !ie=-'alen"ar a'ti!ity, you might =ant to sho= the !ie=-e!ent a'ti!ity &or that e!ent. 5his means that, someho=, you nee" to be able to 'ause the !ie=-e!ent a'ti!ity to laun'h an" sho= a spe'i&i' e!ent (the one the user 'li'ke" upon). 5his 'an be &urther broken "o=n into t=o s'enarios, 1. ?ou kno= =hat a'ti!ity you =ant to laun'h, probably be'ause it is another a'ti!ity in your o=n appli'ation

2. ?ou ha!e a 'ontent 3ri to...something, an" you =ant your users to be able to "o...something =ith it, but you "o not kno= up &ront =hat the options are 5his 'hapter 'o!ers the &irst s'enarioT the 'ompanion a"!an'e" An"roi" book han"les the se'on".

&80
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

Peers and Subs


>ne key Ruestion you nee" to ans=er =hen you "e'i"e to laun'h an a'ti!ity is, "oes your a'ti!ity nee" to kno= =hen the laun'he" a'ti!ity en"sH *or e;ample, suppose you =ant to spa=n an a'ti!ity to 'olle't authenti'ation in&ormation &or some Web ser!i'e you are 'onne'ting to S maybe you nee" to authenti'ate =ith >pen0@ in or"er to use an >Auth ser!i'e. 0n this 'ase, your main a'ti!ity =ill nee" to kno= =hen the authenti'ation is 'omplete so it 'an start to use the Web ser!i'e. >n the other han", imagine an email appli'ation in An"roi". When the user ele'ts to !ie= an atta'hment, neither you nor the user ne'essarily e;pe't the main a'ti!ity to kno= =hen the user is "one !ie=ing that atta'hment. 0n the &irst s'enario, the laun'he" a'ti!ity is 'learly subor"inate to the laun'hing a'ti!ity. 0n that 'ase, you probably =ant to laun'h the 'hil" as a sub-a'ti!ity, =hi'h means your a'ti!ity =ill be noti&ie" =hen the 'hil" a'ti!ity is 'omplete. 0n the se'on" s'enario, the laun'he" a'ti!ity is more a peer o& your a'ti!ity, so you probably =ant to laun'h the 6'hil"9 Gust as a regular a'ti!ity. ?our a'ti!ity =ill not be in&orme" =hen the 6'hil"9 is "one, but, then again, your a'ti!ity really "oes not nee" to kno=.

Start G=m >p


5he t=o pie'es &or starting an a'ti!ity are an intent an" your 'hoi'e o& ho= to start it up.

% $e n Intent
As "is'usse" in a pre!ious 'hapter, intents en'apsulate a reRuest, ma"e to An"roi", &or some a'ti!ity or other re'ei!er to "o something.
&82

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

0& the a'ti!ity you inten" to laun'h is one o& your o=n, you may &in" it simplest to 'reate an e;pli'it intent, naming the 'omponent you =ish to laun'h. *or e;ample, &rom =ithin your a'ti!ity, you 'oul" 'reate an intent like this,
neE IntentPthis8 !elpActivitF.classQJ

5his =oul" stipulate that you =ante" to laun'h the !elpActivitF. 5his a'ti!ity =oul" nee" to be name" in your Android#anifest.Gml &ile, though not ne'essarily =ith any intent &ilter, sin'e you are trying to reRuest it "ire'tly. >r, you 'oul" put together an intent &or some 3ri, reRuesting a parti'ular a'tion,
3ri uri63ri.parseP7geo:7Rlat.toStringPQR787Rlon.toStringPQQJ Intent i6neE IntentPIntent.A+&I"% VI$@8 uriQJ

+ere, gi!en that =e ha!e the latitu"e an" longitu"e o& some position ( lat an" lon, respe'ti!ely) o& type =ouble, =e 'onstru't a geo s'heme 3ri an" 'reate an intent reRuesting to !ie= this 3ri (A+&I"% VI$@).

% $e the C ll
>n'e you ha!e your intent, you nee" to pass it to An"roi" an" get the 'hil" a'ti!ity to laun'h. ?ou ha!e t=o 'hoi'es, 1. 5he simplest option is to 'all startActivitFPQ =ith the Intent S this =ill 'ause An"roi" to &in" the best-mat'h a'ti!ity an" pass the intent to it &or han"ling. ?our a'ti!ity =ill not be in&orme" =hen the 6'hil"9 a'ti!ity is 'omplete.

2. ?ou 'an 'all startActivitF9or?esultPQ, passing it the Intent an" a number (uniRue to the 'alling a'ti!ity). An"roi" =ill &in" the bestmat'h a'ti!ity an" pass the intent o!er to it. +o=e!er, your a'ti!ity =ill be noti&ie" =hen the 'hil" a'ti!ity is 'omplete !ia the onActivitF?esultPQ 'allba'k (see belo=).

&87

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

With startActivitF9or?esultPQ, as note", you 'an implement the onActivitF?esultPQ 'allba'k to be noti&ie" =hen the 'hil" a'ti!ity has 'omplete" its =ork. 5he 'allba'k re'ei!es the uniRue number supplie" to startActivitF9or?esultPQ, so you 'an "etermine =hi'h 'hil" a'ti!ity is the one that has 'omplete". ?ou also get,

A result 'o"e, &rom the 'hil" a'ti!ity 'alling set?esultPQ. 5ypi'ally this is ?$23)& "H or ?$23)& +A%+$)$=, though you 'an 'reate your o=n return 'o"es (pi'k a number starting =ith ?$23)& 9I?2& 32$?) An optional 2tring 'ontaining some result "ata, possibly a $ L to some internal or e;ternal resour'e S &or e;ample, a A+&I"% (I+H intent typi'ally returns the sele'te" bit o& 'ontent !ia this "ata string An optional 4undle 'ontaining a""itional in&ormation beyon" the result 'o"e an" "ata string

5o "emonstrate laun'hing a peer a'ti!ity, take a peek at the Activities/)aunch sample appli'ation. 5he FML layout is &airly straight&or=ar", t=o &iel"s &or the latitu"e an" longitu"e, plus a button,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&able)aFout android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:stretch+olumns6718>7 M L&able?oEM L&eGtVieE android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:padding)eft67>dip7 android:padding?ight67<dip7 android:teGt67)ocation:7 /M L$dit&eGt android:id67ORid/lat7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:cursorVisible67true7 android:editable67true7 android:single)ine67true7

&88

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

android:laFout Eeight6717 /M L$dit&eGt android:id67ORid/lon7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:cursorVisible67true7 android:editable67true7 android:single)ine67true7 android:laFout Eeight6717 /M L/&able?oEM L/&able)aFoutM L4utton android:id67ORid/map7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:teGt672hoE #eX7 android:on+lick67shoE#e7 /M L/)inear)aFoutM

5he button7s shoE#ePQ 'allba'k metho" simply takes the latitu"e an" longitu"e, pours them into a geo s'heme 3ri, then starts the a'ti!ity.
package com.commonsEare.android.activitiesJ import import import import import import android.app.ActivitFJ android.content.IntentJ android.net.3riJ android.os.4undleJ android.vieE.VieEJ android.Eidget.$dit&eGtJ

public class )aunch=emo eGtends ActivitF : private $dit&eGt latJ private $dit&eGt lonJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ lat6P$dit&eGtQfindViewByIdP?.id.latQJ lon6P$dit&eGtQfindViewByIdP?.id.lonQJ ; public void showMePVieE vQ : 2tring lat6lat.getTextPQ.toStringPQJ 2tring lon6lon.getTextPQ.toStringPQJ 3ri uri63ri.parseP7geo:7R latR787R lonQJ start$cti!ityPneE IntentPIntent.A+&I"% VI$@8 uriQQJ

&8:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

; ;

5he a'ti!ity is not mu'h to look at,

"igure :21 The !aunch/emo sample application@ )ith a location filled in

0& you &ill in a lo'ation (e.g., .8.8831 latitu"e an" -44.0<32 longitu"e) an" 'li'k the button, the resulting map is more interesting. 2ote that this is the built-in An"roi" map a'ti!ity S =e "i" not 'reate our o=n a'ti!ity to "isplay this map.

&:<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

"igure :71 The map launched by !aunch /emo@ sho)ing the !incoln +emorial in Washington /C

0n a later 'hapter, you =ill see ho= you 'an 'reate maps in your o=n a'ti!ities, in 'ase you nee" greater 'ontrol o!er ho= the map is "isplaye". 2ote that this geo: Intent =ill only =ork on "e!i'es or emulators that ha!e 8oogle Maps installe", or on "e!i'es that ha!e some other mapping appli'ation that supports the geo: $ L.

Tabbed Bro)sing@ Sort ,f


>ne o& the main &eatures o& the mo"ern "esktop Web bro=ser is tabbe" bro=sing, =here a single bro=ser =in"o= 'an sho= se!eral pages split a'ross a series o& tabs. >n a mobile "e!i'e, this may not make a lot o& sense, gi!en that you lose s'reen real estate &or the tabs themsel!es. 0n this book, ho=e!er, =e "o not let little things like sensibility stop us, so let us "emonstrate a tabbe" bro=ser, using &abActivitF an" Intent obGe'ts.

&:*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

As you may re'all &rom the se'tion on tabbe" !ie=s &rom earlier in this book, a tab 'an ha!e a VieE as its 'ontents. 0t 'an also ha!e an ActivitF as its 'ontents. 0& you =ant to use an ActivitF as the 'ontent o& a tab, you pro!i"e an Intent that =ill laun'h the "esire" ActivitFT An"roi"7s tab-management &rame=ork =ill then pour the ActivitF7s user inter&a'e into the tab. ?our natural instin't might be to use an http: 3ri the =ay =e use" a geo: 3ri in the pre!ious e;ample,
Intent i6neE IntentPIntent.A+&I"% VI$@QJ i.setDataP3ri.parseP7http://commonsEare.com7QQJ

5hat =ay, you 'oul" use the built-in 1ro=ser appli'ation an" get all o& the &eatures that it o&&ers. Alas, this "oes not =ork. ?ou 'annot host other appli'ations7 a'ti!ities in your tabs, only your o=n a'ti!ities, &or se'urity reasons. %o, =e "ust o&& our @ebVieE "emos &rom the 'hapter on WebDit an" use those instea", repa'kage" as Activities/Intent&ab. +ere is the sour'e to the main a'ti!ity, the one hosting the &abVieE,
package com.commonsEare.android.intenttabJ import import import import import import import android.app.ActivitFJ android.app.&abActivitFJ android.content.IntentJ android.net.3riJ android.os.4undleJ android.Eebkit.@ebVieEJ android.Eidget.&ab!ostJ

public class Intent&ab=emo eGtends &abActivitF : O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ &ab!ost host6getTa'(ostPQJ Intent i6neE IntentPthis8 +@4roEser.classQJ i.put+xtraP+@4roEser.3?)8 7http://commonsEare.com7QJ host.addTa'Phost.newTa'SpecP7one7Q

&:&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

.setIndicatorP7+@7Q .setContentPiQQJ i6neE IntentPiQJ i.put+xtraP+@4roEser.3?)8 7http://EEE.android.com7QJ host.addTa'Phost.newTa'SpecP7tEo7Q .setIndicatorP7Android7Q .setContentPiQQJ

; ;

As you 'an see, =e are using &abActivitF as the base 'lass, an" so =e "o not nee" our o=n layout FML S &abActivitF supplies it &or us. All =e "o is get a''ess to the &ab!ost an" a"" t=o tabs, ea'h spe'i&ying an 0ntent that "ire'tly re&ers to another 'lass. 0n this 'ase, our t=o tabs =ill ea'h host a +@4roEser, =ith a $ L to loa" supplie" !ia an Intent e;tra. 5he +@4roEser a'ti!ity is simple mo"i&i'ation to the earlier bro=ser "emos,
package com.commonsEare.android.intenttabJ import import import import import android.app.ActivitFJ android.content.IntentJ android.net.3riJ android.os.4undleJ android.Eebkit.@ebVieEJ

public class +@4roEser eGtends ActivitF : public static final 2tring 3?)67com.commonsEare.android.intenttab.3?)7J private @ebVieE broEserJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ broEser6neE #e'ViewPthisQJ setContentViewPbroEserQJ broEser.load*rlPgetIntentPQ.getString+xtraP3?)QQJ ; ;

5hey simply loa" a "i&&erent $ L into the bro=ser, the CommonsWare home page in one, the An"roi" home page in the other. 5he resulting $0 sho=s =hat tabbe" bro=sing 'oul" look like on An"roi",

&:-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

"igure :81 The ntentTab/emo sample application@ sho)ing the first tab

"igure ::1 The ntentTab/emo sample application@ sho)ing the second tab

+o=e!er, this approa'h is rather =aste&ul. 5here is a &air bit o& o!erhea" in 'reating an a'ti!ity, that one "oes not nee" Gust to populate tabs in a &ab!ost. 0n parti'ular, it in'reases the amount o& sta'k spa'e nee"e" by your
&:%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!aunching Activities and Sub#Activities

appli'ation, an" running out o& sta'k spa'e is a signi&i'ant problem in An"roi", as =ill be "es'ribe" in a later 'hapter.

&:0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &1

Working )ith Cesources

esour'es are stati' bits o& in&ormation hel" outsi"e the Ca!a sour'e 'o"e. ?ou ha!e seen one type o& resour'e S the layout S &reRuently in the e;amples in this book. 5here are many other types o& resour'e, su'h as images an" strings, that you 'an take a"!antage o& in your An"roi" appli'ations.

The Cesource !ineup


esour'es are store" as &iles un"er the res/ "ire'tory in your An"roi" proGe't layout. With the e;'eption o& ra= resour'es ( res/raE/), all the other types o& resour'es are parse" &or you, either by the An"roi" pa'kaging system or by the An"roi" system on the "e!i'e or emulator. %o, &or e;ample, =hen you lay out an a'ti!ity7s $0 !ia a layout resour'e (res/laFout/), you "o not ha!e to parse the layout FML yoursel& S An"roi" han"les that &or you. 0n a""ition to layout resour'es (&irst seen in an earlier 'hapter), there are se!eral other types o& resour'e a!ailable to you, in'lu"ing,

0mages (res/draEable/), &or putting stati' i'ons or other pi'tures in a user inter&a'e a= (res/raE/), &or putting arbitrary &iles that ha!e meaning to your appli'ation but not ne'essarily to An"roi" &rame=orks

&:7
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

%trings, 'olors, arrays, an" "imensions (res/values/), to both gi!e these sorts o& 'onstants symboli' names an" to keep them separate &rom the rest o& the 'o"e (e.g., &or internationaliKation an" lo'aliKation) FML (res/Gml/), &or stati' FML &iles 'ontaining your o=n "ata an" stru'ture

String Theory
Deeping your labels an" other bits o& te;t outsi"e the main sour'e 'o"e o& your appli'ation is generally 'onsi"ere" to be a !ery goo" i"ea. 0n parti'ular, it helps =ith internationaliKation (0182) an" lo'aliKation (L102), 'o!ere" later in this 'hapter. E!en i& you are not going to translate your strings to other languages, it is easier to make 'orre'tions i& all the strings are in one spot instea" o& s'attere" throughout your sour'e 'o"e. An"roi" supports regular e;ternaliKe" strings, along =ith Mstring &ormatsM, =here the string has pla'ehol"ers &or "ynami'ally-inserte" in&ormation. >n top o& that, An"roi" supports simple te;t &ormatting, 'alle" Mstyle" te;tM, so you 'an make your =or"s be bol" or itali' intermingle" =ith normal te;t.

Pl in Strin!s
8enerally speaking, all you nee" to "o is ha!e an FML &ile in the res/values "ire'tory (typi'ally name" res/values/strings.Gml), =ith a resources root element, an" one 'hil" string element &or ea'h string you =ish to en'o"e as a resour'e. 5he string element takes a name attribute, =hi'h is the uniRue name &or this string, an" a single te;t element 'ontaining the te;t o& the string,
LresourcesM Lstring name67Uuick7M&he Uuick broEn foG...L/stringM Lstring name67laughs7M!e Eho laughs last...L/stringM L/resourcesM

5he only tri'ky part is i& the string !alue 'ontains a Ruote ( 7) or an apostrophe (I). 0n those 'ases, you =ill =ant to es'ape those !alues, by
&:8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

pre'e"ing them =ith a ba'kslash (e.g., &hese are the times that trF menTIs souls). >r, i& it is Gust an apostrophe, you 'oul" en'lose the !alue in Ruotes (e.g., 7&hese are the times that trF menIs souls.7). ?ou 'an then re&eren'e this string &rom a layout &ile (as Ostring/..., =here the ellipsis is the uniRue name S e.g., Ostring/laughs). >r you 'an get the string &rom your Ca!a 'o"e by 'alling get2tringPQ =ith the resour'e 0@ o& the string resour'e, that being the uniRue name pre&i;e" =ith ?.string. (e.g., get2tringP?.string.UuickQ).

Strin! 5orm ts
As =ith other implementations o& the Ca!a language, An"roi"7s @al!ik -M supports string &ormats. +ere, the string 'ontains pla'ehol"ers representing "ata to be repla'e" at runtime by !ariable in&ormation (e.g., #F name is \1's). #lain strings store" as resour'es 'an be use" as string &ormats,
2tring str9ormat6getStringP?.string.mF nameQJ 2tring str?esult62tring.formatPstr9ormat8 7&im7QJ PP&eGtVieEQfindViewByIdP?.id.some labelQQ.setTextPstr?esultQJ

5here is also a &la!or o& get2tringPQ that "oes the 2tring.formatPQ 'all &or you,
2tring str?esult6getStringP?.string.mF name8 7&im7QJ PP&eGtVieEQfindViewByIdP?.id.some labelQQ.setTextPstr?esultQJ

0t is !ery important that you use the !ersion o& the pla'ehol"ers that take an in"e; S \1's instea" o& Gust \s. %trategi'ally, translations o& your string resour'es may 'ause you to apply the !ariable "ata in a "i&&erent or"er than "i" your original translation, an" using non-in"e;e" pla'ehol"ers lo'k you into a parti'ular or"er. 5a'ti'ally, your proGe't =ill &ail to 'ompile, as the An"roi" buil" tools reGe't non-in"e;e" pla'ehol"ers no=a"ays.

&::

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

Styled Te0t
0& you =ant really ri'h te;t, you shoul" ha!e ra= resour'es 'ontaining +5ML, then pour those into a WebDit =i"get. +o=e!er, &or light +5ML &ormatting, using inline elements like LbM, LiM, an" LuM, you 'an Gust use them in a string resour'e,
LresourcesM Lstring name67b7M&his has LbMboldL/bM in it.L/stringM Lstring name67i7M@hereas this has LiMitalicsL/iMXL/stringM L/resourcesM

?ou 'an a''ess these !ia get&eGtPQ, =here you =ill get ba'k an obGe't supporting the android.teGt.2panned inter&a'e an" there&ore has all o& the &ormatting applie",
PP&eGtVieEQfindViewByIdP?.id.another labelQQ .setTextPgetTextP?.string.bQQJ

Styled Te0t nd 5orm ts


Where style" te;t gets tri'ky is =ith style" string &ormats, as 2tring.formatPQ =orks on 2tring obGe'ts, not 2panned obGe'ts =ith &ormatting instru'tions. 0& you really =ant to ha!e style" string &ormats, here is the =orkaroun", 1. 2. Entity-es'ape the angle bra'kets in the string resour'e (e.g., this is ZltJbZgtJ\1'sZltJ/bZgtJ) etrie!e the string resour'e as normal, though it =ill not be style" at this point (e.g., get2tringP?.string.funkF formatQ)

.. 8enerate the &ormat results, being sure to es'ape any string !alues you substitute in, in 'ase they 'ontain angle bra'kets or ampersan"s
2tring.formatPgetStringP?.string.funkF formatQ8 &eGt3tils.html+ncodePstr%ameQQJ

<. Con!ert the entity-es'ape" +5ML into a 2panned obGe't !ia


!tml.from!tmlPQ

-<<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

some&eGtVieE.setTextP!tml .from(tmlPresult9rom2tring9ormatQQJ

5o see this in a'tion, let7s look at the ?esources/2trings "emo. +ere is the layout &ile,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L)inear)aFout android:orientation67horiKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 M L4utton android:id67ORid/format7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGt67Ostring/btn name7 android:on+lick67applF9ormat7 /M L$dit&eGt android:id67ORid/name7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L/)inear)aFoutM L&eGtVieE android:id67ORid/result7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L/)inear)aFoutM

As you 'an see, it is Gust a button, a &iel", an" a label. 5he intent is &or somebo"y to enter their name in the &iel", then 'li'k the button to 'ause the label to be up"ate" =ith a &ormatte" message 'ontaining their name. 5he 4utton in the layout &ile re&eren'es a string resour'e (Ostring/btn name), so =e nee" a string resour'e &ile (res/values/strings.Gml),
LNGml version671.-7 encoding67utf-,7NM LresourcesM Lstring name67app name7M2trings=emoL/stringM Lstring name67btn name7M%ame:L/stringM Lstring name67funkF format7M#F name is ZltJbZgtJ\1'sZltJ/bZgtJL/stringM L/resourcesM

-<*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

5he app name resour'e is automati'ally 'reate" by the android create project 'omman". 5he btn name string is the 'aption o& the 4utton, =hile our style" string &ormat is in funkF format. *inally, to hook all this together, =e nee" a pin'h o& Ca!a,
package com.commonsEare.android.stringsJ import import import import import import import android.app.ActivitFJ android.os.4undleJ android.teGt.&eGt3tilsJ android.teGt.!tmlJ android.vieE.VieEJ android.Eidget.$dit&eGtJ android.Eidget.&eGtVieEJ

public class 2trings=emo eGtends ActivitF : $dit&eGt nameJ &eGtVieE resultJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ name6P$dit&eGtQfindViewByIdP?.id.nameQJ result6P&eGtVieEQfindViewByIdP?.id.resultQJ

public void apply"ormatPVieE vQ : 2tring format6getStringP?.string.funkF formatQJ 2tring simple?esult62tring.formatPformat8 &eGt3tils.html+ncodePname.getTextPQ.toStringPQQQJ result.setTextP!tml.from(tmlPsimple?esultQQJ ;

5he string resour'e manipulation 'an be &oun" in applF9ormatPQ, =hi'h is 'alle" =hen the button is 'li'ke". *irst, =e get our &ormat !ia get2tringPQ S something =e 'oul" ha!e "one at on+reatePQ time &or e&&i'ien'y. 2e;t, =e &ormat the !alue in the &iel" using this &ormat, getting a 2tring ba'k, sin'e the string resour'e is in entity-en'o"e" +5ML. 2ote the use o& &eGt3tils.html$ncodePQ to entity-en'o"e the entere" name, in 'ase somebo"y "e'i"es to use an ampersan" or something. *inally, =e 'on!ert the simple +5ML into a style" te;t obGe't !ia !tml.from!tmlPQ an" up"ate our label.

-<&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

When the a'ti!ity is &irst laun'he", =e ha!e an empty label,

"igure *<<1 The Strings/emo sample application@ as initially launched

but i& =e &ill in a name an" 'li'k the button, =e get,

-<-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

"igure *<*1 The same application@ after filling in some heroic figureGs name

(ot the PictureF


An"roi" supports images in the #28, C#E8, an" 80* &ormats. 80* is o&&i'ially "is'ourage", ho=e!erT #28 is the o!erall pre&erre" &ormat. 0mages 'an be use" any=here that reRuires a =raEable, su'h as the image an" ba'kgroun" o& an ImageVieE. $sing images is simply a matter o& putting your image &iles in res/draEable/ an" then re&eren'ing them as a resour'e. Within layout &iles, images are re&eren'e" as OdraEable/... =here the ellipsis is the base name o& the &ile (e.g., &or res/draEable/foo.png, the resour'e name is OdraEable/foo). 0n Ca!a, =here you nee" an image resour'e 0@, use ?.draEable. plus the base name (e.g., ?.draEable.foo). %o, let7s up"ate the pre!ious e;ample to use an i'on &or the button instea" o& the string resour'e. 5his 'an be &oun" as ?esources/Images. *irst, =e slightly a"Gust the layout &ile, using an Image4utton an" re&eren'ing a "ra=able name" OdraEable/icon, =hi'h re&ers to an image &ile in

-<%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

res/draEable

=ith a base name o& i'on. 0n this 'ase, =e use a .2;.2 #28 &ile &rom the 2u!ola i'on set,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L)inear)aFout android:orientation67horiKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 M LImage4utton android:id67ORid/format7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:src67OdraEable/icon7 android:on+lick67applF9ormat7 /M L$dit&eGt android:id67ORid/name7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L/)inear)aFoutM L&eGtVieE android:id67ORid/result7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L/)inear)aFoutM

2o=, our button has the "esire" i'on,

-<0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

"igure *<&1 The mages/emo sample application

E+!5 The Cesource Way


0& you =ish to pa'kage stati' FML =ith your appli'ation, you 'an use an FML resour'e. %imply put the FML &ile in res/Gml/, an" you 'an a''ess it by get]mlPQ on a ?esources obGe't, supplying it a resour'e 0@ o& ?.Gml. plus the base name o& your FML &ile. %o, in an a'ti!ity, =ith an FML &ile o& Eords.Gml, you 'oul" 'all get?esourcesPQ.get]mlP?.Gml.EordsQ. 5his returns an instan'e o& an ]ml(ull(arser, &oun" in the org.Gmlpull.v1 Ca!a namespa'e. An FML pull parser is e!ent-"ri!en, you keep 'alling neGtPQ on the parser to get the ne;t e!ent, =hi'h 'oul" be 2&A?& &AD, $%= &AD, $%= ="+3#$%&, et'. >n a 2&A?& &AD e!ent, you 'an a''ess the tag7s name an" attributesT a single &$]& e!ent represents the 'on'atenation o& all te;t no"es that are "ire't 'hil"ren o& this element. 1y looping, testing, an" in!oking per-element logi', you parse the &ile. 5o see this in a'tion, let7s re=rite the Ca!a 'o"e &or the 9iles/2tatic sample proGe't to use an FML resour'e. 5his ne= proGe't, ?esources/]#), reRuires that you pla'e the Eords.Gml &ile &rom 2tatic not in res/raE/, but in
-<2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

res/Gml/.

5he layout stays the same, so all that nee"s repla'ing is the Ca!a

sour'e,
package com.commonsEare.android.resourcesJ import import import import import import import import import import import import import android.app.ActivitFJ android.os.4undleJ android.app.)istActivitFJ android.vieE.VieEJ android.Eidget.AdapterVieEJ android.Eidget.ArraFAdapterJ android.Eidget.)istVieEJ android.Eidget.&eGtVieEJ android.Eidget.&oastJ java.io.Input2treamJ java.util.ArraF)istJ org.Gmlpull.v1.]ml(ull(arserJ org.Gmlpull.v1.]ml(ull(arser$GceptionJ

public class ]#)?esource=emo eGtends )istActivitF : &eGtVieE selectionJ ArraF)istL2tringM items6neE ArraF)istL2tringMPQJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ trF : ]ml(ull(arser Gpp6get%esourcesPQ.get,mlP?.Gml.EordsQJ Ehile PGpp.get+!entTypePQX6]ml(ull(arser.$%= ="+3#$%&Q : if PGpp.get+!entTypePQ66]ml(ull(arser.2&A?& &ADQ : if PGpp.get&amePQ.e-ualsP7Eord7QQ : items.addPGpp.get$ttri'uteValueP-QQJ ; ; ; Gpp.nextPQJ

; catch P&hroEable tQ : &oast .makeTextPthis8 7?eUuest failed: 7Rt.toStringPQ8 &oast.)$%D&! )"%DQ .showPQJ ; setList$dapterPneE ArraFAdapterL2tringMPthis8 android.?.laFout.simple list item 18 itemsQQJ ;

-<7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

public void onListItemClickP)istVieE parent8 VieE v8 int position8 long idQ : selection.setTextPitems.getPpositionQ.toStringPQQJ ;

2o=, insi"e our trF...catch blo'k, =e get our ]ml(ull(arser an" loop until the en" o& the "o'ument. 0& the 'urrent e!ent is 2&A?& &AD an" the name o& the element is Eord (Gpp.get%amePQ.eUualsP7Eord7Q), then =e get the onean"-only attribute an" pop that into our list o& items &or the sele'tion =i"get. %in'e =e7re in 'omplete 'ontrol o!er the FML &ile, it is sa&e enough to assume there is e;a'tly one attribute. 1ut, i& you =ere not as 'om&ortable that the FML is properly "e&ine", you might 'onsi"er 'he'king the attribute 'ount (getAttribute+ountPQ) an" the name o& the attribute (getAttribute%amePQ) be&ore blin"ly assuming the --in"e; attribute is =hat you think it is. 5he result looks the same as be&ore, albeit =ith a "i&&erent name in the title bar,

"igure *<-1 The E+!Cesource/emo sample application

-<8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

+iscellaneous ;alues
0n the res/values/ "ire'tory, in a""ition to string resour'es, you 'an pla'e one (or more) FML &iles "es'ribing other simple resour'es, su'h as "imensions, 'olors, an" arrays. We ha!e alrea"y seen uses o& "imensions an" 'olors in pre!ious e;amples, =here they =ere passe" as simple strings (e.g., 71-dip7) as parameters to 'alls. ?ou 'an, o& 'ourse, set these up as Ca!a stati' &inal obGe'ts an" use their symboli' names...but this only =orks insi"e Ca!a sour'e, not in layout FML &iles. 1y putting these !alues in resour'e FML &iles, you 'an re&eren'e them &rom both Ca!a an" layouts, plus ha!e them 'entrally lo'ate" &or easy e"iting. esour'e FML &iles ha!e a root element o& resourcesT e!erything else is a 'hil" o& that root.

Dimensions
@imensions are use" in se!eral pla'es in An"roi" to "es'ribe "istan'es, su'h as a =i"get7s pa""ing. 5here are se!eral "i&&erent units o& measurement a!ailable to you,

an" mm &or in'hes an" millimeters, respe'ti!ely, base" on the a'tual siKe o& the s'reen
in pt

&or points, =hi'h in publishing terms is 1P42n" o& an in'h (again, base" on the a'tual physi'al siKe o& the s'reen) an" sp &or "e!i'e-in"epen"ent pi;els an" s'ale-in"epen"ent pi;els S one pi;el eRuals one dip &or a 1/0"pi resolution s'reen, =ith the ratio s'aling base" on the a'tual s'reen pi;el "ensity (s'alein"epen"ent pi;els also take into a''ount the user7s pre&erre" &ont siKe)
dip

5o en'o"e a "imension as a resour'e, a"" a dimen element, =ith a name attribute &or your uniRue name &or this resour'e, an" a single 'hil" te;t element representing the !alue,

-<:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

LresourcesM Ldimen name67thin7M1-pGL/dimenM Ldimen name67fat7M1inL/dimenM L/resourcesM

0n a layout, you 'an re&eren'e "imensions as Odimen/..., =here the ellipsis is a pla'ehol"er &or your uniRue name &or the resour'e (e.g., thin an" fat &rom the sample abo!e). 0n Ca!a, you re&eren'e "imension resour'es by the uniRue name pre&i;e" =ith ?.dimen. (e.g., ?esources.get=imenP?.dimen.thinQ).

Colors
Colors in An"roi" are he;a"e'imal 81 !alues, also optionally spe'i&ying an alpha 'hannel. ?ou ha!e your 'hoi'e o& single-'hara'ter he; !alues or "ouble-'hara'ter he; !alues, lea!ing you =ith &our styles,
S?D4 SA?D4 S??DD44 SAA??DD44

5hese =ork similarly to their 'ounterparts in Cas'a"ing %tyle %heets (C%%). ?ou 'an, o& 'ourse, put these 81 !alues as string literals in Ca!a sour'e or layout resour'es. 0& you =ish to turn them into resour'es, though, all you nee" to "o is a"" color elements to the resour'es &ile, =ith a name attribute &or your uniRue name &or this 'olor, an" a single te;t element 'ontaining the 81 !alue itsel&,
LresourcesM Lcolor name67FelloE orange7MS99=...L/colorM Lcolor name67forest green7MS--..--L/colorM Lcolor name67burnt umber7MS,ACC><L/colorM L/resourcesM

0n a layout, you 'an re&eren'e 'olors as Ocolor/..., repla'ing the ellipsis =ith your uniRue name &or the 'olor (e.g., burnt umber). 0n Ca!a, you

-*<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

re&eren'e 'olor resour'es by the uniRue name pre&i;e" =ith ?.color. (e.g., ?esources.get+olorP?.color.forest greenQ).

Arr ys
Array resour'es are "esigne" to hol" lists o& simple strings, su'h as a list o& honori&i's (Mr., Mrs., Ms., @r., et'.). 0n the resour'e &ile, you nee" one string-arraF element per array, =ith a name attribute &or the uniRue name you are gi!ing the array. 5hen, a"" one or more 'hil" item elements, ea'h o& =hi'h ha!ing a single te;t element =ith the !alue &or that entry in the array,
LNGml version671.-7 encoding67utf-,7NM LresourcesM Lstring-arraF name67cities7M LitemM(hiladelphiaL/itemM LitemM(ittsburghL/itemM LitemMAllentoEn/4ethlehemL/itemM LitemM$rieL/itemM LitemM?eadingL/itemM LitemM2crantonL/itemM LitemM)ancasterL/itemM LitemMAltoonaL/itemM LitemM!arrisburgL/itemM L/string-arraFM Lstring-arraF name67airport codes7M LitemM(!)L/itemM LitemM(I&L/itemM LitemMA4$L/itemM LitemM$?IL/itemM LitemM?=DL/itemM LitemMAV(L/itemM LitemM)%2L/itemM LitemMA""L/itemM LitemM#=&L/itemM L/string-arraFM L/resourcesM

*rom your Ca!a 'o"e, you 'an then use ?esources.get2tringArraFPQ to get a 2tringAB o& the items in the list. 5he parameter to get2tringArraFPQ is your uniRue name &or the array, pre&i;e" =ith ?.arraF. (e.g., ?esources.get2tringArraFP?.arraF.honorificsQ).

-**

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

/ifferent Strokes for /ifferent "olks


>ne set o& resour'es may not &it all situations =here your appli'ation may be use". >ne ob!ious area 'omes =ith string resour'es an" "ealing =ith internationaliKation (0182) an" lo'aliKation (L102). #utting strings all in one language =orks &ine S probably at least &or the "e!eloper S but only 'o!ers one language. 5hat is not the only s'enario =here resour'es might nee" to "i&&er, though. +ere are others,

$creen orientation, is the s'reen in a portrait orientationH Lan"s'apeH 0s the s'reen sRuare an", there&ore, "oes not really ha!e an orientationH $creen si<e, ho= many pi;els "oes the s'reen ha!e, so you 'an siKe your resour'es a''or"ingly (e.g., large !ersus small i'ons)H Touchscreen, "oes the "e!i'e ha!e a tou'hs'reenH 0& so, is the tou'hs'reen set up to be use" =ith a stylus or a &ingerH 9ey,oard, =hat keyboar" "oes the user ha!e (JWE 5?, numeri', neither), either no= or as an optionH Bther input, "oes the "e!i'e ha!e some other &orm o& input, like a "ire'tional pa" or 'li'k-=heelH

5he =ay An"roi" 'urrently han"les this is by ha!ing multiple resour'e "ire'tories, =ith the 'riteria &or ea'h embe""e" in their names. %uppose, &or e;ample, you =ant to support strings in both English an" %panish. 2ormally, &or a single-language setup, you =oul" put your strings in a &ile name" res/values/strings.Gml. 5o support both English an" %panish, you =oul" 'reate t=o &ol"ers, res/values-en/ an" res/values-es/, =here the !alue a&ter the hyphen is the 0%> /.3-1 t=o-letter 'o"e &or the language you =ant. ?our English-language strings =oul" go in res/valuesen/strings.Gml an" the %panish ones in res/values-es/strings.Gml. An"roi" =ill 'hoose the proper &ile base" on the user7s "e!i'e settings.

-*&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

An e!en better approa'h is &or you to 'onsi"er some language to be your "e&ault, an" put those strings in res/values/strings.Gml. 5hen, 'reate other resour'e "ire'tories &or your translations (e.g., res/values-es/strings.Gml &or %panish). An"roi" =ill try to mat'h a spe'i&i' language set o& resour'esT &ailing that, it =ill &all ba'k to the "e&ault o& res/values/strings.Gml. %eems easy, rightH Where things start to get 'ompli'ate" is =hen you nee" to use multiple "isparate 'riteria &or your resour'es. *or e;ample, let us suppose you =ant to "e!elop both &or the 5-Mobile 81, the %amsung 8ala;y 5ab, an" the Motorola Charm.

5he 5-Mobile 81 has a normal-siKe, me"ium-"ensity s'reen an" a har"=are keyboar" 5he %amsung 8ala;y 5ab has a large siKe, high-"ensity s'reen an" no har"=are keyboar" 5he Motorola Charm has a small siKe, me"ium-"ensity s'reen an" a har"=are keyboar"

?ou may =ant to ha!e some=hat "i&&erent layouts &or these "e!i'es, to take a"!antage o& "i&&erent s'reen real estate an" "i&&erent input options. %pe'i&i'ally,

?ou =ant "i&&erent layouts &or ea'h 'ombination o& siKe, orientation, an" keyboar" ?ou =ant "i&&erent "ra=ables &or ea'h "ensity

>n'e you get into these sorts o& situations, though, all sorts o& rules 'ome into play, su'h as,

5he 'on&iguration options (e.g., -en) ha!e a parti'ular or"er o& pre'e"en'e, an" they must appear in the "ire'tory name in that or"er. 5he An"roi" "o'umentation outlines the spe'i&i' or"er in =hi'h these options 'an appear. *or the purposes o& this e;ample, s'reen siKe is more important than s'reen orientation, =hi'h is

-*-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

more important than s'reen "ensity, =hi'h is more important than =hether or not the "e!i'e has a keyboar".

5here 'an only be one !alue o& ea'h 'on&iguration option 'ategory per "ire'tory. >ptions are 'ase sensiti!e

%o, &or the s'enario "es'ribe" abo!e, in theory, =e =oul" nee" the &ollo=ing "ire'tories, representing the possible 'ombinations,
res/laFout-large-port-mdpi-UEertF res/laFout-large-port-mdpi-nokeFs res/laFout-large-port-hdpi-UEertF res/laFout-large-port-hdpi-nokeFs res/laFout-large-land-mdpi-UEertF res/laFout-large-land-mdpi-nokeFs res/laFout-large-land-hdpi-UEertF res/laFout-large-land-hdpi-nokeFs res/laFout-normal-port-mdpi-UEertF res/laFout-normal-port-mdpi-nokeFs res/laFout-normal-port-finger-UEertF res/laFout-normal-port-hdpi-nokeFs res/laFout-normal-land-mdpi-UEertF res/laFout-normal-land-mdpi-nokeFs res/laFout-normal-land-hdpi-UEertF res/laFout-normal-land-hdpi-nokeFs res/draEable-large-port-mdpi-UEertF res/draEable-large-port-mdpi-nokeFs res/draEable-large-port-hdpi-UEertF res/draEable-large-port-hdpi-nokeFs res/draEable-large-land-mdpi-UEertF res/draEable-large-land-mdpi-nokeFs res/draEable-large-land-hdpi-UEertF

-*%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

res/draEable-large-land-hdpi-nokeFs res/draEable-normal-port-mdpi-UEertF res/draEable-normal-port-mdpi-nokeFs res/draEable-normal-port-finger-UEertF res/draEable-normal-port-hdpi-nokeFs res/draEable-normal-land-mdpi-UEertF res/draEable-normal-land-mdpi-nokeFs res/draEable-normal-land-hdpi-UEertF res/draEable-normal-land-hdpi-nokeFs

@on7t pani': We =ill shorten this list in Gust a moment: 2ote that there is nothing pre!enting you &rom also ha!ing a "ire'tory =ith the una"orne" base name (res/laFout). 0n &a't, this is really a goo" i"ea, in 'ase &uture e"itions o& the An"roi" runtime intro"u'e other 'on&iguration options you "i" not 'onsi"er S ha!ing a "e&ault layout might make the "i&&eren'e bet=een your appli'ation =orking or &ailing on that ne= "e!i'e. Also, =e 'an 'ut the number o& reRuire" "ire'tories a lot by "e'o"ing the rules An"roi" uses &or "etermining =hi'h, among a set o& 'an"i"ates, is the MrightM resour'e "ire'tory to use, 1. *irst up, An"roi" tosses out ones that are spe'i&i'ally in!ali". %o, &or e;ample, i& the s'reen siKe o& the "e!i'e is MnormalM, the -large "ire'tories =oul" be "roppe" as 'an"i"ates, sin'e they 'all &or some other siKe.

2. 2e;t, An"roi" 'ounts the number o& mat'hes &or ea'h &ol"er, an" only pays attention to those =ith the most mat'hes. .. *inally, An"roi" goes in the or"er o& pre'e"en'e o& the options S in other =or"s, it goes &rom le&t to right in the "ire'tory name. Also, our "ra=ables are only !arying by "ensity, an" our layouts are not !arying by "ensity, so =e 'an 'lear out a lot o& 'ombinations by &o'using on only the rele!ant plat&orm "i&&eren'es.

-*0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

%o =e 'oul" skate by =ith only the &ollo=ing 'on&igurations,


res/laFout-large-land-UEertF res/laFout-large-UEertF res/laFout-large-land res/laFout-large res/laFout-normal-land-UEertF res/laFout-normal-UEertF res/laFout-normal-land res/laFout res/draEable-hdpi res/draEable

+ere, =e take a"!antage o& the &a't that spe'i&i' mat'hes take pre'e"en'e o!er Munspe'i&ie"M !alues. %o, a "e!i'e =ith a JWE 5? keyboar" =ill 'hoose a resour'e =ith UEertF in the "ire'tory o!er a resour'e that "oes not spe'i&y its keyboar" type. We 'oul" re&ine this e!en &urther, to only 'o!er the spe'i&i' "e!i'es =e are targeting (e.g., there is no large "e!i'e =ith UEertF),
res/laFout-large-land res/laFout-large res/laFout-land-UEertF res/laFout-UEertF res/laFout-land res/laFout res/draEable-hdpi res/draEable

0& =e "i" not 'are about ha!ing "i&&erent layouts &or =hether the "e!i'e ha" a har"=are keyboar", =e 'oul" "rop the t=o -UEertF resour'e sets. We =ill see these resour'e sets again in the 'hapter on supporting multiple s'reen siKes, later in the book.
-*2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Working )ith Cesources

CT! !anguages5 (oing Both Ways


An"roi" 2.. a""e" support &or many more languages than ha" e;iste" in pre!ious !ersions o& the plat&orm. As su'h, you no= ha!e greater opportunity to lo'aliKe your appli'ation =here it is nee"e". 0n parti'ular, An"roi" 2.. a""e" support &or right-to-le&t ( 5L) languages, notably +ebre= an" Arabi'. #re!iously, An"roi" only supporte" languages =ritten horiKontally &rom le&t to right, su'h as English. 5his not only means you ha!e the potential &or 'reating lo'aliKe" !ersions &or 5L languages, but you may nee" to 'onsi"er =hether your $0 in general =ill =ork properly &or 5L languages. *or e;ample,

Are your &eGtVieE =i"gets aligne" on the le&t si"e =ith other =i"gets or 'ontainersH 0& so, is that the right ans=er &or your 5L usersH Will there be any issues =ith your $dit&eGt =i"gets =hen users start entering 5L te;t, su'h as inappropriate s'rolling be'ause you ha!e not properly 'onstraine" the $dit&eGt =i"get7s =i"thH 0& you 'reate" your o=n &orms o& te;t input, outsi"e o& $dit&eGt an" the input metho" &rame=ork (e.g., 'ustom on-s'reen !irtual keyboar"s), =ill they support 5L languagesH

-*7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &2

/efining and >sing Styles

E!ery no= an" then, you =ill &in" some 'o"e =ith a 'rypti' style attribute in a layout element. *or e;ample, in the 'hapter on threa"ing, there =as our (rogress4ar,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L(rogress4ar android:id67ORid/progress7 stFle67Nandroid:attr/progress4ar2tFle!oriKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L/)inear)aFoutM

%omething about that magi' stFle attribute 'hange" our (rogress4ar &rom a normal 'ir'le to a horiKontal bar. 5his 'hapter =ill brie&ly e;plore the 'on'ept o& styles, ho= you 'an 'reate them, an" ho= you 'an apply them to your o=n =i"gets.

Styles5 / . /C.
5he purpose o& styles is to en'apsulate a set o& attributes that you inten" to use repeate"ly, 'on"itionally, or other=ise =ish to keep separate &rom your layouts proper. 5he primary use 'ase is M"on7t repeat yoursel&M (@ ?) S i& you ha!e a bun'h o& =i"gets that look the same, use a style to use a single
-*:
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

/efining and >sing Styles

"e&inition &or Mlook the sameM, rather than 'opying the look &rom =i"get to =i"get. An" that paragraph =ill make a bit more sense i& =e look at an e;ample, spe'i&i'ally the 2tFles/%oE2tFled sample proGe't. 5his is the same proGe't =e e;amine" in an earlier 'hapter, =ith a &ulls'reen button that sho=s the "ate an" time o& =hen the a'ti!ity =as laun'he" or =hen the button =as pushe". 5his time, though, =e =ant to 'hange the =ay the te;t on the &a'e o& the button appears, an" =e =ill "o so using a style. 5he res/laFout/main.Gml &ile in this proGe't is the same as it =as, =ith the a""ition o& a stFle attribute,
LNGml version671.-7 encoding67utf-,7NM L4utton Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/button7 android:teGt677 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 stFle67OstFle/bigred7 /M

2ote that the stFle attribute is part o& sto'k FML an" there&ore is not in the android namespa'e, so it "oes not get the android: pre&i;. 5he !alue, OstFle/bigred, points to a style resour'e. %tyle resour'es are !alues resour'es an" 'an be &oun" in the res/values/ "ire'tory in your proGe't, or in other resour'e sets (e.g., res/values-v11/ &or !alues resour'es only to be use" on A#0 Le!el 11 or higher). 5he 'on!ention is &or styles resour'es to be hel" in a stFles.Gml &ile, su'h as the one &rom the %oE2tFled proGe't,
LNGml version671.-7 encoding67utf-,7NM LresourcesM LstFle name67bigred7M Litem name67android:teGt2iKe7MC-spL/itemM Litem name67android:teGt+olor7MS9999----L/itemM L/stFleM L/resourcesM

-&<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/efining and >sing Styles

5he LstFleM element supplies the name o& the style, =hi'h is =hat =e use =hen re&erring to the style &rom a layout. 5he LitemM 'hil"ren o& the LstFleM element represent !alues o& attributes to be applie" to =hate!er the style is applie" to=ar"s S in our e;ample, our 4utton =i"get. %o, our 4utton =ill ha!e a 'omparati!ely large &ont (android:teGt2iKe set to C-sp) an" ha!e the te;t appear in re" (android:teGt+olor set to S9999----). 5here are no 'hanges nee"e" else=here in the proGe't S nothing nee"s to be a"Guste" in the mani&est, in the Ca!a 'o"e o& the a'ti!ity, et'. Cust "e&ining the style an" applying it to the =i"get gi!es us results,

"igure *<%1 The StylesK?o)Styled sample application

=lements of Style
5here are &our elements to 'onsi"er =hen applying a style, 1. Where "o you put the style attributes to say you =ant to apply a styleH

-&*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/efining and >sing Styles

2. What attributes 'an you "e&ine !ia a styleH .. +o= "o you inherit &rom a pre!iously-"e&ine" style (one o& your o=n or one &rom An"roi")H <. What !alues 'an those attributes ha!e in a style "e&initionH

,here to Apply

Style

5he stFle attribute 'an be applie" to a =i"get, to only a&&e't that =i"get. 5he stFle attribute 'an be applie" to a 'ontainer, to a&&e't that 'ontainer. +o=e!er, "oing this "oes not automati'ally style its 'hil"ren. *or e;ample, suppose res/laFout/main.Gml looke" instea" like this,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 stFle67OstFle/bigred7 M L4utton android:id67ORid/button7 android:teGt677 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 /M L/)inear)aFoutM

5he resulting $0 =oul" not ha!e the 4utton te;t in a big re" &ont, "espite the stFle attribute. 5he style only a&&e'ts the 'ontainer, not the 'ontents o& the 'ontainer. ?ou 'an also apply a style to an a'ti!ity or an appli'ation as a =hole, though then it is re&erre" to as a MthemeM, =hi'h =ill be 'o!ere" a bit later in this 'hapter.

The Av il =le Attri=utes


When styling a =i"get or 'ontainer, you 'an apply any o& that =i"get7s or 'ontainer7s attributes in the style itsel&. %o, i& it sho=s up in the MFML
-&&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/efining and >sing Styles

AttributesM or M0nherite" FML AttributesM portions o& the An"roi" Ca!a@o's, you 'an put it in a style. 2ote that An"roi" =ill ignore in!ali" styles. %o, ha" =e applie" the bigred style to the )inear)aFout as sho=n abo!e, e!erything =oul" run &ine, Gust =ith no !isible results. @espite the &a't that )inear)aFout has no android:teGt2iKe or android:teGt+olor attribute, there is no 'ompile-time &ailure nor a runtime e;'eption. Also, layout "ire'ti!es, su'h as android:laFout Eidth, 'an be put in a style.

Inheritin!

Style

?ou 'an also in"i'ate that you =ant to inherit style attributes &rom another style, by spe'i&ying an parent attribute on the LstFleM element. *or e;ample, take a look at this style resour'e,
LNGml version671.-7 encoding67utf-,7NM LresourcesM LstFle name67activated7 parent67android:&heme.!olo7M Litem name67android:background7MN android:attr/activated4ackgroundIndicatorL/itemM L/stFleM L/resourcesM

We =ill see this resour'e again in a later 'hapter on using the ne= &ragment $0 &rame=ork. +ere, =e are in"i'ating that =e =ant to inherit the &heme.!olo style &rom =ithin An"roi". +en'e, in a""ition to all o& our o=n attribute "e&initions, =e are spe'i&ying that =e =ant all o& the attribute "e&initions &rom &heme.!olo as =ell. 0n many 'ases, this =ill not be ne'essary. 0& you "o not spe'i&y a parent, your attribute "e&initions =ill be blen"e" into =hate!er "e&ault style is being applie" to the =i"get or 'ontainer.

-&-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/efining and >sing Styles

The Possi=le > lues


5ypi'ally, the !alue that you =ill gi!e those attributes in the style =ill be some 'onstant, like C-sp or S9999----. %ometimes, though, you =ant to per&orm a bit o& in"ire'tion S you =ant to apply some other attribute !alue &rom the theme you are inheriting &rom. 0n that 'ase, you =ill =in" up using the some=hat 'rypti' Nandroid:attr/ synta;, along =ith a &e= relate" magi' in'antations. *or e;ample, let7s look again at this style resour'e,
LNGml version671.-7 encoding67utf-,7NM LresourcesM LstFle name67activated7 parent67android:&heme.!olo7M Litem name67android:background7MN android:attr/activated4ackgroundIndicatorL/itemM L/stFleM L/resourcesM

+ere, =e are in"i'ating that the !alue o& android:background is not some 'onstant !alue, or e!en a re&eren'e to a "ra=able resour'e (e.g., OdraEable/mF background). 0nstea", =e are re&erring to the !alue o& some other attribute S activated4ackgroundIndicator S &rom our inherite" theme. Whate!er the theme "e&ines as being the activated4ackgroundIndicator is =hat our ba'kgroun" shoul" be. %ometimes, this is applie" to a style as a =hole. *or e;ample, let7s look again at the (rogress4ar,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L(rogress4ar android:id67ORid/progress7 stFle67Nandroid:attr/progress4ar2tFle!oriKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L/)inear)aFoutM

-&%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/efining and >sing Styles

+ere, our style attribute S not a style resour'e S is pointing to a themesupplie" attribute (progress4ar2tFle!oriKontal). 0& you poke through the An"roi" sour'e 'o"e, you =ill see that this is "e&ine" as being a style resour'e, spe'i&i'ally Oandroid:stFle/@idget.(rogress4ar.!oriKontal. +en'e, =e are saying to An"roi" that =e =ant our (rogress4ar style" as Oandroid:stFle/@idget.(rogress4ar.!oriKontal, !ia the in"ire'tion o& N android:attr/progress4ar2tFle!oriKontal. 5his portion o& the An"roi" style system is !ery un"er-"o'umente", to the point =here 8oogle itsel& re'ommen"s you look at the An"roi" sour'e 'o"e listing the !arious styles to see =hat is possible. 5his is one pla'e =here inheriting a style be'omes important. 0n the &irst e;ample sho=n in this se'tion, =e inherite" &rom &heme.!olo, be'ause =e spe'i&i'ally =ante" the activated4ackgroundIndicator !alue &rom &heme.!olo. 5hat !alue might not e;ist in other styles, or it might not ha!e the !alue =e =ant.

Themes5 Would a Style By Any ,ther ?ame111


5hemes are styles, applie" to an a'ti!ity or appli'ation, !ia an android:theme attribute on the LactivitFM or LapplicationM element. 0& the theme you are applying is your o=n, Gust re&eren'e it as OstFle/..., Gust as you =oul" in a stFle attribute o& a =i"get. 0& the theme you are applying, though, 'omes &rom An"roi", typi'ally you =ill use a !alue =ith Oandroid:stFle/ as the pre&i;, su'h as Oandroid:stFle/&heme.=ialog or Oandroid:stFle/&heme.)ight. 0n a theme, your &o'us is not so mu'h on styling =i"gets, but styling the a'ti!ity itsel&. *or e;ample, here is the "e&inition o& Oandroid:stFle/&heme.%o&itle4ar.9ullscreen,
LX-- Variant of the default PdarkQ theme that has no title bar and fills the entire screen --M LstFle name67&heme.%o&itle4ar.9ullscreen7M Litem name67android:EindoE9ullscreen7MtrueL/itemM Litem name67android:EindoE+ontent"verlaF7MOnullL/itemM L/stFleM

-&0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/efining and >sing Styles

0t spe'i&ies that the a'ti!ity shoul" take o!er the entire s'reen, remo!ing the status bar on An"roi" 1.; an" 2.; "e!i'es ( android:EindoE9ullscreen set to true). 0t also spe'i&ies that the M'ontent o!erlayM S a layout that =raps aroun" your a'ti!ity7s 'ontent !ie= S shoul" be set to nothing (android:EindoE+ontent"verlaF set to Onull), ha!ing the e&&e't o& remo!ing the title bar. A theme might also spe'i&y other styles that are applie" to spe'i&i' =i"gets. *or e;ample, it is in the root theme (&heme) that =e see,
Litem name67progress4ar2tFle!oriKontal7MOandroid:stFle/@idget.(rogress4ar.!oriKontalL/ itemM

+ere, progress4ar2tFle!oriKontal is Oandroid:stFle/@idget.(rogress4ar.!oriKontal. 5his is re&eren'e Nandroid:attr/progress4ar2tFle!oriKontal

pointing to ho= =e are able to in our (rogress4ar =i"get, an" =e 'oul" 'reate our o=n theme that re-"e&ines progress4ar2tFle!oriKontal to point to some other style (e.g., =e =ant to 'hange the roun"e" re'tangle use" &or the a'tual progress bar image itsel&).

-&2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &6

3andling +ultiple Screen SiBes

*or the &irst year or so sin'e An"roi" 1.0 =as release", all pro"u'tion An"roi" "e!i'es ha" the same s'reen resolution (+-8A, .20;<80) an" siKe (aroun" ..AM P 3'm). %tarting in the &all o& 2003, though, "e!i'es starte" arri!ing =ith =i"ely "isparate s'reen siKes an" resolutions, &rom tiny J-8A (2<0;.20) s'reens to mu'h larger W-8A (<80;800) s'reens. An", in the &all o& 2010, tablets an" 8oogle 5- "e!i'es appeare", o&&ering yet more s'reen siKes. >& 'ourse, users =ill be e;pe'ting your appli'ation to be &un'tional on all o& these, an" perhaps take a"!antage o& larger s'reen siKes to a"" greater !alue. 5o that en", An"roi" 1./ a""e" ne= 'apabilities to help better support these "i&&ering s'reen siKes an" resolutions, an" these 'apabilities ha!e been e;ten"e" in subseRuent An"roi" releases. 5he An"roi" "o'umentation has e;tensi!e 'o!erage o& the me'hani's o& han"ling multiple s'reen siKes. ?ou are en'ourage" to rea" that page along =ith this 'hapter, to get the best un"erstan"ing o& ho= best to 'ope =ith, an" perhaps take a"!antage o&, multiple s'reen siKes. A&ter a number o& se'tions "is'ussing the options an" theory, the 'hapter =raps =ith an in"epth look at making a &airly simple appli'ation han"le multiple s'reen siKes =ell.

-&7
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

Taking the /efault


Let7s suppose, though, that you start o&& by totally ignoring the issue o& s'reen siKes an" resolutions. What happensH 0& your appli'ation is 'ompile" &or An"roi" 1.A or lo=er, An"roi" =ill assume your appli'ation =as "esigne" to look goo" on the 'lassi' s'reen siKe an" resolution. An"roi" =ill then automati'ally "o the &ollo=ing,

0& your appli'ation is installe" on a "e!i'e =ith a larger s'reen, An"roi" =ill run your appli'ation in M'ompatibility mo"eM, s'aling e!erything base" on the a'tual s'reen siKe. %o, suppose you ha!e a ><pG sRuare #28 &ile, an" An"roi" install an" runs your appli'ation on a "e!i'e =ith the stan"ar" physi'al siKe but a W-8A resolution (a so-'alle" Mhigh-"ensityM s'reen). An"roi" might s'ale your #28 &ile to be C0pG =hen it "isplays it, so it =ill take up the same !isible spa'e on the s'reen. >n the plus si"e, An"roi" han"les this automati'allyT on the minus si"e, bitmap s'aling algorithms ten" to make the images a bit &uKKy. An"roi" =ill blo'k your appli'ation &rom running on a "e!i'e =ith a smaller s'reen. +en'e, J-8A "e!i'es, like the +5C 5attoo, =ill be unable to get your appli'ation, e!en i& it is a!ailable on the An"roi" Market.

As an e;ample o& ho= this a&&e'ts your app, take a peek at the +ontainers/&able sample appli'ation as !ie=e" on an +5C 5attoo, =ith its J-8A s'reen,

-&8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

"igure *<01 Table!ayout sample in I;(A via compatibility mode

0& your appli'ation is 'ompile" &or An"roi" 1./ or higher, An"roi" assumes that you are properly han"ling all s'reen siKes, an" there&ore =ill not run your appli'ation in M'ompatibility mo"eM. We =ill see ho= to tailor this in a later se'tion.

Whole in ,ne
5he simplest approa'h to han"ling multiple s'reen siKes in An"roi" is to "esign your user inter&a'es su'h that they automati'ally s'ale &or the s'reen siKe, =ithout any siKe-spe'i&i' 'o"e or resour'es. 0n other =or"s, Mit Gust =orksM. 5his implies, though, that e!erything you use in your user inter&a'e 'an be gra'e&ully s'ale" by An"roi" an" that e!erything =ill &it, e!en on a J-8A s'reen. +ere are some tips &or a'hie!ing this Mall in oneM solution,

-&:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

Don't Thin$ A=out Positions4 Thin$ A=out Rules


%ome "e!elopers, perhaps those 'oming &rom the M"rag-an"-"ropM s'hool o& $0 "e!elopment, think &irst an" &oremost about the positions o& =i"gets. 5hey think that they =ant 'ertain =i"gets to be 'ertain &i;e" siKes at 'ertain &i;e" lo'ations. 5hey get &rustrate" =ith An"roi" layout manager ('ontainers) an" may gra!itate to the "epre'ate" Absolute)aFout as a =ay to "esign $0s they =ay they use" to. 5hat rarely =orks =ell e!en on "esktops, as 'an be seen by appli'ations that "o not han"le =in"o= resiKing !ery =ell. %imilarly, it =ill not =ork on mobile "e!i'es, parti'ularly An"roi", =ith its range o& s'reen siKes an" resolutions. 0nstea" o& thinking about positions, think about rules. ?ou nee" to tea'h An"roi" the Mbusiness rulesM about =here =i"gets shoul" be siKe" an" pla'e", =ith An"roi" then interpreting those rules base" upon =hat the "e!i'e7s s'reen a'tually supports in terms o& resolution. 5he simplest rules are the fill parent an" Erap content !alues &or an" android:laFout height. 5hose "o not spe'i&y spe'i&i' siKes, but rather a"apt to the spa'e a!ailable.
android:laFout Eidth

5he ri'hest en!ironment &or easily spe'i&ying rules is to use ?elative)aFout. While 'ompli'ate" on the sur&a'e, ?elative)aFout "oes an e;'ellent Gob o& letting you 'ontrol your layout =hile still a"apting it to other s'reen siKes. *or e;ample, you 'an,

E;pli'itly an'hor =i"gets to the bottom or right si"e o& the s'reen, rather than hoping they =ill =in" up there 'ourtesy o& some other layout Control the "istan'es bet=een =i"gets that are M'onne'te"M (e.g., a label &or a &iel" shoul" be to the le&t o& the &iel") =ithout ha!ing to rely on pa""ing or margins

5he greatest 'ontrol &or spe'i&ying rules is to 'reate your o=n layout 'lass. *or e;ample, suppose you are 'reating a series o& appli'ations that
--<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

implement 'ar" games. ?ou may =ant to ha!e a layout 'lass that kno=s about playing 'ar"s, ho= they o!erlap, =hi'h are &a'e up !ersus &a'e "o=n, ho= big to be to han"le !arying number o& 'ar"s, et'. While you 'oul" a'hie!e the "esire" look =ith, say, a ?elative)aFout, you may be better ser!e" implementing a (laFing+ard)aFout or a !and"f+ards)aFout or something that is more e;pli'itly tailore" &or your appli'ation. $n&ortunately, 'reating 'ustom layout 'lasses is un"er-"o'umente" at this point in time.

Consider Physic l Dimensions


An"roi" o&&ers a =i"e range o& a!ailable units o& measure &or "imensions. 5he most popular has been the pi;el ( pG), be'ause it is easy to M=rap your hea" aroun"M the 'on'ept. A&ter all, all An"roi" "e!i'es =ill ha!e s'reens =ith su'h-an"-so number o& pi;els in ea'h "ire'tion. +o=e!er, pi;els start to be'ome troublesome as s'reen "ensity 'hanges. As the number o& pi;els in a gi!en s'reen siKe in'reases, the pi;els e&&e'ti!ely shrink. A C>pG i'on on a tra"itional An"roi" "e!i'e might be &inger-&rien"ly, but on a high-"ensity "e!i'e (say, W-8A in a mobile phone &orm &a'tor), C>pG may be a bit small &or use =ith a &inger. 0& you ha!e something intrinsi'ally s'alable (e.g., a 4utton) =here you ha" been spe'i&ying a siKe in pi;els, you might 'onsi"er s=it'hing to using millimeters (mm) or in'hes (in) as the unit o& measure. 1-mm is 1-mm regar"less o& the s'reen resolution or the s'reen siKe. 5his =ay, you 'an ensure that your =i"get is siKe" to be &inger-&rien"ly, regar"less o& the number o& pi;els that might take.

Avoid BRe lB Pi0els


0n some 'ir'umstan'e using millimeters &or "imensions =ill not make sense. 5hen, you may =ish to 'onsi"er using other units o& measure =hile still a!oi"ing MrealM pi;els.

--*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

An"roi" o&&ers "imensions measure" in "ensity-in"epen"ent pi;els ( dip). 5hese map 1,1 to pi;els &or a 1/0"pi s'reen (e.g., a 'lassi' +-8A An"roi" "e!i'e) an" s'ale &rom there. *or e;ample, on a 2<0"pi "e!i'e (e.g., a phone-siKe" W-8A "e!i'e), the ratio is 2,., so .-dip X .-pG at 1/0"pi X /.pG at 2<0"pi. 5he a"!antage to the user o& going =ith "ip is that the a'tual siKe o& the "imension stays the same, so !isibly there is no "i&&eren'e bet=een .-dip at 1/0"pi an" .-dip at 2<0"pi. An"roi" also o&&ers "imensions measure" in s'ale" pi;els ( sp). %'ale" pi;els, in theory, are s'ale" base" on the user7s 'hoi'e o& &ont siKe (9"%& 2+A)$ !alue in 2Fstem.2ettings).

Choose Sc l =le Dr # =les


Classi' bitmaps S #28, C#8, 80* S are not intrinsi'ally s'alable. 0& you are not running in M'ompatibility mo"eM, An"roi" =ill not e!en try to s'ale them &or you base" on s'reen resolution an" siKe. Whate!er siKe o& bitmap you supply is the siKe it =ill be, e!en i& that makes the image too large or too small on some s'reens. >ne =ay to a""ress this is to try to a!oi" stati' bitmaps, using nine-pat'h bitmaps an" FML-"e&ine" "ra=ables (e.g., Dradient=raEable) as alternati!es. A nine-pat'h bitmap is a #28 &ile spe'ially en'o"e" to ha!e rules in"i'ating ho= that image 'an be stret'he" to take up more spa'e. FML-"e&ine" "ra=ables use a Ruasi-%-8 FML language to "e&ine shapes, their strokes an" &ills, an" so on.

Tailor +ade@ 6ust "or .ou $And .ou@ And .ou@ And111'
5here =ill be times, though, =hen you =ant to ha!e "i&&erent looks or beha!iors base" upon s'reen siKe or "ensity. An"roi" has =ays &or you to s=it'h out resour'es or 'o"e blo'ks base" on the en!ironment in =hi'h your appli'ation runs. When properly use" in 'ombination =ith the abo!e te'hniRues, a'hie!ing s'reen siKe- an" "ensity-in"epen"en'e is eminently possible, at least &or "e!i'es running An"roi" 1./ an" ne=er.
--&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

Csupports*screensD
5he &irst step to proa'ti!ely supporting s'reen siKes is to a"" the LsupportsscreensM element to your Android#anifest.Gml &ile. 5his spe'i&ies =hi'h s'reen siKes you e;pli'itly support an" =hi'h you "o not. 5hose that you "o not =ill be han"le" by the automati' M'ompatibility mo"eM "es'ribe" pre!iously. +ere is a mani&est 'ontaining a Lsupports-screensM element,
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.eu<Fou7 android:version+ode6717 android:version%ame671.-7M Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7 /M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67.$3<5ou7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7 /M LcategorF android:name67android.intent.categorF.)A3%+!$?7 /M L/intent-filterM L/activitFM L/applicationM L/manifestM

5hree o& these attributes are almost sel&-e;planatory, android:small2creens, android:normal2creens, an" android:large2creens ea'h take a boolean !alue in"i'ating i& your appli'ation e;pli'itly supports those s'reens ( true) or reRuires M'ompatibility mo"eM assistan'e ( false). An"roi" 2.. has also a""e" an android:Glarge2creens &or larger tablets an" (perhaps) tele!isions. 5he android:anF=ensitF attribute in"i'ates =hether you are taking "ensity into a''ount in your 'al'ulations (true) or not (false). 0& false, An"roi" =ill preten" as though all o& your "imensions (e.g., <pG) are &or a normal-"ensity (1/0"pi) s'reen. 0& your appli'ation is running on a s'reen =ith lo=er or higher "ensity, An"roi" =ill s'ale your "imensions a''or"ingly. 0& you
---

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

in"i'ate that android:anF=ensitF 6 7true7, you are telling An"roi" not to "o that, putting the onus on you to use "ensity-in"epen"ent units, su'h as dip, mm, or in.

Resources nd Resource Sets


5he primary =ay to MtoggleM "i&&erent things base" on s'reen siKe or "ensity is to 'reate resour'e sets. 1y 'reating resour'e sets that are spe'i&i' to "i&&erent "e!i'e 'hara'teristi's, you tea'h An"roi" ho= to ren"er ea'h, =ith An"roi" s=it'hing among those sets automati'ally.

De. ult Sc lin!


1y "e&ault, An"roi" =ill s'ale all "ra=able resour'es. 5hose that are intrinsi'ally s'alable, as "es'ribe" in the pre!ious se'tion, =ill s'ale ni'ely. >r"inary bitmaps =ill be s'ale" Gust using a normal s'aling algorithm, =hi'h may or may not gi!e you great results. 0t also may slo= things "o=n a bit. 0& you =ish to a!oi" this, you =ill nee" to set up separate resour'e sets 'ontaining your non-s'alable bitmaps.

Density*B sed Sets


0& you =ish to ha!e "i&&erent layouts, "imensions, or the like base" upon "i&&erent s'reen "ensities, you 'an use the -ldpi, -mdpi, -hdpi, an" -Ghdpi resour'e set labels. *or e;ample, res/values-hdpi/dimens.Gml =oul" 'ontain "imensions use" in high-"ensity "e!i'es. 2ote that there is a bug in An"roi" 1.A (A#0 le!el .) =hen it 'omes to =orking =ith these s'reen "ensity resour'e sets. E!en though all An"roi" 1.A "e!i'es are me"ium "ensity, An"roi" 1.A might pi'k one o& the other "ensities by a''i"ent. %o long as you are aiming to support An"roi" 1.A an" use s'reen "ensity resour'e sets, you =ill nee" to 'lone the 'ontents o& your -mdpi set, =ith the 'lone name" -mdpi-vC. 5his M!ersion-base" setM is "es'ribe" in greater "etail a bit later in this se'tion.

--%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

SiEe*B sed Sets


%imilarly, i& you =ish to ha!e "i&&erent resour'e sets base" upon s'reen siKe, An"roi" o&&ers -small, -normal, an" -large resour'e set labels. Creating res/laFout-large-land/ =oul" in"i'ate layouts to use on large s'reens (e.g., W-8A) in lan"s'ape orientation.

>ersion*B sed Sets


5here may be times =hen earlier !ersions o& An"roi" get 'on&use" by ne=er resour'e set labels. 5o help =ith that, you 'an in'lu"e a !ersion label to your resour'e set, o& the &orm -v%, =here % is an A#0 le!el. +en'e, res/draEable-large-v</ in"i'ates these "ra=ables shoul" be use" on large s'reens at A#0 le!el < (An"roi" 1./) an" ne=er. %o, i& you &in" that An"roi" 1.A emulators or "e!i'es are grabbing the =rong resour'e sets, 'onsi"er a""ing -v< to their resour'e set names to &ilter them out.

5indin! 3our SiEe


0& you nee" to take "i&&erent a'tions in your Ca!a 'o"e base" on s'reen siKe or "ensity, you ha!e a &e= options. 0& there is something "istin'ti!e in your resour'e sets, you 'an Msni&&M on that an" bran'h a''or"ingly in your 'o"e. *or e;ample, as =ill be seen in the 'o"e sample at the en" o& this 'hapter, you 'an ha!e e;tra =i"gets in some layouts (e.g., res/laFout-large/main.Gml) S simply seeing i& an e;tra =i"get e;ists =ill tell you i& you are running a MlargeM s'reen or not. ?ou 'an also &in" out your s'reen siKe 'lass !ia a +onfiguration obGe't, typi'ally obtaine" by an ActivitF !ia get?esourcesPQ.get+onfigurationPQ. A +onfiguration obGe't has a publi' &iel" name" screen)aFout that is a bitmask in"i'ating the type o& s'reen the appli'ation is running on. ?ou 'an test to see i& your s'reen is small, normal, or large, or i& it is MlongM or not (=here

--0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

MlongM in"i'ates a 1/,3 or similar aspe't ratio, 'ompare" to <,.). *or e;ample, here =e test to see i& =e are running on a large s'reen,
if Pget%esourcesPQ.getConfigurationPQ.screen)aFout Z +onfiguration.2+?$$%)A5"3& 2IV$ )A?D$Q 66+onfiguration.2+?$$%)A5"3& 2IV$ )A?D$Q : // Fes8 Ee are large ; else : // no8 Ee are not ;

%imilarly, you 'an &in" out your s'reen "ensity, or the e;a't number o& pi;els in your s'reen siKe, using the =isplaF#etrics 'lass.

AinGt ?othing !ike the Ceal Thing


5he An"roi" emulators =ill help you test your appli'ation on "i&&erent s'reen siKes. +o=e!er, that =ill only get you so &ar, be'ause mobile "e!i'e LC@s ha!e "i&&erent 'hara'teristi's than your "esktop or notebook, su'h as,

Mobile "e!i'e LC@s may ha!e a mu'h higher "ensity than "oes your "e!elopment ma'hine A mouse allo=s &or mu'h more pre'ise Mtou'hs'reenM input than "oes an a'tual &ingertip

Where possible, you are going to nee" to either use the emulator in ne= an" e;'iting =ays, or try to get your han"s on a'tual "e!i'es =ith alternati!e s'reen resolutions.

Density Di..ers
5he Motorola @ >0@ has a 2<0"pi, ..4-in'h, <80;8A< pi;el s'reen. 5o emulate a @ >0@ s'reen, base" on pi;el 'ount, takes up one thir" o& a 13M 1280;102< LC@ monitor, be'ause the LC@ monitor7s "ensity is mu'h lo=er than that o& the @ >0@ S aroun" 3/"pi. %o, =hen you &ire up your

--2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

An"roi" emulator &or an *W-8A "isplay like that o& the @ >0@, you =ill get a massi!e emulator =in"o=. 5his is still per&e'tly &ine &or "etermining the o!erall look o& your appli'ation in an *W-8A en!ironment. egar"less o& "ensity, =i"gets =ill still align the same, siKes =ill ha!e the same relationships (e.g., Wi"get A might be t=i'e as tall as Wi"get 1, an" that =ill be true regar"less o& "ensity), an" so on. +o=e!er,

5hings that might appear to be a suitable siKe =hen !ie=e" on a 13M LC@ may be entirely too small on a mobile "e!i'e s'reen o& the same resolution 5hings that you 'an easily 'li'k upon in the emulator =ith a mouse may be mu'h too small to pi'k out on a physi'ally smaller an" "enser s'reen =hen use" =ith a &inger

Ad7ustin! the Density


1y "e&ault, the emulator =ill keep the pi;el 'ount a''urate at the e;pense o& "ensity, =hi'h is =hy you get the really big emulator =in"o=. ?ou "o ha!e an option, though, o& ha!ing the emulator keep the "ensity a''urate at the e;pense o& pi;el 'ount. 5he easiest =ay to "o this is to use the ne= An"roi" A-@ Manager, intro"u'e" in An"roi" 1./. 5he An"roi" 2.0 e"ition o& this tool has a MLaun'h >ptionsM "ialog that pops up =hen you go to start an emulator instan'e !ia the M%tart...M button,

--7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

"igure *<21 The !aunch ,ptions dialog

1y "e&ault, the M%'ale "isplay to real siKeM 'he'kbo; is un'he'ke", an" An"roi" =ill open the emulator =in"o= normally. ?ou 'an, ho=e!er, 'he'k that 'he'kbo; an" then pro!i"e t=o bits o& s'aling in&ormation, 1. 5he s'reen siKe o& the "e!i'e you =ish to emulate, in in'hes (e.g., ..4 in'hes &or the Motorola @ >0@)

2. 5he "pi o& your monitor S 'li'k the MHM button to bring up a 'al'ulator to help you "etermine =hat your "pi !alue is 5his =ill gi!e you an emulator =in"o= that more a''urately "epi'ts =hat your user inter&a'e =ill look like on a physi'al "e!i'e, at least in terms o& siKes. +o=e!er, sin'e the emulator is using &ar &e=er pi;els than =ill a "e!i'e, &onts may be "i&&i'ult to rea", images may be blo'ky, et'.

Cuthlessly =xploiting the Situation


%o &ar, =e ha!e &o'use" on ho= you 'an ensure your layouts look "e'ent on other s'reen siKes. An", &or smaller s'reens than the norm (e.g., J-8A), that is perhaps all you 'an ask &or. >n'e =e get into larger s'reens, though, another possibility emerges, using "i&&erent layouts "esigne" to take a"!antage o& the e;tra s'reen spa'e. 5his is parti'ularly use&ul =hen the physi'al s'reen siKe is larger (e.g., a AM LC@
--8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

like on the @ell %treak An"roi" tablet, a 4M LC@ like on the %amsung 8ala;y 5ab), rather than simply ha!ing more pi;els in the same physi'al spa'e. +ere are some =ays you might take a"!antage o& a""itional spa'e,

Repl ce %enus #ith Buttons


An options menu sele'tion reRuires t=o physi'al a'tions, press the ME2$ button, then tap on the appropriate menu 'hoi'e. A 'onte;t menu sele'tion reRuires t=o physi'al a'tions as =ell, long-tap on the =i"get, then tap on the menu 'hoi'e. Conte;t menus ha!e the a""itional problem o& being e&&e'ti!ely in!isible S users may not realiKe that your )istVieE, &or e;ample, has a 'onte;t menu. ?ou might 'onsi"er augmenting your user inter&a'e to pro!i"e "ire't ons'reen =ays o& a''omplishing things that might other=ise be hi""en a=ay on a menu. 2ot only "oes this re"u'e the number o& steps a user nee"s to take to "o things, but it makes those options more ob!ious. *or e;ample, let us suppose you are 'reating a me"ia player appli'ation, an" you =ant to o&&er manual playlist management. ?ou ha!e an a'ti!ity that "isplays the songs in a playlist in a )istVieE. >n an options menu, you ha!e an Ma""M 'hoi'e, to a"" a ne= song &rom the ones on the "e!i'e to the playlist. >n a 'onte;t menu on the )istVieE, you ha!e a Mremo!eM 'hoi'e, plus Mmo!e upM an" Mmo!e "o=nM 'hoi'es to reor"er the songs in the list. >n a large s'reen, though, you might 'onsi"er a""ing &our Image4utton =i"gets to your $0 &or these &our options, =ith the three &rom the 'onte;t menu enable" only =hen a ro= is sele'te" by the @-pa" or tra'kball. >n regular or small s'reens, you =oul" sti'k =ith Gust using the menus.

Repl ce T =s #ith

Simple Activity

?ou may ha!e intro"u'e" a &ab!ost into your $0 to allo= you to "isplay more =i"gets in the a!ailable s'reen spa'e. %o long as the =i"get spa'e you Msa!eM by mo!ing them to a separate tab is more than the spa'e taken up by the tabs themsel!es, you =in. +o=e!er, ha!ing multiple tabs means more
--:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

user steps to na!igate your $0, parti'ularly i& they nee" to &lip ba'k an" &orth bet=een tabs &reRuently. 0& you only ha!e t=o tabs, 'onsi"er 'hanging your $0 to o&&er a large-s'reen layout that remo!es the tabs an" puts all the =i"gets on one s'reen. 5his puts e!erything in &ront o& the user, =ithout ha!ing to s=it'h tabs all the time. 0& you ha!e three or more tabs, you probably =ill la'k s'reen spa'e to put all those tabs7 'ontents on one a'ti!ity. +o=e!er, you might 'onsi"er going hal&-an"-hal&, ha!e popular =i"gets be on the a'ti!ity all o& the time, lea!ing your &ab!ost to han"le the rest on (roughly) hal& o& the s'reen.

Consolid te %ultiple Activities


5he most po=er&ul te'hniRue is to use a larger s'reen to get ri" o& a'ti!ity transitions outright. *or e;ample, i& you ha!e a )istActivitF =here 'li'king on an item brings up that item7s "etails in a separate a'ti!ity, 'onsi"er supporting a large-s'reen layout =here the "etails are on the same a'ti!ity as the )istVieE (e.g., )istVieE on the le&t, "etails on the right, in a lan"s'ape layout). 5his eliminates the user ha!ing to 'onstantly press the 1ACD button to lea!e one set o& "etails be&ore !ie=ing another. We =ill see this te'hniRue applie" in the sample 'o"e presente" in the &ollo=ing se'tion.

=xample5 =>%.ou
5o e;amine ho= to use some o& these te'hniRues, let us look at the 2creen2iKes/$3<5ou sample appli'ation. 5his appli'ation has one a'ti!ity ($3<5ou) that 'ontains a )istVieE =ith the roster o& European $nion members an" their respe'ti!e &lags. Cli'king on one o& the 'ountries brings up the mobile Wikipe"ia page &or that 'ountry.

-%<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

0n the sour'e 'o"e to this book, you =ill &in" &our !ersions o& this appli'ation, as =e start =ith an appli'ation that is ignorant o& s'reen siKe an" slo=ly a"" in more s'reen-relate" &eatures.

The 5irst Cut


*irst, here is our Android#anifest.Gml &ile, =hi'h looks "istin'tly like one sho=n earlier in this 'hapter,
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.eu<Fou7 android:version+ode6717 android:version%ame671.-7M Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7 /M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67.$3<5ou7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7 /M LcategorF android:name67android.intent.categorF.)A3%+!$?7 /M L/intent-filterM L/activitFM L/applicationM L/manifestM

?ou =ill note =e ha!e the Lsupports-screensM element, saying that =e in"ee" "o support all s'reen siKes. 5his blo'ks most o& the automati' s'aling that An"roi" =oul" "o i& =e sai" =e "i" not support 'ertain s'reen siKes. >ur main layout is siKe-in"epen"ent, as it is Gust a &ull-s'reen )istVieE,
LNGml version671.-7 encoding67utf-,7NM L)istVieE Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67Oandroid:id/list7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 /M

-%*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

>ur ro=, though, =ill e!entually nee" some t=eaking,


LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:padding67>dip7 android:min!eight67Nandroid:attr/list(referredItem!eight7 M LImageVieE android:id67ORid/flag7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:laFout gravitF67center verticalWleft7 android:padding?ight67<dip7 /M L&eGtVieE android:id67ORid/name7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:laFout gravitF67center verticalWright7 android:teGt2iKe67>-dip7 /M L/)inear)aFoutM

*or e;ample, right no=, our &ont siKe is set to be >-dip, =hi'h =ill not !ary by s'reen siKe or "ensity. >ur $3<5ou a'ti!ity is a bit !erbose, mostly be'ause there are a lot o& E$ members, an" =e ha!e to ha!e the smarts to "isplay the &lag an" the te;t in the ro=,
package com.commonsEare.android.eu<FouJ import import import import import import import import import import import android.app.)istActivitFJ android.content.IntentJ android.net.3riJ android.os.4undleJ android.vieE.VieEJ android.vieE.VieEDroupJ android.Eidget.ArraFAdapterJ android.Eidget.ImageVieEJ android.Eidget.)istVieEJ android.Eidget.&eGtVieEJ java.util.ArraF)istJ

public class $3<5ou eGtends )istActivitF : static private ArraF)istL+ountrFM $36neE ArraF)istL+ountrFMPQJ static : $3.addPneE CountryP?.string.austria8 ?.draEable.austria8

-%&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

?.string.austria urlQQJ $3.addPneE CountryP?.string.belgium8 ?.draEable.belgium8 ?.string.belgium urlQQJ $3.addPneE CountryP?.string.bulgaria8 ?.draEable.bulgaria8 ?.string.bulgaria urlQQJ $3.addPneE CountryP?.string.cFprus8 ?.draEable.cFprus8 ?.string.cFprus urlQQJ $3.addPneE CountryP?.string.cKech republic8 ?.draEable.cKech republic8 ?.string.cKech republic urlQQJ $3.addPneE CountryP?.string.denmark8 ?.draEable.denmark8 ?.string.denmark urlQQJ $3.addPneE CountryP?.string.estonia8 ?.draEable.estonia8 ?.string.estonia urlQQJ $3.addPneE CountryP?.string.finland8 ?.draEable.finland8 ?.string.finland urlQQJ $3.addPneE CountryP?.string.france8 ?.draEable.france8 ?.string.france urlQQJ $3.addPneE CountryP?.string.germanF8 ?.draEable.germanF8 ?.string.germanF urlQQJ $3.addPneE CountryP?.string.greece8 ?.draEable.greece8 ?.string.greece urlQQJ $3.addPneE CountryP?.string.hungarF8 ?.draEable.hungarF8 ?.string.hungarF urlQQJ $3.addPneE CountryP?.string.ireland8 ?.draEable.ireland8 ?.string.ireland urlQQJ $3.addPneE CountryP?.string.italF8 ?.draEable.italF8 ?.string.italF urlQQJ $3.addPneE CountryP?.string.latvia8 ?.draEable.latvia8 ?.string.latvia urlQQJ $3.addPneE CountryP?.string.lithuania8 ?.draEable.lithuania8 ?.string.lithuania urlQQJ $3.addPneE CountryP?.string.luGembourg8 ?.draEable.luGembourg8 ?.string.luGembourg urlQQJ $3.addPneE CountryP?.string.malta8 ?.draEable.malta8 ?.string.malta urlQQJ $3.addPneE CountryP?.string.netherlands8 ?.draEable.netherlands8 ?.string.netherlands urlQQJ $3.addPneE CountryP?.string.poland8 ?.draEable.poland8 ?.string.poland urlQQJ $3.addPneE CountryP?.string.portugal8 ?.draEable.portugal8 ?.string.portugal urlQQJ $3.addPneE CountryP?.string.romania8 ?.draEable.romania8 ?.string.romania urlQQJ $3.addPneE CountryP?.string.slovakia8 ?.draEable.slovakia8 ?.string.slovakia urlQQJ $3.addPneE CountryP?.string.slovenia8 ?.draEable.slovenia8 ?.string.slovenia urlQQJ $3.addPneE CountryP?.string.spain8 ?.draEable.spain8 ?.string.spain urlQQJ $3.addPneE CountryP?.string.sEeden8 ?.draEable.sEeden8 ?.string.sEeden urlQQJ $3.addPneE CountryP?.string.united kingdom8 ?.draEable.united kingdom8

-%-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

?.string.united kingdom urlQQJ ; O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ setList$dapterPneE Country$dapterPQQJ ; O"verride protected void onListItemClickP)istVieE l8 VieE v8 int position8 long idQ : start$cti!ityPneE IntentPIntent.A+&I"% VI$@8 3ri.parsePgetStringP$3.getPpositionQ.urlQQQQJ ; static class +ountrF : int nameJ int flagJ int urlJ CountryPint name8 int flag8 int urlQ : this.name6nameJ this.flag6flagJ this.url6urlJ ; ; class +ountrFAdapter eGtends ArraFAdapterL+ountrFM : Country$dapterPQ : superP$3<5ou.this8 ?.laFout.roE8 ?.id.name8 $3QJ ; O"verride public VieE getViewPint position8 VieE convertVieE8 VieEDroup parentQ : +ountrF@rapper Erapper6nullJ if PconvertVieE66nullQ : convertVieE6getLayoutInflaterPQ.inflateP?.laFout.roE8 nullQJ Erapper6neE Country#rapperPconvertVieEQJ convertVieE.setTagPErapperQJ ; else : Erapper6P+ountrF@rapperQconvertVieE.getTagPQJ ; Erapper.populate"romPgetItemPpositionQQJ returnPconvertVieEQJ ; ;

-%%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

class +ountrF@rapper : private &eGtVieE name6nullJ private ImageVieE flag6nullJ private VieE roE6nullJ Country#rapperPVieE roEQ : this.roE6roEJ ; &eGtVieE get&amePQ : if Pname66nullQ : name6P&eGtVieEQroE.findViewByIdP?.id.nameQJ ; returnPnameQJ ; ImageVieE get"lagPQ : if Pflag66nullQ : flag6PImageVieEQroE.findViewByIdP?.id.flagQJ ; returnPflagQJ ; void populate"romP+ountrF nationQ : get&amePQ.setTextPnation.nameQJ get"lagPQ.setImage%esourcePnation.flagQJ ; ; ;

+ere is =hat the a'ti!ity looks like in an or"inary +-8A emulator,

-%0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

"igure *<71 =>%.ou@ original version@ 3;(A

+ere is =hat the a'ti!ity looks like in a W-8A emulator,

"igure *<81 =>%.ou@ original version@ W;(A $8<<x%8< pixels' -%2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

An", here is =hat it looks like in a J-8A s'reen,

"igure *<:1 =>%.ou@ original version@ I;(A

5i0in! the 5onts


5he &irst problem that shoul" be &i;e" is the &ont siKe. As you 'an see, =ith a &i;e" 20p; siKe, the &ont ranges &rom big to tiny, "epen"ing on s'reen siKe an" "ensity. *or a W-8A s'reen, the &ont may be rather "i&&i'ult to rea". We 'oul" put the "imension as a resour'e (res/values/dimens.Gml) an" ha!e "i&&erent !ersions o& that resour'e base" upon s'reen siKe or "ensity. +o=e!er, it is simpler to Gust spe'i&y a "ensity-in"epen"ent siKe, su'h as .mm, as seen in the 2creen2iKes/$3<5ou > proGe't,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:padding67>dip7 android:min!eight67Nandroid:attr/list(referredItem!eight7 M LImageVieE android:id67ORid/flag7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:laFout gravitF67center verticalWleft7 android:padding?ight67<dip7 -%7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

/M L&eGtVieE android:id67ORid/name7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:laFout gravitF67center verticalWright7 android:teGt2iKe67.mm7 /M L/)inear)aFoutM

+ere is =hat the ne= a'ti!ity looks like in +-8A,

"igure **<1 =>%.ou@ 0mm font version@ 3;(A

...an" W-8A,

-%8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

"igure ***1 =>%.ou@ 0mm font version@ W;(A $8<<x%8< pixels'

....an" J-8A,

"igure **&1 =>%.ou@ 0mm font version@ I;(A

-%:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

2o= our &ont is a 'onsistent siKe, an" large enough to mat'h the &lags.

5i0in! the Icons


%o, =hat about those i'onsH 1y rights, they shoul" be !arying in siKe as =ell, sin'e they are the same &or all three emulators. +o=e!er, An"roi" automati'ally s'ales bitmap resour'es, e!en =ith Lsupports-screensM an" its attributes set to true. >n the plus si"e, this means you may not ha!e to "o anything =ith these bitmaps. +o=e!er, you are relying upon a "e!i'e to "o the s'aling, =hi'h "e&initely 'osts C#$ time (an", hen'e battery li&e). Also, the s'aling algorithms that the "e!i'e uses may not be optimal, 'ompare" to =hat you 'an "o =ith graphi's tools on your "e!elopment ma'hine. proGe't 'reates res/draEable-ldpi an" smaller an" larger ren"itions o& the &lags, respe'ti!ely. 5his proGe't also renames res/draEable to res/draEable-mdpi. An"roi" =ill use the &lags &or the appropriate s'reen "ensity, "epen"ing on =hat the "e!i'e or emulator nee"s.
2creen2iKes/$3<5ou C res/draEable-hdpi, putting in

5he

5his e&&e't is subtle in this 'ase an" =ill not really sho= up =ell in this book.

-sin! the Sp ce
While the a'ti!ity looks &ine on W-8A in portrait mo"e, it really =astes a lot o& spa'e in lan"s'ape mo"e,

-0<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

"igure **-1 =>%.ou@ landscape W;(A $8<<x%8< pixels'

We 'an put that to better use by ha!ing the Wikipe"ia 'ontent appear right on the main a'ti!ity =hen in large-s'reen lan"s'ape mo"e, instea" o& ha!ing to spa=n a separate 1ro=ser a'ti!ity. 5o "o this, =e &irst must 'lone the main.Gml layout into a res/laFout-largeland ren"ition that in'orporates a @ebVieE =i"get, as seen in 2creen2iKes/$3<5ou <,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L)istVieE android:id67Oandroid:id/list7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 /M L@ebVieE android:id67ORid/broEser7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 /M L/)inear)aFoutM

5hen, =e nee" to a"Gust our a'ti!ity to look &or that @ebVieE an" use it =hen &oun", "e&aulting to laun'hing a 1ro=ser a'ti!ity other=ise,
O"verride public void onCreateP4undle savedInstance2tateQ :

-0*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ broEser6P@ebVieEQfindViewByIdP?.id.broEserQJ ; setList$dapterPneE Country$dapterPQQJ

O"verride protected void onListItemClickP)istVieE l8 VieE v8 int position8 long idQ : 2tring url6getStringP$3.getPpositionQ.urlQJ if PbroEser66nullQ : start$cti!ityPneE IntentPIntent.A+&I"% VI$@8 3ri.parsePurlQQQJ ; else : broEser.load*rlPurlQJ ;

5his gi!es us a more spa'e-e&&i'ient e"ition o& the a'ti!ity,

"igure **%1 =>%.ou@ landscape W;(A $8<<x%8< pixels'@ set for normal density@ and sho)ing the embedded Web;ie)

>& 'ourse, i& the user 'li'ks a link in the Wikipe"ia page, that =ill open up the &ull 1ro=ser, &or easier sur&ing.

-0&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling +ultiple Screen SiBes

2ote that testing this !ersion o& the a'ti!ity, to see this beha!ior, reRuires a bit o& e;tra emulator =ork. 1y "e&ault, An"roi" sets up W-8A "e!i'es as being high-"ensity, meaning W-8A is not large in terms o& resour'e sets, but rather normal. ?ou =ill nee" to 'reate a "i&&erent emulator A-@ that is set &or normal (medium) "ensity, =hi'h =ill result in a large s'reen siKe.

,h t I. It Is "ot

Bro#serF

>& 'ourse, $3<5ou "oes 'heat a bit. 5he se'on" a'ti!ity is a 1ro=ser (or @ebVieE in the embe""e" &orm), not some a'ti!ity o& your o=n 'reation. 5hings get slightly more 'ompli'ate" i& the se'on" a'ti!ity is some a'ti!ity o& yours, =ith many =i"gets in a layout, an" you =ant to use it both as an a'ti!ity (&or smaller s'reens) an" ha!e it embe""e" in your main a'ti!ity $0 (&or larger s'reens). 5he best =ay to approa'h this problem, &or An"roi" 1./ an" ne=er, is to employ the ne= &ragments system. While this =as intro"u'e" =ith An"roi" ..0, the An"roi" Compatibility Library makes &ragments a!ailable in earlier !ersions o& An"roi". 5he basi' use o& &ragments S 'omplete =ith another e"ition o& the E$<?ou sample S =ill be 'o!ere" later in this book.

-0-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

PART III Honeycomb and Tablets

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &8

ntroducing the 3oneycomb >

*ebruary 2011 sa= the intro"u'tion o& An"roi" ..0 an" a $0 para"igm that, &or no=, =e =ill re&er to by the An"roi" ..0 'o"ename o& M+oney'ombM. An"roi" ..0 itsel& is e;'lusi!ely targete" at tablets, though elements o& the +oney'omb $0 system =ill make it into &uture !ersions o& An"roi" that support phones as =ell. 5he +oney'omb $0 is perhaps the biggest single 'hange in An"roi" sin'e An"roi" 0.3, be&ore the &irst phones =ere a!ailable. An", the impa'ts o& +oney'omb =ill resoun" through the An"roi" e'osystem &or a long time, as people a"Gust to make use o& =hat =e no= ha!e. Lea"ing o&& some 'hapters on the +oney'omb 'apabilities, this 'hapter is &o'use" more on Mthe big pi'tureM o& +oney'omb an" its pla'e =ithin An"roi".

Why 3oneycombF
0n prin'iple, An"roi"7s original phone-'entri' $0 'an run on tablets. A&ter all, a &e= tablets shippe" =ith An"roi" 2.2 support, su'h as the %amsung 8ala;y 5ab. Clearly, those manu&a'turers thought the An"roi" o& the time =as strong enough &or their tablet "e!i'es. 5hat being sai", as you get into larger tablets (e.g., the Motorola F>>M =ith its 10M "iagonal s'reen), the An"roi" phone $0 starts to be'ome more...'lunky. While appli'ations 'an s'ale up to use the larger s'reen, the
-07
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

ntroducing the 3oneycomb >

"e&ault =ay to s'ale up is Gust to make e!erything bigger, &reRuently resulting in a lot o& =aste" spa'e. While an email 'lient on a phone might "e"i'ate an a'ti!ity to sho=ing the list o& emails in the inbo;, an email 'lient on a tablet really ought to sho= the list o& emails plus something else, su'h as the 'ontent o& a sele'te" email. We ha!e the room S =e may as =ell use it. %imilarly, the "epen"en'e on menus, =hile reasonable on a phone, makes less sense on a tablet. We ha!e the spa'e to sho= more o& those &un'tions right on the s'reen. +i"ing them in menus makes them less "is'o!erable to users an" reRuire e;tra 'li'ks to a''ess. %o, +oney'omb is "esigne" to retain the essen'e o& the An"roi" user e;perien'e, =hile allo=ing appli'ations to (relati!ely) gra'e&ully take a"!antage o& the spa'e that is a!ailable.

What the >ser Sees


An An"roi" ..0 s'reen looks a bit "i&&erent than an An"roi" 2.; s'reen,

"igure **01 The Android -1< app launcher@ as seen on the emulator

-08

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

ntroducing the 3oneycomb >

5he status bar at the top o& the s'reen has been mo!e" to the bottom o& the s'reen an" is no= 'alle" the Msystem barM. >n the le&t are on-s'reen buttons &or 1ACD, +>ME, an" re'ent tasks (=hat &ormerly =oul" take a long-press o& the +>ME button). >n the right, along =ith the 'lo'k an" signalPbattery strength in"i'ators, =ill be =here noti&i'ation i'ons go S the 'on'ept o& noti&i'ations =ill be 'o!ere" later in this book. 0& =e look at an appli'ation that has not been optimiKe" &or An"roi" ..;, =e see mu'h the same $0,

"igure **21 The "ancy!istsK/ynamic sample proAect@ on Android -1<

5he only substanti!e "i&&eren'e is the ne= i'on in the system bar, =hi'h =ill bring up an An"roi" 2.; options menu, i& the appli'ation has one. +o=e!er, An"roi" ..0-optimiKe" appli'ations =ill look a bit "i&&erent,

-0:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

ntroducing the 3oneycomb >

"igure **71 Adding a contact on Android -1<

>n the top, =e see the Ma'tion barM. 5he a'tion bar largely repla'es options menus, e!en though you "e&ine one the same =ay you "e&ine an options menu. +ere, M@oneM an" MCan'elM are the &irst t=o options menu 'hoi'es. 5he i'on to the right represents other options menu 'hoi'es, =hi'h =ill appear =hen the user taps that i'on,

-2<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

ntroducing the 3oneycomb >

"igure **81 The options menu portion of the action bar in Android -1<

5he i'on in the upper-le&t is tappable, an" in this 'ase takes the user MupM in the hierar'hy o& a'tions in this appli'ation, in"i'ate" by the north=estpointing arro=hea". 0n this 'ase, going MupM &rom a""ing a ne= 'onta't takes you to the list o& e;isting 'onta'ts,

"igure **:1 The roster of available contacts in Android -1<

-2*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

ntroducing the 3oneycomb >

0n An"roi" 2.;, the 'onta'ts $0 =oul" ha!e one a'ti!ity =ith the list o& 'onta'ts, an" a separate a'ti!ity to !ie= the "etails o& that 'onta't. 0n An"roi" ..0, these are 'ombine" in a single a'ti!ity. ?et, in the &uture, =hen the +oney'omb $0 is applie" to phones, the same 'o"e base =ill re!ert ba'k to the one-a'ti!ity-per-operation mo"e &rom be&ore. 5his is a''omplishe" through the use o& &ragments, =hi'h =ill be 'o!ere" later in this book.

"igure *&<1 The contact filter spinner in Android -1<

5o the right o& that is a sear'h &iel", built into the a'tion bar. Also, the menu items on the right si"e o& the a'tion bar no= represent a mi; o& options menu items (e.g., a"" a ne= 'onta't) an" 'onte;t menu items &or the sele'te" 'onta't (e.g., e"it the 'onta't). *un'tionally, e!erything is there that you =oul" see in An"roi" 2.;. 0t has been reorganiKe" &or An"roi" ..;, =ith an emphasis on taking &ormerly hi""en things like menus an" a""ing them to the main s'reen &or ease o& "is'o!ery an" use.

-2&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

ntroducing the 3oneycomb >

The 3olographic Theme


An"roi" appli'ations that are up"ate" &or An"roi" ..0 =ill ha!e a "i&&erent look-an"-&eel, not only &or the a'ti!ity as a =hole, but &or in"i!i"ual =i"gets. 5he so-'alle" M+olographi'M theme is applie" by "e&ault to +oney'omb-'apable appli'ations. 5his 'an ha!e some signi&i'ant impa't on the =ay =i"gets look. While they =ork the same, they =ill look "i&&erent, =hi'h may 'ause you to up"ate "o'umentation an" su'h to sho= the 'lassi' theme as =ell as the ne= +olographi' look. *or e;ample, the MAll Conta'tsM item in the a'tion bar o& the last s'reenshot is a 2pinner, one that is opene" up to sho= the a!ailable options. 5he &ormer pop-up "ialog &or 'hoosing the 2pinner !alue is gone, repla'e" by a true "rop-"o=n. %imilarly, tabs, as implemente" =ith &ab@idget, =ill look substantially "i&&erent,

"igure *&*1 The "ancyK/ynamicTabs sample application@ updated for Android -1<

0& you are 'reating your o=n 'ustom styles, there are t=o that you =ill =ant to 'onsi"er inheriting &rom,
-2-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

ntroducing the 3oneycomb >

1.

&heme.!olo

is the stan"ar" "ark Mholographi' themeM ("ark ba'kgroun", light te;t)

2. &heme.!olo.)ight is the light eRui!alent (light ba'kgroun", "ark te;t)

/ealing )ith the Cest of the /evices


>& 'ourse, it7s not like all the An"roi" phones in the =orl" ha!e up an" !anishe" Gust be'ause An"roi" ..0 has been release". 5he !ision is &or you to 'reate an appli'ation that supports both phones an" tablets &rom a single 'o"e base. ?our phone-'entri' app =ill run Gust &ine on a tablet, though you may =ish to "o some things to take a"!antage o& larger s'reen siKes, as =as "is'usse" earlier in this book. 0& you =ant to a"opt the general look an" &eel o& the +oney'omb $0, you =ill nee" to in'lu"e android:target2dkVersion67117 in your Luses-sdkM element in the mani&est. Also, i& you =ant the gra"ient ba'kgroun" &or your +oney'omb a'ti!ities, a"" the android:hardEareAccelerated67true7 attribute to the LapplicationM or LactivitFM elements in the mani&est to turn on har"=are a''eleration &or 2@ graphi's. *or e;ample, &rom the 2creen2iKes/$3<5ou . sample proGe't, here is the An"roi"Mani&est.;ml &ile, sho=ing both o& these 'hanges,
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.eu<Fou7 android:version+ode6717 android:version%ame671.-7M Luses-permission android:name67android.permission.I%&$?%$&7 /M Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7 /M Luses-sdk android:min2dkVersion67<7 android:target2dkVersion67117 /M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7 android:hardEareAccelerated67true7M LactivitF android:name67.$3<5ou7 android:label67Ostring/app name7M Lintent-filterM

-2%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

ntroducing the 3oneycomb >

Laction android:name67android.intent.action.#AI%7 /M LcategorF android:name67android.intent.categorF.)A3%+!$?7 /M L/intent-filterM L/activitFM L/applicationM L/manifestM

5he resulting appli'ation =orks &ine on ol"er "e!i'es, but =ith no other 'hanges, =e get this on a Motorola F>>M,

"igure *&&1 The =>%.ou sample application@ lightly updated for Android -1<

0& you =ant to take a"!antage o& some o& the ne=er &eatures "es'ribe" in this set o& +oney'omb 'hapters, you =ill also nee" to think about ba'k=ar"s 'ompatibility, to make sure that =hat you "o =ill =ork su''ess&ully on both ne=er an" ol"er !ersions o& An"roi". 5his topi' is also 'o!ere" later in this book. 0& you ha!e resour'es, su'h as styles, that nee" to be !ersion-spe'i&i', you 'an use the -v11 resour'e set su&&i;. *or e;ample, you 'oul" ha!e a res/values/stFles.Gml an" a res/values-v11/stFles.Gml S the latter =oul" be use" on +oney'omb, the &ormer on ol"er !ersions o& An"roi".

-20

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

ntroducing the 3oneycomb >

1ut &irst, =e nee" to e;plain =hat all is possible &or you to use to take &ull a"!antage o& the +oney'omb $0, =hi'h is the point o& the ne;t &e= 'hapters.

-22

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &9

>sing the Action Bar

>ne o& the easiest =ays &or an appli'ation to blen" in better =ith the +oney'omb $0 is to make use o& the a'tion bar, "es'ribe" in an earlier 'hapter. What makes it MeasyM is that most o& the basi' &un'tionality is ba'k=ar"s-'ompatible S your +oney'omb settings =ill not 'ause the appli'ation to 'rash on earlier !ersions o& An"roi". 5he sample proGe't sho=n in this 'hapter is #enus/Action4ar, =hi'h e;ten"s the #enus/Inflation proGe't sho=n in a pre!ious 'hapter.

=nabling the Action Bar


1y "e&ault, your An"roi" appli'ation =ill not utiliKe the a'tion bar. 0n &a't, it =ill not e!en be "isplaye" on the s'reen. 0& you =ant the a'tion bar to be there, you =ill nee" to in'lu"e android:target2dkVersion67117 in your Luses-sdkM element in the mani&est, su'h as the mani&est &or the MenusPA'tion1ar proGe't,
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.inflation7M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7 android:hardEareAccelerated67true7M LactivitF android:name67.Inflation=emo7 android:label67Ostring/app name7M Lintent-filterM

-27
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

>sing the Action Bar

Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM Luses-sdk android:min2dkVersion67<7 android:target2dkVersion67117 /M Lsupports-screens android:Glarge2creens67true7 android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

5his =ill 'ause your options menu to appear in the upper-right 'orner o& the s'reen, un"er a menu i'on in the a'tion bar, as sho=n in an earlier 'hapter. Also, your a'ti!ity7s i'on =ill appear in the upper-le&t 'orner, =ith your a'ti!ity7s name (&rom the android:label attribute in the mani&est) alongsi"e o& it. While this gi!es you the basi' +oney'omb look an" &eel S in'lu"ing the +oney'omb-theme" =i"gets, su'h as the ne= 2pinner =ith the southeastpointing arro=hea" S you ha!e not really 'hange" the user e;perien'e all that mu'h.

Promoting +enu tems to the Action Bar


5he ne;t step &or integrating =ith the a'tion bar is to promote 'ertain options menu items &rom being part o& the options menu to being al=ays !isible on the a'tion bar itsel&. 5his makes them easier to "is'o!er an" sa!es the user a 'li'k =hen the time 'omes to use them. in your menu FML resour'e, you 'an a"" the attribute to an LitemM element. A !alue o& if?oom means that the menu item =ill appear in the a'tion bar i& there is spa'e &or it, =hile a !alue o& alEaFs means that the menu item shoul" al=ays be put in the a'tion bar. All else being eRual, if?oom is the better 'hoi'e, as it =ill a"apt better to smaller s'reens, on'e the +oney'omb $0 mo!es onto phones. ?ou 'an also 'ombine this =ith the Eith&eGt !alue (e.g., if?oomW Eith&eGt) S i& you in'lu"e Eith&eGt, the title o& the menu item =ill appear
android:shoEAsAction

5o

"o

this,

-28

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing the Action Bar

a"Ga'ent to the item7s i'on, instea" o& only the i'on being put in the a'tion bar. *or e;ample, the #enus/Action4ar proGe't7s options.Gml menu resour'e has android:shoEAsAction on the &irst t=o menu items,
LNGml version671.-7 encoding67utf-,7NM Lmenu Gmlns:android67http://schemas.android.com/apk/res/android7M Litem android:id67ORid/add7 android:title67Add7 android:icon67OdraEable/ic menu add7 android:action)aFout67OlaFout/add7 android:shoEAsAction67if?oom7/M Litem android:id67ORid/reset7 android:title67?eset7 android:icon67OdraEable/ic menu refresh7 android:shoEAsAction67if?oomWEith&eGt7/M Litem android:id67ORid/about7 android:title67About7 android:icon67OdraEable/ic menu info details7 /M L/menuM

5he se'on" menu item S &or resetting the 'ontents o& our list S is a normal M=ith te;tM a'tion bar button. 5he &irst menu item "oes something a bit "i&&erent, =hi'h =e =ill e;amine later in this 'hapter. 5he &a't that the thir" menu item "oes not ha!e android:shoEAsAction means that it =ill remain in the menu, e!en i& there is room in the a'tion bar itsel&. 2ote that the Ca!a 'o"e "oes not 'hange S on+reate"ptions#enuPQ an" on"ptionsItem2electedPQ &or our Inflation=emo a'ti!ity "o not nee" to be a"Guste" be'ause menu items are promote" into the a'tion bar !ia the menu FML resour'e alone.

Cesponding to the !ogo


5he a'ti!ity i'on in the upper-le&t 'orner o& the s'reen is 'li'kable. 0& the user 'li'ks it, it triggers on"ptionsItem2electedPQ...but not &or one o& your options items you may ha!e "e&ine" yoursel&. ather, the Mmagi' !alueM o& android.?.id.home is use". 0n the #enus/Action4ar proGe't, =e =ire it to the same 'o"e that is in!oke" i& the user 'hooses the MAboutM options menu item S "isplaying a &oast,
-2:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing the Action Bar

O"verride public boolean onOptionsItemSelectedP#enuItem itemQ : sEitch Pitem.getItemIdPQQ : case ?.id.add: addPQJ returnPtrueQJ case ?.id.reset: init$dapterPQJ returnPtrueQJ case ?.id.about: case android.?.id.home: &oast .makeTextPthis8 7Action 4ar 2ample App78 &oast.)$%D&! )"%DQ .showPQJ returnPtrueQJ ; ; returnPsuper.onOptionsItemSelectedPitemQQJ

0n a proGe't =ith multiple a'ti!ities, though, the e;pe'tation is that 'li'king the logo =ill take you to the MhomeM a'ti!ity &or the appli'ation, =hate!er that might mean.

Adding Custom ;ie)s to the Action Bar


?ou 'an "o more =ith the a'tion bar, though, than simply 'on!erting options menu items into =hat amount to toolbar buttons. ?ou 'an a"" your o=n 'ustom $0 to the a'tion bar. 0n the 'ase o& #enus/Action4ar, =e are repla'ing the MA""M menu 'hoi'e an" resulting "ialog =ith an MA""M &iel" right in the a'tion bar itsel&. 5his, ho=e!er, gets a little bit tri'ky to implement.

De.inin! the ) yout


5o put something 'ustom in the a'tion bar, =e nee" to "e&ine =hat the Msomething 'ustomM is, in the &orm o& a layout FML &ile. *ortunately, =e alrea"y ha!e a layout FML &ile &or a""ing a =or" to the list S it is the one
-7<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing the Action Bar

that the #enus/Inflation sample =rappe" in a 'ustom Alert=ialog &or =hen the MA""M options menu item =as 'li'ke". 5hat original layout looke" like this,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67horiKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 M L&eGtVieE android:teGt67@ord:7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 /M L$dit&eGt android:id67ORid/title7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:laFout margin)eft67<dip7 /M L/)inear)aFoutM

We nee" to make some minor a"Gustments to this layout to use it &or the a'tion bar,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67horiKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 M L&eGtVieE android:teGt67@ord:7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGtAppearance67Oandroid:stFle/&eGtAppearance.#edium7 /M L$dit&eGt android:id67ORid/title7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:laFout margin)eft67<dip7 android:Eidth6710-sp7 android:input&Fpe67teGt7 android:imeActionId671CC/7 android:ime"ptions67action=one7 /M L/)inear)aFoutM

-7*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing the Action Bar

%pe'i&i'ally,

We a"" an android:teGtAppearance attribute to the &eGtVieE representing our MA"",M 'aption. 5he android:teGtAppearance attribute allo=s us to "e&ine the &ont type, siKe, 'olor, an" =eight (e.g., bol") in one shot. We spe'i&i'ally use a Mmagi' !alueM o& Oandroid:stFle/&eGtAppearance.#edium, so the 'aption mat'hes the styling o& the M esetM label on our other menu item =e promote" to the a'tion bar. We spe'i&y android:Eidth6710-sp7 &or the $dit&eGt =i"get, be'ause android:laFout Eidth67fill parent7 is ignore" in the a'tion bar S other=ise, =e =oul" take up the =hole rest o& the bar. We spe'i&y android:input&Fpe67teGt7 on the $dit&eGt =i"get, =hi'h, among other things, =ill restri't us to a single line o& te;t. We also spe'i&y android:imeActionId an" android:ime"ptions on the =i"get to 'ontrol the Ma'tion buttonM o& the so&t keyboar", so =e get 'ontrol =hen the user presses NEnterO on the so&t keyboar".
$dit&eGt

Puttin! the ) yout in the B%enuB


2e;t, =e nee" to tea'h An"roi" to use this layout &or our MA""M options menu item i& =e are running on +oney'omb. 5o "o this, =e use the android:action)aFout attribute on our LitemM element, re&eren'ing our layout resour'e (OlaFout/add), as =as sho=n earlier in this 'hapter. 5his attribute =ill be ignore" on earlier !ersions o& An"roi", so it is sa&e to use. 0& =e "i" nothing else, =e =oul" get the "esire" $0,

-7&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing the Action Bar

"igure *&-1 The +enusKActionBar sample application

+o=e!er, =hile the user 'oul" type something in, =e ha!e no =ay to &in" out =hat they type in, =hen they are "one, et'.

Gettin! Control o. -ser Input


8i!en our so&t keyboar" settings =e put on the $dit&eGt =i"get, =e 'an arrange to &in" out =hen the user presses the NEnterO key either on the so&t keyboar" or on a har"=are keyboar". 5o "o that, though, =e nee" to get our han"s on the $dit&eGt =i"get itsel&. ?ou might think it is a""e" =hen the $0 is in&late" in on+reatePQ...but you =oul" be mistaken. 0n a +oney'omb en!ironment, =ith an a'tion bar, on+reate"ptions#enuPQ is 'alle" a&ter on+reatePQ as part o& setting up the $0. >n 'lassi' !ersions o& An"roi", on+reate"ptions#enuPQ =oul" not be 'alle" until the user presse" the ME2$ button. 1ut, sin'e some o& the options menu might be promote" into the a'tion bar, An"roi" 'alls on+reate"ptions#enuPQ automati'ally no=. 5he $dit&eGt =ill e;ist a&ter =e in&late our options.Gml menu resour'e. +o=e!er, the best =ay to get the $dit&eGt is not to use findVieE4FIdPQ on the a'ti!ity. ather, =e shoul" 'all getActionVieEPQ on the #enuItem
-7-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing the Action Bar

asso'iate" =ith our MA""M option. 5his =ill return the root o& the !ie= hierar'hy in&late" &rom the layout resour'e =e "e&ine" in the android:action)aFout attribute in the menu resour'e. 0n this 'ase, that is the )inear)aFout &rom res/laFout/add.Gml, so =e nee" to 'all findVieE4FIdPQ on it to get the $dit&eGt,
O"verride public boolean onCreateOptionsMenuP#enu menuQ : neE MenuInflaterPthisQ.inflateP?.menu.option8 menuQJ $dit&eGt add6P$dit&eGtQmenu .findItemP?.id.addQ .get$ctionViewPQ .findViewByIdP?.id.titleQJ add.setOn+ditor$ctionListenerPon2earchQJ ; returnPsuper.onCreateOptionsMenuPmenuQQJ

5hen, =e 'an 'all set"n$ditorAction)istenerPQ on the $dit&eGt, to register an "n$ditorAction)istener obGe't that =ill get 'ontrol =hen the user 'li'ks NEnterO on the har" or so&t keyboar",
private &eGtVieE."n$ditorAction)istener on2earch6 neE &eGtVieE.On+ditor$ctionListenerPQ : public boolean on+ditor$ctionP&eGtVieE v8 int actionId8 HeF$vent eventQ : if Pevent66null WW event.get$ctionPQ66HeF$vent.A+&I"% 3(Q : add#ordPvQJ Input#ethod#anager imm6PInput#ethod#anagerQgetSystemSer!icePI%(3& #$&!"= 2$?VI+$QJ imm.hideSoftInput"rom#indowPv.get#indowTokenPQ8 -QJ ; ; ;J returnPtrueQJ

5hat in turn 'alls an add@ordPQ metho", supplying the $dit&eGt, =hi'h a""s the =or" to the list !ia the ArraFAdapter,
private void add#ordP&eGtVieE titleQ : ArraFAdapterL2tringM adapter6PArraFAdapterL2tringMQgetList$dapterPQJ

-7%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing the Action Bar

adapter.addPtitle.getTextPQ.toStringPQQJ ;

5hat same add@ordPQ metho" 'an also be use" &rom the addPQ metho" that "isplays the Alert=ialog...e!en though that =ill not be use" on a +oney'omb tablet, sin'e the MA""M menu 'hoi'e no longer e;ists as a menu 'hoi'e,
private void addPQ : final VieE addVieE6getLayoutInflaterPQ.inflateP?.laFout.add8 nullQJ neE Alert=ialog.BuilderPthisQ .setTitleP7Add a @ord7Q .setViewPaddVieEQ .set)ositi!eButtonP7"H78 neE =ialogInterface.OnClickListenerPQ : public void onClickP=ialogInterface dialog8 int Ehich4uttonQ : add#ordPP&eGtVieEQaddVieE.findViewByIdP?.id.titleQQJ ; ;Q .set&egati!eButtonP7+ancel78 nullQ .showPQJ ;

5he net result is that =hen the user types in something in the MA"",M &iel" an" presses NEnterO, the =or" is a""e" to the bottom o& the list. 5his sa!es some 'li'ks o!er the phone $0, as the user "oes not ha!e to open the options menu, "oes not ha!e to 'li'k on the options menu item, an" "oes not ha!e to 'li'k a button on the "ialog. 2ote that our "n$ditorAction)istener "oes one more thing than simply a"" the =or" to the list, it hi"es the so&t keyboar". 0t "oes this using the Input#ethod#anager, as =as seen in a pre!ious 'hapter.

/onGt "orget the Phones!


With the e;'eption o& the 'ustom !ie= &eature "es'ribe" in the pre'e"ing se'tion, e!erything sho=n in this 'hapter regar"ing the a'tion bar is automati'ally ba'k=ar"s-'ompatible. 5he 'o"e an" resour'es that =ork on +oney'omb-&la!ore" !ersions o& An"roi" =ill =ork on 'lassi' !ersions o& An"roi" unmo"i&ie".
-70

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing the Action Bar

0&, ho=e!er, you =ant to use the 'ustom !ie= &eature, you ha!e a problem S the getActionVieEPQ metho" is ne= to A#0 Le!el 11 an" =ill be una!ailable on ol"er !ersions o& An"roi". 5his means you =ill nee" to 'ompile &or A#0 Le!el 11 (e.g., set your E'lipse target or Ant default.properties to re&eren'e android-11), an" you =ill nee" to take steps to a!oi" 'alling getActionVieEPQ on ol"er "e!i'es. We =ill e;plore ho= to pull o&& this &eat in a later 'hapter.

-72

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &:

"ragments

#erhaps the largest 'hange in An"roi" ..0 &a'ing An"roi" "e!elopers is the intro"u'tion o& the &ragment system. 5his is an optional layer you 'an put bet=een your a'ti!ities an" your =i"gets, "esigne" to help you re'on&igure your a'ti!ities to support s'reens both large (e.g., tablets) an" small (e.g., phones). +o=e!er, they also a"" an e;tra layer o& 'omple;ity, one that =ill take the An"roi" "e!eloper 'ommunity some time to a"Gust to. +en'e, you =ill &in" &e=er blog posts or sample apps using &ragments, Gust be'ause they =ere intro"u'e" so long a&ter An"roi" itsel& =as. 5his 'hapter =ill 'o!er basi' uses o& &ragments, in'lu"ing supporting &ragments on pre-An"roi" ..0 "e!i'es.

ntroducing "ragments
*ragments are not =i"gets, like 4utton or $dit&eGt. *ragments are not 'ontainers, like )inear)aFout or ?elative)aFout. *ragments are not a'ti!ities. ather, &ragments aggregate =i"gets an" 'ontainers. *ragments then 'an be pla'e" into a'ti!ities S sometimes se!eral &ragments &or one a'ti!ity, sometimes one &ragment per a'ti!ity.

-77
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

An" the reason &or this is the !ariation in An"roi" s'reen siKes.

The Pro=lem
A tablet has a larger s'reen than "oes a phone. A 5- has a larger s'reen than "oes a tablet. 0t =oul" seem to make sense to try to take a"!antage o& that e;tra s'reen spa'e, mu'h as =e outline" in the 'hapter on han"ling multiple s'reen siKes. 5here, =e pro&ile" an $3<5ou sample appli'ation, e!entually =in"ing up =ith an a'ti!ity that =oul" loa" in a "i&&erent layout &or larger-siKe" s'reens, one that ha" an embe""e" @ebVieE =i"get. 5he a'ti!ity =oul" "ete't that =i"get7s e;isten'e an" use it &or loa"ing Web 'ontent relate" to a sele'te" 'ountry, rather than laun'hing a separate bro=ser a'ti!ity or some a'ti!ity only 'ontaining a @ebVieE. +o=e!er, this =as a &airly tri!ial s'enario. 0magine i&, instea" o& a @ebVieE, =e ha" a &able)aFout 'ontaining 28 =i"gets. >n larger-siKe" s'reens, =e =ant the &able)aFout in the same a'ti!ity as an a"Ga'ent )istVieET on smaller s'reens, =e =ant the &able)aFout to be in a separate a'ti!ity, sin'e there =oul" not be enough room other=ise. 5o "o this using pre+oney'omb te'hnology, =e =oul" either nee" to "upli'ate all o& the &able)aFout-han"ling logi' in both a'ti!ities, or 'reate an a'ti!ity base 'lass an" hope they 'an both inherit &rom it, or turn the &able)aFout an" its 'ontents into a 'ustom VieEDroup, or something. An" that =oul" Gust be &or one su'h s'enario S multiply that by many a'ti!ities in a larger appli'ation, an" the 'omple;ity mounts.

The 5r !ments Solution


*ragments re"u'e, but "o not eliminate, that 'omple;ity. With &ragments, ea'h "is'rete 'hunk o& user inter&a'e that 'oul" be in multiple a'ti!ities (base" on s'reen siKe) goes in a &ragment. 5he a'ti!ities in Ruestion "etermine, base" on s'reen siKe, =ho gets the &ragment.

-78

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

0n the 'ase o& $3<5ou, =e =ill ha!e t=o &ragments. >ne &ragment represents the list o& 'ountries. 5he other &ragment represents the "etails &or that 'ountry (in our 'ase, a @ebVieE). >n a larger-s'reen "e!i'e, =e =ill =ant both &ragments to be in one a'ti!ity, =hile a smaller-s'reen "e!i'e =ill house those &ragments in separate a'ti!ities. 5his gi!es us the same bene&its as =e got =ith the last !ersion o& $3<5ou, =ith users getting more in&ormation in &e=er 'li'ks =hen they ha!e larger s'reens. ?et the te'hniRues =e "emonstrate =ith &ragments =ill be more s'alable, able to han"le more 'omple; $0 patterns than the simple @ebVieE-or-not 'ase o& $3<5ou. 0n this 'ase, our entire $0 =ill be insi"e o& &ragments. 5hat is not ne'essary. *ragments are an Mopt-inM te'hnology S you only nee" them &or the parts o& your $0 that 'oul" appear in "i&&erent a'ti!ities in "i&&erent s'enarios. 0n &a't, your a'ti!ities that "o not 'hange at all (say, a help s'reen) might not use &ragments =hatsoe!er. *ragments also gi!e us a &e= other bells an" =histles, in'lu"ing,

5he ability to "ynami'ally a"" &ragments, base" on user intera'tion. *or e;ample, the 8mail appli'ation initially sho=s a )ist9ragment o& the user7s mail &ol"ers. 5apping a &ol"er a""s a se'on" )ist9ragment to the s'reen, sho=ing the 'on!ersations in that &ol"er. 5apping a 'on!ersation a""s a thir" 9ragment to the s'reen, sho=ing the messages in that 'on!ersation. 5he ability to animate these "ynami' &ragments as they 'ome on an" o&& the s'reen. *or e;ample, =hen the user taps a 'on!ersation in 8mail, the &ol"er )ist9ragment sli"es o&& the s'reen to the le&t, the 'on!ersations )ist9ragment sli"es le&t an" shrinks to take up less room, an" the messages 9ragment sli"es in &rom the right. Automati' 1ACD button management &or "ynami' &ragments. *or e;ample, =hen the user presses 1ACD =hen !ie=ing the messages 9ragment, that 9ragment sli"es o&& to the right, the 'on!ersations )ist9ragment sli"es right an" e;pan"s to &ill more o& the s'reen, an" the &ol"ers )ist9ragment sli"es ba'k in &rom the le&t. 2one o& that has to be manage" by "e!elopers S simply "es'ribing a""ing the "ynami' &ragment !ia a 9ragment&ransaction allo=s An"roi" to
-7:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

automati'ally han"le the 1ACD button, in'lu"ing re!ersing all animations.

A &ragment 'an a"" options to the options menu, an" there&ore to the a'tion bar. Call set!as"ptions#enuPQ in on+reatePQ o& your &ragment to register an interest in this, then o!erri"e on+reate"ptions#enuPQ an" on"ptionsItem2electedPQ in the &ragment the same =ay you might in an a'ti!ity. A &ragment 'an also register =i"gets to ha!e 'onte;t menus, an" han"le those 'onte;t menus, the same =ay as an a'ti!ity =oul". 5he a'tion bar 'an ha!e tabs S repla'ing a &ab!ost S =here ea'h tab7s 'ontents is a &ragment. %imilarly, the a'tion bar 'an ha!e a Mna!igation mo"eM =ith a 2pinner to s=it'h bet=een mo"es, =here ea'h mo"e is represente" by a &ragment.

The Android Comp ti=ility )i=r ry


0& &ragments =ere only a!ailable &or An"roi" ..0 an" higher, =e =oul" be right ba'k =here =e starte", as not all An"roi" "e!i'es to"ay run An"roi" ..0 an" higher. +o=e!er, 8oogle has release" the An"roi" Compatibility Library (ACL). 5his is a!ailable !ia the %@D an" A-@ Manager, =here you install the other %@D support &iles, 'reate an" start your emulator A-@s, et'. 5his library gi!es you a''ess to the &ragment system on !ersions o& An"roi" going ba'k to An"roi" 1./. %in'e the !ast maGority o& An"roi" "e!i'es are running 1./ or ne=er, this allo=s you to start using &ragments =hile maintaining ba'k=ar"s 'ompatibility. >!er time, this library may a"" other &eatures to help =ith ba'k=ar"s 'ompatibility, &or appli'ations that =ish to use it. 5he material in this 'hapter &o'uses on using the ACL =hen employing &ragments. 8enerally speaking, using the ACL &or &ragments is almost i"enti'al to using the nati!e An"roi" ..0 &ragments 'lasses "ire'tly.

-8<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

%in'e the ACL only supports ba'k to An"roi" 1./, An"roi" 1.A "e!i'es =ill not be able to use &ragment-base" appli'ations. 5his is a !ery small per'entage o& the An"roi" "e!i'e spe'trum at this time S ..0L as o& the time o& this =riting.

Creating "ragment Classes


5he &irst step to=ar"s setting up a &ragment-base" appli'ation is to 'reate &ragment 'lasses &or ea'h o& your &ragments. Cust as you inherit &rom ActivitF (or a sub'lass) &or your a'ti!ities, you inherit &rom 9ragment (or a sub'lass) &or your &ragments. +ere, =e =ill e;amine the 9ragments/$3<5ou 0 sample proGe't an" the &ragments that it "e&ines. 5he 'on!ention o& this book =ill be to use M&ragmentM as a generi' noun an" 9ragment to re&er to the a'tual 9ragment 'lass.

Gener l 5r !ments
1esi"es inheriting &rom 9ragment, the only thing reRuire" o& a &ragment is to o!erri"e on+reateVieEPQ. 5his =ill be 'alle" as part o& putting the &ragment on the s'reen. ?ou nee" to return a VieE that represents the bo"y o& the &ragment. Most likely, you =ill 'reate your &ragment7s $0 !ia an FML layout &ile, an" on+reateVieEPQ =ill in&late that &ragment layout &ile. *or e;ample, here is =etails9ragment &rom $3<5ou 0, =hi'h =ill =rap aroun" our @ebVieE to sho= the Web 'ontent &or a gi!en 'ountry,
import import import import import import android.support.v<.app.9ragmentJ android.os.4undleJ android.vieE.)aFoutInflaterJ android.vieE.VieEJ android.vieE.VieEDroupJ android.Eebkit.@ebVieEJ

public class =etails9ragment eGtends 9ragment : O"verride public VieE onCreateViewP)aFoutInflater inflater8 VieEDroup container8 4undle savedInstance2tateQ :

-8*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

returnPinflater.inflateP?.laFout.details fragment8 container8 falseQQJ ; public void load*rlP2tring urlQ : PP@ebVieEQPgetViewPQ.findViewByIdP?.id.broEserQQQ.load*rlPurlQJ ;

2ote that =e are inheriting not &rom android.app.9ragment but &rom 5he latter is the 9ragment implementation &rom the ACL, an" so this 'an be use" a'ross An"roi" !ersions.
android.support.v<.app.9ragment.

5he on+reateVieEPQ implementation in&lates a layout =hi'h happens to ha!e a @ebVieE in it,
LNGml version671.-7 encoding67utf-,7NM L@ebVieE Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/broEser7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 /M

0t also e;poses a load3rlPQ metho", to be use" by a hosting a'ti!ity to tell the &ragment that it is time to "isplay some Web 'ontent an" supply the $ L &or "oing the same. 5he implementation o& load3rlPQ in =etails9ragment uses getVieEPQ to retrie!e the VieE 'reate" in on+reateVieEPQ, &in"s the @ebVieE in it, an" "elegates the load3rlPQ 'all to the @ebVieE. 5here are a myria" o& other li&e'y'le metho"s a!ailable on 9ragment. 5he more important ones in'lu"e mirrors o& the stan"ar" on+reatePQ, on2tartPQ, on?esumePQ, on(ausePQ, on2topPQ, an" on=estroFPQ o& an a'ti!ity. %in'e the &ragment is the one =ith the =i"gets, the &ragment =ill implement more o& the business logi' that &ormerly might ha!e resi"e" in the a'ti!ity &or these metho"s. *or e;ample, in on(ausePQ or on2topPQ, sin'e the user may not be returning to you, you may =ish to sa!e any unsa!e" e"its to some temporary storage. 0n the 'ase o& =etails9ragment, there =as nothing that really Ruali&ie" here, so those li&e'y'le metho"s =ere le&t alone.

-8&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

)ist5r !ment
>ne *ragment sub'lass that is sure to be popular is )ist9ragment. 5his =raps a )istVieE in a 9ragment, "esigne" to simpli&y setting up lists o& things S 'ountries, mail &ol"ers, mail 'on!ersations, et'. %imilar to a )istActivitF, all you nee" to "o is 'all set)istAdapterPQ =ith your 'hosen an" 'on&igure" )istAdapter, plus o!erri"e on)istItem+lickPQ to respon" to =hen the user 'li'ks on a ro= in the list. 0n $3<5ou 0, =e ha!e a +ountries9ragment that represents the list o& a!ailable 'ountries. 0t initialiKes the )istAdapter in onActivitF+reatedPQ, =hi'h is 'alle" a&ter on+reatePQ has =rappe" up in the a'ti!ity that hol"s the &ragment,
O"verride public void on$cti!ityCreatedP4undle stateQ : super.onCreatePstateQJ setList$dapterPneE Country$dapterPQQJ if PstateX6nullQ : int position6state.getIntP2&A&$ +!$+H$=8 -1QJ if PpositionM-1Q : getListViewPQ.setItemCheckedPposition8 trueQJ ; ; ;

5he 'o"e "ealing =ith the 4undle supplie" to on+reatePQ =ill be e;plaine" a bit later in this 'hapter. 5he +ountrFAdapter is nearly i"enti'al to the one &rom past $3<5ou samples, e;'ept that there is no get)aFoutInflaterPQ metho" on a 9ragment, so =e ha!e to use the stati' fromPQ metho" on )aFoutInflater an" supply our a'ti!ity !ia getActivitFPQ,
class +ountrFAdapter eGtends ArraFAdapterL+ountrFM : Country$dapterPQ : superPget$cti!ityPQ8 ?.laFout.roE8 ?.id.name8 $3QJ ; O"verride

-8-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

public VieE getViewPint position8 VieE convertVieE8 VieEDroup parentQ : +ountrF@rapper Erapper6nullJ if PconvertVieE66nullQ : convertVieE6)aFoutInflater .fromPget$cti!ityPQQ .inflateP?.laFout.roE8 nullQJ Erapper6neE Country#rapperPconvertVieEQJ convertVieE.setTagPErapperQJ ; else : Erapper6P+ountrF@rapperQconvertVieE.getTagPQJ ; Erapper.populate"romPgetItemPpositionQQJ ; ; returnPconvertVieEQJ

%imilarly, the +ountrF@rapper is no "i&&erent than be&ore,


static class +ountrF@rapper : private &eGtVieE name6nullJ private ImageVieE flag6nullJ private VieE roE6nullJ Country#rapperPVieE roEQ : this.roE6roEJ name6P&eGtVieEQroE.findViewByIdP?.id.nameQJ flag6PImageVieEQroE.findViewByIdP?.id.flagQJ ; &eGtVieE get&amePQ : returnPnameQJ ; ImageVieE get"lagPQ : returnPflagQJ ; void populate"romP+ountrF nationQ : get&amePQ.setTextPnation.nameQJ get"lagPQ.setImage%esourcePnation.flagQJ ;

As are the list o& 'ountries,

-8%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

static : $3.addPneE CountryP?.string.austria8 ?.draEable.austria8 ?.string.austria urlQQJ $3.addPneE CountryP?.string.belgium8 ?.draEable.belgium8 ?.string.belgium urlQQJ $3.addPneE CountryP?.string.bulgaria8 ?.draEable.bulgaria8 ?.string.bulgaria urlQQJ $3.addPneE CountryP?.string.cFprus8 ?.draEable.cFprus8 ?.string.cFprus urlQQJ $3.addPneE CountryP?.string.cKech republic8 ?.draEable.cKech republic8 ?.string.cKech republic urlQQJ $3.addPneE CountryP?.string.denmark8 ?.draEable.denmark8 ?.string.denmark urlQQJ $3.addPneE CountryP?.string.estonia8 ?.draEable.estonia8 ?.string.estonia urlQQJ $3.addPneE CountryP?.string.finland8 ?.draEable.finland8 ?.string.finland urlQQJ $3.addPneE CountryP?.string.france8 ?.draEable.france8 ?.string.france urlQQJ $3.addPneE CountryP?.string.germanF8 ?.draEable.germanF8 ?.string.germanF urlQQJ $3.addPneE CountryP?.string.greece8 ?.draEable.greece8 ?.string.greece urlQQJ $3.addPneE CountryP?.string.hungarF8 ?.draEable.hungarF8 ?.string.hungarF urlQQJ $3.addPneE CountryP?.string.ireland8 ?.draEable.ireland8 ?.string.ireland urlQQJ $3.addPneE CountryP?.string.italF8 ?.draEable.italF8 ?.string.italF urlQQJ $3.addPneE CountryP?.string.latvia8 ?.draEable.latvia8 ?.string.latvia urlQQJ $3.addPneE CountryP?.string.lithuania8 ?.draEable.lithuania8 ?.string.lithuania urlQQJ $3.addPneE CountryP?.string.luGembourg8 ?.draEable.luGembourg8 ?.string.luGembourg urlQQJ $3.addPneE CountryP?.string.malta8 ?.draEable.malta8 ?.string.malta urlQQJ $3.addPneE CountryP?.string.netherlands8 ?.draEable.netherlands8 ?.string.netherlands urlQQJ $3.addPneE CountryP?.string.poland8 ?.draEable.poland8 ?.string.poland urlQQJ $3.addPneE CountryP?.string.portugal8 ?.draEable.portugal8 ?.string.portugal urlQQJ $3.addPneE CountryP?.string.romania8 ?.draEable.romania8 ?.string.romania urlQQJ $3.addPneE CountryP?.string.slovakia8 ?.draEable.slovakia8 ?.string.slovakia urlQQJ $3.addPneE CountryP?.string.slovenia8 ?.draEable.slovenia8 ?.string.slovenia urlQQJ $3.addPneE CountryP?.string.spain8 ?.draEable.spain8 ?.string.spain urlQQJ $3.addPneE CountryP?.string.sEeden8 ?.draEable.sEeden8 ?.string.sEeden urlQQJ

-80

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

$3.addPneE CountryP?.string.united kingdom8 ?.draEable.united kingdom8 ?.string.united kingdom urlQQJ ;

...an" the "e&inition o& a +ountrF, &rom a separate publi' 'lass,


public class +ountrF : int nameJ int flagJ int urlJ CountryPint name8 int flag8 int urlQ : this.name6nameJ this.flag6flagJ this.url6urlJ ; ;

Persistent Hi!hli!ht
>ne thing leaps out at you =hen you use &ragment-base" appli'ations like 8mail. When you tap on a ro= in a list, an" another &ragment is sho=n (or up"ate") =ithin the same a'ti!ity, the ro= you tappe" remains highlighte". 5his runs 'ounter to the tra"itional use o& a )istVieE, =here the list sele'tor is only present =hen using a @-pa", tra'kball, or similar pointing "e!i'e. 5he purpose is to sho= the user the 'onte;t o& the a"Ga'ent &ragment. 5he a'tual implementation "i&&ers &rom =hat you might e;pe't. 5hese )istVieE =i"gets are a'tually implementing +!"I+$ #"=$ 2I%D)$, =hat normally =oul" be ren"ere" using a ?adio4utton along the right si"e o& the ro=s. 0n a )ist9ragment, though, the typi'al styling &or a single-'hoi'e )ist9ragment is !ia an Ma'ti!ate"M ba'kgroun". 0n $3<5ou 0, this is han"le" !ia the ro= layout ( res/laFout/roE.Gml) use" by our +ountrFAdapter,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7

-82

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

android:padding67>dip7 android:min!eight67Nandroid:attr/list(referredItem!eight7 stFle67OstFle/activated7 M LImageVieE android:id67ORid/flag7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:laFout gravitF67center verticalWleft7 android:padding?ight67<dip7 /M L&eGtVieE android:id67ORid/name7 android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:laFout gravitF67center verticalWright7 android:teGt2iKe67.mm7 /M L/)inear)aFoutM

?ou =ill noti'e the stFle attribute, pointing to an activated style. 5hat is "e&ine" by $3<5ou 0 as a lo'al style, !ersus one pro!i"e" by the operating system. 0n &a't, it has to ha!e t=o implementations o& the style, be'ause the Ma'ti!ate"M 'on'ept is ne= to An"roi" ..0 an" 'annot be use" in pre!ious !ersions o& An"roi". %o, $3<5ou 0 has res/values/stFles.Gml =ith a ba'k=ar"s-'ompatible empty style,
LNGml version671.-7 encoding67utf-,7NM LresourcesM LstFle name67activated7M L/stFleM L/resourcesM

0t also has res/values-v11/stFles.Gml. 5he -v11 resour'e set su&&i; means that this =ill only be use" on A#0 Le!el 11 (An"roi" ..0) an" higher. +ere, the style inherits &rom the stan"ar" An"roi" Mholographi'M theme an" uses the stan"ar" a'ti!ate" ba'kgroun" 'olor,
LNGml version671.-7 encoding67utf-,7NM LresourcesM LstFle name67activated7 parent67android:&heme.!olo7M Litem name67android:background7MN android:attr/activated4ackgroundIndicatorL/itemM L/stFleM L/resourcesM

-87

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

0n +ountries9ragment, the a'ti!ity =ill let us kno= i& +ountries9ragment appears alongsi"e =etails9ragment S there&ore nee"ing single-'hoi'e mo"e S !ia a enable(ersistent2electionPQ metho",
public void ena'le)ersistentSelectionPQ : getListViewPQ.setChoiceModeP)istVieE.+!"I+$ #"=$ 2I%D)$QJ ;

Also, in on)istItem+lickPQ, +ountries9ragment M'he'ksM the ro= the user 'li'ke" upon, thereby enabling the persistent highlight,
O"verride public void onListItemClickP)istVieE l8 VieE v8 int position8 long idQ : l.setItemCheckedPposition8 trueQJ if PlistenerX6nullQ : listener.onCountrySelectedP$3.getPpositionQQJ ; ;

(the listener obGe't an" 'all to on+ountrF2electedPQ =ill be e;plaine" later in this 'hapter)

+ther 5r !ment B se Cl sses


5he ACL has one other sub'lass o& 9ragment, =ialog9ragment. 5his is use" to help 'oor"inate bet=een a mo"al @ialog an" a &ragment-base" $0. An"roi" ..0 itsel& has t=o more sub'lasses o& 9ragment, ones not a!ailable in the ACL as o& the time o& this =riting,
(reference9ragment, &or (referenceActivitF S this @ebVieE9ragment, @ebVieE

use in the ne= +oney'omb-style is 'o!ere" in a later 'hapter

=hi'h is merely a 9ragment =rappe" aroun" a

-88

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

"ragments@ !ayouts@ Activities@ and +ultiple Screen SiBes


+a!ing some &ragment 'lasses an" their a''ompanying layouts is all =ell an" goo", but some=here along the line, =e nee" to hook them up to a'ti!ities an" get them on the s'reen. Along the =ay, =e =ill ha!e to think about "ealing =ith multiple s'reen siKes, mu'h like =e =ent =ith the @ebVieE-or-bro=ser approa'h =ith the pre!ious !ersion o& the $3<5ou sample. 0n An"roi" ..0 an" higher, any a'ti!ity 'an host a &ragment. +o=e!er, &or the ACL, you nee" to inherit &rom 9ragmentActivitF to use &ragments. 5his limitation o& the ACL "e&initely 'auses 'hallenges, parti'ularly i& you =ere aiming to put a map in a &ragment, a topi' =e =ill "is'uss later in this book. >ther a'ti!ity base 'lasses =ill pose less o& an issue S )istActivitF =oul" be repla'e" by )ist9ragment, &or e;ample. *ragments are a""e" in t=o =ays to an a'ti!ity, 1. ?ou 'an "e&ine them !ia LfragmentM elements in the a'ti!ity7s layout. 5hese &ragments are &i;e" an" =ill al=ays e;ist &or the li&etime o& this a'ti!ity instan'e.

2. ?ou 'an a"" them on the &ly !ia 9ragment#anager an" a 9ragment&ransaction. 5his gi!es more &le;ibility, but a""s a "egree o& 'omple;ity. 5his te'hniRue is not 'o!ere" in this book. >ne big limitation o& "ealing =ith multiple s'reen siKes is that the layouts nee" to ha!e the same starting &ragments &or any 'on&iguration 'hange. %o, a small-s'reen !ersion o& an a'ti!ity an" a large-s'reen !ersion o& an a'ti!ity 'an ha!e "i&&erent mi;es o& &ragment, but a portrait layout an" a lan"s'ape layout &or the same s'reen siKe must ha!e the same &ragments "e&ine". >ther=ise, =hen the s'reen is rotate", An"roi" =ill ha!e problems, trying to =ork =ith a &ragment that "oes not e;ist, &or e;ample. We =ill also nee" to =ork out 'ommuni'ations bet=een our &ragments an" our a'ti!ities. 5he a'ti!ities are the ones "e&ining =hat &ragments they hol", so they typi'ally kno= the 'lasses that implement those &ragments an" =ill
-8:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

be able to 'all metho"s on them "ire'tly. 5he &ragments, though, only kno= that they are hoste" by some a'ti!ity, an" that a'ti!ity may "i&&er &rom 'ase to 'ase. +en'e, the typi'al pattern =ill be to use inter&a'es &or &ragment-Oa'ti!ity 'ommuni'ation,

@e&ine an inter&a'e &or the metho"s that the &ragment =ill =ant to 'all on its a'ti!ity (or some other obGe't supplie" by that a'ti!ity) 5he a'ti!ity pro!i"es an implementation o& that inter&a'e !ia some setter metho" on the &ragment =hen the &ragment is 'reate" 5he &ragment uses that inter&a'e implementation as nee"e"

We =ill see all o& this as =e =ork through the $3<5ou 0 a'ti!ities an" their 'orrespon"ing layouts.

E-23ou
0n the earlier !ersions o& the $3<5ou proGe't, =e ha" only one a'ti!ity, also name" $3<5ou. 0n $3<5ou 0, though, =e =ill ha!e t=o a'ti!ities,
$3<5ou

=ill han"le "isplaying the +ountries9ragment in all s'reen siKes, plus the =etails9ragment on larger s'reens
=etailsActivitF =ill

host the =etails9ragment on smaller s'reens

While =e 'oul" probably get a=ay =ith ha!ing $3<5ou laun'h the bro=ser a'ti!ity &or smaller s'reens, rather than ha!e a =etailsActivitF host a @ebVieE-only =etails9ragment, the latter approa'h is more realisti' &or more &ragment-base" appli'ations. With that in min", let7s take a look at the pie'es o& the $3<5ou a'ti!ity.

The ) yout
*or normal-s'reen "e!i'es, =e =ant to Gust "isplay the +ountries9ragment. 5hat is a''omplishe" !ia res/laFout/main.Gml Gust ha!ing the appropriate LfragmentM element,

-:<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

LNGml version671.-7 encoding67utf-,7NM Lfragment Gmlns:android67http://schemas.android.com/apk/res/android7 class67com.commonsEare.android.eu<Fou.+ountries9ragment7 android:id67ORid/countries7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 /M

5he class attribute in"i'ates =hat Ca!a 'lass implements the &ragment. >ther=ise, this layout is unremarkable. 2ote that &ragments "o not get liste" in the mani&est &ile the =ay a'ti!ities "o.

The +ther ) yout


*or large s'reen "e!i'es, in the lan"s'ape mo"e, =e =ant to ha!e both the +ountries9ragment an" the =etails9ragment, si"e-by-si"e. 5hat =ay, users 'an tap on a 'ountry an" !ie= the "etails =ithout &lipping ba'k an" &orth bet=een a'ti!ities. 1esi"es, =e 'an take better a"!antage o& the s'reen spa'e. +o=e!er, there is a 'at'h. 0& =e =ant to pre-"e&ine those t=o &ragments in our layout &ile, =e ha!e to use those same pair o& &ragments &or both lan"s'ape an" portrait. 5his is "espite the &a't that =e "o not =ant to use the =etails9ragment in $3<5ou in portrait mo"e (ha!ing a list !erti'ally sta'ke" o!er the @ebVieE =oul" be o""-looking at best). +ere, =e =ill Gust use the same layout &ile &or both orientations an" make a"Gustments in our Ca!a 'o"e. Another approa'h to the problem =oul" be to ha!e the layout &ile only ha!e +ountries9ragment an" to use 9ragment#anager an" a 9ragment&ransaction to a"" in the =etails9ragment. +ere, though, =e =ill use other tri'ks. +en'e, in res/laFout-large/ (not res/laFout-large-land/), =e ha!e this layout,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7

-:*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

android:orientation67horiKontal7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7M Lfragment class67com.commonsEare.android.eu<Fou.+ountries9ragment7 android:id67ORid/countries7 android:laFout Eeight67C-7 android:laFout Eidth67-pG7 android:laFout height67fill parent7 /M Lfragment class67com.commonsEare.android.eu<Fou.=etails9ragment7 android:id67ORid/details7 android:laFout Eeight67/-7 android:laFout Eidth67-pG7 android:laFout height67fill parent7 /M L/)inear)aFoutM

2ote that =e are responsible &or the positioning o& the &ragments, so here =e use a horiKontal )inear)aFout to =rap aroun" the t=o LfragmentM elements.

The )istener Inter. ce


When the user 'hooses a 'ountry in the +ountries9ragment, =e =ant to let our 'ontaining a'ti!ity kno= about that. 0n this 'ase, it so happens that the only a'ti!ity that =ill e!er host +ountries9ragment is $3<5ou. +o=e!er, perhaps in the &uture that =ill not be the 'ase. %o, =e shoul" abstra't out the 'ommuni'ations &rom +ountries9ragment to its hosting a'ti!ity !ia a listener inter&a'e. +en'e, the $3<5ou 0 proGe't has a +ountrF)istener inter&a'e,
package com.commonsEare.android.eu<FouJ public interface +ountrF)istener : void onCountrySelectedP+ountrF cQJ ;

5he +ountries9ragment hol"s onto an instan'e o& +ountrF)istener, supplie" by the hosting a'ti!ity,
public void setCountryListenerP+ountrF)istener listenerQ : this.listener6listenerJ ; -:&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

An", =hen the user 'li'ks on a 'ountry an" triggers on)istItem+lickPQ, +ountries9ragment 'alls the on+ountrF2electedPQ metho" on the inter&a'e,
O"verride public void onListItemClickP)istVieE l8 VieE v8 int position8 long idQ : l.setItemCheckedPposition8 trueQJ if PlistenerX6nullQ : listener.onCountrySelectedP$3.getPpositionQQJ ; ;

The Activity
5he $3<5ou a'ti!ity is not long, though it is a bit tri'ky,
package com.commonsEare.android.eu<FouJ import import import import import import import android.content.IntentJ android.content.res.+onfigurationJ android.net.3riJ android.os.4undleJ android.support.v<.app.9ragmentJ android.support.v<.app.9ragmentActivitFJ android.vieE.VieEJ

public class $3<5ou eGtends 9ragmentActivitF implements +ountrF)istener : private boolean detailsInline6falseJ O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ +ountries9ragment countries 6P+ountries9ragmentQgetSupport"ragmentManagerPQ .find"ragmentByIdP?.id.countriesQJ countries.setCountryListenerPthisQJ 9ragment f6getSupport"ragmentManagerPQ.find"ragmentByIdP?.id.detailsQJ detailsInline6PfX6null ZZ Pget%esourcesPQ.getConfigurationPQ.orientation66 +onfiguration."?I$%&A&I"% )A%=2+A($QQJ if PdetailsInlineQ : countries.ena'le)ersistentSelectionPQJ ;

-:-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

else if PfX6nullQ : f.getViewPQ.setVisi'ilityPVieE.D"%$QJ ; ; O"verride public void onCountrySelectedP+ountrF cQ : 2tring url6getStringPc.urlQJ if PdetailsInlineQ : PP=etails9ragmentQgetSupport"ragmentManagerPQ .find"ragmentByIdP?.id.detailsQQ .load*rlPurlQJ ; else : Intent i6neE IntentPthis8 =etailsActivitF.classQJ i.put+xtraP=etailsActivitF.$]&?A 3?)8 urlQJ start$cti!ityPiQJ ; ; ;

>ur mission in on+reatePQ is to =ire up our &ragments. 5he &ragments themsel!es are 'reate" by our 'all to set+ontentVieEPQ, in&lating our layout an" the &ragments "e&ine" therein. 0n a""ition, though, $3<5ou,

*in"s

+ountries9ragment an" registers itsel& +ountrF)istener, sin'e $3<5ou implements that inter&a'e.

the

as

the

*in"s the =etails9ragment, i& it e;ists. 0& it e;ists an" =e are in lan"s'ape mo"e, =e tell the +ountries9ragment to enable the persistent highlight, to remin" the user =hat "etails are being loa"e" on the right. 0& =etails9ragment e;ists, but =e are in portrait mo"e, =e a'tually "o not =ant =etails9ragment but nee" it to be 'onsistent =ith the layout mo"e, so =e mark the &ragment7s 'ontents as being D"%$. >ther=ise, the =etails9ragment "oes not e;ist, an" so =e "o not ha!e to "o anything spe'ial.

0n An"roi" ..0, getting the 9ragment#anager &or 'alls like find9ragment4FIdPQ is a''omplishe" !ia get9ragment#anagerPQ. 5he ACL, ho=e!er, "e&ines a separate get2upport9ragment#anagerPQ, to ensure you are =orking =ith the ACL7s implementation o& 9ragment#anager an" to =ork a'ross the =i"er range o& An"roi" !ersions.

-:%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

0n a""ition, sin'e $3<5ou implements the +ountrF)istener inter&a'e, it must implement on+ountrF2electedPQ. +ere, $3<5ou notes =hether =e shoul" be routing to an inline e"ition o& =etails9ragment or not. 0& =e are, then on+ountrF2electedPQ passes the +ountrF to the =etails9ragment, so it loa"s that 'ountry7s Web page. >ther=ise, =e laun'h the =etailsActivitF, supplying the $ L as an e;tra.

Det ilsActivity
5he =etailsActivitF =ill be use" in 'ases =here the =etails9ragment is not being sho=n in the $3<5ou a'ti!ity, in'lu"ing,

When the "e!i'e has a normal s'reen siKe an" there&ore "oes not ha!e the =etails9ragment in the layout When the "e!i'e has a large s'reen in the portrait siKe an" there&ore $3<5ou is hi"ing its o=n =etails9ragment

The ) yout
5he layout Gust has our LfragmentM element in it, sin'e there is nothing else to sho=,
LNGml version671.-7 encoding67utf-,7NM Lfragment Gmlns:android67http://schemas.android.com/apk/res/android7 class67com.commonsEare.android.eu<Fou.=etails9ragment7 android:id67ORid/details7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 /M

The Activity
=etailsActivitF simply passes the $ L &rom the Intent =etails9ragment, telling it =hat Web 'ontent to "isplay,
package com.commonsEare.android.eu<FouJ import android.support.v<.app.9ragmentActivitFJ import android.content.IntentJ

e;tra on to the

-:0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

import android.net.3riJ import android.os.4undleJ public class =etailsActivitF eGtends 9ragmentActivitF : public static final 2tring $]&?A 3?)67com.commonsEare.android.eu<Fou.$]&?A 3?)7J O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.detailsQJ =etails9ragment details 6P=etails9ragmentQgetSupport"ragmentManagerPQ .find"ragmentByIdP?.id.detailsQJ details.load*rlPgetIntentPQ.getString+xtraP$]&?A 3?)QQJ ; ;

"ragments and Configuration Changes


0n a pre!ious 'hapter, =e re!ie=e" ho= a'ti!ities 'an "eal =ith 'on&iguration 'hanges, su'h as s'reen rotations. +o= "oes this translate into a =orl" o& &ragmentsH Well, as is typi'al, there is goo" ne=s, an" there is other ne=s. 5he goo" ne=s is that &ragments ha!e on2aveInstance2tatePQ metho"s that they 'an o!erri"e, beha!ing mu'h like their a'ti!ity 'ounterparts. 5he 4undle then is ma"e a!ailable in a !ariety o& pla'es, su'h as on+reatePQ an" onActivitF+reatedPQ, though there is no "e"i'ate" on?estoreInstance2tatePQ. not only "o &ragments la'k on?etain%on+onfigurationInstancePQ but the ACL7s 9ragmentActivitF "oes not allo= you to e;ten" on?etain%on+onfigurationInstancePQ, as that is use" internally. Appli'ations using the An"roi" ..0 implementation o& &ragments "ire'tly "o not su&&er &rom this problem. 5his limitation is substantial, an" it remains to be seen =hat te'hniRues =e 'olle'ti!ely =ork out to get past the limitation. 5he other ne=s is that

-:2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"ragments

/esigning for "ragments


5he o!erall "esign approa'h &or &ragment &a!ors ha!ing business logi' in the &ragment, =ith a'ti!ities ser!ing as an or'hestration layer &or inter&ragment na!igation an" things that &ragments are in'apable o& (e.g., on?etain%on+onfigurationInstancePQ). *or e;ample, the 8mail appli'ation originally probably ha" mu'h o& its business logi' implemente" in ea'h a'ti!ity (e.g., a'ti!ity &or &ol"ers, a'ti!ity &or a list o& 'on!ersations, a'ti!ity &or a single 'on!ersation). 2o=a"ays, that appli'ation is probably built aroun" ha!ing that business logi' "elegate" to &ragments, =ith the a'ti!ities merely 'hoosing =hi'h &ragments to "isplay base" upon a!ailable s'reen siKe. 5his =ill 'ause some amount o& restru'turing o& an e;isting appli'ation, abo!e an" beyon" the simple a't o& re&a'toring the 'o"e. *or e;ample, a )istActivitF might ha!e laun'he" another a'ti!ity &rom on)istItem+lickPQ. 5he &irst-'ut re&a'toring o& that =oul" ha!e the &ragment7s on)istItem+lickPQ laun'h an a'ti!ity. +o=e!er, the &ragment "oes not kno= =hether the 'ontent reRueste" by the user shoul" be sho=n in another a'ti!ity or not S it might go to another &ragment =ithin the 'urrent a'ti!ity. +en'e, the &ragment shoul" not blin"ly 'all startActivitFPQ but rather shoul" 'all a metho" on its 'ontainer a'ti!ity (or, more likely, a listener inter&a'e implemente" by that a'ti!ity), telling it o& the 'li'k e!ent an" letting it "e'i"e the right 'ourse o& a'tion. ight no=, &ragments are !ery ne=, so there are &e= =ell-establishe" patterns to &ollo=. >!er time, the An"roi" "e!eloper 'ommunity, in 'onGun'tion =ith 8oogle, =ill &igure out those patterns, in some 'ases pa'kaging them in pre-&abri'ate" a'ti!ities an" &ragments &or reuse in the &orm o& libraries an" CA s.

-:7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER &;

3andling Platform Changes

An"roi" is going to un"ergo rapi" e!olution o!er the ne;t &e= years. #erhaps, in time, the rate o& 'hange =ill "e'line some. +o=e!er, &or the here an" no=, you ha!e to assume signi&i'ant An"roi" releases e!ery /-12 months, an" 'hanges to the lineup o& possible An"roi" har"=are on an ongoing basis. %o, =hile right no=, the &o'us o& An"roi" is phones, soon you =ill see An"roi" netbooks, An"roi" tablets, An"roi" me"ia players, an" so on. Many o& these 'hanges =ill ha!e little impa't on your e;isting 'o"e. %ome, though, =ill ne'essitate at least ne= roun"s o& testing &or your appli'ations, an" perhaps 'hanges to those appli'ations base" upon the test results. 0n this 'hapter, =e 'o!er a number o& the areas =hi'h may 'ause you trouble in the &uture as An"roi" e!ol!es, an" ho= to "eal =ith them.

Things That +ake .ou (o DBoomD


An"roi" 'hanges, not only in terms o& =hat 'omes &rom 8oogle, but also in ho= that >% is t=eake" by "e!i'e manu&a'turers &or their o=n har"=are. 5his se'tion points out a 'ouple o& pla'es =here these 'hanges 'an bite you.

-::
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

>ie# Hier rchy


An"roi" is not "esigne" to han"le arbitrarily-'ompli'ate" !ie= hierar'hies. +ere, M!ie= hierar'hyM means 'ontainers hol"ing 'ontainers hol"ing 'ontainers hol"ing =i"gets. 5he hierarchFvieEer program, "es'ribe" in a later 'hapter, "epi'ts su'h !ie= hierar'hies =ell. An"roi" has al=ays ha" limits as to ho= "eep the !ie= hierar'hy 'an be. 0n An"roi" 1.A, though, the limit =as re"u'e", so some appli'ations that =orke" &ine on An"roi" 1.1 =oul" 'rash =ith a 2tack"verfloE$Gception in the ne=er An"roi". 5his, o& 'ourse, =as &rustrating to "e!elopers =ho ne!er realiKe" there =as an issue =ith !ie= hierar'hy "epth an" then got 'aught by this 'hange. 5he lessons to take &rom this,

Deep your !ie= hierar'hies shallo= S on'e you "ri&t into "ouble"igit "epth, you are in'reasingly likely to run out o& sta'k spa'e 0& you en'ounter a 2tack"verfloE$Gception, an" the sta'k tra'e looks like it is some=here in the mi""le o& "ra=ing your =i"gets, your !ie= hierar'hy is probably too 'omple;

Ch n!in! Resources
5he 'ore An"roi" team may 'hange resour'es =ith an An"roi" upgra"e, an" those may ha!e une;pe'te" e&&e'ts in your appli'ation. *or e;ample, in An"roi" 1.A, they 'hange" the sto'k 4utton ba'kgroun", to allo= &or smaller buttons. +o=e!er, appli'ations that impli'itly relie" upon the &ormer larger minimum siKe =oun" up MbreakingM an" nee"ing some $0 a"Gustment. %imilarly, appli'ations 'an reuse publi' resour'es, su'h as i'ons, a!ailable insi"e o& An"roi" proper. While "oing so sa!es some storage spa'e, many o& these resour'es are publi' by ne'essity an" are not 'onsi"ere" part o& the %@D. *or e;ample, har"=are manu&a'turers may 'hange the i'ons to &it some alternati!e $0 look-an"-&eel. elying upon the e;isting ones to al=ays

%<<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

look as they "o is a bit "angerous. ?ou are better ser!e" 'opying those resour'es out o& the An"roi" open sour'e proGe't into your o=n 'o"e base.

3andling AP Changes
5he 'ore An"roi" team has generally "one a goo" Gob o& keeping A#0s stable, an" supporting a "epre'ation mo"el =here they 'hange A#0s. 0n An"roi", being "epre'ate" "oes not mean it is going a=ay, Gust that its 'ontinue" use is "is'ourage". An", o& 'ourse, ne= A#0s are release" =ith e!ery ne= An"roi" up"ate. Changes to the A#0s are =ell-"o'umente" =ith ea'h release !ia an A#0 "i&&eren'es report. $n&ortunately, the An"roi" Market S the primary "istribution 'hannel &or An"roi" appli'ations S only allo=s you to uploa" one A#D &or ea'h appli'ation. +en'e, you nee" that one A#D to "eal =ith as many An"roi" !ersions as possible. Many times, your 'o"e =ill MGust =orkM an" not reRuire 'hanging. >ther times, though, you =ill nee" to make a"Gustments, parti'ularly i& you =ant to support ne= A#0s on ne= !ersions =hile not breaking on ol" !ersions. Let us e;amine some te'hniRues &or han"ling these 'ases.

%inimum4 % 0imum4 T r!et4 nd Build >ersions


An"roi" goes to great lengths to help you "eal =ith the &a't that at any point in time, there =ill be many An"roi" >% !ersions out on the market. $n&ortunately, the tools supplie" by An"roi" ha!e gi!en us a some=hat 'on&using set o& o!erlapping 'on'epts, su'h as targets an" %@D !ersions. 5his se'tion =ill attempt to e;plain a bit more about =hat is all going on here.

T r!ets versus SD( >ersions versus +S >ersions


Way ba'k to=ar"s the beginning o& this book, =e intro"u'e" the 'on'ept o& targets. 5argets are use" =hen "e&ining A-@s, to "etermine =hat sort o& "e!i'e those A-@s support. 5argets are also use" =hen 'reating ne=

%<*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

proGe'ts, primarily to "etermine =hat !ersion o& the %@D buil" tools =ill be use" to buil" your proGe't. A target 'ombines an A#0 le!el =ith an in"i'ator o& =hether or not the target in'lu"es 8oogle A#0s (e.g., 8oogle Maps support). An A#0 le!el is an integer representing a !ersion o& the An"roi" A#0. Ea'h An"roi" >% release that makes 'hanges to the An"roi" A#0 triggers a ne= A#0 le!el. %o, =e ha!e,

An"roi" 1.Ar1, 1.Ar2, an" 1.Ar. all using A#0 Le!el C An"roi" 1./r1 an" 1./r2 using A#0 Le!el < An"roi" 2.0 using A#0 Le!el . An"roi" 2.0.1 using A#0 Le!el 0 An"roi" 2.1 using A#0 Le!el / An"roi" 2.2 using A#0 Le!el , An"roi" 2.. using A#0 Le!el * An"roi" 2.... using A#0 Le!el 1An"roi" ..0 using A#0 Le!el 11

8oogle maintains a Web page outlining =hi'h !ersions o& An"roi" are in use to"ay, base" on reRuests ma"e to the An"roi" Market.

%inimum SD( >ersion


0n your Android#anifest.Gml &ile, you shoul" a"" a Luses-sdkM element. 5his element =ill "es'ribe ho= your appli'ation relates to the !arious %@D !ersions. 5he most 'riti'al attribute to ha!e in Luses-sdkM is android:min2dkVersion. 5his in"i'ates =hat the lo=est A#0 le!el is that you =ill support. @e!i'es running An"roi" >% !ersions asso'iate" =ith lo=er A#0 le!els =ill not be able to install your appli'ation. ?our appli'ation may not e!en appear to
%<&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

those "e!i'es in the An"roi" Market listings, shoul" you ele't to publish !ia that "istributor. 0& you skip this attribute, An"roi" assumes you =ork on all An"roi" A#0 !ersions. 5hat may be true, but it is rather "angerous to assume i& you ha!e not teste" it. +en'e, set android:min2dkVersion to the lo=est le!el you are testing an" are =illing to support.

T r!et SD( >ersion


Another Luses-sdkM attribute is android:target2dkVersion. 5his represents the !ersion o& the An"roi" A#0 that you are primarily "e!eloping &or. Any An"roi" "e!i'e running a ne=er !ersion o& the >% may ele't to apply some M'ompatibility settingsM that =ill help apps like yours, targeting an ol"er A#0, run on the ne=er !ersion. Most o& the time, you shoul" set this to be the then-'urrent An"roi" A#0 !ersion, as o& the time you are publishing your appli'ation. 0n parti'ular, =ith +oney'omb, you nee" to spe'i&y a target o& 11 to get the ne= look-an"-&eel.

% 0imum SD( >ersion


5he thir" Luses-sdkM attribute is android:maG2dkVersion. Any An"roi" "e!i'e running a ne=er An"roi" >% than is in"i'ate" by this A#0 le!el =ill be prohibite" &rom running your appli'ation. >n the plus si"e, this ensures that your appli'ation =ill not be use" on A#0 le!els you ha!e not teste", parti'ularly i& you set this to be the then-'urrent An"roi" A#0 !ersion as o& your publi'ation "ate. +o=e!er, bear in min" that your appli'ation =ill be &iltere" out o& the An"roi" Market &or these ne=er "e!i'es. >!er time, this =ill limit the rea'h

%<-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

o& your appli'ation, i& you "o not release an up"ate =ith a higher ma;imum %@D !ersion. 5he 'ore An"roi" team re'ommen"s not using this option an" relying upon An"roi"7s intrinsi' ba'k=ar"s 'ompatibility S parti'ularly le!eraging your android:target2dkVersion !alue S to allo= your appli'ation to 'ontinue to run on ne= An"roi" >% !ersions.

Detectin! the >ersion


0& all you nee" to "o is take "i&&erent bran'hes in your 'o"e base" upon !ersion, the easiest thing to "o is inspe't android.os.4uild.V$?2I"%.2=H I%&. 5his publi' stati' integer !alue =ill re&le't the same A#0 le!el as you use =hen 'reating A-@s an" spe'i&ying A#0 le!els in the mani&est. %o, you 'an 'ompare that !alue to, say, android.os.4uild.V$?2I"% +"=$2.="%3& to see =hether you are running on An"roi" 1./ or ne=er.

,r ppin! the API


%o long as the A#0s you try to use e;ist a'ross all An"roi" !ersions you are supporting, Gust bran'hing may be su&&i'ient. Where things get troublesome is =hen the A#0s 'hange, ne= parameters to metho"s, ne= metho"s, or e!en ne= 'lasses. ?ou nee" 'o"e that =ill =ork regar"less o& An"roi" !ersion, yet lets you take a"!antage o& ne= A#0s =here a!ailable. 5he 'hallenge is that i& you try loa"ing 'o"e into the !irtual ma'hine that re&ers to 'lasses, metho"s, an" su'h that "o not e;ist in the !ersion o& An"roi" that the "e!i'e is running upon, your appli'ation =ill 'rash =ith a VerifF$rror. ?ou 'an (an" nee" to) compile against the !ersion o& An"roi" that 'ontains the latest A#0s you are trying to use S you Gust 'annot loa" that 'o"e into an ol"er An"roi" "e!i'e. 2ote that the key phrase here is Mloa" that 'o"eM. Cust be'ause a 'lass e;ists in your appli'ation that uses a ne=er-than-a!ailable A#0, you "o not ha!e a problem. 0t is only i& you e;e'ute 'o"e that triggers An"roi" to loa" that 'lass into your running pro'ess =ill you en'ounter the VerifF$rror.
%<%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

With that in min", there are three primary tri'ks to "eal =ith this situation, outline" in the &ollo=ing se'tions.

Detectin! Cl sses
#erhaps all you nee" to "o is "isable some &eatures in your app that lea" to things that are not possible on a gi!en "e!i'e. *or e;ample, maybe you ha!e an a'ti!ity that uses the ne= An"roi" ..0 M&ragmentsM &eature. ?ou 'annot su''ess&ully start that a'ti!ity on a pre-..0 "e!i'e. %topping that may Gust be a matter o& "isabling a menu 'hoi'e or 4utton or something. 5o see i& a 'ertain 'lass S say, )ist9ragment S is a!ailable to you, you 'an 'all +lass.for%amePQ. 5his =ill either return a +lass obGe't representing the reRueste" 'lass, or it =ill thro= an $Gception i& it is not a!ailable. ?ou 'an use the e;'eption han"ler as the spot to "isable the $0 paths that =oul" 'ause you to try starting an a'ti!ity that uses the una!ailable 'lass.

Re.lection
0& you nee" limite" a''ess to a 'lass that =ill not e;ist on ol"er !ersions o& An"roi", you 'an use a bit o& re&le'tion. *or e;ample, in the 'hapter on rotation, =e use" a series o& sample appli'ations that allo=e" the user to pi'k a 'onta't. 5hat relie" upon an A+&I"% (I+H Intent, using a spe'i&i' 3ri &or the 'onta'ts 'ontent pro!i"er. 0n those samples, =e spe'i&i'ally use" +ontacts+ontract, the re!ise" 'onta'ts A#0 o&&ere" in An"roi" 2.0 an" beyon". 5hat means those proGe'ts =ill not =ork on ol"er !ersions o& An"roi". +o=e!er, all =e really nee" is this magi' 3ri !alue. 0& =e 'an "e!ise a =ay to get the right 3ri &or ol"er !ersions o& An"roi", as =ell as the right 3ri &or ne=er !ersions o& An"roi", =ithout 'ausing problems, =e 'an be more ba'k=ar"s-'ompatible. *ortunately, this is &airly easy to "o =ith some re&le'tion,

%<0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

static : int sdk6neE IntegerP4uild.V$?2I"%.2=HQ.intValuePQJ if PsdkM6.Q : trF : +lass claKK6+lass.for&ameP7android.provider.+ontacts+ontract'+ontacts7QJ +"%&$%& 3?I6P3riQclaKK.get"ieldP7+"%&$%& 3?I7Q.getPclaKKQJ ; catch P&hroEable tQ : )og.eP7(ick=emo78 7$Gception Ehen determining +"%&$%& 3?I78 tQJ ;

; else : +"%&$%& 3?I6android.provider.+ontacts.(eople.+"%&$%& 3?IJ ;

+ere, =e e;amine the A#0 le!el o& the "e!i'e, by looking at 4uild.V$?2I"%.2=H (=e 'oul" use 4uild.V$?2I"%.2=H I%&, but that =as only a""e" =ith An"roi" 1./ S the 'o"e sho=n here =orks on An"roi" 1.A as =ell). 0& =e are at An"roi" 2.0 (A#0 le!el A) or higher, =e use +lass.for%amePQ to get at the ne= +ontacts+ontract.+ontacts 'lass, then use re&le'tion to get at the +"%&$%& 3?I stati' "ata member on that 'lass. 0& =e are on an ol"er !ersion o& An"roi", =e simply use the 3ri publishe" by the ol"er +ontacts.(eople 'lass. %in'e =e are not "ire'tly re&eren'ing +ontacts+ontract.+ontacts in our 'o"e, =e 'an sa&ely e;e'ute this, e!en on ol"er !ersions o& An"roi".

Condition l Cl ss )o din!
e&le'tion =orks but is a pain &or anything 'omple;. Also, it is slo=er than 'alling 'o"e "ire'tly. 5he most po=er&ul te'hniRue, there&ore, is simply to organiKe your 'o"e su'h that you ha!e regular 'lasses using ne=er A#0s, but you "o not loa" those 'lasses on ol"er "e!i'es. We =ill e;amine this te'hniRue later in this book.

%<2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

Patterns for 3oneycomb


More so than any pre!ious An"roi" release, +oney'omb (An"roi" ..0) makes supporting multiple An"roi" !ersions a signi&i'ant 'hallenge. 5he $0 'hanges reRuire" to support the +oney'omb $0 =ill, in many 'ases, reRuire you to take steps to make sure that you still =ork su''ess&ully on ol"er !ersions o& An"roi". 5his se'tion =ill outline some patterns &or "ealing =ith this area o& ba'k=ar"s 'ompatibility.

The Action B r
As note" in the 'hapter on the a'tion bar, many o& its basi' &eatures =ill =ork in a ba'k=ar"s-'ompatible &ashion. *or e;ample, in"i'ating than an options menu item 'an be sho=n in the a'tion bar reRuires Gust an attribute in the menu resour'e FML, an attribute that =ill be ignore" on ol"er !ersions o& An"roi". +oney'omb-'apable "e!i'es =ill put the item in the a'tion bar, =hile "e!i'es running pre!ious An"roi" !ersions =ill not. +o=e!er, not e!erything in!ol!e" =ith the a'tion bar is ba'k=ar"s 'ompatible. 0n the #enus/Action4ar sample appli'ation, =e a""e" a 'ustom VieE to the a'tion bar, to allo= people to a"" =or"s to our list =ithout "ealing =ith menus an" "ialogs. +o=e!er, this reRuire" some 'o"e that =oul" only =ork on A#0 Le!el 11 (An"roi" ..0) an" higher. More a"!an'e" a'tion bar 'apabilities S ones beyon" the s'ope o& this book S =ill ha!e similar reRuirements. ?ou nee" to arrange to only use those a'tion bar metho"s on "e!i'es that run A#0 Le!el 11 or higher. Con"itional 'lass loa"ing, outline" in a pre!ious se'tion o& this 'hapter, is one su'h te'hniRue, an" is the te'hniRue use" in the #enus/Action4ar4+ sample appli'ation. Let7s take a look at ho= this =orks.

Chec$in! the API )evel


>ur original implementation o& on+reate"ptions#enuPQ looke" like this,

%<7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

O"verride public boolean onCreateOptionsMenuP#enu menuQ : neE MenuInflaterPthisQ.inflateP?.menu.option8 menuQJ $dit&eGt add6P$dit&eGtQmenu .findItemP?.id.addQ .get$ctionViewPQ .findViewByIdP?.id.titleQJ add.setOn+ditor$ctionListenerPon2earchQJ ; returnPsuper.onCreateOptionsMenuPmenuQQJ

5his is &ine, but it =ill only =ork on A#0 Le!el 11 an" higher, as getActionVieEPQ only e;ists &rom that A#0 le!el on=ar". +en'e, =e 'annot run this 'o"e, or e!en loa" this 'lass, on ol"er !ersions o& An"roi" =ithout getting a VerifF$rror. 5he ne= !ersion o& on+reate"ptions#enuPQ hi"es the o&&en"ing 'o"e an" 'he'ks the A#0 le!el,
O"verride public boolean onCreateOptionsMenuP#enu menuQ : neE MenuInflaterPthisQ.inflateP?.menu.option8 menuQJ $dit&eGt add6nullJ if P4uild.V$?2I"%.2=H I%&M64uild.V$?2I"% +"=$2.!"%$5+"#4Q : VieE v6!oneFcomb!elper.get$dd$ctionViewPmenuQJ if PvX6nullQ : add6P$dit&eGtQv.findViewByIdP?.id.titleQJ ; ; if PaddX6nullQ : add.setOn+ditor$ctionListenerPon2earchQJ ; ; returnPsuper.onCreateOptionsMenuPmenuQQJ

We only hi"e the 'o"e that retrie!es the VieE that =e theoreti'ally ha!e put in the a'tion bar. 0& =e are on an ol"er !ersion o& An"roi", the !"%$5+"#4 'he'k =ill &ail, an" =e =ill =in" up =ith a null VieE, so =e skip a""ing the "n$ditorAction)istener to the $dit&eGt insi"e o& that VieE.
%<8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

5his has another bene&it, it =orks i& the An"roi" "e!i'e runs A#0 Le!el 11 or higher but "oes not ha!e room &or our 'ustom VieE. An"roi" tablets =ill ha!e an a'tion bar an" ha!e su&&i'ient room, but &uture +oney'omb'apable phones might ha!e an a'tion bar but la'k su&&i'ient room. 0n that 'ase, the phone =oul" lea!e the MA""M options menu item in pla'e, an" =e still =oul" =in" up =ith a null VieE. 5his 'o"e han"les that s'enarioT the original 'o"e "i" not.

Isol tin! the Honeycom= Code


>ur +oney'omb-spe'i&i' 'o"e is hel" in a separate !oneFcomb!elper 'lass, one that =ill only be use" on A#0 Le!el 11 (or higher) "e!i'es,
package com.commonsEare.android.inflationJ import android.vieE.#enuJ import android.vieE.VieEJ class !oneFcomb!elper : static VieE get$dd$ctionViewP#enu menuQ : returnPmenu.findItemP?.id.addQ.get$ctionViewPQQJ ; ;

!oneFcomb!elper has a single getAddActionVieEPQ stati' VieE &or the A"" a'tion bar entry, i& there is one.

metho" that &in"s the

%in'e =e "o not try e;e'uting any 'o"e on this 'lass e;'ept insi"e the are=e-on-!"%$5+"#4 'he'k, it is sa&e to ha!e this 'lass on ol"er !ersions o& An"roi". 5he #enus/Action4ar!+ app =orks on An"roi" 1./ an" ne=er.

,ritin! T =let*+nly Apps


0"eally, your An"roi" appli'ations =ork on all &orm &a'tors, phones, tablets, et'. +o=e!er, it may be that you =ant to 'reate an app that simply =oul" be unusable on phones. 0"eally, there =oul" be a =ay to keep su'h an app o&& o& small-s'reen "e!i'es, so users are not "isappointe".

%<:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Platform Changes

5o "o this, you 'an take a"!antage o& the &a't that =hile An"roi" =ill s'ale apps up, it =ill not s'ale apps "o=n. 0n other =or"s, i& you say that you "o not support some larger s'reen siKe (e.g., android:Glarge2creens67false7 in your Lsupports-screensM element in your Android#anifest.Gml &ile), An"roi" =ill still allo= your app to run on su'h s'reens, =ith An"roi" taking steps to help your app run =ith the a""itional s'reen spa'e. +o=e!er, i& you say that you "o not support some smaller s'reen siKe (e.g., android:small2creens67false7 in your Lsupports-screensM element), An"roi" =ill not run your app, an" you =ill be &iltere" out o& the An"roi" Market &or su'h "e!i'es. +en'e, i& your appli'ation =ill only make sense &or larger-s'reen "e!i'es, use a Lsupports-screensM element like this,
Lsupports-screens android:Glarge2creens67true7 android:large2creens67true7 android:normal2creens67false7 android:small2creens67false7 android:anF=ensitF67true7/M

%*<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

PART IV Data Stores, Networ Services, and APIs

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1<

Accessing "iles

While An"roi" o&&ers stru'ture" storage, !ia pre&eren'es an" "atabases, sometimes a simple &ile =ill su&&i'e. An"roi" o&&ers t=o mo"els &or a''essing &iles, one &or &iles pre-pa'kage" =ith your appli'ation, an" one &or &iles 'reate" on-"e!i'e by your appli'ation.

.ou And The 3orse .ou Code n ,n


Let7s suppose you ha!e some stati' "ata you =ant to ship =ith the appli'ation, su'h as a list o& =or"s &or a spell-'he'ker. 5he easiest =ay to "eploy that is to put the &ile in the res/raE "ire'tory, so it gets put in the An"roi" appli'ation .apk &ile as part o& the pa'kaging pro'ess as a ra= resour'e. 5o a''ess this &ile, you nee" to get yoursel& a ?esources obGe't. *rom an a'ti!ity, that is as simple as 'alling get?esourcesPQ. A ?esources obGe't o&&ers open?aE?esourcePQ to get an Input2tream on the &ile you spe'i&y. ather than a path, open?aE?esourcePQ e;pe'ts an integer i"enti&ier &or the &ile as pa'kage". 5his =orks Gust like a''essing =i"gets !ia findVieE4FIdPQ S i& you put a &ile name" Eords.Gml in res/raE, the i"enti&ier is a''essible in Ca!a as ?.raE.Eords. %in'e you 'an only get an Input2tream, you ha!e no means o& mo"i&ying this &ile. +en'e, it is really only use&ul &or stati' re&eren'e "ata. Moreo!er, sin'e it is un'hanging until the user installs an up"ate" !ersion o& your
%*Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

appli'ation pa'kage, either the re&eren'e "ata has to be !ali" &or the &oreseeable &uture, or you =ill nee" to pro!i"e some means o& up"ating the "ata. 5he simplest =ay to han"le that is to use the re&eren'e "ata to bootstrap some other mo"i&iable &orm o& storage (e.g., a "atabase), but this makes &or t=o 'opies o& the "ata in storage. An alternati!e is to keep the re&eren'e "ata as-is but keep mo"i&i'ations in a &ile or "atabase, an" merge them together =hen you nee" a 'omplete pi'ture o& the in&ormation. *or e;ample, i& your appli'ation ships a &ile o& $ Ls, you 'oul" ha!e a se'on" &ile that tra'ks $ Ls a""e" by the user or re&eren'e $ Ls that =ere "elete" by the user. 0n the 9iles/2tatic sample proGe't, you =ill &in" a re=orking o& the listbo; e;ample &rom earlier, this time using a stati' FML &ile instea" o& a har"=ire" array in Ca!a. 5he layout is the same,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&eGtVieE android:id67ORid/selection7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 /M L)istVieE android:id67Oandroid:id/list7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:draE2elector"n&op67false7 /M L/)inear)aFoutM

0n a""ition to that FML &ile, you also nee" an FML &ile =ith the =or"s to sho= in the list,
LEordsM LEord LEord LEord LEord LEord LEord LEord LEord value67lorem7 /M value67ipsum7 /M value67dolor7 /M value67sit7 /M value67amet7 /M value67consectetuer7 /M value67adipiscing7 /M value67elit7 /M

%*%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

LEord value67morbi7 /M LEord value67vel7 /M LEord value67ligula7 /M LEord value67vitae7 /M LEord value67arcu7 /M LEord value67aliUuet7 /M LEord value67mollis7 /M LEord value67etiam7 /M LEord value67vel7 /M LEord value67erat7 /M LEord value67placerat7 /M LEord value67ante7 /M LEord value67porttitor7 /M LEord value67sodales7 /M LEord value67pellentesUue7 /M LEord value67augue7 /M LEord value67purus7 /M L/EordsM

While this FML stru'ture is not e;a'tly a mo"el o& spa'e e&&i'ien'y, it =ill su&&i'e &or a "emo. 5he Ca!a 'o"e no= must rea" in that FML &ile, parse out the =or"s, an" put them somepla'e &or the list to pi'k up,
public class 2tatic9ile=emo eGtends )istActivitF : &eGtVieE selectionJ ArraF)istL2tringM items6neE ArraF)istL2tringMPQJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ selection6P&eGtVieEQfindViewByIdP?.id.selectionQJ trF : Input2tream in6get%esourcesPQ.open%aw%esourceP?.raE.EordsQJ =ocument4uilder builder6=ocument4uilder9actorF .newInstancePQ .newDocumentBuilderPQJ =ocument doc6builder.parsePin8 nullQJ %ode)ist Eords6doc.get+lementsByTag&ameP7Eord7QJ for Pint i6-JiLEords.getLengthPQJiRRQ : items.addPPP$lementQEords.itemPiQQ.get$ttri'uteP7value7QQJ ; in.closePQJ ; catch P&hroEable tQ : &oast %*0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

.makeTextPthis8 7$Gception: 7Rt.toStringPQ8 &oast.)$%D&! )"%DQ .showPQJ

setList$dapterPneE ArraFAdapterL2tringMPthis8 android.?.laFout.simple list item 18 itemsQQJ ; public void onListItemClickP)istVieE parent8 VieE v8 int position8 long idQ : selection.setTextPitems.getPpositionQ.toStringPQQJ ; ;

5he "i&&eren'es mostly lie =ithin on+reatePQ. We get an Input2tream &or the FML &ile (get?esourcesPQ.open?aE?esourceP?.raE.EordsQ), then use the builtin FML parsing logi' to parse the &ile into a @>M =ocument, pi'k out the =or" elements, then pour the !alue attributes into an ArraF)ist &or use by the ArraFAdapter. 5he resulting a'ti!ity looks the same as be&ore, sin'e the list o& =or"s is the same, Gust relo'ate",

"igure *&%1 The Static"ile/emo sample application

%*2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

>& 'ourse, there are e!en easier =ays to ha!e FML &iles a!ailable to you as pre-pa'kage" &iles, su'h as by using an FML resour'e. 5hat is 'o!ere" in the ne;t 'hapter. +o=e!er, =hile this e;ample use" FML, the &ile 'oul" Gust as easily ha!e been a simple one-=or"-per-line list, or in some other &ormat not han"le" nati!ely by the An"roi" resour'e system.

CeadinG Gn WritinG
ea"ing an" =riting your o=n, appli'ation-spe'i&i' "ata &iles is nearly i"enti'al to =hat you might "o in a "esktop Ca!a appli'ation. 5he key is to use open9ileInputPQ an" open9ile"utputPQ on your ActivitF or other +onteGt to get an Input2tream an" "utput2tream, respe'ti!ely. *rom that point &or=ar", it is not mu'h "i&&erent than regular Ca!a 0P> logi',

Wrap those streams as nee"e", su'h as using an Input2tream?eader or "utput2tream@riter &or te;t-base" 0P> ea" or =rite the "ata $se closePQ to release the stream =hen "one

0& t=o appli'ations both try rea"ing a notes.tGt &ile !ia open9ileInputPQ, they =ill ea'h a''ess their o=n e"ition o& the &ile. 0& you nee" to ha!e one &ile a''essible &rom many pla'es, you probably =ant to 'reate a 'ontent pro!i"er, as =ill be "es'ribe" in an up'oming 'hapter. 2ote that open9ileInputPQ an" open9ile"utputPQ "o not a''ept &ile paths (e.g., path/to/file.tGt), Gust simple &ilenames. 1elo= you =ill see the layout &or the =orl"7s most tri!ial te;t e"itor, pulle" &rom the 9iles/?ead@rite sample appli'ation,
LNGml version671.-7 encoding67utf-,7NM L$dit&eGt Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/editor7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:single)ine67false7 android:gravitF67top7 /M

%*7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

All =e ha!e here is a large te;t-e"iting =i"get...=hi'h is pretty boring. 5he Ca!a is only slightly more 'ompli'ate",
package com.commonsEare.android.readEriteJ import import import import import import import import import import import import android.app.ActivitFJ android.os.4undleJ android.vieE.VieEJ android.Eidget.4uttonJ android.Eidget.$dit&eGtJ android.Eidget.&oastJ java.io.4uffered?eaderJ java.io.9ileJ java.io.Input2treamJ java.io.Input2tream?eaderJ java.io."utput2treamJ java.io."utput2tream@riterJ

public class ?ead@rite9ile=emo eGtends ActivitF : private final static 2tring %"&$267notes.tGt7J private $dit&eGt editorJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ editor6P$dit&eGtQfindViewByIdP?.id.editorQJ ; public void on%esumePQ : super.on%esumePQJ trF : Input2tream in6open"ileInputP%"&$2QJ if PinX6nullQ : Input2tream?eader tmp6neE InputStream%eaderPinQJ 4uffered?eader reader6neE Buffered%eaderPtmpQJ 2tring strJ 2tring4uilder buf6neE StringBuilderPQJ Ehile PPstr 6 reader.readLinePQQ X6 nullQ : buf.appendPstrR7Tn7QJ ; in.closePQJ editor.setTextPbuf.toStringPQQJ ; ; catch Pjava.io.9ile%ot9ound$Gception eQ : // thatIs "H8 Ee probablF havenIt created it Fet

%*8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

; catch P&hroEable tQ : &oast .makeTextPthis8 7$Gception: 7Rt.toStringPQ8 &oast.)$%D&! )"%DQ .showPQJ ;

public void on)ausePQ : super.on)ausePQJ trF : "utput2tream@riter out6 neE OutputStream#riterPopen"ileOutputP%"&$28 -QQJ out.writePeditor.getTextPQ.toStringPQQJ out.closePQJ ; catch P&hroEable tQ : &oast .makeTextPthis8 7$Gception: 7Rt.toStringPQ8 &oast.)$%D&! )"%DQ .showPQJ ; ; ;

*irst, =e hook into on?esumePQ, so =e get 'ontrol =hen our e"itor is 'oming ba'k to li&e, &rom a &resh laun'h or a&ter ha!ing been &roKen. We use open9ileInputPQ to rea" in notes.tGt an" pour the 'ontents into the te;t e"itor. 0& the &ile is not &oun", =e assume this is the &irst time the a'ti!ity =as run (or the &ile =as "elete" by other means), an" =e Gust lea!e the e"itor empty. *inally, =e hook into on(ausePQ, so =e get 'ontrol as our a'ti!ity gets hi""en by another a'ti!ity or is 'lose", su'h as !ia the "e!i'e7s 1ACD button. +ere, =e use open9ile"utputPQ to open notes.tGt, into =hi'h =e pour the 'ontents o& the te;t e"itor. 5he net result is that =e ha!e a persistent notepa", =hate!er is type" in =ill remain until "elete", sur!i!ing our a'ti!ity being 'lose" (e.g., !ia the 1ACD button), the phone being turne" o&&, or similar situations.

%*:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

"igure *&01 The CeadWrite"ile/emo sample application@ as initially launched

"igure *&21 The same application@ after entering some text

%&<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

Another approa'h &or =orking =ith appli'ation-lo'al &iles is to use get9iles=irPQ. 5his returns a 9ile obGe't pointing to a pla'e in the on-boar" &lash =here an appli'ation 'an store &iles. 5his "ire'tory is =here open9ileInputPQ an" open9ile"uptutPQ =ork. +o=e!er, =hile open9ileInputPQ an" open9ile"utputPQ "o not support sub"ire'tories, the 9ile &rom get9iles=irPQ 'an be use" to 'reate an" na!igate sub"ire'tories i& "esire". 5he &iles store" here are a''essible only to your appli'ation, by "e&ault. >ther appli'ations on the "e!i'e ha!e no rights to rea", let alone =rite, to this spa'e. +o=e!er, bear in min" that some users MrootM their An"roi" phones, gaining superuser a''ess. 5hese users =ill be able to rea" an" =rite =hate!er &iles they =ish. As a result, please 'onsi"er appli'ation-lo'al &iles to be se'ure against mal=are but not ne'essarily se'ure against intereste" users.

=xternal Storage5 (iant =conomy#SiBe Space


0n a""ition to appli'ation-lo'al storage, you also ha!e a''ess to Me;ternal storageM. 5his may 'ome in the &orm o& a remo!able me"ia 'ar", like an %@ 'ar" or mi'ro%@ 'ar". 5his may 'ome in the &orm o& a""itional on-boar" &lash set asi"e to ser!e in the Me;ternal storageM role. >n the plus si"e, e;ternal storage ten"s to ha!e more spa'e a!ailable. >nboar" storage 'an be rather limite" S the original 5-Mobile 81 (+5C @ream) ha" a total o& 40M1 &or all appli'ations 'ombine". While ne=er phones o&&er more spa'e, e;ternal storage is usually at least 281 an" 'an be as big as .281. >n the minus si"e, all appli'ations 'an, i& they =ish, rea" an" =rite e;ternal storage, an" so these &iles are not !ery se'ure. *urthermore, e;ternal storage 'an be mounte" on a host 'omputer as a $%1 mass storage "e!i'e S =hen it is in use in this mo"e, An"roi" appli'ations 'annot a''ess it. As a result, &iles on e;ternal storage may or may not be a!ailable to you at any gi!en moment.

%&*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

,here to ,rite
0& you ha!e &iles that are tie" to your appli'ation that are simply too big to risk putting in the appli'ation-lo'al &ile area, you 'an use get$Gternal9iles=irPQ, a!ailable on any a'ti!ity or other +onteGt. 5his =ill gi!e you a 9ile obGe't pointing to an automati'ally-'reate" "ire'tory on e;ternal storage, uniRue &or your appli'ation. While not se'ure against other appli'ations, it "oes ha!e one big a"!antage, =hen your appli'ation is uninstalle", these &iles are automati'ally "elete", Gust like the ones in the appli'ation-lo'al &ile area. 0& you ha!e &iles that belong more to the user than to your app S pi'tures taken by the 'amera, "o=nloa"e" M#. &iles, et'. S a better solution is to use get$Gternal2torage(ublic=irectorFPQ, a!ailable on the $nvironment 'lass. 5his =ill gi!e you a 9ile obGe't pointing to a "ire'tory set asi"e &or a 'ertain type o& &ile, base" on the type you pass into get$Gternal2torage(ublic=irectorFPQ. *or e;ample, you 'an ask &or =I?$+&"?5 #"VI$2, =I?$+&"?5 #32I+, or =I?$+&"?5 (I+&3?$2 &or storing M#<, M#., or C#E8 &iles, respe'ti!ely. 5hese &iles =ill be le&t behin" =hen your appli'ation is uninstalle". ?ou =ill also &in" a get$Gternal2torage=irectorFPQ metho" on $nvironment, pointing to the root o& the e;ternal storage. 5his is no longer the pre&erre" approa'h S the metho"s "es'ribe" abo!e help keep the user7s &iles better organiKe". +o=e!er, i& you are supporting ol"er An"roi" "e!i'es, you may nee" to use get$Gternal2torage=irectorFPQ, simply be'ause the ne=er options may not be a!ailable to you.

,hen to ,rite
%tarting =ith An"roi" 1./, you =ill also nee" to hol" permissions to =ork =ith e;ternal storage (e.g., @?I&$ $]&$?%A) 2&"?AD$) S the 'on'ept o& permissions =ill be 'o!ere" in a later 'hapter. Also, e;ternal storage may be tie" up by the user ha!ing mounte" it as a $%1 storage "e!i'e. ?ou 'an use get$Gternal2torage2tatePQ (a stati' metho"
%&&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

on $nvironment) to "etermine i& there e;ternal storage is presently a!ailable or not.

Strict+ode5 Avoiding 6anky Code


$sers are more likely to like your appli'ation i&, to them, it &eels responsi!e. +ere, by Mresponsi!eM, =e mean that it rea'ts s=i&tly an" a''urately to user operations, like taps an" s=ipes. Con!ersely, users are less likely to be happy =ith you i& they per'ei!e that your $0 is MGankyM S sluggish to respon" to their reRuests. *or e;ample, maybe your lists "o not s'roll as smoothly as they =oul" like, or tapping a button "oes not yiel" the imme"iate results they seek. While threa"s an" AsFnc&ask an" the like 'an help, it may not al=ays be ob!ious =here you shoul" be applying them. A &ull-s'ale per&orman'e analysis, using 5ra'e!ie= or similar An"roi" tools, is 'ertainly possible. +o=e!er, there are a &e= stan"ar" sorts o& things that "e!elopers "o, sometimes Ruite by a''i"ent, on the main appli'ation threa" that =ill ten" to 'ause sluggishness,

*lash 0P>, both &or the on-boar" storage an" &or Me;ternal storageM (e.g., the %@ 'ar") 2et=ork 0P>

+o=e!er, e!en here, it may not be ob!ious that you are per&orming these operations on the main appli'ation threa". 5his is parti'ularly true =hen the operations are really being "one by An"roi"7s 'o"e that you are simply 'alling. 5hat is =here 2trict#ode 'omes in. 0ts mission is to help you "etermine =hen you are "oing things on the main appli'ation threa" that might 'ause a Ganky user e;perien'e.

%&-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

Settin! up Strict %ode


=orks on a set o& poli'ies. 5here are presently t=o 'ategories o& poli'ies, -M poli'ies an" threa" poli'ies. 5he &ormer represent ba" 'o"ing pra'ti'es that pertain to your entire appli'ation, notably leaking %JLite +ursor obGe'ts an" kin. 5he latter represent things that are ba" =hen per&orme" on the main appli'ation threa", notably &lash 0P> an" net=ork 0P>.
2trict#ode

Ea'h poli'y "i'tates =hat 2trict#ode shoul" =at'h &or (e.g., &lash rea"s are >D but &lash =rites are not) an" ho= 2trict#ode shoul" rea't =hen you !iolate the rules, su'h as,

Log a message to LogCat @isplay a "ialog Crash your appli'ation (seriously:)

5he simplest thing to "o is 'all the stati' enable=efaultsPQ metho" on 2trict#ode &rom on+reatePQ o& your &irst a'ti!ity. 5his =ill set up normal operation, reporting all !iolations by simply logging to LogCat. +o=e!er, you 'an set your o=n 'ustom poli'ies !ia 4uilder obGe'ts i& you so 'hoose.

Seein! It In Action
5he &hreads/?ead@rite2trict sample appli'ation is a re=orking o& the 9iles/?ead@rite sample sho=n earlier in this 'hapter. All it a""s is a 'ustom 2trict#ode threa" poli'y,
2trict#ode.setThread)olicyPneE 2trict#ode.&hread(olicF.BuilderPQ .detect$llPQ .penaltyLogPQ .'uildPQQJ

0& you run the appli'ation, the user =ill see no "i&&eren'e. +o=e!er, you =ill ha!e a "ebug-le!el log message in LogCat =ith the &ollo=ing sta'k tra'e,

%&%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

1>->, 1/:1*:<-.--*: =$43D/2trict#odeP<,-Q: 2trict#ode policF violationJ ^duration610* ms: android.os.2trict#ode'2trict#ode=isk?eadViolation: policF6>C violation6> 1>->, 1/:1*:<-.--*: =$43D/2trict#odeP<,-Q: at android.os.2trict#ode'Android4lockDuard(olicF.on?ead9rom=iskP2trict#ode.java:/<. Q 1>->, 1/:1*:<-.--*: =$43D/2trict#odeP<,-Q: at dalvik.sFstem.4lockDuard'@rapped9ile2Fstem.openP4lockDuard.java:>>,Q 1>->, 1/:1*:<-.--*: =$43D/2trict#odeP<,-Q: at android.app.+onteGtImpl.open9ile"utputP+onteGtImpl.java:<1-Q 1>->, 1/:1*:<-.--*: =$43D/2trict#odeP<,-Q: at android.content.+onteGt@rapper.open9ile"utputP+onteGt@rapper.java:1.,Q 1>->, 1/:1*:<-.--*: =$43D/2trict#odeP<,-Q: at com.commonsEare.android.readErite.?ead@rite9ile=emo.on(auseP?ead@rite9ile=emo.ja va:,>Q ...

+ere, 2trict#ode is =arning you that you attempte" a &lash =rite on the main appli'ation threa" (the threa" on =hi'h you set the 2trict#ode poli'y). 0"eally, =e =oul" re=rite this proGe't to use an AsFnc&ask or something &or =riting out the "ata.

Development +nly4 Ple seG


@o not use 2trict#ode in pro"u'tion 'o"e. 0t is "esigne" &or use =hen you are buil"ing, testing, an" "ebugging your appli'ation. 0t is not "esigne" to be use" in the &iel". 5o "eal =ith this, you 'oul",

%imply 'omment out or remo!e the 2trict#ode setup 'o"e =hen you prepare your pro"u'tion buil"s $se some sort o& pro"u'tion &lag to skip the 2trict#ode setup 'o"e =hen nee"e"

Condition lly Bein! Strict


is only &or An"roi" 2.. an" higher. +en'e, i& =e ha!e it in our 'o"e, e!en in "e!elopment mo"e, it might inter&ere =hen =e try testing on ol"er emulators or "e!i'es. As =e sa= in an earlier 'hapter, there are
2trict#ode

%&0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

te'hniRues &or "ealing =ith this, but using re&le'tion &or 'on&iguring 2trict#ode =oul" be rather pain&ul. 5he right approa'h, there&ore, is simply to organiKe your 'o"e su'h that you ha!e regular 'lasses using ne=er A#0s, but you "o not loa" those 'lasses on ol"er "e!i'es. 5he A(IVersions/?ead@rite2trict proGe't "emonstrates this, allo=ing an appli'ation to use An"roi" 2..7s 2trict#ode =here a!ailable, or skipping it =here it is not a!ailable. When =e e;amine" 2trict#ode earlier in this se'tion , =e 'on&igure" 2trict#ode right in the on+reatePQ metho" o& our sample a'ti!ity. 5his =orks, but only on An"roi" 2.. an" ne=er. 5o allo= this to =ork on ol"er !ersions o& An"roi", =e ha!e 2trict@rapper,
package com.commonsEare.android.readEriteJ import android.os.4uildJ abstract class 2trict@rapper : static private 2trict@rapper I%2&A%+$6nullJ static public void initPQ : if P4uild.V$?2I"%.2=H I%&M64uild.V$?2I"% +"=$2.DI%D$?4?$A=Q : I%2&A%+$6neE Strict"or%eal.PQJ ; else : I%2&A%+$6neE &ot$llThatStrictPQJ ; ; static class %otAll&hat2trict eGtends 2trict@rapper : // no methods needed ; ;

5his o""-looking 'lass en'apsulates our M"o-=e-or-"on7t-=eM logi' &or "ealing =ith 2trict#ode. 0t 'ontains an initPQ metho" that, =hen 'alle", 'he'ks to see =hat !ersion o& An"roi" the appli'ation is running on, an" 'reates a singleton instan'e o& a 2trict@rapper sub'lass base" upon it S 2trict9or?ealK &or An"roi" 2.. an" higher, %otAll&hat2trict &or ol"er !ersions o& An"roi". 5he latter 'lass, a stati' inner 'lass o& 2trict@rapper,

%&2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

"oes nothing, re&le'ting that there is no 2trict#ode in ne=er !ersions o& An"roi".
2trict9or?ealK 'ontains the 2trict#ode

initialiKation logi',

package com.commonsEare.android.readEriteJ import android.os.2trict#odeJ class 2trict9or?ealK eGtends 2trict@rapper : Strict"or%eal.PQ : 2trict#ode.setThread)olicyPneE 2trict#ode.&hread(olicF.BuilderPQ .detect$llPQ .penaltyLogPQ .'uildPQQJ ; ;

An", our on+reatePQ metho" o& our a'ti!ity 'alls initPQ on 2trict@rapper, to trigger 'reating the proper obGe't,
O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ 2trict@rapper.initPQJ ; editor6P$dit&eGtQfindViewByIdP?.id.editorQJ

When the a'ti!ity &irst starts up, neither 2trict@rapper nor 2trict9or?ealK are loa"e" in the pro'ess. As soon as =e rea'h the initPQ statement in on+reatePQ, An"roi" loa"s 2trict@rapper into the pro'ess, but this is sa&e, as it "oes not re&er to any potentially-none;istent 'lasses. 5he initPQ metho" on 2trict@rapper then only e;e'utes a statement in!ol!ing 2trict9or?ealK i& =e are sa&ely on a supporte" !ersion o& An"roi". +en'e, 2trict9or?ealK =ill only be loa"e" into the pro'ess i& =e are on a ne=er An"roi" release, an" hen'e our use o& 2trict#ode in 2trict9or?ealK =ill not trigger a VerifF$rror. +ere, all =e nee"e" =as a bit o& initialiKation. 5he singleton pattern is use" to "emonstrate that you 'oul" e;pose an !ersion-"epen"ent A#0 implementation i& you "esire". %imply "e&ine the A#0 as abstra't metho"s
%&7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

on the abstra't 'lass ( 2trict@rapper) an" ha!e !ersion-"epen"ent 'on'rete implementations o& those abstra't metho"s on the 'on'rete sub'lasses (2trict9or?ealK, %otAll&hat2trict).

!inux "ilesystems5 .ou Sync@ .ou Win


An"roi" is built atop a Linu; kernel an" uses Linu; &ilesystems &or hol"ing its &iles. Classi'ally, An"roi" use" ?A**% (?et Another *lash *ile %ystem), optimiKe" &or use on lo=-po=er "e!i'es &or storing "ata to &lash memory. Many "e!i'es still use ?A**% to"ay. ?A**% has one big problem, only one pro'ess 'an =rite to the &ilesystem at a time. *or those o& you into &ilesystems, rather than o&&ering &ile-le!el lo'king, ?A**% has partition-le!el lo'king. 5his 'an be'ome a bit o& a bottlene'k, parti'ularly as An"roi" "e!i'es gro= in po=er an" start =anting to "o more things at the same time like their "esktop an" notebook brethren. An"roi" is starting to mo!e to=ar"s e;t<, another Linu; &ilesystem aime" more at "esktopsPnotebooks. ?our appli'ations =ill not "ire'tly per'ei!e the "i&&eren'e. +o=e!er, e;t< "oes a &air bit o& bu&&ering, an" it 'an 'ause problems &or appli'ations that "o not take this bu&&ering into a''ount. Linu; appli'ation "e!elopers ran hea"long into this in 2008-2003, =hen e;t< starte" to be'ome popular. An"roi" "e!elopers =ill nee" to think about it no=...&or your o=n &ile storage. 0& you are using %JLite or 2hared(references, you "o not nee" to =orry about this problem. An"roi" (an" %JLite, in the 'ase o& %JLite) han"le all the bu&&ering issues &or you. 0&, ho=e!er, you =rite your o=n &iles, you may =ish to 'ontemplate an e;tra step as you &lush your "ata to "isk. %pe'i&i'ally, you nee" to trigger a Linu; system 'all kno=n as fsFncPQ, =hi'h tells the &ilesystem to ensure all bu&&ers are =ritten to "isk. 0& you are using java.io.?andomAccess9ile in a syn'hronous mo"e, this step is han"le" &or you as =ell, so you =ill not nee" to =orry about it. +o=e!er, Ca!a "e!elopers ten" to use 9ile"utput2tream, =hi'h "oes not trigger an
%&8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing "iles

fsFncPQ, e!en get9=PQ.sFncPQ

=hen you 'all closePQ on the stream. 0nstea", you 'all on the 9ile"utput2tream to trigger the fsFncPQ. 2ote that this may be time-'onsuming, an" so "isk =rites shoul" be "one o&& the main appli'ation threa" =here!er pra'ti'al, su'h as !ia an AsFnc&ask.

%&:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 11

>sing Preferences

An"roi" has many "i&&erent =ays &or you to store "ata &or long-term use by your a'ti!ity. 5he simplest to use is the pre&eren'es system. An"roi" allo=s a'ti!ities an" appli'ations to keep pre&eren'es, in the &orm o& keyP!alue pairs (akin to a #ap), that =ill hang aroun" bet=een in!o'ations o& an a'ti!ity. As the name suggests, the primary purpose is &or you to store user-spe'i&ie" 'on&iguration "etails, su'h as the last &ee" the user looke" at in your &ee" rea"er, or =hat sort or"er to use by "e&ault on a list, or =hate!er. >& 'ourse, you 'an store in the pre&eren'es =hate!er you like, so long as it is keye" by a 2tring an" has a primiti!e !alue (boolean, 2tring, et'.) #re&eren'es 'an either be &or a single a'ti!ity or share" among all a'ti!ities in an appli'ation. >ther 'omponents, su'h as ser!i'es, also 'an =ork =ith share" pre&eren'es.

(etting What .ou Want


5o get a''ess to the pre&eren'es, you ha!e three A#0s to 'hoose &rom, 1. &rom =ithin your ActivitF, to a''ess a'ti!ityspe'i&i' pre&eren'es
get(referencesPQ

2. get2hared(referencesPQ &rom =ithin your ActivitF (or other appli'ation +onteGt), to a''ess appli'ation-le!el pre&eren'es
%-*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

.. get=efault2hared(referencesPQ, on (reference#anager, to get the share" pre&eren'es that =ork in 'on'ert =ith An"roi"7s o!erall pre&eren'e &rame=ork 5he &irst t=o take a se'urity mo"e parameter S the right ans=er here is #"=$ (?IVA&$, so no other appli'ations 'an a''ess the &ile. 5he get2hared(referencesPQ metho" also takes a name o& a set o& pre&eren'es S get(referencesPQ e&&e'ti!ely 'alls get2hared(referencesPQ =ith the a'ti!ity7s 'lass name as the pre&eren'e set name. 5he get=efault2hared(referencesPQ metho" takes the +onteGt &or the pre&eren'es (e.g., your ActivitF). All o& those metho"s return an instan'e o& 2hared(references, =hi'h o&&ers a series o& getters to a''ess name" pre&eren'es, returning a suitably-type" result (e.g., get4ooleanPQ to return a boolean pre&eren'e). 5he getters also take a "e&ault !alue, =hi'h is returne" i& there is no pre&eren'e set un"er the spe'i&ie" key. $nless you ha!e a goo" reason to "o other=ise, you are best ser!e" using the thir" option abo!e S get=efault2hared(referencesPQ S as that =ill gi!e you the 2hared(references obGe't that =orks =ith a (referenceActivitF by "e&ault, as =ill be "es'ribe" later in this 'hapter.

Stating .our Preference


8i!en the appropriate 2hared(references obGe't, you 'an use editPQ to get an Me"itorM &or the pre&eren'es. 5his obGe't has a set o& setters that mirror the getters on the parent 2hared(references obGe't. 0t also has,
removePQ to get ri" o& a single

name" pre&eren'e ma"e !ia the e"itor

clearPQ to get ri" o& all pre&eren'es commitPQ to persist your 'hanges

5he last one is important S i& you mo"i&y pre&eren'es !ia the e"itor an" &ail to commitPQ the 'hanges, those 'hanges =ill e!aporate on'e the e"itor goes out o& s'ope. 2ote that An"roi" 2.. has an applFPQ metho", that =orks like commitPQ, but runs &aster.
%-&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

Con!ersely, sin'e the pre&eren'es obGe't supports li!e 'hanges, i& one part o& your appli'ation (say, an a'ti!ity) mo"i&ies share" pre&eren'es, another part o& your appli'ation (say, a ser!i'e) =ill ha!e a''ess to the 'hange" !alue imme"iately.

ntroducing PreferenceActivity
?ou 'oul" roll your o=n a'ti!ity to 'olle't pre&eren'es &rom the user. >n the =hole, this is a ba" i"ea. 0nstea", use pre&eren'e FML resour'es an" a (referenceActivitF. WhyH >ne o& the 'ommon 'omplaints about An"roi" "e!elopers is that they la'k "is'ipline, not &ollo=ing any stan"ar"s or 'on!entions inherent in the plat&orm. *or other operating systems, the "e!i'e manu&a'turer might pre!ent you &rom "istributing apps that !iolate their human inter&a'e gui"elines. With An"roi", that is not the 'ase S but this is not a blanket permission to "o =hate!er you =ant. Where there is a stan"ar" or 'on!ention, please &ollo= it, so that users =ill &eel more 'om&ortable =ith your app an" their "e!i'e. $sing a (referenceActivitF &or 'olle'ting pre&eren'es is one su'h 'on!ention. 5he lin'hpin to the pre&eren'es &rame=ork an" (referenceActivitF is yet another FML "ata stru'ture. ?ou 'an "es'ribe your appli'ation7s pre&eren'es in an FML &ile store" in your proGe't7s res/Gml/ "ire'tory. 8i!en that, An"roi" 'an present a pleasant $0 &or manipulating those pre&eren'es, =hi'h are then store" in the 2hared(references you get ba'k &rom get=efault2hared(referencesPQ. 1elo=, you =ill &in" the pre&eren'e FML &or the (refs/2imple pre&eren'es sample proGe't,

%--

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

L(reference2creen Gmlns:android67http://schemas.android.com/apk/res/android7M L+heck4oG(reference android:keF67checkboG7 android:title67+heckboG (reference7 android:summarF67+heck it on8 check it off7 /M L?ingtone(reference android:keF67ringtone7 android:title67?ingtone (reference7 android:shoE=efault67true7 android:shoE2ilent67true7 android:summarF67(ick a tone8 anF tone7 /M L/(reference2creenM

5he root o& the pre&eren'e FML is a (reference2creen element. We =ill e;plain =hy it is name" that later in this 'hapterT &or no=, take it on &aith that it is a sensible name. >ne o& the things you 'an ha!e insi"e a (reference2creen element, not surprisingly, are pre&eren'e "e&initions. 5hese are sub'lasses o& (reference, su'h as +heck4oG(reference or ?ingtone(reference, as sho=n abo!e. As one might e;pe't, these allo= you to 'he'k a 'he'kbo; or 'hoose a ringtone, respe'ti!ely. 0n the 'ase o& ?ingtone(reference, you ha!e your option o& allo=ing users to 'hoose the system "e&ault ringtone, or to 'hoose Msilen'eM as a ringtone.

!etting >sers 3ave Their Say


8i!en that you ha!e set up the pre&eren'e FML, you 'an use a nearly-builtin a'ti!ity &or allo=ing your users to set their pre&eren'es. 5he a'ti!ity is nearly Mbuilt-inM be'ause you merely nee" to sub'lass it an" point it to your pre&eren'e FML, plus hook the a'ti!ity into the rest o& your appli'ation. %o, &or e;ample, here is the $dit(references a'ti!ity o& the (refs/2imple proGe't,
package com.commonsEare.android.simpleJ import android.app.ActivitFJ import android.os.4undleJ import android.preference.(referenceActivitFJ

%-%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

public class $dit(references eGtends (referenceActivitF : O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ add)references"rom%esourceP?.Gml.preferencesQJ ; ;

As you 'an see, there is not mu'h to see. All you nee" to "o is 'all the FML resour'e 'ontaining your pre&eren'es.
add(references9rom?esourcePQ an" spe'i&y

?ou =ill also nee" to a"" this as an a'ti!ity to your Android#anifest.Gml &ile,
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.simple7M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67.2imple(refs=emo7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM LactivitF android:name67.$dit(references7 android:label67Ostring/app name7M L/activitFM L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

An" you =ill nee" to arrange to in!oke the a'ti!ity, su'h as &rom a menu option, here pulle" &rom 2imple(refs=emo,
public boolean onCreateOptionsMenuP#enu menuQ : menu.addP#enu.%"%$8 $=I& I=8 #enu.%"%$8 7$dit (refs7Q .setIconP?.draEable.miscQ .set$lpha'eticShortcutPIeIQJ returnPsuper.onCreateOptionsMenuPmenuQQJ ; O"verride public boolean onOptionsItemSelectedP#enuItem itemQ :

%-0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

sEitch Pitem.getItemIdPQQ : case $=I& I=: start$cti!ityPneE IntentPthis8 $dit(references.classQQJ returnPtrueQJ ; returnPsuper.onOptionsItemSelectedPitemQQJ ; ;

+o=e!er, that is all that is nee"e", an" it really is not that mu'h 'o"e outsi"e o& the pre&eren'es FML. What you get &or your e&&ort is an An"roi"supplie" pre&eren'e $0,

"igure *&71 The Simple proAectGs preferences >

5he 'he'kbo; 'an be "ire'tly 'he'ke" or un'he'ke". 5o 'hange the ringtone pre&eren'e, Gust 'li'k on the entry in the pre&eren'e list to bring up a sele'tion "ialog,

%-2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

"igure *&81 Choosing a ringtone preference

2ote that there is no e;pli'it Msa!eM or M'ommitM button or menu on the (referenceActivitF S 'hanges are persiste" automati'ally. 5he 2imple(refs=emo a'ti!ity, beyon" ha!ing the a&orementione" menu, also "isplays the 'urrent pre&eren'es !ia a &able)aFout,
LNGml version671.-7 encoding67utf-,7NM L&able)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L&able?oEM L&eGtVieE android:teGt67+heckboG:7 android:padding?ight67.dip7 /M L&eGtVieE android:id67ORid/checkboG7 /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67?ingtone:7 android:padding?ight67.dip7 /M L&eGtVieE android:id67ORid/ringtone7

%-7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

/M L/&able?oEM L/&able)aFoutM

5he &iel"s &or the table are &oun" in on+reatePQ,


public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ checkboG6P&eGtVieEQfindViewByIdP?.id.checkboGQJ ringtone6P&eGtVieEQfindViewByIdP?.id.ringtoneQJ

5he &iel"s are up"ate" on ea'h on?esumePQ,


public void on%esumePQ : super.on%esumePQJ 2hared(references prefs6(reference#anager .getDefaultShared)referencesPthisQJ checkboG.setTextPneE BooleanPprefs .getBooleanP7checkboG78 falseQQ .toStringPQQJ ringtone.setTextPprefs.getStringP7ringtone78 7LunsetM7QQJ

5his means the &iel"s =ill be up"ate" =hen the a'ti!ity is opene" an" a&ter the pre&eren'es a'ti!ity is le&t (e.g., !ia the 1ACD button),

%-8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

"igure *&:1 The Simple proAectGs list of saved preferences

Adding a Wee Bit ,G Structure


0& you ha!e a lot o& pre&eren'es &or users to set, ha!ing them all in one big list may be'ome troublesome. An"roi"7s pre&eren'e $0 gi!es you a &e= =ays to impose a bit o& stru'ture on your bag o& pre&eren'es, in'lu"ing 'ategories an" s'reens. Categories are a""e" !ia a (reference+ategorF element in your pre&eren'e FML an" are use" to group together relate" pre&eren'es. ather than ha!e your pre&eren'es all as 'hil"ren o& the root (reference2creen, you 'an put a &e= (reference+ategorF elements in the (reference2creen, an" then put your pre&eren'es in their appropriate 'ategories. -isually, this a""s a "i!i"er =ith the 'ategory title bet=een groups o& pre&eren'es. 0& you ha!e lots an" lots o& pre&eren'es S more than is 'on!enient &or users to s'roll through S you 'an also put them on separate Ms'reensM by intro"u'ing the (reference2creen element. ?es, that (reference2creen element.
%-:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

Any 'hil"ren o& (reference2creen go on their o=n s'reen. 0& you nest (reference2creens, the parent s'reen "isplays the s'reen as a pla'ehol"er entry S tapping that entry brings up the 'hil" s'reen. *or e;ample, &rom the (refs/2tructured sample proGe't, here is a pre&eren'e FML &ile that 'ontains both (reference+ategorF an" neste" (reference2creen elements,
L(reference2creen Gmlns:android67http://schemas.android.com/apk/res/android7M L(reference+ategorF android:title672imple (references7M L+heck4oG(reference android:keF67checkboG7 android:title67+heckboG (reference7 android:summarF67+heck it on8 check it off7 /M L?ingtone(reference android:keF67ringtone7 android:title67?ingtone (reference7 android:shoE=efault67true7 android:shoE2ilent67true7 android:summarF67(ick a tone8 anF tone7 /M L/(reference+ategorFM L(reference+ategorF android:title67=etail 2creens7M L(reference2creen android:keF67detail7 android:title67=etail 2creen7 android:summarF67Additional preferences held in another page7M L+heck4oG(reference android:keF67checkboG>7 android:title67Another +heckboG7 android:summarF67"n. "ff. It reallF doesnIt matter.7 /M L/(reference2creenM L/(reference+ategorFM L/(reference2creenM

5he result, =hen you use this pre&eren'e FML =ith your (referenceActivitF implementation, is a 'ategoriKe" list o& elements,

%%<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

"igure *-<1 The Structured proAectGs preference > @ sho)ing categories and a screen placeholder

An", i& you tap on the @etail %'reen entry, you are taken to the 'hil" pre&eren'e s'reen,

%%*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

"igure *-*1 The child preference screen of the Structured proAectGs preference >

The 9ind ,f Pop#>ps .ou !ike


>& 'ourse, not all pre&eren'es are 'he'kbo;es an" ringtones. *or others, like entry &iel"s an" lists, An"roi" uses pop-up "ialogs. $sers "o not enter their pre&eren'e "ire'tly in the pre&eren'e $0 a'ti!ity, but rather tap on a pre&eren'e, &ill in a !alue, an" 'li'k >D to 'ommit the 'hange. %tru'turally, in the pre&eren'e FML, &iel"s an" lists are not signi&i'antly "i&&erent &rom other pre&eren'e types, as seen in this pre&eren'e FML &rom the (refs/=ialogs sample proGe't,
L(reference2creen Gmlns:android67http://schemas.android.com/apk/res/android7M L(reference+ategorF android:title672imple (references7M L+heck4oG(reference android:keF67checkboG7 android:title67+heckboG (reference7 android:summarF67+heck it on8 check it off7 /M L?ingtone(reference

%%&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

android:keF67ringtone7 android:title67?ingtone (reference7 android:shoE=efault67true7 android:shoE2ilent67true7 android:summarF67(ick a tone8 anF tone7 /M L/(reference+ategorFM L(reference+ategorF android:title67=etail 2creens7M L(reference2creen android:keF67detail7 android:title67=etail 2creen7 android:summarF67Additional preferences held in another page7M L+heck4oG(reference android:keF67checkboG>7 android:title67Another +heckboG7 android:summarF67"n. "ff. It reallF doesnIt matter.7 /M L/(reference2creenM L/(reference+ategorFM L(reference+ategorF android:title67"ther (references7M L$dit&eGt(reference android:keF67teGt7 android:title67&eGt $ntrF =ialog7 android:summarF67+lick to pop up a field for entrF7 android:dialog&itle67$nter something useful7 /M L)ist(reference android:keF67list7 android:title672election =ialog7 android:summarF67+lick to pop up a list to choose from7 android:entries67OarraF/cities7 android:entrFValues67OarraF/airport codes7 android:dialog&itle67+hoose a (ennsFlvania citF7 /M L/(reference+ategorFM L/(reference2creenM

With the &iel" ($dit&eGt(reference), in a""ition to the title an" summary you put on the pre&eren'e itsel&, you 'an also supply the title to use &or the "ialog. With the list ()ist(reference), you supply both a "ialog title an" t=o stringarray resour'es, one &or the "isplay names, one &or the !alues. 5hese nee" to be in the same or"er S the in"e; o& the 'hosen "isplay name "etermines =hi'h !alue is store" as the pre&eren'e in the 2hared(references. *or e;ample, here are the arrays &or use by the )ist(reference sho=n abo!e,
LNGml version671.-7 encoding67utf-,7NM LresourcesM Lstring-arraF name67cities7M

%%-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

LitemM(hiladelphiaL/itemM LitemM(ittsburghL/itemM LitemMAllentoEn/4ethlehemL/itemM LitemM$rieL/itemM LitemM?eadingL/itemM LitemM2crantonL/itemM LitemM)ancasterL/itemM LitemMAltoonaL/itemM LitemM!arrisburgL/itemM L/string-arraFM Lstring-arraF name67airport codes7M LitemM(!)L/itemM LitemM(I&L/itemM LitemMA4$L/itemM LitemM$?IL/itemM LitemM?=DL/itemM LitemMAV(L/itemM LitemM)%2L/itemM LitemMA""L/itemM LitemM#=&L/itemM L/string-arraFM L/resourcesM

When you bring up the pre&eren'e $0, you start =ith another 'ategory =ith another pair o& pre&eren'e entries,

"igure *-&1 The preference screen of the /ialogs proAectGs preference >

%%%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

5apping the 5e;t Entry @ialog one brings up a te;t entry "ialog S in this 'ase, =ith the prior pre&eren'e entry pre-&ille"-in,

"igure *--1 =diting a text preference

5apping the %ele'tion @ialog one brings up a sele'tion "ialog, sho=ing the "isplay names &rom the one array,

%%0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

"igure *-%1 =diting a list preference

Preferences via "ragments


An"roi" ..0 re!ampe" (reference2creen an" (referenceActivitF. >n the plus si"e, the ne= system looks great, pro!i"ing rapi" a''ess to a large number o& settings,

%%2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

"igure *-01 A 3oneycomb#based PreferenceActivity

>n the minus si"e, the ne= system is not part o& the An"roi" Compatibility Library, an" as su'h 'annot "ire'tly be use" on pre-+oney'omb !ersions o& An"roi". 5hat being sai", it is possible to =ork out a ba'k=ar"s-'ompatible solution, though it may reRuire some re"esign o& your pre&eren'es, i& you ha!e a lot o& them an" ha!e been using neste" (reference2creen elements. 0n &a't, this is pretty mu'h reRuire", as the neste" (reference2creen approa'h looks lousy on +oney'omb "e!i'es.

The Honeycom= , y
0n pre-+oney'omb !ersions o& An"roi", a (referenceActivitF sub'lass =oul" loa" pre&eren'es &rom resour'e &iles, to in"i'ate =hat shoul" go on the s'reen. 0n +oney'omb, a (referenceActivitF sub'lass loa"s pre&eren'e headers &rom resour'e &iles, to in"i'ate =hat shoul" go on the s'reen.

%%7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

Pre.erence He ders
-isually, pre&eren'e hea"ers are not pre&eren'e 'ategories (pla'ing a hea"er o!er a set o& pre&eren'es). ather, pre&eren'e hea"ers are the term &or the maGor 'lusters o& pre&eren'es. 5he hea"ers are liste" on the le&t, =ith the pre&eren'es &or the sele'te" hea"er sho=n on the right, as "epi'te" in the pre'e"ing s'reenshot. %o, instea" o& 'alling add(references9rom?esourcePQ, a +oney'omb (referenceActivitF =ill 'all load!eaders9rom?esourcePQ, pointing to another FML resour'e, this time "es'ribing the pre&eren'e hea"ers. *or e;ample, here is res/Gml/preference headers.Gml (refs/9ragments sample proGe't, &rom the

Lpreference-headers Gmlns:android67http://schemas.android.com/apk/res/android7M Lheader android:fragment67com.commonsEare.android.preffrags.2tock(reference9ragment7 android:title67"riginal7 android:summarF67&he original set from the other eGamples7M LeGtra android:name67resource7 android:value67preferences7 /M L/headerM Lheader android:fragment67com.commonsEare.android.preffrags.2tock(reference9ragment7 android:title67"ther 2tuff7 android:summarF67@ell8 Ee needed to shoE tEo sets here...7M LeGtra android:name67resource7 android:value67preferences>7 /M L/headerM L/preference-headersM

Ea'h LheaderM element in"i'ates the (reference9ragment sub'lass that =ill be "es'ribing the pre&eren'es that belong to the hea"er. 0n a""ition, the LheaderM "es'ribes the title an" summary &or the hea"er, along =ith an optional i'on (android:icon attribute). A LheaderM element may also ha!e one or more LeGtraM 'hil" elements, pro!i"ing a key-!alue pair o& e;tra "ata that a (reference9ragment 'an use &or 'on&iguration. 0n the e;ample sho=n abo!e, ea'h LheaderM element has one LeGtraM element "e&ining the name o& an FML resour'e that =ill hol" the pre&eren'es &or that hea"er. +en'e, the (referenceActivitF is still as short as be&ore, Gust =ith a slightly "i&&erent stru'ture,
%%8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

package com.commonsEare.android.preffragsJ import android.os.4undleJ import android.preference.(referenceActivitFJ import java.util.)istJ public class $dit(references eGtends (referenceActivitF : O"verride public void onBuild(eadersP)istL!eaderM targetQ : load(eaders"rom%esourceP?.Gml.preference headers8 targetQJ ; ;

0nstea" o& "e&ining the hea"ers in on+reatePQ, you o!erri"e an on)oad!eadersPQ metho" an" 'all load!eaders9rom?esourcePQ there.

Pre.erence5r !ments nd Stoc$Pre.erence5r !ment


%o, the pre&eren'e hea"ers point to sub'lasses o& (reference9ragment. 5he Gob o& (reference9ragment is to "o =hat (referenceActivitF =oul" "o in ol"er !ersions o& An"roi" S 'all add(references9rom?esourcePQ to "e&ine the pre&eren'es to be "isplaye" on the right =hen the asso'iate" hea"er is 'li'ke" on the le&t. What is o"" about (reference9ragment is that it reRuires sub'lasses. Consi"ering that the !ast maGority o& su'h &ragments =oul" simply 'all add(references9rom?esourcePQ on'e on a single resour'e, it =oul" seem logi'al to ha!e that built into An"roi", allo=ing sub'lasses o& (reference9ragment &or more 'ompli'ate" 'ases. ?et, that is not presently supporte". >&&i'ial An"roi" samples =oul" ha!e you 'reate one (reference9ragment sub'lass &or ea'h pre&eren'e hea"er, =hi'h seems =aste&ul. Another approa'h is to use 2tock(reference9ragment, a (reference9ragment sub'lass that is implemente" in the (refs/9ragments proGe't but 'an be use" =here!er. 0t assumes that you ha!e a""e" an LeGtraM to the LheaderM i"enti&ying the name o& the pre&eren'e FML resour'e to loa", an" it loa"s it. 2o e;tra sub'lasses reRuire". 5hat is ho= both hea"ers sho=n in the pre!ious se'tion 'an point to the single 2tock(reference9ragment implementation.
%%:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

2tock(reference9ragment

is not espe'ially long, but it "oes employ one tri'k,

package com.commonsEare.android.preffragsJ import android.os.4undleJ import android.preference.(reference9ragmentJ public class 2tock(reference9ragment eGtends (reference9ragment : O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ int res6get$cti!ityPQ .get%esourcesPQ .getIdentifierPget$rgumentsPQ.getStringP7resource7Q8 7Gml78 get$cti!ityPQ.get)ackage&amePQQJ add)references"rom%esourcePresQJ ; ;

5o get at the e;tras, a (reference9ragment 'an 'all getArgumentsPQ, =hi'h returns a 4undle. 0n our 'ase, =e 'an get the resources e;tra !alue !ia getArgumentsPQ.get2tringP7resource7Q. 5he problem is, this is a 2tring, not a resour'e 0@. 0n or"er to 'all add(references9rom?esourcePQ, =e nee" the resour'e 0@ o& the pre&eren'e that =e only kno= by name. 5he tri'k is to use getIdentifierPQ. 5he getIdentifierPQ metho" on the ?esources obGe't S itsel& obtaine" by 'alling get?esourcesPQ on an ActivitF S =ill use re&le'tion to &in" the resour'e 0@ gi!en three pie'es o& in&ormation, 1. 5he name o& the resour'e (in this 'ase, the !alue &rom the arguments)

2. 5he type o& the resour'e (in this 'ase, Gml) .. 5he pa'kage =here this 0@ shoul" resi"e (typi'ally, your o=n pa'kage, obtaine" by 'alling get(ackage%amePQ on an ActivitF)

%0<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

%o, 2tock(reference9ragment uses getIdentifierPQ to 'on!ert the resource e;tra into a resour'e 0@, =hi'h it then uses =ith add(references9rom?esourcePQ. 2ote that getIdentifierPQ is not parti'ularly &ast, sin'e it uses re&le'tion. @o not use this in a tight loop, or in getVieEPQ o& an Adapter, or any pla'e =here it may be 'alle" thousan"s o& times.

Avoidin! "ested Pre.erenceScreens


0n pre-+oney'omb An"roi", i& you ha!e a lot o& pre&eren'es, you might 'onsi"er turning them into neste" (reference2creens. 0t is better, on +oney'omb, to break them out into separate pre&eren'e hea"ers. #artly, this is to ha!e a better user e;perien'e S they 'an "ire'tly see an" a''ess the !arious hea"ers, !ersus ha!ing to =a"e through your pre&eren'es to &in" ones that lea" to neste" (reference2creens. #artly, this is be'ause the neste" (reference2creen $0 "oes not a"opt the +oney'omb look-an"-&eel (e.g., there are no neste" pre&eren'e hea"ers), an" so there =ill be a !isual 'lash.

Intents .or He ders or Pre.erences


0& you ha!e the nee" to 'olle't some pre&eren'es that are beyon" =hat the stan"ar" pre&eren'es 'an han"le, you ha!e some 'hoi'es. >ne is to 'reate a 'ustom (reference. E;ten"ing =ialog(reference to 'reate your o=n (reference implementation is not espe'ially har". +o=e!er, it "oes 'onstrain you to something that 'an &it in a "ialog. Another option is to spe'i&y an LintentM element as a 'hil" o& a LheaderM element. When the user taps on this hea"er, your spe'i&ie" Intent is use" =ith startActivitFPQ, gi!ing you a gate=ay to your o=n a'ti!ity &or 'olle'ting things that are beyon" =hat the pre&eren'e $0 'an han"le. *or e;ample, you 'oul" ha!e the &ollo=ing LheaderM,

%0*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

Lheader android:icon67OdraEable/something7 android:title679ancF 2tuff7 android:summarF67+lick here to transcend Four plane of eGistence7M Lintent android:action67com.commonsEare.android.#5 +32&"# A+&I"%7 /M L/headerM

5hen, so long as you ha!e an a'ti!ity =ith an Lintent-filterM spe'i&ying your "esire" a'tion (com.commonsEare.android.#5 +32&"# A+&I"%), that a'ti!ity =ill get 'ontrol =hen the user taps on the asso'iate" hea"er.

Addin! B c$# rds Comp ti=ility


>& 'ourse, e!erything "es'ribe" abo!e is ni'e an" all, but it only =orks on An"roi" ..0 an" higher. What about the millions o& other An"roi" "e!i'esH Are they 'hoppe" li!erH 2o. *or one thing, 'hoppe" li!er has notoriously ba" 'ellular re'eption. +o=e!er, they =ill ha!e to retreat to the original (referenceActivitF approa'h. %in'e ol"er !ersions o& An"roi" 'annot loa" 'lasses that re&er to other 'lasses or metho"s that are &rom ne=er !ersions o& An"roi", the simplest approa'h is to ha!e t=o (referenceActivitF 'lasses, one ne=, an" one ol". *or e;ample, the (refs/9ragments4+ sample proGe't has all the 'o"e &rom (refs/9ragments, =ith a &e= alterations. +oney'omb-spe'i&i' $dit(references 'lass is rename" $dit(references!+. Another $dit(references 'lass, base" upon our original pre-&ragment implementation, is a""e",
package com.commonsEare.android.preffragsJ import android.os.4undleJ import android.preference.(referenceActivitFJ public class $dit(references eGtends (referenceActivitF : O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ

*irst,

the

%0&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

>sing Preferences

add)references"rom%esourceP?.Gml.preferencesQJ add)references"rom%esourceP?.Gml.preferences>QJ ; ;

+ere, =e take a"!antage o& the &a't that add(references9rom?esourcePQ 'an be 'alle" multiple times to simply 'hain together our t=o pre&eren'e hea"ers7 =orth o& pre&eren'es. An", the options menu 'hoi'e &or opening our (referenceActivitF 'hanges to 'hoose the right one, base" on our 4uild.V$?2I"%.2=H I%& !alue,
; O"verride public boolean onOptionsItemSelectedP#enuItem itemQ : sEitch Pitem.getItemIdPQQ : case $=I& I=: if P4uild.V$?2I"%.2=H I%&L4uild.V$?2I"% +"=$2.!"%$5+"#4Q : start$cti!ityPneE IntentPthis8 $dit(references.classQQJ ; else : start$cti!ityPneE IntentPthis8 $dit(references!+.classQQJ ; ; returnPtrueQJ

+en'e, =e only use the $dit(references!+ 'lass =hen that is kno=n to be sa&e. >ther=ise, =e use the ol"er one.

%0-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1&

+anaging and Accessing !ocal /atabases

%JLite is a !ery popular embe""e" "atabase, as it 'ombines a 'lean %JL inter&a'e =ith a !ery small memory &ootprint an" "e'ent spee". Moreo!er, it is publi' "omain, so e!eryone 'an use it. Lots o& &irms (A"obe, Apple, 8oogle, %un, %ymbian) an" open sour'e proGe'ts (MoKilla, #+#, #ython) all ship pro"u'ts =ith %JLite. *or An"roi", %JLite is Mbake" intoM the An"roi" runtime, so e!ery An"roi" appli'ation 'an 'reate %JLite "atabases. %in'e %JLite uses a %JL inter&a'e, it is &airly straight&or=ar" to use &or people =ith e;perien'e in other %JLbase" "atabases. +o=e!er, its nati!e A#0 is not C@1C, an" C@1C might be too mu'h o!erhea" &or a memory-limite" "e!i'e like a phone, any=ay. +en'e, An"roi" programmers ha!e a "i&&erent A#0 to learn S the goo" ne=s being is that it is not that "i&&i'ult. 5his 'hapter =ill 'o!er the basi's o& %JLite use in the 'onte;t o& =orking on An"roi". 0t by no means is a thorough 'o!erage o& %JLite as a =hole. 0& you =ant to learn more about %JLite an" ho= to use it in en!ironments other than An"roi", a &ine book is 5he @e&initi!e 8ui"e to %JLite by Mi'hael >=ens. Mu'h o& the sample 'o"e sho=n in this 'hapter 'omes &rom the =atabase/+onstants appli'ation. 5his appli'ation presents a list o& physi'al 'onstants, =ith names an" !alues 'ulle" &rom An"roi"7s 2ensor#anager,
%00
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

"igure *-21 The Constants sample application@ as initially launched

?ou 'an pop up a menu to a"" a ne= 'onstant, =hi'h brings up a "ialog to &ill in the name an" !alue o& the 'onstant,

"igure *-71 The Constants sample applicationGs add#constant dialog

%02

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

5he 'onstant is then a""e" to the list. A long-tap on an e;isting 'onstant =ill bring up a 'onte;t menu =ith a M@eleteM option S a&ter 'on&irmation, that =ill "elete the 'onstant. An", o& 'ourse, all o& this is store" in a %JLite "atabase.

A Iuick SI!ite Primer


%JLite, as the name suggests, uses a "iale't o& %JL &or Rueries ( 2$)$+&), "ata manipulation (I%2$?&, et al.), an" "ata "e&inition (+?$A&$ &A4)$, et al.). %JLite has a &e= pla'es =here it "e!iates &rom the %JL-32 stan"ar", no "i&&erent than most %JL "atabases. 5he goo" ne=s is that %JLite is so spa'e-e&&i'ient that the An"roi" runtime 'an in'lu"e all o& %JLite, not some arbitrary subset to trim it "o=n to siKe. 5he biggest "i&&eren'e &rom other %JL "atabases you =ill en'ounter is probably the "ata typing. While you 'an spe'i&y the "ata types &or 'olumns in a +?$A&$ &A4)$ statement, an" =hile %JLite =ill use those as a hint, that is as &ar as it goes. ?ou 'an put =hate!er "ata you =ant in =hate!er 'olumn you =ant. #ut a string in an I%&$D$? 'olumnH %ure: 2o problem: -i'e !ersaH Works too: %JLite re&ers to this as Mmani&est typingM, as "es'ribe" in the "o'umentation, n mani!est typing" the datatype is a property o! the value itsel!" not o! the column in which the value is stored. '(Lite thus allows the user to store any value o! any datatype into any column regardless o! the declared type o! that column.

Start at the Beginning


2o "atabases are automati'ally supplie" to you by An"roi". 0& you =ant to use %JLite, you ha!e to 'reate your o=n "atabase, then populate it =ith your o=n tables, in"e;es, an" "ata.

%07

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

5o 'reate an" open a "atabase, your best option is to 'ra&t a sub'lass o& 2Y)ite"pen!elper. 5his 'lass =raps up the logi' to 'reate an" upgra"e a "atabase, per your spe'i&i'ations, as nee"e" by your appli'ation. ?our sub'lass o& 2Y)ite"pen!elper =ill nee" three metho"s,

5he 'onstru'tor, 'haining up=ar" to the 2Y)ite"pen!elper 'onstru'tor. 5his takes the +onteGt (e.g., an ActivitF), the name o& the "atabase, an optional 'ursor &a'tory (typi'ally, Gust pass null), an" an integer representing the !ersion o& the "atabase s'hema you are using.
on+reatePQ,

=hi'h passes you a 2Y)ite=atabase obGe't that you use to populate =ith tables an" initial "ata, as appropriate.
on3pgradePQ,

=hi'h passes you a 2Y)ite=atabase obGe't an" the ol" an" ne= !ersion numbers, so you 'an &igure out ho= best to 'on!ert the "atabase &rom the ol" s'hema to the ne= one. 5he simplest, albeit least &rien"ly, approa'h is to simply "rop the ol" tables an" 'reate ne= ones.

*or e;ample, here is a =atabase!elper 'lass &rom =atabase/+onstants that, in 'reates a table an" a""s a number o& ro=s, an" in on3pgradePQ M'heatsM by "ropping the e;isting table an" e;e'uting on+reatePQ,
on+reatePQ,
package com.commonsEare.android.constantsJ import import import import import import import android.content.+ontentValuesJ android.content.+onteGtJ android.database.+ursorJ android.database.2Y)$GceptionJ android.database.sUlite.2Y)ite"pen!elperJ android.database.sUlite.2Y)ite=atabaseJ android.hardEare.2ensor#anagerJ

public class =atabase!elper eGtends 2Y)ite"pen!elper : private static final 2tring =A&A4A2$ %A#$67db7J static final 2tring &I&)$67title7J static final 2tring VA)3$67value7J public Data'ase(elperP+onteGt conteGtQ : superPconteGt8 =A&A4A2$ %A#$8 null8 1QJ ; O"verride public void onCreateP2Y)ite=atabase dbQ : db.execS/LP7+?$A&$ &A4)$ constants P id I%&$D$? (?I#A?5 H$5 A3&"I%+?$#$%&8

%08

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

title &$]&8 value ?$A)QJ7QJ +ontentValues cv6neE ContentValuesPQJ cv.putP&I&)$8 7DravitF8 =eath 2tar I7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 =$A&! 2&A? IQJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 $arth7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 $A?&!QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 Jupiter7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 J3(I&$?QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 #ars7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 #A?2QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 #ercurF7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 #$?+3?5QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 #oon7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 #""%QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 %eptune7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 %$(&3%$QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 (luto7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 ()3&"QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 2aturn7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 2A&3?%QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 2un7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 23%QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 &he Island7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 &!$ I2)A%=QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 3ranus7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 3?A%32QJ db.insertP7constants78 &I&)$8 cvQJ cv.putP&I&)$8 7DravitF8 Venus7QJ cv.putPVA)3$8 2ensor#anager.D?AVI&5 V$%32QJ

%0:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

db.insertP7constants78 &I&)$8 cvQJ ; O"verride public void on*pgradeP2Y)ite=atabase db8 int oldVersion8 int neEVersionQ : android.util.)og.wP7+onstants78 73pgrading database8 Ehich Eill destroF all old data7QJ db.execS/LP7=?"( &A4)$ I9 $]I2&2 constants7QJ onCreatePdbQJ ; ;

We =ill take a 'loser look at =hat on+reatePQ is "oing S in terms o& eGec2Y)PQ an" insertPQ 'alls S later in this 'hapter. 5o use your 2Y)ite"pen!elper sub'lass, 'reate an" hol" onto an instan'e o& it. 5hen, =hen you nee" a 2Y)ite=atabase obGe't to "o Rueries or "ata mo"i&i'ations, ask your 2Y)ite"pen!elper to get?eadable=atabasePQ or get@riteable=atabasePQ, "epen"ing upon =hether or not you =ill be 'hanging its 'ontents. *or e;ample, our +onstants4roEser a'ti!ity opens the "atabase in on+reatePQ as part o& "oing a Ruery,
constants+ursor6db .get%eada'leData'asePQ .raw/ueryP72$)$+& I=8 title8 value 7R 79?"# constants "?=$? 45 title78 nullQJ

When you are "one =ith the "atabase (e.g., your a'ti!ity is being 'lose"), simply 'all closePQ on your 2Y)ite"pen!elper to release your 'onne'tion. *or on3pgradePQ to =ork properly, your !ersion numbers &or your "atabase s'hema must in'rease as you mo!e &or=ar". A typi'al pattern is to start =ith 1 an" =ork your =ay up &rom there. 5here are t=o other metho"s you 'an ele't to o!erri"e in your 2Y)ite"pen!elper, i& you &eel the nee", 1. ?ou 'an o!erri"e on"penPQ, to get 'ontrol =hen somebo"y opens this "atabase. $sually, this is not reRuire".

%2<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

2. An"roi" ..0 intro"u'e" on=oEngradePQ, =hi'h =ill be 'alle" i& the 'o"e reRuests an ol"er s'hema than =hat is in the "atabase presently. 5his is the 'on!erse o& on3pgradePQ S i& your !ersion numbers "i&&er, one o& these t=o metho"s =ill be in!oke". %in'e normally you are mo!ing &or=ar" =ith up"ates, you 'an usually skip on=oEngradePQ.

Setting the Table


*or 'reating your tables an" in"e;es, you =ill nee" to 'all eGec2Y)PQ on your 2Y)ite=atabase, pro!i"ing the @@L statement you =ish to apply against the "atabase. 1arring a "atabase error, this metho" returns nothing. %o, &or e;ample, you 'an 'all eGec2Y)PQ to 'reate the constants table, as sho=n in the =atabase!elper on+reatePQ metho",
db.execS/LP7+?$A&$ &A4)$ constants P id I%&$D$? (?I#A?5 H$5 A3&"I%+?$#$%&8 title &$]&8 value ?$A)QJ7QJ

5his =ill 'reate a table, name" constants, =ith a primary key 'olumn name" id that is an auto-in'remente" integer (i.e., %JLite =ill assign the !alue &or you =hen you insert ro=s), plus t=o "ata 'olumns, title (te;t) an" value (a &loat, or MrealM in %JLite terms). %JLite =ill automati'ally 'reate an in"e; &or you on your primary key 'olumn S you 'oul" a"" other in"e;es here !ia some +?$A&$ I%=$] statements, i& you so 'hose to. Most likely, you =ill 'reate tables an" in"e;es =hen you &irst 'reate the "atabase, or possibly =hen the "atabase nee"s upgra"ing to a''ommo"ate a ne= release o& your appli'ation. 0& you "o not 'hange your table s'hemas, you might ne!er "rop your tables or in"e;es, but i& you "o, Gust use eGec2Y)PQ to in!oke =?"( I%=$] an" =?"( &A4)$ statements as nee"e".

%2*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

+akinG /ata
8i!en that you ha!e a "atabase an" one or more tables, you probably =ant to put some "ata in them an" su'h. ?ou ha!e t=o maGor approa'hes &or "oing this. ?ou 'an al=ays use eGec2Y)PQ, Gust like you "i" &or 'reating the tables. 5he eGec2Y)PQ metho" =orks &or any %JL that "oes not return results, so it 'an han"le I%2$?&, 3(=A&$, =$)$&$, et'. Gust &ine. ?our alternati!e is to use the insertPQ, updatePQ, an" deletePQ metho"s on the 2Y)ite=atabase obGe't, =hi'h eliminate mu'h o& the %JL synta; reRuire" to "o basi' operations. *or e;ample, here =e insertPQ a ne= ro= into our constants table,
private void process$ddP=ialog@rapper ErapperQ : +ontentValues values6neE ContentValuesP>QJ values.putP=atabase!elper.&I&)$8 Erapper.getTitlePQQJ values.putP=atabase!elper.VA)3$8 Erapper.getValuePQQJ db.get#rita'leData'asePQ.insertP7constants78 =atabase!elper.&I&)$8 valuesQJ constants+ursor.re-ueryPQJ

5hese metho"s make use o& +ontentValues obGe'ts, =hi'h implement a #apesRue inter&a'e, albeit one that has a""itional metho"s &or =orking =ith %JLite types. *or e;ample, in a""ition to getPQ to retrie!e a !alue by its key, you ha!e getAsIntegerPQ, getAs2tringPQ, an" so &orth. 5he insertPQ metho" takes the name o& the table, the name o& one 'olumn as the Mnull 'olumn ha'kM, an" a +ontentValues =ith the initial !alues you =ant put into this ro=. 5he Mnull 'olumn ha'kM is &or the 'ase =here the +ontentValues instan'e is empty S the 'olumn name" as the Mnull 'olumn ha'kM =ill be e;pli'itly assigne" the !alue %3)) in the %JL I%2$?& statement generate" by insertPQ. 5his is reRuire" "ue to a Ruirk in %JLite7s support &or the %JL I%2$?& statement.

%2&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

5he updatePQ metho" takes the name o& the table, a +ontentValues representing the 'olumns an" repla'ement !alues to use, an optional @!$?$ 'lause, an" an optional list o& parameters to &ill into the @!$?$ 'lause, to repla'e any embe""e" Ruestion marks ( N). %in'e updatePQ only repla'es 'olumns =ith &i;e" !alues, !ersus ones 'ompute" base" on other in&ormation, you may nee" to use eGec2Y)PQ to a''omplish some en"s. 5he @!$?$ 'lause an" parameter list =orks akin to the positional %JL parameters you may be use" to &rom other %JL A#0s. 5he deletePQ metho" =orks akin to updatePQ, taking the name o& the table, the optional @!$?$ 'lause, an" the 'orrespon"ing parameters to &ill into the @!$?$ 'lause. *or e;ample, here =e deletePQ a ro= &rom our constants table, gi!en its ]0@,
private void processDeletePlong roEIdQ : 2tringAB args6:2tring.!alueOfProEIdQ;J db.get#rita'leData'asePQ.deleteP7constants78 7 I=6N78 argsQJ constants+ursor.re-ueryPQJ

What (oes Around@ Comes Around


As =ith I%2$?&, 3(=A&$, an" =$)$&$, you ha!e t=o main options &or retrie!ing "ata &rom a %JLite "atabase using 2$)$+&, 1. ?ou 'an use raEYuerFPQ to in!oke a 2$)$+& statement "ire'tly, or

2. ?ou 'an use UuerFPQ to buil" up a Ruery &rom its 'omponent parts Con&oun"ing matters &urther is the 2Y)iteYuerF4uilder 'lass an" the issue o& 'ursors an" 'ursor &a'tories. Let7s take all o& this one pie'e at a time.

R # Hueries
5he simplest solution, at least in terms o& the A#0, is raEYuerFPQ. %imply 'all it =ith your %JL 2$)$+& statement. 5he 2$)$+& statement 'an in'lu"e positional parametersT the array o& these &orms your se'on" parameter to raEYuerFPQ. %o, =e =in" up =ith,
%2-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

constants+ursor6db .get%eada'leData'asePQ .raw/ueryP72$)$+& I=8 title8 value 7R 79?"# constants "?=$? 45 title78 nullQJ

5he return !alue is a +ursor, =hi'h 'ontains metho"s &or iterating o!er results (see belo=). 0& your Rueries are pretty mu'h Mbake" intoM your appli'ation, this is a !ery straight&or=ar" =ay to use them. +o=e!er, it gets 'ompli'ate" i& parts o& the Ruery are "ynami', beyon" =hat positional parameters 'an really han"le. *or e;ample, i& the set o& 'olumns you nee" to retrie!e is not kno=n at 'ompile time, puttering aroun" 'on'atenating 'olumn names into a 'omma-"elimite" list 'an be annoying...=hi'h is =here UuerFPQ 'omes in.

Re!ul r Hueries
5he UuerFPQ metho" takes the "is'rete pie'es o& a %ELEC5 statement an" buil"s the Ruery &rom them. 5he pie'es, in or"er that they appear as parameters to UuerFPQ, are,

5he name o& the table to Ruery against 5he list o& 'olumns to retrie!e 5he @!$?$ 'lause, optionally in'lu"ing positional parameters 5he list o& !alues to substitute in &or those positional parameters 5he D?"3( 45 'lause, i& any 5he !AVI%D 'lause, i& any 5he "?=$? 45 'lause, i& any

5hese 'an be null =hen they are not nee"e" (e;'ept the table name, o& 'ourse),
2tringAB columns6:7I=78 7inventorF7;J 2tringAB parms6:7snicklefritK7;J

%2%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

+ursor result6db.-ueryP7Eidgets78 columns8 7name6N78 parms8 null8 null8 nullQJ

-sin! Cursors
2o matter ho= you e;e'ute the Ruery, you get a +ursor ba'k. 5his is the An"roi"P%JLite e"ition o& the "atabase 'ursor, a 'on'ept use" in many "atabase systems. With the 'ursor, you 'an,

*in" out ho= many ro=s are in the result set !ia get+ountPQ 0terate o!er the ro=s !ia move&o9irstPQ, move&o%eGtPQ, an"
isAfter)astPQ

*in" out the names o& the 'olumns !ia get+olumn%amesPQ, 'on!ert those into 'olumn numbers !ia get+olumnIndeGPQ, an" get !alues &or the 'urrent ro= &or a gi!en 'olumn !ia metho"s like get2tringPQ, getIntPQ, et'. e-e;e'ute the Ruery that 'reate" the 'ursor !ia reUuerFPQ elease the 'ursor7s resour'es !ia closePQ

*or e;ample, here =e iterate o!er a Eidgets table entries,


+ursor result6 db.raw/ueryP72$)$+& I=8 name8 inventorF 9?"# Eidgets78 nullQJ Ehile PXresult.mo!eTo&extPQQ : int id6result.getIntP-QJ 2tring name6result.getStringP1QJ int inventorF6result.getIntP>QJ ; // do something useful Eith these

result.closePQJ

?ou 'an also =rap a +ursor in a 2imple+ursorAdapter or other implementation, then han" the resulting a"apter to a )istVieE or other sele'tion =i"get. 2ote, though, that i& you are going to use +ursorAdapter or its sub'lasses (like 2imple+ursorAdapter), your result set o& your Ruery must 'ontain an integer 'olumn name" I= that is uniRue &or the result set. 5his

%20

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

Mi"M !alue is then supplie" to metho"s like on)istItem+lickPQ, to i"enti&y =hat item the user 'li'ke" upon in the AdapterVieE. *or e;ample, a&ter retrie!ing the sorte" list o& 'onstants, =e pop those into the )istVieE &or the +onstants4roEser a'ti!ity in Gust a &e= lines o& 'o"e,
)istAdapter adapter6neE SimpleCursor$dapterPthis8 ?.laFout.roE8 constants+ursor8 neE 2tringAB :=atabase!elper.&I&)$8 =atabase!elper.VA)3$;8 neE intAB :?.id.title8 ?.id.value;QJ

Custom CursorAd pters


?ou may re'all &rom an earlier 'hapter that you 'an o!erri"e getVieEPQ in ArraFAdapter to pro!i"e more 'ustom 'ontrol o!er ho= ro=s are "isplaye". +o=e!er, +ursorAdapter an" its sub'lasses ha!e a "e&ault implementation o& getVieEPQ. What getVieEPQ "oes is inspe't the supplie" VieE to re'y'le an", i& it is null, 'alls neEVieEPQ then bindVieEPQ, or Gust 'alls bindVieEPQ i& it is not null. 0& you are e;ten"ing +ursorAdapter S use" &or "isplaying results o& a "atabase or 'ontent pro!i"er Ruery S you shoul" o!erri"e neEVieEPQ an" bindVieEPQ instea" o& getVieEPQ. All this "oes is remo!e your ifPQ test you =oul" ha!e ha" in getVieEPQ an" putting ea'h bran'h o& that test in an in"epen"ent metho", akin to the &ollo=ing,
public VieE newViewP+onteGt conteGt8 +ursor cursor8 VieEDroup parentQ : )aFoutInflater inflater6getLayoutInflaterPQJ VieE roE6inflater.inflateP?.laFout.roE8 nullQJ VieE@rapper Erapper6neE View#rapperProEQJ roE.setTagPErapperQJ returnProEQJ ; public void 'indViewPVieE roE8 +onteGt conteGt8 +ursor cursorQ : VieE@rapper Erapper6PVieE@rapperQroE.getTagPQJ

%22

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

// actual logic to populate roE from +ursor goes here ;

% $in! 3our +#n Cursors


5here may be 'ir'umstan'es in =hi'h you =ant to use your o=n +ursor sub'lass, rather than the sto'k implementation pro!i"e" by An"roi". 0n those 'ases, you 'an use UuerF@ith9actorFPQ an" raEYuerF@ith9actorFPQ that take a 2Y)ite=atabase.+ursor9actorF instan'e as a parameter. 5he &a'tory, as one might e;pe't, is responsible &or 'reating ne= 'ursors !ia its neE+ursorPQ implementation. *in"ing an" implementing a !ali" use &or this &a'ility is le&t as an e;er'ise &or the rea"er. %u&&i'e it to say that you shoul" not nee" to 'reate your o=n 'ursor 'lasses mu'h, i& at all, in or"inary An"roi" "e!elopment.

"lash5 Sounds "aster Than t s


?our "atabase =ill be store" on &lash memory, normally the on-boar" &lash &or the "e!i'e. ea"ing "ata o&& o& &lash is relati!ely Rui'k. While the memory is not espe'ially &ast, there is no Mseek timeM to mo!e har" "ri!e hea"s aroun" like you &in" =ith magneti' me"ia, an" so per&orming a Ruery against a %JLite "atabase =ill ten" to be spee"y. Writing "ata to &lash is another matter entirely. %ometimes, this may happen &airly Rui'kly, on the or"er o& a 'ouple o& millise'on"s. %ometimes, though, it may take hun"re"s o& millise'on"s, e!en &or =riting small amounts o& "ata. Moreo!er, &lash ten"s to get slo=er the more &ull it is, so the spee" your users =ill see !aries e!en more. 5he net result is that you shoul" seriously 'onsi"er "oing all "atabase =rite operations o&& the main appli'ation threa", su'h as !ia an AsFnc&ask, as is

%27

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

"es'ribe" in the 'hapter on threa"s. 5his =ay, the "atabase =rite operations =ill not slo= "o=n your user inter&a'e. 2ote that the emulator beha!es "i&&erently, be'ause it is typi'ally using a &ile on your har" "ri!e &or storing "ata, rather than &lash. While the emulator ten"s to be mu'h slo=er than har"=are &or C#$ an" 8#$ operations, the emulator =ill ten" to be mu'h &aster &or =riting "ata to &lash. +en'e, Gust be'ause you are not seeing any $0 slo="o=ns "ue to "atabase 0P> in the emulator, "o not assume that =ill be the same =hen your 'o"e is running on a real An"roi" "e!i'e.

/ata@ /ata@ =very)here


0& you are use" to "e!eloping &or other "atabases, you are also probably use" to ha!ing tools to inspe't an" manipulate the 'ontents o& the "atabase, beyon" merely the "atabase7s A#0. With An"roi"7s emulator, you ha!e t=o main options &or this. *irst, the emulator is suppose" to bun"le in the sUliteC 'onsole program an" makes it a!ailable &rom the adb shell 'omman". >n'e you are in the emulator7s shell, Gust e;e'ute sUliteC, pro!i"ing it the path to your "atabase &ile. ?our "atabase &ile 'an be &oun" at,
/data/data/Four.app.package/databases/Four-db-name

+ere Four.app.package is the Ca!a pa'kage &or your appli'ation (e.g., com.commonsEare.android) an" Four-db-name is the name o& your "atabase, as supplie" to create=atabasePQ. 5he sUliteC program =orks, an" i& you are use" to poking aroun" your tables using a 'onsole inter&a'e, you are =el'ome to use it. 0& you pre&er something a little bit &rien"lier, you 'an al=ays 'opy the %JLite "atabase o&& the "e!i'e onto your "e!elopment ma'hine, then use a %JLite-a=are 'lient program to putter aroun". 2ote, though, that you are =orking o&& a 'opy o& the "atabaseT i& you =ant your 'hanges to go ba'k to the "e!i'e, you =ill nee" to trans&er the "atabase ba'k o!er.

%28

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+anaging and Accessing !ocal /atabases

5o get the "atabase o&& the "e!i'e, you 'an use the adb pull 'omman" (or the eRui!alent in your 0@E, or the *ile Manager in @@M%), =hi'h takes the path to the on-"e!i'e "atabase an" the lo'al "estination as parameters. 5o store a mo"i&ie" "atabase on the "e!i'e, use adb push, =hi'h takes the lo'al path to the "atabase an" the on-"e!i'e "estination as parameters. >ne o& the most-a''essible %JLite 'lients is the %JLite Manager e;tension &or *ire&o;, as it =orks a'ross all plat&orms.

"igure *-81 the SI!ite +anager "irefox extension

?ou 'an &in" other 'lient tools on the %JLite Web site.

%2:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 11

!everaging 6ava !ibraries

Ca!a has as many, i& not more, thir"-party libraries than any other mo"ern programming language. +ere, Mthir"-party librariesM re&er to the innumerable CA s that you 'an in'lu"e in a ser!er or "esktop Ca!a appli'ation S the things that the Ca!a %@Ds themsel!es "o not pro!i"e. 0n the 'ase o& An"roi", the @al!ik -M at its heart is not pre'isely Ca!a, an" =hat it pro!i"es in its %@D is not pre'isely the same as any tra"itional Ca!a %@D. 5hat being sai", many Ca!a thir"-party libraries still pro!i"e 'apabilities that An"roi" la'ks nati!ely an" there&ore may be o& use to you in your proGe't, &or the ones you 'an get =orking =ith An"roi"7s &la!or o& Ca!a. 5his 'hapter e;plains =hat it =ill take &or you to le!erage su'h libraries an" the limitations on An"roi"7s support &or arbitrary thir"-party 'o"e.

Ants and 6ars


?ou ha!e t=o 'hoi'es &or integrating thir"-party 'o"e into your proGe't, use sour'e 'o"e, or use pre-pa'kage" CA s. 0& you 'hoose to use their sour'e 'o"e, all you nee" to "o is 'opy it into your o=n sour'e tree (un"er src/ in your proGe't), so it 'an sit alongsi"e your e;isting 'o"e, then let the 'ompiler per&orm its magi'.

%7*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

!everaging 6ava !ibraries

0& you 'hoose to use an e;isting CA , perhaps one &or =hi'h you "o not ha!e the sour'e 'o"e, you =ill nee" to tea'h your buil" 'hain ho= to use the CA . *irst, pla'e the CA in the libs/ "ire'tory in your An"roi" proGe't. 5hen, i& you are using an 0@E, you probably nee" to a"" the CA to your buil" path (Ant =ill automati'ally pi'k up all CA s &oun" in libs/) S this is "e&initely reRuire" &or E'lipse. An" that7s it. A""ing thir"-party 'o"e to your An"roi" appli'ation is &airly easy. 8etting to a'tually work may be some=hat more 'ompli'ate", ho=e!er.

The ,uter !imits


2ot all a!ailable Ca!a 'o"e =ill =ork =ell =ith An"roi". 5here are a number o& &a'tors to 'onsi"er, in'lu"ing,

*xpected Platform AP8s, @oes the 'o"e assume a ne=er C-M than the one An"roi" is base" onH >r, "oes the 'o"e assume the e;isten'e o& Ca!a A#0s that ship =ith C2%E but not =ith An"roi", su'h as %=ingH $i<e, E;isting Ca!a 'o"e "esigne" &or use on "esktops or ser!ers nee" not =orry too mu'h about on-"isk siKe, or, to some e;tent, e!en in- AM siKe. An"roi", o& 'ourse, is short on both. $sing thir"party Ca!a 'o"e, parti'ularly =hen pre-pa'kage" as CA s, may balloon the siKe o& your appli'ation. Performance, @oes the Ca!a 'o"e e&&e'ti!ely assume a mu'h more po=er&ul C#$ than =hat you may &in" on many An"roi" "e!i'esH Cust be'ause a "esktop 'an run it =ithout issue "oes not mean your a!erage mobile phone =ill han"le it =ell. 8nterface, @oes the Ca!a 'o"e assume a 'onsole inter&a'eH >r is it a pure A#0 that you 'an =rap your o=n inter&a'e aroun"H >perating %ystem, @oes the Ca!a 'o"e assume the e;isten'e o& 'ertain 'onsole programsH @oes the Ca!a 'o"e assume it 'an use a Win"o=s @LLH
%7&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!everaging 6ava !ibraries

Language -ersion, Was the CA 'ompile" =ith an ol"er !ersion o& Ca!a (1.<.2 or ol"er)H Was the CA 'ompile" =ith a "i&&erent 'ompiler than the o&&i'ial one &rom %un (e.g., 8CC)H @epen"en'ies, @oes the Ca!a 'o"e "epen" on other thir"-party CA s that might ha!e some o& these problems as =ellH @oes the Ca!a 'o"e "epen" upon thir"-party libraries (e.g., the org.Gson C%>2 library) that are built into An"roi", but the thir" party e;pe'ts a "i&&erent !ersion o& that libraryH

>ne tri'k &or a""ressing some o& these 'on'erns is to use open sour'e Ca!a 'o"e, an" a'tually =ork =ith the 'o"e to make it more An"roi"-&rien"ly. *or e;ample, i& you are only using 10L o& the thir"-party library, maybe it7s =orth=hile to re'ompile the subset o& the proGe't to be only =hat you nee", or at least remo!ing the unne'essary 'lasses &rom the CA . 5he &ormer approa'h is sa&er, in that you get 'ompiler help to make sure you are not "is'ar"ing some essential pie'e o& 'o"e, though it may be more te"ious to "o.

"ollo)ing the Script


$nlike other mobile "e!i'e operating systems, An"roi" has no restri'tions on =hat you 'an run on it, so long as you 'an "o it in Ca!a using the @al!ik -M. 5his in'lu"es in'orporating your o=n s'ripting language into your appli'ation, something that is e;pressly prohibite" on some other "e!i'es. >ne possible Ca!a s'ripting language is 1ean%hell. 1ean%hell gi!es you Ca!a'ompatible synta; =ith impli'it typing an" no 'ompilation reRuire". %o, to a"" 1ean%hell s'ripting, you nee" to put the 1ean%hell interpreter7s CA &ile in your libs/ "ire'tory. 5he 2.0b< CA a!ailable &or "o=nloa" &rom the 1ean%hell site, un&ortunately, "oes not =ork out o& the bo; =ith the An"roi" 0.3 an" ne=er %@Ds, perhaps "ue to the 'ompiler that =as use" to buil" it. 0nstea", you shoul" probably 'he'k out the sour'e 'o"e &rom %ub!ersion an" e;e'ute ant jarcore to buil" it, then 'opy the resulting CA (in 1ean%hell7s dist/ "ire'tory) to your o=n proGe't7s libs/. >r, Gust use the

%7-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!everaging 6ava !ibraries

1ean%hell CA that a''ompanies the sour'e 'o"e &or this book, up on the CommonsWare site, in the Java/And2hell proGe't. *rom there, using 1ean%hell on An"roi" is no "i&&erent than using 1ean%hell in any other Ca!a en!ironment, 1. Create an instan'e o& the 1ean%hell Interpreter 'lass

2. %et any 6globals9 &or the s'ript[s use !ia InterpreterSsetPQ .. Call InterpreterSevalPQ to run the s'ript an", optionally, get the result o& the last statement *or e;ample, here is the FML layout &or the =orl"[s smallest 1ean%hell 0@E,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L4utton android:id67ORid/eval7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:teGt67DoX7 android:on+lick67go7 /M L$dit&eGt android:id67ORid/script7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:single)ine67false7 android:gravitF67top7 /M L/)inear)aFoutM

Couple that =ith the &ollo=ing a'ti!ity implementation,


package com.commonsEare.android.andshellJ import import import import import import import android.app.ActivitFJ android.app.Alert=ialogJ android.os.4undleJ android.vieE.VieEJ android.Eidget.$dit&eGtJ android.Eidget.&oastJ bsh.InterpreterJ

%7%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!everaging 6ava !ibraries

public class #ainActivitF eGtends ActivitF : private Interpreter i6neE InterpreterPQJ O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ ; public void goPVieE vQ : $dit&eGt script6P$dit&eGtQfindViewByIdP?.id.scriptQJ 2tring src6script.getTextPQ.toStringPQJ trF : i.setP7conteGt78 #ainActivitF.thisQJ i.e!alPsrcQJ ; catch Pbsh.$val$rror eQ : Alert=ialog.4uilder builder6 neE Alert=ialog.BuilderP#ainActivitF.thisQJ builder .setTitleP7$GceptionX7Q .setMessagePe.toStringPQQ .set)ositi!eButtonP7"H78 nullQ .showPQJ ; ; ;

Compile an" run it (in'lu"ing in'orporating the 1ean%hell CA as mentione" abo!e), an" install it on the emulator. *ire it up, an" you get a tri!ial 0@E, =ith a large te;t area &or your s'ript an" a big M8o:M button to e;e'ute it,

%70

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!everaging 6ava !ibraries

"igure *-:1 The AndShell BeanShell /= import android.Eidget.&oastJ &oast.makeTextPconteGt8 7!ello8 EorldX78 &oast.)$%D&! )"%DQ.showPQJ

2ote the use o& conteGt to re&er to the a'ti!ity =hen making the &oast. 5hat is the global set by the a'ti!ity to re&eren'e ba'k to itsel&. ?ou 'oul" 'all this global !ariable anything you =ant, so long as the setPQ 'all an" the s'ript 'o"e use the same name. 5hen, 'li'k the 8o: button, an" you get,

%72

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!everaging 6ava !ibraries

"igure *%<1 The AndShell BeanShell /=@ executing some code

An" no=, some 'a!eats... *irst, not all s'ripting languages =ill =ork. *or e;ample, those that implement their o=n &orm o& Gust-in-time (C05) 'ompilation, generating Ca!a byte'o"es on the &ly, =oul" probably ha!e to be augmente" to generate @al!ik -M byte'o"es instea" o& those &or sto'k Ca!a implementations. %impler languages that e;e'ute o&& o& parse" s'ripts, 'alling Ca!a re&le'tion A#0s to 'all ba'k into 'ompile" 'lasses, =ill likely =ork better. E!en there, though, not e!ery &eature o& the language may =ork, i& it relies upon some &a'ility in a tra"itional Ca!a A#0 that "oes not e;ist in @al!ik S &or e;ample, there 'oul" be stu&& hi""en insi"e 1ean%hell or the a""-on CA s that "oes not =ork on to"ay[s An"roi". %e'on", s'ripting languages =ithout C05 =ill ine!itably be slo=er than 'ompile" @al!ik appli'ations. %lo=er may mean users e;perien'e sluggishness. %lo=er "e&initely means more battery li&e is 'onsume" &or the same amount o& =ork. %o, buil"ing a =hole An"roi" appli'ation in 1ean%hell, simply be'ause you &eel it is easier to program in, may 'ause your users to be unhappy.

%77

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!everaging 6ava !ibraries

5hir", s'ripting languages that e;pose the =hole Ca!a A#0, like 1ean%hell, 'an pretty mu'h "o anything the un"erlying An"roi" se'urity mo"el allo=s. %o, i& your appli'ation has the ?$A= +"%&A+&2 permission, e;pe't any 1ean%hell s'ripts your appli'ation runs to ha!e the same permission. Last, but 'ertainly not least, is that language interpreter CA s ten" to be...portly. 5he 1ean%hell CA use" in this e;ample is 200D1. 5hat is not ri"i'ulous, 'onsi"ering =hat it "oes, but it =ill make appli'ations that use 1ean%hell that mu'h bigger to "o=nloa", take up that mu'h more spa'e on the "e!i'e, et'.

Cevie)ing the Script


%in'e this 'hapter 'o!ers s'ripting in An"roi", you may be intereste" to kno= that you ha!e options beyon" embe""ing 1ean%hell "ire'tly in your proGe't. %ome e;periments ha!e been 'on"u'te" =ith other C-M-base" programming languages, su'h as C uby an" Cython. At present, their support &or An"roi" is in'omplete, but progress is being ma"e. 1eyon" that, though, there is the %'ripting Layer &or An"roi" (%L<A). %L<A allo=s you to =rite s'ripts in a =i"e range o& s'ripting languages, beyon" 1ean%hell, su'h as,

#erl #ython C uby Lua Ca!as'ript (implemente" !ia interpreter =ritten in Ca!a) #+# hino, the MoKilla Ca!as'ript

%78

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

!everaging 6ava !ibraries

5hese s'ripts are not &ull-&le"ge" appli'ations, though the %L<A team is =orking on allo=ing you to turn them into A#D &iles 'omplete =ith basi' $0s. *or on-"e!i'e "e!elopment, %L<A is a &ine 'hoi'e.

%7:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 12

Communicating via the nternet

5he e;pe'tation is that most, i& not all, An"roi" "e!i'es =ill ha!e built-in 0nternet a''ess. 5hat 'oul" be Wi*i, 'ellular "ata ser!i'es (E@8E, .8, et'.), or possibly something else entirely. egar"less, most people S or at least those =ith a "ata plan or Wi*i a''ess S =ill be able to get to the 0nternet &rom their An"roi" phone. 2ot surprisingly, the An"roi" plat&orm gi!es "e!elopers a =i"e range o& =ays to make use o& this 0nternet a''ess. %ome o&&er high-le!el a''ess, su'h as the integrate" WebDit bro=ser 'omponent =e sa= in an earlier 'hapter. 0& you =ant, you 'an "rop all the =ay "o=n to using ra= so'kets. >r, in bet=een, you 'an le!erage A#0s S both on-"e!i'e an" &rom .r"-party CA s S that gi!e you a''ess to spe'i&i' proto'ols, +55#, FM##, %M5#, an" so on. 5he emphasis o& this book is on the higher-le!el &orms o& a''ess, the WebDit 'omponent an" 0nternet-a''ess A#0s, as busy 'o"ers shoul" be trying to reuse e;isting 'omponents !ersus rolling one7s o=n on-the-=ire proto'ol =here!er possible.

C=ST and Celaxation


An"roi" "oes not ha!e built-in %>A# or FML- #C 'lient A#0s. +o=e!er, it "oes ha!e the Apa'he +ttpClient library bake" in. ?ou 'an either layer a %>A#PFML- #C layer atop this library, or use it MstraightM &or a''essing E%5-style Web ser!i'es. *or the purposes o& this book, M E%5-style Web
%8*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

ser!i'esM is "e&ine" as Msimple +55# reRuests &or or"inary $ Ls o!er the &ull range o& +55# !erbs, =ith &ormatte" payloa"s (FML, C%>2, et'.) as responsesM. More e;pansi!e tutorials, *AJs, an" +>W5>s 'an be &oun" at the +ttpClient Web site. +ere, =e7ll 'o!er the basi's, =hile 'he'king the =eather.

HTTP +per tions vi Ap che HttpClient


5he &irst step to using +ttpClient is, not surprisingly, to 'reate an !ttp+lient obGe't. 5he 'lient obGe't han"les all +55# reRuests upon your behal&. %in'e !ttp+lient is an inter&a'e, you =ill nee" to a'tually instantiate some implementation o& that inter&a'e, su'h as =efault!ttp+lient. 5hose reRuests are bun"le" up into !ttp?eUuest instan'es, =ith "i&&erent !ttp?eUuest implementations &or ea'h "i&&erent +55# !erb (e.g., !ttpDet &or +55# D$& reRuests). ?ou 'reate an !ttp?eUuest implementation instan'e, &ill in the $ L to retrie!e an" other 'on&iguration "ata (e.g., &orm !alues i& you are "oing an +55# ("2& !ia !ttp(ost), then pass the metho" to the 'lient to a'tually make the +55# reRuest !ia eGecutePQ. What happens at this point 'an be as simple or as 'ompli'ate" as you =ant. ?ou 'an get an !ttp?esponse obGe't ba'k, =ith response 'o"e (e.g,. >-- &or >D), +55# hea"ers, an" the like. >r, you 'an use a &la!or o& eGecutePQ that takes a ?esponse!andlerL2tringM as a parameter S the net result there being that eGecutePQ returns Gust the 2tring representation o& the response bo"y. 0n pra'ti'e, this is not a re'ommen"e" approa'h, be'ause you really shoul" be 'he'king your +55# response 'o"es &or errors. +o=e!er, &or tri!ial appli'ations, like book e;amples, the ?esponse!andlerL2tringM approa'h =orks Gust &ine. *or e;ample, let7s take a look at the Internet/@eather sample proGe't. 5his implements an a'ti!ity that retrie!es =eather "ata &or your 'urrent lo'ation &rom the 2ational Weather %er!i'e (@BT*, this probably only =orks &or geographi' lo'ations in the $%). 5hat "ata is 'on!erte" into an +5ML page,
%8&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

=hi'h is poure" into a @ebHit =i"get &or "isplay. ebuil"ing this "emo using a )istVieE is le&t as an e;er'ise &or the rea"er. Also, sin'e this sample is relati!ely long, =e =ill only sho= rele!ant pie'es o& the Ca!a 'o"e here in this 'hapter, though you 'an al=ays "o=nloa" the &ull sour'e &rom the CommonsWare Web site. 5o make this a bit more interesting, =e use the An"roi" lo'ation ser!i'es to &igure out =here =e are...sort o&. 5he &ull "etails o& ho= that =orks is "es'ribe" in the 'hapter on lo'ation ser!i'es. 0n the on?esumePQ metho", =e toggle on lo'ation up"ates, so =e =ill be in&orme" =here =e are no= an" =hen =e mo!e a signi&i'ant "istan'e (10km). When a lo'ation is a!ailable S either at the start or base" on mo!ement S =e retrie!e the 2ational Weather %er!i'e "ata !ia our update9orecastPQ metho",
private void update"orecastP)ocation locQ : 2tring url62tring.formatPformat8 loc.getLatitudePQ8 loc.getLongitudePQQJ !ttpDet get#ethod6neE (ttp etPurlQJ trF : ?esponse!andlerL2tringM response!andler6neE Basic%esponse(andlerPQJ 2tring response4odF6client.executePget#ethod8 response!andlerQJ 'uild"orecastsPresponse4odFQJ 2tring page6generate)agePQJ broEser.loadData#ithBase*%LPnull8 page8 7teGt/html78 73&9-,78 nullQJ ; catch P&hroEable tQ : android.util.)og.eP7@eather=emo78 7$Gception fetching data78 tQJ &oast .makeTextPthis8 7?eUuest failed: 7Rt.toStringPQ8 &oast.)$%D&! )"%DQ .showPQJ ;

5he update9orecastPQ metho" takes a )ocation as a parameter, obtaine" &rom the lo'ation up"ate pro'ess. *or no=, all you nee" to kno= is that )ocation sports get)atitudePQ an" get)ongitudePQ metho"s that return the latitu"e an" longitu"e o& the "e!i'e7s position, respe'ti!ely.
%8-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

We hol" the $ L to the 2ational Weather %er!i'e FML in a string resour'e, an" pour in the latitu"e an" longitu"e at runtime. 8i!en our !ttp+lient obGe't 'reate" in on+reatePQ, =e populate an !ttpDet =ith that 'ustomiKe" $ L, then e;e'ute that metho". 8i!en the resulting FML &rom the E%5 ser!i'e, =e buil" the &ore'ast +5ML page (see belo=) an" pour that into the @ebHit =i"get. 0& the !ttp+lient blo=s up =ith an e;'eption, =e pro!i"e that error as a &oast. 2ote that =e also shut "o=n the !ttp+lient obGe't in on=estroFPQ.

P rsin! Responses
5he response you get =ill be &ormatte" using some system S +5ML, FML, C%>2, =hate!er. 0t is up to you, o& 'ourse, to pi'k out =hat in&ormation you nee" an" "o something use&ul =ith it. 0n the 'ase o& the @eather=emo, =e nee" to e;tra't the &ore'ast time, temperature, an" i'on (in"i'ating sky 'on"itions an" pre'ipitation) an" generate an +5ML page &rom it. An"roi" in'lu"es,

5hree FML parsers, the tra"itional W.C @>M (org.ECc.dom), a %AF parser (org.Gml.saG), an" the FML pull parser "is'usse" in the 'hapter on resour'es A C%>2 parser (org.json)

?ou are also =el'ome to use thir"-party Ca!a 'o"e, =here possible, to han"le other &ormats, su'h as a "e"i'ate" %%PAtom parser &or a &ee" rea"er. 5he use o& thir"-party Ca!a 'o"e is "is'usse" in a separate 'hapter. *or @eather=emo, =e use the W.C @>M parser in our build9orecastsPQ metho",
void 'uild"orecastsP2tring raEQ throEs $Gception : =ocument4uilder builder6=ocument4uilder9actorF .newInstancePQ .newDocumentBuilderPQJ =ocument doc6builder.parsePneE InputSourcePneE String%eaderPraEQQQJ %ode)ist times6doc.get+lementsByTag&ameP7start-valid-time7QJ

%8%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

for Pint i6-JiLtimes.getLengthPQJiRRQ : $lement time6P$lementQtimes.itemPiQJ 9orecast forecast6neE "orecastPQJ forecasts.addPforecastQJ forecast.setTimePtime.get"irstChildPQ.get&odeValuePQQJ ; %ode)ist temps6doc.get+lementsByTag&ameP7value7QJ for Pint i6-JiLtemps.getLengthPQJiRRQ : $lement temp6P$lementQtemps.itemPiQJ 9orecast forecast6forecasts.getPiQJ ; forecast.setTempPneE IntegerPtemp.get"irstChildPQ.get&odeValuePQQQJ

%ode)ist icons6doc.get+lementsByTag&ameP7icon-link7QJ for Pint i6-JiLicons.getLengthPQJiRRQ : $lement icon6P$lementQicons.itemPiQJ 9orecast forecast6forecasts.getPiQJ forecast.setIconPicon.get"irstChildPQ.get&odeValuePQQJ ; ;

5he 2ational Weather %er!i'e FML &ormat is...'uriously stru'ture", relying hea!ily on seRuential position in lists !ersus the more obGe't-oriente" style you &in" in &ormats like %% or Atom. 5hat being sai", =e 'an take a &e= liberties an" simpli&y the parsing some=hat, taking a"!antage o& the &a't that the elements =e =ant (start-valid-time &or the &ore'ast time, value &or the temperature, an" icon-link &or the i'on $ L) are all uniRue =ithin the "o'ument. 5he +5ML 'omes in as an Input2tream an" is &e" into the @>M parser. *rom there, =e s'an &or the start-valid-time elements an" populate a set o& 9orecast mo"els using those start times. 5hen, =e &in" the temperature value elements an" icon-link $ Ls an" &ill those in to the 9orecast obGe'ts. 0n turn, the generate(agePQ metho" 'reates a ru"imentary +5ML table =ith the &ore'asts,
2tring generate)agePQ : 2tring4uilder buf?esult6neE StringBuilderP7LhtmlMLbodFMLtableM7QJ

%80

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

buf?esult.appendP7LtrMLth Eidth6T7.-\T7M&imeL/thM7R 7LthM&emperatureL/thMLthM9orecastL/thML/trM7QJ for P9orecast forecast : forecastsQ : buf?esult.appendP7LtrMLtd align6T7centerT7M7QJ buf?esult.appendPforecast.getTimePQQJ buf?esult.appendP7L/tdMLtd align6T7centerT7M7QJ buf?esult.appendPforecast.getTempPQQJ buf?esult.appendP7L/tdMLtdMLimg src6T77QJ buf?esult.appendPforecast.getIconPQQJ buf?esult.appendP7T7ML/tdML/trM7QJ ; buf?esult.appendP7L/tableML/bodFML/htmlM7QJ returnPbuf?esult.toStringPQQJ ;

5he result looks like this,

"igure *%*1 The Weather/emo sample application

Stu.. To Consider
0& you nee" to use %%L, bear in min" that the "e&ault !ttp+lient setup "oes not in'lu"e %%L support. Mostly, this is be'ause you nee" to "e'i"e ho= to
%82

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

han"le %%L 'erti&i'ate presentation S "o you blin"ly a''ept all 'erti&i'ates, e!en sel&-signe" or e;pire" onesH >r "o you =ant to ask the user i& they really =ant to use some strange 'erti&i'atesH %imilarly, !ttp+lient, by "e&ault, is "esigne" &or single-threa"e" use. 0& you =ill be using !ttp+lient &rom some other pla'e =here multiple threa"s might be an issue, you 'an rea"ily set up !ttp+lient to support multiple threa"s. *or these sorts o& topi's, you are best ser!e" by 'he'king out the +ttpClient Web site &or "o'umentation an" support.

AndroidHttpClient
%tarting in An"roi" 2.2 (A#0 le!el 8), you 'an use the Android!ttp+lient 'lass, &oun" in the android.net.http pa'kage. 5his is an implementation o& the !ttp+lient inter&a'e, like =efault!ttp+lient. +o=e!er, it is pre'on&igure" =ith settings that the 'ore An"roi" team &eels make sense &or the plat&orm. What you gain is,

%%L management A "ire't =ay to spe'i&y the user agent string S this is supplie" in your 'all to the stati' neEInstancePQ metho" to get an instan'e o&
Android!ttp+lient

$tility metho"s &or =orking =ith material 'ompresse" !ia 8Q0#, &or parsing "ates in +55# hea"ers, et'.

What you lose is automati' 'ookie storage. A regular =efault!ttp+lient =ill 'a'he 'ookies in memory an" use them on subseRuent reRuests =here they are nee"e". Android!ttp+lient "oes not. 5here are =ays to &i; that, by using an !ttp+onteGt obGe't, as is "es'ribe" in the Android!ttp+lient "o'umentation.

%87

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

Also, Android!ttp+lient pre!ents you &rom using it on the main appli'ation threa" S reRuests 'an only be ma"e on a ba'kgroun" threa". 5his is a &eature, e!en i& some people might 'onsi"er it to be a bug. %in'e this 'lass is only a!ailable in An"roi" 2.2 an" beyon", it may not make sense to "o mu'h =ith it until su'h time as you are only supporting A#0 le!el 8 or higher.

!everaging nternet#A)are Android Components


Where!er possible, aim to use built-in An"roi" 'omponents that 'an han"le your 0nternet a''ess &or you. %u'h 'omponents =ill ha!e been &airly rigorously teste" an" are more likely to han"le e"ge 'ases =ell, su'h as "ealing =ith users on Wi*i =ho mo!e out o& range o& the a''ess point an" &ail o!er to mobile "ata 'onne'tions (e.g., .8). *or e;ample, the @ebVieE =i"get (intro"u'e" in a pre!ious 'hapter) an" the #apVieE =i"get ('o!ere" in a later 'hapter) both han"le 0nternet a''ess &or you. While you still nee" the 025E 2E5 permission, you "o not ha!e to per&orm +55# reRuests or the like yoursel&. 5his se'tion outlines some other =ays you 'an take a"!antage o& built-in 0nternet 'apability.

Do#nlo din! 5iles


An"roi" 2.. has intro"u'e" a =oEnload#anager, "esigne" to han"le a lot o& the 'omple;ities o& "o=nloa"ing larger &iles, su'h as,

@etermining =hether the user is on Wi*i or mobile "ata, an" i& so, =hether the "o=nloa" shoul" o''ur +an"ling =hen the user, pre!iously on Wi*i, mo!es out o& range o& the a''ess point an" M&ails o!erM to mobile "ata Ensuring the "e!i'e stays a=ake =hile the "o=nloa" pro'ee"s
%88

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

=oEnload#anager

itsel& is less 'ompli'ate" than the alternati!e o& =riting all o& it yoursel&. +o=e!er, it "oes present a &e= 'hallenges. 0n this se'tion, =e =ill e;amine the Internet/=oEnload sample proGe't that uses =oEnload#anager.

The Permissions
5o use =oEnload#anager, you =ill nee" to hol" the I%&$?%$& permission. @epen"ing on =here you ele't to "o=nloa" the &ile, you may also nee" the @?I&$ $]&$?%A) 2&"?AD$ permission. +o=e!er, at the time o& this =riting, i& you la'k su&&i'ient permissions, you may get an error 'omplaining that you are missing A++$22 A)) ="@%)"A=2. 5his appears to be a bug in the =oEnload#anager implementation S it shoul" be 'omplaining about I%&$?%$& an"Por @?I&$ $]&$?%A) 2&"?AD$. ?ou "o not nee" to hol" the A++$22 A)) ="@%)"A=2 permission, =hi'h is not e!en "o'umente" as o& An"roi" ..0. *or e;ample, here is the mani&est &or the Internet/=oEnload appli'ation,
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.doEnload7 android:version+ode6717 android:version%ame671.-7M LX-- Luses-permission android:name67android.permission.A++$22 A)) ="@%)"A=27 /M --M Luses-permission android:name67android.permission.I%&$?%$&7/M Luses-permission android:name67android.permission.@?I&$ $]&$?%A) 2&"?AD$7/M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67=oEnload=emo7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

%8:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

The ) yout
>ur sample appli'ation has a simple layout, 'onsisting o& three buttons,

>ne to ki'k o&& a "o=nloa" >ne to Ruery the status o& a "o=nloa" >ne to "isplay a system-supplie" a'ti!ity 'ontaining the roster o& "o=nloa"e" &iles

LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L4utton android:id67ORid/start7 android:teGt672tart =oEnload7 android:laFout Eidth67fill parent7 android:laFout height67-dip7 android:laFout Eeight6717 android:on+lick67start=oEnload7 /M L4utton android:id67ORid/UuerF7 android:teGt67YuerF 2tatus7 android:laFout Eidth67fill parent7 android:laFout height67-dip7 android:laFout Eeight6717 android:on+lick67UuerF2tatus7 android:enabled67false7 /M L4utton android:teGt67VieE )og7 android:laFout Eidth67fill parent7 android:laFout height67-dip7 android:laFout Eeight6717 android:on+lick67vieE)og7 /M L/)inear)aFoutM

ReIuestin! the Do#nlo d


5o ki'k o&& a "o=nloa", =e &irst nee" to get a''ess to the =oEnload#anager. 5his is a so-'alle" Msystem ser!i'eM. ?ou 'an 'all get2Fstem2ervicePQ on any a'ti!ity (or other +onteGt), pro!i"e it the i"enti&ier o& the system ser!i'e you
%:<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

=ant, an" re'ei!e the system ser!i'e obGe't ba'k. +o=e!er, sin'e get2Fstem2ervicePQ supports a =i"e range o& these obGe'ts, you nee" to 'ast it to the proper type &or the ser!i'e you reRueste". %o, &or e;ample, here is a line &rom on+reatePQ o& the =oEnload=emo a'ti!ity =here =e get the =oEnload#anager,
mgr6P=oEnload#anagerQgetSystemSer!iceP="@%)"A= 2$?VI+$QJ

Most o& these managers ha!e no closePQ or releasePQ or goAEaF(leasePQ sort o& metho"s S you 'an Gust use them an" let garbage 'olle'tion take 'are o& 'leaning them up. 8i!en the manager, =e 'an no= 'all an enUueuePQ metho" to reRuest a "o=nloa". 5he name is rele!ant S "o not assume that your "o=nloa" =ill begin imme"iately, though o&ten times it =ill. 5he enUueuePQ metho" takes a =oEnload#anager.?eUuest obGe't as a parameter. 5he ?eUuest obGe't uses the buil"er pattern, in that most metho"s return the ?eUuest itsel&, so you 'an 'hain a series o& 'alls together =ith less typing. *or e;ample, the top-most button in our layout is tie" to a start=oEnloadPQ metho" in =oEnload=emo, sho=n belo=,
public void startDownloadPVieE vQ : 3ri uri63ri.parseP7http://commonsEare.com/misc/test.mp<7QJ $nvironment .get+xternalStorage)u'licDirectory P$nvironment.=I?$+&"?5 ="@%)"A=2Q .mkdirsPQJ last=oEnload6 mgr.en-ueuePneE =oEnload#anager.%e-uestPuriQ .set$llowed&etworkTypesP=oEnload#anager.?eUuest.%$&@"?H @I9I W =oEnload#anager.?eUuest.%$&@"?H #"4I)$Q .set$llowedO!er%oamingPfalseQ .setTitleP7=emo7Q .setDescriptionP72omething useful. %o8 reallF.7Q .setDestinationIn+xternal)u'licDir P$nvironment.=I?$+&"?5 ="@%)"A =28 7test.mp<7QQJ v.set+na'ledPfalseQJ

%:*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

findViewByIdP?.id.UuerFQ.set+na'ledPtrueQJ ;

We are "o=nloa"ing a sample M#< &ile, an" =e =ant to "o=nloa" it to the e;ternal storage area. 5o "o the latter, =e are using get$Gternal2torage(ublic=irectorFPQ on $nvironment, =hi'h gi!es us a "ire'tory suitable &or storing a 'ertain 'lass o& 'ontent. 0n this 'ase, =e are going to store the "o=nloa" in the $nvironment.=I?$+&"?5 ="@%)"A=2, though =e 'oul" Gust as easily ha!e 'hosen $nvironment.=I?$+&"?5 #"VI$2, sin'e =e are "o=nloa"ing a !i"eo 'lip. 2ote that the 9ile obGe't returne" by get$Gternal2torage(ublic=irectorFPQ may point to a not-yet-'reate" "ire'tory, =hi'h is =hy =e 'all mkdirsPQ on it, to ensure the "ire'tory e;ists. We then 'reate the =oEnload#anager.?eUuest obGe't, =ith the &ollo=ing attributes,

We are "o=nloa"ing the spe'i&i' $ L =e =ant, 'ourtesy o& the 3ri supplie" to the ?eUuest 'onstru'tor We are =illing to use either mobile "ata or Wi*i &or the "o=nloa" (setAlloEed%etEork&FpesPQ), but =e "o not =ant the "o=nloa" to in'ur roaming 'harges (setAlloEed"ver?oamingPQ) We =ant the &ile "o=nloa"e" as test.mp< in the "o=nloa"s area on the e;ternal storage (set=estinationIn$Gternal(ublic=irPQ)

We also pro!i"e a name ( set&itlePQ) an" "es'ription (set=escriptionPQ), =hi'h are use" as part o& the noti&i'ation "ra=er entry &or this "o=nloa". 5he user =ill see these =hen they sli"e "o=n the "ra=er =hile the "o=nloa" is progressing. 5he enRueue() metho" returns an 0@ o& this "o=nloa", =hi'h =e hol" onto &or use in Ruerying the "o=nloa" status.

(eepin! Tr c$ o. Do#nlo d St tus


0& the user presses the Juery %tatus button, =e =ant to &in" out the "etails o& ho= the "o=nloa" is progressing. 5o "o that, =e 'an 'all UuerFPQ on the =oEnload#anager. 5he UuerFPQ metho" takes a =oEnload#anager.YuerF obGe't,
%:&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

"es'ribing =hat "o=nloa"(s) you are intereste" in. 0n our 'ase, =e use the !alue =e got &rom the enUueuePQ metho" =hen the user reRueste" the "o=nloa",
public void -ueryStatusPVieE vQ : +ursor c6mgr.-ueryPneE =oEnload#anager./ueryPQ.set"ilterByIdPlast=oEnloadQQJ if Pc66nullQ : &oast.makeTextPthis8 7=oEnload not foundX78 &oast.)$%D&! )"%DQ.showPQJ ; else : c.mo!eTo"irstPQJ )og.dPgetClassPQ.get&amePQ8 7+")3#% I=: 7R c.getLongPc.getColumnIndexP=oEnload#anager.+")3#% I=QQQJ )og.dPgetClassPQ.get&amePQ8 7+")3#% 45&$2 ="@%)"A=$= 2" 9A?: 7R c.getLongPc.getColumnIndexP=oEnload#anager.+")3#% 45&$2 ="@%)"A=$= 2" 9A?QQQJ )og.dPgetClassPQ.get&amePQ8 7+")3#% )A2& #"=I9I$= &I#$2&A#(: 7R c.getLongPc.getColumnIndexP=oEnload#anager.+")3#% )A2& #"=I9I$= &I#$2& A#(QQQJ )og.dPgetClassPQ.get&amePQ8 7+")3#% )"+A) 3?I: 7R c.getStringPc.getColumnIndexP=oEnload#anager.+")3#% )"+A) 3?IQQQJ )og.dPgetClassPQ.get&amePQ8 7+")3#% 2&A&32: 7R c.getIntPc.getColumnIndexP=oEnload#anager.+")3#% 2&A&32QQQJ )og.dPgetClassPQ.get&amePQ8 7+")3#% ?$A2"%: 7R c.getIntPc.getColumnIndexP=oEnload#anager.+")3#% ?$A2"%QQQJ &oast.makeTextPthis8 statusMessagePcQ8 &oast.)$%D&! )"%DQ.showPQJ ; ;

5he UuerFPQ metho" returns a +ursor, 'ontaining a series o& 'olumns representing the "etails about our "o=nloa". 5here are a series o& 'onstants on the =oEnload#anager 'lass outlining =hat is possible. 0n our 'ase, =e retrie!e (an" "ump to LogCat),

5he 0@ o& the "o=nloa" (+")3#% I=) 5he amount o& "ata that has been "o=nloa"e" to "ate (+")3#% 45&$2 ="@%)"A=$= 2" 9A?) What the last-mo"i&ie" timestamp (+")3#% )A2& #"=I9I$= &I#$2&A#() What the a'tual status is (+")3#% 2&A&32) is on the "o=nloa"

Where the &ile is being sa!e" to lo'ally (+")3#% )"+A) 3?I)

%:-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

What the reason is &or that status (+")3#% ?$A2"%)

5here are a number o& possible status 'o"es (e.g., 2&A&32 9AI)$=, 2&A&32 23++$2293), 2&A&32 ?3%%I%D). %ome, like 2&A&32 9AI)$=, may ha!e an a''ompanying reason to pro!i"e more "etails.

,h t the -ser Sees


5he user, upon laun'hing the appli'ation, sees our three pretty buttons,

"igure *%&1 The /o)nload sample application@ as initially launched

Cli'king the &irst "isables the button =hile the "o=nloa" is going on, an" a "o=nloa" i'on appears in the status bar (though it is a bit "i&&i'ult to see, gi!en the poor 'ontrast bet=een An"roi"7s i'on an" An"roi"7s status bar),

%:%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

"igure *%-1 The /o)nload sample application@ performing a do)nload

%li"ing "o=n the noti&i'ation "ra=er sho=s the user the progress in the &orm o& a (rogress4ar =i"get,

%:0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

"igure *%%1 The notification dra)er@ during a do)nload using /o)nload+anager

5apping on the entry in the noti&i'ation "ra=er returns 'ontrol to our original a'ti!ity, =here they see a &oast,

%:2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

"igure *%01 The /o)nload sample application@ after coming to the foreground from the notification

0& they tap the mi""le button "uring the "o=nloa", a &oast =ill appear in"i'ating that the "o=nloa" is in progress,

%:7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

"igure *%21 The /o)nload sample application@ sho)ing the status mid# do)nload

A""itional "etails are also "umpe" to LogCat, !isible !ia @@M% or adb logcat,
1>-1- -,:<.:-1.>,*: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% I=: 1> 1>-1- -,:<.:-1.>,*: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% 45&$2 ="@%)"A=$= 2" 9A?: 01.<-1>-1- -,:<.:-1.>,*: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% )A2& #"=I9I$= &I#$2&A#(: 1>*1*,,0*0>C> 1>-1- -,:<.:-1.>,*: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% )"+A) 3?I: file:///mnt/sdcard/=oEnload/test.mp< 1>-1- -,:<.:-1.>**: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% 2&A&32: > 1>-1- -,:<.:-1.>**: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% ?$A2"%: -

>n'e the "o=nloa" is 'omplete, tapping the mi""le button =ill in"i'ate that the "o=nloa" is, in"ee", 'omplete, an" &inal in&ormation about the "o=nloa" is emitte" to LogCat,

%:8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

1>-1- -,:<*:>/.C0-: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% I=: 1> 1>-1- -,:<*:>/.C0-: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% 45&$2 ="@%)"A=$= 2" 9A?: 0>1*>>* 1>-1- -,:<*:>/.C/-: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% )A2& #"=I9I$= &I#$2&A#(: 1>*1*,,/1C<-* 1>-1- -,:<*:>/.C/-: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% )"+A) 3?I: file:///mnt/sdcard/=oEnload/test.mp< 1>-1- -,:<*:>/.C/-: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% 2&A&32: , 1>-1- -,:<*:>/.C/-: =$43D/com.commonsEare.android.doEnload.=oEnload=emoPC/>Q: +")3#% ?$A2"%: -

5apping the bottom button brings up the a'ti!ity "isplaying all "o=nloa"s, in'lu"ing both su''esses an" &ailures,

"igure *%71 The /o)nloads screen@ sho)ing everything do)nloaded by the /o)nload+anager

An", o& 'ourse, the &ile is "o=nloa"e". 0n An"roi" 2.., in the emulator, our 'hosen lo'ation maps to /mnt/sdcard/=oEnloads/test.mp<.

%::

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Communicating via the nternet

)imit tions
+55# $ Ls, but not +55#% (%%L) $ Ls. 5his is un&ortunate, as more an" more sites are s=it'hing to %%L en'ryption a'ross the boar", to "eal =ith !arious se'urity 'hallenges. +ope&ully, in the &uture, =oEnload#anager =ill ha!e more options here. 0& you "isplay the list o& all "o=nloa"s, an" your "o=nloa" is among them, it is a really goo" i"ea to make sure that some a'ti!ity (perhaps one o& yours) is able to respon" to an A+&I"% VI$@ Intent on that "o=nloa"7s M0ME type. >ther=ise, =hen the user taps on the entry in the list, they =ill get a &oast in"i'ating that there is nothing a!ailable to !ie= the "o=nloa". 5his may 'on&use users. Alternati!ely, use setVisibleIn=oEnloads3iPQ on your reRuest, passing in false, to suppress it &rom this list.
=oEnload#anager =orks =ith

Continuing ,ur =scape "rom 6anky Code


5he rule is simple, "o not a''ess the 0nternet &rom the main appli'ation threa". Al=ays use a ba'kgroun" threa" =ith !ttp+lient, !ttp3rl+onnection, or any other 0nternet a''ess A#0 you =ish to use.
2trict#ode,

intro"u'e" in an earlier 'hapter, =ill =arn you i& you attempt to a''ess the 0nternet on the main appli'ation threa". Android!ttp+lient =ill simply 'rash i& you attempt to make Web reRuests on the main appli'ation threa". +o=e!er, these 'apabilities are only a!ailable in ne=er !ersions o& An"roi". 5hat being sai", there are =ays to ha!e 2trict#ode in your appli'ation yet only use it in ne=er !ersions o& An"roi" using 'on"itional 'lass loa"ing S this te'hniRue =as 'o!ere" earlier in this book.

0<<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

PART V Services

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 16

Services5 The Theory

As note" pre!iously, An"roi" ser!i'es are &or long-running pro'esses that may nee" to keep running e!en =hen "e'ouple" &rom any a'ti!ity. E;amples in'lu"e playing musi' e!en i& the MplayerM a'ti!ity gets garbage'olle'te", polling the 0nternet &or %%PAtom &ee" up"ates, an" maintaining an online 'hat 'onne'tion e!en i& the 'hat 'lient loses &o'us "ue to an in'oming phone 'all. %er!i'es are 'reate" =hen manually starte" (!ia an A#0 'all) or =hen some a'ti!ity tries 'onne'ting to the ser!i'e !ia inter-pro'ess 'ommuni'ation (0#C). %er!i'es =ill li!e until spe'i&i'ally shut "o=n or until An"roi" is "esperate &or AM an" "estroys them prematurely. unning &or a long time has its 'osts, though, so ser!i'es nee" to be 'are&ul not to use too mu'h C#$ or keep ra"ios a'ti!e too mu'h o& the time, lest the ser!i'e 'ause the "e!i'e7s battery to get use" up too Rui'kly. 5his 'hapter outlines the basi' theory behin" 'reating an" 'onsuming ser!i'es. 5he ne;t 'hapter =ill outline a &e= spe'i&i' patterns &or ser!i'es, ones that may 'losely mat'h your parti'ular nee"s. +en'e, this 'hapter is short on 'o"e e;amples S you =ill &in" them an" more in the ne;t 'hapter.

Why ServicesF
%er!i'es are a M%=iss Army kni&eM &or a =i"e range o& &un'tions that "o not reRuire "ire't a''ess to an a'ti!ity7s user inter&a'e, su'h as,
0<Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Services5 The Theory

#er&orming operations that nee" to 'ontinue e!en i& the user lea!es the appli'ation7s a'ti!ities, like a long "o=nloa" (as seen =ith the An"roi" Market) or playing musi' (as seen =ith An"roi" musi' apps) #er&orming operations that nee" to e;ist regar"less o& a'ti!ities 'oming an" going, su'h as maintaining a 'hat 'onne'tion in support o& a 'hat appli'ation #ro!i"ing a lo'al A#0 to remote A#0s, su'h as might be pro!i"e" by a Web ser!i'e #er&orming perio"i' =ork =ithout user inter!ention, akin to 'ron Gobs or Win"o=s s'he"ule" tasks

E!en things like home s'reen app =i"gets o&ten in!ol!e a ser!i'e to assist =ith long-running =ork. Many appli'ations =ill not nee" any ser!i'es. -ery &e= appli'ations =ill nee" more than one. +o=e!er, the ser!i'e is a po=er&ul tool &or an An"roi" "e!eloper7s toolbo; an" is a subGe't =ith =hi'h any Ruali&ie" An"roi" "e!eloper shoul" be &amiliar.

Setting >p a Service


Creating a ser!i'e implementation shares many 'hara'teristi's =ith buil"ing an a'ti!ity. ?ou inherit &rom an An"roi"-supplie" base 'lass, o!erri"e some li&e'y'le metho"s, an" hook the ser!i'e into the system !ia the mani&est.

The Service Cl ss
Cust as an a'ti!ity in your appli'ation e;ten"s either ActivitF or an An"roi"supplie" ActivitF sub'lass, a ser!i'e in your appli'ation e;ten"s either 2ervice or an An"roi"-supplie" 2ervice sub'lass. 5he most 'ommon 2ervice sub'lass is Intent2ervice, use" primarily &or the 'omman" pattern, "es'ribe" later in this 'hapter. 5hat being sai", many ser!i'es simply e;ten" 2ervice.
0<%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Services5 The Theory

)i.ecycle %ethods
Cust as a'ti!ities ha!e on+reatePQ, on?esumePQ, on(ausePQ an" kin, 2ervice implementations ha!e their o=n li&e'y'le metho"s, su'h as, 1.
on+reatePQ,

=hi'h, as =ith a'ti!ities, is 'alle" =hen the ser!i'e pro'ess is 'reate", by any means

2. on2tart+ommandPQ, =hi'h is 'alle" ea'h time the ser!i'e is sent a 'omman" !ia start2ervicePQ .. on4indPQ, =hi'h is 'alle" =hene!er a 'lient bin"s to the ser!i'e !ia
bind2ervicePQ

<. on=estroFPQ =hi'h is 'alle" as the ser!i'e is being shut "o=n As =ith a'ti!ities, ser!i'es initialiKe =hate!er they nee" in on+reatePQ an" 'lean up those items in on=estroFPQ. An", as =ith a'ti!ities, the on=estroFPQ metho" o& a ser!i'e might not be 'alle", i& An"roi" terminates the entire appli'ation pro'ess, su'h as &or emergen'y AM re'lamation. 5he on2tart+ommandPQ an" on4indPQ li&e'y'le metho"s =ill be implemente" base" on your 'hoi'e o& 'ommuni'ating to the 'lient, as =ill be e;plaine" later in this 'hapter.

% ni.est Entry
*inally, you nee" to a"" the ser!i'e to your Android#anifest.Gml &ile, &or it to be re'ogniKe" as an a!ailable ser!i'e &or use. 5hat is simply a matter o& a""ing a LserviceO element as a 'hil" o& the application element, pro!i"ing android:name to re&eren'e your ser!i'e 'lass. %in'e the ser!i'e 'lass is in the same Ca!a namespa'e as e!erything else in this appli'ation, =e 'an use the shorthan" (7@eather2ervice7 or 7.@eather2ervice7) to re&eren'e our 'lass.

0<0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Services5 The Theory

0& you =ish to reRuire some permission o& those =ho =ish to start or bin" to the ser!i'e, a"" an android:permission attribute naming the permission you are man"ating S see the 'hapter on permissions &or more "etails. *or e;ample, here is a mani&est sho=ing the LserviceM element,
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.doEnloader7 android:version+ode6717 android:version%ame671.-7M Luses-permission android:name67android.permission.I%&$?%$&7/M Luses-permission android:name67android.permission.@?I&$ $]&$?%A) 2&"?AD$7/M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67=oEnloader=emo7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM Lservice android:name67=oEnloader7/M L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

Communicating To Services
Clients o& ser!i'es S &reRuently a'ti!ities, though not ne'essarily S ha!e t=o main =ays to sen" reRuests or in&ormation to a ser!i'e. >ne approa'h is to sen" a 'omman", =hi'h 'reates no lasting 'onne'tion to the ser!i'e. 5he other approa'h is to bin" to the ser!i'e, establishing a bi-"ire'tional 'ommuni'ations 'hannel that lasts as long as the 'lient nee"s it.

Sendin! Comm nds #ith st rtService?@


5he simplest =ay to =ork =ith a ser!i'e is to 'all start2ervicePQ. 5he start2ervicePQ metho" takes an 0ntent parameter, mu'h like startActivitFPQ "oes. 0n &a't, the Intent supplie" to start2ervicePQ has the same t=o-part role as it "oes =ith startActivitFPQ,

0"enti&y the ser!i'e to 'ommuni'ate =ith


0<2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Services5 The Theory

%upply parameters, in the &orm o& Intent e;tras, to tell the ser!i'e =hat it is suppose" to "o

*or a lo'al ser!i'e S the &o'us o& this book S the simplest &orm o& Intent is one that i"enti&ies the 'lass that implements the Intent (e.g., neE IntentPthis8 #F2ervice.classQJ). 5he 'all to start2ervicePQ is asyn'hronous, so the 'lient =ill not blo'k. 5he ser!i'e =ill be 'reate" i& it is not alrea"y running, an" it =ill re'ei!e the Intent !ia a 'all to the on2tart+ommandPQ li&e'y'le metho". 5he ser!i'e 'an "o =hate!er it nee"s to in on2tart+ommandPQ, but sin'e on2tart+ommandPQ is 'alle" on the main appli'ation threa", it shoul" "o its =ork !ery Rui'kly. Anything that might take a =hile shoul" be "elegate" to a ba'kgroun" threa". 5he on2tart+ommandPQ metho" 'an return one o& se!eral !alues, mostly to in"i'ate to An"roi" =hat shoul" happen i& the ser!i'e7s pro'ess shoul" be kille" =hile it is running. 5he most likely return !alues are,
2&A?& 2&I+H5,

meaning that the ser!i'e shoul" be mo!e" ba'k into the starte" state (as i& on2tart+ommandPQ ha" been 'alle"), but "o not re-"eli!er the Intent to on2tart+ommandPQ
2&A?& ?$=$)IV$? I%&$%&, meaning that the ser!i'e shoul" be restarte" !ia a 'all to on2tart+ommandPQ, supplying the same Intent as

=as "eli!ere" this time


2&A?& %"& 2&I+H5,

meaning that the ser!i'e shoul" remain stoppe" until e;pli'itly starte" by appli'ation 'o"e

1y "e&ault, 'alling start2ervicePQ not only sen"s the 'omman", but tells An"roi" to keep the ser!i'e running until something tells it to stop. >ne =ay to stop a ser!i'e is to 'all stop2ervicePQ, supplying the same Intent use" =ith start2ervicePQ, or at least one that is eRui!alent (e.g., i"enti&ies the same 'lass). At that point, the ser!i'e =ill stop an" =ill be "estroye". 2ote that stop2ervicePQ "oes not employ any sort o& re&eren'e 'ounting, so three 'alls to start2ervicePQ =ill result in a single ser!i'e running, =hi'h =ill be stoppe" by a 'all to stop2ervicePQ.

0<7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Services5 The Theory

Another possibility &or stopping a ser!i'e is to ha!e the ser!i'e 'all stop2elfPQ on itsel&. ?ou might "o this i& you use start2ervicePQ to ha!e a ser!i'e begin running an" "oing some =ork on a ba'kgroun" threa", then ha!ing the ser!i'e stop itsel& =hen that ba'kgroun" =ork is 'omplete".

Bindin! #ith =indService?@


1in"ing allo=s a ser!i'e to e;pose an A#0 to a'ti!ities (or other ser!i'es) that bin" to it. When an a'ti!ity (or other 'lient) bin"s to a ser!i'e, it primarily is reRuesting to be able to a''ess the publi' A#0 e;pose" by that ser!i'e !ia the ser!i'e7s Mbin"erM, as returne" by the ser!i'e7s on4indPQ metho". When "oing this, the a'ti!ity 'an also in"i'ate, !ia the 4I%= A3&" +?$A&$ &lag, to ha!e An"roi" automati'ally start up the ser!i'e i& it is not alrea"y running. 5he ser!i'e7s Mbin"erM is usually a sub'lass o& 4inder, on =hi'h you 'an put =hate!er metho"s you =ant to e;pose to 'lients. *or lo'al ser!i'es, you 'an ha!e as many metho"s as you =ant, =ith =hate!er metho" signatures (parameters, return type, et'.) that you =ant. 5he ser!i'e returns an instan'e o& the 4inder sub'lass in on4indPQ. Clients 'all bind2ervicePQ, supplying the Intent that i"enti&ies the ser!i'e, a 2ervice+onnection obGe't representing the 'lient si"e o& the bin"ing, an" an optional 4I%= A3&" +?$A&$ &lag. As =ith start2ervicePQ, bind2ervicePQ is asyn'hronous. 5he 'lient =ill not kno= anything about the status o& the bin"ing until the 2ervice+onnection obGe't is 'alle" =ith on2ervice+onnectedPQ. 5his not only in"i'ates the bin"ing has been establishe", but &or lo'al ser!i'es it pro!i"es the 4inder obGe't that the ser!i'e returne" !ia on4indPQ. At this point, the 'lient 'an use the 4inder to ask the ser!i'e to "o =ork on its behal&. 2ote that i& the ser!i'e is not alrea"y running, an" i& you pro!i"e 4I%= A3&" +?$A&$, then the ser!i'e =ill be 'reate" &irst be&ore being boun" to the 'lient. 0& you skip 4I%= A3&" +?$A&$, bind2ervicePQ =ill return false, in"i'ating there =as no e;isting ser!i'e to bin" to.

0<8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Services5 The Theory

E!entually, the 'lient =ill nee" to 'all unbind2ervicePQ, to in"i'ate it no longer nee"s to 'ommuni'ate =ith the ser!i'e. *or e;ample, an a'ti!ity might 'all bind2ervicePQ in its on+reatePQ metho", then 'all unbind2ervicePQ in its on=estroFPQ metho". 5he 'all to unbind2ervicePQ e!entually triggers on2ervice=isconnectedPQ to be 'alle" on the 2ervice+onnection obGe't S at this point, the 'lient 'an no longer sa&ely use the 4inder obGe't. 0& there are no other boun" 'lients to the ser!i'e, An"roi" =ill shut "o=n the ser!i'e as =ell, releasing its memory. +en'e, =e "o not nee" to 'all stop2ervicePQ oursel!es S An"roi" han"les that, i& nee"e", as a si"e e&&e't o& unbin"ing. 0& the 'lient is an a'ti!ity, there are t=o important steps to take to ensure that the bin"ing sur!i!es a 'on&iguration 'hange, like a s'reen rotation, 1. 0nstea" o& 'alling bind2ervicePQ on the a'ti!ity itsel&, 'all bind2ervicePQ on the Application +onteGt (obtaine" !ia getApplication+onteGtPQ).

2. Make sure the 2ervice+onnection gets &rom the ol" instan'e o& the a'ti!ity to the ne= one, probably !ia on?etain%on+onfigurationInstancePQ. 5his allo=s the bin"ing to persist bet=een a'ti!ity instan'es.

Communicating "rom Services


>& 'ourse, the approa'hes liste" in the pre!ious se'tion only =ork &or a 'lient 'alling out to a ser!i'e. 5he re!erse is also &reRuently nee"e", so the ser!i'e 'an let an a'ti!ity or something kno= about asyn'hronous e!ents.

C ll= c$J)istener +=7ects


An a'ti!ity or other ser!i'e 'lient 'an pro!i"e some sort o& M'allba'kM or MlistenerM obGe't to the ser!i'e, =hi'h the ser!i'e 'oul" then 'all =hen nee"e". 5o make this =ork, you =oul" nee" to,

0<:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Services5 The Theory

1.

@e&ine a Ca!a inter&a'e &or that listener obGe't

2. 8i!e the ser!i'e a publi' A#0 to register an" retra't listeners .. +a!e the ser!i'e use those listeners at appropriate times, to noti&y those =ho registere" the listener o& some e!ent <. +a!e the a'ti!ity register an" retra't a listener as nee"e" A. +a!e the a'ti!ity respon" to the listener-base" e!ents in some suitable &ashion 5he biggest 'at'h is to make sure that the a'ti!ity retra'ts the listeners =hen it is "one. Listener obGe'ts generally kno= their a'ti!ity, e;pli'itly (!ia a "ata member) or impli'itly (by being implemente" as an inner 'lass). 0& the ser!i'e is hol"ing onto "e&un't listener obGe'ts, the 'orrespon"ing a'ti!ities =ill linger in memory, e!en i& the a'ti!ities are not being use" by An"roi" any more. 5his represents a big memory leak. ?ou may =ish to use @eak?eferences, 2oft?eferences, or similar 'onstru'ts to ensure that i& an a'ti!ity is "estroye", any listeners it registers =ith your ser!i'e =ill not keep that a'ti!ity in memory.

Bro dc st Intents
An alternati!e approa'h, &irst mentione" in the 'hapter on 0ntent &ilters, is to ha!e the ser!i'e sen" a broa"'ast Intent that 'an be pi'ke" up by the a'ti!ity...assuming the a'ti!ity is still aroun" an" is not pause". 5he ser!i'e 'an 'all send4roadcastPQ, supplying an 0ntent that i"enti&ies the broa"'ast, "esigne" to be pi'ke" up by a 4roadcast?eceiver. 5his 'oul" be a 'omponent-spe'i&i' broa"'ast (e.g., neE IntentPthis8 #F?eceiver.classQ), i& the 4roadcast?eceiver is registere" in the mani&est. >r, it 'an be base" on some a'tion string, perhaps one e!en "o'umente" an" "esigne" &or thir"party appli'ations to listen &or. turn, 'an register a 4roadcast?eceiver !ia though this approa'h =ill only =ork &or Intent obGe'ts spe'i&ying some a'tion, not ones i"enti&ying a parti'ular 'omponent. 1ut, =hen the a'ti!ity7s 4roadcast?eceiver re'ei!es the broa"'ast, it 'an "o =hat it =ants to in&orm the user or other=ise up"ate itsel&.
register?eceiverPQ,
0*<

5he

a'ti!ity,

in

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Services5 The Theory

Pendin! Results
?our a'ti!ity 'an 'all create(ending?esultPQ. 5his returns a (endingIntent S an obGe't that represents an Intent an" the 'orrespon"ing a'tion to be per&orme" upon that Intent (e.g., use it to start an a'ti!ity). 0n this 'ase, the (endingIntent =ill 'ause a result to be "eli!ere" to your a'ti!ity7s implementation o& onActivitF?esultPQ, Gust as i& another a'ti!ity ha" been 'alle" =ith startActivitF9or?esultPQ an", in turn, 'alle" set?esultPQ to sen" ba'k a result. %in'e a (endingIntent is (arcelable, an" 'an there&ore be put into an Intent e;tra, your a'ti!ity 'an pass this (endingIntent to the ser!i'e. 5he ser!i'e, in turn, 'an 'all one o& se!eral &la!ors o& the sendPQ metho" on the (endingIntent, to noti&y the a'ti!ity (!ia onActivitF?esultPQ) o& an e!ent, possibly e!en supplying "ata (in the &orm o& an Intent) representing that e!ent.

%essen!er
?et another possibility is to use a #essenger obGe't. A #essenger sen"s messages to an a'ti!ity7s !andler. Within a single a'ti!ity, a !andler 'an be use" to sen" messages to itsel&, as =as "emonstrate" in the 'hapter on threa"s. +o=e!er, bet=een 'omponents S su'h as bet=een an a'ti!ity an" a ser!i'e S you =ill nee" a #essenger to ser!e as the bri"ge. As =ith a (endingIntent, a #essenger is (arcelable, an" so 'an be put into an Intent e;tra. 5he a'ti!ity 'alling start2ervicePQ or bind2ervicePQ =oul" atta'h a #essenger as an e;tra on the Intent. 5he ser!i'e =oul" obtain that #essenger &rom the Intent. When it is time to alert the a'ti!ity o& some e!ent, the ser!i'e =oul",

Call #essage.obtainPQ to get an empty #essage obGe't #opulate that #essage obGe't as nee"e", =ith =hate!er "ata the ser!i'e =ishes to pass to the a'ti!ity Call sendPQ on the #essenger, supplying the #essage as a parameter

0**

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Services5 The Theory

5he !andler =ill then re'ei!e the message !ia handle#essagePQ, on the main appli'ation threa", an" so 'an up"ate the $0 or =hate!er is ne'essary.

"oti.ic tions
Another approa'h is &or the ser!i'e to let the user kno= "ire'tly about the =ork that =as 'omplete". 5o "o that, a ser!i'e 'an raise a 2oti&i'ation S putting an i'on in the status bar an" optionally shaking or beeping or something. 5his te'hniRue is 'o!ere" in an up'oming 'hapter.

0*&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 18

Basic Service Patterns

2o= that you ha!e seen the pie'es that make up ser!i'es an" their 'lients, let us e;amine a &e= s'enarios that employ ser!i'es an" ho= those s'enarios might be implemente".

The /o)nloader
0& you ele't to "o=nloa" something &rom the An"roi" Market, you are =el'ome to ba'k out o& the Market appli'ation entirely. 5his "oes not 'an'el the "o=nloa" S the "o=nloa" an" installation run to 'ompletion, "espite no Market a'ti!ity being on-s'reen. ?ou may ha!e similar 'ir'umstan'es in your appli'ation, &rom "o=nloa"ing a pur'hase" e-book to "o=nloa"ing a map &or a game to "o=nloa"ing a &ile &rom some sort o& M"rop bo;M &ile-sharing ser!i'e. An"roi" 2.. intro"u'e" the =oEnload#anager ('o!ere" in a pre!ious 'hapter), =hi'h =oul" han"le this &or you. +o=e!er, you might nee" that sort o& 'apability on ol"er !ersions o& An"roi", at least through 2011. 5he sample proGe't re!ie=e" in this se'tion is 2ervices/=oEnloader.

0*Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

The Desi!n
5his sort o& situation is a per&e't use &or the 'omman" pattern an" an Intent2ervice. 5he Intent2ervice has a ba'kgroun" threa", so "o=nloa"s 'an take as long as nee"e". An Intent2ervice =ill automati'ally shut "o=n =hen the =ork is "one, so the ser!i'e =ill not linger an" you "o not nee" to =orry about shutting it "o=n yoursel&. ?our a'ti!ity 'an simply sen" a 'omman" !ia start2ervicePQ to the Intent2ervice to tell it to go "o the =ork. A"mitte"ly, things get a bit tri'kier =hen you =ant to ha!e the a'ti!ity &in" out =hen the "o=nloa" is 'omplete. 5his e;ample =ill sho= the use o& #essenger &or this.

The Service Implement tion


+ere is the implementation o& this Intent2ervice, name" =oEnloader,
package com.commonsEare.android.doEnloaderJ import import import import import import import import import import import import import import import import android.app.ActivitFJ android.app.Intent2erviceJ android.content.IntentJ android.os.4undleJ android.os.$nvironmentJ android.os.#essageJ android.os.#essengerJ android.util.)ogJ java.io.9ileJ java.io.9ile"utput2treamJ java.io.I"$GceptionJ org.apache.http.client.?esponse!andlerJ org.apache.http.client.!ttp+lientJ org.apache.http.client.methods.!ttpDetJ org.apache.http.impl.client.4asic?esponse!andlerJ org.apache.http.impl.client.=efault!ttp+lientJ

public class =oEnloader eGtends Intent2ervice : public static final 2tring $]&?A #$22$%D$?67com.commonsEare.android.doEnloader.$]&?A #$22$%D$?7J private !ttp+lient client6nullJ public DownloaderPQ : superP7=oEnloader7QJ ;

0*%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

O"verride public void onCreatePQ : super.onCreatePQJ ; client6neE Default(ttpClientPQJ

O"verride public void onDestroyPQ : super.onDestroyPQJ client.getConnectionManagerPQ.shutdownPQJ ; O"verride public void on(andleIntentPIntent iQ : !ttpDet get#ethod6neE (ttp etPi.getDataPQ.toStringPQQJ int result6ActivitF.?$23)& +A%+$)$=J trF : ?esponse!andlerLbFteABM response!andler6neE Byte$rray%esponse(andlerPQJ bFteAB response4odF6client.executePget#ethod8 response!andlerQJ 9ile output6neE "ileP$nvironment.get+xternalStorageDirectoryPQ8 i.getDataPQ.getLast)athSegmentPQQJ if Poutput.existsPQQ : output.deletePQJ ; 9ile"utput2tream fos6neE "ileOutputStreamPoutput.get)athPQQJ fos.writePresponse4odFQJ fos.closePQJ result6ActivitF.?$23)& "HJ ; catch PI"$Gception e>Q : )og.ePgetClassPQ.get&amePQ8 7$Gception in doEnload78 e>QJ ; 4undle eGtras6i.get+xtrasPQJ if PeGtrasX6nullQ : #essenger messenger6P#essengerQeGtras.getP$]&?A #$22$%D$?QJ #essage msg6#essage.o'tainPQJ msg.arg16resultJ trF : messenger.sendPmsgQJ ; catch Pandroid.os.?emote$Gception e1Q : )og.wPgetClassPQ.get&amePQ8 7$Gception sending message78 e1QJ ;

0*0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

; ; ;

0n on+reatePQ, =e obtain a =efault!ttp+lient obGe't, as =as "es'ribe" in the 'hapter on 0nternet a''ess. 0n on=estroFPQ, =e shut "o=n the 'lient. 5his =ay, i& se!eral "o=nloa" reRuests are in!oke" in seRuen'e, =e 'an use a single =efault!ttp+lient obGe't S the Intent2ervice =ill only shut "o=n a&ter all enRueue" =ork has been 'omplete". 5he bulk o& the =ork is a''omplishe" in on!andleIntentPQ, =hi'h is 'alle" on the Intent2ervice, on a ba'kgroun" threa", e!ery time start2ervicePQ is 'alle". *or the Intent, =e obtain the $ L o& the &ile to "o=nloa" !ia a 'all to get=ataPQ on the supplie" Intent. A'tually "o=nloa"ing the &ile uses the =efault!ttp+lient obGe't, along =ith an !ttpDet obGe't. +o=e!er, sin'e the &ile might be binary (e.g., M#.) instea" o& te;t, =e 'annot use a 4asic?esponse!andler. 0nstea", =e use a 4FteArraF?esponse!andler S a 'ustom ?esponse!andler 'lone" &rom the sour'e &or 4asic?esponse!andler, but one that returns a bFteAB instea" o& a 2tring,
package com.commonsEare.android.doEnloaderJ import import import import import import import java.io.I"$GceptionJ org.apache.http.!ttp$ntitFJ org.apache.http.!ttp?esponseJ org.apache.http.2tatus)ineJ org.apache.http.client.?esponse!andlerJ org.apache.http.client.!ttp?esponse$GceptionJ org.apache.http.util.$ntitF3tilsJ

public class 4FteArraF?esponse!andler implements ?esponse!andlerLbFteABM : public bFteAB handle%esponsePfinal !ttp?esponse responseQ throEs I"$Gception8 !ttp?esponse$Gception : 2tatus)ine status)ine6response.getStatusLinePQJ if Pstatus)ine.getStatusCodePQM6C--Q : throE neE (ttp%esponse+xceptionPstatus)ine.getStatusCodePQ8 status)ine.get%eason)hrasePQQJ ; !ttp$ntitF entitF6response.get+ntityPQJ if PentitF66nullQ : returnPnullQJ ;

0*2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

returnP$ntitF3tils.toByte$rrayPentitFQQJ ; ;

>n'e the &ile is "o=nloa"e" to e;ternal storage, =e nee" to alert the a'ti!ity that the =ork is 'omplete". 0& the a'ti!ity is intereste" in this sort o& message, it =ill ha!e atta'he" a #essenger obGe't as $]&?A #$22$%D$? to the Intent. =oEnloader gets the #essenger, 'reates an empty #essage obGe't, an" puts a result 'o"e in the arg1 &iel" o& the #essage. 0t then sen"s the #essage to the a'ti!ity. 0& the a'ti!ity =as "estroye" be&ore this point, the reRuest to sen" the message =ill &ail =ith a ?emote"bject$Gception. %in'e this is an Intent2ervice, it =ill automati'ally shut "o=n =hen on!andleIntentPQ 'ompletes, i& there is no more =ork Rueue" to be "one.

-sin! the Service


5he a'ti!ity "emonstrating the use o& =oEnloader has a tri!ial $0, 'onsisting o& one large button,
LNGml version671.-7 encoding67utf-,7NM L4utton Gmlns:android67http://schemas.android.com/apk/res/android7 android:id67ORid/button7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:teGt67=o the =oEnload7 android:on+lick67do&he=oEnload7 /M

5hat $0 is initialiKe" in on+reatePQ, as usual,


O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ ; b6P4uttonQfindViewByIdP?.id.buttonQJ

When the user 'li'ks the button, do&he=oEnloadPQ is 'alle" to "isable the button (to pre!ent a''i"ental "upli'ate "o=nloa"s) an" 'all start2ervicePQ,

0*7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

public void doTheDownloadPVieE vQ : b.set+na'ledPfalseQJ Intent i6neE IntentPthis8 =oEnloader.classQJ i.setDataP3ri.parseP7http://commonsEare.com/Android/eGcerpt.pdf7QQJ i.put+xtraP=oEnloader.$]&?A #$22$%D$?8 neE MessengerPhandlerQQJ startSer!icePiQJ ;

+ere, the Intent =e pass o!er has the $ L o& the &ile to "o=nloa" (in this 'ase, a $ L pointing to a #@*), plus a #essenger in the $]&?A #$22$%D$? e;tra. 5hat #essenger is 'reate" =ith an atta'hment to the a'ti!ity7s !andler,
private !andler handler6neE (andlerPQ : O"verride public void handleMessageP#essage msgQ : b.set+na'ledPtrueQJ &oast .makeTextP=oEnloader=emo.this8 7=oEnload completeX78 &oast.)$%D&! )"%DQ .showPQJ

; ;J

0& the a'ti!ity is still aroun" =hen the "o=nloa" is 'omplete, the !andler enables the button an" "isplays a &oast to let the user kno= that the "o=nloa" is 'omplete. 2ote that the a'ti!ity is ignoring the result 'o"e supplie" by the ser!i'e, though in prin'iple it 'oul" "o something "i&&erent in both the su''ess an" &ailure 'ases.

The +usic Player


Most au"io player appli'ations in An"roi" S &or musi', au"iobooks, or =hate!er S "o not reRuire the user to remain in the player appli'ation itsel&. ather, the user 'an go on an" "o other things =ith their "e!i'e, =ith the au"io playing in the ba'kgroun". 5his is similar in many respe'ts to the "o=nloa" s'enario &rom the pre!ious se'tion. +o=e!er, in this 'ase, the user is the one that 'ontrols =hen the =ork (playing au"io) en"s. 5he sample proGe't re!ie=e" in this se'tion is 2ervices/9ake(laFer.
0*8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

The Desi!n
>n'e again, =e =ill use start2ervicePQ, sin'e =e =ant the ser!i'e to run e!en =hen the a'ti!ity starting it has been "estroye". +o=e!er, this time, =e =ill use a regular 2ervice, rather than an Intent2ervice. An Intent2ervice is "esigne" to "o =ork an" stop itsel&, =hereas in this 'ase, =e =ant the user to be able to stop the musi' playba'k. %in'e musi' playba'k is outsi"e the s'ope o& this book, the ser!i'e =ill simply stub out those parti'ular operations.

The Service Implement tion


+ere is the implementation o& this 2ervice, name" (laFer2ervice,
package com.commonsEare.android.fakeplaFerJ import import import import import android.app.2erviceJ android.content.IntentJ android.os.4undleJ android.os.I4inderJ android.util.)ogJ

public class (laFer2ervice eGtends 2ervice : public static final 2tring $]&?A ()A5)I2&67$]&?A ()A5)I2&7J public static final 2tring $]&?A 2!399)$67$]&?A 2!399)$7J private boolean is(laFing6falseJ O"verride public int onStartCommandPIntent intent8 int flags8 int startIdQ : 2tring plaFlist6intent.getString+xtraP$]&?A ()A5)I2&QJ boolean use2huffle6intent.getBoolean+xtraP$]&?A 2!399)$8 falseQJ playPplaFlist8 use2huffleQJ returnP2&A?& %"& 2&I+H5QJ ; O"verride public void onDestroyPQ : stopPQJ ; O"verride public I4inder onBindPIntent intentQ : returnPnullQJ

0*:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

; private void playP2tring plaFlist8 boolean use2huffleQ : if PXis(laFingQ : )og.wPgetClassPQ.get&amePQ8 7Dot to plaFPQX7QJ is(laFing6trueJ ; ; private void stopPQ : if Pis(laFingQ : )og.wPgetClassPQ.get&amePQ8 7Dot to stopPQX7QJ is(laFing6falseJ ; ; ;

0n this 'ase, =e really "o not nee" anything &or on+reatePQ, so that li&e'y'le metho" is skippe". >n the other han", =e ha!e to implement on4indPQ, be'ause that is a reRuire" metho" o& 2ervice sub'lasses. Intent2ervice implements on4indPQ &or us, =hi'h is =hy that =as not nee"e" &or the =oEnloader sample. When the 'lient 'alls start2ervicePQ, on2tart+ommandPQ is 'alle" in (laFer2ervice. +ere, =e get the Intent an" pi'k out some e;tras to tell us =hat to play ba'k ($]&?A ()A5)I2&) an" other 'on&iguration "etails (e.g., $]&?A 2!399)$). on2tart+ommandPQ 'alls plaFPQ, =hi'h simply &lags that =e are playing an" logs a message to LogCat S a real musi' player =oul" use #edia(laFer to start playing the &irst song in the playlist. on2tart+ommandPQ returns 2&A?& %"& 2&I+H5, in"i'ating that i& An"roi" has to kill o&& this ser!i'e (e.g., lo= memory), it shoul" not restart it on'e 'on"itions impro!e.
on=estroFPQ stops the musi' &rom playing S theoreti'ally, any=ay S by 'alling a stopPQ metho". >n'e again, this Gust logs a message to LogCat,

plus up"ates our internal are-=e-playing &lag.

0n the up'oming 'hapter on noti&i'ations, =e =ill re!isit this sample an" "is'uss the use o& start9oregroundPQ to make it easier &or the user to get ba'k to the musi' player, plus let An"roi" kno= that the ser!i'e is "eli!ering part o& the &oregroun" e;perien'e an" there&ore shoul" not be shut "o=n.

0&<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

-sin! the Service


5he 9ake(laFer a'ti!ity "emonstrating the use o& (laFer2ervice has a $0 t=i'e as 'omple; as the pre!ious sample, 'onsisting o& t=o large buttons,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L4utton android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 android:teGt672tart the (laFer7 android:on+lick67start(laFer7 /M L4utton android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:laFout Eeight6717 android:teGt672top the (laFer7 android:on+lick67stop(laFer7 /M L/)inear)aFoutM

5he a'ti!ity itsel& is not mu'h more 'omple;,


package com.commonsEare.android.fakeplaFerJ import import import import android.app.ActivitFJ android.content.IntentJ android.os.4undleJ android.vieE.VieEJ

public class 9ake(laFer eGtends ActivitF : O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ ; public void start)layerPVieE vQ : Intent i6neE IntentPthis8 (laFer2ervice.classQJ i.put+xtraP(laFer2ervice.$]&?A ()A5)I2&8 7main7QJ i.put+xtraP(laFer2ervice.$]&?A 2!399)$8 trueQJ startSer!icePiQJ

0&*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

; public void stop)layerPVieE vQ : stopSer!icePneE IntentPthis8 (laFer2ervice.classQQJ ; ;

5he on+reatePQ metho" merely loa"s the $0. 5he start(laFerPQ metho" 'onstru'ts an Intent =ith &ake !alues &or $]&?A ()A5)I2& an" $]&?A 2!399)$, then 'alls start2ervicePQ. A&ter you press the top button, you =ill see the 'orrespon"ing message in LogCat. %imilarly, stop(laFerPQ 'alls stop2ervicePQ, triggering the se'on" LogCat message. 2otably, you "o not nee" to keep the a'ti!ity running in bet=een those button 'li'ks S you 'an e;it the a'ti!ity !ia 1ACD an" 'ome ba'k later to stop the ser!i'e.

The Web Service nterface


0& you are going to 'onsume a E%5-style Web ser!i'e, you may =ish to 'reate a Ca!a 'lient-si"e A#0 &or that ser!i'e. 5his allo=s you to isolate "etails about the Web ser!i'e ($ Ls, authoriKation 're"entials, et'.) in one pla'e, =ith the rest o& your appli'ation Gust able to use the publishe" A#0. 0& the 'lient-si"e A#0 might in!ol!e state, su'h as a session 0@ or 'a'he" results, you may =ish to use a ser!i'e to implement the 'lient-si"e A#0. 0n this 'ase, the most natural &orm o& ser!i'e =oul" be one that publishes a 4inder, so 'lients 'an 'all a MrealM A#0, that the ser!i'e translates into +55# reRuests. 0n this 'ase, =e =ant to 'reate a 'lient-si"e Ca!a A#0 &or the $% 2ational Weather %er!i'e7s &ore'ast Web ser!i'e, so =e 'an get a =eather &ore'ast (timestamps, proGe'te" temperatures, an" proGe'te" pre'ipitation) &or a gi!en latitu"e an" longitu"e. As you may re'all, =e e;amine" this Web ser!i'e ba'k in the 'hapter on 0nternet a''ess. 5he sample proGe't re!ie=e" in this se'tion is 2ervices/@eatherA(I.

0&&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

The Desi!n
5o use the bin"ing pattern, =e =ill nee" to e;pose an A#0 &rom a Mbin"erM obGe't. %in'e the =eather &ore'ast arri!es in a singularly a=&ul FML stru'ture, =e =ill ha!e the bin"er be responsible &or parsing the FML. +en'e, =e 'an say that the bin"er =ill ha!e a get9orecastPQ metho" to get us an ArraF)ist o& 9orecast obGe'ts, ea'h 9orecast representing one timestampPtemperaturePpre'ipitation triple. >n'e again, to supply the latitu"e an" longitu"e o& the &ore'ast roster to retrie!e, =e =ill use a )ocation obGe't, =hi'h =ill be obtaine" &rom 8#%. 5his part o& the sample =ill be "es'ribe" in greater "etail in the 'hapter on lo'ation management. %in'e the Web ser!i'e 'all may take a =hile, it is unsa&e to "o this on the main appli'ation threa". 0n this sample, =e =ill ha!e the ser!i'e use an AsFnc&ask to 'all our =eather A#0, so the a'ti!ity largely 'an be ignorant o& threa"ing issues.

The Rot tion Ch llen!e


1a'k in the 'hapter on threa"ing, =e note" the issues in!ol!e" =ith orientation 'hanges (or other 'on&iguration 'hanges) an" ba'kgroun" threa"s in a'ti!ities. 5he solution =as to use on?etain%on+onfigurationInstancePQ =ith a stati' inner 'lass AsFnc&ask implementation, =hi'h =e =oul" manually asso'iate =ith the ne=, post'on&iguration-'hange a'ti!ity. 5hat same problem 'rops up =ith the bin"ing pattern as =ell, one o& the reasons =hy bin"ing is "i&&i'ult to use. 0& you bin" to a ser!i'e &rom an a'ti!ity, that bin"ing =ill not magi'ally pass to the ne= a'ti!ity instan'e a&ter an orientation 'hange. 0nstea", you nee" to "o t=o things, 1. 1in" to the ser!i'e not using the a'ti!ity as the +onteGt, but rather by using getApplication+onteGtPQ, as that +onteGt is one that =ill li!e &or the li&etime o& your pro'ess

0&-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

2. #ass the 2ervice+onnection representing this bin"ing &rom the ol" a'ti!ity instan'e to the ne= one as part o& the 'on&iguration 'hange 5o a''omplish the se'on" &eat, you =ill nee" to use the same on?etain%on+onfigurationInstancePQ tri'k as =as use" =ith threa"s.

The Service Implement tion


>ur ser!i'e-si"e logi' is broken into three 'lasses, 9orecast, @eather4inder, an" @eather2ervice, plus one inter&a'e, @eather)istener.

The 5orec st
5he 9orecast 'lass merely en'apsulates the three pie'es o& the &ore'ast "ata triple, the timestamp, the temperature, an" the i'on in"i'ating the e;pe'te" pre'ipitation (i& any),
package com.commonsEare.android.EeatherJ class 9orecast : 2tring time677J Integer temp6nullJ 2tring icon3rl677J 2tring getTimePQ : returnPtimeQJ ; void setTimeP2tring timeQ : this.time6time.su'stringP-810Q.replacePI&I8 I IQJ ; Integer getTempPQ : returnPtempQJ ; void setTempPInteger tempQ : this.temp6tempJ ; 2tring getIconPQ : returnPicon3rlQJ ; void setIconP2tring icon3rlQ :

0&%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

this.icon3rl6icon3rlJ ; ;

The Inter. ce
1e'ause =e are going to &et'h the a'tual =eather &ore'ast on a ba'kgroun" threa" in the ser!i'e, =e ha!e a slight A#0 'hallenge S 'alls on our bin"er are syn'hronous. +en'e, =e 'annot ha!e a get9orecastPQ metho" that returns our &ore'ast. ather, =e nee" to gi!e some =ay &or the ser!i'e to get the &ore'ast ba'k to our a'ti!ity. 0n this 'ase, =e =ill pass in a listener obGe't (@eather)istener), that the ser!i'e =ill use =hen a &ore'ast is rea"y,
package com.commonsEare.android.EeatherJ import java.util.ArraF)istJ public interface @eather)istener : void update"orecastPArraF)istL9orecastM forecastQJ void handle+rrorP$Gception eQJ ;

The Binder
5he @eather4inder e;ten"s 4inder, a reRuirement &or the lo'al bin"ing pattern. >ther than that, the A#0 is up to us. +en'e, =e e;pose three metho"s, 1.
on+reatePQ, to be 'alle" =hen get a =efault!ttp+lient obGe't

the @eather4inder is set up, so =e 'an to use =ith the Web ser!i'e

2. on=estroFPQ, to be 'alle" =hen the @eather4inder is no longer nee"e", so =e 'an shut "o=n that =efault!ttp+lient obGe't .. get9orecastPQ, the main publi' A#0 &or use by our a'ti!ity, to ki'k o&& the ba'kgroun" =ork to 'reate our ArraF)ist o& 9orecast obGe'ts gi!en a )ocation
package com.commonsEare.android.EeatherJ import android.app.2erviceJ

0&0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

import import import import import import import import import import import import import import import import import import import import

android.content.+onteGtJ android.content.IntentJ android.location.)ocationJ android.os.AsFnc&askJ android.os.4inderJ android.os.4undleJ java.io.I"$GceptionJ java.io.2tring?eaderJ java.util.ArraF)istJ javaG.Gml.parsers.=ocument4uilderJ javaG.Gml.parsers.=ocument4uilder9actorFJ org.apache.http.client.?esponse!andlerJ org.apache.http.client.!ttp+lientJ org.apache.http.client.methods.!ttpDetJ org.apache.http.impl.client.4asic?esponse!andlerJ org.apache.http.impl.client.=efault!ttp+lientJ org.ECc.dom.=ocumentJ org.ECc.dom.$lementJ org.ECc.dom.%ode)istJ org.Gml.saG.Input2ourceJ

public class @eather4inder eGtends 4inder : private 2tring forecast6nullJ private !ttp+lient client6nullJ private 2tring format6nullJ void onCreateP+onteGt ctGtQ : client6neE Default(ttpClientPQJ format6ctGt.getStringP?.string.urlQJ ; void onDestroyPQ : client.getConnectionManagerPQ.shutdownPQJ ; void get"orecastP)ocation loc8 @eather)istener listenerQ : neE "etch"orecastTaskPlistenerQ.executePlocQJ ; private ArraF)istL9orecastM 'uild"orecastsP2tring raEQ throEs $Gception : ArraF)istL9orecastM forecasts6neE ArraF)istL9orecastMPQJ =ocument4uilder builder6=ocument4uilder9actorF .newInstancePQ .newDocumentBuilderPQJ =ocument doc6builder.parsePneE InputSourcePneE String%eaderPraEQQQJ %ode)ist times6doc.get+lementsByTag&ameP7start-valid-time7QJ for Pint i6-JiLtimes.getLengthPQJiRRQ : $lement time6P$lementQtimes.itemPiQJ 9orecast forecast6neE "orecastPQJ forecasts.addPforecastQJ forecast.setTimePtime.get"irstChildPQ.get&odeValuePQQJ ;

0&2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

%ode)ist temps6doc.get+lementsByTag&ameP7value7QJ for Pint i6-JiLtemps.getLengthPQJiRRQ : $lement temp6P$lementQtemps.itemPiQJ 9orecast forecast6forecasts.getPiQJ ; forecast.setTempPneE IntegerPtemp.get"irstChildPQ.get&odeValuePQQQJ

%ode)ist icons6doc.get+lementsByTag&ameP7icon-link7QJ for Pint i6-JiLicons.getLengthPQJiRRQ : $lement icon6P$lementQicons.itemPiQJ 9orecast forecast6forecasts.getPiQJ forecast.setIconPicon.get"irstChildPQ.get&odeValuePQQJ ; ; : returnPforecastsQJ

class 9etch9orecast&ask eGtends AsFnc&askL)ocation8 Void8 ArraF)istL9orecastMM $Gception e6nullJ @eather)istener listener6nullJ "etch"orecastTaskP@eather)istener listenerQ : this.listener6listenerJ ; O"verride protected ArraF)istL9orecastM doInBackgroundP)ocation... locsQ : ArraF)istL9orecastM result6nullJ trF : )ocation loc6locsA-BJ 2tring url62tring.formatPformat8 loc.getLatitudePQ8 loc.getLongitudePQQJ !ttpDet get#ethod6neE (ttp etPurlQJ ?esponse!andlerL2tringM response!andler6neE Basic%esponse(andlerPQJ 2tring response4odF6client.executePget#ethod8 response!andlerQJ result6'uild"orecastsPresponse4odFQJ ; catch P$Gception eQ : this.e6eJ ; ; returnPresultQJ

O"verride protected void on)ost+xecutePArraF)istL9orecastM forecastQ :

0&7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

if PlistenerX6nullQ : if PforecastX6nullQ : listener.update"orecastPforecastQJ ; if PeX6nullQ : listener.handle+rrorPeQJ ;

; ; ; ;

Most o&

is merely "oing the Web ser!i'e reRuest using an" an !ttpDet obGe't, plus using the @>M parser to 'on!ert the FML into the 9orecast obGe'ts. +o=e!er, this is =rappe" in a 9etch9orecast&ask S an AsFnc&ask that =ill "o the +55# operation an" parsing on a ba'kgroun" threa". 0n on(ost$GecutePQ, the task in!okes our @eather)istener, either to supply the &ore'ast ( update9orecastPQ) or han" o!er an $Gception that =as raise" (handle$rrorPQ).
=efault!ttp+lient

this

The Service
5he @eather2ervice, there&ore, is &airly short, =ith the business logi' "elegate" to @eather4inder,
package com.commonsEare.android.EeatherJ import import import import android.app.2erviceJ android.content.IntentJ android.os.I4inderJ java.util.ArraF)istJ

public class @eather2ervice eGtends 2ervice : private final @eather4inder binder6neE #eatherBinderPQJ O"verride public void onCreatePQ : super.onCreatePQJ ; binder.onCreatePthisQJ

O"verride public I4inder onBindPIntent intentQ : returnPbinderQJ ;

0&8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

O"verride public void onDestroyPQ : super.onDestroyPQJ ; ; binder.onDestroyPQJ

>ur on+reatePQ an" on=estroFPQ metho"s "elegate to the @eather4inder, an" on4indPQ returns the @eather4inder itsel&.

-sin! the Service


>n the sur&a'e, the @eather=emo a'ti!ity shoul" be simple,

1in" to the ser!i'e in on+reatePQ Arrange to get 8#% &i;es, in the &orm o& )ocation obGe'ts When a &i; 'omes in, use the @eather4inder to get a &ore'ast, 'on!ert it to +5ML, an" "isplay it in a @ebVieE $nbin" &rom the ser!i'e in on=estroFPQ

+o=e!er, our "e'ision to use the bin"ing pattern an" to ha!e the a'ti!ity "eal =ith the ba'kgroun" threa" means there is more =ork in!ol!e" than those bullet points. *irst, here is the &ull @eather=emo implementation,
package com.commonsEare.android.EeatherJ import import import import import import import import import import import import android.app.ActivitFJ android.app.Alert=ialogJ android.content.+omponent%ameJ android.content.+onteGtJ android.content.IntentJ android.content.Intent9ilterJ android.content.2ervice+onnectionJ android.location.)ocationJ android.location.)ocation)istenerJ android.location.)ocation#anagerJ android.os.AsFnc&askJ android.os.4undleJ

0&:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

import import import import import import

android.os.=ead"bject$GceptionJ android.os.?emote$GceptionJ android.os.I4inderJ android.util.)ogJ android.Eebkit.@ebVieEJ java.util.ArraF)istJ

public class @eather=emo eGtends ActivitF : private @ebVieE broEserJ private )ocation#anager mgr6nullJ private 2tate state6nullJ private boolean is+onfiguration+hanging6falseJ O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ broEser6P@ebVieEQfindViewByIdP?.id.EebkitQJ state6P2tateQgetLast&onConfigurationInstance PQJ if Pstate66nullQ : state6neE StatePQJ get$pplicationContextPQ .'indSer!icePneE IntentPthis8 @eather2ervice.classQ8 state.svc+onn8 4I%= A3&" +?$A&$QJ ; else if Pstate.last9orecastX6nullQ : show"orecastPQJ ; state.attachPthisQJ mgr6P)ocation#anagerQgetSystemSer!iceP)"+A&I"% 2$?VI+$QJ mgr.re-uestLocation*pdatesP)ocation#anager.D(2 (?"VI=$?8 C0-----8 1---8 on)ocation+hangeQJ

O"verride public void onDestroyPQ : super.onDestroyPQJ if PmgrX6nullQ : mgr.remo!e*pdatesPon)ocation+hangeQJ ; if PXis+onfiguration+hangingQ : get$pplicationContextPQ.un'indSer!icePstate.svc+onnQJ ; ; O"verride public "bject on%etain&onConfigurationInstance PQ : is+onfiguration+hanging6trueJ

0-<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

returnPstateQJ

private void goBlooeyP&hroEable tQ : Alert=ialog.4uilder builder6neE Alert=ialog.BuilderPthisQJ builder .setTitleP7$GceptionX7Q .setMessagePt.toStringPQQ .set)ositi!eButtonP7"H78 nullQ .showPQJ

static 2tring generate)agePArraF)istL9orecastM forecastsQ : 2tring4uilder buf?esult6neE StringBuilderP7LhtmlMLbodFMLtableM7QJ buf?esult.appendP7LtrMLth Eidth6T7.-\T7M&imeL/thM7R 7LthM&emperatureL/thMLthM9orecastL/thML/trM7QJ for P9orecast forecast : forecastsQ : buf?esult.appendP7LtrMLtd align6T7centerT7M7QJ buf?esult.appendPforecast.getTimePQQJ buf?esult.appendP7L/tdMLtd align6T7centerT7M7QJ buf?esult.appendPforecast.getTempPQQJ buf?esult.appendP7L/tdMLtdMLimg src6T77QJ buf?esult.appendPforecast.getIconPQQJ buf?esult.appendP7T7ML/tdML/trM7QJ ; buf?esult.appendP7L/tableML/bodFML/htmlM7QJ returnPbuf?esult.toStringPQQJ ; void show"orecastPQ : broEser.loadData#ithBase*%LPnull8 state.last9orecast8 7teGt/html78 73&9-,78 nullQJ ; )ocation)istener on)ocation+hange6neE LocationListenerPQ : public void onLocationChangedP)ocation locationQ : if Pstate.EeatherX6nullQ : state.Eeather.get"orecastPlocation8 stateQJ ; else : )og.wPgetClassPQ.get&amePQ8 73nable to fetch forecast [ no @eather4inder7QJ ; ; public void on)ro!iderDisa'ledP2tring providerQ : // reUuired for interface8 not used ;

0-*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

public void on)ro!ider+na'ledP2tring providerQ : // reUuired for interface8 not used ; public void onStatusChangedP2tring provider8 int status8 4undle eGtrasQ : // reUuired for interface8 not used ; ;J static class 2tate implements @eather)istener : @eather4inder Eeather6nullJ @eather=emo activitF6nullJ 2tring last9orecast6nullJ void attachP@eather=emo activitFQ : this.activitF6activitFJ ; public void update"orecastPArraF)istL9orecastM forecastQ : last9orecast6generate)agePforecastQJ activitF.show"orecastPQJ ; public void handle+rrorP$Gception eQ : activitF.goBlooeyPeQJ ; 2ervice+onnection svc+onn6neE Ser!iceConnectionPQ : public void onSer!iceConnectedP+omponent%ame class%ame8 I4inder raE4inderQ : Eeather6P@eather4inderQraE4inderJ ; public void onSer!iceDisconnectedP+omponent%ame class%ameQ : Eeather6nullJ ;

;J ; ;

2o=, let us look at the highlights o& the ser!i'e 'onne'tion an" the ba'kgroun" threa".

% n !in! the St te
We nee" to ensure that our 2ervice+onnection 'an be passe" bet=een a'ti!ity instan'es on a 'on&iguration 'hange. +en'e, =e ha!e a 2tate stati'

0-&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

inner 'lass to hol" that, plus t=o other bits o& in&ormation, the ActivitF the state is asso'iate" =ith, an" a 2tring sho=ing the last &ore'ast =e retrie!e",
static class 2tate implements @eather)istener : @eather4inder Eeather6nullJ @eather=emo activitF6nullJ 2tring last9orecast6nullJ void attachP@eather=emo activitFQ : this.activitF6activitFJ ; public void update"orecastPArraF)istL9orecastM forecastQ : last9orecast6generate)agePforecastQJ activitF.show"orecastPQJ ; public void handle+rrorP$Gception eQ : activitF.goBlooeyPeQJ ; 2ervice+onnection svc+onn6neE Ser!iceConnectionPQ : public void onSer!iceConnectedP+omponent%ame class%ame8 I4inder raE4inderQ : Eeather6P@eather4inderQraE4inderJ ; public void onSer!iceDisconnectedP+omponent%ame class%ameQ : Eeather6nullJ ;

;J ;

5he last9orecast 2tring is to allo= us to re-"isplay the generate" +5ML a&ter a 'on&iguration 'hange. >ther=ise, i& the user rotates the s'reen, =e =ill lose our &ore'ast (only hel" in the ol" instan'e7s @ebVieE) an" either ha!e to retrie!e a &resh one or =ait &or a 8#% &i;. We return this 2tate obGe't &rom on?etain%on+onfigurationInstancePQ,
O"verride public "bject on%etain&onConfigurationInstance PQ : is+onfiguration+hanging6trueJ ; returnPstateQJ

0--

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

0n on+reatePQ, i& there is no non-'on&iguration instan'e, =e 'reate a &resh 2tate an" bin" to the ser!i'e, sin'e =e "o not ha!e a ser!i'e 'onne'tion at present. >n the other han", i& on+reatePQ gets a 2tate &rom get)ast%on+onfigurationInstancePQ, it simply hol"s onto that state an" reloa"s our &ore'ast in the @ebVieE. 0n either 'ase, on+reatePQ in"i'ates to the 2tate that the ne= a'ti!ity instan'e is the 'urrent one,
O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ broEser6P@ebVieEQfindViewByIdP?.id.EebkitQJ state6P2tateQgetLast&onConfigurationInstance PQJ if Pstate66nullQ : state6neE StatePQJ get$pplicationContextPQ .'indSer!icePneE IntentPthis8 @eather2ervice.classQ8 state.svc+onn8 4I%= A3&" +?$A&$QJ ; else if Pstate.last9orecastX6nullQ : show"orecastPQJ ; state.attachPthisQJ mgr6P)ocation#anagerQgetSystemSer!iceP)"+A&I"% 2$?VI+$QJ mgr.re-uestLocation*pdatesP)ocation#anager.D(2 (?"VI=$?8 C0-----8 1---8 on)ocation+hangeQJ

Time to -n=ind
We bin" to the ser!i'e =hen on+reatePQ is 'alle", i& it "i" not re'ei!e a 2tate !ia get)ast%on+onfigurationInstancePQ (in =hi'h 'ase, =e are alrea"y boun"). 5his begs the Ruestion, =hen "o =e unbin" &rom the ser!i'eH We =ant to unbin" =hen the a'ti!ity is "estroye"...but not i& the a'ti!ity is being "estroye" be'ause o& a 'on&iguration 'hange. $n&ortunately, there is no built-in =ay to make that "etermination &rom on=estroFPQ. 5here is an is9inishingPQ metho" you 'an 'all on an ActivitF, =hi'h =ill return true i& the a'ti!ity is going a=ay &or goo" or false
0-%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Basic Service Patterns

other=ise. 5his "oes return false &or a 'on&iguration 'hange, but it =ill also return false i& the a'ti!ity is being "estroye" to &ree up AM an" the user might be able to return to it !ia the 1ACD button. 5his is =hy on?etain%on+onfigurationInstancePQ is+onfiguration+hanging &lag in @eather=emo to true. 5hat &lag false. We then 'he'k that &lag to see i& =e shoul" unbin" &rom or not, &lips a is initially the ser!i'e

O"verride public void onDestroyPQ : super.onDestroyPQJ if PmgrX6nullQ : mgr.remo!e*pdatesPon)ocation+hangeQJ ; if PXis+onfiguration+hangingQ : get$pplicationContextPQ.un'indSer!icePstate.svc+onnQJ ; ;

0-0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 19

Alerting >sers ;ia ?otifications

#op-up messages. 5ray i'ons an" their asso'iate" MbubbleM messages. 1oun'ing "o'k i'ons. ?ou are no "oubt use" to programs trying to get your attention, sometimes &or goo" reason. ?our phone also probably 'hirps at you &or more than Gust in'oming 'alls, lo= battery, alarm 'lo'ks, appointment noti&i'ations, in'oming te;t message or email, et'. 2ot surprisingly, An"roi" has a =hole &rame=ork &or "ealing =ith these sorts o& things, 'olle'ti!ely 'alle" Mnoti&i'ationsM.

?otification Configuration
A ser!i'e, running in the ba'kgroun", nee"s a =ay to let users kno= something o& interest has o''urre", su'h as =hen email has been re'ei!e". Moreo!er, the ser!i'e may nee" some =ay to steer the user to an a'ti!ity =here they 'an a't upon the e!ent S rea"ing a re'ei!e" message, &or e;ample. *or this, An"roi" supplies status bar i'ons, &lashing lights, an" other in"i'ators 'olle'ti!ely kno=n as Mnoti&i'ationsM. ?our 'urrent phone may =ell ha!e su'h i'ons, to in"i'ate battery li&e, signal strength, =hether 1luetooth is enable", an" the like. With An"roi", appli'ations 'an a"" their o=n status bar i'ons, =ith an eye to=ar"s ha!ing them appear only =hen nee"e" (e.g., a message has arri!e").
0-7
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

0n An"roi", you 'an raise noti&i'ations !ia the %otification#anager. 5he %otification#anager is a system ser!i'e. 5o use it, you nee" to get the ser!i'e obGe't !ia get2Fstem2erviceP%"&I9I+A&I"% 2$?VI+$Q &rom your a'ti!ity. 5he %otification#anager gi!es you three metho"s, one to raise a %otification (notifFPQ) an" t=o to get ri" o& an e;isting %otification (cancelPQ an" cancelAllPQ). 5he notifFPQ metho" takes a %otification, =hi'h is a "ata stru'ture that spells out =hat &orm your pestering shoul" take S the 'apabilities o& this obGe't are "es'ribe" in the &ollo=ing se'tions.

H rd# re "oti.ic tions


?ou 'an &lash LE@s on the "e!i'e by setting lights to true, also spe'i&ying the 'olor (as an SA?D4 !alue in ledA?D4) an" =hat pattern the light shoul" blink in (by pro!i"ing o&&Pon "urations in millise'on"s &or the light !ia led"n#2 an" led"ff#2). 2ote, ho=e!er, that An"roi" "e!i'es =ill apply Mbest e&&ortsM to meet your 'olor reRuest, meaning that "i&&erent "e!i'es may gi!e you "i&&erent 'olors, or perhaps no 'ontrol o!er 'olor at all. *or e;ample, the Motorola CL0J only has a =hite LE@, so you 'an ask &or any 'olor you =ant, an" you =ill get =hite. 2ote that you =ill ha!e to > ( W) in the %otification.9)AD 2!"@ )ID!&2 !alue into the publi' flags &iel" on the %otification obGe't &or &lashing the LE@ to =ork. ?ou 'an play a soun", using a 3ri to a pie'e o& 'ontent hel", perhaps, by a +ontent#anager (sound). 5hink o& this as a MringtoneM &or your appli'ation. ?ou 'an !ibrate the "e!i'e, 'ontrolle" !ia a longAB in"i'ating the onPo&& patterns (in millise'on"s) &or the !ibration ( vibrate). ?ou might "o this by "e&ault, or you might make it an option the user 'an 'hoose =hen 'ir'umstan'es reRuire a more subtle noti&i'ation than a ringtone. 5o use this, though, you =ill nee" to reRuest the VI4?A&$ permission.

0-8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

All o& these, by "e&ault, happen on'e (e.g., one LE@ &lash, one playba'k o& the soun"). 0& you =ant to ha!e them persist until the %otification is 'an'ele", you =ill nee" to set the flags publi' &iel" in your %otification to in'lu"e 9)AD I%2I2&$%&. 0nstea" o& manually spe'i&ying the har"=are options, you 'an also use the defaults &iel" in the %otification, setting it to =$9A3)& )ID!&2, =$9A3)& 2"3%=, =$9A3)& VI4?A&$, or =$9A3)& A)), =hi'h =ill use plat&orm "e&aults &or all har"=are options.

Icons
While the &lashing lights, soun"s, an" !ibrations are aime" at getting somebo"y to look at the "e!i'e, i'ons are "esigne" to take them the ne;t step an" tell them =hat7s so important. 5o set up an i'on &or a %otification, you nee" to set t=o publi' &iel"s, icon, =here you pro!i"e the i"enti&ier o& a =raEable resour'e representing the i'on, an" contentIntent, =here you supply a (endingIntent to be raise" =hen the i'on is 'li'ke". A (endingIntent is a =rapper aroun" a regular Intent that allo=s the Intent to be in!oke" later, by another pro'ess, to start an a'ti!ity or =hate!er. 5ypi'ally, a %otification =ill trigger an a'ti!ity, in =hi'h 'ase you =oul" 'reate the (endingIntent !ia the stati' getActivitFPQ metho" an" gi!e it an Intent that i"enti&ies one o& your a'ti!ities. 5hat being sai", you 'oul" ha!e the %otification sen" a broa"'ast Intent instea" by using a get4roadcastPQ !ersion o& a (endingIntent. ?ou 'an also supply a te;t blurb to appear =hen the i'on is put on the status bar (ticker&eGt). 0& you =ant all three, the simpler approa'h is to 'all set)atest$ventInfoPQ, =hi'h =raps all three o& those in a single 'all. ?ou 'an also set a !alue in the number publi' &iel" o& your %otification. 5his =ill 'ause the number you supply to be "ra=n o!er top o& the icon in one
0-:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

'orner. 5his is use", &or e;ample, to sho= the number o& unrea" email messages, to sa!e you &rom ha!ing to ha!e a bun'h o& "i&&erent i'ons, one &or ea'h possible number o& unrea" messages. 1y "e&ault, the number =ill be ignore" an" not use". 2ote that the siKe o& the i'ons use" =ith a %otification 'hange" =ith An"roi" 2... 0t use" to be that 2Ap; sRuare =as the "esire" siKe. 2o=, they pre&er per-"ensity i'ons in a more re'tangular shape,

2<p; sRuare (insi"e a 2<p; =i"e by .8p; high boun"ing bo;) &or high-"ensity s'reens 1/p; sRuare (insi"e a 1/p; by 2Ap; boun"ing bo;) &or me"ium"ensity s'reens 12p; sRuare (insi"e a 12p; by 13p; boun"ing bo;) &or lo=-"ensity s'reens

Appli'ations &ollo=ing these rules =ill =ant to use spe'i&i' resour'e sets &or the ne= i'ons,
res/draEable-hdpi-v*/ res/draEable-mdpi-v*/ res/draEable-ldpi-v*/ res/draEable/

&or the high-"ensity An"roi" 2.. e"itions &or the me"ium-"ensity An"roi" 2.. e"itions &or the lo=-"ensity An"roi" 2.. e"itions

&or the i'on to use on An"roi" 2.2 an" earlier

More "etails on gui"elines &or all i'ons, in'lu"ing status bar i'ons, 'an be &oun" in the An"roi" "e!eloper "o'umentation.

?otifications in Action
Let us no= take a peek at the %otifications/%otifF1 sample proGe't, in parti'ular the %otifF=emo 'lass,
package com.commonsEare.android.notifFJ import android.app.ActivitFJ import android.app.%otificationJ

0%<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

import import import import import

android.app.%otification#anagerJ android.app.(endingIntentJ android.content.IntentJ android.os.4undleJ android.vieE.VieEJ

public class %otifF=emo eGtends ActivitF : private static final int %"&I95 #$ I=61CC/J private int count6-J private %otification#anager mgr6nullJ O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ mgr6P%otification#anagerQgetSystemSer!iceP%"&I9I+A&I"% 2$?VI+$QJ ; public void notifyMePVieE vQ : %otification note6neE &otificationP?.draEable.stat notifF chat8 72tatus messageX78 2Fstem.currentTimeMillisPQQJ (endingIntent i6(endingIntent.get$cti!ityPthis8 -8 neE IntentPthis8 %otifF#essage.classQ8 -QJ note.setLatest+!entInfoPthis8 7%otification &itle78 7&his is the notification message78 iQJ note.number6RRcountJ note.vibrate6neE longAB :.--)8 >--)8 >--)8 .--);J note.flagsW6%otification.9)AD A3&" +A%+$)J ; mgr.notifyP%"&I95 #$ I=8 noteQJ

public void clear&otificationPVieE vQ : mgr.cancelP%"&I95 #$ I=QJ ; ;

5his a'ti!ity sports t=o large buttons, one to ki'k o&& a noti&i'ation a&ter a &i!e-se'on" "elay, an" one to 'an'el that noti&i'ation (i& it is a'ti!e),

0%*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

"igure *%81 The ?otify/emo activity main vie)

Creating the noti&i'ation, in notifF#ePQ, is a''omplishe" in a han"&ul o& steps, 1. Create a %otification obGe't =ith our i'on, a message to &lash on the status bar as the noti&i'ation is raise", an" the time asso'iate" =ith this e!ent

2. Create a (endingIntent that =ill trigger the "isplay o& another a'ti!ity (%otifF#essage) .. $se set)atest$ventInfoPQ to spe'i&y that, =hen the noti&i'ation is 'li'ke" on, =e are to "isplay a 'ertain title an" message, an" i& that is 'li'ke" on, =e laun'h the (endingIntent <. $p"ate the MnumberM asso'iate" =ith the noti&i'ation A. %pe'i&y a !ibration pattern S A00ms on, 200ms o&&, 200ms on, A00ms o&& /. 0n'lu"e 9)AD A3&" +A%+$) in the %otification obGe't7s flags &iel"

0%&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

4. 5ell the %otification#anager (obtaine" in on+reatePQ)to "isplay the noti&i'ation +en'e, i& =e 'li'k the top button, our i'on =ill appear in the status bar, brie&ly along =ith our status message.

"igure *%:1 ,ur notification as it appears on the status bar@ )ith our status message

A&ter the status message goes a=ay, the i'on =ill ha!e our number (initially 1) superimpose" on the lo=er-right 'orner S you might use this to signi&y the number o& unrea" messages.

0%-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

"igure *0<1 ,ur notification )ith the superimposed number

0& you "rag "o=n the i'on, a "ra=er =ill appear beneath the status bar. @rag that "ra=er all the =ay to the bottom o& the s'reen to sho= the outstan"ing noti&i'ations, in'lu"ing our o=n,

0%%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

"igure *0*1 The notifications dra)er@ fully expanded@ )ith our notification

0& you 'li'k on the noti&i'ation entry in the "ra=er, you7ll be taken to a tri!ial a'ti!ity "isplaying a message S though in a real appli'ation, this a'ti!ity =oul" "o something use&ul base" upon the e!ent that o''urre" (e.g., take users to the ne=ly-arri!e" mail messages). Cli'king on the 'an'el button, or 'li'king on the Clear button in the "ra=er, or 'li'king on the noti&i'ation entry in the "ra=er, =ill remo!e the i'on &rom the status bar. 5he latter is be'ause =e in'lu"e" 9)AD A3&" +A%+$) in the %otification, in"i'ating that a tap on the "ra=er entry shoul" 'an'el the %otification itsel&.

Staying in the "oreground


2oti&i'ations ha!e another use, keeping sele't ser!i'es aroun". %er!i'es "o not li!e &ore!er. An"roi" may terminate your appli'ation7s pro'ess to &ree up memory in an emergen'y situation, or Gust be'ause it
0%0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

seems to ha!e been hanging aroun" memory too long. 0"eally, you "esign your ser!i'es to "eal =ith the &a't that they may not run in"e&initely. +o=e!er, some ser!i'es =ill be misse" by the user i& they mysteriously !anish. *or e;ample, the "e&ault musi' player appli'ation that ships =ith An"roi" uses a ser!i'e &or the a'tual musi' playba'k. 5hat =ay, the user 'an listen to musi' =hile 'ontinuing to use their phone &or other purposes. 5he ser!i'e only stops =hen the user goes in an" presses the stop button in the musi' player a'ti!ity. 0& that ser!i'e =ere to be shut "o=n une;pe'te"ly, the user might =on"er =hat is =rong. %er!i'es like this 'an "e'lare themsel!es as being part o& the M&oregroun"M. 5his =ill 'ause their priority to rise an" make them less likely to be bumpe" out o& memory. 5he tra"e-o&& is that the ser!i'e has to maintain a %otification, so the user kno=s that this ser!i'e is 'laiming part o& the &oregroun". An", i"eally, that %otification pro!i"es an easy path ba'k to some a'ti!ity =here the user 'an stop the ser!i'e. 5o "o this, on on+reatePQ o& your ser!i'e (or =here!er else in the ser!i'e7s li&e it =oul" make sense), 'all start9oregroundPQ. 5his takes a %otification an" a lo'ally-uniRue integer, Gust like the notifFPQ metho" on %otification#anager. 0t 'auses the %otification to appear an" mo!es the ser!i'e into &oregroun" priority. Later on, you 'an 'all stop9oregroundPQ to return to normal priority. 2ote that this metho" =as a""e" =ith An"roi" 2.0 (A#0 le!el A). 5here =as an earlier metho", set9oregroundPQ, that per&orms a similar &un'tion in earlier !ersions o& An"roi".

5 $ePl yer4 Redu0


0n the 'hapter on ser!i'e patterns, =e sho=e" a &ake musi' player, implemente" =ith an ActivitF (9ake(laFer) an" a 2ervice ((laFer2ervice). 5he (laFer2ervice is a'tually =hat is playing the musi', so the musi' 'an play e!en =hile the 9ake(laFer a'ti!ity is gone.

0%2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

+o=e!er, An"roi" may not 'onsi"er (laFer2ervice to be part o& the user e;perien'e, sin'e ser!i'es normally intera't !ery little "ire'tly =ith users. 5his means An"roi" may run (laFer2ervice in a =ay that 'aps C#$ usage (not ne'essarily ba") an" might ele't to shut "o=n the ser!i'e i& it thinks it has been running too long (probably ba"). 5he ans=er is to use start9oregroundPQ an" stop9oregroundPQ. We 'an 'all start9oregroundPQ =hen =e start the musi' playing in our plaFPQ metho",
private void playP2tring plaFlist8 boolean use2huffleQ : if PXis(laFingQ : )og.wPgetClassPQ.get&amePQ8 7Dot to plaFPQX7QJ is(laFing6trueJ %otification note6neE &otificationP?.draEable.stat notifF chat8 7+an Fou hear the musicN78 2Fstem.currentTimeMillisPQQJ Intent i6neE IntentPthis8 9ake(laFer.classQJ i.set"lagsPIntent.9)AD A+&IVI&5 +)$A? &"(W Intent.9)AD A+&IVI&5 2I%D)$ &"(QJ (endingIntent pi6(endingIntent.get$cti!ityPthis8 -8 i8 -QJ note.setLatest+!entInfoPthis8 79ake (laFer78 7%oE (laFing: T73mmmm8 %othingT778 piQJ note.flagsW6%otification.9)AD %" +)$A?J ; ; start"oregroundP1CC/8 noteQJ

5he plus si"e is that our ser!i'e =ill ha!e more C#$ a!ailability i& nee"e" an" =ill be &ar less likely to be kille". 5he user =ill see an i'on in the status bar, though. 0& they sli"e "o=n the noti&i'ation "ra=er an" tap on our %otification7s entry, they =ill be taken ba'k to 9ake(laFer S the e;isting instan'e i& there is one, other=ise a &resh instan'e, 'ourtesy o& our 0ntent &lags (Intent.9)AD A+&IVI&5 +)$A? &"(W Intent.9)AD A+&IVI&5 2I%D)$ &"(). *or a musi' player, this $0 pattern is a goo" thing, as it makes it easy &or the user to Rui'kly go ba'k to stop the musi' =hen nee"e". %topping the musi', !ia our stopPQ metho", =ill 'all stop9oregroundPQ,

0%7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

private void stopPQ : if Pis(laFingQ : )og.wPgetClassPQ.get&amePQ8 7Dot to stopPQX7QJ is(laFing6falseJ stop"oregroundPtrueQJ ; ;

5he true !alue passe" to stop9oregroundPQ tells An"roi" to remo!e the %otification, =hi'h =oul" be the typi'al approa'h &or this pattern.

?otifications and 3oneycomb


5he +oney'omb $0 intro"u'e" in An"roi" ..0 supports noti&i'ations, Gust like all pre!ious !ersions o& An"roi". +o=e!er, the user e;perien'e is a bit "i&&erent, o=ing to the tablet metaphor an" its a""itional s'reen spa'e. +ere is the unmo"i&ie" %otifications/%otifF1 proGe't, as seen in the An"roi" ..0 emulator,

"igure *0&1 ?otify* as seen on an Android -1< emulator

0%8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

>ther than the An"roi" ..0 !ersion o& the status bar, an" the e;tra-huge buttons, this is no "i&&erent than =hat you =oul" see on a pre-+oney'omb phone. 2o=, i& =e 'li'k the top button, our 2oti&i'ation appears, this time in the lo=er right, =ith the i'on an" ti'ker te;t,

"igure *0-1 ?otify* )ith a notification being added

2ote that i& the user taps the ti'ker, it triggers your (endingIntent, Gust as i& they ha" tappe" on the noti&i'ation "ra=er entry on a phone. When the ti'ker is remo!e", our i'on remains...=ithout the number,

0%:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

"igure *0%1 ?otify* )ith a number#less notification icon

0& the user taps that i'on, a noti&i'ation "ra=er-style pop-up appears nearby,

"igure *001 ?otify* )ith the notification content appearing

00<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Alerting >sers ;ia ?otifications

5apping the i'on or the te;t triggers the (endingIntent, =hile 'li'king the F on the right 'an'els this %otification.

00*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1:

CeLuesting and CeLuiring Permissions

0n the late 13307s, a =a!e o& !iruses sprea" through the 0nternet, "eli!ere" !ia email, using 'onta't in&ormation 'ulle" &rom Mi'roso&t >utlook. A !irus =oul" simply email 'opies o& itsel& to ea'h o& the >utlook 'onta'ts that ha" an email a""ress. 5his =as possible be'ause, at the time, >utlook "i" not take any steps to prote't "ata &rom programs using the >utlook A#0, sin'e that A#0 =as "esigne" &or or"inary "e!elopers, not !irus authors. 2o=a"ays, many appli'ations that hol" onto 'onta't "ata se'ure that "ata by reRuiring that a user e;pli'itly grant rights &or other programs to a''ess the 'onta't in&ormation. 5hose rights 'oul" be grante" on a 'ase-by-'ase basis or all at on'e at install time. An"roi" is no "i&&erent, in that it reRuires permissions &or appli'ations to rea" or =rite 'onta't "ata. An"roi"7s permission system is use&ul =ell beyon" 'onta't "ata, an" &or 'ontent pro!i"ers an" ser!i'es beyon" those supplie" by the An"roi" &rame=ork. ?ou, as an An"roi" "e!eloper, =ill &reRuently nee" to ensure your appli'ations ha!e the appropriate permissions to "o =hat you =ant to "o =ith other appli'ations7 "ata. ?ou may also ele't to reRuire permissions &or other appli'ations to use your "ata or ser!i'es, i& you make those a!ailable to other An"roi" 'omponents. 5his 'hapter 'o!ers ho= to a''omplish both these en"s.
00Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

CeLuesting and CeLuiring Permissions

+other@ +ay F
eRuesting the use o& other appli'ations7 "ata or ser!i'es reRuires the useselement to be a""e" to your Android#anifest.Gml &ile. ?our mani&est may ha!e Kero or more uses-permission elements, all as "ire't 'hil"ren o& the root manifest element.
permission

5he uses-permission element takes a single attribute, android:name, =hi'h is the name o& the permission your appli'ation reRuires,
Luses-permission android:name67android.permission.A++$22 )"+A&I"%7 /M

5he sto'k system permissions all begin =ith android.permission an" are liste" in the An"roi" %@D "o'umentation &or #anifest.permission. 5hir"party appli'ations may ha!e their o=n permissions, =hi'h hope&ully they ha!e "o'umente" &or you. +ere are some o& the permissions =e =ill see in this book,
I%&$?%$&,

i& your appli'ation =ishes to a''ess the 0nternet through any means, &rom ra= Ca!a so'kets through the @ebVieE =i"get
@?I&$ $]&$?%A) 2&"?AD$, A++$22 +"A?2$ )"+A&I"%

&or =riting "ata to the %@ 'ar" (or =hate!er the "e!i'e has "esignate" as Me;ternal storageM) =here the "e!i'e is an" A++$22 9I%$ )"+A&I"%, &or "etermining

+A)) (!"%$,

to allo= the appli'ation to pla'e phone 'alls "ire'tly, =ithout user inter!ention

#ermissions are 'on&irme" at the time the appli'ation is installe" S the user =ill be prompte" to 'on&irm it is >D &or your appli'ation to "o =hat the permission 'alls &or. +en'e, it is important &or you to ask &or as &e= permissions as possible an" to Gusti&y those you ask &or, so users "o not ele't to skip installing your appli'ation be'ause you ask &or too many unne'essary permissions. 5his prompt =ill not appear =hen loa"ing an appli'ation !ia $%1, su'h as "uring "e!elopment.

00%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CeLuesting and CeLuiring Permissions

0& you "o not ha!e the "esire" permission an" try to "o something that nee"s it, you shoul" get a 2ecuritF$Gception in&orming you o& the missing permission. 2ote that you =ill only &ail on a permission 'he'k i& you &orgot to ask &or the permission S it is impossible &or your appli'ation to be running an" not ha!e been grante" your reRueste" permissions.

3alt! Who (oes ThereF


5he other si"e o& the 'oin, o& 'ourse, is to se'ure your o=n appli'ation. 0& your appli'ation is mostly a'ti!ities, se'urity may be Gust an 6outboun"9 thing, =here you reRuest the right to use resour'es o& other appli'ations. 0&, on the other han", you put 'ontent pro!i"ers or ser!i'es in your appli'ation, you =ill =ant to implement 6inboun"9 se'urity to 'ontrol =hi'h appli'ations 'an "o =hat =ith the "ata. 2ote that the issue here is less about =hether other appli'ations might 6mess up9 your "ata, but rather about pri!a'y o& the user7s in&ormation or use o& ser!i'es that might in'ur e;pense. 5hat is =here the sto'k permissions &or built-in An"roi" appli'ations are &o'use" S 'an you rea" or mo"i&y 'onta'ts, 'an you sen" %M%, et'. 0& your appli'ation "oes not store in&ormation that might be 'onsi"ere" pri!ate, se'urity is less an issue. 0&, on the other han", your appli'ation stores pri!ate "ata, su'h as me"i'al in&ormation, se'urity is mu'h more important. 5he &irst step to se'uring your o=n appli'ation using permissions is to "e'lare sai" permissions, on'e again in the Android#anifest.Gml &ile. 0n this 'ase, instea" o& uses-permission, you a"" permission elements. >n'e again, you 'an ha!e Kero or more permission elements, all as "ire't 'hil"ren o& the root manifest element. @e'laring a permission is slightly more 'ompli'ate" than using a permission. 5here are three pie'es o& in&ormation you nee" to supply, 1. 5he symboli' name o& the permission. 5o keep your permissions &rom 'olli"ing =ith those &rom other appli'ations, you shoul" use your appli'ation7s Ca!a namespa'e as a pre&i;

000

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CeLuesting and CeLuiring Permissions

2. A label &or the permission, something short that =oul" be un"erstan"able by users .. A "es'ription &or the permission, something a =ee bit longer that is un"erstan"able by your users
Lpermission android:name67vnd.tlagencF.sekrits.2$$ 2$H?I&27 android:label67Ostring/see sekrits label7 android:description67Ostring/see sekrits description7 /M

5his "oes not en&or'e the permission. ather, it in"i'ates that it is a possible permissionT your appli'ation must still &lag se'urity !iolations as they o''ur.

En.orcin! Permissions vi the % ni.est


5here are t=o =ays &or your appli'ation to en&or'e permissions, "i'tating =here an" un"er =hat 'ir'umstan'es they are reRuire". 5he easier one is to in"i'ate in the mani&est =here permissions are reRuire". A'ti!ities, ser!i'es, an" re'ei!ers 'an all "e'lare an attribute name" android:permission, =hose !alue is the name o& the permission that is reRuire" to a''ess those items,
LactivitF android:name67.2ekritApp7 android:label67&op 2ekrit7 android:permission67vnd.tlagencF.sekrits.2$$ 2$H?I&27M Lintent-filterM Laction android:name67android.intent.action.#AI%7 /M LcategorF android:name67android.intent.categorF.)A3%+!$?7 /M L/intent-filterM L/activitFM

>nly appli'ations that ha!e reRueste" your in"i'ate" permission =ill be able to a''ess the se'ure" 'omponent. 0n this 'ase, 6a''ess9 means,

A'ti!ities 'annot be starte" =ithout the permission

002

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CeLuesting and CeLuiring Permissions

%er!i'es 'annot be starte", stoppe", or boun" to an a'ti!ity =ithout the permission 0ntent re'ei!ers ignore messages sent !ia send4roadcastPQ unless the sen"er has the permission

En.orcin! Permissions Else#here


0n your 'o"e, you ha!e t=o a""itional =ays to en&or'e permissions. permissions on a per-'all basis !ia 5his returns ($?#I22I"% D?A%&$= or on =hether the 'aller has the permission you spe'i&ie". *or e;ample, i& your ser!i'e implements separate rea" an" =rite metho"s, you 'oul" reRuire separate rea" !ersus =rite permissions in 'o"e by 'he'king those metho"s &or the permissions you nee" &rom Ca!a.
check+alling(ermissionPQ. ($?#I22I"% =$%I$= "epen"ing

?our

ser!i'es

'an

'he'k

Also, you 'an in'lu"e a permission =hen you 'all send4roadcastPQ. 5his means that eligible broa"'ast re'ei!ers must hol" that permissionT those =ithout the permission are ineligible to re'ei!e it. We =ill e;amine send4roadcastPQ in greater "etail else=here in this book.

+ay

See .our /ocumentsF

5here is no automati' "is'o!ery o& permissions at 'ompile timeT all permission &ailures o''ur at runtime. +en'e, it is important that you "o'ument the permissions reRuire" &or your publi' A#0s, in'lu"ing 'ontent pro!i"ers, ser!i'es, an" a'ti!ities inten"e" &or laun'hing &rom other a'ti!ities. >ther=ise, the programmers attempting to inter&a'e =ith your appli'ation =ill ha!e to &in" out the permission rules by trial an" error. *urthermore, you shoul" e;pe't that users o& your appli'ation =ill be prompte" to 'on&irm any permissions your appli'ation says it nee"s. +en'e, you nee" to "o'ument &or your users =hat they shoul" e;pe't, lest they get 'on&use" by the Ruestion pose" by the phone an" ele't to not install or use your appli'ation. ?ou may =ish to use string resour'es &or this,

007

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CeLuesting and CeLuiring Permissions

so you 'an internationaliKe your permission "etails the =ay you internationaliKe all the other messages an" prompts in your appli'ation.

?e) Permissions in ,ld Applications


%ometimes, An"roi" intro"u'es ne= permissions that go!ern beha!ior that &ormerly "i" not reRuire permissions. @?I&$ $]&$?%A) 2&"?AD$ is one e;ample S originally, appli'ations 'oul" =rite to e;ternal storage =ithout any permission at all. An"roi" 1./ intro"u'e" @?I&$ $]&$?%A) 2&"?AD$, reRuire" be&ore you 'an =rite to e;ternal storage. +o=e!er, appli'ations that =ere =ritten be&ore An"roi" 1./ 'oul" not possibly reRuest that permission, sin'e it "i" not e;ist at the time. 1reaking those appli'ations =oul" seem to be a harsh pri'e &or progress. What An"roi" "oes is Mgran"&atherM in 'ertain permissions &or appli'ations supporting earlier %@D !ersions. 0n parti'ular, i& you ha!e Luses-sdk android:min2dkVersion67C7M in your mani&est, saying that you support An"roi" 1.A, your appli'ation =ill automati'ally reRuest @?I&$ $]&$?%A) 2&"?AD$ an" ?$A= (!"%$ 2&A&$, e!en i& you "o not e;pli'itly reRuest those permissions. #eople installing your appli'ation on an An"roi" 1.A "e!i'e =ill see these reRuests. E!entually, =hen you "rop support &or the ol"er !ersion (e.g., s=it'h to Luses-sdk android:min2dkVersion67<7M), An"roi" =ill no longer automati'ally reRuest those permissions. +en'e, i& your 'o"e really does nee" those permissions, you =ill nee" to ask &or them yoursel&.

Permissions5 >p "ront ,r ?ot At All


5he permission system in An"roi" is not espe'ially &le;ible. 2otably, you ha!e to ask &or all permissions you might e!er nee" up &ront, an" the user has to agree to all o& them or aban"on the installation o& your app. 5his means,
008

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CeLuesting and CeLuiring Permissions

?ou 'annot 'reate optional permissions, ones the user 'oul" say Mno, thanksM to, that your appli'ation 'oul" rea't to "ynami'ally ?ou 'annot reRuest ne= permissions a&ter installation, so e!en i& a permission is only nee"e" &or some lightly-use" &eature, you ha!e to ask &or it any=ay

+en'e, it is important as you 'ome up =ith the &eature list &or your app that you keep permissions in min". E!ery a""itional permission that your reRuest is a &ilter that =ill 'ost you some portion o& your prospe'ti!e au"ien'e. Certain 'ombinations S su'h as I%&$?%$& an" ?$A= +"%&A+&2 S =ill ha!e a stronger e&&e't, as users &ear =hat the 'ombination 'an "o. ?ou =ill nee" to "e'i"e &or yoursel& i& the a""itional users you =ill get &rom ha!ing the &eature =ill be =orth the 'ost o& reRuiring the permissions the &eature nee"s to operate.

00:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

PART VI !t"er Android Capabilities

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 1;

Accessing !ocation#Based Services

A popular &eature on 'urrent-era mobile "e!i'es is 8#% 'apability, so the "e!i'e 'an tell you =here you are at any point in time. While the most popular use o& 8#% ser!i'e is mapping an" "ire'tions, there are other things you 'an "o i& you kno= your lo'ation. *or e;ample, you might set up a "ynami' 'hat appli'ation =here the people you 'an 'hat =ith are base" on physi'al lo'ation, so you are 'hatting =ith those you are nearest. >r, you 'oul" automati'ally MgeotagM posts to 5=itter or similar ser!i'es. 8#% is not the only =ay a mobile "e!i'e 'an i"enti&y your lo'ation. Alternati!es in'lu"e,

5he European eRui!alent to 8#%, 'alle" 8alileo, =hi'h is still un"er "e!elopment at the time o& this =riting Cell to=er triangulation, =here your position is "etermine" base" on signal strength to nearby 'ell to=ers #ro;imity to publi' Wi*i MhotspotsM that ha!e kno=n geographi' lo'ations

An"roi" "e!i'es may ha!e one or more o& these ser!i'es a!ailable to them. ?ou, as a "e!eloper, 'an ask the "e!i'e &or your lo'ation, plus "etails on =hat pro!i"ers are a!ailable. 5here are e!en =ays &or you to simulate your lo'ation in the emulator, &or use in testing your lo'ation-enable" appli'ations.
02Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing !ocation#Based Services

!ocation Providers5 They 9no) Where .ouGre 3iding


An"roi" "e!i'es 'an ha!e a''ess to se!eral "i&&erent means o& "etermining your lo'ation. %ome =ill ha!e better a''ura'y than others. %ome may be &ree, =hile others may ha!e a 'ost asso'iate" =ith them. %ome may be able to tell you more than Gust your 'urrent position, su'h as your ele!ation o!er sea le!el, or your 'urrent spee". An"roi", there&ore, has abstra'te" all this out into a set o& )ocation(rovider obGe'ts. ?our An"roi" en!ironment =ill ha!e Kero or more )ocation(rovider instan'es, one &or ea'h "istin't lo'ating ser!i'e that is a!ailable on the "e!i'e. #ro!i"ers kno= not only your lo'ation, but their o=n 'hara'teristi's, in terms o& a''ura'y, 'ost, et'. ?ou, as a "e!eloper, =ill use a )ocation#anager, =hi'h hol"s the )ocation(rovider set, to &igure out =hi'h )ocation(rovider is right &or your parti'ular 'ir'umstan'e. ?ou =ill also nee" a permission in your appli'ation, or the !arious lo'ation A#0s =ill &ail "ue to a se'urity !iolation. @epen"ing on =hi'h lo'ation pro!i"ers you =ish to use, you may nee" A++$22 +"A?2$ )"+A&I"%, A++$22 9I%$ )"+A&I"%, or both.

"inding .ourself
5he ob!ious thing to "o =ith a lo'ation ser!i'e is to &igure out =here you are right no=. 5o get a )ocation#anager S 'all get2Fstem2erviceP)"+A&I"% 2$?VI+$Q &rom your a'ti!ity or ser!i'e an" 'ast it to be a )ocation#anager. 5he ne;t step to &in" out =here you are is to get the name o& the ha!e t=o main options, 1. Ask the user to pi'k a pro!i"er "o that, you nee" to

)ocation(rovider you =ant to use. +ere, you

2. *in" the best-mat'h pro!i"er base" on a set o& 'riteria


02%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing !ocation#Based Services

0& you =ant the user to pi'k a pro!i"er, 'alling get(rovidersPQ on the )ocation#anager =ill gi!e you a )ist o& pro!i"ers, =hi'h you 'an then present to the user &or sele'tion. >r, you 'an 'reate an" populate a +riteria obGe't, stating the parti'ulars o& =hat you =ant out o& a )ocation(rovider, su'h as,
setAltitude?eUuiredPQ

to in"i'ate i& you nee" the 'urrent altitu"e or

not
setAccuracFPQ

position

to set a minimum le!el o& a''ura'y, in meters, &or the

to 'ontrol i& the pro!i"er must be &ree or i& it 'an in'ur a 'ost on behal& o& the "e!i'e user
set+ostAlloEedPQ

8i!en a &ille"-in +riteria obGe't, 'all get4est(roviderPQ on your )ocation#anager, an" An"roi" =ill si&t through the 'riteria an" gi!e you the best ans=er. 2ote that not all o& your 'riteria may be met S all but the monetary 'ost 'riterion might be rela;e" i& nothing mat'hes. ?ou are also =el'ome to har"-=ire in a )ocation(rovider name (e.g., D(2 (?"VI=$?), perhaps Gust &or testing purposes. >n'e you kno= the name o& the )ocation(rovider, you 'an 'all get)astHnoEn(ositionPQ to &in" out =here you =ere re'ently. +o=e!er, unless something else is 'ausing the "esire" pro!i"er to 'olle't &i;es (e.g., unless the 8#% ra"io is on), get)astHnoEn(ositionPQ =ill return null, in"i'ating that there is no kno=n position. >n the other han", get)astHnoEn(ositionPQ in'urs no monetary or po=er 'ost, sin'e the pro!i"er "oes not nee" to be a'ti!ate" to get the !alue. 5hese metho"s return a )ocation obGe't, =hi'h 'an gi!e you the latitu"e an" longitu"e o& the "e!i'e in "egrees as a Ca!a double. 0& the parti'ular lo'ation pro!i"er o&&ers other "ata, you 'an get at that as =ell,

*or altitu"e, hasAltitudePQ =ill tell you i& there is an altitu"e !alue, an" getAltitudePQ =ill return the altitu"e in meters.

020

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing !ocation#Based Services

*or bearing (i.e., 'ompass-style "ire'tion), has4earingPQ =ill tell you i& there is a bearing a!ailable, an" get4earingPQ =ill return it as "egrees east o& true north. *or spee", has2peedPQ =ill tell you i& the spee" is kno=n an" get2peedPQ =ill return the spee" in meters per se'on".

A more likely approa'h to getting the )ocation &rom a )ocation(rovider, though, is to register &or up"ates, as "es'ribe" in the ne;t se'tion.

,n the +ove
2ot all lo'ation pro!i"ers are ne'essarily imme"iately responsi!e. 8#%, &or e;ample, reRuires a'ti!ating a ra"io an" getting a &i; &rom the satellites be&ore you get a lo'ation. 5hat is =hy An"roi" "oes not o&&er a get#e#F+urrent)ocation%oEPQ metho". Combine that =ith the &a't that your users may =ell =ant their mo!ements to be re&le'te" in your appli'ation, an" you are probably best o&& registering &or lo'ation up"ates an" using that as your means o& getting the 'urrent lo'ation. 5he Internet/@eather an" 2ervice/@eatherA(I sample appli'ations sho= ho= to register &or up"ates S 'all reUuest)ocation3pdatesPQ on your )ocation#anager instan'e. 5his takes &our parameters, 1. 5he name o& the lo'ation pro!i"er you =ish to use

2. +o= long, in millise'on"s, should ha!e elapse" be&ore =e might get a lo'ation up"ate .. +o= &ar, in meters, must the "e!i'e ha!e mo!e" be&ore =e might get a lo'ation up"ate <. A )ocation)istener that =ill be noti&ie" o& key lo'ation-relate" e!ents, as sho=n belo=,
)ocation)istener on)ocation+hange6neE LocationListenerPQ : public void onLocationChangedP)ocation locationQ : if Pstate.EeatherX6nullQ : state.Eeather.get"orecastPlocation8 stateQJ ; else :

022

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing !ocation#Based Services

)og.wPgetClassPQ.get&amePQ8 73nable to fetch forecast [ no @eather4inder7QJ ; ; public void on)ro!iderDisa'ledP2tring providerQ : // reUuired for interface8 not used ; public void on)ro!ider+na'ledP2tring providerQ : // reUuired for interface8 not used ; public void onStatusChangedP2tring provider8 int status8 4undle eGtrasQ : // reUuired for interface8 not used ; ;J

+ere, all =e "o is trigger a 9etch9orecast&ask =ith the )ocation supplie" to the on)ocation+hangedPQ 'allba'k metho". 1ear in min" that the time parameter is only a gui"e to help steer An"roi" &rom a po=er 'onsumption stan"point. ?ou may get many more lo'ation up"ates than this. 5o get the ma;imum number o& lo'ation up"ates, supply - &or both the time an" "istan'e 'onstraints. When you no longer nee" the up"ates, 'all remove3pdatesPQ =ith the )ocation)istener you registere". 0& you &ail to "o this, your appli'ation =ill 'ontinue re'ei!ing lo'ation up"ates e!en a&ter all a'ti!ities an" su'h are 'lose" up, =hi'h =ill also pre!ent An"roi" &rom re'laiming your appli'ation7s memory. 5here is another !ersion o& reUuest)ocation3pdatesPQ that takes a (endingIntent rather than a )ocation)istener. 5his is use&ul i& you =ant to be noti&ie" o& 'hanges in your position e!en =hen your 'o"e is not running. *or e;ample, i& you are logging mo!ements, you 'oul" use a (endingIntent that triggers a 4roadcast?eceiver (get4roadcastP)) an" ha!e the 4roadcast?eceiver a"" the entry to the log. 5his =ay, your 'o"e is only in memory =hen the position 'hanges, so you "o not tie up system resour'es =hile the "e!i'e is not mo!ing.

027

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing !ocation#Based Services

Are We There .etF Are We There .etF Are We There .etF


%ometimes, you =ant to kno= not =here you are no=, or e!en =hen you mo!e, but =hen you get to =here you are going. 5his 'oul" be an en" "estination, or it 'oul" be getting to the ne;t step on a set o& "ire'tions, so you 'an gi!e the user the ne;t turn. 5o a''omplish this, )ocation#anager o&&ers add(roGimitFAlertPQ. 5his registers an (endingIntent, =hi'h =ill be &ire" o&& =hen the "e!i'e gets =ithin a 'ertain "istan'e o& a 'ertain lo'ation. 5he add(roGimitFAlertPQ metho" takes, as parameters,

5he latitu"e an" longitu"e o& the position that you are intereste" in A ra"ius, spe'i&ying ho= 'lose you shoul" be to that position &or the Intent to be raise" A "uration &or the registration, in millise'on"s S a&ter this perio", the registration automati'ally lapses. A !alue o& -1 means the registration lasts until you manually remo!e it !ia remove(roGimitFAlertPQ. 5he (endingIntent to be raise" =hen the "e!i'e is =ithin the Mtarget KoneM e;presse" by the position an" ra"ius

2ote that it is not guarantee" that you =ill a'tually re'ei!e an Intent, i& there is an interruption in lo'ation ser!i'es, or i& the "e!i'e is not in the target Kone "uring the perio" o& time the pro;imity alert is a'ti!e. *or e;ample, i& the position is o&& by a bit, an" the ra"ius is a little too tight, the "e!i'e might only skirt the e"ge o& the target Kone, or go by so Rui'kly that the "e!i'e7s lo'ation isn7t sample" =hile in the target Kone. 0t is up to you to arrange &or an a'ti!ity or re'ei!er to respon" to the Intent you register =ith the pro;imity alert. What you then "o =hen the Intent arri!es is up to you, set up a noti&i'ation (e.g., !ibrate the "e!i'e), log the in&ormation to a 'ontent pro!i"er, post a message to a Web site, et'. 2ote that you =ill re'ei!e the Intent =hene!er the position is sample" an" you are =ithin the target Kone S not Gust upon entering the Kone. +en'e, you
028

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Accessing !ocation#Based Services

=ill get the Intent se!eral times, perhaps Ruite a &e= times "epen"ing on the siKe o& the target Kone an" the spee" o& the "e!i'e7s mo!ement.

Testing111Testing111
5he An"roi" emulator "oes not ha!e the ability to get a &i; &rom 8#%, triangulate your position &rom 'ell to=ers, or i"enti&y your lo'ation by some nearby Wi*i signal. %o, i& you =ant to simulate a mo!ing "e!i'e, you =ill nee" to ha!e some means o& pro!i"ing mo'k lo'ation "ata to the emulator. *or =hate!er reason, this parti'ular area has un"ergone signi&i'ant 'hanges as An"roi" itsel& has e!ol!e". 0t use" to be that you 'oul" pro!i"e mo'k lo'ation "ata =ithin your appli'ation, =hi'h =as !ery han"y &or "emonstration purposes. Alas, those options ha!e all been remo!e" as o& An"roi" 1.0. >ne likely option &or supplying mo'k lo'ation "ata is the @al!ik @ebug Monitor %er!i'e (@@M%). 5his is an e;ternal program, separate &rom the emulator, =here you 'an &ee" it single lo'ation points or &ull routes to tra!erse, in a &e= "i&&erent &ormats. @@M% is "es'ribe" in greater "etail in the 'hapter on An"roi" "e!elopment tools.

02:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 2<

+apping )ith +ap;ie) and +apActivity

>ne o& 8oogle7s most popular ser!i'es S a&ter sear'h, o& 'ourse S is 8oogle Maps, =here you 'an &in" e!erything &rom the nearest piKKa parlor to "ire'tions &rom 2e= ?ork City to %an *ran'is'o (only 2,30A miles:) to street !ie=s an" satellite imagery. Most An"roi" "e!i'es, not surprisingly, integrate 8oogle Maps. *or those that "o, there is a mapping a'ti!ity a!ailable to users straight o&& the main An"roi" laun'her. More rele!ant to you, as a "e!eloper, are #apVieE an" #apActivitF, =hi'h allo= you to integrate maps into your o=n appli'ations. 2ot only 'an you "isplay maps, 'ontrol the Koom le!el, an" allo= people to pan aroun", but you 'an tie in An"roi"7s lo'ation-base" ser!i'es to sho= =here the "e!i'e is an" =here it is going. *ortunately, integrating basi' mapping &eatures into your An"roi" proGe't is &airly easy. +o=e!er, there is a &air bit o& po=er a!ailable to you, i& you =ant to get sophisti'ate".

Terms@ ?ot of =ndearment


8oogle Maps, parti'ularly =hen integrate" into thir" party appli'ations, reRuires agreeing to a &airly lengthy set o& legal terms. 5hese terms in'lu"e 'lauses that you may &in" unpalatable.

07*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

0& you are 'onsi"ering 8oogle Maps, please re!ie= these terms 'losely to "etermine i& your inten"e" use =ill not run a&oul o& any 'lauses. ?ou are strongly re'ommen"e" to seek pro&essional legal 'ounsel i& there are any potential areas o& 'on&li't. Also, keep your eyes peele" &or other mapping options, base" o&& o& other sour'es o& map "ata, su'h as >pen%treetMap.

Piling ,n
As o& An"roi" 1.A, 8oogle Maps are not stri'tly part o& the An"roi" %@D. 0nstea", they are part o& the 8oogle A#0s A""->n, an e;tension o& the sto'k %@D. 5he An"roi" a""-on system pro!i"es hooks &or other subsystems that may be part o& some "e!i'es, but not others. A&ter all, 8oogle Maps is not part o& the An"roi" open sour'e proGe't, an" un"oubte"ly there =ill be some "e!i'es that la'k 8oogle Maps "ue to li'ensing issues. *or e;ample, at the time o& this =riting, the A C+>% A An"roi" tablet "oes not ha!e 8oogle Maps. 1y an" large, the &a't that 8oogle Maps is in an a""-on "oes not a&&e't your "ay-to-"ay "e!elopment. +o=e!er, bear in min",

?ou =ill nee" to 'reate your proGe't =ith an appropriate target to ensure the 8oogle Maps A#0s =ill be a!ailable 5o test your 8oogle Maps integration, you =ill also nee" an A-@ that uses an appropriate target

The 9ey To t All


0& you "o=nloa" the sour'e 'o"e &or the book, 'ompile the #aps/%oo5aEk proGe't, install it in your emulator, an" run it, you =ill probably see a s'reen =ith a gri" an" a 'ouple o& push-pins, but no a'tual maps.

07&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

5hat7s be'ause the A#0 key in the sour'e 'o"e is in!ali" &or your "e!elopment ma'hine. 0nstea", you =ill nee" to generate your o=n A#0 key(s) &or use =ith your appli'ation. 5his also hol"s true &or any mapenable" proGe'ts you 'reate on your o=n &rom s'rat'h. *ull instru'tions &or generating A#0 keys, &or "e!elopment an" pro"u'tion use, 'an be &oun" on the An"roi" Web site. 0n the interest o& bre!ity, let7s &o'us on the narro= 'ase o& getting %oo5aEk running in your emulator. @oing this reRuires the &ollo=ing steps, 1. 2. -isit the A#0 key signup page an" re!ie= the terms o& ser!i'e. e-rea" those terms o& ser!i'e an" make really really sure you =ant to agree to them.

.. *in" the M@A "igest o& the 'erti&i'ate use" &or signing your "ebugmo"e appli'ations ("es'ribe" in "etail belo=) <. >n the A#0 key signup page, paste in that M@A signature an" submit the &orm A. >n the resulting page, 'opy the A#0 key an" paste it as the !alue o& apiHeF in your #apVieE-using layout 5he tri'kiest part is &in"ing the M@A signature o& the 'erti&i'ate use" &or signing your "ebug-mo"e appli'ations... an" mu'h o& the 'omple;ity is merely in making sense o& the 'on'ept. All An"roi" appli'ations are signe" using a "igital signature generate" &rom a 'erti&i'ate. ?ou are automati'ally gi!en a "ebug 'erti&i'ate =hen you set up the %@D, an" there is a separate pro'ess &or 'reating a sel&-signe" 'erti&i'ate &or use in your pro"u'tion appli'ations. 5his signature pro'ess in!ol!es the use o& the Ca!a keFtool an" jarsigner utilities. *or the purposes o& getting your A#0 key, you only nee" to =orry about keFtool. 5o get your M@A "igest o& your "ebug 'erti&i'ate, i& you are on >% F or Linu;, use the &ollo=ing 'omman",
keFtool -list -alias androiddebugkeF -keFstore ^/.android/debug.keFstore -storepass android -keFpass android

07-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

>n other "e!elopment plat&orms, you =ill nee" to repla'e the !alue o& the -keFstore s=it'h =ith the lo'ation &or your plat&orm an" user a''ount,

F#, +:T=ocuments and 2ettingsTLuserMT.androidTdebug.keFstore -ista, +:T3sersTLuserMT.androidTdebug.keFstore

(=here LuserM is your a''ount name) 5he se'on" line o& the output 'ontains your M@A "igest, as a series o& pairs o& he; "igits separate" by 'olons.

The Bare Bones


5o put a map into your appli'ation, you nee" to 'reate your o=n sub'lass o& #apActivitF. Like )istActivitF, =hi'h =raps up some o& the smarts behin" ha!ing an a'ti!ity "ominate" by a )istVieE, #apActivitF han"les some o& the nuan'es o& setting up an a'ti!ity "ominate" by a #apVieE. A #apVieE 'an only be use" by a #apActivitF, not any other type o& ActivitF. 0n your layout &or the #apActivitF sub'lass, you nee" to a"" an element name" com.google.android.maps.#apVieE. 5his is the Mlonghan"M =ay to spell out the names o& =i"get 'lasses, by in'lu"ing the &ull pa'kage name along =ith the 'lass name. 5his is ne'essary be'ause #apVieE is not in the android.Eidget namespa'e. ?ou 'an gi!e the #apVieE =i"get =hate!er android:id attribute !alue you =ant, plus han"le all the layout "etails to ha!e it ren"er properly alongsi"e your other =i"gets. +o=e!er, you "o nee" to ha!e,
android:apiHeF, your

8oogle Maps A#0 key i& you =ant users to be able to 'li'k an"

pan through your map

android:clickable 6 7true7,

*or e;ample, &rom the #aps/%oo5aEk sample appli'ation, here is the main layout,

07%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

LNGml version671.-7 encoding67utf-,7NM L?elative)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7M Lcom.google.android.maps.#apVieE android:id67ORid/map7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:apiHeF67--F!j-k/ /vGbuY*KEF]I<b%#JrAj5rJ*HH!gbY7 android:clickable67true7 /M L/?elative)aFoutM

0n a""ition, you =ill nee" a 'ouple o& e;tra things in your Android#anifest.Gml &ile,

5he I%&$?%$& an" A++$22 9I%$ )"+A&I"% permissions (the latter &or use =ith the #F)ocation"verlaF 'lass, "es'ribe" later in this 'hapter) 0nsi"e your LapplicationM, a Luses-librarFM element android:name 6 7com.google.android.maps7, to in"i'ate you are one o& the optional An"roi" A#0s =ith using

+ere is the Android#anifest.Gml &ile &or %oo5aEk,


LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.maps7M Luses-permission android:name67android.permission.I%&$?%$&7/M Luses-permission android:name67android.permission.A++$22 9I%$ )"+A&I"%7/M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M Luses-librarF android:name67com.google.android.maps7/M LactivitF android:name67.%oo5aEk7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

5hat is pretty mu'h all you nee" &or starters, plus to sub'lass your a'ti!ity &rom #apActivitF. 0& you =ere to "o nothing else, an" built that proGe't an" tosse" it in the emulator, you7" get a ni'e map o& the =orl". 2ote, ho=e!er, that #apActivitF is abstra't S you nee" to implement is?oute=isplaFedPQ to in"i'ate i& you are supplying some sort o& "ri!ing "ire'tions or not. %in'e
070

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

"isplaying "ri!ing "ire'tions is not supporte" by the 'urrent e"ition o& the terms o& ser!i'e, you shoul" ha!e is?oute=isplaFedPQ return false.

+ption l % ps
2ot e!ery An"roi" "e!i'e =ill ha!e 8oogle Maps, be'ause they "i" not ele't to li'ense it &rom 8oogle. While most mainstream "e!i'es =ill ha!e 8oogle Maps, a &e= per'ent o& An"roi" "e!i'es =ill be =ithout it. ?ou nee" to "e'i"e i& ha!ing 8oogle Maps is essential &or your appli'ation7s operation, or not. 0& it is, the Luses-librarFM element sho=n abo!e is the right ans=er, as that =ill reRuire any "e!i'e running your app to ha!e 8oogle Maps. 0&, ho=e!er, you =ant 8oogle Maps to be optional, there is an un"o'umente" android:reUuired attribute a!ailable on Luses-librarFM. %et that to false, an" then 8oogle Maps =ill be loa"e" into your appli'ation i& it is a!ailable, but your appli'ation =ill run regar"less. ?ou =ill then nee" to use something like +lass.for%ameP7com.google.android.maps.#apVieE7Q to see i& 8oogle Maps is a!ailable to you. 0& it is not, you 'an "isable the menu items or =hate!er =oul" lea" the user to your #apActivitF. While this attribute is un"o'umente", 8oogle has in"i'ate" that it is an a!ailable option, an" hope&ully it =ill be o&&i'ially "o'umente" in a &uture An"roi" release.

=xercising .our Control


?ou 'an &in" your #apVieE =i"get by findVieE4FIdPQ, no "i&&erent than any other =i"get. 5he =i"get itsel& then o&&ers a get+ontrollerPQ metho". 1et=een the #apVieE an" #ap+ontroller, you ha!e a &air bit o& 'apability to "etermine =hat the map sho=s an" ho= it beha!es. +ere are some likely &eatures you =ill =ant to use,

072

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

Koom
5he map o& the =orl" you start =ith is rather broa". $sually, people looking at a map on a phone =ill be e;pe'ting something a bit narro=er in s'ope, su'h as a &e= 'ity blo'ks. ?ou 'an 'ontrol the Koom le!el "ire'tly !ia the setVoomPQ metho" on the #ap+ontroller. 5his takes an integer representing the le!el o& Koom, =here 1 is the =orl" !ie= an" 21 is the tightest Koom you 'an get. Ea'h le!el is a "oubling o& the e&&e'ti!e resolution, 1 has the eRuator measuring 2A/ pi;els =i"e, =hile 21 has the eRuator measuring 2/8,<.A,<A/ pi;els =i"e. %in'e the phone7s "isplay probably "oes not ha!e 2/8,<.A,<A/ pi;els in either "imension, the user sees a small map &o'use" on one tiny 'orner o& the globe. A le!el o& 14 =ill sho= you se!eral 'ity blo'ks in ea'h "imension an" is probably a reasonable starting point &or you to e;periment =ith. 0& to 'hange the Koom le!el, 'all the user =ill be able to Koom in an" out o& the map !ia Koom 'ontrols &oun" in the bottom 'enter o& the map.
set4uiltInVoom+ontrolsPtrueQJ, an"

you

=ish

to

allo=

users

Center
5ypi'ally, you =ill nee" to 'ontrol =hat the map is sho=ing, beyon" the Koom le!el, su'h as the user7s 'urrent lo'ation, or a lo'ation sa!e" =ith some "ata in your a'ti!ity. 5o 'hange the map7s position, 'all set+enterPQ on the #ap+ontroller. 5his takes a Deo(oint as a parameter. A Deo(oint represents a lo'ation, !ia latitu"e an" longitu"e. 5he 'at'h is that the Deo(oint stores latitu"e an" longitu"e as integers representing the a'tual latitu"e an" longitu"e in mi'ro"egrees ("egrees multiplie" by 1$0). 5his sa!es a bit o& memory !ersus storing a float or double, an" it greatly spee"s up some internal 'al'ulations An"roi" nee"s to "o to 'on!ert the Deo(oint into a map position. +o=e!er, it "oes mean you ha!e to remember to multiply the Mreal =orl"M latitu"e an" longitu"e by 1$0.

077

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

!ayers >pon !ayers


0& you ha!e e!er use" the &ull-siKe e"ition o& 8oogle Maps, you are probably use" to seeing things o!erlai" atop the map itsel&, su'h as Mpush-pinsM in"i'ating businesses near the lo'ation being sear'he". 0n map parlan'e S an", &or that matter, in many serious graphi' e"itors S the push-pins are on a separate layer than the map itsel&, an" =hat you are seeing is the 'omposition o& the push-pin layer atop the map layer. An"roi"7s mapping allo=s you to 'reate layers as =ell, so you 'an mark up the maps as you nee" to base" on user input an" your appli'ation7s purpose. *or e;ample, %oo5aEk uses a layer to sho= =here sele't buil"ings are lo'ate" in the islan" o& Manhattan.

+verl y Cl sses
Any o!erlay you =ant to a"" to your map nee"s to be implemente" as a sub'lass o& "verlaF. 5here is an ItemiKed"verlaF sub'lass a!ailable i& you are looking to a"" push-pins or the likeT ItemiKed"verlaF simpli&ies this pro'ess. 5o atta'h an o!erlay 'lass to your map, Gust 'all get"verlaFsPQ on your #apVieE an" addPQ your "verlaF instan'e to it, as =e "o here =ith a 'ustom 2ites"verlaF,
marker.setBoundsP-8 -8 marker.getIntrinsic#idthPQ8 marker.getIntrinsic(eightPQQJ map.getO!erlaysPQ.addPneE SitesO!erlayPmarkerQQJ

We =ill e;plain that marker in Gust a bit.

Dr #in! the ItemiEed+verl y


As the name suggests, ItemiKed"verlaF allo=s you to supply a list o& points o& interest to be "isplaye" on the map S spe'i&i'ally, instan'es o& "verlaFItem. 5he o!erlay, then, han"les mu'h o& the "ra=ing logi' &or you. +ere are the minimum steps to make this =ork,
078

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

*irst, o!erri"e ItemiKed"verlaFL"verlaFItemM as your o=n sub'lass (in this e;ample, 2ites"verlaF) 0n the 'onstru'tor, buil" your roster o& "verlaFItem instan'es, an" 'all populatePQ =hen they are rea"y &or use by the o!erlay 0mplement siKePQ to return the number o& items to be han"le" by the o!erlay >!erri"e createItemPQ to return "verlaFItem instan'es gi!en an in"e; When you instantiate your ItemiKed"verlaF sub'lass, pro!i"e it =ith a =raEable that represents the "e&ault i'on (e.g., push-pin) to "isplay &or ea'h item, on =hi'h you 'all bound+enter4ottomPQ to enable the "rop-sha"o= e&&e't

5he marker &rom the %oo5aEk 'onstru'tor is the =raEable use" &or the last bullet abo!e S it sho=s a push-pin. *or e;ample, here is 2ites"verlaF,
private class 2ites"verlaF eGtends ItemiKed"verlaFL"verlaFItemM : private )istL"verlaFItemM items6neE ArraF)istL"verlaFItemMPQJ private =raEable marker6nullJ public SitesO!erlayP=raEable markerQ : superPmarkerQJ this.marker6markerJ 'oundCenterBottomPmarkerQJ items.addPneE O!erlayItemPget)ointP<-./<,*0C,</C10-C<8 -/C.*0,-/1*C/.01-<Q8 73%78 73nited %ations7QQJ items.addPneE O!erlayItemPget)ointP<-./0,00>***/<C,/8 -/C.*,>0,<01>>/<1/Q8 7)incoln +enter78 7!ome of JaKK at )incoln +enter7QQJ items.addPneE O!erlayItemPget)ointP<-./0.1C0<C.C10/..8 -/C.*/*,*.11<,*,0,Q8 7+arnegie !all78 7@here Fou go Eith practice8 practice8 practice7QQJ items.addPneE O!erlayItemPget)ointP<-./-0,0<1/<*1/**8 -/<.-1./>*<>/CC/0.Q8 7&he =oEntoEn +lub78 7"riginal home of the !eisman &rophF7QQJ

07:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

populatePQJ ; O"verride protected "verlaFItem createItemPint iQ : returnPitems.getPiQQJ ; O"verride protected boolean onTapPint iQ : &oast.makeTextP%oo5aEk.this8 items.getPiQ.getSnippetPQ8 &oast.)$%D&! 2!"?&Q.showPQJ returnPtrueQJ ; O"verride public int si.ePQ : returnPitems.si.ePQQJ ; ;

H ndlin! Screen T ps
An "verlaF sub'lass 'an also implement on&apPQ, to be noti&ie" =hen the user taps on the map, so the o!erlay 'an a"Gust =hat it "ra=s. *or e;ample, in &ull-siKe 8oogle Maps, 'li'king on a push-pin pops up a bubble =ith in&ormation about the business at that pin7s lo'ation. With on&apPQ, you 'an "o mu'h the same in An"roi". 5he on&apPQ metho" &or ItemiKed"verlaF "verlaFItem that =as 'li'ke". 0t is up to you =ith this e!ent. 0n the 'ase o& 2ites"verlaF, as sho=n abo!e, on&apPQ looks like this,
O"verride protected boolean onTapPint iQ : &oast.makeTextP%oo5aEk.this8 items.getPiQ.getSnippetPQ8 &oast.)$%D&! 2!"?&Q.showPQJ returnPtrueQJ ;

re'ei!es the in"e; o& the to "o something =orth=hile

08<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

+ere, =e Gust toss up a short &oast =ith the MsnippetM &rom the "verlaFItem, returning true to in"i'ate =e han"le" the tap.

+y@ +yself@ and +y!ocation,verlay


An"roi" has a built-in o!erlay to han"le t=o 'ommon s'enarios, 1. %ho=ing =here you are on the map, base" on 8#% or other lo'ationpro!i"ing logi'

2. %ho=ing =here you are pointe", base" on the built-in 'ompass sensor, =here a!ailable All you nee" to "o is 'reate a #F)ocation"verlaF instan'e, a"" it to your #apVieE7s list o& o!erlays, an" enable an" "isable the "esire" &eatures at appropriate times. 5he Mat appropriate timesM notion is &or ma;imiKing battery li&e. 5here is no sense in up"ating lo'ations or "ire'tions =hen the a'ti!ity is pause", so it is re'ommen"e" that you enable these &eatures in on?esumePQ an" "isable them in on(ausePQ. *or e;ample, %oo5aEk =ill "isplay a 'ompass rose using #F)ocation"verlaF. 5o "o this, =e &irst nee" to 'reate the o!erlay an" a"" it to the list o& o!erlays,
me6neE MyLocationO!erlayPthis8 mapQJ map.getO!erlaysPQ.addPmeQJ

(=here me is the #F)ocation"verlaF instan'e as a pri!ate "ata member) 5hen, =e enable an" "isable the 'ompass rose as appropriate,
O"verride public void on%esumePQ : super.on%esumePQJ me.ena'leCompassPQJ ;

08*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

O"verride public void on)ausePQ : super.on)ausePQJ ; me.disa'leCompassPQJ

5his gi!es us a 'ompass rose =hile the a'ti!ity is on-s'reen,

"igure *021 The ?oo.a)k map@ sho)ing a compass rose and t)o ,verlay tems

Cugged Terrain
Cust as the 8oogle Maps you use on your &ull-siKe 'omputer 'an "isplay satellite imagery, so too 'an An"roi" maps. o&&ers toggle2atellitePQ, =hi'h, as the name suggests, toggles on an" o&& this perspe'ti!e on the area being !ie=e". ?ou 'an ha!e the user trigger these !ia an options menu or, in the 'ase o& %oo5aEk, !ia keypresses,
#apVieE

08&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

O"verride public boolean on0eyDownPint keF+ode8 HeF$vent eventQ : if PkeF+ode 66 HeF$vent.H$5+"=$ 2Q : map.setSatellitePXmap.isSatellitePQQJ returnPtrueQJ ; else if PkeF+ode 66 HeF$vent.H$5+"=$ VQ : map.display1oomControlsPtrueQJ returnPtrueQJ ; ; returnPsuper.on0eyDownPkeF+ode8 eventQQJ

%o, &or e;ample, here is %oo5aEk sho=ing a satellite !ie=, 'ourtesy o& pressing the 2 key,

"igure *071 The ?oo.a)k map@ sho)ing a compass rose and t)o ,verlay tems@ overlaid on the satellite vie)

08-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

+aps and "ragments


?ou might think that maps =oul" be an i"eal pla'e to use &ragments. A&ter all, on a large tablet s'reen, =e 'oul" allo'ate most o& the spa'e to the map but then ha!e other stu&& alongsi"e. Alas, as o& the time o& this =riting, maps an" &ragments are t=o great tastes that "o not taste so great together. *irst, #apVieE reRuires you to inherit &rom #apActivitF. 5his has a &e= rami&i'ations,

?ou 'annot use the An"roi" Compatibility Library (ACL), be'ause that reRuires you to inherit &rom 9ragmentActivitF, an" Ca!a "oes not support multiple inheritan'e. +en'e, you 'an only use maps-in&ragments on An"roi" ..0 an" higher, &alling ba'k to some alternati!e implementation on ol"er !ersions o& An"roi". Any a'ti!ity that might host a map in a &ragment =ill ha!e to inherit &rom #apActivitF, e!en i& in some 'ases it might not host a map in a &ragment.

Also, #apVieE makes some assumptions about the timing o& !arious e!ents, in a &ashion that makes setting up a map-base" &ragment a bit more 'omple; than it might other=ise ha!e to be. 0t is entirely possible that some"ay these problems =ill be resol!e", through a 'ombination o& an up"ate" 8oogle A#0s A""->n &or An"roi" =ith &ragment support, an" possibly an up"ate" ACL. 0n the meantime, here is the re'ipe &or getting maps to =ork, as =ell as they 'an, in &ragments.

)imit 3oursel. to Android 1A<


0n the mani&est, make sure that you set both your android:min2dkVersion an" your android:target2dkVersion to 11, so you only run on An"roi" ..0

08%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

an"

e;ample, here #aps/%oo5aEk9ragments sample proGe't,

ne=er.

*or

is

the

mani&est

&rom

the

LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.android.maps7M Luses-permission android:name67android.permission.I%&$?%$&7/M Luses-permission android:name67android.permission.A++$22 9I%$ )"+A&I"%7/M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7 android:hardEareAccelerated67true7M Luses-librarF android:name67com.google.android.maps7/M LactivitF android:name67.%oo5aEk7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7/M LcategorF android:name67android.intent.categorF.)A3%+!$?7/M L/intent-filterM L/activitFM L/applicationM Luses-sdk android:min2dkVersion67117 android:target2dkVersion67117 /M Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:anF=ensitF67true7/M L/manifestM

-se onCre te>ie#?@ nd onActivityCre ted?@


A map-base" &ragment is simply a 9ragment that sho=s a #apVieE. 1y an" large, this 'o"e 'an look an" =ork mu'h like a #apActivitF =oul", 'on&iguring the #apVieE, setting up an ItemiKed"verlaF, an" so on. +o=e!er, there is that timing problem. 5he timing problem is that you 'annot reliably return a #apVieE =i"get, or an in&late" layout 'ontaining su'h a =i"get, &rom on+reateVieEPQ. *or =hate!er reason, it =orks &ine the &irst time, but on a 'on&iguration 'hange (e.g., s'reen rotation) it &ails. 5he solution is to return a 'ontainer &rom on+reateVieEPQ, su'h as a 9rame)aFout, as sho=n here in the #ap9ragment 'lass &rom %oo5aEk9ragments,
O"verride public VieE onCreateViewP)aFoutInflater inflater8 VieEDroup container8

080

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

4undle savedInstance2tateQ : returnPneE "rameLayoutPget$cti!ityPQQQJ

5hen, in onActivitF+reatedPQ S on'e on+reatePQ has been 'omplete" in the hosting #apActivitF S you 'an a"" a #apVieE to that 'ontainer an" 'ontinue =ith the rest o& your normal setup,
O"verride public void on$cti!ityCreatedP4undle savedInstance2tateQ : super.on$cti!ityCreatedPsavedInstance2tateQJ map6neE MapViewPget$cti!ityPQ8 7--F!j-k/ /vGbuY*KEF]I<b%#JrAj5rJ*HH!gbY7QJ map.setClicka'lePtrueQJ map.getControllerPQ.setCenterPget)ointP<-./0/*C10***>-<<8 -/C.*,1,-<,<//1/>*QQJ map.getControllerPQ.set1oomP1/QJ map.setBuiltIn1oomControlsPtrueQJ =raEable marker6get%esourcesPQ.getDrawa'leP?.draEable.markerQJ marker.setBoundsP-8 -8 marker.getIntrinsic#idthPQ8 marker.getIntrinsic(eightPQQJ map.getO!erlaysPQ.addPneE SitesO!erlayPmarkerQQJ me6neE MyLocationO!erlayPget$cti!ityPQ8 mapQJ map.getO!erlaysPQ.addPmeQJ PPVieEDroupQgetViewPQQ.addViewPmapQJ ;

2ote that =e are 'reating a #apVieE in Ca!a 'o"e, =hi'h means our Maps A#0 key resi"es in the Ca!a 'o"e (or something rea'hable &rom the Ca!a 'o"e, su'h as a string resour'e). ?ou 'oul" in&late a layout 'ontaining a #apVieE here i& you =ishe" S the 'hange &or #ap9ragment =as simply to illustrate 'reating a #apVieE &rom Ca!a 'o"e.

Host the 5r !ment in

% pActivity

?ou must make sure that =hate!er a'ti!ity hosts the map-enable" &ragment is a #apActivitF. %o, e!en though the %oo5aEk a'ti!ity no longer has mu'h to "o =ith mapping, it must still be a #apActivitF,

082

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

package com.commonsEare.android.mapsJ import android.os.4undleJ import com.google.android.maps.#apActivitFJ public class %oo5aEk eGtends #apActivitF : O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ setContentViewP?.laFout.mainQJ ; O"verride protected boolean is%outeDisplayedPQ : returnPfalseQJ ;

5he layout no= points to a LfragmentM instea" o& a #apVieE,


LNGml version671.-7 encoding67utf-,7NM Lfragment Gmlns:android67http://schemas.android.com/apk/res/android7 class67com.commonsEare.android.maps.#ap9ragment7 android:id67ORid/map fragment7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 /M

5he resulting appli'ation looks like the original %oo5aEk a'ti!ity =oul" on a large s'reen, be'ause =e are not "oing anything mu'h else =ith the &ragment system (e.g., ha!ing other &ragments alongsi"e in a lan"s'ape layout),

087

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+apping )ith +ap;ie) and +apActivity

"igure *081 The ?oo.a)k"ragments map@ rendered on a +otorola E,,+

088

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 21

3andling Telephone Calls

Many, i& not most, An"roi" "e!i'es =ill be phones. As su'h, not only =ill users be e;pe'ting to pla'e an" re'ei!e 'alls using An"roi", but you =ill ha!e the opportunity to help them pla'e 'alls, i& you =ish. Why might you =ant toH

Maybe you are =riting an An"roi" inter&a'e to a sales management appli'ation (a la %ales&or'e.'om) an" you =ant to o&&er users the ability to 'all prospe'ts =ith a single button 'li'k, an" =ithout them ha!ing to keep those 'onta'ts both in your appli'ation an" in the phone7s 'onta'ts appli'ation Maybe you are =riting a so'ial net=orking appli'ation, an" the roster o& phone numbers that you 'an a''ess shi&ts 'onstantly, so rather than try to Msyn'M the so'ial net=ork 'onta'ts =ith the phone7s 'onta't "atabase, you let people pla'e 'alls "ire'tly &rom your appli'ation Maybe you are 'reating an alternati!e inter&a'e to the e;isting 'onta'ts system, perhaps &or users =ith re"u'e" motor 'ontrol (e.g., the el"erly), sporting big buttons an" the like to make it easier &or them to pla'e 'alls

Whate!er the reason, An"roi" has the means to let you manipulate the phone Gust like any other pie'e o& the An"roi" system.

08:
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Telephone Calls

Ceport To The +anager


5o get at mu'h o& the phone A#0, you use the &elephonF#anager. 5hat 'lass lets you "o things like,

@etermine i& the phone is in use !ia get+all2tatePQ, =ith return !alues o& +A)) 2&A&$ I=)$ (phone not in use), +A)) 2&A&$ ?I%DI%D ('all reRueste" but still being 'onne'te"), an" +A)) 2&A&$ "99!""H ('all in progress) *in" out the %0M 0@ (0M%0) !ia get2ubscriberIdPQ *in" out the phone type (e.g., 8%M) !ia get(hone&FpePQ or &in" out the "ata 'onne'tion type (e.g., 8# %, E@8E) !ia get%etEork&FpePQ

.ou +ake the Call!


?ou 'an also initiate a 'all &rom your appli'ation, su'h as &rom a phone number you obtaine" through your o=n Web ser!i'e. 5o "o this, simply 'ra&t an A+&I"% =IA) Intent =ith a 3ri o& the &orm tel:%%%%% (=here %%%%% is the phone number to "ial) an" use that Intent =ith startActivitFPQ. 5his =ill not a'tually "ial the phoneT rather, it a'ti!ates the "ialer a'ti!ity, &rom =hi'h the user 'an then press a button to pla'e the 'all. *or e;ample, let7s look at the (hone/=ialer sample appli'ation. +ere7s the 'ru"e-but-e&&e'ti!e layout,
LNGml version671.-7 encoding67utf-,7NM L)inear)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:orientation67vertical7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 M L)inear)aFout android:orientation67horiKontal7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 M L&eGtVieE android:laFout Eidth67Erap content7 android:laFout height67Erap content7 android:teGt67%umber to dial:7 /M

0:<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Telephone Calls

L$dit&eGt android:id67ORid/number7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:cursorVisible67true7 android:editable67true7 android:single)ine67true7 /M L/)inear)aFoutM L4utton android:id67ORid/dial7 android:laFout Eidth67fill parent7 android:laFout height67Erap content7 android:laFout Eeight6717 android:teGt67=ial ItX7 android:on+lick67dial7 /M L/)inear)aFoutM

We ha!e a labele" &iel" &or typing in a phone number, plus a button &or "ialing sai" number. 5he Ca!a 'o"e simply laun'hes the "ialer using the phone number &rom the &iel",
package com.commonsEare.android.dialerJ import import import import import import android.app.ActivitFJ android.content.IntentJ android.net.3riJ android.os.4undleJ android.vieE.VieEJ android.Eidget.$dit&eGtJ

public class =ialer=emo eGtends ActivitF : O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ ; public void dialPVieE vQ : $dit&eGt number6P$dit&eGtQfindViewByIdP?.id.numberQJ 2tring to=ial67tel:7Rnumber.getTextPQ.toStringPQJ start$cti!ityPneE IntentPIntent.A+&I"% =IA)8 3ri.parsePto=ialQQQJ ; ;

5he a'ti!ity7s o=n $0 is not that impressi!e,

0:*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Telephone Calls

"igure *0:1 The /ialer/emo sample application@ as initially launched

+o=e!er, the "ialer you get &rom 'li'king the "ial button is better, sho=ing you the number you are about to "ial,

"igure *2<1 The Android /ialer activity@ as launched from /ialer/emo

0:&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3andling Telephone Calls

?o@ Ceally@ .ou +ake the Call!


5he goo" ne=s is that A+&I"% =IA) =orks =ithout any spe'ial permissions. 5he ba" ne=s is that it only takes the user to the @ialer S the user still has to take a'tion (pressing the green 'all button) to a'tually pla'e the phone 'all. An alternati!e approa'h is to use A+&I"% +A)) instea" o& A+&I"% =IA). Calling startActivitFPQ on an A+&I"% +A)) Intent =ill imme"iately pla'e the phone 'all, =ithout any other $0 steps reRuire". +o=e!er, you nee" the +A)) (!"%$ permission in or"er to use A+&I"% +A)).

0:-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 2&

"onts

0ne!itably, you[ll get the Ruestion 6hey, 'an =e 'hange this &ontH9 =hen "oing appli'ation "e!elopment. 5he ans=er "epen"s on =hat &onts 'ome =ith the plat&orm, =hether you 'an a"" other &onts, an" ho= to apply them to the =i"get or =hate!er nee"s the &ont 'hange. An"roi" is no "i&&erent. 0t 'omes =ith some &onts plus a means &or a""ing ne= &onts. 5hough, as =ith any ne= en!ironment, there are a &e= i"iosyn'rasies to "eal =ith.

!ove The ,ne .ouGre With


An"roi" nati!ely kno=s three &onts, by the shorthan" names o& 6sans9, 6seri&9, an" 6monospa'e9. 5hese &onts are a'tually the @roi" series o& &onts, 'reate" &or the >pen +an"set Allian'e by As'en"er. *or those &onts, you 'an Gust re&eren'e them in your layout FML, i& you 'hoose, su'h as the &ollo=ing layout &rom the 9onts/9ont2ampler sample proGe't,
LNGml version671.-7 encoding67utf-,7NM L&able)aFout Gmlns:android67http://schemas.android.com/apk/res/android7 android:laFout Eidth67fill parent7 android:laFout height67fill parent7 android:stretch+olumns6717M L&able?oEM

0:0
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

"onts

L&eGtVieE android:teGt67sans:7 android:laFout margin?ight67<dip7 android:teGt2iKe67>-sp7 /M L&eGtVieE android:id67ORid/sans7 android:teGt67!ello8 EorldX7 android:tFpeface67sans7 android:teGt2iKe67>-sp7 /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67serif:7 android:laFout margin?ight67<dip7 android:teGt2iKe67>-sp7 /M L&eGtVieE android:id67ORid/serif7 android:teGt67!ello8 EorldX7 android:tFpeface67serif7 android:teGt2iKe67>-sp7 /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67monospace:7 android:laFout margin?ight67<dip7 android:teGt2iKe67>-sp7 /M L&eGtVieE android:id67ORid/monospace7 android:teGt67!ello8 EorldX7 android:tFpeface67monospace7 android:teGt2iKe67>-sp7 /M L/&able?oEM L&able?oEM L&eGtVieE android:teGt67+ustom:7 android:laFout margin?ight67<dip7 android:teGt2iKe67>-sp7 /M L&eGtVieE android:id67ORid/custom7 android:teGt67!ello8 EorldX7 android:teGt2iKe67>-sp7 /M L/&able?oEM L&able?oE android:id67ORid/fileroE7M L&eGtVieE android:teGt67+ustom from 9ile:7 android:laFout margin?ight67<dip7

0:2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"onts

android:teGt2iKe67>-sp7 /M L&eGtVieE android:id67ORid/file7 android:teGt67!ello8 EorldX7 android:teGt2iKe67>-sp7 /M L/&able?oEM L/&able)aFoutM

5his layout buil"s a table sho=ing short samples o& &i!e &onts. 2oti'e ho= the &irst three ha!e the android:tFpeface attribute, =hose !alue is one o& the three built-in &ont &a'es (e.g., 6sans9). 5he three built-in &onts are !ery ni'e. +o=e!er, it may be that a "esigner, or a manager, or a 'ustomer =ants a "i&&erent &ont than one o& those three. >r perhaps you =ant to use a &ont &or spe'ialiKe" purposes, su'h as a 6"ingbats9 &ont instea" o& a series o& #28 graphi's. 5he easiest =ay to a''omplish this is to pa'kage the "esire" &ont(s) =ith your appli'ation. 5o "o this, simply 'reate an assets/ &ol"er in the proGe't root, an" put your 5rue5ype (55*) &onts in the assets. ?ou might, &or e;ample, 'reate assets/fontsP an" put your 55* &iles in there. 5hen, you nee" to tell your =i"gets to use that &ont. $n&ortunately, you 'an no longer use layout FML &or this, sin'e the FML "oes not kno= about any &onts you may ha!e tu'ke" a=ay as an appli'ation asset. 0nstea", you nee" to make the 'hange in Ca!a 'o"e,
import android.Eidget.&eGtVieEJ import java.io.9ileJ public class 9ont2ampler eGtends ActivitF : O"verride public void onCreateP4undle icicleQ : super.onCreatePicicleQJ setContentViewP?.laFout.mainQJ &eGtVieE tv6P&eGtVieEQfindViewByIdP?.id.customQJ &Fpeface face6&Fpeface.create"rom$ssetPget$ssetsPQ8 7fonts/!andmade&FpeEriter.ttf7QJ tv.setTypefacePfaceQJ

0:7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"onts

9ile font6neE "ileP$nvironment.get+xternalStorageDirectoryPQ8 7#g"pen+osmetica4old.ttf7QJ if Pfont.existsPQQ : tv6P&eGtVieEQfindViewByIdP?.id.fileQJ face6&Fpeface.create"rom"ilePfontQJ tv.setTypefacePfaceQJ ; else : findViewByIdP?.id.fileroEQ.setVisi'ilityPVieE.D"%$QJ ;

; ;

+ere =e grab the &eGtVieE &or our 6'ustom9 sample, then 'reate a &Fpeface obGe't !ia the stati' create9romAssetPQ buil"er metho". 5his takes the appli'ation[s Asset#anager (&rom getAssetsPQ) an" a path =ithin your assets/ "ire'tory to the &ont you =ant. 5hen, it is Gust a matter o& telling the &eGtVieE to set&FpefacePQ, pro!i"ing the &Fpeface you Gust 'reate". 0n this 'ase, =e are using the +an"ma"e 5ype=riter &ont. ?ou 'an also loa" a &ont out o& a lo'al &ile an" use it. 5he bene&it is that you 'an 'ustomiKe your &onts a&ter your appli'ation has been "istribute". >n the other han", you ha!e to someho= arrange to get the &ont onto the "e!i'e. 1ut Gust as you 'an get a &Fpeface !ia create9romAssetPQ, you 'an get a &Fpeface !ia create9rom9ilePQ. 0n our 9ont2ampler, =e look in the root o& Me;ternal storageM (typi'ally the %@ 'ar") &or the Mg>penCosmeti'a1ol" 5rue5ype &ont &ile, an" i& it is &oun", =e use it &or the &i&th ro= o& the table. >ther=ise, =e hi"e that ro=. 5he resultsH

0:8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"onts

"igure *2*1 The "ontSampler application

We =ill go into more "etails regar"ing assets an" lo'al &iles in an up'oming 'hapter. 2ote that An"roi" "oes not seem to like all 5rue5ype &onts. When An"roi" "islikes a 'ustom &ont, rather than raise an $Gception, it seems to substitute @roi" %ans (9sans9) Ruietly. %o, i& you try to use a "i&&erent &ont an" it "oes not seem to be =orking, it may be that the &ont in Ruestion is in'ompatible =ith An"roi", &or =hate!er reason.

3ere a (lyph@ There a (lyph


5rue5ype &onts 'an be rather pu"gy, parti'ularly i& they support an e;tensi!e subset o& the a!ailable $ni'o"e 'hara'ters. 5he +an"ma"e 5ype=riter &ont use" abo!e runs o!er 40D1T the @eGa-u &ree &onts 'an run up=ar"s o& A00D1 apie'e. E!en 'ompresse", these a"" bulk to your appli'ation, so be 'are&ul not to go o!erboar" =ith 'ustom &onts, lest your appli'ation take up too mu'h room on your users[ phones.
0::

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

"onts

Con!ersely, bear in min" that &onts may not ha!e all o& the glyphs that you nee". As an e;ample, let us talk about the ellipsis. An"roi"7s &eGtVieE 'lass has the built-in ability to MellipsiKeM te;t, trun'ating it an" a""ing an ellipsis i& the te;t is longer than the a!ailable spa'e. ?ou 'an use this !ia the android:ellipsiKe attribute, &or e;ample. 5his =orks &airly =ell, at least &or single-line te;t. 5he ellipsis that An"roi" uses is not three perio"s. ather it uses an a'tual ellipsis 'hara'ter, =here the three "ots are 'ontaine" in a single glyph. +en'e, any &ont that you use that you also use the MellipsiKingM &eature =ill nee" the ellipsis glyph. 1eyon" that, though, An"roi" pa"s out the string that gets ren"ere" ons'reen, su'h that the length (in 'hara'ters) is the same be&ore an" a&ter MellipsiKingM. 5o make this =ork, An"roi" repla'es one 'hara'ter =ith the ellipsis, an" repla'es all other remo!e" 'hara'ters =ith the $ni'o"e 'hara'ter 7QE > W0@5+ 2>-1 EAD %#ACE7 ( 3R9$99). 5his means the Me;traM 'hara'ters a&ter the ellipsis "o not take up any !isible spa'e on s'reen, yet they 'an be part o& the string. +o=e!er, this means any 'ustom &onts you use &or &eGtVieE =i"gets that you use =ith android:ellipsiKe must also support this spe'ial $ni'o"e 'hara'ter. 2ot all &onts "o, an" you =ill get arti&a'ts in the on-s'reen representation o& your shortene" strings i& your &ont la'ks this 'hara'ter (e.g., rogue F7s appear at the en" o& the line). An", o& 'ourse, An"roi"7s international "eployment means your &ont must han"le any language your users might be looking to enter, perhaps through a language-spe'i&i' input metho" e"itor. +en'e, =hile using 'ustom &onts in An"roi" is !ery possible, there are many potential problems, an" so you must =eigh 'are&ully the bene&its o& the 'ustom &onts !ersus their potential 'osts.

2<<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 21

+ore /evelopment Tools

5he An"roi" %@D is more than a library o& Ca!a 'lasses an" A#0 'alls. 0t also in'lu"es a number o& tools to assist in appli'ation "e!elopment. E'lipse, o& 'ourse, ten"s to "ominate the "is'ussion. +o=e!er, that is not the only tool at your "isposal, so, let7s take a Rui'k tour o& =hat else is a!ailable to you.

3ierarchy ;ie)er5 3o) /eep s .our CodeF


An"roi" 'omes =ith a +ierar'hy -ie=er tool, "esigne" to help you !isualiKe your layouts as they are seen in a running a'ti!ity in a running emulator. %o, &or e;ample, you 'an "etermine ho= mu'h spa'e a 'ertain =i"get is taking up, or try to &in" =here a =i"get is hi"ing that "oes not appear on the s'reen. 5o use the +ierar'hy -ie=er, you &irst nee" to &ire up your emulator, install your appli'ation, laun'h your a'ti!ity, an" na!igate to the spot you =ish to e;amine. 2ote that you 'annot use +ierar'hy -ie=er =ith a pro"u'tion An"roi" "e!i'e. ?ou 'an laun'h the +ierar'hy -ie=er !ia the hierarchFvieEer program, &oun" in the tools/ "ire'tory in your An"roi" %@D installation, or &rom insi"e o& E'lipse,

2<*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *2&1 3ierarchy ;ie)er main )indo)

5he roots o& the table sho= the emulator instan'es presently running on your "e!elopment ma'hine. 5he lea!es represent appli'ations running on that parti'ular emulator. ?our a'ti!ity =ill be i"enti&ie" by appli'ation pa'kage an" 'lass (e.g., com.commonsEare.android.files/...). Where things get interesting, though, is =hen you 'hoose a =in"o= an" 'li'k Loa" -ie= +ierar'hy. A&ter a &e= se'on"s, the "etails spring into, er, !ie=,

2<&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *2-1 3ierarchy ;ie)er !ayout ;ie)

5he main area o& the Layout -ie= sho=s a tree o& the !arious =i"gets an" stu&& that make up your a'ti!ity, starting &rom the o!erall system =in"o= an" "ri!ing "o=n into the in"i!i"ual $0 =i"gets that users are suppose" to intera't =ith. 5his in'lu"es both =i"gets an" 'ontainers "e&ine" by your appli'ation an" others that are supplie" by the system, in'lu"ing the title bar. Cli'king on one o& the !ie=s a""s more in&ormation to this perspe'ti!e,

2<-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *2%1 3ierarchy ;ie)er ;ie) properties

2o=, in the right region o& the -ie=er, =e see properties o& the sele'te" =i"get or 'ontainer, plus timing "etails &or ho= long it took to ren"er that 'ontainer an" its 'hil"ren. Also, the =i"get is highlighte" in re" in the =ire&rame o& the a'ti!ity, sho=n beneath the properties (by "e&ault, !ie=s are sho=n as =hite outlines on a bla'k ba'kgroun"). 5his 'an help you ensure you ha!e sele'te" the right =i"get, i&, say, you ha!e se!eral buttons an" 'annot rea"ily tell &rom the tree =hat is =hat. ?ou 'an also,

%a!e the tree "iagram as a #28 &ile %a!e the $0 as a #hotoshop #%@ &ile, =ith "i&&erent layers &or the "i&&erent =i"gets an" 'ontainers *or'e the $0 to repaint in the emulator or re-loa" the hierar'hy, in 'ase you ha!e ma"e 'hanges to a "atabase or to the app7s 'ontents an" nee" a &resh "iagram

2<%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

1a'k on the main s'reen, instea" o& 'li'king Loa" -ie= +ierar'hy, you 'oul" ha!e 'li'ke" 0nspe't %'reenshot. 5his puts the -ie=er in a =hole ne= perspe'ti!e, 'alle" the #i;el #er&e't -ie=,

"igure *201 3ierarchy ;ie)er Pixel Perfect ;ie)

>n the le&t, you see a tree representing the =i"gets an" other VieEs in your a'ti!ity. 0n the mi""le, you see a Koome" !ie= o& your a'ti!ity, sho=n at normal siKe on the right. 5he 'rosshairs o!erlaying the a'ti!ity sho= the position being Koome" upon Z Gust 'li'k on a ne= area to 'hange =here =hat you are seeing. 5here is a sli"er to 'ontrol the le!el o& Koom. Cli'king on a pi;el also in"i'ates the position an" 'olor o& that pi;el. 0& you toggle the Auto e&resh 'he'kbo; in the toolbar, the -ie=er =ill poll an" reloa" the $0 &rom your a'ti!ity perio"i'ally, =ith the &reRuen'y 'ontrolle" by another sli"er.

2<0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

//+S5 >nder AndroidGs 3ood


Another tool in the An"roi" "e!eloper7s arsenal is the @al!ik @ebug Monitor %er!i'e (@@M%). 5his is a M%=iss army kni&eM, allo=ing you to "o e!erything &rom bro=se log &iles, up"ate the 8#% lo'ation pro!i"e" by emulator, simulate in'oming 'alls an" messages, an" bro=se the onemulator storage to push an" pull &iles. E!entually, this se'tion =ill 'ontain a 'omplete o!er!ie= o& @@M%. +o=e!er, @@M% has a =i"e range o& uses, so this se'tion =ill gra"ually e;pan" o!er time to try to 'o!er them all. 5o laun'h @@M%, run the ddms program insi"e the tools/ "ire'tory in your An"roi" %@D "istribution, or open the @@M% perspe'ti!e in E'lipse. 0t =ill initially "isplay Gust a tree o& emulators an" running programs on the le&t,

2<2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *221 //+S initial vie)

Cli'king on an emulator allo=s you to bro=se the e!ent log on the bottom an" manipulate the emulator !ia the tabs on the right,

2<7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *271 //+S@ )ith emulator selected

)o!!in!
ather than use adb logcat, @@M% lets you !ie= your logging in&ormation in a s'rollable table. Cust highlight the emulator or "e!i'e you =ant to monitor, an" the bottom hal& o& the s'reen sho=s the logs. 0n a""ition, you 'an,

*ilter the Log tab by any o& the &i!e logging le!els, sho=n as the through E toolbar buttons. Create a 'ustom &ilter, so you 'an !ie= only those tagge" =ith your appli'ation7s tag, by pressing the \ toolbar button an" 'ompleting the &orm (sho=n belo=). 5he name you enter in the &orm =ill be
2<8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

use" as the name o& another logging output tab in the bottom portion o& the @@M% main =in"o=.

%a!e the log in&ormation to a te;t &ile &or later perusal, or &or sear'hing.

"igure *281 //+S logging filter

5ile Push nd Pull


While you 'an use adb pull an" adb push to get &iles to an" &rom an emulator or "e!i'e, @@M% lets you "o that !isually. Cust highlight the emulator or "e!i'e you =ish to =ork =ith, then 'hoose DeviceD'ile *xplorer... &rom the main menu. 5hat =ill bring up your typi'al "ire'tory bro=ser,

2<:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *2:1 //+S "ile =xplorer

Cust bro=se to the &ile you =ant an" 'li'k either the pull (le&t-most) or push (mi""le) toolbar button to trans&er the &ile toP&rom your "e!elopment ma'hine. >r, 'li'k the "elete (right-most) toolbar button to "elete the &ile. 5here are a &e= 'a!eats to this,

?ou 'annot 'reate "ire'tories through this tool. ?ou =ill either nee" to use adb shell or 'reate them &rom =ithin your appli'ation. While you 'an putter through most o& the &iles on an emulator, you 'an a''ess !ery little outsi"e o& /sdcard on an a'tual "e!i'e, "ue to An"roi" se'urity restri'tions.

Screenshots
5o take a s'reenshot o& the An"roi" emulator or "e!i'e, simply press L+trlM-L2M or 'hoose DeviceD $creen capture... &rom the main menu. 5his =ill bring up a "ialog bo; 'ontaining an image o& the 'urrent s'reen,

2*<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *7<1 //+S screen capture

*rom here, you 'an 'li'k E$aveF to sa!e the image as a #28 &ile some=here on your "e!elopment ma'hine, E0efreshF to up"ate the image base" on the 'urrent state o& the emulator or "e!i'e, or EDoneF to 'lose the "ialog.

)oc tion -pd tes


5o use @@M% to supply lo'ation up"ates to your appli'ation, the &irst thing you must "o is ha!e your appli'ation use the gps )ocation(rovider, as that is the one that @@M% is set to up"ate. 5hen, 'li'k on the Emulator Control tab an" s'roll "o=n to the Lo'ation Controls se'tion. +ere, you =ill &in" a smaller tabbe" pane =ith three options &or spe'i&ying lo'ations, Manual, 8#F, an" DML,

2**

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *7*1 //+S location controls

5he Manual tab is &airly sel&-e;planatory, pro!i"e a latitu"e an" longitu"e an" 'li'k the %en" button to submit that lo'ation to the emulator. 5he emulator, in turn =ill noti&y any lo'ation listeners o& the ne= position. @is'ussion o& the 8#F an" DML options is reser!e" &or a &uture e"ition o& this book.

Pl cin! C lls nd %ess !es


0& you =ant to simulate in'oming 'alls or %M% messages to the An"roi" emulator, @@M% 'an han"le that as =ell.

2*&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

>n the Emulator Control tab, abo!e the Lo'ation Controls group, is the 5elephony A'tions group,

"igure *7&1 //+S telephony controls

5o simulate an in'oming 'all, &ill in a phone number, 'hoose the -oi'e ra"io button, an" 'li'k Call. At that point, the emulator =ill sho= the in'oming 'all, allo=ing you to a''ept it (!ia the green phone button) or reGe't it (!ia the re" phone button),

2*-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *7-1 Simulated incoming call

5o simulate in an in'oming te;t message, &ill in a phone number, 'hoose the %M% ra"io button, enter a message in the pro!i"e" te;t area, an" 'li'k %en". 5he te;t message =ill then appear as a noti&i'ation,

2*%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *7%1 Simulated text message

An", o& 'ourse, you 'an 'li'k on the noti&i'ation to !ie= the message in the &ull-&le"ge" Messaging appli'ation,

"igure *701 Simulated text message@ in +essaging application

2*0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

%emory % n !ement
@@M% also helps you "iagnose issues relate" to ho= your appli'ation makes use o& memory, parti'ularly heap spa'e. >n the M%ysin&oM tab, you 'an see a pie 'hart o& the o!erall memory allo'ation &or the emulator,

"igure *721 //+S memory usage chart

>n the MAllo'ation 5ra'kerM tab, you 'an re'or" ea'h an" e!ery time your 'o"e (or 'o"e you 'all insi"e o& An"roi") allo'ates memory. %imply highlight your appli'ation7s pro'ess in the tree-table, then 'li'k the %tart 5ra'king button on the Allo'ation 5ra'ker tab. When you =ant to see =hat you ha!e allo'ate" sin'e you 'li'ke" %tart 5ra'king, 'li'k the 8et Allo'ations button, =hi'h =ill &ill in a table sho=ing ea'h allo'ation, ho= mu'h memory it =as, an" =here in the 'o"e the memory =as allo'ate",
2*2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

"igure *771 //+S allocation tracker

An", you 'an e!en "ump the entire heap &or your appli'ation !ia the @ump +# >* option, a!ailable !ia a toolbar button (looks like a hal&-empty 'an =ith a "o=n=ar"-pointing arro= to its right). 5he resulting +# >* &ile 'an be use" =ith MA5, an a""-in &or E'lipse, to see =hat obGe'ts are still on the heap an" =ho is 'ausing them to sti'k aroun". 1e&ore "umping the +# >* &ile, you may =ish to &or'e a garbage 'olle'tion run on your pro'ess S this 'an be "one by 'li'king the toolbar button that looks like a 'lassi' metal garbage 'an.

adb5 !ike //+S@ With +ore Typing


5he An"roi" @ebug 1ri"ge, or adb utility, ser!es t=o roles,

2*7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

+ore /evelopment Tools

1.

1ehin" the s'enes, it ser!es as a bri"ge bet=een your emulatorsP"e!i'es an" the rest o& the tools. *or e;ample, A@5, +ierar'hy -ie=er, an" @@M% all 'ommuni'ate =ith your emulator !ia the adb bri"ge. 5his bri"ge 'omes in the &orm o& a "aemon pro'ess, spa=ne" the &irst time you try using any o& those tools sin'e your last reboot.

2. 0t o&&ers 'omman"-line eRui!alents &or many &eatures o& the other tools, notably @@M%. %ome o& the things you 'an "o =ith adb in'lu"e,

%tart (adb start-server) or a&orementione" "aemon pro'ess

stop

(adb

kill-server)

the

List all o& the re'ogniKe" An"roi" "e!i'es an" emulators presently !isible (adb devices) 8et a''ess to a Linu; shell insi"e your "e!i'e or emulator ( adb shell) 0nstall or uninstall An"roi" appli'ations on your "e!i'e or emulator (adb install) Copy &iles to (adb push) or &rom (adb pull) the emulator, mu'h like @@M%7s *ile E;plorer E;amine LogCat (adb logcat)

2*8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

PART VII Alternative Application #nvironments

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 22

The Cole of Alternative =nvironments

?ou might think that An"roi" is all about Ca!a. 5he o&&i'ial An"roi" %o&t=are @e!elopment Dit (%@D) is &or Ca!a "e!elopment, the buil" tools are &or Ca!a "e!elopment, the "is'ussion groups an" blog posts an", yes, most books are &or Ca!a "e!elopment. +e'k, most o& this book is about Ca!a. +o=e!er (an" =ith apologies to William 8ol"man), it Gust so happens that An"roi" is only mostly Ca!a. 5here7s a big "i&&eren'e bet=een mostly Ca!a an" all Ca!a. Mostly Ca!a is slightly not Ca!a. %o, =hile An"roi"7s Ms=eet spotM =ill remain Ca!a-base" appli'ations &or the near term, you 'an still 'reate appli'ations using other te'hnologies. 5his part o& the book =ill take a peek at some o& those alternati!es. 5his 'hapter starts =ith an e;amination o& the pros an" 'ons o& An"roi"7s Ca!a-'entri' strategy. 0t then enumerates some reasons =hy you might =ant to use something else &or your An"roi" appli'ations. 5he "o=nsi"es o& alternati!e An"roi" appli'ation en!ironments S la'k o& support an" te'hni'al 'hallenges S are also "is'usse".

2&*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

The Cole of Alternative =nvironments

n the Beginning@ There Was 6ava111


5he 'ore An"roi" team ma"e a &airly reasonable 'hoi'e o& language =hen they 'hose Ca!a. 0t is a !ery popular language, an" in the mobile 'ommunity it ha" a 'lear pre"e'essor in Ca!a Mi'ro E"ition (C2ME). La'king "ire't a''ess to memory a""resses (so-'alle" MpointersM), a Ca!a-base" appli'ation =ill be less prone to "e!eloper errors lea"ing to bu&&er o!erruns, resulting in possible ha'ks. An" there is a &airly robust e'osystem aroun" Ca!a, in terms o& e"u'ational materials, e;isting 'o"e bases, integrate" "e!elopment en!ironments (0@Es), an" so on. +o=e!er, =hile you 'an program An"roi" in the Ca!a language, an An"roi" "e!i'e "oes not run a Ca!a appli'ation. 0nstea", your Ca!a 'o"e is 'on!erte" into something that runs on the M@al!ik !irtual ma'hineM. 5his is akin to the te'hnology use" &or regular Ca!a appli'ations, but @al!ik is spe'i&i'ally tune" &or An"roi"7s en!ironment. Moreo!er, it limits the "epen"en'y o& An"roi" on Ca!a itsel& to a han"&ul o& programming tools, important as Ca!a7s ste=ar"ship mo!es &rom %un to >ra'le to =here!er. 5hat @al!ik !irtual ma'hine is also 'apable o& running 'o"e &rom other programming languages, a &eature that makes possible mu'h o& =hat this book 'o!ers.

111And t Was ,9
2o mobile "e!elopment en!ironment is per&e't, an" so the 'ombination o& Ca!a an" An"roi" has its issues. At the time o& this =riting, Ca!a, as implemente" &or the @al!ik !irtual ma'hine, is interprete", =ithout any o& the MGust-in-time 'ompilerM tri'ks regular Ca!a uses to boost per&orman'e. 5his is a bigger problem in mobile, sin'e the "e!i'es An"roi" runs upon ten" to be less po=er&ul than your a!erage "esktop, notebook, or Web ser!er. +en'e, there =ill be some things you Gust 'an7t "o on An"roi" =ith Ca!a be'ause it is too slo=.

2&&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The Cole of Alternative =nvironments

Ca!a uses garbage 'olle'tion to sa!e people &rom ha!ing to keep tra'k o& all o& their memory allo'ations. 5hat =orks &or the most part, an" it is generally a boon to "e!eloper pro"u'ti!ity. +o=e!er, it is not a 'ure-all &or e!ery memory an" resour'e allo'ation problem. ?ou 'an still ha!e =hat amounts to Mmemory leaksM in Ca!a, e!en i& the pre'ise me'hani's o& those leaks "i&&er &rom the 'lassi' leaks you get in C, C\\, et'. Most importantly, though, not e!erybo"y likes Ca!a. 0t 'oul" be be'ause they la'k e;perien'e =ith it, or perhaps they ha!e e;perien'e =ith it an" "i" not enGoy that e;perien'e. Certainly, Ca!a is slo=ly being 'onsi"ere" as a language &or big enterprise systems an", there&ore, is not ne'essarily M'oolM. A"!o'ates o& "i&&erent languages =ill ha!e their o=n pet pee!es =ith Ca!a as =ell (e.g., to a uby "e!eloper, Ca!a is really !erbose). %o, =hile Ca!a =as not a ba" 'hoi'e &or An"roi", it =as not per&e't, either.

Bucking the Trend


+o=e!er, Gust be'ause Ca!a is the "ominant =ay to buil" apps &or An"roi", that "oes not mean it is the only =ay, an" &or you, it may not e!en be the best =ay. #erhaps Ca!a is not in your e;isting skill set. ?ou might be a Web "e!eloper, more 'om&ortable =ith +5ML, C%%, an" Ca!as'ript. 5here are &rame=orks to help you =ith that. >r, maybe you 'ut your teeth on ser!er-si"e s'ripting languages like #erl or #ython S there are =ays to sling that 'o"e on An"roi" as =ell. >r perhaps you alrea"y ha!e a bun'h o& 'o"e in CPC\\, su'h as game physi's algorithms, that =oul" be pain&ul to re=rite in Ca!a S you shoul" be able to reuse that 'o"e too. E!en i& you =oul" be =illing to learn Ca!a, it may be that your ine;perien'e =ith Ca!a an" the An"roi" A#0s =ill Gust slo= you "o=n. ?ou might be able to get something built mu'h more Rui'kly =ith another &rame=ork, e!en i& you =in" up repla'ing it =ith a Ca!a-base" implementation in the &uture. api" "e!elopment an" prototyping is &reRuently important, to get early &ee"ba'k =ith minimal in!estment in time.
2&-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The Cole of Alternative =nvironments

An", o& 'ourse, you might Gust &in" Ca!a programming to be irritating. ?ou =oul" not be the &irst, nor the last, to ha!e that sentiment. #arti'ularly i& you are getting into An"roi" as a hobby, rather than as part o& your M"ay GobM, ha!ing &un =ill be important to you, an" you might not &in" Ca!a to be mu'h &un. *ortunately, An"roi" is &rien"ly to=ar"s alternati!e =ays o& buil"ing appli'ations, unlike some mobile plat&orms.

Support@ Structure
+o=e!er, M&rien"lyM an" M&ully supporte"M are t=o "i&&erent things. %ome alternati!es to Ca!a-base" "e!elopment are o&&i'ially supporte" by the 'ore An"roi" team, su'h as CPC\\ "e!elopment !ia the 2ati!e @e!elopment Dit (2@D) an" Web-style "e!elopment !ia +5MLA. %ome alternati!es to Ca!a-base" "e!elopment are supporte" by 'ompanies. A"obe supports A0 , 2itobi supports #hone8ap, homobile supports ho"es, an" so on. >ther alternati!es are supporte" by stan"ar"s bo"ies, like the Worl" Wi"e Web Consortium (W.C) supporting +5MLA. %till others are Gust tiny proGe'ts =ith only the ba'king o& a 'ouple o& "e!elopers. ?ou =ill nee" to make the "e'ision &or yoursel& =hi'h o& these le!els o& support =ill meet your reRuirements. *or many things, support is not mu'h o& an issue, but there =ill al=ays be 'ases =here support be'omes paramount (e.g., enterprise appli'ation "e!elopment).

Caveat /eveloper
>& 'ourse, going outsi"e the tra"itional Ca!a en!ironment &or An"roi" "e!elopment has its issues, beyon" Gust ho= mu'h support might be a!ailable.

2&%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

The Cole of Alternative =nvironments

%ome may be less e&&i'ient, in terms o& pro'essor time, memory, or battery li&e, than =ill "e!elopment in Ca!a. CPC\\, on the =hole, is probably better than Ca!a, but +5MLA may be =orse, &or e;ample. @epen"ing on =hat you are =riting an" ho= hea!ily it =ill be use" =ill "etermine ho= 'riti'al that ine&&i'ien'y =ill be. %ome may not be a!ailable on all "e!i'es. ight no=, *lash is the best e;ample o& this S some "e!i'es o&&er some amount o& *lash support, =hile other "e!i'es ha!e no *lash at all. %imilarly, +5MLA support =as only a""e" to An"roi" in An"roi" 2.0, so "e!i'es running ol"er !ersions o& An"roi" "o not ha!e +5MLA as a built-in option. E!ery layer bet=een you an" o&&i'ially supporte" en!ironments makes it that mu'h more "i&&i'ult &or you to ensure 'ompatibility =ith ne= !ersions o& An"roi", =hen they arise. *or e;ample, i& you 'reate an appli'ation using #hone8ap, an" a ne= An"roi" !ersion be'omes a!ailable, there may be in'ompatibilities that only the #hone8ap team 'an a""ress. While they =ill probably a""ress those Rui'kly S an" they may pro!i"e some measure o& insulation to you &rom those in'ompatibilities S the response time is outsi"e o& your 'ontrol. 0n some 'ases, that is not a problem, but in other 'ases, that might be ba" &or your proGe't. +en'e, Gust be'ause you are "e!eloping outsi"e o& Ca!a "oes not mean e!erything is per&e't. ?ou simply ha!e to tra"e o&& bet=een these problems an" the ones Ca!a-base" "e!elopment might 'ause you. Where the balan'e lies is up to ea'h in"i!i"ual "e!eloper or &irm.

2&0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 26

3T+!0

#rior to the 'urrent =a!e o& interest in mobile appli'ations, the te'hnology du )our =as Web appli'ations. A lot o& attention =as pai" to ACAF, uby on ails, an" other te'hniRues an" te'hnologies that ma"e Web appli'ations 'limb 'lose to e;perien'e o& a "esktop appli'ation, an" sometimes superior. 5he e;plosion o& Web appli'ations e!entually "ro!e the ne;t roun" o& enhan'ements to Web stan"ar"s, 'olle'ti!ely 'alle" +5MLA. An"roi" 2.0 a""e" the &irst roun" o& support &or these +5MLA enhan'ements. 2otably, An"roi" supports o&&line appli'ations an" Web storage, meaning that +5MLA be'omes a rele!ant te'hniRue &or 'reating An"roi" appli'ations, =ithout "ealing =ith Ca!a.

,ffline Applications
5he lin'hpin &or using +5MLA &or o&&line appli'ations S on An"roi" or else=here S is the ability &or those appli'ations to be use" =hen there is no 'onne'ti!ity, either "ue to problems on the 'lient si"e (e.g., on an airplane sans Wi*i) or on the ser!er si"e (e.g., Web ser!er maintenan'e).

,h t Does It %e nF
+istori'ally, Web appli'ations ha!e ha" this annoying ten"en'y to reRuire Web ser!ers. 5his le" to all sorts o& =orkaroun"s &or o&&line use, up to an" in'lu"ing shipping a Web ser!er an" "eploying it to the "esktop.
2&7
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

+5MLA sol!es this problem by allo=ing Web pages to spe'i&y their o=n 'a'hing rules. A Web app 'an publish a M'a'he mani&estM, "es'ribing =hi'h resour'es,

Can be sa&ely 'a'he", su'h that i& the Web ser!er is una!ailable, the bro=ser =ill Gust use the 'a'he" 'opy Cannot be sa&ely 'a'he", su'h that i& the Web ser!er is una!ailable, the bro=ser shoul" &ail like it normally "oes +a!e a M&allba'kM resour'e, su'h that i& the Web ser!er is una!ailable, the 'a'he" &allba'k resour'e shoul" be use" instea"

*or mobile "e!i'es, this means that a &ully +5MLA-'apable bro=ser shoul" be able to loa" all its assets up &ront an" keep them 'a'he". 0& the user loses 'onne'ti!ity, the appli'ation =ill still run. 0n this respe't, the Web app beha!es almost i"enti'ally to a regular app.

Ho# Do 3ou -se ItF


*or this 'hapter, =e =ill use the Che'klist Mmini appM 'reate" by Ale; 8ibson. While the most up-to-"ate !ersion o& this app 'an be &oun" at the MiniApps Web site, this 'hapter =ill re!ie= the 'opy &oun" in !&#)./+hecklist o& the book7s sour'e 'o"e repository. 5his 'opy is also hoste" online on the CommonsWare site, or !ia a shortene" $ L, http://bit.lF/cE-html..

A=out the S mple App


Che'klist is, as the name suggests, a simple 'he'klist appli'ation. When you &irst laun'h it, the list =ill be empty,

2&8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

"igure *781 The Checklist@ as initially launched

?ou 'an enter some te;t in the top &iel" an" 'li'k the A"" button to a"" it to the list,

2&:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

"igure *7:1 The Checklist@ )ith one item added

?ou 'an M'he'k o&&M in"i!i"ual items, =hi'h are then "isplaye" in strikethrough,

2-<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

"igure *8<1 The Checklist@ )ith one item marked as completed

?ou 'an also "elete the 'he'ke" entries (!ia the @elete Che'ke" button) or all entries (!ia the @elete All button), =hi'h =ill pop up a 'on&irmation "ialog be&ore pro'ee"ing,

2-*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

"igure *8*1 The ChecklistGs delete confirmation dialog

BInst llin!B Chec$list on 3our Phone


5o a''ess Che'klist on your An"roi" "e!i'e, !isit one o& the $ Ls abo!e &or the hoste" e"ition using the 1ro=ser appli'ation S the shortene" one may be easiest to enter into the bro=ser on the "e!i'e. ?ou 'an then a"" a bookmark &or it (More O A"" bookmark &rom the bro=ser7s options menu) to 'ome ba'k to it later. ?ou 'an e!en set up a short'ut &or the bookmark on your home s'reen, i& you so 'hoose S Gust long-tap on the ba'kgroun", 'hoose 1ookmark, then 'hoose the Che'klist bookmark you set up be&ore.

E0 minin! the HT%)


All o& that is a''omplishe" using Gust a han"&ul o& lines o& +5ML,

2-&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

LX="+&5($ htmlM Lhtml lang67en7 manifest67checklist.manifest7M LheadM Lmeta http-eUuiv67+ontent-&Fpe7 content67teGt/htmlJ charset6utf-,7 /M LtitleM+hecklistL/titleM Lmeta name67vieEport7 content67Eidth6device-EidthJ initial-scale61.-J maGimum-scale61.-J userscalable6-J7 /M Lmeta name67apple-mobile-Eeb-app-capable7 content67Fes7 /M Lmeta name67apple-mobile-Eeb-app-status-bar-stFle7 /M Llink rel67apple-touch-startup-image7 href67splashscreen.png7 /M Llink rel67stFlesheet7 href67stFles.css7 /M Llink rel67apple-touch-icon-precomposed7 href67apple-touch-icon-precomposed.png7 /M L/headM LbodFM LsectionM LheaderM Lbutton tFpe67button7 id67sendmail7M#ailL/buttonM Lh1M+hecklistL/h1M L/headerM LarticleM Lform id67inputarea7 onsubmit67add%eEItemPQ7M Linput tFpe67teGt7 name67name7 id67name7 maGlength67/.7 autocorrect placeholder67&ap to enter a neE itemZhellipJ7 /M Lbutton tFpe67button7 id67add7MAddL/buttonM L/formM Lul id67maillist7M Lli class67emptF7MLa href677 id67maillink7M#ail remaining itemsL/aML/liM L/ulM Lp id67totals7MLspan id67tallF17M&otal: Lspan id67total7M-L/spanML/spanM Lspan id67tallF>7M?emaining: Lspan id67remaining7M-L/spanML/spanML/pM Lul id67checklist7M Lli class67emptF7M)oadingZhellipJL/liM L/ulM L/articleM LfieldsetM Lbutton tFpe67button7 id67deletechecked7M=elete +heckedL/buttonM Lbutton tFpe67button7 id67deleteall7M=elete AllL/buttonM L/fieldsetM L/sectionM Lscript src67main.js7ML/scriptM L/bodFM L/htmlM

*or the purposes o& o&&line appli'ations, though, the key is the manifest attribute o& our html element,
Lhtml lang67en7 manifest67checklist.manifest7M

2--

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

+ere, =e spe'i&y the relati!e path to a mani&est &ile, in"i'ating =hat the rules are &or 'a'hing !arious portions o& this appli'ation o&&line.

E0 minin! the % ni.est


%o, sin'e the mani&est is =here all the &un is, here is =hat Che'klist7s mani&est looks like,
+A+!$ #A%I9$2& Sversion .< stFles.css main.js splashscreen.png

5he +5MLA mani&est &ormat is e;tremely simple. 0t starts =ith a +A+!$ #A%I9$2& line, &ollo=e" by a list o& &iles (te'hni'ally, relati!e $ Ls) that shoul" be 'a'he". 0t also supports 'omments, =hi'h are lines beginning =ith S. 5he mani&est 'an also ha!e a %$&@"?H: line, &ollo=e" by relati!e $ Ls that shoul" ne!er be 'a'he". %imilarly, the mani&est 'an ha!e a 9A))4A+H: line, &ollo=e" by pairs o& relati!e $ Ls, the $ L to try to &et'h o&& the net=ork, &ollo=e" by the $ L o& a 'a'he" resour'e to use i& the net=ork is not a!ailable. 0n prin'iple, the mani&est shoul" reRuest 'a'hing &or e!erything that the appli'ation nee"s to run, though the page that reRueste" the 'a'hing (indeG.html in this 'ase) is also 'a'he".

Web Storage
Ca'hing the +5MLA appli'ation7s assets &or o&&line use is all =ell an" goo", but that =ill be rather limiting on its o=n. 0n an o&&line situation, the appli'ation =oul" not be able to use ACAF te'hniRues to intera't =ith a Web ser!i'e. %o, i& the appli'ation is going to be able to store in&ormation, it =ill nee" to "o so on the bro=ser itsel&.

2-%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

8oogle 8ears an" relate" tools pioneere" this 'on'ept an" blaKe" the trail &or =hat is no= !ariously 'alle" MWeb %torageM or M@>M %torageM &or +5MLA appli'ations. An +5MLA app 'an store "ata persistently on the 'lient, =ithin 'lient-impose" limits. 5hat, in 'onGun'tion =ith o&&line asset 'a'hing, means an +5MLA appli'ation 'an "eli!er &ar more !alue =hen it la'ks an 0nternet 'onne'tion, or &or "ata that Gust "oes not make sense to store Min the 'lou"M. 2ote that, te'hni'ally, Web %torage is not part o& +5MLA, but is a relate" spe'i&i'ation. +o=e!er, it ten"s to get Mlumpe" in =ithM +5MLA in 'ommon 'on!ersation.

,h t Does It %e nF
>n a Web %torage-enable" bro=ser, your Ca!as'ript 'o"e =ill ha!e a''ess to a local2torage obGe't, representing your appli'ation7s "ata. More a''urately, ea'h MoriginM (i.e., "omain) =ill ha!e a "istin't local2torage obGe't on the bro=ser. 5he local2torage obGe't is an Masso'iati!e arrayM, meaning you 'an =ork =ith it either !ia numeri'al in"e;es or string-base" keys at your "is'retion. -alues typi'ally are strings. ?ou 'an,

*in" out ho= many entries are in the array !ia lengthPQ 8et an" set items by key !ia getItemPQ an" setItemPQ 8et the key &or a numeri'al in"e; !ia keFPQ
clearPQ

emo!e in"i!i"ual entries !ia removeItemPQ or remo!e all items !ia

5his means you "o not ha!e the &ull ri'hness o& a %JL "atabase, like you might ha!e =ith %JLite in a nati!e An"roi" appli'ation. 1ut, &or many appli'ations, this shoul" su&&i'e.

2-0

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

Ho# Do 3ou -se ItF


Che'klist stores the list items as keys in the asso'iati!e array, =ith a !alue o& - &or a regular item an" 1 &or a "elete" item. +ere, =e see the 'o"e &or putting a ne= item into the 'he'klist,
trF : local2torage.setItemPstripped2tring8 dataQJ ; catch PeQ : if Pe 66 Y3"&A $]+$$=$= $??Q : alertPIYuota eGceededXIQJ ; ;

+ere is the 'o"e =here those items are pulle" ba'k out o& storage an" put into an array &or sorting an", later, "isplay as @>M elements on the Web page itsel&,
/*get all items from local2torage and push them one bF one into an arraF.*/ for Pi 6 -J i L6 listlengthJ iRRQ : var item 6 local2torage.keyPiQJ mFArraF.pushPitemQJ

/*sort the arraF into alphabetical order.*/ mFArraF.sortPQJ

When the user 'he'ks the 'he'kmark ne;t to an item, the storage is up"ate" to toggle the 'he'ke" setting persistently,
/*toggle the check flag.*/ if Ptarget.previous2ibling.checkedQ : data 6 -J ; else : data 6 1J ; /*save item in local2torage.*/ trF : local2torage.setItemPname8 dataQJ ; catch PeQ : if Pe 66 Y3"&A $]+$$=$= $??Q : alertPIYuota eGceededXIQJ

2-2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

; ;

Che'klist also has 'o"e to "elete items &rom storage, either all those marke" as 'he'ke",
/*remove everF item from local2torage that has the data flag checked.*/ Ehile Pi L6 local2torage.length-1Q : var keF 6 local2torage.keyPiQJ if Plocal2torage.getItemPkeFQ 666 I1IQ : local2torage.remo!eItemPkeFQJ ; else : iRRJ ;

...or all items,


/*deletes all items in the list.*/ deleteAll: functionPQ : /*ask for user confirmation.*/ var ansEer 6 confirmP7=elete all itemsN7QJ /*if Fes.*/ if PansEerQ : /*remove all items from local2torage.*/ local2torage.clearPQJ /*update vieE.*/ checklistApp.get$llItemsPQJ ; /*clear up.*/ delete checklistApp.deleteAllJ ;8

,e= SH) D t = se
An"roi"7s built-in bro=ser also supports a MWeb %JL @atabaseM option, one =here you 'an use %JLite-style "atabases &rom Ca!as'ript. 5his a""s a lot more po=er than basi' Web %torage, albeit at a 'omple;ity 'ost. 0t is also not part o& an a'ti!e stan"ar" S the W+A5W8 team =orking on this stan"ar" has set it asi"e &or the time being.

2-7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

?ou might 'onsi"er e!aluating La=n'hair, =hi'h is a Ca!as'ript A#0 that allo=s you to store arbitrary C%>2-en'o"e" obGe'ts. 0t =ill use =hate!er storage options are a!ailable, an" there&ore =ill help you "eal =ith 'rossplat&orm !ariety. 0n parti'ular, it supports the 8oogle 8ears &a'ility &oun" in some ol"er !ersions o& An"roi".

(oing To Production
Creating a little test appli'ation reRuires nothing magi'al. #resumably, though, you are intereste" in others using your appli'ation S perhaps many others. Classi' Ca!a-base" An"roi" appli'ations ha!e to "eal =ith testing, ha!ing the appli'ation "igitally signe" &or pro"u'tion, "istribution through !arious 'hannels (su'h as the An"roi" Market), an" up"ates to the appli'ation by one means or another. 5hose issues "o not all magi'ally !anish be'ause +5MLA is use" as the appli'ation en!ironment. +o=e!er, +5MLA "oes 'hange things signi&i'antly &rom =hat Ca!a "e!elopers ha!e to "o.

Testin!
%in'e +5MLA =orks in other bro=sers, testing your business logi' 'oul" easily take a"!antage o& any number o& +5ML an" Ca!as'ript testing tools, &rom %elenium to J$nit to Casmine. *or testing on An"roi" proper S to ensure there are no issues relate" to An"roi"7s bro=ser implementation S you 'an use %elenium7s An"roi" @ri!er or emote Control mo"es.

Si!nin! nd Distri=ution
$nlike nati!e An"roi" appli'ations, you "o not nee" to =orry about signing your +5MLA appli'ations. 5he "o=nsi"e o& this is that there is no support &or "istribution o& +5MLA appli'ations through the An"roi" Market, =hi'h to"ay only supports nati!e
2-8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

An"roi" apps. $sers =ill ha!e to &in" your appli'ation by one means or another, !isit it in the bro=ser, bookmark the page, an" possibly 'reate a home s'reen short'ut to that bookmark.

-pd tes
$nlike nati!e An"roi" appli'ations, =hi'h by "e&ault must be up"ate" manually, +5MLA appli'ations =ill be transparently up"ate" the ne;t time they run the app =hile 'onne'te" to the 0nternet. 5he o&&line 'a'hing proto'ol =ill 'he'k the Web ser!er &or ne= e"itions o& &iles be&ore &alling ba'k to the 'a'he" 'opies. +en'e, there is nothing more &or you to "o other than publish the latest Web app assets.

ssues .ou +ay =ncounter


$n&ortunately, nothing is per&e't. While +5MLA may make many things easier, it is not a pana'ea &or all An"roi" "e!elopment problems. 5his se'tion 'o!ers some potential areas o& 'on'ern you =ill =ant to 'onsi"er as you mo!e &or=ar" =ith +5MLA appli'ations &or An"roi".

Android Device >ersions


2ot all An"roi" "e!i'es support +5MLA S only those running An"roi" 2.; or higher. 0"eally, there&ore, you "o a bit o& Muser-agent sni&&ingM on your Web ser!er an" re"ire't ol"er An"roi" users to some other page e;plaining the limitations in their "e!i'e. +ere is the user-agent string &or a 2e;us >ne "e!i'e running An"roi" 2.1,
#oKilla/..- P)inuGJ 3J Android >.1-update1J en-usJ %eGus "ne 4uild/$?$>/Q Apple@ebHit/.C-.1/ PH!&#)8 like DeckoQ Version/<.- #obile 2afari/.C-.1/

2-:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

As you 'an see, it is &ormatte" like a typi'al mo"ern user-agent string, meaning it is Ruite a mess. 0t "oes in"i'ate it is running Android >.1update1. E!entually, somebo"y =ill 'reate a "atabase o& user-agent strings &or "i&&erent "e!i'e mo"els, an" &rom there =e 'an "eri!e appropriate regular e;pressions or similar algorithms to "etermine =hether a gi!en "e!i'e 'an support +5MLA appli'ations.

Screen SiEes nd Densities


+5MLA appli'ations 'an be run on a =i"e range o& s'reen siKes, &rom J-8A An"roi" "e!i'es to 1080p LC@s an" beyon". %imilarly, s'reen "ensities may !ary Ruite a bit, so =hile a <8;<8 pi;el image on a smartphone may be an appropriate siKe, it may be too big &or a 1080p tele!ision, let alone a 2<M LC@ "esktop monitor. >ther than in'reasing the possible options on the lo= en" o& s'reen siKes, none o& this is uniRue to An"roi". ?ou =ill nee" to "etermine ho= best to "esign your +5ML an" C%% to =ork on a range o& siKes an" "ensities, e!en i& An"roi" =ere not part o& the pi'ture.

)imited Pl t.orm Inte!r tion


+5MLA, =hile o&&ering more plat&orm integration than e!er be&ore, "oes not 'ome 'lose to 'o!ering e!erything an An"roi" appli'ation might =ant to be able to "o. *or e;ample, an or"inary +5MLA appli'ation 'annot,

Laun'h another appli'ation Work =ith the 'onta'ts "atabase aise a noti&i'ation @o =ork truly in the ba'kgroun" (though MWeb =orkersM may alle!iate this some=hat some"ay) 0ntera't =ith 1luetooth "e!i'es

2%<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

e'or" au"io or !i"eo $se the stan"ar" An"roi" pre&eren'e system $se spee'h re'ognition or te;t-to-spee'h An" so on

Many appli'ations =ill not nee" these 'apabilities, o& 'ourse. An", one 'an e;pe't that other appli'ation en!ironments, like #hone8ap, =ill e!ol!e into M+5MLA #lusM &or An"roi". 5hat =ay, you 'oul" 'reate a sto'k appli'ation that =orks a'ross all "e!i'es an" an enhan'e" An"roi" appli'ation that le!erages greater plat&orm integration, at the 'ost o& some a""itional amount o& programming.

Per.orm nce nd B ttery


5here has been a nagging 'on'ern &or some time that +5ML-base" user inter&a'es are ine&&i'ient 'ompare" to nati!e An"roi" $0s, in terms o& pro'essor time, memory, an" battery. *or e;ample, one o& the state" reasons &or a!oi"ing 1>2@0-style Web =i"gets &or the An"roi" home s'reen is per&orman'e. Certainly, it is possible to "esign +5MLA appli'ations that =ill su'k "o=n the battery. *or e;ample, i& you ha!e a hunk o& Ca!as'ript 'o"e running e!ery se'on" in"e&initely, that is going to 'onsume a &air amount o& pro'essor time. +o=e!er, outsi"e o& that, it seems unlikely that an or"inary appli'ation =oul" be use" so hea!ily as to materially impa't battery li&e. Certainly, more testing =ill nee" to be "one in this area. Also, an +5MLA appli'ation may be a bit slo=er to start up than are other appli'ations, i& the 1ro=ser has not been use" in a =hile, or i& the net=ork 'onne'tion is there but has minimal ban"=i"th to your ser!er.

2%*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

)oo$ nd 5eel
+5MLA appli'ations 'an 'ertainly look !ery sli'k an" pro&essional S a&ter all, they are built =ith Web te'hnologies, an" Web apps 'an look !ery sli'k an" pro&essional. +o=e!er, +5MLA appli'ations =ill not ne'essarily look like stan"ar" An"roi" appli'ations, at least not initially. %ome enterprising "e!elopers =ill, no "oubt, 'reate some reusable C%%, Ca!as'ript, an" images that =ill, &or e;ample, mirror an An"roi" nati!e 2pinner =i"get (a type o& "rop-"o=n 'ontrol). %imilarly, +5MLA appli'ations =ill ten" to la'k options menus, noti&i'ations, or other $0 &eatures that a nati!e An"roi" appli'ation may =ell use. 5his is not ne'essarily ba". Consi"ering the "i&&i'ulty in 'reating a !ery sli'k-looking An"roi" appli'ation, +5MLA appli'ations may ten" to look better than their An"roi" 'ounterparts. A&ter all, there are many more people skille" in 'reating sli'k Web apps than are skille" in 'reating sli'k An"roi" apps. +o=e!er, some users may 'omplain about the look-an"-&eel "isparity, Gust be'ause it is "i&&erent.

Distri=ution
+5MLA appli'ations 'an be tri!ially a""e" to a user7s "e!i'e S bro=se, bookmark, an" a"" a short'ut to the home s'reen. +o=e!er, +5MLA appli'ations =ill not sho= up in the An"roi" Market, so users traine" to look at the Market &or a!ailable appli'ations =ill not &in" +5MLA appli'ations, e!en ones that may be better than their nati!e 'ounterparts. 0t is 'on'ei!able that, some"ay, the An"roi" Market =ill support +5MLA appli'ations. 0t is also 'on'ei!able that, some"ay, An"roi" users =ill ten" to &in" their apps by means other than sear'hing the An"roi" Market, an" =ill
2%&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

be able to get their +5MLA apps that =ay. +o=e!er, until one o& those be'omes true, +5MLA appli'ations may be less M"is'o!erableM than their nati!e eRui!alents.

3T+!0 and Alternative Android Bro)sers


While the built-in An"roi" bro=ser =ill be the 'hoi'e o& many An"roi" users, there are other bro=sers a!ailable. +ere is ho= some o& the betterkno=n alternati!es stan" in terms o& +5MLA support.

5ire.o0 %o=ile
*ire&o; Mobile is presently in beta &orm. 0t supports o&&line 'a'hing an" lo'al storage. +o=e!er, it is unable to run the Che'klist sample 'orre'tly at this time, &or reasons presently unkno=n.

+per %o=ile
>pera Mobile, also in beta, "oes not support lo'al storage, ren"ering Che'klist moot. 0t also "oes not support o&&line 'a'hing at this time.

Dolphin Bro#ser HD 2A<


@olphin 1ro=ser +@ <.0 supports o&&line 'a'hing an" lo'al storage. While there are slight ren"ering problems S perhaps C%%-relate" S in Che'klist, the appli'ation other=ise runs &ine, e!en =ithout an 0nternet 'onne'tion.

3T+!05 The Baseline


+5MLA is likely to be'ome rather popular &or 'on!entional appli'ation "e!elopment. 0t gi!es Web "e!elopers a route to the "esktop. 0t may be the only option &or 8oogle7s Chrome >%. An", =ith e!er-impro!ing support on popular mobile "e!i'es S An"roi" among them S "e!elopers =ill 'ertainly be enti'e" by another roun" o& M=rite on'e, run any=hereM promises.
2%-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

3T+!0

0t is &airly likely that, o!er time, +5MLA =ill be the B2 option &or An"roi" appli'ation "e!elopment, a&ter the 'on!entional Ca!a appli'ation =ritten to the An"roi" %@D. 5hat =ill make +5MLA the baseline &or 'omparing alternati!e An"roi" "e!elopment options S not only =ill those options be 'ompare" to using the %@D, they =ill be 'ompare" to using +5MLA.

2%%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 28

Phone(ap

#hone8ap is perhaps the original alternati!e appli'ation &rame=ork &or An"roi", arri!ing on the s'ene in early 2003. #hone8ap is open sour'e, ba'ke" by 2itobi, =ho o&&ers a mi; o& open sour'e an" 'ommer'ial pro"u'ts, along =ith 'onsulting an" training ser!i'es.

What s Phone(apF
As the #hone8ap About page puts it, The Phone*ap mission is to +eb-enable native device !unctionality with open standards like ,TML" -'' and .ava'cript so that you can !ocus on the app you/re building" not on authoring comple0 plat!orm compatibility layers. #hone8ap, to"ay, &o'uses on bri"ging the gap bet=een Web te'hnologies an" nati!e mobile "e!elopment, =ith a''ess to more &eatures than +5MLA appli'ations ha!e.

,h t Do 3ou ,rite InF


A #hone8ap appli'ation is ma"e up o& +5ML, C%%, an" Ca!a%'ript, no "i&&erent than a mobile Web site or +5MLA appli'ation, e;'ept that the

2%0
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

Web assets are pa'kage" =ith the appli'ation, rather than "o=nloa"e" on the &ly. A pre-installe" #hone8ap appli'ation, there&ore, 'an 'ontain 'omparati!ely large assets, su'h as 'omple; Ca!a%'ript libraries, that might be too slo= to "o=nloa" o!er slo=er E@8E 'onne'tions. +o=e!er, #hone8ap =ill still be limite" by the spee" o& mobile "e!i'es an" ho= Rui'kly WebDit 'an loa" an" pro'ess those assets. Also, "e!elopment &or WebDit-&or-mobile has its "i&&eren'es o!er "e!elopment &or WebDit-&or-"esktops, parti'ularly =ith respe't to tou'h !ersus mouse e!ents. ?ou may =ant to "e!elop using mobile layers o& Ca!a%'ript &rame=orks (e.g., GR5ou'h !ersus plain GJuery) =here pra'ti'al.

,h t 5e tures Do 3ou GetF


As =ith an +5MLA appli'ation, you get the basi' 'apabilities o& a Web bro=ser, in'lu"ing ACAF support. 1eyon" that, #hone8ap a""s a number o& Ca!a%'ript A#0s to allo= you to get at the un"erlying &eatures o& the An"roi" plat&orm. At the time o& this =riting, that in'lu"es,

A''elerometer a''ess, &or "ete'ting mo!ement o& the "e!i'e Au"io re'or"ing Camera a''ess, &or taking still pi'tures @atabase a''ess, both to "atabases o& your 'reation (%JLite) or others built into An"roi" (e.g., 'onta'ts) *ile system a''ess, su'h as to the %@ 'ar" or other e;ternal storage 8eolo'ation, &or "etermining =here the "e!i'e is -ibration, &or shaking the phone (e.g., &or'e-&ee"ba'k)

%in'e some o& these are part o& the +5MLA spe'i&i'ation (e.g., geolo'ation), you ha!e your 'hoi'e o& A#0s. Also, this list 'hanges o!er time, so you may ha!e a''ess to more than =hat is "es'ribe" here.

2%2

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

,h t Do Apps )oo$ )i$eF


5hey =ill look like Web pages, more so than nati!e An"roi" apps. ?ou 'an use C%% an" images to mimi' the An"roi" look an" &eel to some e;tent, but only &or those sorts o& =i"gets that are rea"ily able to be 'reate" in both An"roi" an" +5ML. *or e;ample, the An"roi" 2pinner =i"get S =hi'h resembles a "rop-"o=n list S may be "i&&i'ult to mimi' in +5ML. +ere is a s'reenshot o& the e;ample appli'ation that ships =ith #hone8ap,

"igure *8&1 The example application that comes )ith Phone(ap

Ho# Does Distri=ution ,or$F


@istributing a #hone8ap appli'ation is pretty mu'h i"enti'al to "istributing any other stan"ar" An"roi" appli'ation. A&ter testing, you =ill 'reate a stan"ar" A#D &ile =ith the An"roi" buil" tools, &rom an An"roi" proGe't generate" &or you by #hone8ap. 5his proGe't =ill 'ontain the Ca!a, FML, an" other ne'essary bits to =rap aroun" your +5ML, C%%, an"

2%7

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

Ca!a%'ript to make up your appli'ation. 5hen, you "igitally sign the appli'ation an" uploa" it to the An"roi" Market or any other "istribution me'hanism you =ish to use.

,h t A=out +ther Pl t.ormsF


#hone8ap is not Gust &or An"roi". ?ou 'an 'reate #hone8ap appli'ations &or i#hone, 1la'kberry, some &la!ors o& %ymbian, an" #alm7s Web>%. 0n theory, at least, you 'an 'reate one appli'ation using +5ML, C%%, Ca!a%'ript, an" the #hone8ap Ca!a%'ript A#0s, an" ha!e it run a'ross many "e!i'es. 5here are a 'ouple o& limitations that =ill hamper your progress to that goal, 1. 5he Web bro=sing 'omponent use" by #hone8ap a'ross all those plat&orms is not i"enti'al. E!en multiple plat&orms using WebDit =ill ha!e "i&&erent WebDit releases, base" upon =hat =as a!ailable =hen WebDit =as integrate" into a gi!en "e!i'e7s &irm=are. +en'e, you =ill =ant to test an" ensure your C%%, in parti'ular, =orks as you =oul" e;pe't on as many "e!i'es as possible.

2. 2ot all #hone8ap Ca!a%'ript A#0s are a!ailable on all "e!i'es as yet, "ue to a !ariety o& &a'tors (e.g., not e;pose" in the plat&orm7s nati!e A#0s, la'k o& engineering time to hoist the 'apability into the #hone8ap A#0s). 5here is a table on the #hone8ap =iki that =ill keep you apprise" o& =hat =orks an" =hat "oes not a'ross the "e!i'es. ?ou =ill =ant to restri't your &eature use to mat'h your "esire" plat&orms, or restri't your plat&orms to mat'h your "esire" &eatures.

>sing Phone(ap
2o=, let7s look at more o& the me'hani's &or using #hone8ap. #hone8ap7s installation an" usage, as o& the time o& this =riting, normally reRuires an e;pert in Ca!a-base" An"roi" "e!elopment. ?ou nee" to install a
2%8

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

=hole bun'h o& tools, e"it 'on&iguration &iles by han", an" so &orth. 0& you =ant to "o all o& that, "o'umentation is a!ailable on the #hone8ap site. 0& you are rea"ing this 'hapter, there7s a "e'ent 'han'e that you =oul" rather skip all o& that. +en'e, &or many, the best ans=er is the #hone8apP1uil" ser!i'e, still in pri!ate beta at the time o& this =riting.

Inst ll tion
5he #hone8ap Web site =ill allo= you to "o=nloa" the latest #hone8ap tools as a Q0# ar'hi!e. ?ou 'an unpa'k those =here!er it makes sense &or your "e!elopment ma'hine an" plat&orm. *or An"roi" "e!elopment, that is all o& the #hone8ap-spe'i&i' installation you =ill nee". +o=e!er, you =ill nee" the An"roi" %@D an" relate" tools (e.g., E'lipse, i& you =ish to use E'lipse) &or setting up the proGe't.

Cre tin! nd Inst llin! 3our Pro7ect


A #hone8ap An"roi" proGe't is, at its 'ore, a regular An"roi" proGe't, =hi'h you 'an 'reate &ollo=ing the instru'tions outline" earlier in this book. 5o 'on!ert the stan"ar" generate" M+ello, Worl"M appli'ation into a #hone8ap proGe't, you nee" to "o the &ollo=ing, 1. *rom the Android/ "ire'tory o& =here!er you unQ0#pe" the #hone8ap Q0# &ile, 'opy the #hone8ap CA &ile to the libs/ "ire'tory o& your proGe't. 0& you are using E'lipse, you =ill also nee" to a"" it to your buil" path.

2. Create an assets/EEE/ "ire'tory in your proGe't. 5hen, 'opy o!er the #hone8ap C% &ile &rom the Android/ "ire'tory o& =here!er you unQ0#pe" the #hone8ap Q0# &ile. .. A"Gust the stan"ar" M+ello, Worl"M a'ti!ity to inherit &rom =roidDap instea" o& ActivitF. 5his =ill reRuire you to import com.phonegap.=roidDap.

2%:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

<. 0n your a'ti!ity7s on+reatePQ metho", repla'e set+ontentVieEPQ =ith


super.load3rlP7file:///android asset/EEE/indeG.html7QJ

A. 0n your mani&est, a"" all o& the permissions that #hone8ap reRuests, liste" later in this 'hapter. /. Also in your mani&est, a"" a suitable Lsupports-screensM element base" upon =hat s'reen siKes you are =illing to test an" support. 4. Also in your mani&est, a"" android:config+hanges67orientationW keFboard!idden7 to your LactivitFM element, as =roidDap han"les orientation-relate" 'on&iguration 'hanges At this point, you 'an 'reate an assets/EEE/indeG.html &ile in your proGe't an" start 'reating your #hone8ap appli'ation using +5ML, C%%, an" Ca!as'ript. ?ou =ill nee" to ha!e a re&eren'e to the #hone8ap Ca!as'ript &ile (e.g., Lscript tFpe67teGt/javascript7 charset67utf-,7 src67phonegap.-.*.<.js7 /M). When you =ant to test the appli'ation, you 'an buil" an" install it like any other An"roi" appli'ation (e.g., ant clean install i& you are using the 'omman" line buil" pro'ess). *or somebo"y e;perien'e" in An"roi" %@D "e!elopment, setting this up is not a big 'hallenge.

PhoneG pJBuild
#hone8apP1uil" is a 5ools-as-a-%er!i'e (5aa%) hoste" approa'h to 'reating #hone8ap proGe'ts. 5his =ay, all o& the An"roi" buil" pro'ess is han"le" &or you by #hone8ap-supplie" ser!ers. ?ou Gust &o'us on 'reating your +5ML, C%%, an" Ca!as'ript as you see &it. As note" earlier, #hone8apP1uil" is still in pri!ate beta at the time o& this =riting, though hope&ully it =ill be open to the publi' in the near &uture. When you log into #hone8apP1uil", you are &irst prompte" to 'reate your initial proGe't, by supplying a name an" the Web assets to go into the app,

20<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

"igure *8-1 Creating your first proAect in Phone(apKBuild

?ou =ill be able to a"" ne= proGe'ts later on !ia a 2e= App button, =hi'h gi!es you the same set o& options. ?our 'hoi'es &or the assets are to uploa" a Q0# &ile 'ontaining all o& them, or to spe'i&y the $ L to a publi' 8it+ub repository that #hone8apP1uil" 'an pull &rom. 5he latter ten"s to be more 'on!enient, i& you are use" to using 8it &or !ersion 'ontrol, an" i& your proGe't is open sour'e (an" there&ore has a publi' repository). >n'e you 'li'k the $ploa" button, the #hone8apP1uil" ser!er =ill imme"iately start buil"ing your appli'ation &or An"roi", plus 1la'kberry, %ymbian, an" Web>%,

20*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

"igure *8%1 Building your first proAect in Phone(apKBuild

Ea'h o& the targets has its o=n &ile e;tension (e.g., apk &or An"roi"). Cli'king that link =ill let you "o=nloa" that &ile. >r, 'li'k on the name o& the proGe't, an" you get J 'o"es to enable "o=nloa"s straight to your test "e!i'e,

"igure *801 .our proAectGs IC codes in Phone(apKBuild

20&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

5his page also gi!es you a link to up"ate the app &rom its 8it+ub repo (i& you 'hose that option). >r, 'li'k E"it to spe'i&y more options, su'h as the !ersion o& your appli'ation or its laun'her i'on,

"igure *821 .our proAectGs settings in Phone(apKBuild

All in all, i& you "o not other=ise nee" the An"roi" %@D an" relate" tools on your "e!elopment ma'hine, #hone8apP1uil" 'ertainly simpli&ies the #hone8ap buil"ing pro'ess. 2ote, though, that at the present time, 2itobi (the &irm behin" #hone8ap an" #hone8apP1uil") is planning on #hone8apP1uil" to be a 'ommer'ial ser!i'e &or non-open-sour'e appli'ations, though rates ha!e not yet been announ'e" at this time.

20-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

Phone(ap and the Checklist Sample


5he beauty o& #hone8ap is that it =raps aroun" +5ML, C%%, an" Ca!as'ript. 0n other =or"s, you "o not ha!e to "o mu'h o& anything #hone8ap-spe'i&i' to be able to take a"!antage o& #hone8ap "eli!ering to you an A#D suitable &or installation on an An"roi" "e!i'e. 5hat being sai", #hone8ap "oes e;pose more stu&& to you than you 'an get &rom the stan"ar"s, i& you nee" them an" are =illing to use proprietary #hone8ap A#0s &or them.

Stic$in! to the St nd rds


8i!en an e;isting +5MLA appli'ation, all you nee" to "o to make it be an installable A#D is =rap it in #hone8ap. *or e;ample, to 'on!ert the +5MLA !ersion o& Che'klist into an A#D &ile, you nee" to, 1. *ollo= the steps to 'reate an empty #hone8ap proGe't outline" earlier in this 'hapter

2. Copy the +5ML, C%%, Ca!as'ript, an" images &rom the +5MLA proGe't into the assets/EEE/ "ire'tory o& the #hone8ap proGe't (note that you "o not nee" things uniRue to +5MLA, su'h as the 'a'he mani&est) .. Make sure that your +5ML entry point &ilename mat'hes the path you use" =ith the load3rlPQ 'all in your a'ti!ity (e.g., indeG.html) <. A"" a re&eren'e to the #hone8ap Ca!as'ript &ile &rom your +5ML A. 1uil" an" install the proGe't +ere is the =roidDap a'ti!ity &or our app, &rom the (honeDap/+hecklist proGe't,
package com.commonsEare.pg.checklistJ import android.app.ActivitFJ import android.os.4undleJ

20%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

import com.phonegap.=roidDapJ public class +hecklist eGtends =roidDap : O"verride public void onCreateP4undle savedInstance2tateQ : super.onCreatePsavedInstance2tateQJ super.load*rlP7file:///android asset/EEE/indeG.html7QJ ; ;

+ere is the mani&est, =ith all o& the #hone8ap-reRueste" settings a""e",
LNGml version671.-7 encoding67utf-,7NM Lmanifest Gmlns:android67http://schemas.android.com/apk/res/android7 package67com.commonsEare.pg.checklist7 android:version+ode6717 android:version%ame671.-7M Lapplication android:label67Ostring/app name7 android:icon67OdraEable/cE7M LactivitF android:name67+hecklist7 android:config+hanges67orientationWkeFboard!idden7 android:label67Ostring/app name7M Lintent-filterM Laction android:name67android.intent.action.#AI%7 /M LcategorF android:name67android.intent.categorF.)A3%+!$?7 /M L/intent-filterM L/activitFM L/applicationM Lsupports-screens android:large2creens67true7 android:normal2creens67true7 android:small2creens67true7 android:resiKeable67true7 android:anF=ensitF67true7 /M Luses-permission android:name67android.permission.+A#$?A7 /M Luses-permission android:name67android.permission.VI4?A&$7 /M Luses-permission android:name67android.permission.A++$22 +"A?2$ )"+A&I"%7 /M Luses-permission android:name67android.permission.A++$22 9I%$ )"+A&I"%7 /M Luses-permission android:name67android.permission.A++$22 )"+A&I"% $]&?A +"##A%=27 /M Luses-permission android:name67android.permission.?$A= (!"%$ 2&A&$7 /M Luses-permission android:name67android.permission.I%&$?%$&7 /M Luses-permission android:name67android.permission.?$+$IV$ 2#27 /M Luses-permission android:name67android.permission.?$+"?= A3=I"7 /M Luses-permission android:name67android.permission.#"=I95 A3=I" 2$&&I%D27 /M Luses-permission android:name67android.permission.?$A= +"%&A+&27 /M Luses-permission android:name67android.permission.@?I&$ +"%&A+&27 /M Luses-permission android:name67android.permission.@?I&$ $]&$?%A) 2&"?AD$7 /M Luses-permission android:name67android.permission.A++$22 %$&@"?H 2&A&$7 /M L/manifestM

200

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

An" here is the +5ML S almost i"enti'al to the +5MLA original, remo!ing some +5MLA o&&line stu&& (e.g., i#hone i'ons) an" a""ing in the re&eren'e to #hone8ap7s Ca!as'ript &ile,
LX="+&5($ htmlM Lhtml lang67en7 manifest67checklist.manifest7M LheadM Lmeta http-eUuiv67+ontent-&Fpe7 content67teGt/htmlJ charset6utf-,7 /M LtitleM+hecklistL/titleM Lmeta name67vieEport7 content67Eidth6device-EidthJ initial-scale61.-J maGimum-scale61.-J userscalable6-J7 /M Llink rel67stFlesheet7 href67stFles.css7 /M Lscript tFpe67teGt/javascript7 charset67utf-,7 src67phonegap.-.*.<.js7ML/scriptM L/headM LbodFM LsectionM LheaderM Lbutton tFpe67button7 id67sendmail7M#ailL/buttonM Lh1M+hecklistL/h1M L/headerM LarticleM Lform id67inputarea7 onsubmit67add%eEItemPQ7M Linput tFpe67teGt7 name67name7 id67name7 maGlength67/.7 autocorrect placeholder67&ap to enter a neE itemZhellipJ7 /M Lbutton tFpe67button7 id67add7MAddL/buttonM L/formM Lul id67maillist7M Lli class67emptF7MLa href677 id67maillink7M#ail remaining itemsL/aML/liM L/ulM Lp id67totals7MLspan id67tallF17M&otal: Lspan id67total7M-L/spanML/spanM Lspan id67tallF>7M?emaining: Lspan id67remaining7M-L/spanML/spanML/pM Lul id67checklist7M Lli class67emptF7M)oadingZhellipJL/liM L/ulM L/articleM LfieldsetM Lbutton tFpe67button7 id67deletechecked7M=elete +heckedL/buttonM Lbutton tFpe67button7 id67deleteall7M=elete AllL/buttonM L/fieldsetM L/sectionM Lscript src67main.js7ML/scriptM L/bodFM L/htmlM

202

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

*or many appli'ations, this is all you =ill nee" S you are simply looking at #hone8ap to gi!e you something you 'an "istribute on the An"roi" Market, on the i>% App %tore, an" so on.

Addin! PhoneG p APIs


0& you =ant to take a"!antage o& more "e!i'e 'apabilities, you 'an augment your +5MLA appli'ation to use #hone8ap-spe'i&i' A#0s. 5hese run the gamut &rom telling you the "e!i'e7s mo"el to letting you get 'ompass rea"ings. +en'e, their 'omple;ity =ill !ary. *or the purposes o& this 'hapter, =e =ill look at some o& the simpler ones.

Set up Device*Re dy Event H ndler


*or !arious reasons, #hone8ap =ill not be rea"y to respon" to all o& its A#0s right a=ay =hen your page is loa"e". 0nstea", there is a devicereadF e!ent that you =ill nee" to =at'h &or in or"er to kno= =hen it is sa&e to use #hone8ap-spe'i&i' Ca!as'ript globals. 5he typi'al re'ipe is, 1. A"" an onload attribute to your LbodFM tag, re&eren'ing a global Ca!as'ript &un'tion (e.g., on)oadPQ)

2. 0n on)oadPQ, use add$vent)istenerPQ to register another global Ca!as'ript &un'tion (e.g., on=evice?eadFPQ) &or the devicereadF e!ent .. 0n on=evice?eadFPQ, start using the #hone8ap A#0s

-se ,h t PhoneG p Gives 3ou


#hone8ap makes a number o& metho"s a!ailable to you through a series o& !irtual Ca!as'ript obGe'ts. +ere, M!irtualM means that you 'annot 'he'k to see i& the obGe'ts e;ist, but you 'an 'all metho"s an" rea" properties on them. %o, &or e;ample, there is a device obGe't that has a han"&ul o& use&ul properties, su'h as phonegap to return the #hone8ap !ersion an" version to return the >% !ersion. 5hese !irtual obGe'ts are rea"y &or use in or a&ter the devicereadF e!ent.

207

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

here is a Ca!as'ript &ile (props.js &rom the (honeDap/+hecklist$G proGe't) that implements an on)oadPQ &un'tion (to register &or devicereadF) an" an on=evice?eadFPQ &un'tion (to use the device obGe't7s properties),
// (honeDapIs A(Is are not immediatelF readF8 so set up an // event handler to find out Ehen theF are readF function onLoadPQ : document.add+!entListenerP7devicereadF78 on=evice?eadF8 falseQJ ; // %oE (honeDapIs A(Is are readF function onDe!ice%eadyPQ : var element6document.get+lementByIdPIpropsIQJ element.inner!&#)6ILliM#odel: IRdevice.nameRIL/liMI R ILliM"2 and Version: IRdevice.platform RI IRdevice.versionRIL/liMI R ILliM(honeDap Version: IRdevice.phonegapRIL/liMIJ ;

*or

e;ample,

5he on=evice?eadFPQ &un'tion nee"s a list element =ith an id o& props. 5hat, plus loa"ing this Ca!as'ript in the &irst pla'e, =ill reRuire some minor mo"i&i'ations to our +5ML,
LX="+&5($ htmlM Lhtml lang67en7 manifest67checklist.manifest7M LheadM Lmeta http-eUuiv67+ontent-&Fpe7 content67teGt/htmlJ charset6utf-,7 /M LtitleM+hecklistL/titleM Lmeta name67vieEport7 content67Eidth6device-EidthJ initial-scale61.-J maGimum-scale61.-J userscalable6-J7 /M Llink rel67stFlesheet7 href67stFles.css7 /M Lscript tFpe67teGt/javascript7 charset67utf-,7 src67phonegap.-.*.<.js7ML/scriptM Lscript tFpe67teGt/javascript7 charset67utf-,7 src67props.js7ML/scriptM L/headM LbodF onload67on)oadPQ7M LsectionM LheaderM Lbutton tFpe67button7 id67sendmail7M#ailL/buttonM Lh1M+hecklistL/h1M L/headerM LarticleM Lform id67inputarea7 onsubmit67add%eEItemPQ7M Linput tFpe67teGt7 name67name7 id67name7 maGlength67/.7 autocorrect placeholder67&ap to enter a neE itemZhellipJ7 /M

208

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

Lbutton tFpe67button7 id67add7MAddL/buttonM L/formM Lul id67maillist7M Lli class67emptF7MLa href677 id67maillink7M#ail remaining itemsL/aML/liM L/ulM Lp id67totals7MLspan id67tallF17M&otal: Lspan id67total7M-L/spanML/spanM Lspan id67tallF>7M?emaining: Lspan id67remaining7M-L/spanML/spanML/pM Lul id67checklist7M Lli class67emptF7M)oadingZhellipJL/liM L/ulM L/articleM LfieldsetM Lbutton tFpe67button7 id67deletechecked7M=elete +heckedL/buttonM Lbutton tFpe67button7 id67deleteall7M=elete AllL/buttonM L/fieldsetM LfooterM Lh>M=evice (ropertiesL/h>M Lul id67props7ML/ulM L/footerM L/sectionM Lscript src67main.js7ML/scriptM L/bodFM L/htmlM

5he resulting app looks like,

"igure *871 The Phone(ap Checklist application )ith device properties

20:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

>b!iously, rea"ing a han"&ul o& properties is &ar simpler than, say, taking a pi'ture =ith the "e!i'e7s 'amera. +o=e!er, the "i&&eren'e in 'omple;ity is mostly in =hat #hone8ap7s !irtual Ca!as'ript obGe'ts gi!e you an" ho= you 'an use them, more so than anything pe'uliar to An"roi".

ssues .ou +ay =ncounter


#hone8ap is a &ine 'hoi'e &or 'reating 'ross-plat&orm appli'ations. +o=e!er, it is not =ithout its issues. %ome o& these issues may be resol!e" in timeT some may be en"emi' to the nature o& #hone8ap.

Security
An"roi" appli'ations use a permission system to reRuest a''ess to 'ertain system &eatures, su'h as making 0nternet reRuests or rea"ing the user7s 'onta'ts. Appli'ations must reRuest these permissions at install time, so the user 'an ele't to aban"on the installation i& the reRueste" permissions seem suspe't. A general rule o& thumb is that you shoul" reRuest as &e= permissions as possible, an" make sure that you 'an Gusti&y =hy you are reRuesting the remaining permissions. #hone8ap, &or a ne= proGe't, reRuests Ruite a &e= permissions,
+A#$?A VI4?A&$ A++$22 +"A?2$ )"+A&I"% A++$22 9I%$ )"+A&I"% A++$22 )"+A&I"% $]&?A +"##A%=2 ?$A= (!"%$ 2&A&$ I%&$?%$& ?$+$IV$ 2#2 ?$+"?= A3=I"

22<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

#"=I95 A3=I" 2$&&I%D2 ?$A= +"%&A+&2 @?I&$ +"%&A+&2 @?I&$ $]&$?%A) 2&"?AD$ A++$22 %$&@"?H 2&A&$

Lea!ing this roster inta't =ill gi!e you an appli'ation that 'an use e!ery A#0 #hone8ap makes a!ailable to your Ca!as'ript...an" an appli'ation that =ill s'are a=ay many users. A&ter all, it is unlikely that your appli'ation =ill be able to use, let alone Gusti&y, all o& these permissions. 0t is 'ertainly possible &or you to trim "o=n this list, by mo"i&ying the Android#anifest.Gml &ile in the root o& your #hone8ap proGe't. +o=e!er, you =ill then nee" to thoroughly test your appli'ation to make sure you "i" not get ri" o& a permission that you a'tually nee". Also, it may be un'lear to you =hi'h permissions you 'an sa&ely remo!e. E!entually, the #hone8ap proGe't may ha!e tools to help gui"e you in the 'hoi'e o& permissions, perhaps by stati'ally analyKing your Ca!as'ript 'o"e to see =hi'h #hone8ap A#0s you are using. 0n the meantime, though, getting the proper set o& permissions =ill in!ol!e a lot o& trial an" error.

Screen SiEes nd Densities


2ormal Web appli'ations primarily &o'us on s'reen resolution an" =in"o= siKes as their primary !ariables. +o=e!er, mobile Web appli'ations =ill not ha!e to =orry about =in"o= siKes, as bro=sers an" apps typi'ally run &ulls'reen. Mobile Web appli'ations =ill nee" to "eal =ith physi'al siKe an" "ensity, though S issues that are Mo&& the ra"arM &or tra"itional Web "e!elopment. 2etbooks 'an ha!e s'reens that are 10M or smaller. @esktops 'an ha!e s'reens that are 2<M or larger. >n the sur&a'e, there&ore, physi'al s'reen siKe =oul" seem to be something Web "e!elopers =oul" nee" to a""ress. +o=e!er, generally, s'reen resolution (in pi;els) tra'ks =ell =ith physi'al

22*

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

siKe in the netbookPnotebookP"esktop realm. 5hat is be'ause s'reen "ensity is &airly 'onsistent a'ross their LC@s, an" that "ensity is &airly lo=. %martphones, on the other han", ha!e se!eral "i&&erent "ensities, 'ausing the 'onne'tion bet=een resolution an" siKe to be broken. %ome lo=-en" phones, parti'ularly =ith small (e.g., .M) LC@s, ha!e "ensities on par =ith ni'e monitors. Mi"-range phones ha!e t=i'e the "ensity (2<0"pi !ersus 120"pi). Apple7s i#hone < has e!en higher "ensity, an" one 'an imagine that there =ill soon be some An"roi" "e!i'es =ith so-'alle" Mretina "isplaysM as =ell. +en'e, an 800;<80 resolution 'oul" be on a s'reen ranging any=here &rom <M to 4M, &or e;ample. 5ablets a"" e!en more possible siKes to the mi;. 5his is 'ompoun"e" by the problems 'ause" by tou'hs'reens. A mouse 'an get pi;el-le!el pre'ision in its 'li'ks. *ingers are mu'h less pre'ise. +en'e, you ten" to nee" to make your buttons an" su'h that mu'h bigger on a tou'hs'reen, so it 'an be M&inger-&rien"lyM. 5his 'auses some problems =ith s'aling o& assets, parti'ularly images. What might be M&inger-&rien"lyM on a lo=-"ensity .M "e!i'e might be entirely too small &or a high-"ensity <M "e!i'e. 2ati!e An"roi" appli'ations ha!e built-in logi' &or "ealing =ith this issue, in the &orm o& multiple sets o& Mresour'esM (e.g., images) that 'an be s=appe" in base" upon "e!i'e 'hara'teristi's. E!entually, #hone8ap an" similar tools =ill nee" to pro!i"e rele!ant a"!i'e &or their users &or ho= to 'reate appli'ations that 'an similarly a"apt to 'ir'umstan'es.

)oo$ nd 5eel
A Web app ne!er Ruite looks like a nati!e one. 5his is not ne'essarily a ba" thing. +o=e!er, some users may &in" it "is'on'erting, parti'ularly sin'e they =ill not un"erstan" =hy their ne=ly-installe" app (ma"e =ith #hone8ap, &or e;ample) =oul" ne'essarily look substantially "i&&erent than any other similar app they may alrea"y ha!e.

22&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Phone(ap

As +5MLA appli'ations be'ome more prominent on An"roi", this issue shoul" "e'line in importan'e. +o=e!er, it is something to keep in min" &or the ne;t year or t=o.

"or +ore nformation


At the time o& this =riting, there are no books a!ailable "e"i'ate" to #hone8ap "e!elopment. Also, it is still a &ast-mo!ing target, parti'ularly as it hea"s to -ersion 1.0. +en'e, at the moment, the best in&ormation on #hone8ap 'an be &oun" on the #hone8ap site, in'lu"ing their A#0 "o'umentation.

22-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 29

,ther Alternative =nvironments

5he alternati!e appli'ation en!ironments "es'ribe" in the pre'e"ing 'hapters are but the tip o& the i'eberg. +ere, =e =ill take a look at a &e= other alternati!e appli'ation en!ironments, &rom the gro=ing &loo" o& su'h te'hnologies. 2ote that this area 'hanges rapi"ly, an" so the material in this 'hapter may be some=hat out o& "ate relati!e to the progress ea'h o& these te'hnologies has ma"e.

Chodes
%piritually, ho"es is similar to #hone8ap, in that you "e!elop an An"roi" appli'ation =hose user inter&a'e is "e&ine" !ia +5ML, C%%, an" Ca!as'ript. 5he "i&&eren'e is that ho"es bakes in a &ull uby en!ironment, =ith a ails-esRue &rame=ork. ?our uby 'o"e generates +5ML an" su'h to be Mser!e"M to an a'ti!ity !ia a @ebVieE =i"get, mu'h like a ser!er-si"e uby Web app =oul" generate +5ML to be ser!e" to a stan"alone Web bro=ser. %imilar to #hone8ap, you 'an either buil" the proGe't on your "e!elopment ma'hine or use their hoste" buil" pro'ess. 5he latter is re'ommen"e", partly be'ause the reRuirements &or lo'al buil"s are higher than those &or #hone8ap S notably, ho"es reRuires the 2ati!e @e!elopment Dit (2@D) &or buil"ing an" linking the uby interpreter to your appli'ation.

220
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

,ther Alternative =nvironments

ho"es =in"s up 'reating larger appli'ations than "oes #hone8ap, "ue to the o!erhea" o& the uby interpreter (^1.AM1). +o=e!er, i& you are use" to ser!er-si"e Web "e!elopment, ho"es may be easier &or you to pi'k up than =oul" #hone8ap.

"lash@ "lex@ and A C


A"obe has been har" at =ork e;ten"ing their *lash, *le;, an" A0 te'hnologies to the mobile spa'e. ?ou 'an use *le; (the M+eroM e"ition) an" *lash 1uil"er (the M1urritoM e"ition... begging the Ruestion o& =hether the MheroM is hungry) to 'reate An"roi" A#D &iles that 'an be "istribute" on the An"roi" Market an" "eploye" to An"roi" "e!i'es. 5hose "e!i'es =ill nee" to ha!e the A0 runtime installe" S this is &ree, but a large "o=nloa", an" it only =orks on An"roi" 2.2 "e!i'es. 5he same proGe'ts 'an be repa'kage" &or i>% an" the 1la'kberry #laybook tablet, an" possibly &uture "e!i'es "o=n the roa". A0 "oes not ha!e Ruite as tight o& integration to the plat&orm as "oes #hone8ap (e.g., no a''ess to the "e!i'e7s 'onta'ts), though one imagines that this is an area on =hi'h A"obe =ill "e!ote more resour'es o!er time. An", A"obe is a large &irm, =ith a large e'osystem behin" it an" many e;isting *lash, *le;, an" A0 "e!eloper resour'es to tap into.

6Cuby and Cuboto


>ne o& the most popular languages "esigne" to run on the C-M S besi"es Ca!a itsel& S is C uby. C uby =as Rui'kly porte" to run on An"roi", but =ith some optimiKations "isable", sin'e C uby is really running on the @al!ik !irtual ma'hine that un"erlies the An"roi" en!ironment, not a 'lassi' Ca!a -M. +o=e!er, C uby alone 'annot 'reate An"roi" appli'ations. As a s'ripting language, there is no =ay &or it to "e&ine an a'ti!ity or other 'omponent S those nee" to be registere" in the appli'ation7s mani&est as regular Ca!a 'lass &iles.

222

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

,ther Alternative =nvironments

5his is =here uboto 'omes in. uboto is a &rame=ork &or a generi' C ubyPAn"roi" appli'ation. 0t pro!i"es skeletal a'ti!ities !ia a 'o"e generator an" allo=s C uby s'ripts to "e&ine han"lers &or all o& the li&e'y'le metho"s (e.g., on+reatePQ), plus "e&ine user inter&a'es using C uby 'o"e, et'. 5he result 'an be pa'kage" up as an A#D &ile using supplie" ake s'ript. 5he results 'an be uploa"e" to the An"roi" Market or "istribute" ho=e!er else you "esire.

+ono/roid
Mono is a re-implementation o& CB an" .2E5 &or non-Win"o=s en!ironments. Mono has ha" its &air share o& 'ontro!ersies, mostly stemming &rom Mi'roso&t, su'h as =hether Mi'roso&t =ill some"ay sRuash Mono o!er patent 'onsi"erations. Mono@roi" has been in the =orks &or some time. 5his =oul" allo= Mono "e!elopers to target An"roi" &or their apps. 0n prin'iple, one 'oul" "e!elop CB appli'ations &or An"roi" this =ay. While Mono itsel& is an open sour'e proGe't, MMono@roi" is a 'ommer'ial pro"u't...li'ense" on a per-"e!eloper basisM, a''or"ing to the Mono proGe't. 5his may 'ome as a bit o& a sho'k to those e;pe'ting Mono-on-An"roi" to remain open sour'e. Mono@roi", =hile eagerly anti'ipate", has not been release" as o& the time o& this =riting, beyon" a beta.

App nventor
App 0n!entor is an An"roi" appli'ation "e!elopment tool ma"e a!ailable by 8oogle, but outsi"e o& the normal An"roi" "e!eloper site. App 0n!entor =as originally "e!elope" &or use in e"u'ation, but they ha!e been in!iting others into their 'lose" beta.

227

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

,ther Alternative =nvironments

App 0n!entor is theoreti'ally a Web-base" "e!elopment tool. +ere, Mtheoreti'allyM means that, in pra'ti'e, users ha!e to "o a &air amount o& =ork outsi"e o& the bro=ser to get e!erything set up,

+a!e Ca!a installe" an" &un'tioning in the bro=ser, 'apable o& running Ca!a Web %tart (.Gnlp) appli'ations @o=nloa" an" install a large (^AAM1) 'lient-si"e set o& tools +a!e a phone an" ha!e it 'on&igure" to =ork =ith App 0n!entor an" the An"roi" %@D

>n'e set up, App 0n!entor gi!es you a "rag-an"-"rop 8$0 e"itor,

"igure *881 The App nventor D/esignerD vie)

...an" a Mblo'ksM e"itor, =here you atta'h beha!iors to e!ents (e.g., button 'li'ks) by snapping together !arious Mblo'ksM representing e!ents, metho"s, an" properties,

228

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

,ther Alternative =nvironments

"igure *8:1 The App nventor DBlocksD vie)

While =orking in the 8$0 e"itor, you see =hat you are buil"ing li!e on an atta'he" phone an" 'an be teste" in real time. Later, =hen you are rea"y, you 'an pa'kage the appli'ation into a stan"ar" A#D &ile. +o=e!er, App 0n!entor is not really set up &or pro"u'tion appli'ation use to"ay,

?ou 'annot "istribute App 0n!entor apps on the An"roi" Market 0t has more 'omponents aime" at MsiKKleM (e.g., 5=itter integration) an" &e=er "eli!ering 'apabilities that a typi'al mo"ern app might nee" (e.g., relational "atabases, lists) >nly one "e!eloper at a time 'an =ork on a proGe't

0n the &uture, it is possible that App 0n!entor =ill be'ome a soli" option, or that App 0n!entor =ill trigger other &irms to 'reate similar sorts o& programming-&ree "e!elopment options &or An"roi".

Titanium +obile
5itanium Mobile7s 'laim to &ame is using Ca!as'ript to 'ompletely "e&ine the user inter&a'e, es'he=ing +5ML entirely. ather, their Ca!as'ript library S in a""ition to pro!i"ing a''ess to "atabases an" plat&orm 'apabilities S also
22:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

,ther Alternative =nvironments

lets you "e'lare user inter&a'e =i"gets. 0ts layout 'apabilities, &or positioning sai" =i"gets, lea!es a bit to be "esire". As o& the time o& this =riting, App'elerator S the 'reators o& 5itanium Mobile S "oes not o&&er a 'lou"-base" set o& tools. 5heir 5itanium tool has a !ery sli'k-looking $0, but it still reRuires the Ca!a %@D an" An"roi" %@D in or"er to be able to buil" An"roi" appli'ations, making the setup a bit "aunting &or some. As o& the time o& this =riting, 5itanium Mobile supports "e!elopment &or An"roi" an" i>%, =ith 1la'kberry support in a pri!ate beta.

,ther 6;+ Compiled !anguages


0& your issue is less =ith regular An"roi" "e!elopment, but you Gust "o not like Ca!a, any language that 'an generate 'ompatible C-M byte'o"e shoul" =ork =ith An"roi". ?ou =oul" ha!e to mo"i&y the buil" 'hain &or that other language to "o the rest o& the An"roi" buil" pro'ess (e.g., generate ?.java &rom the resour'es, 'reate the A#D &ile in the en"). %'ala an" CloGure are t=o su'h languages, &or =hi'h their respe'ti!e 'ommunities ha!e put together instru'tions &or using their languages &or An"roi" "e!elopment.

27<

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

PART VIII T"e #ver$#volvin% Android

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 2:

/ealing With /evices

An"roi" is M&ree as in beerM &or "e!i'e manu&a'turers, as it is an open sour'e proGe't. +en'e, "e!i'e manu&a'turers ha!e carte blanche to "o =hat they =ant =ith An"roi" as they put it on their "e!i'es. 5his means a brea"th o& 'hoi'es &or "e!i'e users, =ho =ill be able to ha!e An"roi" "e!i'es in all shapes, siKes, an" 'olors. 5his also means "e!elopers =ill ha!e some "e!i'e "i&&eren'es an" i"iosyn'rasies to take into a''ount. 5his 'hapter =ill gi!e you some tips an" a"!i'e &or "ealing =ith these "e!i'e-spe'i&i' issues, to go along =ith the s'reen siKe material &rom the pre!ious 'hapter.

This App Contains =xplicit111 nstructions


>riginally, the only An"roi" "e!i'e =as the 5-Mobile 81. +en'e, i& you =ere =riting an An"roi" appli'ation, you 'oul" assume the e;isten'e o& a har"=are JWE 5? keyboar", a tra'kball &or na!igation, an" so on. 2o=, though, o!er one hun"re" other "e!i'es e;ist, many =ith "i&&erent har"=are 'apabilities (e.g., no keyboar"). 0"eally, your appli'ation 'an =ork regar"less o& the e;isten'e o& !arious types o& har"=are. %ome appli'ations, though, =ill be unusable =ithout 'ertain har"=are 'hara'teristi's. *or e;ample, a &ull-s'reen game may rely upon a har"=are keyboar" or tra'kball to in"i'ate player a'tions S so&t keyboar"s an" tou'hs'reens may be insu&&i'ient.
27Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing With /evices

*ortunately, starting =ith An"roi" 1.A, you 'an no= a"" e;pli'it instru'tions, telling An"roi" =hat you nee", so your appli'ation is not installe" on "e!i'es la'king su'h har"=are. 0n a""ition to using the target 0@ system to in"i'ate =hat le!el o& "e!i'e your proGe't is targeting, you 'an use a ne= Android#anifest.Gml element to spe'i&y har"=are that is reRuire" &or your appli'ation to run properly. ?ou 'an a"" one or more Luses-configurationM elements insi"e the LmanifestM element. Ea'h Luses-configurationM element spe'i&ies one !ali" 'on&iguration o& har"=are that your appli'ation =ill =ork =ith. At the present time, there are &i!e possible har"=are reRuirements you 'an spe'i&y this =ay,

to in"i'ate you nee" a A-=ay na!igation pointing "e!i'e o& some &orm (e.g, android:reU9ive@aF%av 6 7true7)
android:reU9ive@aF%av android:reU%avigation

to restri't the A-=ay na!igation pointing "e!i'e to a spe'i&i' type (e.g, android:reU%avigation 6 7trackball7)
android:reU!ardHeFboard to spe'i&y i& a har"=are (physi'al) is reRuire" (e.g, android:reU!ardHeFboard 6 7true7) android:reUHeFboard&Fpe, android:reU!ardHeFboard,

keyboar"

probably use" in 'onGun'tion =ith to in"i'ate a spe'i&i' type o& har"=are keyboar" that is reRuire" (e.g, android:reUHeFboard&Fpe 6 7UEertF7)
android:reU&ouch2creen to in"i'ate =hat type o& tou'hs'reen reRuire", i& any (e.g, android:reU&ouch2creen 6 7finger7)

is

%tarting in An"roi" 1./, there is a similar mani&est element, Luses-featureM, =hi'h is "esigne" to "o'ument reRuirements an appli'ation has o& other optional &eatures on An"roi" "e!i'es. *or e;ample, the &ollo=ing attributes 'an be pla'e" in a Luses-featureM element,
android:gl$sVersion in"i'ates that your appli'ation reRuires >pen8L, =here the !alue o& the attribute in"i'ates =hat le!el o& >pen8L support (e.g., -G---1---> &or >pen8L 1.2 or higher) android:name 6 7android.hardEare.camera7

in"i'ates that your


android:name 6

appli'ation

nee"s

'amera,

=hile

27%

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing With /evices

in"i'ates that your appli'ation spe'i&i'ally nee"s an auto-&o'us 'amera


7android.hardEare.camera.autofocus7

Ea'h An"roi" release a""s more an" more &eatures you 'an reRuire. 5hese reRuests =ill 'ause the An"roi" Market S an" other thir"-party markets, one hopes S to &ilter your appli'ation out &rom "e!i'es &or =hi'h it is unsuitable. 5he Luses-featureM element has an android:reUuired attribute that you 'an spe'i&y. 1y "e&ault, it is set to true, meaning you absolutely nee" this &eature. 0& you set it to false, you are a"!ertising that you 'an take a"!antage o& the &eature i& it e;ists, but you "o not absolutely nee" it. 5o &in" out at runtime =hether the &eature is there, you 'an use the has2Fstem9eaturePQ metho" on (ackage#anager to interrogate the "e!i'e to see i& =hat you =ant is a!ailable.

Implied 5e ture ReIuests


0& you ha!e reRueste" permissions like +A)) (!"%$ or 2$%= 2#2, unless you take the proper steps, your appli'ation =ill not be a!ailable &or the Motorola F>>M, an" presumably &or other An"roi" ..0-base" tablets. %ome permissions imply that you nee" 'ertain har"=are &eatures S s'roll "o=n to the 6#ermissions that 0mply *eature eRuirements9 se'tion on the linke"-to page to &in" the list. 5he An"roi" Market treats as though reRuesting a permission like +A)) (!"%$ also reRuests,
Luses-feature ndroid:name67android.hardEare.telephonF7 /M

5he F>>M "oes not ha!e telephony Z the &irst An"roi" Market-'ompliant "e!i'e =ith that limitation. While it 'an ha!e a "ata plan, it has no !oi'e or %M% 'apability, an" so it is treate" as not ha!ing android.hardEare.telephonF. 1ut, i& you reRuest permissions like +A)) (!"%$, the An"roi" Market by "e&ault =ill assume you need

270

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing With /evices

android.hardEare.telephonF.

As a result, you =ill be &iltere" out o& the

Market &or the F>>M. 5he solution is simple, &or any har"=are &eatures that might be implie" by permissions but that you "o not absolutely nee", manually a"" the appropriate Luses-featureM element to your mani&est =ith android:reUuired67false7,
Luses-feature android:name67android.hardEare.telephonF7 android:reUuired67false7 /M

5hen, be&ore you try pla'ing a phone 'all or sen"ing an %M% or something, use (ackage#anager an" get2FstemAvailable9eaturesPQ to &in" out i& android.hardEare.telephonF is in"ee" a!ailable on the "e!i'e. *or e;ample, you might 'he'k &or telephony early on an" "isable !arious menu 'hoi'es S buttons that might lea" to the user to pla'e a 'all or sen" an %M%. 2o=, i& your appli'ation absolutely nee"s telephony, then the implie" Luses-featureM =ill =ork, though you may =ish to 'onsi"er putting one in e;pli'itly. +o=e!er, Gust bear in min" that this means your app =ill not =ork on the F>>M or other tablets that la'k telephony.

A (uaranteed +arket
As mentione" in the intro"u'tion to the 'hapter, An"roi" is open sour'e. %pe'i&i'ally, it is mostly a!ailable un"er the Apa'he %o&t=are Li'ense 2.0. 5his li'ense pla'es &e= restri'tions on "e!i'e manu&a'turers. 5here&ore, it is !ery possible &or a "e!i'e manu&a'turer to 'reate a "e!i'e that, &rankly, "oes not run An"roi" !ery =ell. 0t might =ork &ine &or stan"ar" appli'ations shippe" on the "e!i'e but "o a poor Gob o& han"ling thir"-party appli'ations, like the ones you might =rite. 5o help a""ress this, 8oogle has some appli'ations, su'h as the An"roi" Market, that it has not release" as open sour'e. While these appli'ations are a!ailable to "e!i'e manu&a'turers, the "e!i'es that run the An"roi"
272

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing With /evices

Market are teste" &irst, to help ensure that a user7s e;perien'e =ith the "e!i'e =ill be reasonable. A 8oogle engineer 'ite" one 'ase =here a "e!i'e manu&a'turer =as rea"ying a phone that ha" a J-8A s'reen, be&ore the release o& An"roi" 1./ =here J-8A support =as o&&i'ially a""e" to the plat&orm. While that manu&a'turer ha" arrange" &or the built-in appli'ations to =ork a''eptably on the smaller-resolution s'reen, thir" party appli'ations =ere a mess. 8oogle apparently "e'line" to pro!i"e the An"roi" Market to the manu&a'turer &or this "e!i'e. +en'e, the e;isten'e o& the An"roi" Market on a "e!i'e, beyon" pro!i"ing a "istribution means &or your appli'ations, also ser!es as a bit o& a Mseal o& appro!alM that the "e!i'e shoul" support =ell-=ritten thir"-party appli'ations. %pe'i&i'ally, any "e!i'e that has the An"roi" Market,

Will meet the 'riteria outline" in the Compatibility @e&inition @o'ument (C@@) Will ha!e passe" the Compatibility 5est %uite (C5%)

,ther Stuff That ;aries


5here are other things that are kno=n to !ary &rom "e!i'e to "e!i'e, su'h as,

What lo'ation te'hnologies are a!ailable (8#%H Cell to=er pro;imityH 8alileoH) What 'amera &eatures are a!ailable (&lashH auto-&o'usH sepia toneH) What sensors are a!ailable (a''elerometerH gyros'opeH barometerH)

5he strategy &or these is to interrogate the system to &in" out =hat the possibilities are, then "e'i"e =hi'h to use, =here the "e'ision 'oul" be ma"e solely by you or =ith user input. *or e;ample, you 'an use +riteria to "etermine =hi'h is the best lo'ation pro!i"er to use =ith )ocation#anager.

277

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing With /evices

Bugs@ Bugs@ Bugs


$n&ortunately, "e!i'es ine!itably ha!e bugs. %ome bugs are truly a''i"ental. %ome are si"e-e&&e'ts &rom 'hanges the "e!i'e manu&a'turer ma"e to a'hie!e some business aims. %ome are a'tually intentional, though the engineers =ho implemente" them may not ha!e &ully un"erstoo" their rami&i'ations. $n&ortunately, there is not mu'h one 'an "o ta'ti'ally about these bugs, beyon" try to =ork aroun" them. 5he 4uild 'lass, in the android.os pa'kage, 'an tell you the make an" mo"el o& the "e!i'e that is running your app. 5hat, plus your o=n har"-=on e;perien'e =ith 'ertain problems, =ill help you i"enti&y =here you nee" to route aroun" &irm=are "amage. %trategi'ally, i& you &in" something that is 'learly a "e!i'e bug, &ile an issue to ha!e this bug "ete'te" !ia the Compatibility 5est %uite (C5%). 5he C5% is suppose" to &ilter out "e!i'es that 'annot &aith&ully run An"roi" appli'ations. +o=e!er, the C5% has many holes, an" "e!i'e bugs slip through. 1y impro!ing the C5%, =e 'an help pre!ent this sort o& problem &rom 'ropping up in the &uture. ?ou 'an &ile this issue out on the An"roi" publi' issue tra'ker.

/evice Testing
0"eally, you try to test your apps on a !ariety o& har"=are. 5his 'an get e;pensi!e. +ere are some options &or trying to "o it more 'heaply,

%ign up &or @e!i'eAny=here7s in"epen"ent "e!eloper plan, =hi'h is a lo=er-'ost =ay o& being able to a''ess their "e!i'e &arm &or testing &rom remote %ome "e!i'e manu&a'turers hol" M"e!i'e labsM at !arious e!ents, su'h as Motorola hel" at An@e!Con 2011 %ome 'arriers ha!e perpetual "e!i'e labs, su'h as >range7s M"e!eloper 'entresM

278

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

/ealing With /evices

?ou may be able to arrange short-term (e.g., 1A minute) "e!i'e s=aps as part o& a Meetup or 8oogle 5e'hnology $ser 8roup =ith &ello= An"roi" "e!elopers

27:

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

CHAPTER 2;

Where /o We (o "rom 3ereF

>b!iously, this book "oes not 'o!er e!erything. An" =hile your B1 resour'e (besi"es the book) is going to be the An"roi" %@D "o'umentation, you are likely to nee" in&ormation beyon" =hat7s 'o!ere" in either o& those pla'es. %ear'hing online &or Man"roi"M an" a 'lass name is a goo" =ay to turn up tutorials that re&eren'e a gi!en An"roi" 'lass. +o=e!er, bear in min" that tutorials =ritten be&ore late August 2008 are probably =ritten &or the MA %@D an", as su'h, =ill reRuire 'onsi"erable a"Gustment to =ork properly in 'urrent %@Ds. 1eyon" ran"omly hunting aroun" &or tutorials, though, this 'hapter outlines some other resour'es to keep in min".

Iuestions1 Sometimes@ With Ans)ers1


5he Mo&&i'ialM pla'es to get assistan'e =ith An"roi" are the An"roi" 8oogle 8roups. With respe't to the %@D, there are three to 'onsi"er &ollo=ing,

%ta'k>!er&lo=7s an"roi" tag an"roi"-"e!elopers, &or %@D Ruestions an" ans=ers an"roi"-"is'uss, "esigne" &or &ree-&orm "is'ussion o& anything An"roi"-relate", not ne'essarily &or programming Ruestions an" ans=ers

28*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Where /o We (o "rom 3ereF

?ou might also 'onsi"er,


5he An"roi" tutorials an" programming &orums o!er at an""e!.org 5he An"Mob =iki 5he Sandroid-dev 0 C 'hannel on &reeno"e (ir'.&reeno"e.net) 5he An"roi" boar" on Ca!a an'h

0t is important, parti'ularly &or %ta'k>!er&lo= an" the 8oogle 8roups, to =rite =ell-=ritten Ruestions,

0n'lu"e rele!ant portions o& the sour'e 'o"e (e.g., the metho" in =hi'h you are getting an e;'eption) 5he sta'k tra'e &rom LogCat, i& the problem is an unhan"le" e;'eption >n %ta'k>!er&lo=, make sure your sour'e 'o"e an" sta'k tra'e are &ormatte" as sour'e 'o"eT on 8oogle 8roups, 'onsi"er posting long listings on gist.github.'om or a similar sort o& 'o"e-paste site E;plain thoroughly =hat you are trying to "o, ho= you are trying to "o it, an" =hy you are "oing it this =ay (i& you think your goal or approa'h may be a little o&&beat) >n %ta'k>!er&lo=, respon" to ans=ers an" 'omments =ith your o=n 'omments, a""ressing the person using the I synta; (e.g., ICommonsWare), to ma;imiKe the o""s you =ill get a reply >n the 8oogle 8roups, "o not MpingM or reply to your o=n message to try to eli'it a response until a reasonable amount o& time has gone by (e.g., 2< hours)

3eading to the Source


5he sour'e 'o"e to An"roi" is no= a!ailable. Mostly this is &or people looking to enhan'e, impro!e, or other=ise &uss =ith the insi"es o& the An"roi" operating system. 1ut, it is possible that you =ill &in" the ans=ers you seek in that 'o"e, parti'ularly i& you =ant to see ho= some built-in An"roi" 'omponent M"oes it7s thingM.

28&

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Where /o We (o "rom 3ereF

5he sour'e 'o"e an" relate" resour'es http,PPsour'e.an"roi".'om. +ere, you 'an,

'an

be

&oun"

at

@o=nloa" or bro=se the sour'e 'o"e *ile bug reports against the operating system itsel& %ubmit pat'hes an" learn about the pro'ess &or ho= su'h pat'hes get e!aluate" an" appro!e" Coin a separate set o& 8oogle 8roups &or An"roi" plat&orm "e!elopment

ather than "o=nloa" the multi-gigabyte An"roi" sour'e 'o"e snapshot, you may =ish to use 8oogle Co"e %ear'h instea". Cust a"" the android:package 'onstraint to your sear'h Ruery, an" it =ill only sear'h in An"roi" an" relate" proGe'ts.

(etting .our ?e)s "ix


E" 1urnette, a ni'e guy =ho happene" to =rite his o=n An"roi" book, is also the manager o& #lanet An"roi", a &ee" aggregator &or a number o& An"roi"-relate" blogs. %ubs'ribing to the planet7s &ee" =ill let you monitor Ruite a bit o& An"roi"-relate" blog posts, though not e;'lusi!ely relate" to programming. 5o try to &o'us more on programming-relate" An"roi"-re&eren'ing blog posts, you 'an sear'h @Qone &or Man"roi"M an" subs'ribe to a &ee" base" o&& that sear'h.

28-

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

Subscribe to updates at http://commonsware.com

Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

Class...............................................
AbsoluteLayout........................................134, ..0 A'tionE!ent......................................................./4 A'tionListener.................................................../4 A'ti!ity......8, 81, 1.., 1A8, 181, 22A, 22/, 2.2, 2<4, 2/0, 2/2, 241, 242, 24<, 282, 28., 232, ..A, .81, <14, <.1, <.2, <A0, <A8, A0<, A.., A.<, A</, A42, /<4 A"apter........................................1.., 1A2, 1A<, <A1 A"apter-ie=............................................1A<, </A A"apter-ie=.A"apterConte;tMenu0n&o........218 A""%trings5ask...............................................2/3 A""%tring5ask.........................................2/4, 2/3 Alert@ialog.........................21/, 22/-228, .41, .4A AnalogClo'k.............................................14/, 18/ an"roi".te;t.%panne"......................................00 An"roi"+ttpClient.........................<84, <88, A00 Appli'ation......................................................A03 ArrayA"apter...1.2-1./, 1<., 1A.-1A/, 1/1, 1/., 1/<, 1/4, 21A, 214, 218, 2/4, 2/8, .4<, <1/, <// ArrayList.....................................21A, <1/, A2., A2A AssetManager..................................................A3/

Asyn'5ask. .2/2-2/A, 2/4-241, 24A, <2., <2A, <23, </4, A2., A28 AutoComplete5e;t-ie=..............8A, 1<A, 1<4, 138 1asi' esponse+an"ler....................................A1/ 1in"er.......................................A08, A03, A22, A2A 1o;.....................................................................3. 1o;Layout..........................................................3. 1roa"'ast e'ei!er....................282, 28., A10, A/A 1uil"................................................................/4/ 1uil"er..............................................22/, 224, <2< 1un"le.......2.., 2.A, 2.8, 2<A, 2<4, 243, 288, .8., .3/, <A0 1utton...41, 4.-4/, 80-82, 30, 34, 102, 10., 110, 111, 188, 183, 131, 132, 13<, 228, 2.A, .01, .21, .22, ..1, .44, <00, <0A 1yteArray esponse+an"ler............................A1/ Calen"ar...........................................................14< Che'k1o;...............................................8A, 88, 31 Che'k1o;#re&eren'e.......................................<.< Che'ke"5e;t-ie=............................................134 Chronometer.............................................144, 134 Class.................................................................<0A

280
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

Color%tateList..............................................31, 32 Compoun"1utton.............................................88 Con&iguration...........................................2A0, ..A Constants1ro=ser..................................</0, <// Conta'ts.#eople..............................................<0/ Conta'tsContra't............................................<0A Conta'tsContra't.Conta'ts............................<0/ ContentManager.............................................A.8 Content-alues.........................................</2, </. Conte;t1.2, 22/, 241, <14, <22, <.1, <.2, <A8, <30, A03, A2. Conte;tMenu............................................212, 222

@ialog#re&eren'e.............................................<A1 @igitalClo'k.....................................................14/ @isplayMetri's.................................................../ @o'ument........................................................<1/ @ouble.............................................................284 @o=nloa"@emo..............................................<31 @o=nloa"er.......................................A1<, A14, A20 @o=nloa"Manager..................<88-<31, <3., A00 @o=nloa"Manager.Juery..............................<3. @o=nloa"Manager. eRuest...................<31, <32 @ra=able....................1<3, 182, 2<A, .0<, A.3, A44 @ra=er@emo....................................................134

Conte;tMenu.Conte;tMenu0n&o....................212 @roi"8ap........................................./<4, /<8, /A2 Countries*ragment...................8., .88, .30-.3< @ynami'@emo..........................................1A/, 1A4 Country.....................................................8/, .3A E"it#re&eren'es.......................................<.<, <A2 CountryA"apter........................................8., .8/ E"it#re&eren'es+C..................................<A2, <A. CountryListener................................32, .3<, .3A CountryWrapper..............................................8< Criteria.....................................................A/., /4A Cursor..............................<2<, </<, </A, </4, <3. CursorA"apter........................................</A, <// CW1ro=ser......................................................23. @atabase+elper.......................................<A8, </1 @ate*ormat......................................................14< @ate#i'ker.........................................................141 @ate#i'ker@ialog......................................141, 14< @e&ault+ttpClient............<82, <84, A1/, A2A, A28 @etailsA'ti!ity..........................................30, .3A @etails*ragment .81, .82, .88, .30, .31, .3<, .3A @ialog*ragment...............................................88 E"it5e;t.....8., 108, 113, 120, 122, 12A-124, 123, 1<A, 141, 2.A, 2.3, .14, .42-.4<, .44, <08 E"it5e;t#re&eren'e..........................................<<. En!ironment....................................<22, <2., <32 E$<?ou...............................<0, .<2, .A., .30-.3A E;'eption.........................................<0A, A28, A34 E;pan"ableList-ie=........................................134 *ake#layer.........................................A21, A</, A<4 *an'yListsP-ie=+ol"er...................................1/2 *et'h*ore'ast5ask...................................A28, A/A *iel"@emo........................................................113 *ile....................................................<21, <22, <32 *ile>utput%tream...................................<28, <23 *lo=Layout........................................................3<

282
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

*ont%ampler....................................................A3/ *ore'ast.....................................<8A, A2.-A2A, A28 *ragment.............................43, .81-.8., .88, A8. *ragmentA'ti!ity.............................83, .3/, A82 *ragmentManager............................83, .31, .3< *ragment5ransa'tion........................43, .83, .31 *rameLayout.......................180, 181, 188, 13<, A8. 8allery.................................................1.1, 1<3, 134 8eo#oint..........................................................A4A 8ra"ient@ra=able.............................................2 8ri"-ie=.............................................1<1, 1<2, 1<3 +an"ler.........2.<, 2A8-2/2, 240, 24/, A11, A12, A18 +an">&Car"sLayout..........................................1 +elpA'ti!ity....................................................284 +oney'omb+elper.........................................<03 +oriKontal%'roll-ie=.......................................118 +ttpClient.......................<82, <8<, <8/, <84, A00 +ttpConte;t....................................................<84 +ttp8et....................................<82, <8<, A1/, A28 +ttp#ost..........................................................<82 +ttp eRuest....................................................<82 +ttp esponse..................................................<82 +ttp$rlConne'tion........................................A00 0'oni'A"apter............................................1A<, 1AA 0mage1utton.................................81, 82, .0<, ..3 0mage%=it'her.................................................138 0mage-ie=. 81, 82, 1AA, 1A8, 1/1, 1/2, 1/<, 13<, .0< 0ME@emo1........................................................124 0ME@emo2.......................................................124 0n&lation@emo................................................../3

0nputMetho"Manager.............................128, .4A 0nput%tream...............................<1., <1/, <14, <8A 0nput%tream ea"er.........................................<14 0nteger..............................................................1/4 0ntent.....<, 143, 20<, 2<0, 2<1, 243, 281, 28., 284, 231-23., .3A, <0A, <A1, A00, A0/-A08, A10, A11, A1/-A18, A20, A22, A.3, A//, A/4, A88, A31 0ntent%er!i'e...............A0<, A1<, A1/, A14, A13, A20 0nterpreter.......................................................<4< 0temiKe">!erlay...............................A4/-A48, A8. C1utton........................................................./4, /8 CChe'k1o;.........................................................1.2 CCombo1o;.......................................................1.4 CLabel................................................................1.2 CList...................................................................1.2 C5abbe"#ane....................................................180 C5able................................................................1.2 Layout0n&later............................1A4, 1A8, 18/, .8. LinearLayout....3.-38, 100, 102, 10., 103, 11., 1A2, 1A8, 1/4, 181, 13<, 2<8, 2A0, .2., .4<, .44, .32 List.............................................................21., A/. ListA'ti!ity. . .1..-1.A, 181, 214, 2/A, .<0, .8., .83, .34, A42 ListA"apter........................................1/1, 134, .8. ListCell en"erer..............................................1.2 List*ragment.....................43, .8., .8/, .83, <0A List#re&eren'e.................................................<<. List-ie=.....118, 123, 1.., 1.A-1.8, 1<3, 1A1-1A<, 1A/, 1A3, 1/1, 1/., 1/<, 21., 21A, 218, ..3-.<1, .48, .8., .8/, </A, <//, <8., A42 Lo'ation.....................<8., A2., A2A, A23, A/.-A/A Lo'ationListener.....................................A/<, A/A Lo'ationManager.....................A/2-A/<, A//, /4A

287
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

Lo'ation#ro!i"er.............................A/2-A/<, /03 Map...........................................................<.1, </2 MapA'ti!ity.......................A/3, A42-A4<, A82-A8< MapController.........................................A4<, A4A Map*ragment..........................................A8., A8< Map-ie=. .<88, A/3, A41, A42, A4<, A4/, A43, A80, A82-A8A Me"ia#layer.....................................................A20

>n5imeChange"Listener................................142 >n5ime%etListener..................................142, 14< >utput%tream..................................................<14 >utput%treamWriter.......................................<14 >!erlay.....................................................A4/, A48 >!erlay0tem.............................................A4/-A43 #a'kageManager...................................../4., /4< #ar'elable..........................................................A11

Menu...........................................210, 211, 220-222 #en"ing0ntent....A11, A.3, A<2, A<3, AA0, A/A, A// Menu0n&later.............................................221, 222 #layer%er!i'e..............................A13-A21, A</, A<4 Menu0tem..............211, 212, 21/, 218, 220, 221, .4. #layingCar"Layout.............................................1 Message.......................2A8, 2A3, 2/1, 2/2, A11, A14 #re&eren'e.................................................<.<, <A1 Messenger....................................A11, A1<, A14, A18 MultiAutoComplete5e;t-ie=.........................138 MyLo'ation>!erlay.................................A4., A43 2oo?a=k.............A4., A4/, A44, A43-A81, A8<, A8A 2otAll5hat%tri't.....................................<2/, <28 2oti&i'ation........2.2, A.8-A<0, A<2, A<A-A<8, AA0 2oti&i'ationManager.......................A.8, A<., A</ 2oti&y@emo.....................................................A<0 2oti&yMessage.................................................A<2 2o=..............................................................4A, 4/ 2o= e"u;.........................................................4A >bGe't..............................................................2<A >nChe'ke"ChangeListener................8A, 8/, 100 >nCli'kListener................................../4, /8, 228 >n@ateChange"Listener.................................142 >n@ate%etListener...................................142, 14< >nE"itorA'tionListener..................4<, .4A, <08 >n0tem%ele'te"Listener.................................1.3 #re&eren'eA'ti!ity...88, <.2, <.., <.4, <<0, <</<<3, <A2, <A. #re&eren'eCategory................................<.3, <<0 #re&eren'e*ragment.........................88, <<8-<A0 #re&eren'eManager.........................................<.2 #re&eren'e%'reen.....<.<, <.3, <<0, <</, <<4, <A1 #rogress1ar. .141, 2A4, 2A3-2/1, 2/A, 2/3-241, 24A, 24/, .13, .2<-.2/, <3A #rogress@ialog.................................................2A4 Jui'kConta't1a"ge........................................138 a"io1utton...............88, 30, 31, 3., 38, 100, .8/ a"io8roup...............................88, 30, 3., 38-101 an"omA''ess*ile..........................................<28 atingA"apter..................................................1/4 ating1ar....................................1/<, 1/4, 1/8, 143 elati!eLayout 3., 10<, 10A, 104-110, 11<, 13<, ..0, ..1, .44 emote>bGe'tE;'eption.................................A14 esour'es...........................................0A, <1., <A0

288
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

esponse+an"ler.............................................A1/ ingtone#re&eren'e........................................<.< otationAsyn'..................................242, 24<, 24A otationA=are5ask..........................242, 24<, 24A o=Mo"el........................................................1/4

%tri't*or ealK..........................................<2/-<28 %tri'tMo"e........................................<2.-<24, A00 %tri'tWrapper..........................................<2/-<28 %tring. .1/4, 21A, 22/, 224, 2/4, 288, .00, .02, <.1, <A0, <82, A1/, A.. %ystem.%ettings..................................................2

unnable..................................2A8, 2/2, 2/<, 2/A 5abA'ti!ity..................................181, 182, 231, 23. %'roll-ie=...............................3., 11A-118, 124, 128 5ab+ost..............180-18., 23., 23<, ..3, .<0, .80 %e'urityE;'eption............................................AA. 5ab+ost.5abContent*a'tory...................18<, 18/ %eek1ar.............................................................148 5ab+ost.5ab%pe'.............................................18/ %ensorManager................................................<AA 5ableLayout..............3., 111-11<, 122, 124, .48, <.4 %er!i'e...............................A0<, A0A, A13, A20, A</ 5able o=......................................................111-11. %er!i'eConne'tion...................A08, A03, A2<, A.2 5ab%pe'.....................................................182, 18. %hare"#re&eren'es...................<28, <.2, <.., <<. 5ab-ie=.....................................................131, 232 %impleCursorA"apter.....................................</A 5abWi"get....................180, 181, 18<, 188, 131, ./. %imple#re&s@emo....................................<.A, <.4 5elephonyManager.........................................A88 %ites>!erlay.............................................A4/-A48 5e;t%=it'her....................................................138 %li"ing@ra=er............................................13.-134 %o&t e&eren'e...................................................A10 %panne"............................................................00 %pinner 1.4, 1.8, 1<A, 1<3, 1A<, ./., ./8, .80, /<0, /<A %JLite@atabase...............................<A8, </0-</2 %JLite@atabase.Cursor*a'tory......................</4 %JLite>pen+elper.................................<A8, </0 %JLiteJuery1uil"er.......................................</. %ta'k>!er&lo=E;'eption................................<00 %tate..........................................................A.2-A.< %tati'.................................................................0/ %tati'@emo.......................................................1AA %to'k#re&eren'e*ragment.......................<<3-<A1 5e;t-ie=......4<, 43-81, 8., 8A, 88, 31, 32, 34, 108, 12/, 1.., 1A., 1AA, 1A8, 1/2, 1/<, 1/4, 14<, 183-131, 134, 203, 2AA, 240, 241, .1/, .42, A3/, A38 5e;tWat'her..............................................1<A, 1<4 5hrea"..............................................................2A/ 5ime#i'ker.................................................141, 142 5ime#i'ker@ialog...............................141, 142, 14< 5oast22A, 22/, 228, 2/3, ./3, <4/, <8<, <3/, <34, A00, A18, A43 5oggle1utton...................................................138 toolsP..................................................................1/ 5ype&a'e...........................................................A3/ $ri......2<0, 2<1, 2<., 2<4, 248, 243, 281, 28A, 284, 283, 232, <0A, <0/, <32, A.8, A88 -eri&yError.......................................<0<, <08, <24

28:
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

-ie=. . .41, 4A, 81, 30, 11., 114, 1.3, 1A1, 1A<-1A3, 1/11/., 1/8, 18<, 18/, 188, 212, 218, 213, 22/, 2/2, 232, .81, .82, <04-<03, <//, /0. -ie=.>nCli'kListener.......................................81 -ie=Animator.................................................183 -ie=*lipper..........................188, 183, 131-13., 138 -ie=8roup........................................................48 -ie=+ol"er.................................1/2-1/<, 1/4, 1/8 -ie=+ol"er@emo............................................1/. -ie=%=it'her...................................................138 -oi"..........................................................2/4-2/3 Weak e&eren'e................................................A10 Weather1in"er.........................A2<, A2A, A28, A23 Weather@emo.................................<8<, A23, A.A WeatherListener..............................A2<, A2A, A28 Weather%er!i'e........................................A2<, A28 WebDit.....................................................<8., <8< Web%ettings....................................................20/ Web-ie=.....133-20/, 232, .A1, .A., .48, .43, .81, .82, .88-.31, <88, A23, A.., A.<, AA2, //. Web-ie=Client.......................................20<, 20A Web-ie=*ragment..........................................88 Fml#ull#arser...........................................0A, .04

a"b shell...........................................</8, /08, /1/ a"b start-ser!er................................................/1/ an"roi"..........................................................3, A< an"roi" 'reate proGe't...................4, .8, 280, .01 an"roi" list targets..............................................1 an"roi" up"ate proGe't -p ..........................;;!iii ant.................................................................8, <0 ant -!ersion........................................................1/ ant 'lean install......................................../8, /<8 ant Gar'ore........................................................<4. ""ms................................................................/0< hierar'hy!ie=er......................................<00, A33 Garsigner............................................................A41 keytool..............................................................A41 p"&tk _.p"& 'at output 'ombine".p"&............;;i! sRlite...............................................................</8 su"o ser!i'e u"e! reloa"..................................2/ Kipalign..............................................................<0

Constant.........................................
ACCE%%]C>A %E]L>CA50>2.....................A/2 ACCE%%]*02E]L>CA50>2............................A/2 AC50>2]E@05................................................248 AC50>2]#0CD........................................248, 288 AC50>2]-0EW.......................................248, 284 AL5E 2A50-E................................................243 @E*A$L5.........................................................243 @ELE5E...................................................</2, </. E2@]@>C$ME25..........................................0A E2@]5A8.........................................................0A

Command......................................
a"b............................................................./1A, /1/ a"b "e!i'es.................................................2A, /1/ a"b install........................................................./1/ a"b kill-ser!er................................................../1/ a"b log'at........................................<38, /0/, /1/ a"b pull............................................</8, /04, /1/ a"b push..........................................</3, /04, /1/

2:<
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

8E5..................................................................<82 +> 0Q>25AL..................................................3<

a""#re&eren'es*rom esour'e().....<.A, <<8-<A1, <A. a""#ro;imityAlert().......................................A//

02%E 5.............................................<A4, </2, </. a""%ubMenu()..................................................211 025E8E .........................................................<A4 a""5ab()....................................................18., 18/ LA 8E ...........................................................204 a""Wor"().................................................4<, .4A LA$2C+E ..............................................243, 281 a&ter5e;tChange"()..........................................1<4 LE285+]L>28.............................................22/ animateClose()................................................13/ LE285+]%+> 5...........................................22/ animate>pen()................................................13/ MA02................................................................281 animate5oggle()..............................................13/ 2$LL...............................................................</2 apply()..............................................................<.2 #E M0%%0>2]@E20E@..................................AAA apply*ormat()...................................................02 #E M0%%0>2]8 A25E@...............................AAA atta'h()............................................................24< #>%5................................................................<82 be&ore5e;tChange"().......................................1<4 ......................................................................... 4A bin"%er!i'e().............................A0A, A08, A03, A11 E%$L5]CA2CELE@.....................................288 bin"-ie=()......................................................<// E%$L5]*0 %5]$%E ....................................288 boun"Center1ottom()....................................A44 E%$L5]>D....................................................288 buil"*ore'asts()..............................................<8< %ELEC5....................................................<A4, </. 'an'el()............................................................A.8 %MALLE%5.......................................................204 'an'elAll().......................................................A.8 %5A 5]5A8..............................................0A, .04 'an8o1a'k()....................................................20. 5EF5.................................................................0A 'an8o1a'k>r*or=ar"().................................20< $#@A5E...................................................</2, </. 'an8o*or=ar"()..............................................20. -E 50CAL.........................................................3< 'he'k()........................................................88, 30 W+E E...................................................</., </< 'he'kCalling#ermission()...............................AAA ]i".....................................................................</1 'hoose@ate()....................................................14<

4ethod...........................................
a""().............................210, 211, 21/, 214, .4A, A4/ a""E!entListener()........................................./AA a""Menu()........................................................211

'hoose5ime()...................................................14< 'lear().......................................................<.2, /.. 'learCa'he()....................................................20< 'learChe'k()......................................................88

2:*
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

'lear+istory()..................................................20< 'lose()...............................13/, <14, <23, </0, </A 'ommit()..........................................................<.2 'reate().............................................................224 'reate@atabase().............................................</8 'reate*romAsset()..........................................A3/ 'reate*rom*ile().............................................A3/ 'reate0tem().....................................................A44 'reate#en"ing esult()......................................A11 'reate5abContent().........................................18< "elete()....................................................</2, </. "eta'h()...........................................................24< "o0n1a'kgroun"()....2/<, 2/A, 2/4-2/3, 24<, 24A "o5he@o=nloa"()...........................................A14 e"it()................................................................<.2 enable@e&aults().............................................<2< enable#ersistent%ele'tion().............................88 enRueue().................................................<31, <3. e;e'%JL()................................................</0-</. e;e'ute()..........................................2/., 2/3, <82 &in"*ragment1y0"().........................................3< &in"-ie=1y0"()....4A, 4/, 31, 1A3, 1/1-1/., 181, 18., .4., .4<, <1., A4< &inish().......................................................2.., 2<1

getA""A'tion-ie=()......................................<03 getAltitu"e()....................................................A/< getAppli'ationConte;t().........................A03, A2. getArguments()...............................................<A0 getAs0nteger().................................................</2 getAssets().......................................................A3/ getAs%tring()...................................................</2 getAttributeCount().........................................04 getAttribute2ame().........................................04 get1earing().....................................................A/< get1est#ro!i"er()............................................A/. get1oolean()....................................................<.2 get1roa"'ast(..................................................A/A get1roa"'ast().................................................A.3 getCall%tate()..................................................A88 getChe'ke"0tem#ositions().............................1.4 getChe'ke" a"io1utton0"()............................88 getColumn0n"e;()..........................................</A getColumn2ames()........................................</A getController()................................................A4< getCount().......................................................</A get@ata()...................................................2<1, A1/ get@e&ault%hare"#re&eren'es()..............<.2, <.. getE;ternal*iles@ir()......................................<22

&rom()................................................................8. getE;ternal%torage@ire'tory().......................<22 &syn'()......................................................<28, <23 getE;ternal%torage#ubli'@ire'tory()....<22, <32 generate#age()................................................<8A getE;ternal%torage%tate()..............................<22 get().................................................................</2 get*iles@ir().....................................................<21 getA'tion-ie=()...............................4., .4/, <08 get*ore'ast()............................................A2., A2A getA'ti!ity()..............................................8., A.3 get*ragmentManager()...................................3<

2:&
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

get0"enti&ier()...........................................<A0, <A1 get0nt()............................................................</A get0tem()........................................................../.. get0tem0"().......................................................21/ getLastDno=n#osition().................................A/. getLast2onCon&iguration0nstan'e().....2<4, 24<, A.< getLatitu"e()...................................................<8.

get%upport*ragmentManager()......................3< get%ystemA!ailable*eatures()......................../4< get%ystem%er!i'e()..................................<30, <31 get5ag()..............................................1/2-1/<, 1/4 get5e;t()...........................................................00 get-ie=().1A<, 1AA, 1A3-1/1, 1/., 1/4, .82, <A1, <// getWriteable@atabase().................................</0 getFml()............................................................0A

getLayout0n&later()...................................1A8, .8. go1a'k()...........................................................20. getList-ie=()....................................................1.A go1a'k>r*or=ar"()................................20., 20< getLongitu"e()................................................<8. go*or=ar"().....................................................20. getMeMyCurrentLo'ation2o=()...................A/< han"leError()..................................................A28 getMenu0n&o()...........................................212, 218 han"leMessage()..............................2A3, 2/0, A12 get2et=ork5ype()...........................................A88 hasAltitu"e()...................................................A/< get>!erlays()...................................................A4/ has1earing()....................................................A/< get#a'kage2ame()..........................................<A0 has%pee"().......................................................A/< get#arent().........................................................31 has%ystem*eature()........................................./4. get#hone5ype()...............................................A88 hi"e%o&t0nput*romWin"o=().........................123 get#re&eren'es().......................................<.1, <.2 in'rement#rogress1y()...................................2A4 get#rogress()............................................143, 2A4 init().........................................................<2/, <24 get#ro!i"ers()..................................................A/. initA"apter().............................................21A, 214 get ea"able@atabase()..................................</0 insert().....................................................</0, </2 get esour'es()..........................................<1., <A0 isA&terLast()....................................................</A get oot-ie=()....................................................31 isChe'ke"().................................................8A, 88 get%ettings()....................................................20/ isCon&igurationChanging................................A.A get%hare"#re&eren'es()...........................<.1, <.2 isEnable"().........................................................31 get%pee"().......................................................A/< is*inishing().....................................................A.< get%tring().......................................233, .02, </A is*o'use"().........................................................31 get%tringArray().................................................11 is oute@isplaye"()..................................A4., A4< get%ubs'riber0"()............................................A88 key()................................................................./..

2:Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

length()............................................................/.. loa"@ata()........................................................202 loa"+ea"ers*rom esour'e().................<<8, <<3 loa"5ime().......................................................20A loa"$rl()...................................200, 202, .82, /A2 lo'k()................................................................13/ make5e;t()......................................................22/ MenuBset8roupChe'kable()...........................211 Menu0temBsetChe'kable()..............................211 mk"irs()...........................................................<32 mo!e5o*irst()..................................................</A mo!e5o2e;t().................................................</A ne=Cursor()....................................................</4 ne=0nstan'e().................................................<84 ne=5ab%pe'()...........................................182, 18. ne=-ie=().......................................................<// ne;t().................................................................0A noti&y().....................................................A.8, A</ noti&yMe()........................................................A<2 obtainMessage()......................................2A8, 2A3 onA'ti!ityCreate"().........................8., .3/, A8< onA'ti!ity esult().....................2<1, 284, 288, A11 on1in"()...................................A0A, A08, A20, A23 onChe'ke"Change"()...............................8/, 100 onCli'k()..................................................../8, 2A/ onCon&igurationChange"().............2<4, 2A0, 2A1 onConte;t0tem%ele'te"()........................212, 222 onConte;tMenu%ele'te"()..............................218 onCountry%ele'te"()........................88, .3., .3A

onCreate()..../4, /8, 4<, 4A, 30, 33, 200, 210, 21A, 2.2-2.A, 2<., 2<<, 2A/, 24<, 24A, .02, .4., .80, .82, .8., .3<, .3/, <1/, <2<, <2/, <24, <.8, <<3, <A8, </0, </1, <8<, <31, A0A, A03, A1/, A14, A20, A22, A2A, A23, A.<, A<., A</, A8<, /<4, //A onCreateConte;tMenu()...................212, 214, 222 onCreate>ptionsMenu()...210, 211, 21A, 222, ./3, .4., .80, <04, <08 onCreate#anelMenu()......................................211 onCreate-ie=().................................81, .82, A8. on@estroy()......2.., .82, <8<, A0A, A03, A1/, A20, A2A, A23, A.< on@e!i'e ea"y()...................................../AA, /A/ on@o=ngra"e()...............................................</1 on+an"le0ntent().....................................A1/, A14 onList0temCli'k().....1.<, 1/4, 2A/, .8., .88, .3., .34, </A onLoa"()................................................../AA, /A/ onLoa"+ea"ers()............................................<<3 onLo'ationChange"().....................................A/A on>pen().........................................................</0 on>ptions0tem%ele'te"()...210, 211, 21., 21/, 222, ./3, .80 on#age%tarte"()..............................................20< on#ause()..................2.<, 28., .82, <13, A0A, A43 on#ostE;e'ute().......................2/A, 2/8, 24A, A28 on#reE;e'ute()................................................2/A on#repare>ptionsMenu()...............................210 on#rogress$p"ate()........................2/A, 2/4, 2/8 on atingChange"().........................................1/4 on e'ei!e()......................................................282 on e'ei!e"+ttpAuth eRuest().....................20< on estart().......................................................2.. on estore0nstan'e%tate().......................2.A, .3/

2:%
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

on esume()......2.., 2.<, 282, .82, <13, <.8, <8., A0A, A43 on etain2onCon&iguration0nstan'e(). .2<4, 2A., 24<, 24A, .3/, .34, A03, A2., A2<, A.., A.A on%a!e0nstan'e%tate().....2.., 2.A, 2<2, 2<., 2A., .3/ on%er!i'eConne'te"()....................................A08 on%er!i'e@is'onne'te"()...............................A03 on%tart()............................................2.., 2/1, .82 on%tartComman"().........................A0A, A04, A20 on%top()............................................2.., 2/1, .82 on5ap()............................................................A48 on5e;tChange"().............................................1<4 on5ooMany e"ire'ts()...................................20< on$pgra"e()....................................<A8, </0, </1 open()...............................................................13/ open*ile0nput().................................<14, <13, <21 open*ile>uptut()............................................<21 open*ile>utput()..............................<14, <13, <21 open a= esour'e().........................................<1. play()........................................................A20, A<4 populate()........................................................A44 post()................................................................2/2 post@elaye"()..................................................2/2 publish#rogress()............................2/A, 2/4, 2/8 Ruery().....................................</., </<, <32, <3. RueryWith*a'tory()........................................</4 ra=Juery()......................................................</. ra=JueryWith*a'tory().................................</4 register*orConte;tMenu()..............................212 register e'ei!er().....................................282, A10

reloa"()............................................................20. remo!e()..........................................................<.2 remo!e0tem().................................................../.. remo!e#ro;imityAlert().................................A// remo!e$p"ates()............................................A/A reRuery()..........................................................</A reRuest*o'us()...................................................31 reRuestLo'ation$p"ates()......................A/<, A/A restoreMe()......................................2<., 2<<, 2<4 run>n$i5hrea"()...........................................2/2 sen"()................................................................A11 sen"1roa"'ast().......................................A10, AAA sen"EmptyMessage()......................................2A3 sen"Message().................................................2A8 sen"MessageAt*ront>&Jueue()....................2A8 sen"MessageAt5ime()....................................2A8 sen"Message@elaye"()...................................2A3 set()..................................................................<4/ setA''ura'y()...................................................A/. setA"apter().................................1.., 1.8, 1<1, 1<A setAllo=e"2et=ork5ypes()............................<32 setAllo=e">!er oaming()............................<32 setAlphabeti'%hort'ut()...................................211 setAltitu"e eRuire"().....................................A/. setCell en"erer().............................................1.2 setCenter().......................................................A4A setChe'ke"()...............................................8A, 30 setChoi'eMo"e()..............................................1.A setColumnCollapse"().....................................11< setColumn%hrinkable()....................................11<

2:0
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

setColumn%tret'hable()...................................11< setContent()..............................................182-18< setContent-ie=().................../4, 4A, 31, .3<, /<4 setCostAllo=e"().............................................A/. setCurrent5ab()...............................................18. set@e&ault*ont%iKe().......................................204 set@es'ription()..............................................<32 set@estination0nE;ternal#ubli'@ir()............<32 set@rop@o=n-ie= esour'e()........................1.8 set@uration()...................................................22/ setEnable"()................................................31, 221 set*antasy*ont*amily()..................................20/ set*oregroun"()..............................................A</ set8ra!ity().......................................................3/ set8roupChe'kable()......................................210 set8roupEnable"()..........................................221 set8roup-isible().............................................221 set+as>ptionsMenu().....................................80 set0'on()...........................................................224 set0n"eterminate()..........................................2A4 set0n"i'ator()............................................182, 18. set0tem()........................................................../.. set0temChe'ke"().............................................1.4 setCa!a%'riptCan>penWin"o=sAutomati'ally( )........................................................................ 204 setCa!a%'riptEnable"()....................................204

set2egati!e1utton()........................................224 set2eutral1utton()..........................................224 set2umeri'%hort'ut()......................................211 set>nCli'kListener()......................................../4 set>nE"itorA'tionListener()..................12/, .4< set>n0tem%ele'te"Listener().............1.., 1.8, 1<1 set>n%eek1arChangeListener().....................143 set>rientation()................................................3< set#a""ing()......................................................30 set#ositi!e1utton().........................................224 set#rogress()....................................................2A4 setJ=ertyMo"e().............................................211 set esult().................................................288, A11 set5ag()...............................................1/2-1/<, 1/4 set5e;t()...................................................../8, 2AA set5e;tColor()....................................................31 set5e;t%iKe()....................................................204 set5itle()..................................................224, <32 set5ype&a'e().............................................42, A3/ setup()........................................................181-18. set$serAgent()................................................204 set-ie=()..........................................................22/ set-isible().......................................................221 set-isible0n@o=nloa"s$i()............................A00 setWeb-ie=Client().......................................20< setQoom()........................................................A4A

setLatestE!ent0n&o()................................A.3, A<2 shoul">!erri"e$rlLoa"ing().................20<, 20A setListA"apter().......................................1.<, .8. sho=().......................................................22/-228 setMa;().............................................143, 2A4, 2/1 sho=Me()........................................................283 setMessage()....................................................224 sho=2e;t()......................................................183

2:2
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

siKe().................................................................A44 start()................................................................144 startA'ti!ity()...2<0, 2<1, 284, .34, <A1, A0/, A88, A31 startA'ti!ity*or esult()....2<0-2<2, 284, 288, A11

an"roi",'ollapseColumns................................11< an"roi",'olumnWi"th.....................................1<1 an"roi",'ompletion5hreshol"........................1<A an"roi","igits....................................................8. an"roi","ra=%ele'tor>n5op...................1.8, 1<3

start@o=nloa"()..............................................<31 an"roi",horiKontal%pa'ing..............................1<1 start*oregroun"()............................A20, A</, A<4 an"roi",i".........................4., 4<, 88, 10A, 181, 182 start#layer().....................................................A22 an"roi",label.....................................................<2 start%er!i'e() A0A-A08, A11, A1<, A1/, A14, A13, A20, A22 stop().................................................144, A20, A<4 stop*oregroun"()....................................A</-A<8 stop#layer().....................................................A22 stop%el&().........................................................A08 stop%er!i'e()....................................A04, A03, A22 s=it'h().............................................................211 toggle().................................................8A, 88, 13/ toggle%atellite()...............................................A80 to%tring()..........................................................1.2 unbin"%er!i'e()......................................A08, A03 unlo'k()............................................................13/ unregister e'ei!er().......................................28. up"ate()...................................................</2, </. up"ate*ore'ast().....................................<8., A28 up"ateLabel()...................................................14< up"ate5ime()............................................../4, /8 !alue>&()...........................................................32 an"roi",layout]abo!e......................................10/ an"roi",layout]align1aseline.........................104 an"roi",layout]align1ottom..........................10/ an"roi",layout]alignLe&t................................10/ an"roi",layout]align#arent1ottom................10A an"roi",layout]align#arentLe&t......................10A an"roi",layout]align#arent ight...................10A an"roi",layout]align#arent5op......................10A an"roi",layout]align ight..............................104 an"roi",layout]align5op..........................10/, 104 an"roi",layout]belo=.....................................10/ an"roi",layout]'enter+oriKontal...................10A an"roi",layout]'enter0n#arent......................10A an"roi",layout]'enter-erti'al........................10A an"roi",layout]'olumn....................................112 an"roi",layout]gra!ity.....................................3/ an"roi",layout]height................................4., 3A an"roi",layout]span.........................................112 an"roi",layout]toLe&t>&.................................10/

Property.........................................
an"roi",auto5e;t...............................................8. an"roi",'apitaliKe.............................................8.

an"roi",layout]to ight>&..............................10/ an"roi",layout]=eight.....................................3A an"roi",layout]=i"th...........................4., 3A, 38

2:7
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

9ey)ord ndex

an"roi",mani&est...............................................<1 an"roi",name.....................................<2, A0A, AA2 an"roi",ne;t*o'us@o=n..................................30 an"roi",ne;t*o'usLe&t.....................................30 an"roi",ne;t*o'us ight...................................30 an"roi",ne;t*o'us$p.......................................30 an"roi",numColumns......................................1<1 an"roi",orientation..........................................3< an"roi",permission.................................A0/, AA< an"roi",shrinkColumns...................................11< an"roi",singleLine............................................8.

an"roi",spa'ing...............................................1<3 an"roi",spinner%ele'tor..................................1<3 an"roi",sr'........................................................82 an"roi",stret'hColumns..................................11. an"roi",stret'hMo"e.......................................1<1 an"roi",te;t.................................................4., 43 an"roi",te;tColor.......................................80, 8A an"roi",te;t%tyle.........................................43, 8. an"roi",type&a'e...............................................43 an"roi",!erti'al%pa'ing...................................1<1 an"roi",!isibility...............................................30

2:8
Subscribe to updates at http://commonsware.com Special Creative Commons BY-NC-SA 3.0 License Edition

Vous aimerez peut-être aussi