From e1216dafb4018166be8d2142c71bd063a7deb5ae Mon Sep 17 00:00:00 2001 From: Marco Gomiero Date: Sat, 29 Nov 2025 12:18:05 +0100 Subject: [PATCH 1/6] fix: require padding values for screens --- .../prof18/moneyflow/navigation/MoneyFlowNavHost.kt | 4 ++++ .../addtransaction/AddTransactionScreen.kt | 8 ++++++-- .../alltransactions/AllTransactionsScreen.kt | 9 +++++++-- .../presentation/categories/CategoriesScreen.kt | 10 ++++++++-- .../prof18/moneyflow/presentation/home/HomeScreen.kt | 11 ++++++++--- .../moneyflow/presentation/settings/SettingsScreen.kt | 11 ++++++++++- 6 files changed, 43 insertions(+), 10 deletions(-) diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/navigation/MoneyFlowNavHost.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/navigation/MoneyFlowNavHost.kt index 86d36ae6..cbf36c24 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/navigation/MoneyFlowNavHost.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/navigation/MoneyFlowNavHost.kt @@ -165,6 +165,7 @@ private fun EntryProviderScope.screens( dateLabel = uiState.dateLabel, addTransactionAction = uiState.addTransactionAction, resetAction = viewModel::resetAction, + paddingValues = paddingValues, ) } @@ -182,6 +183,7 @@ private fun EntryProviderScope.screens( }, isFromAddTransaction = route.fromAddTransaction, categoryModel = categoryModel, + paddingValues = paddingValues, ) } @@ -191,6 +193,7 @@ private fun EntryProviderScope.screens( navigateUp = { backStack.removeLastOrNull() }, stateFlow = viewModel.state, loadNextPage = viewModel::loadNextPage, + paddingValues = paddingValues, ) } @@ -206,6 +209,7 @@ private fun EntryProviderScope.screens( onBiometricEnabled = viewModel::updateBiometricState, hideSensitiveDataState = hideDataState, onHideSensitiveDataEnabled = viewModel::updateHideSensitiveDataState, + paddingValues = paddingValues, ) } } diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/addtransaction/AddTransactionScreen.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/addtransaction/AddTransactionScreen.kt index 696f8859..416c2964 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/addtransaction/AddTransactionScreen.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/addtransaction/AddTransactionScreen.kt @@ -1,6 +1,7 @@ package com.prof18.moneyflow.presentation.addtransaction import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.PaddingValues import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding import androidx.compose.material.Icon @@ -61,6 +62,7 @@ internal fun AddTransactionScreen( dateLabel: String?, addTransactionAction: AddTransactionAction?, resetAction: () -> Unit, + paddingValues: PaddingValues, ) { val (showDatePickerDialog, setShowedDatePickerDialog) = remember { mutableStateOf(false) } @@ -102,6 +104,7 @@ internal fun AddTransactionScreen( val keyboardController = LocalSoftwareKeyboardController.current Scaffold( + modifier = Modifier.padding(paddingValues), scaffoldState = scaffoldState, topBar = { MFTopBar( @@ -115,8 +118,8 @@ internal fun AddTransactionScreen( actionEnabled = categoryState.value?.id != null && amountText.isNotEmpty(), ) }, - content = { - Column { + content = { innerPadding -> + Column(modifier = Modifier.padding(innerPadding)) { DatePickerDialog( showDatePickerDialog, setShowedDatePickerDialog, @@ -239,6 +242,7 @@ private fun AddTransactionScreenPreview() { dateLabel = "11 July 2021", addTransactionAction = null, resetAction = {}, + paddingValues = PaddingValues(), ) } } diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/alltransactions/AllTransactionsScreen.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/alltransactions/AllTransactionsScreen.kt index f0fb2ec6..1ee1e965 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/alltransactions/AllTransactionsScreen.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/alltransactions/AllTransactionsScreen.kt @@ -1,10 +1,12 @@ package com.prof18.moneyflow.presentation.alltransactions +import androidx.compose.foundation.layout.PaddingValues import androidx.compose.foundation.lazy.LazyColumn import androidx.compose.material.Divider import androidx.compose.material.Scaffold import androidx.compose.runtime.Composable import androidx.compose.runtime.collectAsState +import androidx.compose.ui.Modifier import androidx.compose.ui.tooling.preview.Preview import com.prof18.moneyflow.domain.entities.MoneyTransaction import com.prof18.moneyflow.domain.entities.TransactionTypeUI @@ -26,18 +28,20 @@ internal fun AllTransactionsScreen( stateFlow: StateFlow, loadNextPage: () -> Unit, navigateUp: () -> Unit = {}, + paddingValues: PaddingValues, ) { Scaffold( + modifier = Modifier.padding(paddingValues), topBar = { MFTopBar( topAppBarText = stringResource(Res.string.all_transactions), onBackPressed = { navigateUp() }, ) }, - content = { + content = { innerPadding -> val uiState = stateFlow.collectAsState().value - LazyColumn { + LazyColumn(modifier = Modifier.padding(innerPadding)) { when { uiState.error != null -> { item { ErrorView(uiErrorMessage = uiState.error) } @@ -91,6 +95,7 @@ private fun AllTransactionsScreenPreviews() { ), ), loadNextPage = {}, + paddingValues = PaddingValues(), ) } } diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/categories/CategoriesScreen.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/categories/CategoriesScreen.kt index f353584f..150d415a 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/categories/CategoriesScreen.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/categories/CategoriesScreen.kt @@ -1,11 +1,13 @@ package com.prof18.moneyflow.presentation.categories +import androidx.compose.foundation.layout.PaddingValues import androidx.compose.foundation.lazy.LazyColumn import androidx.compose.foundation.lazy.items import androidx.compose.material.Divider import androidx.compose.material.Scaffold import androidx.compose.material.Surface import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier import androidx.compose.ui.tooling.preview.Preview import com.prof18.moneyflow.domain.entities.Category import com.prof18.moneyflow.presentation.categories.components.CategoryCard @@ -30,8 +32,10 @@ internal fun CategoriesScreen( sendCategoryBack: (CategoryUIData) -> Unit, isFromAddTransaction: Boolean, categoryModel: CategoryModel, + paddingValues: PaddingValues, ) { Scaffold( + modifier = Modifier.padding(paddingValues), topBar = { MFTopBar( topAppBarText = stringResource(Res.string.categories_screen), @@ -43,14 +47,14 @@ internal fun CategoriesScreen( actionEnabled = true, ) }, - content = { + content = { innerPadding -> when (categoryModel) { CategoryModel.Loading -> Loader() is CategoryModel.Error -> { ErrorView(uiErrorMessage = categoryModel.uiErrorMessage) } is CategoryModel.CategoryState -> { - LazyColumn { + LazyColumn(modifier = Modifier.padding(innerPadding)) { items(categoryModel.categories) { CategoryCard( category = it, @@ -93,6 +97,7 @@ private fun CategoriesScreenPreview() { ), ), ), + paddingValues = PaddingValues(), ) } } @@ -116,6 +121,7 @@ private fun CategoriesScreenErrorPreview() { nerdMessageArgs = listOf("101"), ), ), + paddingValues = PaddingValues(), ) } } diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/home/HomeScreen.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/home/HomeScreen.kt index 2f107df8..4d7cdfe5 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/home/HomeScreen.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/home/HomeScreen.kt @@ -29,7 +29,6 @@ import androidx.compose.runtime.remember import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.tooling.preview.Preview -import androidx.compose.ui.unit.dp import co.touchlab.kermit.Logger import com.prof18.moneyflow.domain.entities.BalanceRecap import com.prof18.moneyflow.domain.entities.MoneyTransaction @@ -62,14 +61,18 @@ internal fun HomeScreen( hideSensitiveDataState: Boolean, navigateToAllTransactions: () -> Unit, navigateToAddTransaction: () -> Unit = {}, - paddingValues: PaddingValues = PaddingValues(0.dp), + paddingValues: PaddingValues, deleteTransaction: (Long) -> Unit = {}, changeSensitiveDataVisibility: (Boolean) -> Unit = {}, ) { when (homeModel) { is HomeModel.Loading -> Loader() is HomeModel.HomeState -> { - Column(modifier = Modifier.padding(Margins.small)) { + Column( + modifier = Modifier + .padding(paddingValues) + .padding(Margins.small), + ) { Row( modifier = Modifier.fillMaxWidth(), horizontalArrangement = Arrangement.SpaceBetween, @@ -230,6 +233,7 @@ private fun HomeScreenPreview() { ), hideSensitiveDataState = true, navigateToAllTransactions = {}, + paddingValues = PaddingValues(), ) } } @@ -252,6 +256,7 @@ private fun HomeScreenErrorPreview() { ), hideSensitiveDataState = true, navigateToAllTransactions = {}, + paddingValues = PaddingValues(), ) } } diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/settings/SettingsScreen.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/settings/SettingsScreen.kt index 8961cf24..8508db56 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/settings/SettingsScreen.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/settings/SettingsScreen.kt @@ -1,6 +1,7 @@ package com.prof18.moneyflow.presentation.settings import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.PaddingValues import androidx.compose.foundation.layout.padding import androidx.compose.material.MaterialTheme import androidx.compose.material.Scaffold @@ -27,6 +28,7 @@ internal fun SettingsScreen( onBiometricEnabled: (Boolean) -> Unit, hideSensitiveDataState: Boolean, onHideSensitiveDataEnabled: (Boolean) -> Unit, + paddingValues: PaddingValues, ) { SettingsScreenContent( isBiometricSupported = biometricAvailabilityChecker.isBiometricSupported(), @@ -34,6 +36,7 @@ internal fun SettingsScreen( onBiometricEnabled = onBiometricEnabled, hideSensitiveDataState = hideSensitiveDataState, onHideSensitiveDataEnabled = onHideSensitiveDataEnabled, + paddingValues = paddingValues, ) } @@ -45,20 +48,25 @@ private fun SettingsScreenContent( onBiometricEnabled: (Boolean) -> Unit, hideSensitiveDataState: Boolean, onHideSensitiveDataEnabled: (Boolean) -> Unit, + paddingValues: PaddingValues, ) { Scaffold( + modifier = Modifier.padding(paddingValues), topBar = { Text( text = stringResource(Res.string.settings_screen), style = MaterialTheme.typography.h4, modifier = Modifier + .padding(paddingValues) .padding(horizontal = Margins.regular) .padding(top = Margins.regular), ) }, - content = { + content = { innerPadding -> Column( modifier = Modifier + .padding(paddingValues) + .padding(innerPadding) .padding(top = Margins.regular), ) { Text( @@ -96,6 +104,7 @@ private fun SettingsScreenPreview() { onBiometricEnabled = {}, hideSensitiveDataState = true, onHideSensitiveDataEnabled = {}, + paddingValues = PaddingValues(), ) } } From 0ff9d8b995d4079e233c6b11176b89cbb0844d39 Mon Sep 17 00:00:00 2001 From: Marco Gomiero Date: Sat, 29 Nov 2025 12:26:29 +0100 Subject: [PATCH 2/6] fix: update roborazzi padding usages --- AGENTS.md | 1 + .../kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt | 2 ++ .../kotlin/com/prof18/moneyflow/AllTransactionsRoborazziTest.kt | 2 ++ .../kotlin/com/prof18/moneyflow/CategoriesRoborazziTest.kt | 2 ++ .../kotlin/com/prof18/moneyflow/HomeRoborazziTest.kt | 2 ++ .../kotlin/com/prof18/moneyflow/SettingsRoborazziTest.kt | 2 ++ 6 files changed, 11 insertions(+) diff --git a/AGENTS.md b/AGENTS.md index 6238ac25..b9649fed 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -25,6 +25,7 @@ - When modifying or adding UI, add screenshot tests in `androidApp/src/androidTest` following existing patterns to keep visual coverage current. - Run `./gradlew :shared:check` for KMP unit coverage; - Name tests with intent (e.g., `shouldReturnZeroBalanceWhenEmptyWallet`); group by feature or use-case. +- When you change the API surface of composables, search for related tests and update them so snapshots and unit coverage stay in sync. ## Commit & Pull Request Guidelines - Commit messages: concise, imperative. Conventional prefixes (`feat:`, `fix:`, `chore:`, `docs:`) are welcome and match existing history. diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt index 0aee3b7a..e07568aa 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt @@ -1,5 +1,6 @@ package com.prof18.moneyflow +import androidx.compose.foundation.layout.PaddingValues import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember import androidx.test.ext.junit.runners.AndroidJUnit4 @@ -42,6 +43,7 @@ class AddTransactionRoborazziTest : RoborazziTestBase() { dateLabel = "11 July 2021", addTransactionAction = null, resetAction = {}, + paddingValues = PaddingValues(), ) } } diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AllTransactionsRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AllTransactionsRoborazziTest.kt index 0fdf2730..2e50e92c 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AllTransactionsRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AllTransactionsRoborazziTest.kt @@ -1,5 +1,6 @@ package com.prof18.moneyflow +import androidx.compose.foundation.layout.PaddingValues import androidx.test.ext.junit.runners.AndroidJUnit4 import com.prof18.moneyflow.features.alltransactions.AllTransactionsUiState import com.prof18.moneyflow.presentation.alltransactions.AllTransactionsScreen @@ -26,6 +27,7 @@ class AllTransactionsRoborazziTest : RoborazziTestBase() { ), ), loadNextPage = {}, + paddingValues = PaddingValues(), ) } } diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/CategoriesRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/CategoriesRoborazziTest.kt index a090ba1f..dd2a6075 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/CategoriesRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/CategoriesRoborazziTest.kt @@ -1,5 +1,6 @@ package com.prof18.moneyflow +import androidx.compose.foundation.layout.PaddingValues import androidx.test.ext.junit.runners.AndroidJUnit4 import com.prof18.moneyflow.domain.entities.Category import com.prof18.moneyflow.presentation.categories.CategoriesScreen @@ -38,6 +39,7 @@ class CategoriesRoborazziTest : RoborazziTestBase() { ), ), ), + paddingValues = PaddingValues(), ) } } diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/HomeRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/HomeRoborazziTest.kt index abb663eb..4ac6a2f4 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/HomeRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/HomeRoborazziTest.kt @@ -1,5 +1,6 @@ package com.prof18.moneyflow +import androidx.compose.foundation.layout.PaddingValues import androidx.test.ext.junit.runners.AndroidJUnit4 import com.prof18.moneyflow.domain.entities.BalanceRecap import com.prof18.moneyflow.presentation.home.HomeModel @@ -30,6 +31,7 @@ class HomeRoborazziTest : RoborazziTestBase() { ), hideSensitiveDataState = false, navigateToAllTransactions = {}, + paddingValues = PaddingValues(), ) } } diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/SettingsRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/SettingsRoborazziTest.kt index 17a08257..f047e365 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/SettingsRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/SettingsRoborazziTest.kt @@ -1,5 +1,6 @@ package com.prof18.moneyflow +import androidx.compose.foundation.layout.PaddingValues import androidx.test.ext.junit.runners.AndroidJUnit4 import com.prof18.moneyflow.features.settings.BiometricAvailabilityChecker import com.prof18.moneyflow.presentation.settings.SettingsScreen @@ -26,6 +27,7 @@ class SettingsRoborazziTest : RoborazziTestBase() { onBiometricEnabled = {}, hideSensitiveDataState = true, onHideSensitiveDataEnabled = {}, + paddingValues = PaddingValues(), ) } } From 4aad8f9d6f944aed3ea8c062a02e9157837cd93e Mon Sep 17 00:00:00 2001 From: Marco Gomiero Date: Sat, 29 Nov 2025 12:47:34 +0100 Subject: [PATCH 3/6] Update Roborazzi tests with scaffold padding --- .../moneyflow/AddTransactionRoborazziTest.kt | 44 ++++++++++--------- .../moneyflow/AllTransactionsRoborazziTest.kt | 20 +++++---- .../moneyflow/CategoriesRoborazziTest.kt | 40 +++++++++-------- .../com/prof18/moneyflow/HomeRoborazziTest.kt | 28 ++++++------ .../prof18/moneyflow/SettingsRoborazziTest.kt | 24 +++++----- 5 files changed, 83 insertions(+), 73 deletions(-) diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt index e07568aa..0e28b706 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt @@ -1,8 +1,8 @@ package com.prof18.moneyflow -import androidx.compose.foundation.layout.PaddingValues import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember +import androidx.compose.material.Scaffold import androidx.test.ext.junit.runners.AndroidJUnit4 import com.github.takahirom.roborazzi.RobolectricDeviceQualifiers import com.prof18.moneyflow.database.model.TransactionType @@ -25,26 +25,28 @@ class AddTransactionRoborazziTest : RoborazziTestBase() { fun captureAddTransactionScreen() { composeRule.setContent { MoneyFlowTheme { - AddTransactionScreen( - categoryState = remember { mutableStateOf(RoborazziSampleData.sampleCategory) }, - navigateUp = {}, - navigateToCategoryList = {}, - addTransaction = {}, - amountText = "10.00", - updateAmountText = {}, - descriptionText = "Pizza 🍕", - updateDescriptionText = {}, - selectedTransactionType = TransactionType.OUTCOME, - updateTransactionType = {}, - updateYear = {}, - updateMonth = {}, - updateDay = {}, - saveDate = {}, - dateLabel = "11 July 2021", - addTransactionAction = null, - resetAction = {}, - paddingValues = PaddingValues(), - ) + Scaffold { + AddTransactionScreen( + categoryState = remember { mutableStateOf(RoborazziSampleData.sampleCategory) }, + navigateUp = {}, + navigateToCategoryList = {}, + addTransaction = {}, + amountText = "10.00", + updateAmountText = {}, + descriptionText = "Pizza 🍕", + updateDescriptionText = {}, + selectedTransactionType = TransactionType.OUTCOME, + updateTransactionType = {}, + updateYear = {}, + updateMonth = {}, + updateDay = {}, + saveDate = {}, + dateLabel = "11 July 2021", + addTransactionAction = null, + resetAction = {}, + paddingValues = it, + ) + } } } diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AllTransactionsRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AllTransactionsRoborazziTest.kt index 2e50e92c..a8370759 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AllTransactionsRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AllTransactionsRoborazziTest.kt @@ -1,6 +1,6 @@ package com.prof18.moneyflow -import androidx.compose.foundation.layout.PaddingValues +import androidx.compose.material.Scaffold import androidx.test.ext.junit.runners.AndroidJUnit4 import com.prof18.moneyflow.features.alltransactions.AllTransactionsUiState import com.prof18.moneyflow.presentation.alltransactions.AllTransactionsScreen @@ -20,15 +20,17 @@ class AllTransactionsRoborazziTest : RoborazziTestBase() { fun captureAllTransactionsScreen() { composeRule.setContent { MoneyFlowTheme { - AllTransactionsScreen( - stateFlow = MutableStateFlow( - AllTransactionsUiState( - transactions = RoborazziSampleData.sampleTransactions, + Scaffold { + AllTransactionsScreen( + stateFlow = MutableStateFlow( + AllTransactionsUiState( + transactions = RoborazziSampleData.sampleTransactions, + ), ), - ), - loadNextPage = {}, - paddingValues = PaddingValues(), - ) + loadNextPage = {}, + paddingValues = it, + ) + } } } diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/CategoriesRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/CategoriesRoborazziTest.kt index dd2a6075..75d3687b 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/CategoriesRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/CategoriesRoborazziTest.kt @@ -1,6 +1,6 @@ package com.prof18.moneyflow -import androidx.compose.foundation.layout.PaddingValues +import androidx.compose.material.Scaffold import androidx.test.ext.junit.runners.AndroidJUnit4 import com.prof18.moneyflow.domain.entities.Category import com.prof18.moneyflow.presentation.categories.CategoriesScreen @@ -21,26 +21,28 @@ class CategoriesRoborazziTest : RoborazziTestBase() { fun captureCategoriesScreen() { composeRule.setContent { MoneyFlowTheme { - CategoriesScreen( - navigateUp = {}, - sendCategoryBack = {}, - isFromAddTransaction = true, - categoryModel = CategoryModel.CategoryState( - categories = listOf( - Category( - id = 0, - name = "Food", - icon = CategoryIcon.IC_HAMBURGER_SOLID, - ), - Category( - id = 1, - name = "Drinks", - icon = CategoryIcon.IC_COCKTAIL_SOLID, + Scaffold { + CategoriesScreen( + navigateUp = {}, + sendCategoryBack = {}, + isFromAddTransaction = true, + categoryModel = CategoryModel.CategoryState( + categories = listOf( + Category( + id = 0, + name = "Food", + icon = CategoryIcon.IC_HAMBURGER_SOLID, + ), + Category( + id = 1, + name = "Drinks", + icon = CategoryIcon.IC_COCKTAIL_SOLID, + ), ), ), - ), - paddingValues = PaddingValues(), - ) + paddingValues = it, + ) + } } } diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/HomeRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/HomeRoborazziTest.kt index 4ac6a2f4..c5cfa0c9 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/HomeRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/HomeRoborazziTest.kt @@ -1,6 +1,6 @@ package com.prof18.moneyflow -import androidx.compose.foundation.layout.PaddingValues +import androidx.compose.material.Scaffold import androidx.test.ext.junit.runners.AndroidJUnit4 import com.prof18.moneyflow.domain.entities.BalanceRecap import com.prof18.moneyflow.presentation.home.HomeModel @@ -20,19 +20,21 @@ class HomeRoborazziTest : RoborazziTestBase() { fun captureHomeScreen() { composeRule.setContent { MoneyFlowTheme { - HomeScreen( - homeModel = HomeModel.HomeState( - balanceRecap = BalanceRecap( - totalBalance = 5000.0, - monthlyIncome = 1000.0, - monthlyExpenses = 50.0, + Scaffold { + HomeScreen( + homeModel = HomeModel.HomeState( + balanceRecap = BalanceRecap( + totalBalance = 5000.0, + monthlyIncome = 1000.0, + monthlyExpenses = 50.0, + ), + latestTransactions = RoborazziSampleData.sampleTransactions, ), - latestTransactions = RoborazziSampleData.sampleTransactions, - ), - hideSensitiveDataState = false, - navigateToAllTransactions = {}, - paddingValues = PaddingValues(), - ) + hideSensitiveDataState = false, + navigateToAllTransactions = {}, + paddingValues = it, + ) + } } } diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/SettingsRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/SettingsRoborazziTest.kt index f047e365..069590b3 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/SettingsRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/SettingsRoborazziTest.kt @@ -1,6 +1,6 @@ package com.prof18.moneyflow -import androidx.compose.foundation.layout.PaddingValues +import androidx.compose.material.Scaffold import androidx.test.ext.junit.runners.AndroidJUnit4 import com.prof18.moneyflow.features.settings.BiometricAvailabilityChecker import com.prof18.moneyflow.presentation.settings.SettingsScreen @@ -19,16 +19,18 @@ class SettingsRoborazziTest : RoborazziTestBase() { fun captureSettingsScreen() { composeRule.setContent { MoneyFlowTheme { - SettingsScreen( - biometricAvailabilityChecker = object : BiometricAvailabilityChecker { - override fun isBiometricSupported(): Boolean = true - }, - biometricState = true, - onBiometricEnabled = {}, - hideSensitiveDataState = true, - onHideSensitiveDataEnabled = {}, - paddingValues = PaddingValues(), - ) + Scaffold { + SettingsScreen( + biometricAvailabilityChecker = object : BiometricAvailabilityChecker { + override fun isBiometricSupported(): Boolean = true + }, + biometricState = true, + onBiometricEnabled = {}, + hideSensitiveDataState = true, + onHideSensitiveDataEnabled = {}, + paddingValues = it, + ) + } } } From d6d9b6b5d1d1d0200cf56e0055237da312b3f473 Mon Sep 17 00:00:00 2001 From: Marco Gomiero Date: Sat, 29 Nov 2025 13:13:08 +0100 Subject: [PATCH 4/6] Fix padding parameter ordering for screens --- .../prof18/moneyflow/AddTransactionRoborazziTest.kt | 2 +- .../prof18/moneyflow/navigation/MoneyFlowNavHost.kt | 10 +++++----- .../alltransactions/AllTransactionsScreen.kt | 5 +++-- .../presentation/categories/CategoriesScreen.kt | 1 + .../prof18/moneyflow/presentation/home/HomeScreen.kt | 2 +- 5 files changed, 11 insertions(+), 9 deletions(-) diff --git a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt index 0e28b706..37ba9a7c 100644 --- a/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt +++ b/shared/src/androidUnitTest/kotlin/com/prof18/moneyflow/AddTransactionRoborazziTest.kt @@ -1,8 +1,8 @@ package com.prof18.moneyflow +import androidx.compose.material.Scaffold import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember -import androidx.compose.material.Scaffold import androidx.test.ext.junit.runners.AndroidJUnit4 import com.github.takahirom.roborazzi.RobolectricDeviceQualifiers import com.prof18.moneyflow.database.model.TransactionType diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/navigation/MoneyFlowNavHost.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/navigation/MoneyFlowNavHost.kt index cbf36c24..a2d0697c 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/navigation/MoneyFlowNavHost.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/navigation/MoneyFlowNavHost.kt @@ -133,13 +133,13 @@ private fun EntryProviderScope.screens( val hideSensitiveData by homeViewModel.hideSensitiveDataState.collectAsState() HomeScreen( - navigateToAddTransaction = { backStack.add(AddTransactionRoute) }, - paddingValues = paddingValues, - deleteTransaction = { id -> homeViewModel.deleteTransaction(id) }, homeModel = homeModel, hideSensitiveDataState = hideSensitiveData, - changeSensitiveDataVisibility = { homeViewModel.changeSensitiveDataVisibility(it) }, navigateToAllTransactions = { backStack.add(AllTransactionsRoute) }, + paddingValues = paddingValues, + navigateToAddTransaction = { backStack.add(AddTransactionRoute) }, + deleteTransaction = { id -> homeViewModel.deleteTransaction(id) }, + changeSensitiveDataVisibility = { homeViewModel.changeSensitiveDataVisibility(it) }, ) } @@ -190,10 +190,10 @@ private fun EntryProviderScope.screens( entry { val viewModel = koinViewModel() AllTransactionsScreen( - navigateUp = { backStack.removeLastOrNull() }, stateFlow = viewModel.state, loadNextPage = viewModel::loadNextPage, paddingValues = paddingValues, + navigateUp = { backStack.removeLastOrNull() }, ) } diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/alltransactions/AllTransactionsScreen.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/alltransactions/AllTransactionsScreen.kt index 1ee1e965..0f911536 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/alltransactions/AllTransactionsScreen.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/alltransactions/AllTransactionsScreen.kt @@ -1,6 +1,7 @@ package com.prof18.moneyflow.presentation.alltransactions import androidx.compose.foundation.layout.PaddingValues +import androidx.compose.foundation.layout.padding import androidx.compose.foundation.lazy.LazyColumn import androidx.compose.material.Divider import androidx.compose.material.Scaffold @@ -27,8 +28,8 @@ import org.jetbrains.compose.resources.stringResource internal fun AllTransactionsScreen( stateFlow: StateFlow, loadNextPage: () -> Unit, - navigateUp: () -> Unit = {}, paddingValues: PaddingValues, + navigateUp: () -> Unit = {}, ) { Scaffold( modifier = Modifier.padding(paddingValues), @@ -85,7 +86,6 @@ internal fun AllTransactionsScreen( private fun AllTransactionsScreenPreviews() { MoneyFlowTheme { AllTransactionsScreen( - navigateUp = {}, stateFlow = MutableStateFlow( AllTransactionsUiState( transactions = listOf( @@ -96,6 +96,7 @@ private fun AllTransactionsScreenPreviews() { ), loadNextPage = {}, paddingValues = PaddingValues(), + navigateUp = {}, ) } } diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/categories/CategoriesScreen.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/categories/CategoriesScreen.kt index 150d415a..aab5e74b 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/categories/CategoriesScreen.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/categories/CategoriesScreen.kt @@ -1,6 +1,7 @@ package com.prof18.moneyflow.presentation.categories import androidx.compose.foundation.layout.PaddingValues +import androidx.compose.foundation.layout.padding import androidx.compose.foundation.lazy.LazyColumn import androidx.compose.foundation.lazy.items import androidx.compose.material.Divider diff --git a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/home/HomeScreen.kt b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/home/HomeScreen.kt index 4d7cdfe5..9ffcccfb 100644 --- a/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/home/HomeScreen.kt +++ b/shared/src/commonMain/kotlin/com/prof18/moneyflow/presentation/home/HomeScreen.kt @@ -60,8 +60,8 @@ internal fun HomeScreen( homeModel: HomeModel, hideSensitiveDataState: Boolean, navigateToAllTransactions: () -> Unit, - navigateToAddTransaction: () -> Unit = {}, paddingValues: PaddingValues, + navigateToAddTransaction: () -> Unit = {}, deleteTransaction: (Long) -> Unit = {}, changeSensitiveDataVisibility: (Boolean) -> Unit = {}, ) { From a9abc2d65786eea1623fd1679465d40312f5fa47 Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Sat, 29 Nov 2025 12:15:10 +0000 Subject: [PATCH 5/6] chore: update Roborazzi snapshots --- image/roborazzi/home_screen.png | Bin 16484 -> 16628 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/image/roborazzi/home_screen.png b/image/roborazzi/home_screen.png index 25ffefe4623c6c6e1b22e22eb6c6f4705a910a2a..2ce957312f067f836cfe878342632cf4c0a6fd71 100644 GIT binary patch literal 16628 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 BiLn3x From d944a0ee3bf613d0e68f55c43c4065b76c72e829 Mon Sep 17 00:00:00 2001 From: Marco Gomiero Date: Sat, 29 Nov 2025 16:59:13 +0100 Subject: [PATCH 6/6] Merge branch 'origin/main' into work --- gradle/libs.versions.toml | 10 +++++----- settings.gradle.kts | 2 +- shared/build.gradle.kts | 19 +++++++++++++++++++ 3 files changed, 25 insertions(+), 6 deletions(-) diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index 970f1887..258cc370 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -4,7 +4,7 @@ android-compileSdk = "36" android-minSdk = "26" android-targetSdk = "36" androidx-test = "1.7.0" -androidx-test-runner = "1.6.2" +androidx-test-runner = "1.7.0" androidx-test-ext = "1.3.0" biometric = "1.2.0-alpha05" compose = "1.10.0-beta02" @@ -13,7 +13,7 @@ immutable-collections = "0.4.0" coroutines = "1.10.2" agp = "8.10.1" detekt = "1.23.8" -detekt-compose-rules = "0.4.27" +detekt-compose-rules = "0.4.28" java = "21" kermit = "2.0.8" koin = "4.1.1" @@ -25,10 +25,10 @@ lifecycle-navigation3 = "2.10.0-alpha05" navigation3 = "1.0.0-alpha05" kotlinx-serialization = "1.7.3" lifecycle = "2.10.0" -sqlDelight = "2.1.0" +sqlDelight = "2.2.1" turbine = "1.2.1" -triplet-play = "3.12.1" -roborazzi = "1.44.0-alpha03" +triplet-play = "3.12.2" +roborazzi = "1.52.0" robolectric = "4.12.2" [libraries] diff --git a/settings.gradle.kts b/settings.gradle.kts index 680ed6e7..215596b8 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -16,7 +16,7 @@ dependencyResolutionManagement { } plugins { - id("org.gradle.toolchains.foojay-resolver-convention") version "0.10.0" + id("org.gradle.toolchains.foojay-resolver-convention") version "1.0.0" } rootProject.name = "money-flow" diff --git a/shared/build.gradle.kts b/shared/build.gradle.kts index 085917dd..7455a601 100644 --- a/shared/build.gradle.kts +++ b/shared/build.gradle.kts @@ -1,3 +1,5 @@ +import java.net.URI + import org.jetbrains.kotlin.gradle.ExperimentalKotlinGradlePluginApi import org.jetbrains.kotlin.gradle.dsl.JvmTarget @@ -147,6 +149,23 @@ dependencies { tasks.withType().configureEach { systemProperty("roborazzi.test.record.dir", rootProject.layout.projectDirectory.dir("image/roborazzi").asFile.path) + + listOf( + "http" to System.getenv("http_proxy"), + "https" to System.getenv("https_proxy"), + ).forEach { (scheme, proxyValue) -> + proxyValue + ?.takeIf { it.isNotBlank() } + ?.let(::URI) + ?.let { proxyUri -> + proxyUri.host?.let { host -> + systemProperty("$scheme.proxyHost", host) + } + proxyUri.port.takeIf { it != -1 }?.let { port -> + systemProperty("$scheme.proxyPort", port) + } + } + } } sqldelight {