Skip to content

Commit f7bd228

Browse files
committed
feat(currencycreator): add shared transitions between flow steps
Signed-off-by: Brandon McAnsh <git@bmcreations.dev>
1 parent 34cca4a commit f7bd228

8 files changed

Lines changed: 71 additions & 38 deletions

File tree

apps/flipcash/core/src/main/kotlin/com/flipcash/app/core/ui/DisplayTextInput.kt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ fun DisplayTextInput(
2929
state: TextFieldState,
3030
placeholder: String,
3131
modifier: Modifier = Modifier,
32+
textModifier: Modifier = Modifier,
3233
style: TextStyle = CodeTheme.typography.displayMedium.copy(
3334
color = CodeTheme.colors.textMain,
3435
fontWeight = FontWeight.SemiBold,
@@ -44,6 +45,7 @@ fun DisplayTextInput(
4445
TextInput(
4546
state = state,
4647
modifier = modifier,
48+
textModifier = textModifier,
4749
placeholder = placeholder,
4850
style = style,
4951
placeholderStyle = placeholderStyle,

apps/flipcash/core/src/main/kotlin/com/flipcash/app/core/ui/TokenImageWithName.kt

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,8 @@ fun TokenIconWithName(
3030
tokenImage: Any?,
3131
imageSize: Dp,
3232
modifier: Modifier = Modifier,
33+
textModifier: Modifier = Modifier,
34+
iconModifier: Modifier = Modifier,
3335
textStyle: TextStyle = CodeTheme.typography.screenTitle,
3436
textColor: Color = CodeTheme.colors.textMain,
3537
spacing: Dp = 0.dp,
@@ -41,9 +43,10 @@ fun TokenIconWithName(
4143
) {
4244
TokenIcon(
4345
image = tokenImage,
44-
modifier = Modifier.size(imageSize)
46+
modifier = Modifier.size(imageSize).then(iconModifier)
4547
)
4648
Text(
49+
modifier = textModifier,
4750
text = tokenName,
4851
style = textStyle,
4952
color = textColor,
@@ -56,6 +59,8 @@ fun TokenIconWithName(
5659
token: Token,
5760
imageSize: Dp,
5861
modifier: Modifier = Modifier,
62+
textModifier: Modifier = Modifier,
63+
iconModifier: Modifier = Modifier,
5964
displayName: (Token) -> String = { it.name },
6065
textStyle: TextStyle = CodeTheme.typography.screenTitle,
6166
textColor: Color = CodeTheme.colors.textMain,
@@ -66,6 +71,8 @@ fun TokenIconWithName(
6671
tokenImage = token.imageUrl,
6772
imageSize = imageSize,
6873
modifier = modifier,
74+
textModifier = textModifier,
75+
iconModifier = iconModifier,
6976
textStyle = textStyle,
7077
textColor = textColor,
7178
spacing = spacing
@@ -89,7 +96,7 @@ fun TokenIcon(
8996
modifier: Modifier = Modifier,
9097
) {
9198
AsyncImage(
92-
modifier = modifier.clip(CircleShape),
99+
modifier = Modifier.clip(CircleShape).then(modifier),
93100
model = ImageRequest.Builder(LocalPlatformContext.current)
94101
.data(image)
95102
.crossfade(false)

apps/flipcash/features/currency-creator/src/main/kotlin/com/flipcash/app/currencycreator/internal/screens/BillCustomizationScreen.kt

Lines changed: 13 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,8 @@ import com.flipcash.app.bill.customization.LocalBillPlaygroundController
2424
import com.flipcash.app.bill.customization.components.BillPlayground
2525
import com.flipcash.app.bills.RenderedBill
2626
import com.flipcash.app.core.bill.Bill
27+
import com.flipcash.app.core.ui.transitions.SharedTransition
28+
import com.flipcash.app.core.ui.transitions.sharedBoundsTransition
2729
import com.flipcash.app.currencycreator.internal.CurrencyCreatorViewModel
2830
import com.getcode.navigation.flow.flowSharedViewModel
2931
import com.getcode.theme.CodeTheme
@@ -75,23 +77,17 @@ internal fun BillCustomizationContent(
7577
modifier = Modifier.fillMaxSize(),
7678
horizontalAlignment = Alignment.CenterHorizontally
7779
) {
78-
AnimatedContent(
79-
modifier = Modifier
80-
.padding(top = CodeTheme.dimens.grid.x3)
81-
.fillMaxWidth()
82-
.weight(1f),
83-
targetState = augmentedBill,
84-
transitionSpec = { fadeIn() togetherWith fadeOut() },
85-
contentKey = { it?.data },
86-
) { bill ->
87-
if (bill != null) {
88-
RenderedBill(
89-
modifier = Modifier.weight(1f),
90-
bill = augmentedBill as Bill,
91-
)
92-
} else {
93-
Spacer(Modifier.weight(1f))
94-
}
80+
augmentedBill?.let { bill ->
81+
RenderedBill(
82+
modifier = Modifier
83+
.padding(top = CodeTheme.dimens.grid.x3)
84+
.fillMaxWidth()
85+
.weight(1f)
86+
.sharedBoundsTransition(
87+
transition = SharedTransition.CurrencyBill
88+
),
89+
bill = bill as Bill,
90+
)
9591
}
9692

9793
BillPlayground(

apps/flipcash/features/currency-creator/src/main/kotlin/com/flipcash/app/currencycreator/internal/screens/DescriptionSelectionScreen.kt

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
package com.flipcash.app.currencycreator.internal.screens
22

33
import androidx.compose.animation.AnimatedVisibility
4+
import androidx.compose.animation.ExperimentalSharedTransitionApi
45
import androidx.compose.animation.animateColorAsState
56
import androidx.compose.animation.fadeIn
67
import androidx.compose.animation.fadeOut
@@ -31,6 +32,9 @@ import com.flipcash.app.core.tokens.CurrencyCreatorResult
3132
import com.flipcash.app.core.tokens.CurrencyCreatorStep
3233
import com.flipcash.app.core.ui.DisplayTextInput
3334
import com.flipcash.app.core.ui.TokenIconWithName
35+
import com.flipcash.app.core.ui.transitions.CircleOverlayClip
36+
import com.flipcash.app.core.ui.transitions.SharedTransition
37+
import com.flipcash.app.core.ui.transitions.sharedBoundsTransition
3438
import com.flipcash.app.currencycreator.internal.CurrencyCreatorViewModel
3539
import com.flipcash.core.R
3640
import com.getcode.navigation.flow.flowSharedViewModel
@@ -49,6 +53,7 @@ internal fun DescriptionSelectionScreen() {
4953
DescriptionSelectionContent(state, viewModel::dispatchEvent)
5054
}
5155

56+
@OptIn(ExperimentalSharedTransitionApi::class)
5257
@Composable
5358
internal fun DescriptionSelectionContent(
5459
state: CurrencyCreatorViewModel.State,
@@ -141,6 +146,12 @@ internal fun DescriptionSelectionContent(
141146
R.string.placeholder_currencyName
142147
)
143148
},
149+
iconModifier = Modifier.sharedBoundsTransition(
150+
transition = SharedTransition.CurrencyIcon,
151+
),
152+
textModifier = Modifier.sharedBoundsTransition(
153+
transition = SharedTransition.CurrencyName,
154+
),
144155
tokenImage = state.icon.dataOrNull,
145156
imageSize = CodeTheme.dimens.staticGrid.x6,
146157
spacing = CodeTheme.dimens.grid.x2

apps/flipcash/features/currency-creator/src/main/kotlin/com/flipcash/app/currencycreator/internal/screens/IconSelectionScreen.kt

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import androidx.activity.compose.rememberLauncherForActivityResult
44
import androidx.activity.result.PickVisualMediaRequest
55
import androidx.activity.result.contract.ActivityResultContracts.PickVisualMedia
66
import androidx.compose.animation.Crossfade
7+
import androidx.compose.animation.ExperimentalSharedTransitionApi
78
import androidx.compose.foundation.background
89
import androidx.compose.foundation.clickable
910
import androidx.compose.foundation.layout.Arrangement
@@ -37,6 +38,9 @@ import com.flipcash.app.core.data.isLoaded
3738
import com.flipcash.app.core.data.isLoading
3839
import com.flipcash.app.core.tokens.CurrencyCreatorResult
3940
import com.flipcash.app.core.tokens.CurrencyCreatorStep
41+
import com.flipcash.app.core.ui.transitions.CircleOverlayClip
42+
import com.flipcash.app.core.ui.transitions.SharedTransition
43+
import com.flipcash.app.core.ui.transitions.sharedBoundsTransition
4044
import com.flipcash.app.currencycreator.internal.CurrencyCreatorViewModel
4145
import com.flipcash.core.R
4246
import com.getcode.navigation.flow.flowSharedViewModel
@@ -58,6 +62,7 @@ internal fun IconSelectionScreen() {
5862
}
5963

6064

65+
@OptIn(ExperimentalSharedTransitionApi::class)
6166
@Composable
6267
internal fun IconSelectionContent(
6368
state: CurrencyCreatorViewModel.State,
@@ -138,6 +143,9 @@ internal fun IconSelectionContent(
138143
Box(
139144
modifier = Modifier
140145
.size(150.dp)
146+
.sharedBoundsTransition(
147+
transition = SharedTransition.CurrencyIcon,
148+
)
141149
.background(
142150
color = CodeTheme.colors.divider,
143151
shape = CircleShape,
@@ -182,7 +190,11 @@ internal fun IconSelectionContent(
182190
}
183191

184192
val name = state.nameFieldState.text
193+
185194
Text(
195+
modifier = Modifier.sharedBoundsTransition(
196+
transition = SharedTransition.CurrencyName,
197+
),
186198
text = if (name.isNotBlank()) name.toString() else stringResource(R.string.placeholder_currencyName),
187199
style = CodeTheme.typography.displaySmall,
188200
color = Color.White,

apps/flipcash/features/currency-creator/src/main/kotlin/com/flipcash/app/currencycreator/internal/screens/NameSelectionScreen.kt

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,9 @@ import androidx.lifecycle.compose.collectAsStateWithLifecycle
1919
import com.flipcash.app.core.tokens.CurrencyCreatorResult
2020
import com.flipcash.app.core.tokens.CurrencyCreatorStep
2121
import com.flipcash.app.core.ui.DisplayTextInput
22+
import com.flipcash.app.core.ui.transitions.SharedTransition
23+
import com.flipcash.app.core.ui.transitions.sharedBoundsTransition
24+
import com.flipcash.app.core.ui.transitions.sharedElementTransition
2225
import com.flipcash.app.currencycreator.internal.CurrencyCreatorViewModel
2326
import com.flipcash.core.R
2427
import com.getcode.navigation.flow.flowSharedViewModel
@@ -85,6 +88,9 @@ internal fun NameSelectionContent(
8588
.fillMaxWidth()
8689
.padding(padding)
8790
.focusRequester(focusRequester),
91+
textModifier = Modifier.sharedElementTransition(
92+
transition = SharedTransition.CurrencyName,
93+
),
8894
keyboardOptions = KeyboardOptions(
8995
keyboardType = KeyboardType.Text,
9096
imeAction = ImeAction.Done,

apps/flipcash/features/currency-creator/src/main/kotlin/com/flipcash/app/currencycreator/internal/screens/ReviewAndPurchaseScreen.kt

Lines changed: 13 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,8 @@ import com.flipcash.app.bills.RenderedBill
2121
import com.flipcash.app.core.tokens.CurrencyCreatorResult
2222
import com.flipcash.app.core.tokens.CurrencyCreatorStep
2323
import com.flipcash.app.core.ui.TokenIconWithName
24+
import com.flipcash.app.core.ui.transitions.SharedTransition
25+
import com.flipcash.app.core.ui.transitions.sharedBoundsTransition
2426
import com.flipcash.app.currencycreator.internal.CurrencyCreatorViewModel
2527
import com.flipcash.core.R
2628
import com.getcode.navigation.flow.flowSharedViewModel
@@ -85,23 +87,17 @@ internal fun ReviewAndPurchaseContent(
8587
spacing = CodeTheme.dimens.grid.x2,
8688
)
8789

88-
AnimatedContent(
89-
modifier = Modifier
90-
.padding(top = CodeTheme.dimens.grid.x3)
91-
.fillMaxWidth()
92-
.weight(1f),
93-
targetState = state.bill,
94-
transitionSpec = { fadeIn() togetherWith fadeOut() },
95-
contentKey = { it?.data },
96-
) { bill ->
97-
if (bill != null) {
98-
RenderedBill(
99-
modifier = Modifier.weight(1f),
100-
bill = bill,
101-
)
102-
} else {
103-
Spacer(Modifier.weight(1f))
104-
}
90+
state.bill?.let { bill ->
91+
RenderedBill(
92+
modifier = Modifier
93+
.weight(1f)
94+
.padding(top = CodeTheme.dimens.grid.x3)
95+
.fillMaxWidth()
96+
.sharedBoundsTransition(
97+
transition = SharedTransition.CurrencyBill
98+
),
99+
bill = bill,
100+
)
105101
}
106102
}
107103
}

ui/components/src/main/kotlin/com/getcode/ui/components/TextInput.kt

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,7 @@ import kotlinx.coroutines.flow.onEach
6060
@Composable
6161
fun TextInput(
6262
modifier: Modifier = Modifier,
63+
textModifier: Modifier = Modifier,
6364
placeholder: String = "",
6465
minLines: Int = 1,
6566
maxLines: Int = 4,
@@ -144,7 +145,8 @@ fun TextInput(
144145
contentPadding = contentPadding,
145146
textFieldAlignment = textFieldAlignment,
146147
shape = shape,
147-
innerTextField = it
148+
innerTextField = it,
149+
textModifier = textModifier,
148150
)
149151
},
150152
scrollState = scrollState
@@ -172,6 +174,7 @@ private fun DecoratorBox(
172174
placeholder: String,
173175
placeholderStyle: TextStyle,
174176
placeholderColor: Color,
177+
textModifier: Modifier = Modifier,
175178
borderColor: Color = CodeTheme.colors.brandLight,
176179
contentPadding: PaddingValues,
177180
leadingIcon: (@Composable () -> Unit)?,
@@ -197,7 +200,7 @@ private fun DecoratorBox(
197200
.weight(1f),
198201
contentAlignment = textFieldAlignment
199202
) {
200-
Box(modifier = Modifier.padding(contentPadding)) {
203+
Box(modifier = Modifier.padding(contentPadding).then(textModifier)) {
201204
innerTextField()
202205
}
203206
if (state.text.isEmpty() && placeholder.isNotEmpty()) {

0 commit comments

Comments
 (0)