当前位置: 首页 > article >正文

Flutter 弹窗封装:支持多种常见弹框,灵活易用

在 Flutter 开发中,弹窗(Dialog)是常见的 UI 组件,用于提示信息、确认操作、输入内容等。为了提高代码复用性和开发效率,我们可以将弹窗封装成一个通用的工具类,支持多种常见弹框类型,包括:

  • 通用弹窗:显示标题、内容和操作按钮。
  • 确认弹框:用于确认用户操作(如删除、退出等)。
  • 输入弹框:允许用户输入文本。
  • 选择弹框:提供多个选项供用户选择。
  • 加载弹框:显示加载状态。
  • 底部弹框:从屏幕底部弹出的弹框。

通过封装,弹窗的调用更加简洁,代码更易维护,同时支持高度自定义样式和异步操作。


封装代码

import 'package:flutter/material.dart';

class DialogHelper {
  // 显示通用弹窗
  static Future<void> showCustomDialog({
    required BuildContext context,
    String? title,
    String? content,
    List<Widget>? actions,
    Widget? customContent,
    Color? backgroundColor,
    TextStyle? titleStyle,
    TextStyle? contentStyle,
  }) async {
    return showDialog(
      context: context,
      builder: (context) {
        return AlertDialog(
          backgroundColor: backgroundColor,
          title: title != null
              ? Text(
                  title!,
                  style: titleStyle ?? Theme.of(context).textTheme.headline6,
                )
              : null,
          content: customContent ??
              (content != null
                  ? Text(
                      content!,
                      style: contentStyle ?? Theme.of(context).textTheme.bodyText2,
                    )
                  : null),
          actions: actions,
        );
      },
    );
  }

  // 显示确认弹框
  static Future<bool?> showConfirmDialog({
    required BuildContext context,
    String? title,
    String? content,
    String confirmText = '确认',
    String cancelText = '取消',
  }) async {
    return showDialog<bool>(
      context: context,
      builder: (context) {
        return AlertDialog(
          title: title != null ? Text(title) : null,
          content: content != null ? Text(content) : null,
          actions: [
            TextButton(
              onPressed: () => Navigator.of(context).pop(false),
              child: Text(cancelText),
            ),
            TextButton(
              onPressed: () => Navigator.of(context).pop(true),
              child: Text(confirmText),
            ),
          ],
        );
      },
    );
  }

  // 显示输入弹框
  static Future<String?> showInputDialog({
    required BuildContext context,
    String? title,
    String? hintText,
    String confirmText = '确认',
    String cancelText = '取消',
  }) async {
    final TextEditingController controller = TextEditingController();
    return showDialog<String>(
      context: context,
      builder: (context) {
        return AlertDialog(
          title: title != null ? Text(title) : null,
          content: TextField(
            controller: controller,
            decoration: InputDecoration(hintText: hintText),
          ),
          actions: [
            TextButton(
              onPressed: () => Navigator.of(context).pop(),
              child: Text(cancelText),
            ),
            TextButton(
              onPressed: () => Navigator.of(context).pop(controller.text),
              child: Text(confirmText),
            ),
          ],
        );
      },
    );
  }

  // 显示选择弹框
  static Future<void> showSelectionDialog({
    required BuildContext context,
    String? title,
    required List<String> options,
  }) async {
    return showDialog(
      context: context,
      builder: (context) {
        return SimpleDialog(
          title: title != null ? Text(title) : null,
          children: options.map((option) {
            return SimpleDialogOption(
              onPressed: () {
                Navigator.of(context).pop(option);
              },
              child: Text(option),
            );
          }).toList(),
        );
      },
    );
  }

  // 显示加载弹框
  static Future<void> showLoadingDialog({
    required BuildContext context,
    String? message,
  }) async {
    return showDialog(
      context: context,
      barrierDismissible: false, // 点击外部不可关闭
      builder: (context) {
        return AlertDialog(
          content: Column(
            mainAxisSize: MainAxisSize.min,
            children: [
              CircularProgressIndicator(),
              SizedBox(height: 16),
              Text(message ?? '加载中...'),
            ],
          ),
        );
      },
    );
  }

  // 显示底部弹框
  static Future<void> showBottomSheetDialog({
    required BuildContext context,
    required Widget child,
  }) async {
    return showModalBottomSheet(
      context: context,
      builder: (context) {
        return child;
      },
    );
  }
}

使用示例

