Compare commits
No commits in common. "ea22a66fa6e4744715d31019bd2efa25b2784ae8" and "fa202ff162b3bc3bf2cb6d165603e54514837506" have entirely different histories.
ea22a66fa6
...
fa202ff162
6
.github/renovate.json
vendored
6
.github/renovate.json
vendored
@ -1,6 +0,0 @@
|
|||||||
{
|
|
||||||
"$schema": "https://docs.renovatebot.com/renovate-schema.json",
|
|
||||||
"extends": [
|
|
||||||
"local>android/.github:renovate-config"
|
|
||||||
]
|
|
||||||
}
|
|
||||||
@ -5,12 +5,15 @@ This app contains an order flow for cupcakes with options for quantity, flavor,
|
|||||||
The order details get displayed on an order summary screen and can be shared to another app to
|
The order details get displayed on an order summary screen and can be shared to another app to
|
||||||
send the order.
|
send the order.
|
||||||
|
|
||||||
perubahan
|
TODO
|
||||||
|
|
||||||
|
|
||||||
Pre-requisites
|
Pre-requisites
|
||||||
--------------
|
--------------
|
||||||
* Experience with Kotlin syntax.
|
* Experience with Kotlin syntax.
|
||||||
* How to create and run a project in Android Studio.
|
* How to create and run a project in Android Studio.
|
||||||
* How to create composable functions
|
* How to create composable functions
|
||||||
|
* TODO
|
||||||
|
|
||||||
|
|
||||||
Getting Started
|
Getting Started
|
||||||
|
|||||||
@ -20,12 +20,12 @@ plugins {
|
|||||||
|
|
||||||
android {
|
android {
|
||||||
namespace = "com.example.cupcake"
|
namespace = "com.example.cupcake"
|
||||||
compileSdk = 34
|
compileSdk = 33
|
||||||
|
|
||||||
defaultConfig {
|
defaultConfig {
|
||||||
applicationId = "com.example.cupcake"
|
applicationId = "com.example.cupcake"
|
||||||
minSdk = 24
|
minSdk = 24
|
||||||
targetSdk = 34
|
targetSdk = 33
|
||||||
versionCode = 1
|
versionCode = 1
|
||||||
versionName = "1.0"
|
versionName = "1.0"
|
||||||
|
|
||||||
@ -56,7 +56,7 @@ android {
|
|||||||
compose = true
|
compose = true
|
||||||
}
|
}
|
||||||
composeOptions {
|
composeOptions {
|
||||||
kotlinCompilerExtensionVersion = "1.5.3"
|
kotlinCompilerExtensionVersion = "1.4.7"
|
||||||
}
|
}
|
||||||
packaging {
|
packaging {
|
||||||
resources {
|
resources {
|
||||||
@ -67,24 +67,24 @@ android {
|
|||||||
|
|
||||||
dependencies {
|
dependencies {
|
||||||
|
|
||||||
implementation(platform("androidx.compose:compose-bom:2023.10.01"))
|
implementation(platform("androidx.compose:compose-bom:2023.05.01"))
|
||||||
implementation("androidx.activity:activity-compose:1.8.0")
|
implementation("androidx.activity:activity-compose:1.7.2")
|
||||||
implementation("androidx.compose.material3:material3")
|
implementation("androidx.compose.material3:material3")
|
||||||
implementation("androidx.compose.runtime:runtime")
|
implementation("androidx.compose.runtime:runtime")
|
||||||
implementation("androidx.compose.runtime:runtime-livedata")
|
implementation("androidx.compose.runtime:runtime-livedata")
|
||||||
implementation("androidx.compose.ui:ui")
|
implementation("androidx.compose.ui:ui")
|
||||||
implementation("androidx.compose.ui:ui-graphics")
|
implementation("androidx.compose.ui:ui-graphics")
|
||||||
implementation("androidx.compose.ui:ui-tooling-preview")
|
implementation("androidx.compose.ui:ui-tooling-preview")
|
||||||
implementation("androidx.core:core-ktx:1.12.0")
|
implementation("androidx.core:core-ktx:1.10.1")
|
||||||
implementation("androidx.lifecycle:lifecycle-livedata-ktx:${rootProject.extra["lifecycle_version"]}")
|
implementation("androidx.lifecycle:lifecycle-livedata-ktx:${rootProject.extra["lifecycle_version"]}")
|
||||||
implementation("androidx.lifecycle:lifecycle-runtime-ktx:${rootProject.extra["lifecycle_version"]}")
|
implementation("androidx.lifecycle:lifecycle-runtime-ktx:${rootProject.extra["lifecycle_version"]}")
|
||||||
implementation("androidx.lifecycle:lifecycle-viewmodel-ktx:${rootProject.extra["lifecycle_version"]}")
|
implementation("androidx.lifecycle:lifecycle-viewmodel-ktx:${rootProject.extra["lifecycle_version"]}")
|
||||||
implementation("androidx.lifecycle:lifecycle-viewmodel-savedstate:${rootProject.extra["lifecycle_version"]}")
|
implementation("androidx.lifecycle:lifecycle-viewmodel-savedstate:${rootProject.extra["lifecycle_version"]}")
|
||||||
implementation("androidx.navigation:navigation-compose:2.7.4")
|
implementation("androidx.navigation:navigation-compose:2.5.3")
|
||||||
|
|
||||||
androidTestImplementation(platform("androidx.compose:compose-bom:2023.10.01"))
|
androidTestImplementation(platform("androidx.compose:compose-bom:2023.05.01"))
|
||||||
androidTestImplementation("androidx.compose.ui:ui-test-junit4")
|
androidTestImplementation("androidx.compose.ui:ui-test-junit4")
|
||||||
androidTestImplementation("androidx.navigation:navigation-testing:2.7.4")
|
androidTestImplementation("androidx.navigation:navigation-testing:2.5.3")
|
||||||
androidTestImplementation("androidx.test.espresso:espresso-intents:3.5.1")
|
androidTestImplementation("androidx.test.espresso:espresso-intents:3.5.1")
|
||||||
androidTestImplementation("androidx.test.ext:junit:1.1.5")
|
androidTestImplementation("androidx.test.ext:junit:1.1.5")
|
||||||
|
|
||||||
|
|||||||
@ -76,25 +76,25 @@ class CupcakeOrderScreenTest {
|
|||||||
@Test
|
@Test
|
||||||
fun selectOptionScreen_verifyContent() {
|
fun selectOptionScreen_verifyContent() {
|
||||||
// Given list of options
|
// Given list of options
|
||||||
val flavors = listOf("Vanilla", "Chocolate", "Hazelnut", "Cookie", "Mango")
|
val flavours = listOf("Vanilla", "Chocolate", "Hazelnut", "Cookie", "Mango")
|
||||||
// And subtotal
|
// And sub total
|
||||||
val subtotal = "$100"
|
val subTotal = "$100"
|
||||||
|
|
||||||
// When SelectOptionScreen is loaded
|
// When SelectOptionScreen is loaded
|
||||||
composeTestRule.setContent {
|
composeTestRule.setContent {
|
||||||
SelectOptionScreen(subtotal = subtotal, options = flavors)
|
SelectOptionScreen(subtotal = subTotal, options = flavours)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Then all the options are displayed on the screen.
|
// Then all the options are displayed on the screen.
|
||||||
flavors.forEach { flavor ->
|
flavours.forEach { flavour ->
|
||||||
composeTestRule.onNodeWithText(flavor).assertIsDisplayed()
|
composeTestRule.onNodeWithText(flavour).assertIsDisplayed()
|
||||||
}
|
}
|
||||||
|
|
||||||
// And then the subtotal is displayed correctly.
|
// And then the subtotal is displayed correctly.
|
||||||
composeTestRule.onNodeWithText(
|
composeTestRule.onNodeWithText(
|
||||||
composeTestRule.activity.getString(
|
composeTestRule.activity.getString(
|
||||||
R.string.subtotal_price,
|
R.string.subtotal_price,
|
||||||
subtotal
|
subTotal
|
||||||
)
|
)
|
||||||
).assertIsDisplayed()
|
).assertIsDisplayed()
|
||||||
|
|
||||||
@ -148,6 +148,6 @@ class CupcakeOrderScreenTest {
|
|||||||
R.string.subtotal_price,
|
R.string.subtotal_price,
|
||||||
fakeOrderUiState.price
|
fakeOrderUiState.price
|
||||||
)
|
)
|
||||||
).assertIsDisplayed()
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -21,8 +21,6 @@ import androidx.annotation.StringRes
|
|||||||
import androidx.compose.foundation.layout.fillMaxHeight
|
import androidx.compose.foundation.layout.fillMaxHeight
|
||||||
import androidx.compose.foundation.layout.fillMaxSize
|
import androidx.compose.foundation.layout.fillMaxSize
|
||||||
import androidx.compose.foundation.layout.padding
|
import androidx.compose.foundation.layout.padding
|
||||||
import androidx.compose.foundation.rememberScrollState
|
|
||||||
import androidx.compose.foundation.verticalScroll
|
|
||||||
import androidx.compose.material.icons.Icons
|
import androidx.compose.material.icons.Icons
|
||||||
import androidx.compose.material.icons.filled.ArrowBack
|
import androidx.compose.material.icons.filled.ArrowBack
|
||||||
import androidx.compose.material3.Icon
|
import androidx.compose.material3.Icon
|
||||||
@ -117,10 +115,7 @@ fun CupcakeApp(
|
|||||||
NavHost(
|
NavHost(
|
||||||
navController = navController,
|
navController = navController,
|
||||||
startDestination = CupcakeScreen.Start.name,
|
startDestination = CupcakeScreen.Start.name,
|
||||||
modifier = Modifier
|
modifier = Modifier.padding(innerPadding)
|
||||||
.fillMaxSize()
|
|
||||||
.verticalScroll(rememberScrollState())
|
|
||||||
.padding(innerPadding)
|
|
||||||
) {
|
) {
|
||||||
composable(route = CupcakeScreen.Start.name) {
|
composable(route = CupcakeScreen.Start.name) {
|
||||||
StartOrderScreen(
|
StartOrderScreen(
|
||||||
|
|||||||
@ -18,13 +18,13 @@ package com.example.cupcake
|
|||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
import androidx.activity.ComponentActivity
|
import androidx.activity.ComponentActivity
|
||||||
import androidx.activity.compose.setContent
|
import androidx.activity.compose.setContent
|
||||||
import androidx.activity.enableEdgeToEdge
|
import androidx.core.view.WindowCompat
|
||||||
import com.example.cupcake.ui.theme.CupcakeTheme
|
import com.example.cupcake.ui.theme.CupcakeTheme
|
||||||
|
|
||||||
class MainActivity : ComponentActivity() {
|
class MainActivity : ComponentActivity() {
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
override fun onCreate(savedInstanceState: Bundle?) {
|
||||||
enableEdgeToEdge()
|
|
||||||
super.onCreate(savedInstanceState)
|
super.onCreate(savedInstanceState)
|
||||||
|
WindowCompat.setDecorFitsSystemWindows(window, false)
|
||||||
setContent {
|
setContent {
|
||||||
CupcakeTheme {
|
CupcakeTheme {
|
||||||
CupcakeApp()
|
CupcakeApp()
|
||||||
|
|||||||
@ -19,16 +19,16 @@ import com.example.cupcake.R
|
|||||||
|
|
||||||
object DataSource {
|
object DataSource {
|
||||||
val flavors = listOf(
|
val flavors = listOf(
|
||||||
R.string.coconut,
|
R.string.vanilla,
|
||||||
R.string.chocolate,
|
R.string.chocolate,
|
||||||
R.string.cheese,
|
R.string.red_velvet,
|
||||||
R.string.mocha,
|
R.string.salted_caramel,
|
||||||
R.string.coffee
|
R.string.coffee
|
||||||
)
|
)
|
||||||
|
|
||||||
val quantityOptions = listOf(
|
val quantityOptions = listOf(
|
||||||
Pair(R.string.one_bread, 1),
|
Pair(R.string.one_cupcake, 1),
|
||||||
Pair(R.string.six_bread, 6),
|
Pair(R.string.six_cupcakes, 6),
|
||||||
Pair(R.string.twelve_bread, 12)
|
Pair(R.string.twelve_cupcakes, 12)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
@ -27,10 +27,10 @@ import java.util.Calendar
|
|||||||
import java.util.Locale
|
import java.util.Locale
|
||||||
|
|
||||||
/** Price for a single cupcake */
|
/** Price for a single cupcake */
|
||||||
private const val PRICE_PER_BREAD = 2.50
|
private const val PRICE_PER_CUPCAKE = 2.00
|
||||||
|
|
||||||
/** Additional cost for same day pickup of an order */
|
/** Additional cost for same day pickup of an order */
|
||||||
private const val PRICE_FOR_SAME_DAY_PICKUP = 4.00
|
private const val PRICE_FOR_SAME_DAY_PICKUP = 3.00
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* [OrderViewModel] holds information about a cupcake order in terms of quantity, flavor, and
|
* [OrderViewModel] holds information about a cupcake order in terms of quantity, flavor, and
|
||||||
@ -92,7 +92,7 @@ class OrderViewModel : ViewModel() {
|
|||||||
quantity: Int = _uiState.value.quantity,
|
quantity: Int = _uiState.value.quantity,
|
||||||
pickupDate: String = _uiState.value.date
|
pickupDate: String = _uiState.value.date
|
||||||
): String {
|
): String {
|
||||||
var calculatedPrice = quantity * PRICE_PER_BREAD
|
var calculatedPrice = quantity * PRICE_PER_CUPCAKE
|
||||||
// If the user selected the first option (today) for pickup, add the surcharge
|
// If the user selected the first option (today) for pickup, add the surcharge
|
||||||
if (pickupOptions()[0] == pickupDate) {
|
if (pickupOptions()[0] == pickupDate) {
|
||||||
calculatedPrice += PRICE_FOR_SAME_DAY_PICKUP
|
calculatedPrice += PRICE_FOR_SAME_DAY_PICKUP
|
||||||
|
|||||||
@ -39,7 +39,6 @@ import androidx.compose.ui.res.stringResource
|
|||||||
import androidx.compose.ui.tooling.preview.Preview
|
import androidx.compose.ui.tooling.preview.Preview
|
||||||
import com.example.cupcake.R
|
import com.example.cupcake.R
|
||||||
import com.example.cupcake.ui.components.FormattedPriceLabel
|
import com.example.cupcake.ui.components.FormattedPriceLabel
|
||||||
import com.example.cupcake.ui.theme.CupcakeTheme
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Composable that displays the list of items as [RadioButton] options,
|
* Composable that displays the list of items as [RadioButton] options,
|
||||||
@ -55,14 +54,14 @@ fun SelectOptionScreen(
|
|||||||
onCancelButtonClicked: () -> Unit = {},
|
onCancelButtonClicked: () -> Unit = {},
|
||||||
onNextButtonClicked: () -> Unit = {},
|
onNextButtonClicked: () -> Unit = {},
|
||||||
modifier: Modifier = Modifier
|
modifier: Modifier = Modifier
|
||||||
) {
|
){
|
||||||
var selectedValue by rememberSaveable { mutableStateOf("") }
|
var selectedValue by rememberSaveable { mutableStateOf("") }
|
||||||
|
|
||||||
Column(
|
Column(
|
||||||
modifier = modifier,
|
modifier = modifier,
|
||||||
verticalArrangement = Arrangement.SpaceBetween
|
verticalArrangement = Arrangement.SpaceBetween
|
||||||
) {
|
) {
|
||||||
Column(modifier = Modifier.padding(dimensionResource(R.dimen.padding_medium))) {
|
Column(modifier = Modifier.padding(dimensionResource(R.dimen.padding_medium))){
|
||||||
options.forEach { item ->
|
options.forEach { item ->
|
||||||
Row(
|
Row(
|
||||||
modifier = Modifier.selectable(
|
modifier = Modifier.selectable(
|
||||||
@ -73,7 +72,7 @@ fun SelectOptionScreen(
|
|||||||
}
|
}
|
||||||
),
|
),
|
||||||
verticalAlignment = Alignment.CenterVertically
|
verticalAlignment = Alignment.CenterVertically
|
||||||
) {
|
){
|
||||||
RadioButton(
|
RadioButton(
|
||||||
selected = selectedValue == item,
|
selected = selectedValue == item,
|
||||||
onClick = {
|
onClick = {
|
||||||
@ -101,14 +100,12 @@ fun SelectOptionScreen(
|
|||||||
Row(
|
Row(
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
.fillMaxWidth()
|
.fillMaxWidth()
|
||||||
.padding(dimensionResource(R.dimen.padding_medium)),
|
.padding(dimensionResource(R.dimen.padding_medium))
|
||||||
|
.weight(1f, false),
|
||||||
horizontalArrangement = Arrangement.spacedBy(dimensionResource(R.dimen.padding_medium)),
|
horizontalArrangement = Arrangement.spacedBy(dimensionResource(R.dimen.padding_medium)),
|
||||||
verticalAlignment = Alignment.Bottom
|
verticalAlignment = Alignment.Bottom
|
||||||
) {
|
){
|
||||||
OutlinedButton(
|
OutlinedButton(modifier = Modifier.weight(1f), onClick = onCancelButtonClicked) {
|
||||||
modifier = Modifier.weight(1f),
|
|
||||||
onClick = onCancelButtonClicked
|
|
||||||
) {
|
|
||||||
Text(stringResource(R.string.cancel))
|
Text(stringResource(R.string.cancel))
|
||||||
}
|
}
|
||||||
Button(
|
Button(
|
||||||
@ -126,12 +123,10 @@ fun SelectOptionScreen(
|
|||||||
|
|
||||||
@Preview
|
@Preview
|
||||||
@Composable
|
@Composable
|
||||||
fun SelectOptionPreview() {
|
fun SelectOptionPreview(){
|
||||||
CupcakeTheme {
|
|
||||||
SelectOptionScreen(
|
SelectOptionScreen(
|
||||||
subtotal = "299.99",
|
subtotal = "299.99",
|
||||||
options = listOf("Option 1", "Option 2", "Option 3", "Option 4"),
|
options = listOf("Option 1", "Option 2", "Option 3", "Option 4"),
|
||||||
modifier = Modifier.fillMaxHeight()
|
modifier = Modifier.fillMaxHeight()
|
||||||
)
|
)
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -19,7 +19,9 @@ import androidx.annotation.StringRes
|
|||||||
import androidx.compose.foundation.Image
|
import androidx.compose.foundation.Image
|
||||||
import androidx.compose.foundation.layout.Arrangement
|
import androidx.compose.foundation.layout.Arrangement
|
||||||
import androidx.compose.foundation.layout.Column
|
import androidx.compose.foundation.layout.Column
|
||||||
|
import androidx.compose.foundation.layout.Row
|
||||||
import androidx.compose.foundation.layout.Spacer
|
import androidx.compose.foundation.layout.Spacer
|
||||||
|
import androidx.compose.foundation.layout.fillMaxHeight
|
||||||
import androidx.compose.foundation.layout.fillMaxSize
|
import androidx.compose.foundation.layout.fillMaxSize
|
||||||
import androidx.compose.foundation.layout.fillMaxWidth
|
import androidx.compose.foundation.layout.fillMaxWidth
|
||||||
import androidx.compose.foundation.layout.height
|
import androidx.compose.foundation.layout.height
|
||||||
@ -39,7 +41,6 @@ import androidx.compose.ui.tooling.preview.Preview
|
|||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
import com.example.cupcake.R
|
import com.example.cupcake.R
|
||||||
import com.example.cupcake.data.DataSource
|
import com.example.cupcake.data.DataSource
|
||||||
import com.example.cupcake.ui.theme.CupcakeTheme
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Composable that allows the user to select the desired cupcake quantity and expects
|
* Composable that allows the user to select the desired cupcake quantity and expects
|
||||||
@ -51,7 +52,7 @@ fun StartOrderScreen(
|
|||||||
quantityOptions: List<Pair<Int, Int>>,
|
quantityOptions: List<Pair<Int, Int>>,
|
||||||
onNextButtonClicked: (Int) -> Unit,
|
onNextButtonClicked: (Int) -> Unit,
|
||||||
modifier: Modifier = Modifier
|
modifier: Modifier = Modifier
|
||||||
) {
|
){
|
||||||
Column(
|
Column(
|
||||||
modifier = modifier,
|
modifier = modifier,
|
||||||
verticalArrangement = Arrangement.SpaceBetween
|
verticalArrangement = Arrangement.SpaceBetween
|
||||||
@ -63,17 +64,18 @@ fun StartOrderScreen(
|
|||||||
) {
|
) {
|
||||||
Spacer(modifier = Modifier.height(dimensionResource(R.dimen.padding_medium)))
|
Spacer(modifier = Modifier.height(dimensionResource(R.dimen.padding_medium)))
|
||||||
Image(
|
Image(
|
||||||
painter = painterResource(R.drawable.bread),//bagian yang diganti gambar
|
painter = painterResource(R.drawable.cupcake),
|
||||||
contentDescription = null,
|
contentDescription = null,
|
||||||
modifier = Modifier.width(300.dp)
|
modifier = Modifier.width(300.dp)
|
||||||
)
|
)
|
||||||
Spacer(modifier = Modifier.height(dimensionResource(R.dimen.padding_medium)))
|
Spacer(modifier = Modifier.height(dimensionResource(R.dimen.padding_medium)))
|
||||||
Text(
|
Text(
|
||||||
text = stringResource(R.string.order_bread),
|
text = stringResource(R.string.order_cupcakes),
|
||||||
style = MaterialTheme.typography.headlineSmall
|
style = MaterialTheme.typography.headlineSmall
|
||||||
)
|
)
|
||||||
Spacer(modifier = Modifier.height(dimensionResource(R.dimen.padding_small)))
|
Spacer(modifier = Modifier.height(dimensionResource(R.dimen.padding_small)))
|
||||||
}
|
}
|
||||||
|
Row(modifier = Modifier.weight(1f, false)) {
|
||||||
Column(
|
Column(
|
||||||
modifier = Modifier.fillMaxWidth(),
|
modifier = Modifier.fillMaxWidth(),
|
||||||
horizontalAlignment = Alignment.CenterHorizontally,
|
horizontalAlignment = Alignment.CenterHorizontally,
|
||||||
@ -84,12 +86,12 @@ fun StartOrderScreen(
|
|||||||
quantityOptions.forEach { item ->
|
quantityOptions.forEach { item ->
|
||||||
SelectQuantityButton(
|
SelectQuantityButton(
|
||||||
labelResourceId = item.first,
|
labelResourceId = item.first,
|
||||||
onClick = { onNextButtonClicked(item.second) },
|
onClick = { onNextButtonClicked(item.second) }
|
||||||
modifier = Modifier.fillMaxWidth(),
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -101,7 +103,7 @@ fun SelectQuantityButton(
|
|||||||
@StringRes labelResourceId: Int,
|
@StringRes labelResourceId: Int,
|
||||||
onClick: () -> Unit,
|
onClick: () -> Unit,
|
||||||
modifier: Modifier = Modifier
|
modifier: Modifier = Modifier
|
||||||
) {
|
){
|
||||||
Button(
|
Button(
|
||||||
onClick = onClick,
|
onClick = onClick,
|
||||||
modifier = modifier.widthIn(min = 250.dp)
|
modifier = modifier.widthIn(min = 250.dp)
|
||||||
@ -112,14 +114,10 @@ fun SelectQuantityButton(
|
|||||||
|
|
||||||
@Preview
|
@Preview
|
||||||
@Composable
|
@Composable
|
||||||
fun StartOrderPreview() {
|
fun StartOrderPreview(){
|
||||||
CupcakeTheme {
|
|
||||||
StartOrderScreen(
|
StartOrderScreen(
|
||||||
quantityOptions = DataSource.quantityOptions,
|
quantityOptions = DataSource.quantityOptions,
|
||||||
onNextButtonClicked = {},
|
onNextButtonClicked = {},
|
||||||
modifier = Modifier
|
modifier = Modifier.fillMaxSize().padding(dimensionResource(R.dimen.padding_medium))
|
||||||
.fillMaxSize()
|
|
||||||
.padding(dimensionResource(R.dimen.padding_medium))
|
|
||||||
)
|
)
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -38,7 +38,6 @@ import androidx.compose.ui.tooling.preview.Preview
|
|||||||
import com.example.cupcake.R
|
import com.example.cupcake.R
|
||||||
import com.example.cupcake.data.OrderUiState
|
import com.example.cupcake.data.OrderUiState
|
||||||
import com.example.cupcake.ui.components.FormattedPriceLabel
|
import com.example.cupcake.ui.components.FormattedPriceLabel
|
||||||
import com.example.cupcake.ui.theme.CupcakeTheme
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This composable expects [orderUiState] that represents the order state, [onCancelButtonClicked]
|
* This composable expects [orderUiState] that represents the order state, [onCancelButtonClicked]
|
||||||
@ -51,11 +50,11 @@ fun OrderSummaryScreen(
|
|||||||
onCancelButtonClicked: () -> Unit,
|
onCancelButtonClicked: () -> Unit,
|
||||||
onSendButtonClicked: (String, String) -> Unit,
|
onSendButtonClicked: (String, String) -> Unit,
|
||||||
modifier: Modifier = Modifier
|
modifier: Modifier = Modifier
|
||||||
) {
|
){
|
||||||
val resources = LocalContext.current.resources
|
val resources = LocalContext.current.resources
|
||||||
|
|
||||||
val numberOfCupcakes = resources.getQuantityString(
|
val numberOfCupcakes = resources.getQuantityString(
|
||||||
R.plurals.bread,
|
R.plurals.cupcakes,
|
||||||
orderUiState.quantity,
|
orderUiState.quantity,
|
||||||
orderUiState.quantity
|
orderUiState.quantity
|
||||||
)
|
)
|
||||||
@ -67,7 +66,7 @@ fun OrderSummaryScreen(
|
|||||||
orderUiState.date,
|
orderUiState.date,
|
||||||
orderUiState.quantity
|
orderUiState.quantity
|
||||||
)
|
)
|
||||||
val newOrder = stringResource(R.string.new_bread_order)
|
val newOrder = stringResource(R.string.new_cupcake_order)
|
||||||
//Create a list of order summary to display
|
//Create a list of order summary to display
|
||||||
val items = listOf(
|
val items = listOf(
|
||||||
// Summary line 1: display selected quantity
|
// Summary line 1: display selected quantity
|
||||||
@ -98,7 +97,9 @@ fun OrderSummaryScreen(
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
Row(
|
Row(
|
||||||
modifier = Modifier.padding(dimensionResource(R.dimen.padding_medium))
|
modifier = Modifier
|
||||||
|
.weight(1f, false)
|
||||||
|
.padding(dimensionResource(R.dimen.padding_medium))
|
||||||
) {
|
) {
|
||||||
Column(
|
Column(
|
||||||
verticalArrangement = Arrangement.spacedBy(dimensionResource(R.dimen.padding_small))
|
verticalArrangement = Arrangement.spacedBy(dimensionResource(R.dimen.padding_small))
|
||||||
@ -122,13 +123,11 @@ fun OrderSummaryScreen(
|
|||||||
|
|
||||||
@Preview
|
@Preview
|
||||||
@Composable
|
@Composable
|
||||||
fun OrderSummaryPreview() {
|
fun OrderSummaryPreview(){
|
||||||
CupcakeTheme {
|
|
||||||
OrderSummaryScreen(
|
OrderSummaryScreen(
|
||||||
orderUiState = OrderUiState(0, "Test", "Test", "$300.00"),
|
orderUiState = OrderUiState(0, "Test", "Test", "$300.00"),
|
||||||
onSendButtonClicked = { subject: String, summary: String -> },
|
onSendButtonClicked = { subject: String, summary: String -> },
|
||||||
onCancelButtonClicked = {},
|
onCancelButtonClicked = {},
|
||||||
modifier = Modifier.fillMaxHeight()
|
modifier = Modifier.fillMaxHeight()
|
||||||
)
|
)
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,39 +0,0 @@
|
|||||||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
|
||||||
android:width="800dp"
|
|
||||||
android:height="800dp"
|
|
||||||
android:viewportWidth="1024"
|
|
||||||
android:viewportHeight="1024">
|
|
||||||
<path
|
|
||||||
android:pathData="M175.4,866.3c39.1,25.7 166.1,114.6 488.5,-229.7s223,-425.9 196.2,-454.9c-26.8,-29 -263.6,-149.6 -556,122.5C21.6,567 175.4,866.3 175.4,866.3z"
|
|
||||||
android:fillColor="#EAAD6A"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M241.9,696.5s26.7,26.1 48.6,4.5c21.9,-21.7 -2.2,-40.2 -2.2,-40.2L171.6,514l-27.3,67.4 97.6,115.1zM623.3,323.5s26.7,26.1 48.6,4.5c21.9,-21.7 -2.2,-40.2 -2.2,-40.2L565.9,153.9l-62.1,19.2 119.5,150.4zM386.5,463.8s26.7,26.1 48.6,4.5c21.9,-21.7 -2.2,-40.2 -2.2,-40.2L322.4,287.5 280.8,332l105.7,131.8z"
|
|
||||||
android:fillColor="#FFC661"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M604.8,577.4c-227.5,243 -389.5,280.3 -455.1,229.3 10.4,34.3 20.7,54.5 20.7,54.5 39.1,25.7 166.1,114.6 488.5,-229.7s223,-425.9 196.2,-454.9c-6.1,-6.6 -22.9,-17.8 -48.6,-28.1 36.5,54.7 15.2,197.1 -201.7,428.9z"
|
|
||||||
android:fillColor="#D19152"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M310.5,281c-4.3,4 -8.6,8.1 -12.9,12.4 -0.7,0.7 -1.5,1.4 -2.2,2.1 -0.4,0.4 -0.7,0.8 -1.1,1.1 -3.8,3.8 -7.7,7.9 -11.7,12.2 -183.1,193.9 -212.5,464 -112.4,564.1 90.5,90.5 259.8,16.9 489.7,-213 229.8,-229.8 303.5,-399.2 213,-489.7C773.1,70.4 504.2,99.3 310.5,281zM659.6,288.6c3.5,3.1 5.5,7.4 5.6,12 0.2,4.7 -1.6,9.1 -4.9,12.4 -6.3,6.3 -16.3,6.6 -23,0.7l-2.8,-2.4c-37,-32.7 -69.3,-70.4 -95.9,-112L524.3,177c1.2,-0.5 2.5,-0.9 3.7,-1.4 8.8,-3.4 17.6,-6.6 26.3,-9.4 0.4,-0.1 0.7,-0.2 1.1,-0.4l3.4,5.3c28.1,43.6 61.9,83.2 100.8,117.5zM434.6,443.1c3.5,3.1 5.5,7.4 5.6,12 0.2,4.7 -1.6,9.1 -4.9,12.4 -6.3,6.3 -16.3,6.6 -23,0.7l-2.8,-2.4c-37,-32.7 -69.3,-70.4 -95.9,-112l-14.9,-23.4c6.7,-7.2 13.6,-14.3 20.7,-21.2 0.8,-0.8 1.7,-1.6 2.5,-2.4l11.9,18.7c28.1,43.6 61.9,83.2 100.8,117.6zM280.1,668.1c3.5,3.1 5.5,7.4 5.6,12 0.2,4.7 -1.6,9.1 -4.9,12.4 -6.3,6.3 -16.3,6.6 -23,0.7l-2.8,-2.4c-37,-32.7 -69.3,-70.4 -95.8,-112l-0.4,-0.6c3.7,-13.1 7.9,-26.5 12.8,-39.9l7.8,12.2c28,43.6 61.9,83.2 100.7,117.6zM641.1,641.1c-124.2,124.2 -348,317 -452,213 -47.2,-47.2 -60.4,-139.1 -38.7,-241.5 25.2,35.9 54.2,69 87.2,98.1l2.8,2.4c17.1,15.1 43.2,14.3 59.4,-1.8 8.4,-8.4 13.1,-20.1 12.7,-32 -0.4,-11.9 -5.7,-23.3 -14.6,-31.2 -37,-32.7 -69.3,-70.4 -95.9,-112l-18.1,-28.3c23,-54 55.2,-107.7 96.7,-156.7l10.9,17c27.9,43.7 61.8,83.3 100.6,117.6l2.8,2.4c17.1,15.1 43.2,14.4 59.4,-1.8 8.4,-8.4 13.1,-20.1 12.7,-32 -0.4,-11.9 -5.7,-23.3 -14.6,-31.2 -37,-32.7 -69.3,-70.4 -95.9,-112L342,288.4c49,-43.2 103.1,-76.9 157.6,-101.2l16.8,26.3c27.9,43.7 61.8,83.3 100.6,117.6l2.8,2.4c17.1,15.1 43.2,14.3 59.4,-1.8 8.4,-8.4 13.1,-20.1 12.7,-32 -0.4,-11.9 -5.7,-23.3 -14.6,-31.2 -36.7,-32.4 -68.6,-69.8 -95.1,-110.9 114.4,-31.4 220.1,-20.6 272,31.3 103.9,104.2 -88.9,328 -213.1,452.2z"
|
|
||||||
android:fillColor="#004364"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M462,257.8m-15.4,0a15.4,15.4 0,1 0,30.8 0,15.4 15.4,0 1,0 -30.8,0Z"
|
|
||||||
android:fillColor="#004364"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M686.7,188.2m-15.4,0a15.4,15.4 0,1 0,30.8 0,15.4 15.4,0 1,0 -30.8,0Z"
|
|
||||||
android:fillColor="#004364"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M681,520.2m-15.4,0a15.4,15.4 0,1 0,30.8 0,15.4 15.4,0 1,0 -30.8,0Z"
|
|
||||||
android:fillColor="#004364"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M607,601.3m-15.4,0a15.4,15.4 0,1 0,30.8 0,15.4 15.4,0 1,0 -30.8,0Z"
|
|
||||||
android:fillColor="#004364"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M249.5,457.8m-15.4,0a15.4,15.4 0,1 0,30.8 0,15.4 15.4,0 1,0 -30.8,0Z"
|
|
||||||
android:fillColor="#004364"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M392.9,292.7m-15.4,0a15.4,15.4 0,1 0,30.8 0,15.4 15.4,0 1,0 -30.8,0Z"
|
|
||||||
android:fillColor="#004364"/>
|
|
||||||
<path
|
|
||||||
android:pathData="M197,758.3m-15.4,0a15.4,15.4 0,1 0,30.8 0,15.4 15.4,0 1,0 -30.8,0Z"
|
|
||||||
android:fillColor="#004364"/>
|
|
||||||
</vector>
|
|
||||||
Binary file not shown.
|
Before Width: | Height: | Size: 361 KiB |
@ -14,16 +14,16 @@
|
|||||||
limitations under the License.
|
limitations under the License.
|
||||||
-->
|
-->
|
||||||
<resources>
|
<resources>
|
||||||
<string name="app_name">Bread</string>
|
<string name="app_name">Cupcake</string>
|
||||||
<string name="order_bread">Order Bread</string>
|
<string name="order_cupcakes">Order Cupcakes</string>
|
||||||
<string name="one_bread">One Bread</string>
|
<string name="one_cupcake">One Cupcake</string>
|
||||||
<string name="six_bread">Six Breads</string>
|
<string name="six_cupcakes">Six Cupcakes</string>
|
||||||
<string name="twelve_bread">Twelve Breads</string>
|
<string name="twelve_cupcakes">Twelve Cupcakes</string>
|
||||||
<string name="choose_flavor">Choose Flavor</string>
|
<string name="choose_flavor">Choose Flavor</string>
|
||||||
<string name="coconut">Coconut</string>
|
<string name="vanilla">Vanilla</string>
|
||||||
<string name="chocolate">Chocolate</string>
|
<string name="chocolate">Chocolate</string>
|
||||||
<string name="cheese">Cheese</string>
|
<string name="red_velvet">Red Velvet</string>
|
||||||
<string name="mocha">Mocha</string>
|
<string name="salted_caramel">Salted Caramel</string>
|
||||||
<string name="coffee">Coffee</string>
|
<string name="coffee">Coffee</string>
|
||||||
<string name="special_flavor">Special Flavor</string>
|
<string name="special_flavor">Special Flavor</string>
|
||||||
<string name="cancel">Cancel</string>
|
<string name="cancel">Cancel</string>
|
||||||
@ -36,11 +36,11 @@
|
|||||||
<string name="pickup_date">Pickup date</string>
|
<string name="pickup_date">Pickup date</string>
|
||||||
<string name="subtotal_price">Subtotal %s</string>
|
<string name="subtotal_price">Subtotal %s</string>
|
||||||
<string name="total_price">Total %s</string>
|
<string name="total_price">Total %s</string>
|
||||||
<string name="new_bread_order">New Bread Order</string>
|
<string name="new_cupcake_order">New Cupcake Order</string>
|
||||||
<string name="order_details">Quantity: %1$s \nFlavor: %2$s \nPickup date: %3$s \nTotal: %4$s \n\nThank you!</string>
|
<string name="order_details">Quantity: %1$s \nFlavor: %2$s \nPickup date: %3$s \nTotal: %4$s \n\nThank you!</string>
|
||||||
<string name="back_button">Back</string>
|
<string name="back_button">Back</string>
|
||||||
<plurals name="bread">
|
<plurals name="cupcakes">
|
||||||
<item quantity="one">%d bread</item>
|
<item quantity="one">%d cupcake</item>
|
||||||
<item quantity="other">%d bread</item>
|
<item quantity="other">%d cupcakes</item>
|
||||||
</plurals>
|
</plurals>
|
||||||
</resources>
|
</resources>
|
||||||
|
|||||||
@ -16,11 +16,11 @@
|
|||||||
// Top-level build file where you can add configuration options common to all sub-projects/modules.
|
// Top-level build file where you can add configuration options common to all sub-projects/modules.
|
||||||
buildscript {
|
buildscript {
|
||||||
extra.apply {
|
extra.apply {
|
||||||
set("lifecycle_version", "2.6.2")
|
set("lifecycle_version", "2.6.1")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
plugins {
|
plugins {
|
||||||
id("com.android.application") version "8.1.2" apply false
|
id("com.android.application") version "8.0.2" apply false
|
||||||
id("com.android.library") version "8.1.2" apply false
|
id("com.android.library") version "8.0.2" apply false
|
||||||
id("org.jetbrains.kotlin.android") version "1.9.10" apply false
|
id("org.jetbrains.kotlin.android") version "1.8.21" apply false
|
||||||
}
|
}
|
||||||
|
|||||||
2
gradle/wrapper/gradle-wrapper.properties
vendored
2
gradle/wrapper/gradle-wrapper.properties
vendored
@ -1,6 +1,6 @@
|
|||||||
#Sun Mar 19 17:30:22 PDT 2023
|
#Sun Mar 19 17:30:22 PDT 2023
|
||||||
distributionBase=GRADLE_USER_HOME
|
distributionBase=GRADLE_USER_HOME
|
||||||
distributionPath=wrapper/dists
|
distributionPath=wrapper/dists
|
||||||
distributionUrl=https\://services.gradle.org/distributions/gradle-8.4-bin.zip
|
distributionUrl=https\://services.gradle.org/distributions/gradle-8.1.1-bin.zip
|
||||||
zipStoreBase=GRADLE_USER_HOME
|
zipStoreBase=GRADLE_USER_HOME
|
||||||
zipStorePath=wrapper/dists
|
zipStorePath=wrapper/dists
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user