Skip to content

Commit c92df72

Browse files
committed
fix: adjust AppDrawer ripple effect to match content shape
BREAKING CHANGE: If you use the appDrawer modifier in your custom AppDrawer UI, you need to move the onClick function to its content, e.g. to the AppDrawerContent.
1 parent 55a6f8b commit c92df72

File tree

2 files changed

+76
-62
lines changed

2 files changed

+76
-62
lines changed

docs/index.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ This framework combines multipe functionalities provided by PACE i.e. authorizin
2222
+ [19.x.x -> 20.x.x](#from-19xx-to-20xx)
2323
+ [20.x.x -> 21.x.x](#from-20xx-to-21xx)
2424
+ [21.x.x -> 22.x.x](#from-21xx-to-22xx)
25+
+ [22.x.x -> 23.x.x](#from-22xx-to-23xx)
2526

2627
## Documentation
2728
The full documentation and instructions on how to integrate PACE Cloud SDK can be found [here](https://docs.pace.cloud/en/integrating/mobile-app)
@@ -175,6 +176,12 @@ The `GasStations` properties `paymentMethods`, `amenities`, `foods`, `loyaltyPro
175176
### From 21.x.x to 22.x.x
176177
- Updated Fueling, Pay, User and POI API
177178

179+
### From 22.x.x to 23.x.x
180+
- Reworked the AppDrawer ripple effect to match its shape:
181+
- If you do not override the `AppDrawer` in the `AppDrawerHost`, no changes are required.
182+
- If you use the `appDrawer` modifier in your custom `AppDrawer` UI, you need to move the `onClick` function to its content, e.g. to the `AppDrawerContent`.
183+
- You can use the newly introduced `AppDrawerColumn` as a wrapper around your content so that the swipe gestures are handled for you.
184+
178185
## SDK API Docs
179186

180187
Here is a complete list of all our SDK API documentations:

library/src/main/java/cloud/pace/sdk/appkit/app/drawer/ui/AppDrawer.kt

Lines changed: 69 additions & 62 deletions
Original file line numberDiff line numberDiff line change
@@ -4,36 +4,33 @@ import androidx.compose.animation.core.Spring
44
import androidx.compose.animation.core.animateIntAsState
55
import androidx.compose.animation.core.spring
66
import androidx.compose.foundation.background
7-
import androidx.compose.foundation.clickable
87
import androidx.compose.foundation.gestures.Orientation
98
import androidx.compose.foundation.layout.Arrangement
109
import androidx.compose.foundation.layout.Box
1110
import androidx.compose.foundation.layout.BoxWithConstraints
1211
import androidx.compose.foundation.layout.Column
12+
import androidx.compose.foundation.layout.ColumnScope
1313
import androidx.compose.foundation.layout.Row
1414
import androidx.compose.foundation.layout.fillMaxWidth
1515
import androidx.compose.foundation.layout.offset
1616
import androidx.compose.foundation.layout.padding
17-
import androidx.compose.foundation.layout.requiredHeight
1817
import androidx.compose.foundation.layout.requiredSize
1918
import androidx.compose.foundation.layout.size
2019
import androidx.compose.foundation.shape.RoundedCornerShape
21-
import androidx.compose.material.Card
2220
import androidx.compose.material.DrawerValue
2321
import androidx.compose.material.ExperimentalMaterialApi
2422
import androidx.compose.material.FractionalThreshold
2523
import androidx.compose.material.Icon
2624
import androidx.compose.material.IconButton
27-
import androidx.compose.material.LocalElevationOverlay
2825
import androidx.compose.material.MaterialTheme
26+
import androidx.compose.material.Surface
2927
import androidx.compose.material.SwipeableDefaults
3028
import androidx.compose.material.SwipeableDefaults.resistanceConfig
3129
import androidx.compose.material.SwipeableState
3230
import androidx.compose.material.Text
3331
import androidx.compose.material.rememberSwipeableState
3432
import androidx.compose.material.swipeable
3533
import androidx.compose.runtime.Composable
36-
import androidx.compose.runtime.CompositionLocalProvider
3734
import androidx.compose.runtime.LaunchedEffect
3835
import androidx.compose.runtime.derivedStateOf
3936
import androidx.compose.runtime.getValue
@@ -101,53 +98,76 @@ fun AppDrawer(
10198
initialDrawerValue: DrawerValue = DrawerValue.Closed,
10299
onClick: () -> Unit
103100
) {
104-
val height = dimensionResource(id = R.dimen.app_drawer_height)
101+
val coroutineScope = rememberCoroutineScope()
102+
val swipeableState = rememberSwipeableState(
103+
initialValue = initialDrawerValue,
104+
animationSpec = spring(dampingRatio = 0.6f, stiffness = 1000f)
105+
)
106+
val collapsed by remember {
107+
derivedStateOf {
108+
swipeableState.targetValue == DrawerValue.Closed
109+
}
110+
}
111+
112+
AppDrawerColumn(swipeableState = swipeableState) {
113+
AppDrawerContent(
114+
iconUrl = iconUrl,
115+
caption = caption,
116+
distance = distance,
117+
headline = headline,
118+
isExpanded = !collapsed,
119+
iconBackgroundColor = iconBackgroundColor,
120+
backgroundColor = backgroundColor,
121+
textColor = textColor,
122+
onClose = {
123+
coroutineScope.launch {
124+
swipeableState.animateTo(DrawerValue.Closed)
125+
}
126+
},
127+
onClick = {
128+
if (collapsed) {
129+
coroutineScope.launch {
130+
swipeableState.animateTo(DrawerValue.Open)
131+
}
132+
} else {
133+
onClick()
134+
}
135+
}
136+
)
137+
}
138+
}
105139

140+
@OptIn(ExperimentalMaterialApi::class)
141+
@Composable
142+
fun AppDrawerColumn(
143+
modifier: Modifier = Modifier,
144+
collapsedWidth: Dp = dimensionResource(id = R.dimen.app_drawer_height),
145+
swipeableState: SwipeableState<DrawerValue> = rememberSwipeableState(
146+
initialValue = DrawerValue.Closed,
147+
animationSpec = spring(dampingRatio = 0.6f, stiffness = 1000f)
148+
),
149+
content: @Composable ColumnScope.() -> Unit
150+
) {
106151
BoxWithConstraints(
107-
modifier = Modifier
152+
modifier = modifier
108153
.padding(start = 20.dp)
109-
.fillMaxWidth()
110-
.requiredHeight(height),
154+
.fillMaxWidth(),
111155
contentAlignment = Alignment.CenterEnd
112156
) {
113-
// Disable elevation overlay in Card so that the background color is not lighter
114-
CompositionLocalProvider(LocalElevationOverlay provides null) {
115-
val coroutineScope = rememberCoroutineScope()
116-
val iconBoxSizePx = with(LocalDensity.current) { height.toPx() }
117-
val collapsedOffset = constraints.maxWidth - iconBoxSizePx
118-
val swipeableState = rememberSwipeableState(
119-
initialValue = initialDrawerValue,
120-
animationSpec = spring(dampingRatio = 0.6f, stiffness = 1000f)
121-
)
122-
val collapsed by remember {
123-
derivedStateOf {
124-
swipeableState.targetValue == DrawerValue.Closed
125-
}
126-
}
157+
val collapsedWidthPx = with(LocalDensity.current) { collapsedWidth.toPx() }
158+
val collapsedOffset = constraints.maxWidth - collapsedWidthPx
127159

128-
AppDrawerContent(
129-
modifier = Modifier.appDrawer(
130-
swipeableState = swipeableState,
131-
collapsedOffset = collapsedOffset,
132-
onClick = onClick
133-
),
134-
iconUrl = iconUrl,
135-
caption = caption,
136-
distance = distance,
137-
headline = headline,
138-
isExpanded = !collapsed,
139-
iconBackgroundColor = iconBackgroundColor,
140-
backgroundColor = backgroundColor,
141-
textColor = textColor
142-
) {
143-
coroutineScope.launch {
144-
swipeableState.animateTo(DrawerValue.Closed)
145-
}
146-
}
147-
}
160+
Column(
161+
modifier = Modifier.appDrawer(
162+
swipeableState = swipeableState,
163+
collapsedOffset = collapsedOffset
164+
),
165+
content = content
166+
)
148167
}
149168
}
150169

170+
@OptIn(ExperimentalMaterialApi::class)
151171
@Composable
152172
fun AppDrawerContent(
153173
modifier: Modifier = Modifier,
@@ -160,19 +180,21 @@ fun AppDrawerContent(
160180
iconBackgroundColor: Color? = null,
161181
backgroundColor: Color? = null,
162182
textColor: Color? = null,
163-
onClose: () -> Unit
183+
onClose: () -> Unit,
184+
onClick: () -> Unit
164185
) {
165186
val drawerIconBackgroundColor = iconBackgroundColor ?: Title
166187
val drawerBackgroundColor = backgroundColor ?: PACEBlue
167188
val drawerTextColor = textColor ?: Title
168189

169-
Card(
190+
Surface(
191+
onClick = onClick,
170192
modifier = modifier,
171193
shape = RoundedCornerShape(
172194
topStartPercent = 50,
173195
bottomStartPercent = 50
174196
),
175-
backgroundColor = drawerBackgroundColor,
197+
color = drawerBackgroundColor,
176198
elevation = 10.dp
177199
) {
178200
Row(verticalAlignment = Alignment.CenterVertically) {
@@ -331,16 +353,10 @@ fun AppDrawerCloseButton(
331353
@Composable
332354
fun Modifier.appDrawer(
333355
swipeableState: SwipeableState<DrawerValue>,
334-
collapsedOffset: Float,
335-
onClick: () -> Unit
356+
collapsedOffset: Float
336357
): Modifier {
337358
val coroutineScope = rememberCoroutineScope()
338359
val anchors = mapOf(0f to DrawerValue.Open, collapsedOffset to DrawerValue.Closed)
339-
val collapsed by remember {
340-
derivedStateOf {
341-
swipeableState.targetValue == DrawerValue.Closed
342-
}
343-
}
344360

345361
LaunchedEffect(Unit) {
346362
coroutineScope.launch {
@@ -366,15 +382,6 @@ fun Modifier.appDrawer(
366382
factorAtMax = SwipeableDefaults.StandardResistanceFactor
367383
)
368384
)
369-
.clickable {
370-
if (collapsed) {
371-
coroutineScope.launch {
372-
swipeableState.animateTo(DrawerValue.Open)
373-
}
374-
} else {
375-
onClick()
376-
}
377-
}
378385
}
379386

380387
@Preview(showBackground = true)

0 commit comments

Comments
 (0)