M8f: instant navigation, no transitions (D-108)
NavHost enter, exit, pop and size transitions are None, so pushed screens, tab switches, editors and the session gate change at once instead of the default 700 ms cross-fade. NavTransitionsTest asserts the values. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01TQd3pEP9UeN2uifbHknQ7B
This commit is contained in:
@@ -149,7 +149,16 @@ private fun AppGraph(viewModel: AppViewModel, session: SessionState, updateCheck
|
||||
|
||||
// Result snackbars are shown in the scaffold of the screen returned to (Home, S-5, S-8, S-10, S-12, S-16), which
|
||||
// each host [snackbar] (D-071).
|
||||
NavHost(nav, startDestination = start) {
|
||||
// D-108: every destination change is instant (NavTransitions).
|
||||
NavHost(
|
||||
nav,
|
||||
startDestination = start,
|
||||
enterTransition = NavTransitions.enter,
|
||||
exitTransition = NavTransitions.exit,
|
||||
popEnterTransition = NavTransitions.enter,
|
||||
popExitTransition = NavTransitions.exit,
|
||||
sizeTransform = NavTransitions.size,
|
||||
) {
|
||||
onboarding(viewModel, shell)
|
||||
topLevel(session, shell)
|
||||
accountsAndExpenses(viewModel, shell)
|
||||
|
||||
@@ -0,0 +1,27 @@
|
||||
package se.hagstedt.kvitt.nav
|
||||
|
||||
import androidx.compose.animation.AnimatedContentTransitionScope
|
||||
import androidx.compose.animation.EnterTransition
|
||||
import androidx.compose.animation.ExitTransition
|
||||
import androidx.compose.animation.SizeTransform
|
||||
import androidx.navigation.NavBackStackEntry
|
||||
|
||||
/**
|
||||
* Destination changes are instant (D-108): no enter, exit, pop or size animation for pushed screens, tab switches,
|
||||
* editors or the session gate (`NavHost` otherwise cross-fades every change over 700 ms). Motion inside a screen
|
||||
* (ripples, expanding sections, the FAB, sheets) belongs to the components and is not affected.
|
||||
*
|
||||
* The `NavHost` lambdas only delegate to [enterTransition], [exitTransition] and [sizeTransform], which the unit
|
||||
* test asserts (the transition scope is sealed and cannot be built outside a composition).
|
||||
*/
|
||||
internal object NavTransitions {
|
||||
fun enterTransition(): EnterTransition = EnterTransition.None
|
||||
|
||||
fun exitTransition(): ExitTransition = ExitTransition.None
|
||||
|
||||
fun sizeTransform(): SizeTransform? = null
|
||||
|
||||
val enter: AnimatedContentTransitionScope<NavBackStackEntry>.() -> EnterTransition = { enterTransition() }
|
||||
val exit: AnimatedContentTransitionScope<NavBackStackEntry>.() -> ExitTransition = { exitTransition() }
|
||||
val size: AnimatedContentTransitionScope<NavBackStackEntry>.() -> SizeTransform? = { sizeTransform() }
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
package se.hagstedt.kvitt.nav
|
||||
|
||||
import androidx.compose.animation.EnterTransition
|
||||
import androidx.compose.animation.ExitTransition
|
||||
import org.junit.Assert.assertNull
|
||||
import org.junit.Assert.assertSame
|
||||
import org.junit.Test
|
||||
|
||||
/** D-108: the app's `NavHost` changes destination without any animation. */
|
||||
class NavTransitionsTest {
|
||||
@Test
|
||||
fun enterIsNone() {
|
||||
assertSame(EnterTransition.None, NavTransitions.enterTransition())
|
||||
}
|
||||
|
||||
@Test
|
||||
fun exitIsNone() {
|
||||
assertSame(ExitTransition.None, NavTransitions.exitTransition())
|
||||
}
|
||||
|
||||
@Test
|
||||
fun noSizeTransform() {
|
||||
assertNull(NavTransitions.sizeTransform())
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user