fix: scroll to date when clicked on stats screen

This commit is contained in:
Rafal Wisniewski
2026-05-04 15:44:32 +02:00
parent 5fb54bf18e
commit aad0de1499
3 changed files with 52 additions and 22 deletions

View File

@@ -12,7 +12,6 @@ import androidx.compose.material3.DrawerValue
import androidx.compose.material3.Scaffold
import androidx.compose.material3.rememberDrawerState
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
@@ -26,6 +25,7 @@ import androidx.navigation.compose.NavHost
import androidx.navigation.compose.composable
import androidx.navigation.compose.currentBackStackEntryAsState
import androidx.navigation.compose.rememberNavController
import androidx.navigation.navArgument
import cc.n0th1ng.tripmoney.data.entity.Category
import cc.n0th1ng.tripmoney.data.entity.Trip
import cc.n0th1ng.tripmoney.navigation.BottomNavigation
@@ -111,17 +111,20 @@ fun NavigationDrawer() {
startDestination = if (currentTripId == -1) Screens.TRIP_PICKER else Screens.LIST_EXPENSE,
modifier = Modifier.padding(innerPadding)
) {
composable(Screens.LIST_EXPENSE) {
composable(Screens.LIST_EXPENSE+"?dateToScroll={dateToScroll}",
arguments = listOf(navArgument("dateToScroll"){defaultValue = ""})) {
backStackEntry ->
ListExpenseScreen(
filter = filter, search = search,
initialAutoOpen = shouldTriggerAutoOpen,
onAutoOpenConsumed = { hasHandledStartupOpen = true })
onAutoOpenConsumed = { hasHandledStartupOpen = true },
dateToScroll = backStackEntry.arguments?.getString("dateToScroll")?: "")
}
composable(Screens.TRIP_PICKER) {
TripPickerScreen(navController)
}
composable(Screens.STATISTICS) {
StatisticsScreen()
StatisticsScreen(navController)
}
composable(Screens.SETTINGS) {
SettingsScreen(navController)

View File

@@ -90,7 +90,8 @@ fun ListExpenseScreen(
filter: Filter,
search: String,
initialAutoOpen: Boolean,
onAutoOpenConsumed: () -> Unit
onAutoOpenConsumed: () -> Unit,
dateToScroll: String
) {
val settingsViewModel: SettingsViewModel = hiltViewModel()
val tripViewModel: TripViewModel = hiltViewModel()
@@ -115,7 +116,8 @@ fun ListExpenseScreen(
isRecalculatingRate = isRecalculatingRate,
initialAutoOpen = initialAutoOpen,
onAutoOpenConsumed = onAutoOpenConsumed,
idToScroll = idToScroll
idToScroll = idToScroll,
dateToScroll = dateToScroll
)
}
@@ -130,7 +132,8 @@ fun ListExpenseScreen(
isRecalculatingRate: Boolean,
initialAutoOpen: Boolean,
onAutoOpenConsumed: () -> Unit,
idToScroll: Int
idToScroll: Int,
dateToScroll: String
) {
val sheetState = rememberModalBottomSheetState(skipPartiallyExpanded = true)
@@ -181,6 +184,16 @@ fun ListExpenseScreen(
}
} else {
LaunchedEffect(Unit) {
if (dateToScroll == "") return@LaunchedEffect
for (index in 0 until items.itemCount) {
val item = items.peek(index)
if (item is ExpenseListItemUi.Header && item.date.toString() == dateToScroll) {
listState.animateScrollToItem(index)
break
}
}
}
LaunchedEffect(idToScroll) {
if (idToScroll == -1) return@LaunchedEffect
for (index in 0 until items.itemCount) {
@@ -527,7 +540,8 @@ fun PreviewListExpenseScreen() {
isRecalculatingRate = true,
false,
{},
0
0,
""
)
}
@@ -553,7 +567,8 @@ fun PreviewListExpenseScreenWithoutExpenses() {
isRecalculatingRate = true,
false,
{},
0
0,
""
)
}
@@ -573,7 +588,8 @@ fun PreviewListExpenseScreenWithoutTrip() {
isRecalculatingRate = true,
false,
{},
0
0,
""
)
}

View File

@@ -4,6 +4,7 @@ import android.annotation.SuppressLint
import android.os.Build
import androidx.annotation.RequiresApi
import androidx.compose.foundation.background
import androidx.compose.foundation.clickable
import androidx.compose.foundation.horizontalScroll
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
@@ -42,10 +43,12 @@ import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import androidx.core.graphics.toColorInt
import androidx.hilt.lifecycle.viewmodel.compose.hiltViewModel
import androidx.navigation.NavController
import cc.n0th1ng.tripmoney.data.dto.SummaryPerCategory
import cc.n0th1ng.tripmoney.data.dto.SummaryPerDay
import cc.n0th1ng.tripmoney.data.entity.Category
import cc.n0th1ng.tripmoney.data.entity.Trip
import cc.n0th1ng.tripmoney.navigation.Screens
import cc.n0th1ng.tripmoney.theme.TripMoneyTheme
import cc.n0th1ng.tripmoney.utils.AllPreviews
import cc.n0th1ng.tripmoney.utils.Currencies
@@ -60,7 +63,7 @@ import java.time.format.DateTimeFormatter
@RequiresApi(Build.VERSION_CODES.O)
@Composable
fun StatisticsScreen() {
fun StatisticsScreen(navController: NavController) {
val expenseAndCategoryViewModel: ExpenseAndCategoryViewModel = hiltViewModel()
val settingsViewModel: SettingsViewModel = hiltViewModel()
val tripViewModel: TripViewModel = hiltViewModel()
@@ -78,7 +81,10 @@ fun StatisticsScreen() {
summaryPerDayList,
summaryAmount,
Currencies.valueOf(currentTrip?.currency ?: Currencies.default().name),
moneyLeft
moneyLeft,
onDayClicked = {
date -> navController.navigate(Screens.LIST_EXPENSE + "?dateToScroll=$date")
}
)
}
@@ -89,7 +95,8 @@ fun StatisticsScreen(
summaryPerDayList: List<SummaryPerDay>,
summaryAmount: Double,
tripCurrency: Currencies,
moneyLeft: Double?
moneyLeft: Double?,
onDayClicked: (String) -> Unit
) {
Column(
modifier = Modifier
@@ -117,7 +124,7 @@ fun StatisticsScreen(
modifier = Modifier.heightIn(max = 300.dp),
summaryPerCategoryList = summaryPerCategoryList
)
SummaryPerDayCard(modifier = Modifier.height(300.dp), summaryPerDayList = summaryPerDayList)
SummaryPerDayCard(modifier = Modifier.height(300.dp), summaryPerDayList = summaryPerDayList, onDayClicked = onDayClicked)
}
}
@@ -217,7 +224,7 @@ fun SummaryPerCategoryCard(
@RequiresApi(Build.VERSION_CODES.O)
@Composable
fun SummaryPerDayCard(modifier: Modifier = Modifier, summaryPerDayList: List<SummaryPerDay>) {
fun SummaryPerDayCard(modifier: Modifier = Modifier, summaryPerDayList: List<SummaryPerDay>, onDayClicked: (String) -> Unit) {
ElevatedCard(
modifier = modifier
.fillMaxWidth(),
@@ -246,9 +253,10 @@ fun SummaryPerDayCard(modifier: Modifier = Modifier, summaryPerDayList: List<Sum
.horizontalScroll(rememberScrollState()),
horizontalArrangement = Arrangement.spacedBy(5.dp)
) {
summaryPerDayList.forEach {
summaryPerDayList.forEach { it ->
DayCard(
summaryPerDay = it
summaryPerDay = it,
onDayClicked = {date -> onDayClicked(date)}
)
}
}
@@ -316,7 +324,7 @@ fun CategoryCard(modifier: Modifier = Modifier, summaryPerCategory: SummaryPerCa
@RequiresApi(Build.VERSION_CODES.O)
@Composable
fun DayCard(modifier: Modifier = Modifier, summaryPerDay: SummaryPerDay) {
fun DayCard(modifier: Modifier = Modifier, summaryPerDay: SummaryPerDay, onDayClicked: (String) -> Unit) {
Column(
modifier = modifier.fillMaxHeight(), verticalArrangement = Arrangement.Bottom,
horizontalAlignment = Alignment.CenterHorizontally
@@ -334,6 +342,7 @@ fun DayCard(modifier: Modifier = Modifier, summaryPerDay: SummaryPerDay) {
.fillMaxHeight(0.2f + (0.98f - 0.2f) * summaryPerDay.percent)
.clip(RoundedCornerShape(width / 2))
.background(MaterialTheme.colorScheme.primary)
.clickable(onClick = {onDayClicked(summaryPerDay.day.toString())})
.padding(top = 5.dp)
) {
Column(
@@ -387,7 +396,8 @@ fun PreviewStatisticScreen() {
summaryPerDayList,
summaryAmount = 125.24,
Currencies.entries.random(),
432.14
432.14,
{}
)
}
}
@@ -405,7 +415,8 @@ fun PreviewStatisticScreenWithNoData() {
emptyList(),
summaryAmount = 0.0,
Currencies.entries.random(),
null
null,
{}
)
}
}