Skip to content

Commit 1a7bae8

Browse files
Add extensive logging for notification and accessibility flows
This commit introduces detailed logging across multiple files to help diagnose two reported regressions: 1. Failure to navigate to Accessibility Settings when the service is off and the 'Send' button is pressed. 2. The stop notification not appearing when an operation is running. Logging has been added to: - MenuScreen.kt: To trace the notification permission request flow initiated from the 'Try It' button, including rationale display and permission request calls. - PhotoReasoningViewModel.kt: To confirm that the flag to show the stop notification is being set. - MainActivity.kt: To track the observation of the notification display flag and the invocation of notification utility functions. - NotificationUtil.kt: To log the process of showing a notification, including the crucial permission check. The existing code for accessibility navigation was reviewed and appears logically correct. These logs will help confirm if the issue lies in the execution flow or permission states.
1 parent d24c04f commit 1a7bae8

4 files changed

Lines changed: 57 additions & 41 deletions

File tree

app/src/main/kotlin/com/google/ai/sample/MainActivity.kt

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -449,9 +449,12 @@ class MainActivity : ComponentActivity() {
449449
if (photoReasoningViewModel != null) {
450450
lifecycleScope.launch {
451451
photoReasoningViewModel!!.showStopNotificationFlow.collect { show ->
452+
Log.d(TAG, "showStopNotificationFlow collected value: $show")
452453
if (show) {
454+
Log.d(TAG, "Calling showStopOperationNotification()")
453455
showStopOperationNotification()
454456
} else {
457+
Log.d(TAG, "Calling cancelStopOperationNotification()")
455458
cancelStopOperationNotification()
456459
}
457460
}
@@ -462,7 +465,9 @@ class MainActivity : ComponentActivity() {
462465
}
463466

464467
fun showStopOperationNotification() {
468+
Log.d(TAG, "MainActivity.showStopOperationNotification() entered.")
465469
NotificationUtil.showStopNotification(this)
470+
Log.d(TAG, "MainActivity.showStopOperationNotification() finished call to NotificationUtil.")
466471
}
467472

468473
fun cancelStopOperationNotification() {

app/src/main/kotlin/com/google/ai/sample/MenuScreen.kt

Lines changed: 26 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ import android.widget.Toast
3838
import android.Manifest // For Manifest.permission.POST_NOTIFICATIONS
3939
import androidx.compose.material3.AlertDialog // For the rationale dialog
4040
import androidx.compose.runtime.saveable.rememberSaveable
41+
import android.util.Log
4142

4243
data class MenuItem(
4344
val routeId: String,
@@ -192,19 +193,25 @@ fun MenuScreen(
192193
} else {
193194
if (menuItem.routeId == "photo_reasoning") {
194195
val mainActivity = context as? MainActivity
195-
if (mainActivity != null && !mainActivity.isNotificationPermissionGranted()) {
196-
// Check if rationale should be shown
197-
if (mainActivity.shouldShowRequestPermissionRationale(Manifest.permission.POST_NOTIFICATIONS) && !mainActivity.hasShownNotificationRationale()) {
198-
showRationaleDialogForPhotoReasoning = true
199-
// onItemClicked will be called from the dialog's OK button or if rationale is not shown
196+
if (mainActivity != null) { // Ensure mainActivity is not null
197+
if (!mainActivity.isNotificationPermissionGranted()) {
198+
Log.d("MenuScreen", "Notification permission NOT granted.")
199+
if (mainActivity.shouldShowRequestPermissionRationale(Manifest.permission.POST_NOTIFICATIONS) && !mainActivity.hasShownNotificationRationale()) {
200+
Log.d("MenuScreen", "Showing notification rationale dialog.")
201+
showRationaleDialogForPhotoReasoning = true
202+
// onItemClicked will be called from dialog
203+
} else {
204+
Log.d("MenuScreen", "Rationale not needed or already handled. Requesting permission directly.")
205+
mainActivity.requestNotificationPermission()
206+
onItemClicked(menuItem.routeId) // Proceed to navigate
207+
}
200208
} else {
201-
// Rationale not needed or already shown and dismissed, directly request permission
202-
mainActivity.requestNotificationPermission()
209+
Log.d("MenuScreen", "Notification permission ALREADY granted.")
203210
onItemClicked(menuItem.routeId) // Proceed to navigate
204211
}
205212
} else {
206-
// Permission already granted or not on Android 13+ or mainActivity is null
207-
onItemClicked(menuItem.routeId) // Proceed to navigate
213+
Log.e("MenuScreen", "MainActivity instance is null. Cannot check/request permission.")
214+
onItemClicked(menuItem.routeId) // Proceed to navigate anyway
208215
}
209216
} else {
210217
// For other menu items, navigate directly
@@ -311,24 +318,26 @@ fun MenuScreen(
311318
confirmButton = {
312319
TextButton(
313320
onClick = {
321+
Log.d("MenuScreen", "Rationale dialog OK clicked.")
314322
showRationaleDialogForPhotoReasoning = false
315323
mainActivity?.setNotificationRationaleShown(true)
324+
Log.d("MenuScreen", "Requesting notification permission from rationale dialog.")
316325
mainActivity?.requestNotificationPermission()
317-
mainActivity?.let { onItemClicked("photo_reasoning") } // Proceed to navigate
326+
// Log after to see if it's called immediately or if requestNotificationPermission is suspending (it's not)
327+
Log.d("MenuScreen", "Navigating to photo_reasoning after rationale OK.")
328+
mainActivity?.let { onItemClicked("photo_reasoning") }
318329
}
319-
) {
320-
Text("OK")
321-
}
330+
) { Text("OK") }
322331
},
323332
dismissButton = {
324333
TextButton(
325334
onClick = {
335+
Log.d("MenuScreen", "Rationale dialog Cancel clicked or dismissed.")
326336
showRationaleDialogForPhotoReasoning = false
327-
mainActivity?.let { onItemClicked("photo_reasoning") } // Proceed to navigate even on cancel
337+
Log.d("MenuScreen", "Navigating to photo_reasoning after rationale cancel/dismiss.")
338+
mainActivity?.let { onItemClicked("photo_reasoning") }
328339
}
329-
) {
330-
Text("Cancel")
331-
}
340+
) { Text("Cancel") }
332341
}
333342
)
334343
}

app/src/main/kotlin/com/google/ai/sample/feature/multimodal/PhotoReasoningViewModel.kt

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -106,9 +106,12 @@ class PhotoReasoningViewModel(
106106
userInput: String,
107107
selectedImages: List<Bitmap>
108108
) {
109+
Log.d(TAG, "reason() called. User input: '$userInput', Image count: ${selectedImages.size}")
109110
_uiState.value = PhotoReasoningUiState.Loading
110-
_showStopNotificationFlow.value = true // Show notification when loading starts
111-
stopExecutionFlag.set(false) // Reset flag at the beginning of a new reason call
111+
Log.d(TAG, "Setting _showStopNotificationFlow to true")
112+
_showStopNotificationFlow.value = true
113+
Log.d(TAG, "_showStopNotificationFlow value is now: ${_showStopNotificationFlow.value}")
114+
stopExecutionFlag.set(false)
112115

113116
val prompt = "FOLLOW THE INSTRUCTIONS STRICTLY: $userInput"
114117

app/src/main/kotlin/com/google/ai/sample/util/NotificationUtil.kt

Lines changed: 21 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,8 @@ import androidx.core.app.NotificationCompat
1313
import androidx.core.app.NotificationManagerCompat
1414
import androidx.core.content.ContextCompat
1515
import com.google.ai.sample.MainActivity
16+
import android.os.Build // Added import
17+
import android.util.Log // Added import
1618
// Import R class if needed for custom drawables, for android.R.drawable it's not needed.
1719
// import com.google.ai.sample.R
1820

@@ -22,7 +24,7 @@ object NotificationUtil {
2224
const val CHANNEL_NAME = "Screen Operator Controls"
2325
const val NOTIFICATION_ID = 1001
2426
const val ACTION_STOP_OPERATION = "com.google.ai.sample.ACTION_STOP_OPERATION"
25-
private const val TAG = "NotificationUtil"
27+
private const val TAG = "NotificationUtil" // Ensure TAG is defined
2628

2729
fun createNotificationChannel(context: Context) {
2830
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
@@ -41,6 +43,7 @@ object NotificationUtil {
4143
}
4244

4345
fun showStopNotification(context: Context) {
46+
Log.d(TAG, "NotificationUtil.showStopNotification() entered.")
4447
// Create an Intent for MainActivity
4548
val intent = Intent(context, MainActivity::class.java).apply {
4649
action = ACTION_STOP_OPERATION
@@ -74,31 +77,27 @@ object NotificationUtil {
7477

7578
val notificationManager = NotificationManagerCompat.from(context)
7679

77-
// Check for notification permission on Android 13+
78-
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
79-
if (ContextCompat.checkSelfPermission(context, Manifest.permission.POST_NOTIFICATIONS) ==
80-
PackageManager.PERMISSION_GRANTED
81-
) {
82-
try {
83-
notificationManager.notify(NOTIFICATION_ID, notificationBuilder.build())
84-
Log.d(TAG, "Stop notification shown.")
85-
} catch (e: SecurityException) {
86-
Log.e(TAG, "SecurityException while showing notification, even though permission was granted.", e)
87-
}
88-
} else {
89-
Log.w(TAG, "Cannot show stop notification: POST_NOTIFICATIONS permission not granted.")
90-
// Optionally, inform the user via a Toast or other means if this is critical
91-
// Toast.makeText(context, "Notification permission needed to show stop control.", Toast.LENGTH_LONG).show()
92-
}
80+
val permissionGranted = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
81+
ContextCompat.checkSelfPermission(context, Manifest.permission.POST_NOTIFICATIONS) == PackageManager.PERMISSION_GRANTED
9382
} else {
94-
// For older versions, permission is not needed at runtime in this manner
83+
true // Effectively granted for older versions
84+
}
85+
Log.d(TAG, "Notification permission granted: $permissionGranted (API Level: ${Build.VERSION.SDK_INT})")
86+
87+
if (permissionGranted) {
9588
try {
89+
Log.d(TAG, "Attempting to show notification (ID: $NOTIFICATION_ID).")
9690
notificationManager.notify(NOTIFICATION_ID, notificationBuilder.build())
97-
Log.d(TAG, "Stop notification shown (pre-Android 13).")
98-
} catch (e: Exception) {
99-
// Catch any other potential exceptions, though less likely for notifications on older versions
100-
Log.e(TAG, "Exception while showing notification (pre-Android 13).", e)
91+
Log.d(TAG, "Stop notification shown successfully.")
92+
} catch (e: SecurityException) {
93+
Log.e(TAG, "SecurityException while showing notification, even though permission was granted.", e)
94+
} catch (e: Exception) { // Catch any other exception during notify
95+
Log.e(TAG, "Generic Exception while calling notificationManager.notify().", e)
10196
}
97+
} else {
98+
Log.w(TAG, "Cannot show stop notification: POST_NOTIFICATIONS permission not granted.")
99+
// Optionally, inform the user via a Toast or other means if this is critical
100+
// Toast.makeText(context, "Notification permission needed to show stop control.", Toast.LENGTH_LONG).show()
102101
}
103102
}
104103

0 commit comments

Comments
 (0)