/* Ċ Ġ* ĠCopyright Ġ 2 0 2 0 ĠThe ĠAndroid ĠOpen ĠSource ĠProject Ċ Ġ* Ċ Ġ* Ġ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 Ċ Ġ* Ċ Ġ* ĠĠĠĠ Ġhttps :// 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 . wen . ex posure Ċ Ċ import Ġandroid . Manifest Ċ import Ġandroid . annotation . Suppress Lint Ċ import Ġandroid . content . Content Values Ċ import Ġandroid . content . pm . PackageManager Ċ import Ġandroid . os . Bundle Ċ import Ġandroid . os . System Clock Ċ import Ġandroid . provider . Media Store Ċ import Ġandroid . util . Display Metrics Ċ import Ġandroid . util . Log Ċ import Ġandroid . util . Rational Ċ import Ġandroid . view . View Ċ import Ġandroid . widget . Image Button Ċ import Ġandroid . widget . Toast Ċ import Ġandroidx . activity . result . Activity Result Callback Ċ import Ġandroidx . activity . result . contract . Activity Result Contracts . Request Multiple Permissions Ċ import Ġandroidx . appcompat . app . AppCompatActivity Ċ import Ġandroidx . camera . core . AspectRatio Ċ import Ġandroidx . camera . core . Camera Ċ import Ġandroidx . camera . core . Camera Info Unavailable Exception Ċ import Ġandroidx . camera . core . Camera Selector Ċ import Ġandroidx . camera . core . Image Capture Ċ import Ġandroidx . camera . core . Image Capture Exception Ċ import Ġandroidx . camera . core . Preview Ċ import Ġandroidx . camera . core . UseCase Group Ċ import Ġandroidx . camera . core . View Port Ċ import Ġandroidx . camera . lifecycle . Process Camera Provider Ċ import Ġandroidx . camera . view . Preview View Ċ import Ġandroidx . constraint layout . widget . Constraint Layout Ċ import Ġandroidx . core . content . Context Compat Ċ import Ġcom . google . android . material . slider . Slider Ċ import Ġjava . util . concurrent . ExecutorService Ċ import Ġjava . util . concurrent . Executors Ċ import Ġkotlin . math . abs Ċ import Ġkotlin . math . max Ċ import Ġkotlin . math . min Ċ import Ġkotlin . math . round ToInt Ċ Ċ private Ġconst Ġval ĠI MM ER SIVE _ FLAG _ TIMEOUT Ġ= Ġ 5 0 0 L Ċ Ċ /** ĠCombin ation Ġof Ġall Ġflags Ġrequired Ġto Ġput Ġactivity Ġinto Ġimm ers ive Ġmode Ġ*/ Ċ private Ġconst Ġval ĠFLAGS _ FULL SCREEN Ġ= ĊĠĠĠ ĠView . SYSTEM _ UI _ FLAG _ LOW _ PROFILE Ġor ĊĠĠĠĠĠ ĠView . SYSTEM _ UI _ FLAG _ FULL SCREEN Ġor ĊĠĠĠĠĠ ĠView . SYSTEM _ UI _ FLAG _ LAYOUT _ ST ABLE Ġor ĊĠĠĠĠĠ ĠView . SYSTEM _ UI _ FLAG _ IM MER SIVE _ STICK Y Ġor ĊĠĠĠĠĠ ĠView . SYSTEM _ UI _ FLAG _ LAYOUT _ HIDE _ NAV IG ATION Ġor ĊĠĠĠĠĠ ĠView . SYSTEM _ UI _ FLAG _ HIDE _ NAV IG ATION Ċ Ċ private Ġval ĠREQUIRED _ PERMISSION S Ġ= ĠarrayOf ( ĊĠĠĠ ĠManifest . permission . CAMERA , Ċ ) Ċ Ċ /** Ċ Ġ* ĠMain Ġentry Ġpoint Ġinto Ġour Ġapp . Ċ Ġ*/ Ċ class ĠMainActivity Ġ: ĠAppCompatActivity () Ġ{ ĊĠĠĠ Ġprivate Ġlateinit Ġvar Ġcontainer : ĠConstraint Layout ĊĠĠĠ Ġprivate Ġlateinit Ġvar Ġview Finder : ĠPreview View ĊĊĠĠĠ Ġ/** ĠBlock ing Ġcamera Ġoperations Ġare Ġperformed Ġusing Ġthis Ġexecutor Ġ*/ ĊĠĠĠ Ġprivate Ġlateinit Ġvar Ġcamera Executor : ĠExecutor Service ĊĊĠĠĠ Ġprivate Ġvar Ġlens Facing : ĠInt Ġ= ĠCamera Selector . LEN S _ F ACING _ BACK ĊĠĠĠ Ġprivate Ġvar Ġpreview : ĠPreview ? Ġ= Ġnull ĊĠĠĠ Ġprivate Ġvar Ġimage Capture : ĠImage Capture ? Ġ= Ġnull ĊĠĠĠ Ġprivate Ġvar Ġcamera : ĠCamera ? Ġ= Ġnull ĊĠĠĠ Ġprivate Ġvar Ġcamera Provider : ĠProcess Camera Provider ? Ġ= Ġnull ĊĠĠĠ Ġprivate Ġvar Ġslider : ĠSlider ? Ġ= Ġnull ĊĊĠĠĠ Ġoverride Ġfun ĠonCreate ( savedInstanceState : ĠBundle ?) Ġ{ ĊĠĠĠĠĠĠĠ Ġsuper . onCreate ( savedInstanceState ) ĊĠĠĠĠĠĠĠ ĠsetContentView ( R . layout . activity _ main ) ĊĠĠĠĠĠĠĠ Ġcontainer Ġ= ĠfindViewById ( R . id . main _ container ) ĊĠĠĠĠĠĠĠ Ġview Finder Ġ= Ġcontainer . findViewById ( R . id . view _ finder ) ĊĊĠĠĠĠĠĠĠ Ġ// ĠInitialize Ġour Ġbackground Ġexecutor ĊĠĠĠĠĠĠĠ Ġcamera Executor Ġ= ĠExec utors . new Single Thread Executor () ĊĊĠĠĠĠĠĠĠ Ġsetup Permissions () ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠRequest Ġpermission Ġif Ġmissing . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġsetup Permissions () Ġ{ ĊĠĠĠĠĠĠĠ Ġif Ġ( is Permission Missing ()) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġpermission Launcher Ġ= Ġregister For Activity Result ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠRequest Multiple Permissions (), ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠActivity Result Callback < Map < String ?, ĠBoolean ? >> Ġ{ Ġresult : ĠMap < String ?, ĠBoolean ?> Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( permission Ġin ĠREQUIRED _ PERMISSION S ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġresult [ permission ]?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ(! it ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . makeText ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġapplication Context , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ" Camera Ġpermission Ġdenied .", ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . LENGTH _ SHORT ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ). show () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfinish () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġreturn @ Activity Result Callback ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġstart () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ}) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġpermission Launcher . launch ( REQUIRED _ PERMISSION S ) ĊĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠPermissions Ġalready Ġgranted . ĠStart Ġcamera . ĊĠĠĠĠĠĠĠĠĠĠĠ Ġstart () ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġis Permission Missing (): ĠBoolean Ġ{ ĊĠĠĠĠĠĠĠ Ġfor Ġ( permission Ġin ĠREQUIRED _ PERMISSION S ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( Context Compat . check Self Permission ( this , Ġpermission ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ!= ĠPackage Manager . PERMISSION _ GRAN TED ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġreturn Ġtrue ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġfalse ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġstart () Ġ{ ĊĠĠĠĠĠĠĠ Ġ// ĠWait Ġfor Ġthe Ġviews Ġto Ġbe Ġproperly Ġla id Ġout ĊĠĠĠĠĠĠĠ Ġview Finder . post Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠBuild ĠUI Ġcontrols ĊĠĠĠĠĠĠĠĠĠĠĠ Ġupdate Camera Ui () ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠSet Ġup Ġthe Ġcamera Ġand Ġits Ġuse Ġcases ĊĠĠĠĠĠĠĠĠĠĠĠ ĠsetUp Camera () ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĠInitialize ĠCamera X , Ġand Ġprepare Ġto Ġbind Ġthe Ġcamera Ġuse Ġcases Ġ Ġ*/ ĊĠĠĠ Ġprivate Ġfun ĠsetUp Camera () Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġcamera Provider Future Ġ= ĠProcess Camera Provider . getInstance ( this ) ĊĠĠĠĠĠĠĠ Ġcamera Provider Future . addListener ({ ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠCamera Provider ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcamera Provider Ġ= Ġcamera Provider Future . get () ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠSelect Ġlens Facing Ġdepending Ġon Ġthe Ġavailable Ġcameras ĊĠĠĠĠĠĠĠĠĠĠĠ Ġlens Facing Ġ= Ġwhen Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcamera Provider . has Back Camera () Ġ-> ĠCamera Selector . LEN S _ F ACING _ BACK ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcamera Provider . has Front Camera () Ġ-> ĠCamera Selector . LEN S _ F ACING _ FRONT ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġelse Ġ-> Ġthrow ĠIllegalStateException (" Back Ġand Ġfront Ġcamera Ġare Ġunavailable ") ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠEnable Ġor Ġdisable Ġswitching Ġbetween Ġcameras ĊĠĠĠĠĠĠĠĠĠĠĠ Ġupdate Camera Switch Button () ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠBuild Ġand Ġbind Ġthe Ġcamera Ġuse Ġcases ĊĠĠĠĠĠĠĠĠĠĠĠ Ġbind Camera Use Cases () ĊĊĠĠĠĠĠĠĠ Ġ}, ĠContext Compat . get Main Executor ( this )) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĠEnabled Ġor Ġdisabled Ġa Ġbutton Ġto Ġswitch Ġcameras Ġdepending Ġon Ġthe Ġavailable Ġcameras Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġupdate Camera Switch Button () Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġswitch Cam eras Button Ġ= Ġcontainer . findViewById < Image Button >( R . id . camera _ switch _ button ) ĊĠĠĠĠĠĠĠ Ġtry Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġswitch Cam eras Button . isEnabled Ġ= ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcamera Provider . has Back Camera () Ġ&& Ġcamera Provider . has Front Camera () ĊĠĠĠĠĠĠĠ Ġ} Ġcatch Ġ( exception : ĠCamera Info Unavailable Exception ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġswitch Cam eras Button . isEnabled Ġ= Ġfalse ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĠReturns Ġtrue Ġif Ġthe Ġdevice Ġhas Ġan Ġavailable Ġback Ġcamera . ĠFalse Ġotherwise Ġ*/ ĊĠĠĠ Ġprivate Ġfun ĠProcess Camera Provider ?. has Back Camera (): ĠBoolean Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġthis ?. has Camera ( Camera Selector . DEFAULT _ BACK _ CAMERA ) Ġ?: Ġfalse ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĠReturns Ġtrue Ġif Ġthe Ġdevice Ġhas Ġan Ġavailable Ġfront Ġcamera . ĠFalse Ġotherwise Ġ*/ ĊĠĠĠ Ġprivate Ġfun ĠProcess Camera Provider ?. has Front Camera (): ĠBoolean Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġthis ?. has Camera ( Camera Selector . DEFAULT _ FRONT _ CAMERA ) Ġ?: Ġfalse ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĠMethod Ġused Ġto Ġre - draw Ġthe Ġcamera ĠUI Ġcontrols , Ġcalled Ġevery Ġtime Ġconfiguration Ġchanges . Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġupdate Camera Ui () Ġ{ ĊĊĠĠĠĠĠĠĠ Ġ// ĠRemove Ġprevious ĠUI Ġif Ġany ĊĠĠĠĠĠĠĠ Ġcontainer . findViewById < Constraint Layout >( R . id . camera _ ui _ container )?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcontainer . remove View ( it ) ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġ// ĠInf late Ġa Ġnew Ġview Ġcontaining Ġall ĠUI Ġfor Ġcontrolling Ġthe Ġcamera ĊĠĠĠĠĠĠĠ Ġval Ġcontrols Ġ= ĠView . inflate ( this , ĠR . layout . camera _ ui _ container , Ġcontainer ) ĊĠĠĠĠĠĠĠ Ġslider Ġ= Ġcontrols . findViewById ( R . id . slider ) Ġas ĠSlider ĊĊĠĠĠĠĠĠĠ Ġ// ĠListener Ġfor Ġbutton Ġused Ġto Ġcapture Ġphoto ĊĠĠĠĠĠĠĠ Ġcontrols . findViewById < Image Button >( R . id . camera _ capture _ button ). setOnClickListener Ġ{ ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠGet Ġa Ġstable Ġreference Ġof Ġthe Ġmod ifiable Ġimage Ġcapture Ġuse Ġcase ĊĠĠĠĠĠĠĠĠĠĠĠ Ġimage Capture ?. let Ġ{ Ġimage Capture Ġ-> ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval ĠoutputFile Options Ġ= ĠImage Capture . OutputFile Options . Builder ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcontent Resolver , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠMedia Store . Images . Media . EXTERNAL _ CONTENT _ URI , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠContent Values (). apply Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġput ( Media Store . Media Columns . MIME _ TYPE , Ġ" image / jpeg ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ). build () ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠSetup Ġimage Ġcapture Ġlistener Ġwhich Ġis Ġtriggered Ġafter Ġphoto Ġhas Ġbeen Ġtaken ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġimage Capture . take Picture ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠoutputFile Options , Ġcamera Executor , Ġobject Ġ: ĠImage Capture . On Image Saved Callback Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġstart Capture Time Ġ= ĠSystem Clock . elapsed Realtime () ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġoverride Ġfun ĠonError ( exc : ĠImage Capture Exception ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLog . e ( TAG , Ġ" Photo Ġcapture Ġfailed : Ġ${ exc . message }", Ġexc ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcontainer . post Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . makeText ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġapplication Context , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ" Failed Ġto Ġsave Ġimage . Ġ${ exc . message }", ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . LENGTH _ SHORT ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ). show () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġoverride Ġfun Ġon Image Saved ( output : ĠImage Capture . OutputFile Results ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLog . d ( TAG , Ġ" Photo Ġcapture Ġsucceeded : Ġ${ output . saved Uri }") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcontainer . post Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . makeText ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġapplication Context , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ" Image Ġcaptured Ġin Ġ${ System Clock . elapsed Realtime () Ġ- Ġstart Capture Time } Ġms ", ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠToast . LENGTH _ SHORT ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ). show () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ}) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġ// ĠSetup Ġfor Ġbutton Ġused Ġto Ġswitch Ġcameras ĊĠĠĠĠĠĠĠ Ġcontrols . findViewById < Image Button >( R . id . camera _ switch _ button ). let Ġ{ ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠDisable Ġthe Ġbutton Ġuntil Ġthe Ġcamera Ġis Ġset Ġup ĊĠĠĠĠĠĠĠĠĠĠĠ Ġit . isEnabled Ġ= Ġfalse ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠListener Ġfor Ġbutton Ġused Ġto Ġswitch Ġcameras . ĠOnly Ġcalled Ġif Ġthe Ġbutton Ġis Ġenabled ĊĠĠĠĠĠĠĠĠĠĠĠ Ġit . setOnClickListener Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġlens Facing Ġ= Ġif Ġ( Camera Selector . LEN S _ F ACING _ FRONT Ġ== Ġlens Facing ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠCamera Selector . LEN S _ F ACING _ BACK ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} Ġelse Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠCamera Selector . LEN S _ F ACING _ FRONT ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠRe - bind Ġuse Ġcases Ġto Ġupdate Ġselected Ġcamera ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġbind Camera Use Cases () ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ@ Suppress Lint (" Unsafe Opt In Usage Error ") ĊĠĠĠ Ġprivate Ġfun ĠSlider . setup ( camera : ĠCamera ) Ġ{ ĊĠĠĠĠĠĠĠ Ġcamera . camera Info . ex posure State . let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġvalue Ġ= Ġit . ex posure Comp ensation Index . toFloat () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġvalue From Ġ= Ġit . ex posure Comp ensation Range . lower . toFloat () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġvalue To Ġ= Ġit . ex posure Comp ensation Range . upper . toFloat () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġadd On ChangeListener Ġ{ Ġ_, Ġvalue , Ġ_ Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcamera . camera Control . set Exposure Comp ensation Index ( value . round ToInt ()) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġset Label Formatter Ġ{ Ġvalue : ĠFloat Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ"% . 2 f ". format (( value Ġ* Ġit . ex posure Comp ensation Step . toFloat ())) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĠDeclare Ġand Ġbind Ġpreview Ġand Ġcapture Ġuse Ġcases Ġ*/ ĊĠĠĠ Ġ@ Suppress Lint (" Unsafe Opt In Usage Error ") ĊĠĠĠ Ġprivate Ġfun Ġbind Camera Use Cases () Ġ{ ĊĊĠĠĠĠĠĠĠ Ġ// ĠGet Ġscreen Ġmetrics Ġused Ġto Ġsetup Ġcamera Ġfor Ġfull Ġscreen Ġresolution ĊĠĠĠĠĠĠĠ Ġval Ġmetrics Ġ= ĠDisplay Metrics (). also Ġ{ Ġview Finder . display . get Real Metrics ( it ) Ġ} ĊĠĠĠĠĠĠĠ ĠLog . d ( TAG , Ġ" Screen Ġmetrics : Ġ${ metrics . width Pixels } Ġx Ġ${ metrics . height Pixels }") ĊĊĠĠĠĠĠĠĠ Ġval Ġscreen AspectRatio Ġ= Ġaspect Ratio ( metrics . width Pixels , Ġmetrics . height Pixels ) ĊĠĠĠĠĠĠĠ ĠLog . d ( TAG , Ġ" Preview Ġaspect Ġratio : Ġ$ screen AspectRatio ") ĊĊĠĠĠĠĠĠĠ Ġ// ĠCamera Provider ĊĠĠĠĠĠĠĠ Ġval Ġcamera Provider Ġ= Ġcamera Provider ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ?: Ġthrow ĠIllegalStateException (" Camera Ġinitialization Ġfailed .") ĊĊĠĠĠĠĠĠĠ Ġ// ĠCamera Selector ĊĠĠĠĠĠĠĠ Ġval Ġcamera Selector Ġ= ĠCamera Selector . Builder (). require Lens Facing ( lens Facing ). build () ĊĊĠĠĠĠĠĠĠ Ġ// ĠPreview ĊĠĠĠĠĠĠĠ Ġpreview Ġ= ĠPreview . Builder () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠWe Ġrequest Ġaspect Ġratio Ġbut Ġno Ġresolution ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ. setTarget AspectRatio ( screen AspectRatio ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ. build () ĊĊĠĠĠĠĠĠĠ Ġ// ĠImage Capture ĊĠĠĠĠĠĠĠ Ġimage Capture Ġ= ĠImage Capture . Builder () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ. set Capture Mode ( Image Capture . CAPTURE _ MODE _ MIN IM IZE _ LAT ENCY ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠWe Ġrequest Ġaspect Ġratio Ġbut Ġno Ġresolution Ġto Ġmatch Ġpreview Ġconfig , Ġbut Ġletting ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠCamera X Ġoptimize Ġfor Ġwhatever Ġspecific Ġresolution Ġbest Ġfits Ġour Ġuse Ġcases ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ. setTarget AspectRatio ( screen AspectRatio ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ. build () ĊĊĠĠĠĠĠĠĠ Ġ// ĠMust Ġun bind Ġthe Ġuse - cases Ġbefore Ġre binding Ġthem ĊĠĠĠĠĠĠĠ Ġcamera Provider . unbind All () ĊĊĠĠĠĠĠĠĠ Ġtry Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġuse Case Group Builder Ġ= ĠUse Case Group . Builder (). setView Port ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠView Port . Builder ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠRational ( view Finder . width , Ġview Finder . height ), ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġview Finder . display . rotation ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ). set Scale Type ( View Port . FILL _ CENTER ). build () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ). apply Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠlistOf NotNull ( preview , Ġimage Capture ). forEach Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġadd UseCase ( it ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠA Ġvariable Ġnumber Ġof Ġuse - cases Ġcan Ġbe Ġpassed Ġhere Ġ- ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// Ġcamera Ġprovides Ġaccess Ġto ĠCamera Control Ġ& ĠCamera Info ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcamera Ġ= Ġcamera Provider . bind To Lifecycle ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġthis , Ġcamera Selector , Ġuse Case Group Builder . build () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ) ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠUpdate Ġthe ĠEV Ġslider ĠUI Ġaccording Ġto Ġthe ĠCamera Info ĊĠĠĠĠĠĠĠĠĠĠĠ Ġslider ?. setup ( camera !! ) ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġ// ĠAttach Ġthe Ġview finder 's Ġsurface Ġprovider Ġto Ġpreview Ġuse Ġcase ĊĠĠĠĠĠĠĠĠĠĠĠ Ġpreview ?. set Surface Provider ( view Finder . surface Provider ) ĊĠĠĠĠĠĠĠ Ġ} Ġcatch Ġ( exc : ĠException ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ ĠLog . e ( TAG , Ġ" Use Ġcase Ġbinding Ġfailed ", Ġexc ) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* Ġ ĠDetect ing Ġthe Ġmost Ġsuitable Ġratio Ġfor Ġdimensions Ġprovided Ġin Ġ@ params Ġby Ġcounting Ġabsolute ĊĠĠĠĠ Ġ* Ġ Ġof Ġpreview Ġratio Ġto Ġone Ġof Ġthe Ġprovided Ġvalues . ĊĠĠĠĠ Ġ* ĊĠĠĠĠ Ġ* Ġ Ġ@ param Ġwidth Ġ- Ġpreview Ġwidth ĊĠĠĠĠ Ġ* Ġ Ġ@ param Ġheight Ġ- Ġpreview Ġheight ĊĠĠĠĠ Ġ* Ġ Ġ@ return Ġsuitable Ġaspect Ġratio ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġaspect Ratio ( width : ĠInt , Ġheight : ĠInt ): ĠInt Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġpreview Ratio Ġ= Ġmax ( width , Ġheight ). toDouble () Ġ/ Ġmin ( width , Ġheight ) ĊĠĠĠĠĠĠĠ Ġif Ġ( abs ( preview Ratio Ġ- ĠR AT IO _ 4 _ 3 _ VALUE ) Ġ<= Ġabs ( preview Ratio Ġ- ĠR AT IO _ 1 6 _ 9 _ VALUE )) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn ĠAs pect Ratio . RATIO _ 4 _ 3 ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġreturn ĠAs pect Ratio . RATIO _ 1 6 _ 9 ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġon Resume () Ġ{ ĊĠĠĠĠĠĠĠ Ġsuper . on Resume () ĊĠĠĠĠĠĠĠ Ġ// ĠBefore Ġsetting Ġfull Ġscreen Ġflags , Ġwe Ġmust Ġwait Ġa Ġbit Ġto Ġlet ĠUI Ġset tle ; Ġotherwise , Ġwe Ġmay ĊĠĠĠĠĠĠĠ Ġ// Ġbe Ġtrying Ġto Ġset Ġapp Ġto Ġimm ers ive Ġmode Ġbefore Ġit 's Ġready Ġand Ġthe Ġflags Ġdo Ġnot Ġstick ĊĠĠĠĠĠĠĠ Ġcontainer . post Delayed ( ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ{ Ġcontainer . system Ui Visibility Ġ= ĠFLAGS _ FULL SCREEN Ġ}, ĊĠĠĠĠĠĠĠĠĠĠĠ ĠI MM ER SIVE _ FLAG _ TIMEOUT ĊĠĠĠĠĠĠĠ Ġ) ĊĊĠĠĠĠĠĠĠ Ġcamera ?. let Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġslider ?. setup ( it ) ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġon Destroy () Ġ{ ĊĠĠĠĠĠĠĠ Ġsuper . on Destroy () ĊĊĠĠĠĠĠĠĠ Ġ// ĠSh ut Ġdown Ġour Ġbackground Ġexecutor ĊĠĠĠĠĠĠĠ Ġcamera Executor . shutdown () ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġcompanion Ġobject Ġ{ ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠTAG Ġ= Ġ" Camera X Ev Sample " ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠR AT IO _ 4 _ 3 _ VALUE Ġ= Ġ 4 . 0 Ġ/ Ġ 3 . 0 ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠR AT IO _ 1 6 _ 9 _ VALUE Ġ= Ġ 1 6 . 0 Ġ/ Ġ 9 . 0 ĊĠĠĠ Ġ} Ċ } Ċ