package Ġcom . cisco web ex . android sdk . k itch ens ink . messaging . composer Ċ Ċ import Ġandroid . app . Activity Ċ import Ġandroid . content . Context Ċ import Ġandroid . content . Intent Ċ import Ġandroid . net . Uri Ċ import Ġandroid . os . Bundle Ċ import Ġandroid . text . Html Ċ import Ġandroid . util . Log Ċ import Ġandroid . view . LayoutInflater Ċ import Ġandroid . view . View Ċ import Ġandroid . view . ViewGroup Ċ import Ġandroid . widget . Toast Ċ import Ġandroidx . appcompat . app . AppCompatActivity Ċ import Ġandroidx . databinding . Data Binding Util Ċ import Ġandroidx . lifecycle . Observer Ċ import Ġandroidx . recyclerview . widget . Divider Item Decoration Ċ import Ġandroidx . recyclerview . widget . Linear LayoutManager Ċ import Ġandroidx . recyclerview . widget . RecyclerView Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . R Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . databinding . Activity Message Composer Binding Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . databinding . Dialog Post MessageHandler Binding Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . databinding . ListItem Upload Attachment Binding Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . messaging . composer . Message Composer ViewModel . Companion . MIN IMUM _ MEMBER S _ REQUIRED _ FOR _ MENT IONS Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . messaging . spaces . Reply Message Model Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . utils . Constants Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . utils . FileUtils . get Upload Uri Path Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . utils . Permissions Helper Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . utils . extensions . hide Keyboard Ċ import Ġcom . cisco web ex . android sdk . k itch ens ink . utils . show Dialog With Message Ċ import Ġcom . cisco web ex . android sdk . message . Local File Ċ import Ġcom . cisco web ex . android sdk . message . Message Ċ import Ġcom . cisco web ex . android sdk . utils . EmailAddress Ċ import Ġcom . cisco web ex . android sdk . utils . internal . Mime Utils Ċ import Ġorg . k oin . android . ext . android . inject Ċ import Ġjava . io . File ĊĊ Ċ class ĠMessage Composer Activity Ġ: ĠAppCompatActivity () Ġ{ ĊĊĠĠĠ Ġcompanion Ġobject Ġ{ ĊĠĠĠĠĠĠĠ Ġenum Ġclass ĠComposer Type Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠPOST _ SPACE , ĊĠĠĠĠĠĠĠĠĠĠĠ ĠPOST _ PERSON _ ID , ĊĠĠĠĠĠĠĠĠĠĠĠ ĠPOST _ PERSON _ EMAIL ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġenum Ġclass ĠStyle Type Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠP LA IN _ TEXT , ĊĠĠĠĠĠĠĠĠĠĠĠ ĠMARK DOWN _ TEXT ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġfun Ġget Intent ( context : ĠContext , Ġtype : ĠComposer Type , Ġid : ĠString , Ġreply Parent Message : ĠReply Message Model ?, ĠmessageId : ĠString ? Ġ= Ġnull ): ĠIntent Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġintent Ġ= ĠIntent ( context , ĠMessage Composer Activity :: class . java ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġintent . putExtra ( Constants . Intent . COMP O SER _ TYPE , Ġtype ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġintent . putExtra ( Constants . Intent . COMP O SER _ ID , Ġid ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġintent . putExtra ( Constants . Intent . COMP O SER _ REPLY _ PARENT _ MESSAGE , Ġreply Parent Message ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġintent . putExtra ( Constants . Intent . MESSAGE _ ID , ĠmessageId ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn Ġintent ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġval Ġtag Ġ= Ġ" Message Composer Activity " ĊĠĠĠ Ġprivate Ġval ĠP ICK FILE _ REQUEST _ CODE Ġ= Ġ 1 0 0 5 ĊĠĠĠ Ġprivate Ġlateinit Ġvar Ġbinding : ĠActivity Message Composer Binding ĊĠĠĠ Ġprivate Ġval Ġmessage Composer ViewModel : ĠMessage Composer ViewModel Ġby Ġinject () ĊĠĠĠ Ġprivate Ġval Ġpermissions Helper : ĠPermissions Helper Ġby Ġinject () ĊĠĠĠ Ġprivate Ġlateinit Ġvar Ġcomposer Type : ĠComposer Type ĊĠĠĠ Ġprivate Ġvar Ġid : ĠString ? Ġ= Ġnull ĊĠĠĠ Ġprivate Ġvar Ġstyle Type Ġ= ĠStyle Type . PLAIN _ TEXT ĊĠĠĠ Ġprivate Ġlateinit Ġvar Ġattachment Adapter : ĠUpload Attachments Adapter ĊĠĠĠ Ġprivate Ġvar Ġis Ment ions Enabled : ĠBoolean Ġ= Ġfalse ĊĠĠĠ Ġprivate Ġvar Ġreply Parent Message : ĠReply Message Model ? Ġ= Ġnull ĊĠĠĠ Ġ// ĠMessage Id Ġis Ġnot Ġnull Ġin Ġcase Ġof Ġedit Ġfeature . ĊĠĠĠ Ġprivate Ġvar ĠmessageId : ĠString ? Ġ= Ġnull ĊĊĠĠĠ Ġoverride Ġfun ĠonCreate ( savedInstanceState : ĠBundle ?) Ġ{ ĊĠĠĠĠĠĠĠ Ġsuper . onCreate ( savedInstanceState ) ĊĠĠĠĠĠĠĠ Ġcomposer Type Ġ= Ġintent . get Serializable Extra ( Constants . Intent . COMP O SER _ TYPE ) Ġas ĠComposer Type ĊĠĠĠĠĠĠĠ Ġid Ġ= Ġintent . getString Extra ( Constants . Intent . COMP O SER _ ID ) ĊĠĠĠĠĠĠĠ Ġreply Parent Message Ġ= Ġintent . get Parcelable Extra ( Constants . Intent . COMP O SER _ REPLY _ PARENT _ MESSAGE ) ĊĠĠĠĠĠĠĠ ĠmessageId Ġ= Ġintent . getString Extra ( Constants . Intent . MESSAGE _ ID ) ĊĊĠĠĠĠĠĠĠ Ġif Ġ( composer Type Ġ== ĠComposer Type . POST _ SPACE ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġis Ment ions Enabled Ġ= Ġtrue ĊĠĠĠĠĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . fetch All Members In Space ( id ) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ ĠData Binding Util . set ContentView < Activity Message Composer Binding >( this , ĠR . layout . activity _ message _ composer ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ. also Ġ{ Ġbinding Ġ= Ġit Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ. apply Ġ{ ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġplain RadioButton . isChecked Ġ= Ġtrue ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġsend Button . setOnClickListener Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġsend Button Clicked () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠsetUp Observer s () ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( message Id Ġ== Ġnull ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġattachment Button . setOnClickListener Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġchecking Permission Ġ= Ġcheck Read Storage Permissions () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ(! checking Permission ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġopen File Explorer () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠIn Ġcase Ġof Ġedit Ġwe Ġdo Ġnot Ġsupport Ġediting Ġattachments ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġattachment Button . visibility Ġ= ĠView . GONE ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġradio Group . setOn Checked ChangeListener Ġ{ Ġ_, Ġchecked Id Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( checked Id ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠR . id . plain RadioButton Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġstyle Type Ġ= ĠStyle Type . PLAIN _ TEXT ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠR . id . markdown RadioButton Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġstyle Type Ġ= ĠStyle Type . MARK DOWN _ TEXT ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġon Attachment Cross Click : Ġ( File ) Ġ-> ĠUnit Ġ= Ġ{ Ġfile Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLog . d ( tag , Ġ" on Attachment Cross Click Ġpath : Ġ${ file . absolute Path }") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġposition Ġ= Ġattachment Adapter . attached Files . indexOf ( file ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġattachment Adapter . attached Files . remove At ( position ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġattachment Adapter . notify Item Removed ( position ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġdivider Item Decoration Ġ= ĠDiv ider Item Decoration ( this @ Message Composer Activity , ĠLinearLayoutManager . VERTICAL ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġattachment RecyclerView . addItem Decoration ( divider Item Decoration ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġattachment Adapter Ġ= ĠUpload Attachments Adapter ( on Attachment Cross Click ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġattachment RecyclerView . adapter Ġ= Ġattachment Adapter ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun ĠsetUp Observer s () Ġ{ ĊĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . post Messages . observe ( this @ Message Composer Activity , ĠObserver Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġit ?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġdisplay Post MessageHandler ( it ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġ?: Ġrun Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġshow Dialog With Message ( this @ Message Composer Activity , ĠR . string . post _ message _ internal _ error , Ġ"") ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreset View () ĊĠĠĠĠĠĠĠ Ġ}) ĊĊĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . postMessage Error . observe ( this @ Message Composer Activity , ĠObserver Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġit ?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġshow Dialog With Message ( this @ Message Composer Activity , ĠR . string . post _ message _ internal _ error , Ġit ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġ?: Ġrun Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġshow Dialog With Message ( this @ Message Composer Activity , ĠR . string . post _ message _ internal _ error , Ġ"") ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreset View () ĊĠĠĠĠĠĠĠ Ġ}) ĊĊĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . fetch Membership s LiveData . observe ( this @ Message Composer Activity , ĠObserver Ġ{ Ġ Ġmembership s Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠ Ġmembership s ?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif ( is Ment ions Enabled Ġ&& Ġit . size Ġ> ĠMIN IMUM _ MEMBER S _ REQUIRED _ FOR _ MENT IONS Ġ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbinding . message . add Auto Complete Plugin ( Ment ions Plugin ( this @ Message Composer Activity , Ġthis , Ġmessage Composer ViewModel )) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ}) ĊĊĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . edit Message . observe ( this @ Message Composer Activity , ĠObserver Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġit ?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġshow Dialog With Message ( this @ Message Composer Activity , Ġnull , ĠgetString ( R . string . message _ edit _ successful )) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġ?: Ġrun Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġshow Dialog With Message ( this @ Message Composer Activity , Ġnull , ĠgetString ( R . string . edit _ message _ internal _ error )) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreset View () ĊĠĠĠĠĠĠĠ Ġ}) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġopen File Explorer () Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġintent Ġ= ĠIntent ( Intent . ACTION _ GET _ CONTENT ). apply Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġflags Ġ= ĠIntent . FLAG _ GRANT _ READ _ URI _ PERMISSION ĊĠĠĠĠĠĠĠĠĠĠĠ Ġtype Ġ= Ġ"* /* " ĊĠĠĠĠĠĠĠĠĠĠĠ Ġadd Category ( Intent . CATEGORY _ OP ENABLE ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġput Extra ( Intent . EXTRA _ ALLOW _ MULTIPLE , Ġtrue ) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ ĠstartActivity For Result ( intent , ĠP ICK FILE _ REQUEST _ CODE ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġon Activity Result ( request Code : ĠInt , ĠresultCode : ĠInt , Ġdata : ĠIntent ?) Ġ{ ĊĠĠĠĠĠĠĠ Ġsuper . on Activity Result ( request Code , ĠresultCode , Ġdata ) ĊĠĠĠĠĠĠĠ Ġhandle Activity Result ( request Code , ĠresultCode , Ġdata ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġhandle Activity Result ( ĊĠĠĠĠĠĠĠ Ġrequest Code : ĠInt , ĊĠĠĠĠĠĠĠ ĠresultCode : ĠInt , ĊĠĠĠĠĠĠĠ Ġdata : ĠIntent ? ĊĠĠĠ Ġ) Ġ{ ĊĠĠĠĠĠĠĠ Ġif Ġ( request Code Ġ== ĠP ICK FILE _ REQUEST _ CODE Ġ&& ĠresultCode Ġ== ĠActivity . RESULT _ OK ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġdata ?. let Ġ{ Ġintent Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġintent . clip Data ?. let Ġ{ Ġdata Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( index Ġin Ġ 0 Ġuntil Ġdata . item Count ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġuri Ġ= Ġdata . getItem At ( index ). uri ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġadd Uri ToList ( uri ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġ?: Ġrun Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġintent . data ?. let Ġ{ Ġuri Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġadd Uri ToList ( uri ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġadd Uri ToList ( uri : ĠUri ) Ġ{ ĊĠĠĠĠĠĠĠ Ġval ĠfilePath Ġ= Ġget Upload Uri Path ( this @ Message Composer Activity , Ġuri ) ĊĠĠĠĠĠĠĠ ĠfilePath ?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġfile Ġ= ĠFile ( it ) ĊĠĠĠĠĠĠĠĠĠĠĠ ĠLog . d ( tag , Ġ" P ICK FILE _ REQUEST _ CODE ĠfilePath : Ġ$ it ") ĊĠĠĠĠĠĠĠĠĠĠĠ ĠLog . d ( tag , Ġ" P ICK FILE _ REQUEST _ CODE Ġfile ĠEx ist : Ġ${ file . exists () }") ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġattachment Adapter . attached Files . add ( file ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġattachment Adapter . notify DataSet Changed () ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġprocess Attachment Files (): ĠArrayList < Local File > Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġfiles Ġ= ĠArrayList < Local File >() ĊĊĠĠĠĠĠĠĠ Ġfor Ġ( file Ġin Ġattachment Adapter . attached Files ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġvar Ġthumbnail : ĠLocal File . Thumbnail ? Ġ= Ġnull ĊĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( Mime Utils . get ContentType By Filename ( file . name ) Ġ== ĠMime Utils . ContentType . IMAGE ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġthumbnail Ġ= ĠLocal File . Thumbnail ( file , Ġnull , Ġresources . getInteger ( R . integer . attachment _ thumbnail _ width ), Ġresources . getInteger ( R . integer . attachment _ thumbnail _ height )) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġlocal File Ġ= ĠLocal File ( file , Ġnull , Ġthumbnail , Ġnull ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġfiles . add ( local File ) ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġreturn Ġfiles ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġsend Button Clicked () Ġ{ ĊĠĠĠĠĠĠĠ Ġif Ġ( binding . message . text . isEmpty () Ġ&& Ġattachment Adapter . attached Files . isEmpty ()) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġshow Dialog With Message ( this @ Message Composer Activity , ĠR . string . post _ message _ error , ĠgetString ( R . string . post _ message _ empty _ error )) ĊĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠmessageId ?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠEdit Ġmessage Ġflow ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġedit Message ( it ) Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ?: Ġcomposer Type . let Ġ{ Ġtype Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġid ?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġfiles Ġ= Ġprocess Attachment Files () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( type ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠComposer Type . POST _ SPACE Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġpost To Space ( it , Ġfiles ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠComposer Type . POST _ PERSON _ ID Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġpost Person ById ( it , Ġfiles ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠComposer Type . POST _ PERSON _ EMAIL Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġpost Person By Email ( it , Ġfiles ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġedit Message ( message Id : ĠString ) Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġstr Ġ= Ġbinding . message . text . toString () ĊĠĠĠĠĠĠĠ Ġval Ġmessage Content Ġ= Ġbinding . message . getMessage Content () ĊĠĠĠĠĠĠĠ Ġval Ġtext : ĠMessage . Text Ġ= Ġif Ġ( style Type Ġ== ĠStyle Type . PLAIN _ TEXT ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠMessage . Text . plain ( str ) ĊĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠMessage . Text . markdown ( str , Ġnull , Ġnull ) ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . edit Message ( message Id , Ġtext , Ġmessage Content . message Input Ment ions ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġdisplay Post MessageHandler ( message : ĠMessage ) Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġbuilder : Ġandroidx . appcompat . app . AlertDialog . Builder Ġ= Ġandroidx . appcompat . app . AlertDialog . Builder ( this ) ĊĊĠĠĠĠĠĠĠ Ġbuilder . setTitle ( R . string . message _ details ) ĊĊĠĠĠĠĠĠĠ ĠDialog Post MessageHandler Binding . inflate ( layout Inflater ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ. apply Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġmessage Data Ġ= Ġmessage ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġmsg Ġ= Ġmessage . getText As Object () ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġmsg . get Markdown ()?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġmessage Body TextView . text Ġ= ĠHtml . from Html ( msg . get Markdown (), ĠHtml . FROM _ HTML _ MODE _ LEG ACY ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġ?: Ġrun Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġmsg . get Plain ()?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġmessage Body TextView . text Ġ= ĠHtml . from Html ( msg . get Plain (), ĠHtml . FROM _ HTML _ MODE _ LEG ACY ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbuilder . setView ( this . root ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbuilder . set Positive Button ( android . R . string . ok ) Ġ{ Ġdialog , Ġ_ Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġdialog . dismiss () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbuilder . show () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġpost Person By Email ( email : ĠString , Ġfiles : ĠArrayList < Local File > ?) Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġemail Address Ġ= ĠEmail Address . fromString ( email ) ĊĠĠĠĠĠĠĠ Ġemail Address ?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . post To Person ( email Address , Ġbinding . message . text . toString (), Ġstyle Type Ġ== ĠStyle Type . PLAIN _ TEXT , Ġfiles ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġshow Progress () ĊĠĠĠĠĠĠĠ Ġ} Ġ?: Ġrun Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġshow Dialog With Message ( this @ Message Composer Activity , ĠR . string . post _ message _ error , ĠgetString ( R . string . post _ message _ email _ empty )) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġpost Person ById ( person Id : ĠString , Ġfiles : ĠArrayList < Local File > ?) Ġ{ ĊĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . post To Person ( person Id , Ġbinding . message . text . toString (), Ġstyle Type Ġ== ĠStyle Type . PLAIN _ TEXT , Ġfiles ) ĊĠĠĠĠĠĠĠ Ġshow Progress () ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġpost To Space ( space Id : ĠString , Ġfiles : ĠArrayList < Local File > ?) Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġmessage Content Ġ= Ġbinding . message . getMessage Content () ĊĊĠĠĠĠĠĠĠ Ġvar Ġprogress Ġ= Ġtrue ĊĊĠĠĠĠĠĠĠ Ġreply Parent Message ?. let Ġ{ Ġreply Message Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġstr Ġ= Ġbinding . message . text . toString () ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġtext : ĠMessage . Text ? Ġ= Ġif Ġ( style Type Ġ== ĠStyle Type . PLAIN _ TEXT ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠMessage . Text . plain ( str ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠMessage . Text . markdown ( str , Ġnull , Ġnull ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġtext ?. let Ġ{ Ġmsg Txt Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġdraft Ġ= ĠMessage . draft ( msg Txt ) ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġmessage Content . message Input Ment ions ?. let Ġ{ Ġmentions Array Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( item Ġin Ġmentions Array ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġdraft . add Ment ions ( item ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfiles ?. let Ġ{ Ġfiles Array Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( item Ġin Ġfiles Array ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġdraft . add Attachments ( item ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġdraft . setParent ( reply Message . getMessage ()) ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . postMessage Draft ( space Id , Ġdraft ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġ?: Ġrun Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġprogress Ġ= Ġfalse ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġshow Dialog With Message ( this @ Message Composer Activity , ĠR . string . post _ message _ error , ĠgetString ( R . string . post _ message _ invalid _ message )) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} Ġ?: Ġrun Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġmessage Composer ViewModel . post To Space ( space Id , Ġbinding . message . text . toString (), Ġstyle Type Ġ== ĠStyle Type . PLAIN _ TEXT , Ġmessage Content . message Input Ment ions , Ġfiles ) ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġif Ġ( progress ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġshow Progress () ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġshow Progress () Ġ{ ĊĠĠĠĠĠĠĠ Ġbinding . progress Layout . visibility Ġ= ĠView . VISIBLE ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġhide Progress () Ġ{ ĊĠĠĠĠĠĠĠ Ġbinding . progress Layout . visibility Ġ= ĠView . GONE ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġreset View () Ġ{ ĊĠĠĠĠĠĠĠ Ġbinding . message . text . clear () ĊĠĠĠĠĠĠĠ Ġhide Keyboard ( binding . message ) ĊĠĠĠĠĠĠĠ Ġattachment Adapter . attached Files . clear () ĊĠĠĠĠĠĠĠ Ġattachment Adapter . notify DataSet Changed () ĊĠĠĠĠĠĠĠ Ġhide Progress () ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġcheck Read Storage Permissions (): ĠBoolean Ġ{ ĊĠĠĠĠĠĠĠ Ġif Ġ(! permissions Helper . has Read Storage Permission ()) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠLog . d ( tag , Ġ" request ing Ġread Ġpermission ") ĊĠĠĠĠĠĠĠĠĠĠĠ Ġrequest Permissions ( Permissions Helper . permission For Storage (), ĠPermissions Helper . PERMISSION S _ STORAGE _ REQUEST ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn Ġtrue ĊĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠLog . d ( tag , Ġ" read Ġpermission Ġgranted ") ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġfalse ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġon Request Permissions Result ( request Code : ĠInt , Ġpermissions : ĠArray < String >, Ġgrant Results : ĠInt Array ) Ġ{ ĊĠĠĠĠĠĠĠ Ġwhen Ġ( request Code ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠPermissions Helper . PERMISSION S _ STORAGE _ REQUEST Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( Permissions Helper . result For Calling Permissions ( permissions , Ġgrant Results )) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLog . d ( tag , Ġ" read Ġpermission Ġgranted ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġopen File Explorer () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . makeText ( this @ Message Composer Activity , ĠgetString ( R . string . post _ message _ attach _ permission _ error ), ĠToast . LENGTH _ LONG ). show () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġclass ĠUpload Attachments Adapter ( private Ġval Ġon Attachment Cross Click : Ġ( File ) Ġ-> ĠUnit ) Ġ: ĠRecyclerView . Adapter < Upload Attachments Adapter . Attachment ViewHolder >() Ġ{ ĊĠĠĠĠĠĠĠ Ġvar Ġattached Files : ĠMutable List < File > Ġ= Ġmutable ListOf () ĊĠĠĠĠĠĠĠ Ġoverride Ġfun ĠonCreate ViewHolder ( parent : ĠViewGroup , Ġview Type : ĠInt ): ĠUpload Attachments Adapter . Attachment ViewHolder Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġbinding Ġ= ĠListItem Upload Attachment Binding . inflate ( LayoutInflater . from ( parent . context ), Ġparent , Ġfalse ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn ĠAttachment ViewHolder ( binding , Ġon Attachment Cross Click ) ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġoverride Ġfun ĠgetItem Count (): ĠInt Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn Ġattached Files . size ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġoverride Ġfun Ġon Bind ViewHolder ( holder : ĠAttachment ViewHolder , Ġposition : ĠInt ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġholder . bind ( attached Files [ position ]) ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġinner Ġclass ĠAttachment ViewHolder ( private Ġval Ġbinding : ĠListItem Upload Attachment Binding , Ġprivate Ġval Ġon Attachment Cross Click : Ġ( File ) Ġ-> ĠUnit ) Ġ: ĠRecyclerView . ViewHolder ( binding . root ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġinit Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbinding . button Layout . setOnClickListener Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġon Attachment Cross Click ( attached Files [ adapter Position ]) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġfun Ġbind ( file : ĠFile ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbinding . name . text Ġ= Ġfile . name ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbinding . path . text Ġ= Ġfile . path ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} Ċ }