diff --git a/CHANGELOG.md b/CHANGELOG.md index 27835e1..9986bb1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,6 @@ # [4.9.8+x] * SmartDialog.config.checkExist() adjust to SmartDialog.checkExist() +* Fix [#209](https://github.com/fluttercandies/flutter_smart_dialog/issues/209) * # [4.9.7+x] * optimize bindWidget, when bindWidget is not null, bindPage will be automatically set to false. diff --git a/example/lib/demo/issue209.dart b/example/lib/demo/issue209.dart new file mode 100644 index 0000000..9af16b8 --- /dev/null +++ b/example/lib/demo/issue209.dart @@ -0,0 +1,56 @@ +import 'package:flutter/material.dart'; +import 'package:flutter_smart_dialog/flutter_smart_dialog.dart'; + +void main() => runApp(const MyApp()); + +class MyApp extends StatelessWidget { + const MyApp({Key? key}) : super(key: key); + + @override + Widget build(BuildContext context) { + return MaterialApp( + home: Scaffold( + body: Center( + child: ElevatedButton( + onPressed: () => _show(), + child: const Text('show'), + ), + ), + ), + navigatorObservers: [FlutterSmartDialog.observer], + builder: FlutterSmartDialog.init(), + ); + } + + void _show() async { + print("before:${DateTime.now().millisecondsSinceEpoch}"); + var result = await SmartDialog.show( + tag: 'tag', + backDismiss: false, + clickMaskDismiss: false, + builder: (_) { + return ElevatedButton( + onPressed: () { + SmartDialog.dismiss(tag: 'tag', result: true); + }, + child: const Text('关闭Dialog,显示Loading'), + ); + }, + onDismiss: () { + print("onDismiss:${DateTime.now().millisecondsSinceEpoch}"); + // showLoading()放在这里能正常显示 + // SmartDialog.showLoading(); + }); + + print("aftermiss:${DateTime.now().millisecondsSinceEpoch}"); + if (result == true) { + // showLoading() 放在这里需要加一点延时才能显示Loading + // await Future.delayed(const Duration(seconds: 1)); + SmartDialog.showLoading(); + + // 延时关闭Loading + await Future.delayed(const Duration(seconds: 2)); + SmartDialog.dismiss(); + } + } +} diff --git a/lib/src/custom/main_dialog.dart b/lib/src/custom/main_dialog.dart index 0479445..c486ed6 100644 --- a/lib/src/custom/main_dialog.dart +++ b/lib/src/custom/main_dialog.dart @@ -226,16 +226,16 @@ class MainDialog { Navigator.pop(DialogProxy.contextNavigator!); } + await DialogProxy.instance.smartOverlayController.dismiss(); + + // safety await + await ViewUtils.awaitPostFrame(); + //end waiting _handleAwaitOver( awaitOverType: SmartAwaitOverType.dialogDismiss, result: result, ); - - await DialogProxy.instance.smartOverlayController.dismiss(); - - // safety await - await Future.delayed(const Duration(milliseconds: 20)); } Widget getWidget() => Offstage(offstage: !visible, child: _widget); diff --git a/lib/src/kit/view_utils.dart b/lib/src/kit/view_utils.dart index 7818ec3..d2a108a 100644 --- a/lib/src/kit/view_utils.dart +++ b/lib/src/kit/view_utils.dart @@ -1,4 +1,5 @@ -import 'package:flutter/cupertino.dart'; +import 'dart:async'; + import 'package:flutter/material.dart'; import 'package:flutter/scheduler.dart'; @@ -14,6 +15,31 @@ class ViewUtils { } } + static Future awaitSafeUse({VoidCallback? onPostFrame}) async { + final completer = Completer(); + var schedulerPhase = schedulerBinding.schedulerPhase; + if (schedulerPhase == SchedulerPhase.persistentCallbacks) { + widgetsBinding.addPostFrameCallback((timeStamp) { + onPostFrame?.call(); + if (!completer.isCompleted) completer.complete(); + }); + } else { + onPostFrame?.call(); + if (!completer.isCompleted) completer.complete(); + } + + await completer.future; + } + + static Future awaitPostFrame({VoidCallback? onPostFrame}) async { + final completer = Completer(); + widgetsBinding.addPostFrameCallback((timeStamp) { + onPostFrame?.call(); + if (!completer.isCompleted) completer.complete(); + }); + await completer.future; + } + static bool isDarkModel() { if (DialogProxy.contextNavigator == null) { return false; diff --git a/lib/src/widget/helper/smart_overlay.dart b/lib/src/widget/helper/smart_overlay.dart index 15a8eff..f9e1fc4 100644 --- a/lib/src/widget/helper/smart_overlay.dart +++ b/lib/src/widget/helper/smart_overlay.dart @@ -46,12 +46,9 @@ class _SmartOverlayState extends State { if (showCompleter?.isCompleted == false) showCompleter?.complete(); showCompleter = Completer(); - var completer = Completer(); - ViewUtils.addSafeUse(() { + await ViewUtils.awaitSafeUse(onPostFrame: () { setState(() => visible = true); - completer.complete(); }); - await completer.future; // await show isExist widgetsBinding.addPostFrameCallback((timeStamp) { diff --git a/pubspec.yaml b/pubspec.yaml index 37ef2bc..845434a 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -3,7 +3,7 @@ description: An elegant Flutter Dialog solution, Easily implement Toast, Loading and custom Dialog, Make the use of the dialog easier! -version: 4.9.8 +version: 4.9.8+1 homepage: https://github.com/fluttercandies/flutter_smart_dialog # flutter pub publish --server=https://pub.dartlang.org # flutter build web --release --base-href="/flutter_smart_dialog/web/"