import 'package:flutter/material.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: Text('Flutter 弹窗封装示例'),
        ),
        body: Center(
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: [
              ElevatedButton(
                onPressed: () {
                  DialogHelper.showCustomDialog(
                    context: context,
                    title: '提示',
                    content: '这是一个通用弹窗示例。',
                    actions: [
                      TextButton(
                        onPressed: () {
                          Navigator.of(context).pop();
                        },
                        child: Text('关闭'),
                      ),
                    ],
                  );
                },
                child: Text('显示通用弹窗'),
              ),
              SizedBox(height: 16),
              ElevatedButton(
                onPressed: () async {
                  bool? result = await DialogHelper.showConfirmDialog(
                    context: context,
                    title: '确认删除',
                    content: '确定要删除此项吗?',
                  );
                  if (result == true) {
                    print('用户确认删除');
                  } else {
                    print('用户取消删除');
                  }
                },
                child: Text('显示确认弹框'),
              ),
              SizedBox(height: 16),
              ElevatedButton(
                onPressed: () async {
                  String? result = await DialogHelper.showInputDialog(
                    context: context,
                    title: '输入内容',
                    hintText: '请输入文本',
                  );
                  if (result != null) {
                    print('用户输入: $result');
                  }
                },
                child: Text('显示输入弹框'),
              ),
              SizedBox(height: 16),
              ElevatedButton(
                onPressed: () async {
                  String? result = await DialogHelper.showSelectionDialog(
                    context: context,
                    title: '选择一个选项',
                    options: ['选项1', '选项2', '选项3'],
                  );
                  if (result != null) {
                    print('用户选择: $result');
                  }
                },
                child: Text('显示选择弹框'),
              ),
              SizedBox(height: 16),
              ElevatedButton(
                onPressed: () {
                  DialogHelper.showLoadingDialog(
                    context: context,
                    message: '请稍候...',
                  );
                  // 模拟异步操作
                  Future.delayed(Duration(seconds: 2), () {
                    Navigator.of(context).pop(); // 关闭弹窗
                  });
                },
                child: Text('显示加载弹框'),
              ),
              SizedBox(height: 16),
              ElevatedButton(
                onPressed: () {
                  DialogHelper.showBottomSheetDialog(
                    context: context,
                    child: Container(
                      padding: EdgeInsets.all(16),
                      child: Column(
                        mainAxisSize: MainAxisSize.min,
                        children: [
                          Text('这是一个底部弹框'),
                          SizedBox(height: 16),
                          ElevatedButton(
                            onPressed: () {
                              Navigator.of(context).pop();
                            },
                            child: Text('关闭'),
                          ),
                        ],
                      ),
                    ),
                  );
                },
                child: Text('显示底部弹框'),
              ),
            ],
          ),
        ),
      ),
    );
  }
}

优点

  1. 支持多种弹框类型:覆盖常见的使用场景。
  2. 调用简洁:通过静态方法调用,代码更清晰。
  3. 高度可定制:支持自定义样式、内容和操作。
  4. 异步支持:通过 Future 处理用户操作结果。
  5. 易于扩展:可以根据需求继续扩展其他弹框类型。

通过这种封装方式,Flutter 弹窗的使用变得更加灵活和高效!


http://www.kler.cn/a/611273.html

相关文章:

  • React-nodejs 练习 个人博客
  • Es结合kibana查询
  • Docker容器之Dockerfile
  • CosyVoice2在Windows系统上本地部署的详细步骤
  • LlamaFactory部署及模型微调【win10环境】
  • 如何分析和解决服务器的僵尸进程问题
  • Spring Boot 连接 MySQL 配置参数详解
  • 使用ucharts写的小程序,然后让圆环中间的空白位置变大
  • Django之旅:第六节--mysql数据库操作增删改查(二)
  • 网络编程和计算机网络五层模型的关系
  • 日语Learn,英语再认识(4)
  • Docker 数据卷与文件挂载
  • pyqt SQL Server 数据库查询-优化
  • 根据模板将 Excel 明细数据生成 PDF 文档 | PDF实现邮件合并功能
  • MyBatis打印SQL日志的配置
  • 英伟达黄仁勋谈人工智能趋势,首提代理式AI,后续机器人将登场
  • 算法及数据结构系列 - 滑动窗口
  • SpringCloud微服务框架搭建指南
  • 图解AI对话系统架构:一次讲透核心技术
  • 使用 HBuilder 打包 ruoyi-mall-uniapp 并在微信开发者工具中模拟运行的教程