在 Jetpack Compose 中打开抽屉时推送内容

时间:2021-07-23 17:49:05

标签: android kotlin android-jetpack-compose

抽屉打开时如何滑动脚手架的内容。类似于这个question 但在喷气背包中。

1 个答案:

答案 0 :(得分:1)

我找到了解决方案...

// This is optional if you need to open/close the drawer programmatically
val coroutineScope = rememberCoroutineScope()

// We need the drawer state to check:
// 1. if it is opened or closed
// 2. request to open/close it
// 3. get the drawer's offset (and do the slide of the content)
val drawerState = rememberDrawerState(initialValue = DrawerValue.Closed)

// Drawer's width. It will be updated later in LaunchedEffect
var drawerWidth by remember {
    mutableStateOf(drawerState.offset.value)
}
// As soon the user move the drawer, the content must move in sync.
// So here we're creating a derived state of the drawer state 
// to update the content position.
val contentOffset = remember {
    derivedStateOf {
        drawerState.offset.value
    }
}
// The scaffold state contains the drawer state.
val scaffoldState = rememberScaffoldState(
    drawerState = drawerState
)

Scaffold(
    scaffoldState = scaffoldState,
    drawerContent = {
        Box {
            // your drawer content here...
        }
    }
) {
    Box(Modifier.fillMaxSize()) {
        // Here's the content's offset calculation logic
        val xPos = (abs(drawerWidth) - abs(contentOffset.value))
        Column(
            // Set the content's offset
            Modifier.offset(
                x = with(LocalDensity.current) {
                    max(0.dp, xPos.toDp() - 56.dp)
                }
            )
        ) {
            // Optional: opening the drawer using a button
            Button(onClick = {    
                coroutineScope.launch {
                    drawerState.open()
                }
            }) {
                Text("Open Drawer")
            }
        }
    }
}
// Important! Initializing the drawerWidth
SideEffect {
    if (drawerWidth == 0f) {
        drawerWidth = drawerState.offset.value
    }
}

结果如下:

enter image description here

警告!此解决方案有一个问题:如您所见,我使用的是硬编码值 56.dp。这是因为 Material Design 库使用这个值作为抽屉的末端填充。您可以在 Material Design 库的 Drawer.kt 文件中看到这个常量。

private val EndDrawerPadding = 56.dp