@@ -19,59 +19,68 @@ package com.example.xr.projected
1919import android.os.Bundle
2020import androidx.activity.ComponentActivity
2121import androidx.activity.compose.setContent
22- import androidx.activity.viewModels
2322import androidx.compose.foundation.layout.Box
2423import androidx.compose.foundation.layout.fillMaxSize
2524import androidx.compose.runtime.Composable
2625import androidx.compose.runtime.getValue
26+ import androidx.compose.runtime.mutableStateOf
27+ import androidx.compose.runtime.setValue
2728import androidx.compose.ui.Alignment
2829import androidx.compose.ui.Modifier
29- import androidx.lifecycle.LifecycleOwner
3030import androidx.lifecycle.DefaultLifecycleObserver
31- import androidx.lifecycle.compose.collectAsStateWithLifecycle
31+ import androidx.lifecycle.LifecycleOwner
3232import androidx.lifecycle.lifecycleScope
3333import androidx.xr.glimmer.Button
3434import androidx.xr.glimmer.Card
3535import androidx.xr.glimmer.GlimmerTheme
3636import androidx.xr.glimmer.Text
3737import androidx.xr.glimmer.surface
3838import androidx.xr.projected.ProjectedDisplayController
39+ import androidx.xr.projected.ProjectedDeviceController
40+ import androidx.xr.projected.ProjectedDeviceController.Capability.Companion.CAPABILITY_VISUAL_UI
3941import androidx.xr.projected.experimental.ExperimentalProjectedApi
4042import kotlinx.coroutines.launch
4143
4244// [START androidxr_projected_ai_glasses_activity]
4345@OptIn(ExperimentalProjectedApi ::class )
4446class GlassesMainActivity : ComponentActivity () {
4547
48+ private var displayController: ProjectedDisplayController ? = null
49+ private var isVisualUiSupported by mutableStateOf(false )
50+ private var areVisualsOn by mutableStateOf(true )
51+
4652 override fun onCreate (savedInstanceState : Bundle ? ) {
4753 super .onCreate(savedInstanceState)
48- val viewModel: GlassesViewModel by viewModels()
54+
55+ lifecycle.addObserver(object : DefaultLifecycleObserver {
56+ override fun onDestroy (owner : LifecycleOwner ) {
57+ displayController?.close()
58+ displayController = null
59+ }
60+ })
4961
5062 lifecycleScope.launch {
51- val controller = ProjectedDisplayController .create(this @GlassesMainActivity)
63+ // [START androidxr_projected_device_capabilities_check]
64+ // Check device capabilities
65+ val projectedDeviceController = ProjectedDeviceController .create(this @GlassesMainActivity)
66+ isVisualUiSupported = projectedDeviceController.capabilities.contains(CAPABILITY_VISUAL_UI )
67+ // [END androidxr_projected_device_capabilities_check]
5268
69+ val controller = ProjectedDisplayController .create(this @GlassesMainActivity)
70+ displayController = controller
5371 val observer = GlassesLifecycleObserver (
5472 context = this @GlassesMainActivity,
5573 controller = controller,
56- onVisualsChanged = viewModel::updateVisuals
74+ onVisualsChanged = { visualsOn -> areVisualsOn = visualsOn }
5775 )
5876 lifecycle.addObserver(observer)
59-
60- // Cleanup observer to close the controller
61- lifecycle.addObserver(object : DefaultLifecycleObserver {
62- override fun onDestroy (owner : LifecycleOwner ) {
63- controller.close()
64- }
65- })
6677 }
6778
6879 setContent {
69- // [required] Use collectAsStateWithLifecycle for safe collection
70- val uiState by viewModel.uiState.collectAsStateWithLifecycle()
71-
7280 GlimmerTheme {
7381 HomeScreen (
74- visualsOn = uiState.areVisualsOn,
82+ areVisualsOn = areVisualsOn,
83+ isVisualUiSupported = isVisualUiSupported,
7584 onClose = { finish() }
7685 )
7786 }
@@ -83,7 +92,8 @@ class GlassesMainActivity : ComponentActivity() {
8392// [START androidxr_projected_ai_glasses_activity_homescreen]
8493@Composable
8594fun HomeScreen (
86- visualsOn : Boolean ,
95+ areVisualsOn : Boolean ,
96+ isVisualUiSupported : Boolean ,
8797 onClose : () -> Unit ,
8898 modifier : Modifier = Modifier
8999) {
@@ -93,19 +103,23 @@ fun HomeScreen(
93103 .fillMaxSize(),
94104 contentAlignment = Alignment .Center
95105 ) {
96- Card (
97- title = { Text (" Android XR" ) },
98- action = {
99- Button (onClick = onClose) {
100- Text (" Close" )
106+ if (isVisualUiSupported) {
107+ Card (
108+ title = { Text (" Android XR" ) },
109+ action = {
110+ Button (onClick = onClose) {
111+ Text (" Close" )
112+ }
113+ }
114+ ) {
115+ if (areVisualsOn) {
116+ Text (" Hello, AI Glasses!" )
117+ } else {
118+ Text (" Display is off. Audio guidance active." )
101119 }
102120 }
103- ) {
104- if (visualsOn) {
105- Text (" Hello, AI Glasses!" )
106- } else {
107- Text (" Display is off. Audio guidance active." )
108- }
121+ } else {
122+ Text (" Audio Guidance Mode Active" )
109123 }
110124 }
111125}
0 commit comments