如何在Jetpack Compose中带过渡效果实现滚动隐藏FAB按钮
实现效果

实现思路
- 首先通过滚动状态对象监听页面滚动方向与偏移量
- 使用
derivedStateOf封装滚动判断逻辑,减少不必要的重组触发 - 搭配Compose自带的动画API实现FAB的平滑过渡效果
代码实现
以下为LazyColumn场景下的完整示例:
import androidx.compose.animation.AnimatedVisibility import androidx.compose.animation.fadeIn import androidx.compose.animation.fadeOut import androidx.compose.animation.slideInVertically import androidx.compose.animation.slideOutVertically import androidx.compose.foundation.layout.padding import androidx.compose.foundation.lazy.LazyColumn import androidx.compose.foundation.lazy.items import androidx.compose.foundation.lazy.rememberLazyListState import androidx.compose.material.icons.Icons import androidx.compose.material.icons.filled.Add import androidx.compose.material3.FloatingActionButton import androidx.compose.material3.Icon import androidx.compose.material3.Scaffold import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.runtime.derivedStateOf import androidx.compose.runtime.getValue import androidx.compose.runtime.remember import androidx.compose.ui.Modifier import androidx.compose.ui.unit.dp @Composable fun ScrollHideFabDemo() { val listState = rememberLazyListState() // 示例逻辑:页面回到顶部时显示FAB,滚动时隐藏 val showFab by remember { derivedStateOf { listState.firstVisibleItemIndex == 0 && listState.firstVisibleItemScrollOffset == 0 } } Scaffold( floatingActionButton = { AnimatedVisibility( visible = showFab, // 自定义进入动画:从底部滑入+淡入 enter = slideInVertically(initialOffsetY = { it * 2 }) + fadeIn(), // 自定义退出动画:向下滑出+淡出 exit = slideOutVertically(targetOffsetY = { it * 2 }) + fadeOut() ) { FloatingActionButton( onClick = { /* 补充FAB点击逻辑 */ } ) { Icon(Icons.Default.Add, contentDescription = "新增") } } } ) { innerPadding -> LazyColumn( state = listState, modifier = Modifier.padding(innerPadding) ) { items(50) { index -> Text( text = "列表项 $index", modifier = Modifier.padding(horizontal = 16.dp, vertical = 12.dp) ) } } } }
适配说明
- 若使用普通可滚动Column,将
rememberLazyListState替换为rememberScrollState(),判断逻辑改为scrollState.value == 0即可 - 可调整动画的
animationSpec参数自定义动画时长、插值器,匹配项目设计规范 - 如果需要实现"只要向下滚动就隐藏、向上滚动就显示"的逻辑,而非仅在顶部显示,可修改
derivedStateOf中的判断逻辑,对比前后滚动偏移的差值即可
内容的提问来源于stack exchange,提问作者GvHarish
相关产品推荐
相关产品推荐

