Preserve pane expansion state across window size class changes.

This commit is contained in:
Alex Hart
2025-10-29 11:22:46 -03:00
committed by jeffrey-signal
parent 47201f4955
commit 6d84ea984d
2 changed files with 28 additions and 11 deletions

View File

@@ -47,6 +47,7 @@ import androidx.compose.runtime.getValue
import androidx.compose.runtime.key
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
@@ -356,18 +357,36 @@ class MainActivity : PassphraseRequiredActivity(), VoiceNoteMediaControllerOwner
MainContainer {
val wrappedNavigator = rememberNavigator(windowSizeClass, contentLayoutData, maxWidth)
val listPaneWidth = contentLayoutData.rememberDefaultPanePreferredWidth(maxWidth)
val halfPartitionWidth = contentLayoutData.partitionWidth / 2
val detailOffset = if (mainToolbarState.mode == MainToolbarMode.SEARCH || mainToolbarState.mode == MainToolbarMode.ACTION_MODE) 0.dp else 80.dp
val detailOnlyAnchor = PaneExpansionAnchor.Offset.fromStart(detailOffset + contentLayoutData.listPaddingStart + halfPartitionWidth)
val detailAndListAnchor = PaneExpansionAnchor.Offset.fromStart(listPaneWidth + halfPartitionWidth)
val listOnlyAnchor = PaneExpansionAnchor.Offset.fromEnd(contentLayoutData.detailPaddingEnd - halfPartitionWidth)
val anchors = remember(contentLayoutData, mainToolbarState) {
val halfPartitionWidth = contentLayoutData.partitionWidth / 2
val detailOffset = if (mainToolbarState.mode == MainToolbarMode.SEARCH || mainToolbarState.mode == MainToolbarMode.ACTION_MODE) 0.dp else 80.dp
val detailOnlyAnchor = PaneExpansionAnchor.Offset.fromStart(detailOffset + contentLayoutData.listPaddingStart + halfPartitionWidth)
val detailAndListAnchor = PaneExpansionAnchor.Offset.fromStart(listPaneWidth + halfPartitionWidth)
val listOnlyAnchor = PaneExpansionAnchor.Offset.fromEnd(contentLayoutData.detailPaddingEnd - halfPartitionWidth)
listOf(detailOnlyAnchor, detailAndListAnchor, listOnlyAnchor)
}
val (detailOnlyAnchor, detailAndListAnchor, listOnlyAnchor) = anchors
val paneExpansionState = rememberPaneExpansionState(
anchors = listOf(detailOnlyAnchor, detailAndListAnchor, listOnlyAnchor),
key = wrappedNavigator.scaffoldValue.paneExpansionStateKey,
anchors = anchors,
initialAnchoredIndex = 1
)
val paneAnchorIndex = rememberSaveable(paneExpansionState.currentAnchor) {
anchors.indexOf(paneExpansionState.currentAnchor)
}
LaunchedEffect(windowSizeClass) {
val anchor = anchors[paneAnchorIndex]
paneExpansionState.animateTo(anchor)
}
val chatNavGraphState = ChatNavGraphState.remember(windowSizeClass)
val mutableInteractionSource = remember { MutableInteractionSource() }
val mainNavigationDetailLocation by rememberMainNavigationDetailLocation(mainNavigationViewModel, chatNavGraphState::writeGraphicsLayerToBitmap)
@@ -428,10 +447,6 @@ class MainActivity : PassphraseRequiredActivity(), VoiceNoteMediaControllerOwner
}
}
LaunchedEffect(windowSizeClass) {
paneExpansionState.animateTo(detailAndListAnchor)
}
LaunchedEffect(paneExpansionState.currentAnchor, detailOnlyAnchor, listOnlyAnchor, detailAndListAnchor) {
val isFullScreenPane = when (paneExpansionState.currentAnchor) {
listOnlyAnchor, detailOnlyAnchor -> {
@@ -451,9 +466,11 @@ class MainActivity : PassphraseRequiredActivity(), VoiceNoteMediaControllerOwner
listOnlyAnchor -> {
mainNavigationViewModel.setFocusedPane(ThreePaneScaffoldRole.Secondary)
}
detailOnlyAnchor -> {
mainNavigationViewModel.setFocusedPane(ThreePaneScaffoldRole.Primary)
}
else -> Unit
}
}

View File

@@ -59,7 +59,7 @@ import org.thoughtcrime.securesms.main.MainNavigationBar
import org.thoughtcrime.securesms.main.MainNavigationRail
import org.thoughtcrime.securesms.main.MainNavigationState
import org.thoughtcrime.securesms.util.RemoteConfig
import java.lang.Integer.max
import kotlin.math.max
enum class Navigation {
RAIL,