You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Jetpack Compose中BottomSheet内SelectionContainer不显示选中选项问题

解决方法

这个问题的核心原因是**ModalBottomSheet的内部布局拦截了文本选择后的上下文菜单事件**,导致系统无法正常弹出操作菜单。可以通过以下两种方式解决:

方法一:手动绑定文本工具栏锚点

在ModalBottomSheet的内容布局中,通过LocalTextToolbar将上下文菜单锚定到BottomSheet的区域,绕过事件拦截:

@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun BottomSheet(
    showSheet: Boolean,
    onDismiss: () -> Unit,
) {
    val modalBottomSheetState = rememberModalBottomSheetState()
    val textToolbar = LocalTextToolbar.current
    if (showSheet) {
        ModalBottomSheet(
            onDismissRequest = { onDismiss() },
            sheetState = modalBottomSheetState,
            dragHandle = { BottomSheetDefaults.DragHandle() },
        ) {
            Column(
                modifier = Modifier
                    .fillMaxSize()
                    .background(MaterialTheme.colorScheme.tertiary)
                    // 绑定工具栏锚点到BottomSheet的布局范围
                    .onGloballyPositioned { coordinates ->
                        textToolbar.setAnchorRect(coordinates.boundsInWindow())
                    }
            ) {
                SelectionContainer {
                    Text(
                        text = "muh text",
                        color = Color.Black,
                        modifier = Modifier
                            .padding(10.dp)
                            .verticalScroll(rememberScrollState()),
                        style = MaterialTheme.typography.displayMedium,
                        textAlign = TextAlign.Right,
                    )
                }
            }
        }
    }
}

方法二:替换为BottomSheetScaffold(推荐)

如果业务场景允许,使用BottomSheetScaffold替代ModalBottomSheet,它对文本选择的上下文菜单支持更完善,无需额外配置:

@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun BottomSheetScaffoldExample(
    showSheet: Boolean,
    onDismiss: () -> Unit,
) {
    val scope = rememberCoroutineScope()
    val sheetState = rememberStandardBottomSheetState(
        initialValue = if (showSheet) SheetValue.Expanded else SheetValue.Hidden
    )

    // 根据showSheet状态控制弹窗展开/隐藏
    LaunchedEffect(showSheet) {
        if (showSheet) sheetState.expand() else sheetState.hide()
    }

    BottomSheetScaffold(
        sheetContent = {
            Column(
                modifier = Modifier
                    .fillMaxWidth()
                    .background(MaterialTheme.colorScheme.tertiary)
            ) {
                SelectionContainer {
                    Text(
                        text = "muh text",
                        color = Color.Black,
                        modifier = Modifier
                            .padding(10.dp)
                            .verticalScroll(rememberScrollState()),
                        style = MaterialTheme.typography.displayMedium,
                        textAlign = TextAlign.Right,
                    )
                }
            }
        },
        sheetState = sheetState,
        sheetDragHandle = { BottomSheetDefaults.DragHandle() },
        onSheetHidden = onDismiss
    ) {
        // 此处放置主页面内容
    }
}

原因说明

ModalBottomSheet的内部实现中,弹窗的窗口层级和事件分发逻辑会阻止文本选择工具栏的正常渲染。而BottomSheetScaffold基于Scaffold的布局体系,与系统上下文菜单的兼容性更好;手动绑定LocalTextToolbar则是强制将菜单锚点指向BottomSheet的布局区域,从而绕过事件拦截。


内容的提问来源于stack exchange,提问作者M.KH

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 05:40:28