Support navigating back to MainActivity with no conversation selected.

This commit is contained in:
jeffrey-signal
2026-03-23 10:36:12 -04:00
committed by Cody Henthorne
parent 7a2eca3bd5
commit a588522c9b
3 changed files with 35 additions and 19 deletions

View File

@@ -90,6 +90,7 @@ import org.signal.core.ui.isSplitPane
import org.signal.core.ui.permissions.Permissions
import org.signal.core.util.Util
import org.signal.core.util.concurrent.LifecycleDisposable
import org.signal.core.util.getParcelableCompat
import org.signal.core.util.getSerializableCompat
import org.signal.core.util.logging.Log
import org.signal.donations.StripeApi
@@ -118,7 +119,6 @@ import org.thoughtcrime.securesms.components.voice.VoiceNoteMediaController
import org.thoughtcrime.securesms.components.voice.VoiceNoteMediaControllerOwner
import org.thoughtcrime.securesms.conversation.ConversationIntents
import org.thoughtcrime.securesms.conversation.NewConversationActivity
import org.thoughtcrime.securesms.conversation.v2.ConversationFragment
import org.thoughtcrime.securesms.conversation.v2.MotionEventRelay
import org.thoughtcrime.securesms.conversation.v2.ShareDataTimestampViewModel
import org.thoughtcrime.securesms.conversationlist.ConversationListArchiveFragment
@@ -143,6 +143,7 @@ import org.thoughtcrime.securesms.main.MainNavigationDetailLocation
import org.thoughtcrime.securesms.main.MainNavigationDetailLocationEffect
import org.thoughtcrime.securesms.main.MainNavigationListLocation
import org.thoughtcrime.securesms.main.MainNavigationRail
import org.thoughtcrime.securesms.main.MainNavigationRouter
import org.thoughtcrime.securesms.main.MainNavigationViewModel
import org.thoughtcrime.securesms.main.MainSnackbar
import org.thoughtcrime.securesms.main.MainSnackbarHostKey
@@ -200,7 +201,7 @@ class MainActivity :
MainNavigator.NavigatorProvider,
Material3OnScrollHelperBinder,
ConversationListFragment.Callback,
ConversationFragment.NavigationHost,
MainNavigationRouter,
CallLogFragment.Callback,
GooglePayComponent {
@@ -208,6 +209,7 @@ class MainActivity :
private val TAG = Log.tag(MainActivity::class)
private const val KEY_STARTING_TAB = "STARTING_TAB"
private const val KEY_DETAIL_LOCATION = "DETAIL_LOCATION"
const val RESULT_CONFIG_CHANGED = Activity.RESULT_FIRST_USER + 901
@JvmStatic
@@ -220,6 +222,11 @@ class MainActivity :
fun clearTopAndOpenTab(context: Context, startingTab: MainNavigationListLocation): Intent {
return clearTop(context).putExtra(KEY_STARTING_TAB, startingTab)
}
@JvmStatic
fun clearTopAndOpenDetail(context: Context, location: MainNavigationDetailLocation): Intent {
return clearTop(context).putExtra(KEY_DETAIL_LOCATION, location)
}
}
private val dynamicTheme = DynamicNoActionBarTheme()
@@ -822,6 +829,13 @@ class MainActivity :
handleDeepLinkIntent(intent)
val extras = intent.extras ?: return
val detailLocation = extras.getParcelableCompat(KEY_DETAIL_LOCATION, MainNavigationDetailLocation::class.java)
if (detailLocation != null) {
mainNavigationViewModel.goTo(detailLocation)
return
}
val startingTab = extras.getSerializableCompat(KEY_STARTING_TAB, MainNavigationListLocation::class.java)
when (startingTab) {
@@ -1300,7 +1314,6 @@ class MainActivity :
}
}
override fun navigateTo(location: MainNavigationDetailLocation) {
mainNavigationViewModel.goTo(location)
}
override fun goTo(location: MainNavigationListLocation) = mainNavigationViewModel.goTo(location)
override fun goTo(location: MainNavigationDetailLocation) = mainNavigationViewModel.goTo(location)
}

View File

