/* Ċ Ġ* ĠCopyright Ġ 2 0 2 1 ĠGoogle ĠInc . ĠAll ĠRights ĠReserved . Ċ Ġ* Ċ Ġ* ĠLicensed Ġunder Ġthe ĠApache ĠLicense , ĠVersion Ġ 2 . 0 Ġ( the Ġ" License "); Ċ Ġ* Ġyou Ġmay Ġnot Ġuse Ġthis Ġfile Ġexcept Ġin Ġcompliance Ġwith Ġthe ĠLicense . Ċ Ġ* ĠYou Ġmay Ġobtain Ġa Ġcopy Ġof Ġthe ĠLicense Ġat Ċ Ġ* Ċ Ġ* ĠĠĠĠ Ġhttp :// www . apache . org / licenses / LICENSE - 2 . 0 Ċ Ġ* Ċ Ġ* ĠUnless Ġrequired Ġby Ġapplicable Ġlaw Ġor Ġagreed Ġto Ġin Ġwriting , Ġsoftware Ċ Ġ* Ġdistributed Ġunder Ġthe ĠLicense Ġis Ġdistributed Ġon Ġan Ġ" AS ĠIS " ĠBASIS , Ċ Ġ* ĠWITHOUT ĠWARRANTIES ĠOR ĠCONDITIONS ĠOF ĠANY ĠKIND , Ġeither Ġexpress Ġor Ġimplied . Ċ Ġ* ĠSee Ġthe ĠLicense Ġfor Ġthe Ġspecific Ġlanguage Ġgoverning Ġpermissions Ġand Ċ Ġ* Ġlimitations Ġunder Ġthe ĠLicense . Ċ Ġ*/ Ċ Ċ package Ġcom . google . android . gms . identity . sample . f ido 2 . ui . home Ċ Ċ import Ġandroid . app . Activity Ċ import Ġandroid . os . Bundle Ċ import Ġandroid . view . LayoutInflater Ċ import Ġandroid . view . View Ċ import Ġandroid . view . ViewGroup Ċ import Ġandroid . widget . Toast Ċ import Ġandroidx . activity . result . Activity Result Ċ import Ġandroidx . activity . result . Intent Sender Request Ċ import Ġandroidx . activity . result . contract . Activity Result Contracts Ċ import Ġandroidx . core . view . isVisible Ċ import Ġandroidx . fragment . app . Fragment Ċ import Ġandroidx . fragment . app . view Models Ċ import Ġandroidx . lifecycle . lifecycle Scope Ċ import Ġcom . google . android . gms . f ido . F ido Ċ import Ġcom . google . android . gms . f ido . f ido 2 . api . common . Authenticator ErrorResponse Ċ import Ġcom . google . android . gms . f ido . f ido 2 . api . common . PublicKey Credential Ċ import Ġcom . google . android . gms . identity . sample . f ido 2 . R Ċ import Ġcom . google . android . gms . identity . sample . f ido 2 . databinding . Home Fragment Binding Ċ import Ġdagger . h ilt . android . Android EntryPoint Ċ import Ġkotlinx . coroutines . flow . collect Ċ import Ġkotlinx . coroutines . launch Ċ Ċ @ Android EntryPoint Ċ class ĠHome Fragment Ġ: ĠFragment (), ĠDelete Confirmation Fragment . Listener Ġ{ ĊĊĠĠĠ Ġcompanion Ġobject Ġ{ ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠTAG Ġ= Ġ" Home Fragment " ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠFR AG MENT _ DELETE _ CONFIRM ATION Ġ= Ġ" delete _ confirmation " ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġval ĠviewModel : ĠHome ViewModel Ġby Ġview Models () ĊĠĠĠ Ġprivate Ġlateinit Ġvar Ġbinding : ĠHome Fragment Binding ĊĊĠĠĠ Ġprivate Ġval Ġcreate Credential Intent Launcher Ġ= Ġregister For Activity Result ( ĊĠĠĠĠĠĠĠ ĠActivity Result Contracts . Start Intent Sender For Result (), ĊĠĠĠĠĠĠĠ Ġ:: handle Create Credential Result ĊĠĠĠ Ġ) ĊĊĠĠĠ Ġoverride Ġfun ĠonCreate View ( ĊĠĠĠĠĠĠĠ Ġinflater : ĠLayoutInflater , ĊĠĠĠĠĠĠĠ Ġcontainer : ĠViewGroup ?, ĠsavedInstanceState : ĠBundle ? ĊĠĠĠ Ġ): ĠView ? Ġ{ ĊĠĠĠĠĠĠĠ Ġbinding Ġ= ĠHome Fragment Binding . inflate ( in flater , Ġcontainer , Ġfalse ) ĊĠĠĠĠĠĠĠ Ġbinding . lifecycle Owner Ġ= Ġview Lifecycle Owner ĊĠĠĠĠĠĠĠ Ġbinding . viewModel Ġ= ĠviewModel ĊĠĠĠĠĠĠĠ Ġreturn Ġbinding . root ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġon View Created ( view : ĠView , ĠsavedInstanceState : ĠBundle ?) Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġcredential Adapter Ġ= ĠCredential Adapter Ġ{ Ġcredential Id Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠ ĠDelete Confirmation Fragment . newInstance ( credential Id ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ. show ( child FragmentManager , ĠFR AG MENT _ DELETE _ CONFIRM ATION ) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġbinding . credentials . adapter Ġ= Ġcredential Adapter ĊĊĠĠĠĠĠĠĠ Ġview Lifecycle Owner . lifecycle Scope . launch When Started Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠviewModel . credentials . collect Ġ{ Ġcredentials Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcredential Adapter . submit List ( credentials ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbinding . empty Credentials . isVisible Ġ= Ġcredentials . isEmpty () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbinding . credentials Caption . isVisible Ġ= Ġcredentials . isNotEmpty () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġ// ĠMenu ĊĠĠĠĠĠĠĠ Ġbinding . app Bar . replace Menu ( R . menu . home ) ĊĠĠĠĠĠĠĠ Ġbinding . app Bar . setOn MenuItem ClickListener Ġ{ Ġitem Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( item . itemId ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠR . id . action _ re auth Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠviewModel . re auth () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġtrue ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠR . id . action _ sign _ out Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠviewModel . sign Out () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġtrue ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġelse Ġ-> Ġfalse ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġview Lifecycle Owner . lifecycle Scope . launch When Started Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠviewModel . processing . collect Ġ{ Ġprocessing Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( processing ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbinding . processing . show () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbinding . processing . hide () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġ// ĠF AB ĊĠĠĠĠĠĠĠ Ġbinding . add . setOnClickListener Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġlifecycle Scope . launch Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġintent Ġ= ĠviewModel . register Request () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( intent Ġ!= Ġnull ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcreate Credential Intent Launcher . launch ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠIntent Sender Request . Builder ( intent ). build () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun ĠonDelete Confirmed ( credential Id : ĠString ) Ġ{ ĊĠĠĠĠĠĠĠ ĠviewModel . remove Key ( credential Id ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġhandle Create Credential Result ( activity Result : ĠActivity Result ) Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġbytes Ġ= Ġactivity Result . data ?. get ByteArray Extra ( F ido . F ID O 2 _ KEY _ CRED ENTIAL _ EXTRA ) ĊĠĠĠĠĠĠĠ Ġwhen Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġactivity Result . result Code Ġ!= ĠActivity . RESULT _ OK Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . makeText ( require Context (), ĠR . string . cancelled , ĠToast . LENGTH _ LONG ). show () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġbytes Ġ== Ġnull Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . makeText ( require Context (), ĠR . string . credential _ error , ĠToast . LENGTH _ LONG ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ. show () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġelse Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġcredential Ġ= ĠPublicKey Credential . deserialize From Bytes ( bytes ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġresponse Ġ= Ġcredential . response ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( response Ġis ĠAuth enticator ErrorResponse ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . makeText ( require Context (), Ġresponse . errorMessage , ĠToast . LENGTH _ LONG ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ. show () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠviewModel . register Response ( credential ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} Ċ } Ċ