Skip to content

Commit 9e8819d

Browse files
adsamcikCopilot
andcommitted
Phase 13 drop challenges and scale achievements
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
1 parent b3898ba commit 9e8819d

179 files changed

Lines changed: 4014 additions & 21137 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

app/src/main/java/com/adsamcik/tracker/app/Application.kt

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,6 @@ import com.adsamcik.tracker.tracker.shortcut.Shortcuts
2525
import com.adsamcik.tracker.tracker.worker.DailySummaryMaterializationWorker
2626
import android.app.Application as AndroidApplication
2727
import com.adsamcik.tracker.shared.base.concurrency.DispatchersProvider
28-
import com.adsamcik.tracker.shared.base.database.ChallengeDatabaseFold
2928
import com.adsamcik.tracker.shared.base.di.ApplicationScope
3029
import com.adsamcik.tracker.shared.preferences.store.PreferenceFlushLifecycleObserver
3130
import com.adsamcik.tracker.tracker.controller.LockManager
@@ -80,9 +79,6 @@ class Application : AndroidApplication(), Configuration.Provider {
8079
@Inject
8180
lateinit var precisionUpgradeConsumerProvider: Provider<PrecisionUpgradeDomainEventConsumer>
8281

83-
@Inject
84-
lateinit var challengeDatabaseFoldProvider: Provider<ChallengeDatabaseFold>
85-
8682
@Volatile
8783
var isStartupReady: Boolean = false
8884
private set
@@ -171,7 +167,6 @@ class Application : AndroidApplication(), Configuration.Provider {
171167
Reporter.initialize(this@Application)
172168
Logger.initialize(this@Application)
173169
CrashHandler(this@Application).initialize()
174-
challengeDatabaseFoldProvider.get().awaitComplete()
175170
if (!isRobolectricUnitTest()) {
176171
initializeModules()
177172
}

app/src/main/java/com/adsamcik/tracker/app/di/AppGraphModule.kt

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,6 @@ package com.adsamcik.tracker.app.di
22

33
import android.content.Context
44
import com.adsamcik.tracker.app.Application
5-
import com.adsamcik.tracker.game.di.DefaultActiveChallengesProvider
65
import com.adsamcik.tracker.game.di.DefaultDailyPointsProvider
76
import com.adsamcik.tracker.game.di.DefaultGoalProgressProvider
87
import com.adsamcik.tracker.game.repository.GameRepository
@@ -12,7 +11,6 @@ import com.adsamcik.tracker.shared.base.concurrency.DispatchersProvider
1211
import com.adsamcik.tracker.shared.base.database.dao.DailySummaryDao
1312
import com.adsamcik.tracker.shared.base.database.dao.LiveStatsDao
1413
import com.adsamcik.tracker.shared.base.database.dao.TripDao
15-
import com.adsamcik.tracker.shared.base.di.ActiveChallengesProvider
1614
import com.adsamcik.tracker.shared.base.di.ApplicationScope
1715
import com.adsamcik.tracker.shared.base.di.DailyPointsProvider
1816
import com.adsamcik.tracker.shared.base.di.DailySummaryProvider
@@ -95,13 +93,6 @@ object AppGraphModule {
9593
@ApplicationScope appScope: CoroutineScope,
9694
): GoalProgressProvider = DefaultGoalProgressProvider(context, gameRepository, appScope)
9795

98-
@Provides
99-
@Singleton
100-
fun provideActiveChallengesProvider(
101-
gameRepository: GameRepository,
102-
@ApplicationScope appScope: CoroutineScope,
103-
): ActiveChallengesProvider = DefaultActiveChallengesProvider(gameRepository, appScope)
104-
10596
@Provides
10697
@Singleton
10798
fun provideExportPlanStore(

app/src/main/java/com/adsamcik/tracker/app/di/InfrastructureModule.kt

Lines changed: 0 additions & 49 deletions
Original file line numberDiff line numberDiff line change
@@ -4,17 +4,11 @@ import android.content.Context
44
import com.adsamcik.tracker.shared.base.concurrency.DefaultDispatchersProvider
55
import com.adsamcik.tracker.shared.base.concurrency.DispatchersProvider
66
import com.adsamcik.tracker.shared.base.database.AppDatabase
7-
import com.adsamcik.tracker.shared.base.database.ChallengeDatabaseFold
8-
import com.adsamcik.tracker.shared.base.database.ChallengeDatabaseFoldMarker
97
import com.adsamcik.tracker.shared.base.database.dao.AchievementProgressDao
108
import com.adsamcik.tracker.shared.base.database.dao.ActivityDao
119
import com.adsamcik.tracker.shared.base.database.dao.ActivitySnapshotDao
1210
import com.adsamcik.tracker.shared.base.database.dao.CellOperatorDao
1311
import com.adsamcik.tracker.shared.base.database.dao.CellSampleDao
14-
import com.adsamcik.tracker.shared.base.database.dao.ChallengeDao
15-
import com.adsamcik.tracker.shared.base.database.dao.ChallengeHistoryDao
16-
import com.adsamcik.tracker.shared.base.database.dao.ChallengePersonalRecordDao
17-
import com.adsamcik.tracker.shared.base.database.dao.ChallengeStreakDao
1812
import com.adsamcik.tracker.shared.base.database.dao.DailySummaryDao
1913
import com.adsamcik.tracker.shared.base.database.dao.DomainEventDao
2014
import com.adsamcik.tracker.shared.base.database.dao.ExplorationCellDao
@@ -46,7 +40,6 @@ import com.adsamcik.tracker.shared.base.di.DefaultDispatcher
4640
import com.adsamcik.tracker.shared.base.di.IoDispatcher
4741
import com.adsamcik.tracker.shared.base.time.Clock
4842
import com.adsamcik.tracker.shared.base.time.SystemClock
49-
import com.adsamcik.tracker.shared.preferences.Preferences
5043
import dagger.Module
5144
import dagger.Provides
5245
import dagger.hilt.InstallIn
@@ -128,35 +121,6 @@ object InfrastructureModule {
128121
fun provideAppDatabase(@ApplicationContext context: Context): AppDatabase =
129122
AppDatabase.database(context)
130123

131-
@Provides
132-
@Singleton
133-
fun provideChallengeDatabaseFoldMarker(preferences: Preferences): ChallengeDatabaseFoldMarker =
134-
object : ChallengeDatabaseFoldMarker {
135-
override suspend fun isComplete(): Boolean =
136-
preferences.fetchBoolean(ChallengeDatabaseFold.MARKER_KEY, default = false)
137-
138-
override suspend fun markComplete() {
139-
preferences.editSuspend { setBoolean(ChallengeDatabaseFold.MARKER_KEY, true) }
140-
}
141-
142-
override suspend fun isLegacyDataUnrecoverable(): Boolean =
143-
preferences.fetchBoolean(ChallengeDatabaseFold.UNRECOVERABLE_MARKER_KEY, default = false)
144-
145-
override suspend fun markLegacyDataUnrecoverable() {
146-
preferences.editSuspend {
147-
setBoolean(ChallengeDatabaseFold.UNRECOVERABLE_MARKER_KEY, true)
148-
}
149-
}
150-
}
151-
152-
@Provides
153-
@Singleton
154-
fun provideChallengeDatabaseFold(
155-
@ApplicationContext context: Context,
156-
database: AppDatabase,
157-
marker: ChallengeDatabaseFoldMarker,
158-
): ChallengeDatabaseFold = ChallengeDatabaseFold(context, database, marker)
159-
160124
// DAO Providers - enable direct DAO injection without going through AppDatabase.
161125
// DAOs are lightweight proxies to the singleton database and do not need @Singleton scoping.
162126

@@ -244,19 +208,6 @@ object InfrastructureModule {
244208
@Provides
245209
fun providePendingSignalDao(database: AppDatabase): PendingSignalDao = database.pendingSignalDao()
246210

247-
@Provides
248-
fun provideChallengeDao(database: AppDatabase): ChallengeDao = database.challengeDao()
249-
250-
@Provides
251-
fun provideChallengeHistoryDao(database: AppDatabase): ChallengeHistoryDao = database.challengeHistoryDao()
252-
253-
@Provides
254-
fun provideChallengeStreakDao(database: AppDatabase): ChallengeStreakDao = database.challengeStreakDao()
255-
256-
@Provides
257-
fun provideChallengePersonalRecordDao(database: AppDatabase): ChallengePersonalRecordDao =
258-
database.challengePersonalRecordDao()
259-
260211
@Provides
261212
fun provideXpLedgerDao(database: AppDatabase): XpLedgerDao = database.xpLedgerDao()
262213

Lines changed: 1 addition & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1,32 +1,8 @@
11
package com.adsamcik.tracker.app.settings
22

33
import androidx.lifecycle.ViewModel
4-
import androidx.lifecycle.viewModelScope
5-
import com.adsamcik.tracker.game.goals.settings.GoalsSettingsRepository
64
import dagger.hilt.android.lifecycle.HiltViewModel
7-
import kotlinx.coroutines.flow.MutableStateFlow
8-
import kotlinx.coroutines.flow.StateFlow
9-
import kotlinx.coroutines.flow.asStateFlow
10-
import kotlinx.coroutines.launch
115
import javax.inject.Inject
126

137
@HiltViewModel
14-
class GameSettingsViewModel @Inject constructor(
15-
private val goalsSettingsRepository: GoalsSettingsRepository
16-
) : ViewModel() {
17-
18-
private val _challengeEnabled = MutableStateFlow(true)
19-
val challengeEnabled: StateFlow<Boolean> = _challengeEnabled.asStateFlow()
20-
21-
init {
22-
viewModelScope.launch {
23-
goalsSettingsRepository.data.collect { _challengeEnabled.value = it.challengesEnabled }
24-
}
25-
}
26-
27-
fun setChallengeEnabled(enabled: Boolean) {
28-
viewModelScope.launch {
29-
goalsSettingsRepository.setChallengesEnabled(enabled)
30-
}
31-
}
32-
}
8+
class GameSettingsViewModel @Inject constructor() : ViewModel()

app/src/main/java/com/adsamcik/tracker/app/settings/game/GameSettingsScreen.kt

Lines changed: 14 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -7,50 +7,24 @@ import androidx.compose.foundation.lazy.LazyColumn
77
import androidx.compose.material3.MaterialTheme
88
import androidx.compose.material3.Text
99
import androidx.compose.runtime.Composable
10-
import androidx.lifecycle.compose.collectAsStateWithLifecycle
11-
import androidx.compose.runtime.getValue
1210
import androidx.compose.ui.Modifier
1311
import androidx.compose.ui.res.stringResource
1412
import androidx.compose.ui.unit.dp
15-
import androidx.hilt.lifecycle.viewmodel.compose.hiltViewModel
16-
import com.adsamcik.tracker.app.settings.GameSettingsViewModel
1713
import com.adsamcik.tracker.app.settings.components.SectionHeader
18-
import com.adsamcik.tracker.app.settings.components.SwitchSettingsItem
1914

2015
@Composable
21-
fun GameSettingsScreen(
22-
viewModel: GameSettingsViewModel = hiltViewModel()
23-
) {
24-
val challengeEnabled by viewModel.challengeEnabled.collectAsStateWithLifecycle()
25-
26-
LazyColumn(
27-
modifier = Modifier.fillMaxSize(),
28-
contentPadding = PaddingValues(top = 8.dp, bottom = 88.dp)
29-
) {
30-
// Challenges section
31-
item {
32-
SectionHeader(stringResource(com.adsamcik.tracker.game.R.string.settings_game_challenge_category_title))
33-
}
34-
35-
item {
36-
SwitchSettingsItem(
37-
title = stringResource(com.adsamcik.tracker.game.R.string.settings_game_challenge_enable_title),
38-
checked = challengeEnabled,
39-
onCheckedChange = { viewModel.setChallengeEnabled(it) }
40-
)
41-
}
42-
43-
// Goals section
44-
item {
45-
SectionHeader(stringResource(com.adsamcik.tracker.game.R.string.settings_game_goals_category_title))
46-
}
47-
48-
item {
49-
Text(
50-
text = stringResource(com.adsamcik.tracker.R.string.settings_game_goals_managed_hint),
51-
style = MaterialTheme.typography.bodyMedium,
52-
modifier = Modifier.padding(horizontal = 16.dp, vertical = 8.dp)
53-
)
54-
}
55-
}
16+
fun GameSettingsScreen() {
17+
LazyColumn(
18+
modifier = Modifier.fillMaxSize(),
19+
contentPadding = PaddingValues(top = 8.dp, bottom = 88.dp),
20+
) {
21+
item { SectionHeader(stringResource(com.adsamcik.tracker.game.R.string.settings_game_goals_category_title)) }
22+
item {
23+
Text(
24+
text = stringResource(com.adsamcik.tracker.R.string.settings_game_goals_managed_hint),
25+
style = MaterialTheme.typography.bodyMedium,
26+
modifier = Modifier.padding(horizontal = 16.dp, vertical = 8.dp),
27+
)
28+
}
29+
}
5630
}

app/src/main/java/com/adsamcik/tracker/app/ui/MainRoot.kt

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ import com.adsamcik.tracker.app.ui.navigation.Stats
6363
import com.adsamcik.tracker.app.ui.navigation.Map
6464
import com.adsamcik.tracker.app.ui.navigation.MapTripContext
6565
import com.adsamcik.tracker.app.ui.navigation.Game
66-
import com.adsamcik.tracker.app.ui.navigation.TrophyCase
66+
import com.adsamcik.tracker.app.ui.navigation.Achievements
6767
import com.adsamcik.tracker.app.ui.navigation.TripDetail
6868
import com.adsamcik.tracker.app.ui.navigation.History
6969
import com.adsamcik.tracker.app.ui.navigation.Debug
@@ -122,7 +122,6 @@ fun MainRoot(
122122
}
123123
var settingsLaunchNonce by remember { mutableStateOf(0L) }
124124
var tripDetailFallbackRoute by remember { mutableStateOf<AppRoute>(Stats) }
125-
var gameChallengePickerRequest by remember { mutableStateOf(0L) }
126125

127126
// Phase 2: Precision upgrade prompt state
128127
val context = LocalContext.current
@@ -158,7 +157,7 @@ fun MainRoot(
158157
destination.hasRoute<Map>() -> Map
159158
destination.hasRoute<MapTripContext>() -> Map
160159
destination.hasRoute<Game>() -> Game
161-
destination.hasRoute<TrophyCase>() -> TrophyCase
160+
destination.hasRoute<Achievements>() -> Achievements
162161
destination.hasRoute<TripDetail>() -> Stats
163162
destination.hasRoute<History>() -> Stats
164163
destination.hasRoute<Debug>() -> Debug
@@ -302,7 +301,7 @@ fun MainRoot(
302301
destination.hasRoute<ActivitySettings>() ||
303302
destination.hasRoute<TripDetail>() ||
304303
destination.hasRoute<History>() ||
305-
destination.hasRoute<TrophyCase>()
304+
destination.hasRoute<Achievements>()
306305
} == true
307306
val effectiveRouteObj = currentRouteObj ?: navItems.find { it.id == lastTopLevelRoute }
308307
val isDashboard = effectiveRouteObj?.id == Dashboard
@@ -395,10 +394,6 @@ fun MainRoot(
395394
useSideRail = useSideRail,
396395
onOpenSettings = { openSettings(Dashboard) },
397396
onSetTripDetailFallback = { tripDetailFallbackRoute = it },
398-
onOpenChallenges = {
399-
gameChallengePickerRequest += 1L
400-
navController.navigate(Game) { launchSingleTop = true }
401-
},
402397
)
403398
mapGraph(useSideRail = useSideRail)
404399
statsGraph(
@@ -408,7 +403,6 @@ fun MainRoot(
408403
)
409404
gameGraph(
410405
navController = navController,
411-
openChallengePickerRequest = gameChallengePickerRequest,
412406
onOpenSettings = { openSettings(Game) },
413407
)
414408
settingsGraph(navController = navController)

app/src/main/java/com/adsamcik/tracker/app/ui/navigation/DashboardNavGraph.kt

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@ internal fun NavGraphBuilder.dashboardGraph(
1717
useSideRail: Boolean,
1818
onOpenSettings: () -> Unit,
1919
onSetTripDetailFallback: (AppRoute) -> Unit,
20-
onOpenChallenges: () -> Unit,
2120
) {
2221
composable<Dashboard> {
2322
com.adsamcik.tracker.dashboard.ui.compose.DashboardRoute(
@@ -34,7 +33,6 @@ internal fun NavGraphBuilder.dashboardGraph(
3433
restoreState = true
3534
}
3635
},
37-
onOpenChallenges = onOpenChallenges,
3836
onSessionDetailClick = { sessionId ->
3937
onSetTripDetailFallback(Dashboard)
4038
navController.navigate(TripDetail(sessionId)) {

app/src/main/java/com/adsamcik/tracker/app/ui/navigation/GameNavGraph.kt

Lines changed: 22 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -5,36 +5,29 @@ import androidx.navigation.NavGraphBuilder
55
import androidx.navigation.NavHostController
66
import androidx.navigation.compose.composable
77

8-
/**
9-
* Game-related destinations: Game screen and Trophy case.
10-
*/
118
internal fun NavGraphBuilder.gameGraph(
12-
navController: NavHostController,
13-
openChallengePickerRequest: Long,
14-
onOpenSettings: () -> Unit,
9+
navController: NavHostController,
10+
onOpenSettings: () -> Unit,
1511
) {
16-
composable<Game> {
17-
com.adsamcik.tracker.game.ui.compose.GameRoute(
18-
openChallengePickerRequest = openChallengePickerRequest,
19-
onOpenSettings = onOpenSettings,
20-
onNavigateToTrophyCase = {
21-
navController.navigate(TrophyCase) {
22-
launchSingleTop = true
23-
}
24-
},
25-
onNavigateToTracker = {
26-
navController.navigate(Dashboard) {
27-
popUpTo(navController.graph.findStartDestination().id) { saveState = true }
28-
launchSingleTop = true
29-
restoreState = true
30-
}
31-
},
32-
)
33-
}
12+
composable<Game> {
13+
com.adsamcik.tracker.game.ui.compose.GameRoute(
14+
onOpenSettings = onOpenSettings,
15+
onNavigateToAchievements = {
16+
navController.navigate(Achievements) { launchSingleTop = true }
17+
},
18+
onNavigateToTracker = {
19+
navController.navigate(Dashboard) {
20+
popUpTo(navController.graph.findStartDestination().id) { saveState = true }
21+
launchSingleTop = true
22+
restoreState = true
23+
}
24+
},
25+
)
26+
}
3427

35-
composable<TrophyCase> {
36-
com.adsamcik.tracker.game.ui.compose.TrophyCaseRoute(
37-
onBack = { navController.popBackStack() },
38-
)
39-
}
28+
composable<Achievements> {
29+
com.adsamcik.tracker.game.ui.compose.AchievementDetailRoute(
30+
onBack = { navController.popBackStack() },
31+
)
32+
}
4033
}

app/src/main/java/com/adsamcik/tracker/app/ui/navigation/Routes.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ data class MapTripContext(
3131
data object Game : AppRoute
3232

3333
@Serializable
34-
data object TrophyCase : AppRoute
34+
data object Achievements : AppRoute
3535

3636
@Serializable
3737
data class TripDetail(val tripId: Long) : AppRoute

0 commit comments

Comments
 (0)