@@ -41,6 +41,7 @@ import org.signal.core.util.requireParcelableCompat
import org.signal.donations.InAppPaymentType
import org.thoughtcrime.securesms.AvatarPreviewActivity
import org.thoughtcrime.securesms.BlockUnblockDialog
import org.thoughtcrime.securesms.MainActivity
import org.thoughtcrime.securesms.PushContactSelectionActivity
import org.thoughtcrime.securesms.R
import org.thoughtcrime.securesms.badges.BadgeImageView
@@ -90,6 +91,8 @@ import org.thoughtcrime.securesms.groups.ui.managegroup.dialogs.GroupDescription
import org.thoughtcrime.securesms.groups.ui.managegroup.dialogs.GroupInviteSentDialog
import org.thoughtcrime.securesms.groups.ui.managegroup.dialogs.GroupsLearnMoreBottomSheetDialogFragment
import org.thoughtcrime.securesms.keyvalue.SignalStore
import org.thoughtcrime.securesms.main.MainNavigationDetailLocation
import org.thoughtcrime.securesms.main.MainNavigationRouter
import org.thoughtcrime.securesms.mediaoverview.MediaOverviewActivity
import org.thoughtcrime.securesms.mediapreview.MediaIntentFactory
import org.thoughtcrime.securesms.mediasend.camerax.CameraXUtil
@@ -175,6 +178,7 @@ class ConversationSettingsFragment :
)
private var transitionCallback: TransitionCallback? = null
private var mainNavRouter: MainNavigationRouter? = null
private lateinit var toolbar: Toolbar
private lateinit var toolbarAvatarContainer: FrameLayout
@@ -191,6 +195,7 @@ class ConversationSettingsFragment :
override fun onAttach(context: Context) {
super.onAttach(context)
transitionCallback = context as? TransitionCallback
mainNavRouter = context as? MainNavigationRouter
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
@@ -981,7 +986,11 @@ class ConversationSettingsFragment :
lifecycleScope.launch {
viewModel.deleteChat()
progressDialog.dismissAllowingStateLoss()
onToolbarNavigationClicked()
if (mainNavRouter != null) {
mainNavRouter?.goTo(MainNavigationDetailLocation.Empty)
} else {
startActivity(MainActivity.clearTopAndOpenDetail(requireContext(), MainNavigationDetailLocation.Empty))
}
}
}
)

View File

@@ -288,6 +288,7 @@ import org.thoughtcrime.securesms.linkpreview.LinkPreviewViewModelV2
import org.thoughtcrime.securesms.longmessage.LongMessageFragment
import org.thoughtcrime.securesms.main.MainNavigationDetailLocation
import org.thoughtcrime.securesms.main.MainNavigationListLocation
import org.thoughtcrime.securesms.main.MainNavigationRouter
import org.thoughtcrime.securesms.main.MainNavigationViewModel
import org.thoughtcrime.securesms.main.MainSnackbarHostKey
import org.thoughtcrime.securesms.mediaoverview.MediaOverviewActivity
@@ -565,7 +566,7 @@ class ConversationFragment :
private lateinit var conversationItemDecorations: ConversationItemDecorations
private lateinit var optionsMenuCallback: ConversationOptionsMenuCallback
private var navigationHost: NavigationHost? = null
private var mainNavRouter: MainNavigationRouter? = null
private var animationsAllowed = false
private var pinnedShortcutReceiver: BroadcastReceiver? = null
@@ -641,7 +642,7 @@ class ConversationFragment :
override fun onAttach(context: Context) {
super.onAttach(context)
navigationHost = context as? NavigationHost
mainNavRouter = context as? MainNavigationRouter
}
override fun onCreate(savedInstanceState: Bundle?) {
@@ -4216,12 +4217,12 @@ class ConversationFragment :
/**
* Routes to the appropriate destination based on the current window configuration.
*
* In split-pane mode, delegates to the [NavigationHost] to display content in the detail pane. Otherwise, opens the destination as a standalone screen.
* In split-pane mode, delegates to the [MainNavigationRouter] to display content in the detail pane. Otherwise, opens the destination as a standalone screen.
*/
private fun navigateTo(location: MainNavigationDetailLocation.Chats) {
val host = navigationHost
if (host != null && resources.getWindowSizeClass().isSplitPane()) {
host.navigateTo(location)
val router = mainNavRouter
if (router != null && resources.getWindowSizeClass().isSplitPane()) {
router.goTo(location)
} else {
when (location) {
is MainNavigationDetailLocation.Chats.MessageDetails -> navigateToMessageDetailsStandalone(location)
@@ -5206,11 +5207,4 @@ class ConversationFragment :
override fun onDoubleTapEditEducationSheetNext(conversationMessage: ConversationMessage) {
handleEditMessage(conversationMessage)
}
/**
* Optional hook for host activity to intercept and handle detail navigation, used by split-pane layouts.
*/
interface NavigationHost {
fun navigateTo(location: MainNavigationDetailLocation)
}
}