Skip to content

BottomSheet

BottomSheet 是从底部滑出的面板,常用于操作菜单、筛选器等。

showModalBottomSheet — 模态弹窗

dart
// 获取返回值
final result = await showModalBottomSheet<String>(
  context: context,
  isScrollControlled: true,    // 允许全屏高度
  shape: const RoundedRectangleBorder(
    borderRadius: BorderRadius.vertical(top: Radius.circular(16)),
  ),
  builder: (context) => SizedBox(
    height: 300,
    child: Column(
      children: [
        // 顶部拖拽指示条
        Container(
          width: 40,
          height: 4,
          margin: const EdgeInsets.symmetric(vertical: 12),
          decoration: BoxDecoration(
            color: Colors.grey[300],
            borderRadius: BorderRadius.circular(2),
          ),
        ),
        ListTile(
          leading: const Icon(Icons.camera_alt),
          title: const Text('拍照'),
          onTap: () => Navigator.pop(context, 'camera'),
        ),
        ListTile(
          leading: const Icon(Icons.photo_library),
          title: const Text('从相册选择'),
          onTap: () => Navigator.pop(context, 'gallery'),
        ),
      ],
    ),
  ),
);

if (result == 'camera') {
  // 用户选择了拍照
}

适配键盘

dart
showModalBottomSheet(
  context: context,
  isScrollControlled: true,   // 必须
  builder: (context) => Padding(
    padding: EdgeInsets.only(
      bottom: MediaQuery.of(context).viewInsets.bottom,  // 键盘高度
    ),
    child: Column(
      mainAxisSize: MainAxisSize.min,
      children: [
        const TextField(
          decoration: InputDecoration(labelText: '输入内容'),
        ),
        Padding(
          padding: const EdgeInsets.all(16),
          child: SizedBox(
            width: double.infinity,
            child: ElevatedButton(
              onPressed: () => Navigator.pop(context),
              child: const Text('确定'),
            ),
          ),
        ),
      ],
    ),
  ),
)

showBottomSheet — 持久面板

dart
// 持久底部面板(不会自动关闭,需要手动关闭)
final controller = showBottomSheet(
  context: context,
  shape: const RoundedRectangleBorder(
    borderRadius: BorderRadius.vertical(top: Radius.circular(16)),
  ),
  builder: (context) => const SizedBox(
    height: 200,
    child: Center(child: Text('这是底部面板')),
  ),
);

// 关闭
controller.close();

DraggableScrollableSheet — 可拖拽面板

dart
showModalBottomSheet(
  context: context,
  isScrollControlled: true,
  builder: (context) => DraggableScrollableSheet(
    initialChildSize: 0.5,     // 初始高度(屏幕比例)
    minChildSize: 0.25,        // 最小高度
    maxChildSize: 0.9,         // 最大高度
    expand: false,             // 不自动展开到 maxChildSize
    builder: (context, scrollController) {
      return ListView.builder(
        controller: scrollController,
        itemCount: 50,
        itemBuilder: (context, index) {
          return ListTile(title: Text('Item $index'));
        },
      );
    },
  ),
)

基于 Flutter 官方文档整理