Skip to content

Commit 4222251

Browse files
authored
Merge pull request #14769 from woocommerce/feat/WOOMOB-1157-POS-Orders-Details-Model
[POS Orders] Details State + View Model
2 parents 4ad858a + 6181054 commit 4222251

File tree

6 files changed

+692
-222
lines changed

6 files changed

+692
-222
lines changed
Lines changed: 283 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,283 @@
1+
package com.woocommerce.android.ui.woopos.orders
2+
3+
import androidx.compose.foundation.Image
4+
import androidx.compose.foundation.background
5+
import androidx.compose.foundation.layout.Arrangement
6+
import androidx.compose.foundation.layout.Box
7+
import androidx.compose.foundation.layout.Column
8+
import androidx.compose.foundation.layout.Row
9+
import androidx.compose.foundation.layout.Spacer
10+
import androidx.compose.foundation.layout.fillMaxHeight
11+
import androidx.compose.foundation.layout.fillMaxSize
12+
import androidx.compose.foundation.layout.fillMaxWidth
13+
import androidx.compose.foundation.layout.height
14+
import androidx.compose.foundation.layout.heightIn
15+
import androidx.compose.foundation.layout.padding
16+
import androidx.compose.foundation.layout.size
17+
import androidx.compose.foundation.layout.width
18+
import androidx.compose.foundation.rememberScrollState
19+
import androidx.compose.foundation.verticalScroll
20+
import androidx.compose.material.icons.Icons
21+
import androidx.compose.material.icons.outlined.Inventory2
22+
import androidx.compose.material3.MaterialTheme
23+
import androidx.compose.runtime.Composable
24+
import androidx.compose.ui.Alignment
25+
import androidx.compose.ui.Modifier
26+
import androidx.compose.ui.graphics.ColorFilter
27+
import androidx.compose.ui.layout.ContentScale
28+
import androidx.compose.ui.platform.LocalContext
29+
import androidx.compose.ui.res.stringResource
30+
import androidx.compose.ui.text.font.FontWeight
31+
import androidx.compose.ui.unit.dp
32+
import coil.compose.AsyncImage
33+
import coil.request.ImageRequest
34+
import com.woocommerce.android.R
35+
import com.woocommerce.android.ui.woopos.common.composeui.component.WooPosButton
36+
import com.woocommerce.android.ui.woopos.common.composeui.component.WooPosCard
37+
import com.woocommerce.android.ui.woopos.common.composeui.component.WooPosText
38+
import com.woocommerce.android.ui.woopos.common.composeui.component.WooPosToolbar
39+
import com.woocommerce.android.ui.woopos.common.composeui.designsystem.WooPosElevation
40+
import com.woocommerce.android.ui.woopos.common.composeui.designsystem.WooPosSpacing
41+
import com.woocommerce.android.ui.woopos.common.composeui.designsystem.WooPosTheme
42+
import com.woocommerce.android.ui.woopos.common.composeui.designsystem.WooPosTypography
43+
44+
@Composable
45+
fun OrderDetails(
46+
modifier: Modifier = Modifier,
47+
details: OrderDetailsViewState,
48+
onEmailReceiptButtonClicked: (Long) -> Unit = {}
49+
) {
50+
Column(modifier = modifier.fillMaxSize()) {
51+
WooPosToolbar(
52+
modifier = Modifier.fillMaxWidth(),
53+
titleText = details.number,
54+
onBackClicked = null
55+
)
56+
57+
Column(
58+
modifier = Modifier
59+
.fillMaxSize()
60+
.verticalScroll(rememberScrollState())
61+
.padding(
62+
start = WooPosSpacing.Large.value,
63+
end = WooPosSpacing.Large.value,
64+
top = WooPosSpacing.Medium.value,
65+
bottom = WooPosSpacing.XLarge.value
66+
),
67+
verticalArrangement = Arrangement.spacedBy(WooPosSpacing.Large.value)
68+
) {
69+
Row(
70+
modifier = Modifier.fillMaxWidth(),
71+
verticalAlignment = Alignment.CenterVertically
72+
) {
73+
Column(modifier = Modifier.weight(1f)) {
74+
WooPosText(
75+
text = details.dateTime,
76+
style = WooPosTypography.BodySmall,
77+
color = WooPosTheme.colors.onSurfaceVariantHighest
78+
)
79+
details.customerEmail?.takeIf { it.isNotBlank() }?.let {
80+
Spacer(Modifier.height(WooPosSpacing.XSmall.value))
81+
WooPosText(
82+
text = it,
83+
style = WooPosTypography.BodySmall,
84+
color = WooPosTheme.colors.onSurfaceVariantHighest
85+
)
86+
}
87+
Spacer(Modifier.height(WooPosSpacing.Small.value))
88+
OrderStatusBadge(details.status)
89+
}
90+
91+
WooPosButton(
92+
text = stringResource(R.string.woopos_orders_email_receipt),
93+
onClick = { onEmailReceiptButtonClicked(details.id) }
94+
)
95+
}
96+
97+
WooPosCard(
98+
shape = MaterialTheme.shapes.medium,
99+
backgroundColor = MaterialTheme.colorScheme.surface,
100+
elevation = WooPosElevation.Medium,
101+
shadowType = com.woocommerce.android.ui.woopos.common.composeui.component.ShadowType.Soft
102+
) {
103+
Column(Modifier.padding(WooPosSpacing.Medium.value)) {
104+
WooPosText(
105+
text = stringResource(R.string.woopos_orders_details_products_title),
106+
style = WooPosTypography.Heading
107+
)
108+
Spacer(Modifier.height(WooPosSpacing.Small.value))
109+
110+
details.lineItems.forEach { row ->
111+
Row(
112+
modifier = Modifier
113+
.fillMaxWidth()
114+
.padding(vertical = WooPosSpacing.Small.value),
115+
verticalAlignment = Alignment.CenterVertically
116+
) {
117+
OrderLineItemImage(imageUrl = row.imageUrl)
118+
119+
Column(Modifier.weight(1f)) {
120+
WooPosText(
121+
text = row.name,
122+
style = WooPosTypography.BodySmall,
123+
fontWeight = FontWeight.Medium
124+
)
125+
Spacer(Modifier.height(WooPosSpacing.XSmall.value))
126+
WooPosText(
127+
text = row.qtyAndUnitPrice,
128+
style = WooPosTypography.BodySmall,
129+
color = WooPosTheme.colors.onSurfaceVariantHighest
130+
)
131+
}
132+
WooPosText(
133+
text = row.lineTotal,
134+
style = WooPosTypography.BodySmall
135+
)
136+
}
137+
}
138+
}
139+
}
140+
141+
WooPosCard(
142+
shape = MaterialTheme.shapes.medium,
143+
backgroundColor = MaterialTheme.colorScheme.surface,
144+
elevation = WooPosElevation.Medium,
145+
shadowType = com.woocommerce.android.ui.woopos.common.composeui.component.ShadowType.Soft
146+
) {
147+
Column(Modifier.padding(WooPosSpacing.Medium.value)) {
148+
WooPosText(
149+
text = stringResource(R.string.woopos_orders_details_totals_title),
150+
style = WooPosTypography.Heading
151+
)
152+
Spacer(Modifier.height(WooPosSpacing.Small.value))
153+
154+
@Composable
155+
fun RowLine(label: String, value: String) {
156+
Row(
157+
Modifier
158+
.fillMaxWidth()
159+
.padding(vertical = WooPosSpacing.XSmall.value)
160+
) {
161+
WooPosText(
162+
text = label,
163+
style = WooPosTypography.BodySmall,
164+
color = WooPosTheme.colors.onSurfaceVariantHighest,
165+
modifier = Modifier.weight(1f)
166+
)
167+
WooPosText(
168+
text = value,
169+
style = WooPosTypography.BodySmall
170+
)
171+
}
172+
}
173+
174+
val b = details.breakdown
175+
RowLine(
176+
label = stringResource(R.string.woopos_orders_details_breakdown_products_label),
177+
value = b.products
178+
)
179+
180+
b.discount?.let { d ->
181+
val label =
182+
if (b.discountCode.isNullOrBlank()) {
183+
stringResource(R.string.woopos_orders_details_breakdown_discount_label)
184+
} else {
185+
stringResource(
186+
R.string.woopos_orders_details_breakdown_discount_with_code_label,
187+
b.discountCode
188+
)
189+
}
190+
RowLine(label, d)
191+
}
192+
193+
RowLine(
194+
label = stringResource(R.string.woopos_orders_details_breakdown_taxes_label),
195+
value = b.taxes
196+
)
197+
198+
b.shipping?.let {
199+
RowLine(
200+
label = stringResource(R.string.woopos_orders_details_breakdown_shipping_label),
201+
value = it
202+
)
203+
}
204+
205+
Spacer(Modifier.height(WooPosSpacing.Small.value))
206+
Box(
207+
Modifier
208+
.fillMaxWidth()
209+
.height(1.dp)
210+
.background(MaterialTheme.colorScheme.surfaceContainerHighest)
211+
)
212+
213+
Row(
214+
Modifier
215+
.fillMaxWidth()
216+
.padding(vertical = WooPosSpacing.Small.value)
217+
) {
218+
WooPosText(
219+
text = stringResource(R.string.woopos_orders_details_total_label),
220+
style = WooPosTypography.BodySmall,
221+
fontWeight = FontWeight.Bold,
222+
modifier = Modifier.weight(1f)
223+
)
224+
WooPosText(
225+
text = details.total,
226+
style = WooPosTypography.BodySmall,
227+
fontWeight = FontWeight.Bold
228+
)
229+
}
230+
}
231+
}
232+
233+
Column {
234+
Row(Modifier.fillMaxWidth()) {
235+
WooPosText(
236+
text = stringResource(R.string.woopos_orders_details_total_paid_label),
237+
style = WooPosTypography.BodySmall,
238+
modifier = Modifier.weight(1f)
239+
)
240+
WooPosText(
241+
text = details.totalPaid,
242+
style = WooPosTypography.BodySmall
243+
)
244+
}
245+
details.paymentMethodTitle?.let {
246+
Spacer(Modifier.height(WooPosSpacing.XSmall.value))
247+
WooPosText(
248+
text = it,
249+
style = WooPosTypography.BodySmall,
250+
color = WooPosTheme.colors.onSurfaceVariantHighest
251+
)
252+
}
253+
}
254+
}
255+
}
256+
}
257+
258+
@Composable
259+
private fun OrderLineItemImage(imageUrl: String?) {
260+
Box(
261+
modifier = Modifier
262+
.width(56.dp)
263+
.fillMaxHeight()
264+
.heightIn(min = 56.dp)
265+
.background(MaterialTheme.colorScheme.surfaceDim),
266+
contentAlignment = Alignment.Center
267+
) {
268+
Image(
269+
imageVector = Icons.Outlined.Inventory2,
270+
contentDescription = null,
271+
colorFilter = ColorFilter.tint(WooPosTheme.colors.onSurfaceVariantLowest),
272+
modifier = Modifier.size(24.dp)
273+
)
274+
AsyncImage(
275+
model = ImageRequest.Builder(LocalContext.current)
276+
.data(imageUrl)
277+
.crossfade(true)
278+
.build(),
279+
contentDescription = null,
280+
contentScale = ContentScale.Crop
281+
)
282+
}
283+
}

0 commit comments

Comments
 (0)