Compare commits
1 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| d7ccc2b858 |
@@ -12,8 +12,8 @@ android {
|
|||||||
applicationId = "com.crsmthw.phase10tracker"
|
applicationId = "com.crsmthw.phase10tracker"
|
||||||
minSdk = 35
|
minSdk = 35
|
||||||
targetSdk = 37
|
targetSdk = 37
|
||||||
versionCode = 6
|
versionCode = 7
|
||||||
versionName = "3.0.2"
|
versionName = "3.0.3"
|
||||||
|
|
||||||
testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner"
|
testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner"
|
||||||
vectorDrawables {
|
vectorDrawables {
|
||||||
|
|||||||
Binary file not shown.
Binary file not shown.
@@ -11,8 +11,8 @@
|
|||||||
"type": "SINGLE",
|
"type": "SINGLE",
|
||||||
"filters": [],
|
"filters": [],
|
||||||
"attributes": [],
|
"attributes": [],
|
||||||
"versionCode": 6,
|
"versionCode": 7,
|
||||||
"versionName": "3.0.2",
|
"versionName": "3.0.3",
|
||||||
"outputFile": "app-release.apk"
|
"outputFile": "app-release.apk"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
|
|||||||
@@ -2,8 +2,11 @@ package com.crsmthw.phase10tracker.ui
|
|||||||
|
|
||||||
import androidx.compose.runtime.*
|
import androidx.compose.runtime.*
|
||||||
import androidx.compose.ui.platform.LocalContext
|
import androidx.compose.ui.platform.LocalContext
|
||||||
|
import androidx.lifecycle.Lifecycle
|
||||||
import androidx.lifecycle.viewmodel.compose.viewModel
|
import androidx.lifecycle.viewmodel.compose.viewModel
|
||||||
|
import androidx.navigation.NavController
|
||||||
import androidx.navigation.NavHostController
|
import androidx.navigation.NavHostController
|
||||||
|
import androidx.navigation.NavOptionsBuilder
|
||||||
import androidx.navigation.NavType
|
import androidx.navigation.NavType
|
||||||
import androidx.navigation.compose.*
|
import androidx.navigation.compose.*
|
||||||
import androidx.navigation.navArgument
|
import androidx.navigation.navArgument
|
||||||
@@ -27,6 +30,25 @@ object Routes {
|
|||||||
fun gameResults(id: Long) = "results/$id"
|
fun gameResults(id: Long) = "results/$id"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ── Safe navigation helpers ───────────────────────────────────────────────────
|
||||||
|
// Guards every nav action behind a RESUMED check so rapid double-taps during
|
||||||
|
// transition animations can't pop extra destinations and cause a blank screen.
|
||||||
|
|
||||||
|
private fun NavController.navigateSafe(
|
||||||
|
route: String,
|
||||||
|
builder: NavOptionsBuilder.() -> Unit = {}
|
||||||
|
) {
|
||||||
|
if (currentBackStackEntry?.lifecycle?.currentState == Lifecycle.State.RESUMED) {
|
||||||
|
navigate(route, builder)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun NavController.popSafe() {
|
||||||
|
if (currentBackStackEntry?.lifecycle?.currentState == Lifecycle.State.RESUMED) {
|
||||||
|
popBackStack()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Composable
|
@Composable
|
||||||
fun Phase10NavHost(
|
fun Phase10NavHost(
|
||||||
navController: NavHostController,
|
navController: NavHostController,
|
||||||
@@ -57,12 +79,12 @@ fun Phase10NavHost(
|
|||||||
amoledBlack = amoledBlack,
|
amoledBlack = amoledBlack,
|
||||||
onThemeModeChange = themeVm::setThemeMode,
|
onThemeModeChange = themeVm::setThemeMode,
|
||||||
onAmoledBlackChange = themeVm::setAmoledBlack,
|
onAmoledBlackChange = themeVm::setAmoledBlack,
|
||||||
onContinueGame = { gameId -> navController.navigate(Routes.activeGame(gameId)) },
|
onContinueGame = { gameId -> navController.navigateSafe(Routes.activeGame(gameId)) },
|
||||||
onStartNew = { navController.navigate(Routes.GAME_SETUP) },
|
onStartNew = { navController.navigateSafe(Routes.GAME_SETUP) },
|
||||||
onLeaderboard = { navController.navigate(Routes.LEADERBOARD) },
|
onLeaderboard = { navController.navigateSafe(Routes.LEADERBOARD) },
|
||||||
onManagePlayers = { navController.navigate(Routes.PLAYER_ROSTER) },
|
onManagePlayers = { navController.navigateSafe(Routes.PLAYER_ROSTER) },
|
||||||
onCustomRules = { navController.navigate(Routes.CUSTOM_RULES) },
|
onCustomRules = { navController.navigateSafe(Routes.CUSTOM_RULES) },
|
||||||
onAbout = { navController.navigate(Routes.ABOUT) }
|
onAbout = { navController.navigateSafe(Routes.ABOUT) }
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -70,7 +92,7 @@ fun Phase10NavHost(
|
|||||||
val vm: PlayerRosterViewModel = viewModel(factory = factory)
|
val vm: PlayerRosterViewModel = viewModel(factory = factory)
|
||||||
PlayerRosterScreen(
|
PlayerRosterScreen(
|
||||||
vm = vm,
|
vm = vm,
|
||||||
onBack = { navController.popBackStack() }
|
onBack = { navController.popSafe() }
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -79,11 +101,11 @@ fun Phase10NavHost(
|
|||||||
GameSetupScreen(
|
GameSetupScreen(
|
||||||
vm = vm,
|
vm = vm,
|
||||||
onGameStarted = { gameId ->
|
onGameStarted = { gameId ->
|
||||||
navController.navigate(Routes.activeGame(gameId)) {
|
navController.navigateSafe(Routes.activeGame(gameId)) {
|
||||||
popUpTo(Routes.HOME)
|
popUpTo(Routes.HOME)
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onBack = { navController.popBackStack() }
|
onBack = { navController.popSafe() }
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -96,18 +118,18 @@ fun Phase10NavHost(
|
|||||||
val vm: ActiveGameViewModel = viewModel(factory = gameFactory)
|
val vm: ActiveGameViewModel = viewModel(factory = gameFactory)
|
||||||
ActiveGameScreen(
|
ActiveGameScreen(
|
||||||
vm = vm,
|
vm = vm,
|
||||||
onEnterRound = { navController.navigate(Routes.roundEntry(gameId)) },
|
onEnterRound = { navController.navigateSafe(Routes.roundEntry(gameId)) },
|
||||||
onGameEnd = {
|
onGameEnd = {
|
||||||
navController.navigate(Routes.gameResults(gameId)) {
|
navController.navigateSafe(Routes.gameResults(gameId)) {
|
||||||
popUpTo(Routes.HOME)
|
popUpTo(Routes.HOME)
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onGameCancelled = {
|
onGameCancelled = {
|
||||||
navController.navigate(Routes.HOME) {
|
navController.navigateSafe(Routes.HOME) {
|
||||||
popUpTo(Routes.HOME) { inclusive = true }
|
popUpTo(Routes.HOME) { inclusive = true }
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onBack = { navController.popBackStack() }
|
onBack = { navController.popSafe() }
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -120,8 +142,8 @@ fun Phase10NavHost(
|
|||||||
val vm: RoundEntryViewModel = viewModel(factory = gameFactory)
|
val vm: RoundEntryViewModel = viewModel(factory = gameFactory)
|
||||||
RoundEntryScreen(
|
RoundEntryScreen(
|
||||||
vm = vm,
|
vm = vm,
|
||||||
onRoundSubmitted = { navController.popBackStack() },
|
onRoundSubmitted = { navController.popSafe() },
|
||||||
onBack = { navController.popBackStack() }
|
onBack = { navController.popSafe() }
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -135,7 +157,7 @@ fun Phase10NavHost(
|
|||||||
GameResultsScreen(
|
GameResultsScreen(
|
||||||
vm = vm,
|
vm = vm,
|
||||||
onHome = {
|
onHome = {
|
||||||
navController.navigate(Routes.HOME) {
|
navController.navigateSafe(Routes.HOME) {
|
||||||
popUpTo(Routes.HOME) { inclusive = true }
|
popUpTo(Routes.HOME) { inclusive = true }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -146,7 +168,7 @@ fun Phase10NavHost(
|
|||||||
val vm: LeaderboardViewModel = viewModel(factory = factory)
|
val vm: LeaderboardViewModel = viewModel(factory = factory)
|
||||||
LeaderboardScreen(
|
LeaderboardScreen(
|
||||||
vm = vm,
|
vm = vm,
|
||||||
onBack = { navController.popBackStack() }
|
onBack = { navController.popSafe() }
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -154,12 +176,12 @@ fun Phase10NavHost(
|
|||||||
val vm: CustomPhasesViewModel = viewModel(factory = factory)
|
val vm: CustomPhasesViewModel = viewModel(factory = factory)
|
||||||
CustomPhasesScreen(
|
CustomPhasesScreen(
|
||||||
vm = vm,
|
vm = vm,
|
||||||
onBack = { navController.popBackStack() }
|
onBack = { navController.popSafe() }
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
composable(Routes.ABOUT) {
|
composable(Routes.ABOUT) {
|
||||||
AboutScreen(onBack = { navController.popBackStack() })
|
AboutScreen(onBack = { navController.popSafe() })
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user