Skip to content

Commit e132de3

Browse files
authored
feat: add share account stepper pages (#2507)
Co-authored-by: kampit ojha <97059622+Itskampitojha@users.noreply.github.com>
1 parent 657eb15 commit e132de3

File tree

9 files changed

+317
-1
lines changed

9 files changed

+317
-1
lines changed

cmp-android/build.gradle.kts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,7 @@ android {
7575
}
7676
}
7777

78+
@Suppress("UnstableApiUsage")
7879
testOptions {
7980
unitTests {
8081
isIncludeAndroidResources = true
Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,101 @@
1+
/*
2+
* Copyright 2025 Mifos Initiative
3+
*
4+
* This Source Code Form is subject to the terms of the Mozilla Public
5+
* License, v. 2.0. If a copy of the MPL was not distributed with this
6+
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
7+
*
8+
* See https://github.com/openMF/android-client/blob/master/LICENSE.md
9+
*/
10+
package com.mifos.feature.client.createShareAccount
11+
12+
import androidx.compose.foundation.layout.fillMaxWidth
13+
import androidx.compose.foundation.layout.padding
14+
import androidx.compose.runtime.Composable
15+
import androidx.compose.runtime.getValue
16+
import androidx.compose.runtime.remember
17+
import androidx.compose.ui.Modifier
18+
import androidx.lifecycle.compose.collectAsStateWithLifecycle
19+
import androidx.lifecycle.viewmodel.compose.viewModel
20+
import com.mifos.core.designsystem.component.MifosScaffold
21+
import com.mifos.core.ui.components.MifosStepper
22+
import com.mifos.core.ui.components.Step
23+
import com.mifos.core.ui.util.EventsEffect
24+
import com.mifos.feature.client.createShareAccount.pages.ChargesPage
25+
import com.mifos.feature.client.createShareAccount.pages.DetailsPage
26+
import com.mifos.feature.client.createShareAccount.pages.PreviewPage
27+
import com.mifos.feature.client.createShareAccount.pages.TermsPage
28+
29+
@Composable
30+
internal fun ShareAccountScreen(
31+
onNavigateBack: () -> Unit,
32+
onFinish: () -> Unit,
33+
modifier: Modifier = Modifier,
34+
viewModel: ShareAccountViewModel = viewModel(),
35+
) {
36+
val state by viewModel.stateFlow.collectAsStateWithLifecycle()
37+
38+
EventsEffect(viewModel.eventFlow) { event ->
39+
when (event) {
40+
ShareAccountEvent.NavigateBack -> onNavigateBack()
41+
ShareAccountEvent.Finish -> onFinish()
42+
}
43+
}
44+
45+
ShareAccountScaffold(
46+
modifier = modifier,
47+
state = state,
48+
onAction = { viewModel.trySendAction(it) },
49+
)
50+
}
51+
52+
@Composable
53+
private fun ShareAccountScaffold(
54+
state: ShareAccountState,
55+
modifier: Modifier = Modifier,
56+
onAction: (ShareAccountAction) -> Unit,
57+
) {
58+
val steps = remember {
59+
listOf(
60+
Step(name = "Details") {
61+
DetailsPage(
62+
onNext = { onAction(ShareAccountAction.NextStep) },
63+
)
64+
},
65+
Step(name = "Terms") {
66+
TermsPage(
67+
onNext = { onAction(ShareAccountAction.NextStep) },
68+
)
69+
},
70+
Step(name = "Charges") {
71+
ChargesPage(
72+
onNext = { onAction(ShareAccountAction.NextStep) },
73+
)
74+
},
75+
Step(name = "Preview") {
76+
PreviewPage(
77+
onNext = { onAction(ShareAccountAction.Finish) },
78+
)
79+
},
80+
)
81+
}
82+
83+
MifosScaffold(
84+
title = "Create Share Account",
85+
onBackPressed = { onAction(ShareAccountAction.NavigateBack) },
86+
modifier = modifier,
87+
) { paddingValues ->
88+
if (state.dialogState == null) {
89+
MifosStepper(
90+
steps = steps,
91+
currentIndex = state.currentStep,
92+
onStepChange = { newIndex ->
93+
onAction(ShareAccountAction.OnStepChange(newIndex))
94+
},
95+
modifier = Modifier
96+
.fillMaxWidth()
97+
.padding(paddingValues),
98+
)
99+
}
100+
}
101+
}
Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
/*
2+
* Copyright 2025 Mifos Initiative
3+
*
4+
* This Source Code Form is subject to the terms of the Mozilla Public
5+
* License, v. 2.0. If a copy of the MPL was not distributed with this
6+
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
7+
*
8+
* See https://github.com/openMF/android-client/blob/master/LICENSE.md
9+
*/
10+
package com.mifos.feature.client.createShareAccount
11+
12+
import com.mifos.core.ui.util.BaseViewModel
13+
import kotlinx.coroutines.flow.update
14+
15+
class ShareAccountViewModel : BaseViewModel<ShareAccountState, ShareAccountEvent, ShareAccountAction> (ShareAccountState()) {
16+
17+
override fun handleAction(action: ShareAccountAction) {
18+
when (action) {
19+
ShareAccountAction.NextStep -> {
20+
mutableStateFlow.update { state ->
21+
val maxIndex = 3 // total steps - 1
22+
state.copy(currentStep = (state.currentStep + 1).coerceAtMost(maxIndex))
23+
}
24+
}
25+
is ShareAccountAction.OnStepChange -> {
26+
mutableStateFlow.update { it.copy(currentStep = action.index) }
27+
}
28+
ShareAccountAction.NavigateBack -> {
29+
sendEvent(ShareAccountEvent.NavigateBack)
30+
}
31+
ShareAccountAction.Finish -> {
32+
sendEvent(ShareAccountEvent.Finish)
33+
}
34+
}
35+
}
36+
}
37+
38+
data class ShareAccountState(
39+
val currentStep: Int = 0,
40+
val dialogState: Any? = null,
41+
)
42+
43+
sealed class ShareAccountAction {
44+
object NextStep : ShareAccountAction()
45+
data class OnStepChange(val index: Int) : ShareAccountAction()
46+
object NavigateBack : ShareAccountAction()
47+
object Finish : ShareAccountAction()
48+
}
49+
50+
sealed class ShareAccountEvent {
51+
object NavigateBack : ShareAccountEvent()
52+
object Finish : ShareAccountEvent()
53+
}
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
/*
2+
* Copyright 2025 Mifos Initiative
3+
*
4+
* This Source Code Form is subject to the terms of the Mozilla Public
5+
* License, v. 2.0. If a copy of the MPL was not distributed with this
6+
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
7+
*
8+
* See https://github.com/openMF/android-client/blob/master/LICENSE.md
9+
*/
10+
package com.mifos.feature.client.createShareAccount
11+
12+
import androidx.navigation.NavController
13+
import androidx.navigation.NavGraphBuilder
14+
import androidx.navigation.compose.composable
15+
import kotlinx.serialization.Serializable
16+
17+
@Serializable
18+
data object ShareAccountRoute
19+
20+
fun NavGraphBuilder.shareAccountDestination() {
21+
composable<ShareAccountRoute> {
22+
ShareAccountScreen(
23+
onNavigateBack = {},
24+
onFinish = {},
25+
)
26+
}
27+
}
28+
29+
fun NavController.navigateToShareAccountRoute() {
30+
this.navigate(
31+
ShareAccountRoute,
32+
)
33+
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
/*
2+
* Copyright 2025 Mifos Initiative
3+
*
4+
* This Source Code Form is subject to the terms of the Mozilla Public
5+
* License, v. 2.0. If a copy of the MPL was not distributed with this
6+
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
7+
*
8+
* See https://github.com/openMF/android-client/blob/master/LICENSE.md
9+
*/
10+
package com.mifos.feature.client.createShareAccount.pages
11+
12+
import androidx.compose.foundation.layout.Column
13+
import androidx.compose.foundation.layout.Spacer
14+
import androidx.compose.foundation.layout.height
15+
import androidx.compose.material3.Button
16+
import androidx.compose.material3.Text
17+
import androidx.compose.runtime.Composable
18+
import androidx.compose.ui.Alignment
19+
import androidx.compose.ui.Modifier
20+
import androidx.compose.ui.unit.dp
21+
22+
@Composable
23+
fun ChargesPage(onNext: () -> Unit) {
24+
Column(horizontalAlignment = Alignment.CenterHorizontally) {
25+
Text("Charges Page")
26+
Spacer(Modifier.height(8.dp))
27+
Button(onClick = onNext) {
28+
Text("Next Button")
29+
}
30+
}
31+
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
/*
2+
* Copyright 2025 Mifos Initiative
3+
*
4+
* This Source Code Form is subject to the terms of the Mozilla Public
5+
* License, v. 2.0. If a copy of the MPL was not distributed with this
6+
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
7+
*
8+
* See https://github.com/openMF/android-client/blob/master/LICENSE.md
9+
*/
10+
package com.mifos.feature.client.createShareAccount.pages
11+
12+
import androidx.compose.foundation.layout.Column
13+
import androidx.compose.foundation.layout.Spacer
14+
import androidx.compose.foundation.layout.height
15+
import androidx.compose.material3.Button
16+
import androidx.compose.material3.Text
17+
import androidx.compose.runtime.Composable
18+
import androidx.compose.ui.Alignment
19+
import androidx.compose.ui.Modifier
20+
import androidx.compose.ui.unit.dp
21+
22+
@Composable
23+
fun DetailsPage(onNext: () -> Unit) {
24+
Column(horizontalAlignment = Alignment.CenterHorizontally) {
25+
Text("Details Page")
26+
Spacer(Modifier.height(8.dp))
27+
Button(onClick = onNext) {
28+
Text("Next Button")
29+
}
30+
}
31+
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
/*
2+
* Copyright 2025 Mifos Initiative
3+
*
4+
* This Source Code Form is subject to the terms of the Mozilla Public
5+
* License, v. 2.0. If a copy of the MPL was not distributed with this
6+
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
7+
*
8+
* See https://github.com/openMF/android-client/blob/master/LICENSE.md
9+
*/
10+
package com.mifos.feature.client.createShareAccount.pages
11+
12+
import androidx.compose.foundation.layout.Column
13+
import androidx.compose.foundation.layout.Spacer
14+
import androidx.compose.foundation.layout.height
15+
import androidx.compose.material3.Button
16+
import androidx.compose.material3.Text
17+
import androidx.compose.runtime.Composable
18+
import androidx.compose.ui.Alignment
19+
import androidx.compose.ui.Modifier
20+
import androidx.compose.ui.unit.dp
21+
22+
@Composable
23+
fun PreviewPage(onNext: () -> Unit) {
24+
Column(horizontalAlignment = Alignment.CenterHorizontally) {
25+
Text("Preview Page")
26+
Spacer(Modifier.height(8.dp))
27+
Button(onClick = onNext) {
28+
Text("Next Button")
29+
}
30+
}
31+
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
/*
2+
* Copyright 2025 Mifos Initiative
3+
*
4+
* This Source Code Form is subject to the terms of the Mozilla Public
5+
* License, v. 2.0. If a copy of the MPL was not distributed with this
6+
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
7+
*
8+
* See https://github.com/openMF/android-client/blob/master/LICENSE.md
9+
*/
10+
package com.mifos.feature.client.createShareAccount.pages
11+
12+
import androidx.compose.foundation.layout.Column
13+
import androidx.compose.foundation.layout.Spacer
14+
import androidx.compose.foundation.layout.height
15+
import androidx.compose.material3.Button
16+
import androidx.compose.material3.Text
17+
import androidx.compose.runtime.Composable
18+
import androidx.compose.ui.Alignment
19+
import androidx.compose.ui.Modifier
20+
import androidx.compose.ui.unit.dp
21+
22+
@Composable
23+
fun TermsPage(onNext: () -> Unit) {
24+
Column(horizontalAlignment = Alignment.CenterHorizontally) {
25+
Text("Terms Page")
26+
Spacer(Modifier.height(8.dp))
27+
Button(onClick = onNext) {
28+
Text("Next Button")
29+
}
30+
}
31+
}

feature/client/src/commonMain/kotlin/com/mifos/feature/client/navigation/ClientNavigation.kt

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,8 @@ import com.mifos.feature.client.clientUpdateDefaultAccount.navigateToUpdateDefau
6969
import com.mifos.feature.client.clientUpdateDefaultAccount.updateDefaultAccountDestination
7070
import com.mifos.feature.client.clientsList.ClientListScreen
7171
import com.mifos.feature.client.createNewClient.CreateNewClientScreen
72+
import com.mifos.feature.client.createShareAccount.navigateToShareAccountRoute
73+
import com.mifos.feature.client.createShareAccount.shareAccountDestination
7274
import com.mifos.feature.client.documentPreviewScreen.createDocumentPreviewRoute
7375
import com.mifos.feature.client.documentPreviewScreen.navigateToDocumentPreviewRoute
7476
import com.mifos.feature.client.fixedDepositAccount.clientFixedDepositAccountDestination
@@ -302,9 +304,9 @@ fun NavGraphBuilder.clientNavGraph(
302304
)
303305
clientApplyNewApplicationRoute(
304306
onNavigateBack = navController::popBackStack,
307+
onNavigateApplyShareAccount = navController::navigateToShareAccountRoute,
305308
onNavigateApplyLoanAccount = navController::navigateToNewLoanAccountRoute,
306309
onNavigateApplySavingsAccount = navController::navigateToSavingsAccountRoute,
307-
onNavigateApplyShareAccount = { },
308310
onNavigateApplyRecurringAccount = { },
309311
onNavigateApplyFixedAccount = { },
310312
navController = navController,
@@ -334,6 +336,8 @@ fun NavGraphBuilder.clientNavGraph(
334336
loadMoreSavingsAccountInfo = navController::navigateToDataTable,
335337
loadDocuments = navController::navigateToDocumentListScreen,
336338
)
339+
340+
shareAccountDestination()
337341
}
338342
}
339343

0 commit comments

Comments
 (0)