I have three cards in HorizontalPager and I want to animate its offset like this one when user scroll through pages.
val pagerState = rememberPagerState(pageCount = 3)
val currentIndex = pagerState.currentPage
HorizontalPager(
state = pagerState,
modifier = Modifier.fillMaxSize()
) { page ->
Card(
modifier = Modifier
.fillMaxWidth(0.7f)
.fillMaxHeight(0.7f)
.padding(22.dp)
.offset(y = if (currentIndex == page) 0.dp else 70.dp),
shape = RoundedCornerShape(30.dp),
elevation = 110.dp
) {}
}
CodePudding user response:
You can calculate the offset using pagerState.currentPageOffset.
When you scroll the HorizontalPager, the currentPage will not change until you release the drag. When you scroll to the right, currentPageOffset increases from 0f to 1f, and when you scroll to the left, it decreases from 0f to -1f.
In my code, I calculate offset for each page:
- The offset of the current page should increase as we scroll left and right, so we can take
absoluteValue. - The left page offset should decrease as long as
currentPageOffsetchanges from0fto-1f. - The right page offset should decrease while
currentPageOffsetincreases from0fto1f.
@Composable
fun TestScreen() {
val pagerState = rememberPagerState(pageCount = 3)
val currentIndex = pagerState.currentPage
val currentPageOffset = pagerState.currentPageOffset
HorizontalPager(
state = pagerState,
modifier = Modifier.fillMaxSize()
) { page ->
val offset = maxOffset * when (page) {
currentIndex -> {
currentPageOffset.absoluteValue
}
currentIndex - 1 -> {
1 currentPageOffset.coerceAtMost(0f)
}
currentIndex 1 -> {
1 - currentPageOffset.coerceAtLeast(0f)
}
else -> {
1f
}
}
Card(
modifier = Modifier
.fillMaxWidth(0.7f)
.fillMaxHeight(0.7f)
.padding(22.dp)
.offset(y = offset),
shape = RoundedCornerShape(30.dp),
elevation = 110.dp
) {}
}
}
private val maxOffset = 70.dp
Result:

