|
|
@@ -1,46 +1,111 @@
|
|
|
import 'package:chicken_farm/core/services/navigation_service.dart';
|
|
|
import 'package:flutter/material.dart';
|
|
|
-import 'package:fluttertoast/fluttertoast.dart';
|
|
|
|
|
|
class ToastUtil {
|
|
|
- // 用于跟踪最近显示的Toast消息
|
|
|
- static final Set<String> _recentMessages = {};
|
|
|
- static const Duration _deduplicationDuration = Duration(seconds: 3);
|
|
|
+ static void success(String message) => show(message, bgColor: Colors.green);
|
|
|
+ static void successB(String message) =>
|
|
|
+ show(message, bgColor: Colors.green, position: "bottom");
|
|
|
|
|
|
- static void success(
|
|
|
- String message, [
|
|
|
- Toast? toastLength = Toast.LENGTH_SHORT,
|
|
|
- ToastGravity? gravity = ToastGravity.CENTER,
|
|
|
- Color? textColor = Colors.white,
|
|
|
- double? fontSize = 16.0,
|
|
|
- ]) => show(message, Colors.green, toastLength, gravity, textColor, fontSize);
|
|
|
+ static void error(String message, [double duration = 3.0]) =>
|
|
|
+ show(message, duration: duration, bgColor: Colors.red);
|
|
|
+ static void errorB(String message, [double duration = 3.0]) => show(
|
|
|
+ message,
|
|
|
+ duration: duration,
|
|
|
+ bgColor: Colors.red,
|
|
|
+ position: "bottom",
|
|
|
+ );
|
|
|
|
|
|
- static void error(
|
|
|
- String message, [
|
|
|
- Toast? toastLength = Toast.LENGTH_SHORT,
|
|
|
- ToastGravity? gravity = ToastGravity.CENTER,
|
|
|
- Color? textColor = Colors.white,
|
|
|
- double? fontSize = 16.0,
|
|
|
- ]) => show(message, Colors.red, toastLength, gravity, textColor, fontSize);
|
|
|
+ static void info(String message) => show(message, bgColor: Colors.lightBlue);
|
|
|
+ static void infoB(String message) =>
|
|
|
+ show(message, bgColor: Colors.lightBlue, position: "bottom");
|
|
|
|
|
|
- static void info(
|
|
|
- String message, [
|
|
|
- Toast? toastLength = Toast.LENGTH_SHORT,
|
|
|
- ToastGravity? gravity = ToastGravity.CENTER,
|
|
|
- Color? textColor = Colors.white,
|
|
|
- double? fontSize = 16.0,
|
|
|
- ]) => show(message, Colors.blue, toastLength, gravity, textColor, fontSize);
|
|
|
+ static void warning(String message) => show(message, bgColor: Colors.orange);
|
|
|
+ static void warningB(String message) =>
|
|
|
+ show(message, bgColor: Colors.orange, position: "bottom");
|
|
|
|
|
|
- static void warning(
|
|
|
- String message, [
|
|
|
- Toast? toastLength = Toast.LENGTH_SHORT,
|
|
|
- ToastGravity? gravity = ToastGravity.CENTER,
|
|
|
+ static void show(
|
|
|
+ String message, {
|
|
|
+ Color? bgColor = Colors.lightBlue,
|
|
|
+ double duration = 2.0,
|
|
|
+ String position = "center",
|
|
|
Color? textColor = Colors.white,
|
|
|
double? fontSize = 16.0,
|
|
|
- ]) => show(message, Colors.orange, toastLength, gravity, textColor, fontSize);
|
|
|
+ }) {
|
|
|
+ final BuildContext? context = NavigationService.navigatorKey.currentContext;
|
|
|
+ if (context == null) return;
|
|
|
+
|
|
|
+ // 确保在WidgetsBinding.instance调度器中执行
|
|
|
+ WidgetsBinding.instance.addPostFrameCallback((_) {
|
|
|
+ final scaffoldMessenger = ScaffoldMessenger.of(context);
|
|
|
+
|
|
|
+ // 先清除之前的snackbars
|
|
|
+ scaffoldMessenger.clearSnackBars();
|
|
|
+
|
|
|
+ // 计算显示时长
|
|
|
+ final Duration displayDuration = Duration(
|
|
|
+ milliseconds: (duration * 1000).toInt(),
|
|
|
+ );
|
|
|
+ bool isBottomPosition = position == "bottom";
|
|
|
+ bool isCenterPosition = !isBottomPosition;
|
|
|
+
|
|
|
+ // 显示新的snackbar
|
|
|
+ scaffoldMessenger.showSnackBar(
|
|
|
+ SnackBar(
|
|
|
+ content: Text(
|
|
|
+ message,
|
|
|
+ textAlign: isCenterPosition ? TextAlign.center : TextAlign.left,
|
|
|
+ style: TextStyle(color: textColor, fontSize: fontSize),
|
|
|
+ ),
|
|
|
+ backgroundColor: bgColor,
|
|
|
+ duration: displayDuration,
|
|
|
+ behavior: isCenterPosition
|
|
|
+ ? SnackBarBehavior.floating
|
|
|
+ : SnackBarBehavior.fixed,
|
|
|
+ shape: isCenterPosition
|
|
|
+ ? RoundedRectangleBorder(borderRadius: BorderRadius.circular(10))
|
|
|
+ : null,
|
|
|
+ margin: isCenterPosition
|
|
|
+ ? _calculateCenterMargin(message, textColor, fontSize, context)
|
|
|
+ : null,
|
|
|
+ padding: const EdgeInsets.symmetric(horizontal: 16.0, vertical: 12.0),
|
|
|
+ showCloseIcon: duration == 0,
|
|
|
+ ),
|
|
|
+ );
|
|
|
+ });
|
|
|
+ }
|
|
|
+
|
|
|
+ /// 计算center位置的margin
|
|
|
+ static EdgeInsetsGeometry _calculateCenterMargin(
|
|
|
+ String message,
|
|
|
+ Color? textColor,
|
|
|
+ double? fontSize,
|
|
|
+ BuildContext context,
|
|
|
+ ) {
|
|
|
+ final textPainter = TextPainter(
|
|
|
+ text: TextSpan(
|
|
|
+ text: message,
|
|
|
+ style: TextStyle(color: textColor, fontSize: fontSize),
|
|
|
+ ),
|
|
|
+ textDirection: TextDirection.ltr,
|
|
|
+ )..layout();
|
|
|
+
|
|
|
+ final contentWidth = textPainter.width + 50; // 加上padding的宽度
|
|
|
+ final maxContentWidth = 320.0;
|
|
|
+ final actualWidth = contentWidth > maxContentWidth
|
|
|
+ ? maxContentWidth
|
|
|
+ : contentWidth;
|
|
|
+ final screenWidth = MediaQuery.of(context).size.width;
|
|
|
+ final horizontalMargin = (screenWidth - actualWidth) / 2;
|
|
|
+
|
|
|
+ return EdgeInsets.symmetric(
|
|
|
+ horizontal: horizontalMargin > 0 ? horizontalMargin : 20,
|
|
|
+ vertical: MediaQuery.of(context).size.height * 0.4,
|
|
|
+ );
|
|
|
+ }
|
|
|
|
|
|
static Future<void> errorAlert(
|
|
|
String message, {
|
|
|
+ VoidCallback? onConfirm,
|
|
|
String? title,
|
|
|
String confirmText = '确定',
|
|
|
BuildContext? context,
|
|
|
@@ -51,7 +116,7 @@ class ToastUtil {
|
|
|
if (dialogContext == null) {
|
|
|
return;
|
|
|
}
|
|
|
- return await showDialog(
|
|
|
+ bool result = await showDialog(
|
|
|
context: dialogContext,
|
|
|
builder: (BuildContext context) {
|
|
|
return AlertDialog(
|
|
|
@@ -114,6 +179,9 @@ class ToastUtil {
|
|
|
);
|
|
|
},
|
|
|
);
|
|
|
+ if (result == true && onConfirm != null) {
|
|
|
+ onConfirm();
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
static Future<void> confirm(
|
|
|
@@ -231,36 +299,4 @@ class ToastUtil {
|
|
|
onConfirm();
|
|
|
}
|
|
|
}
|
|
|
-
|
|
|
- static void show(
|
|
|
- String message, [
|
|
|
- Color? backgroundColor = Colors.blue,
|
|
|
- Toast? toastLength = Toast.LENGTH_SHORT,
|
|
|
- ToastGravity? gravity = ToastGravity.CENTER,
|
|
|
- Color? textColor = Colors.white,
|
|
|
- double? fontSize = 16.0,
|
|
|
- ]) {
|
|
|
- // 检查消息是否在去重期内
|
|
|
- if (_recentMessages.contains(message)) {
|
|
|
- return;
|
|
|
- }
|
|
|
-
|
|
|
- // 添加消息到集合中
|
|
|
- _recentMessages.add(message);
|
|
|
-
|
|
|
- // 设置定时器,在一定时间后移除消息记录
|
|
|
- Future.delayed(_deduplicationDuration, () {
|
|
|
- _recentMessages.remove(message);
|
|
|
- });
|
|
|
-
|
|
|
- Fluttertoast.showToast(
|
|
|
- msg: message,
|
|
|
- toastLength: toastLength,
|
|
|
- gravity: gravity,
|
|
|
- timeInSecForIosWeb: 1,
|
|
|
- backgroundColor: backgroundColor,
|
|
|
- textColor: textColor,
|
|
|
- fontSize: fontSize,
|
|
|
- );
|
|
|
- }
|
|
|
}
|