From 271df2e720f7b23fa9896b97f3456ea7cab3d7e4 Mon Sep 17 00:00:00 2001 From: callebtc <93376500+callebtc@users.noreply.github.com> Date: Fri, 25 Jul 2025 19:17:36 +0200 Subject: [PATCH] on focus (#189) --- .../com/bitchat/android/ui/ChatViewModel.kt | 3 +- .../bitchat/android/ui/MeshDelegateHandler.kt | 29 ++++++++++++++++++- .../bitchat/android/ui/NotificationManager.kt | 14 +++++++++ .../bitchat/android/ui/PrivateChatManager.kt | 2 +- 4 files changed, 45 insertions(+), 3 deletions(-) diff --git a/app/src/main/java/com/bitchat/android/ui/ChatViewModel.kt b/app/src/main/java/com/bitchat/android/ui/ChatViewModel.kt index fda892db..c09789d3 100644 --- a/app/src/main/java/com/bitchat/android/ui/ChatViewModel.kt +++ b/app/src/main/java/com/bitchat/android/ui/ChatViewModel.kt @@ -55,7 +55,8 @@ class ChatViewModel( notificationManager = notificationManager, coroutineScope = viewModelScope, onHapticFeedback = { ChatViewModelUtils.triggerHapticFeedback(application.applicationContext) }, - getMyPeerID = { meshService.myPeerID } + getMyPeerID = { meshService.myPeerID }, + getMeshService = { meshService } ) // Expose state through LiveData (maintaining the same interface) diff --git a/app/src/main/java/com/bitchat/android/ui/MeshDelegateHandler.kt b/app/src/main/java/com/bitchat/android/ui/MeshDelegateHandler.kt index daf30451..1a75d94e 100644 --- a/app/src/main/java/com/bitchat/android/ui/MeshDelegateHandler.kt +++ b/app/src/main/java/com/bitchat/android/ui/MeshDelegateHandler.kt @@ -21,7 +21,8 @@ class MeshDelegateHandler( private val notificationManager: NotificationManager, private val coroutineScope: CoroutineScope, private val onHapticFeedback: () -> Unit, - private val getMyPeerID: () -> String + private val getMyPeerID: () -> String, + private val getMeshService: () -> Any ) : BluetoothMeshDelegate { override fun didReceiveMessage(message: BitchatMessage) { @@ -47,6 +48,11 @@ class MeshDelegateHandler( // Private message privateChatManager.handleIncomingPrivateMessage(message) + // Reactive read receipts: Send immediately if user is currently viewing this chat + message.senderPeerID?.let { senderPeerID -> + sendReadReceiptIfFocused(senderPeerID) + } + // Show notification with enhanced information - now includes senderPeerID message.senderPeerID?.let { senderPeerID -> // Use nickname if available, fall back to sender or senderPeerID @@ -153,5 +159,26 @@ class MeshDelegateHandler( return privateChatManager.isFavorite(peerID) } + /** + * Send read receipts reactively based on UI focus state. + * Uses same logic as notification system - send read receipt if user is currently + * viewing the private chat with this sender AND app is in foreground. + */ + private fun sendReadReceiptIfFocused(senderPeerID: String) { + // Get notification manager's focus state (mirror the notification logic) + val isAppInBackground = notificationManager.getAppBackgroundState() + val currentPrivateChatPeer = notificationManager.getCurrentPrivateChatPeer() + + // Send read receipt if user is currently focused on this specific chat + val shouldSendReadReceipt = !isAppInBackground && currentPrivateChatPeer == senderPeerID + + if (shouldSendReadReceipt) { + android.util.Log.d("MeshDelegateHandler", "Sending reactive read receipt for focused chat with $senderPeerID") + privateChatManager.sendReadReceiptsForPeer(senderPeerID, getMeshService()) + } else { + android.util.Log.d("MeshDelegateHandler", "Skipping read receipt - chat not focused (background: $isAppInBackground, current peer: $currentPrivateChatPeer, sender: $senderPeerID)") + } + } + // registerPeerPublicKey REMOVED - fingerprints now handled centrally in PeerManager } diff --git a/app/src/main/java/com/bitchat/android/ui/NotificationManager.kt b/app/src/main/java/com/bitchat/android/ui/NotificationManager.kt index 265ea48c..42028fff 100644 --- a/app/src/main/java/com/bitchat/android/ui/NotificationManager.kt +++ b/app/src/main/java/com/bitchat/android/ui/NotificationManager.kt @@ -306,6 +306,20 @@ class NotificationManager(private val context: Context) { return pendingNotifications.values.sumOf { it.size } } + /** + * Get app background state for reactive read receipts + */ + fun getAppBackgroundState(): Boolean { + return isAppInBackground + } + + /** + * Get current private chat peer for reactive read receipts + */ + fun getCurrentPrivateChatPeer(): String? { + return currentPrivateChatPeer + } + /** * Get pending notifications for debugging */ diff --git a/app/src/main/java/com/bitchat/android/ui/PrivateChatManager.kt b/app/src/main/java/com/bitchat/android/ui/PrivateChatManager.kt index b3a8aadf..0a79ee13 100644 --- a/app/src/main/java/com/bitchat/android/ui/PrivateChatManager.kt +++ b/app/src/main/java/com/bitchat/android/ui/PrivateChatManager.kt @@ -64,7 +64,7 @@ class PrivateChatManager( // Initialize chat if needed messageManager.initializePrivateChat(peerID) - + // Send read receipts for all unread messages from this peer sendReadReceiptsForPeer(peerID, meshService)