showAlertDialog<T> function

  1. @useResult
Future<T?> showAlertDialog<T>(
  1. {required BuildContext context,
  2. String? title,
  3. String? message,
  4. List<AlertDialogAction<T>> actions = const [],
  5. bool barrierDismissible = true,
  6. AdaptiveStyle? style,
  7. @Deprecated('Use `useActionSheetForIOS` instead. Will be removed in v2.') bool useActionSheetForCupertino = false,
  8. bool useActionSheetForIOS = false,
  9. bool useRootNavigator = true,
  10. VerticalDirection actionsOverflowDirection = VerticalDirection.up,
  11. bool fullyCapitalizedForMaterial = true,
  12. bool canPop = true,
  13. PopInvokedCallback? onPopInvoked,
  14. AdaptiveDialogBuilder? builder,
  15. Widget? macOSApplicationIcon,
  16. RouteSettings? routeSettings}
)

Show alert dialog, whose appearance is adaptive according to platform

barrierDismissible (default: true) only works for Material style. useActionSheetForIOS (default: false) only works for iOS style. If it is set to true, showModalActionSheet is called instead. actionsOverflowDirection works only for Material style currently.

Implementation

@useResult
Future<T?> showAlertDialog<T>({
  required BuildContext context,
  String? title,
  String? message,
  List<AlertDialogAction<T>> actions = const [],
  bool barrierDismissible = true,
  AdaptiveStyle? style,
  @Deprecated('Use `useActionSheetForIOS` instead. Will be removed in v2.')
  bool useActionSheetForCupertino = false,
  bool useActionSheetForIOS = false,
  bool useRootNavigator = true,
  VerticalDirection actionsOverflowDirection = VerticalDirection.up,
  bool fullyCapitalizedForMaterial = true,
  bool canPop = true,
  PopInvokedCallback? onPopInvoked,
  AdaptiveDialogBuilder? builder,
  Widget? macOSApplicationIcon,
  RouteSettings? routeSettings,
}) {
  void pop({required BuildContext context, required T? key}) => Navigator.of(
        context,
        rootNavigator: useRootNavigator,
      ).pop(key);

  final theme = Theme.of(context);
  final colorScheme = theme.colorScheme;
  final adaptiveStyle = style ?? AdaptiveDialog.instance.defaultStyle;
  final isIOSStyle = adaptiveStyle.effectiveStyle(theme) == AdaptiveStyle.iOS;
  if (isIOSStyle && (useActionSheetForCupertino || useActionSheetForIOS)) {
    return showModalActionSheet(
      context: context,
      title: title,
      message: message,
      cancelLabel: actions.findCancelLabel(),
      actions: actions.convertToSheetActions(),
      style: style,
      useRootNavigator: useRootNavigator,
      canPop: canPop,
      onPopInvoked: onPopInvoked,
      builder: builder,
      routeSettings: routeSettings,
    );
  }

  final titleText = title == null ? null : Text(title);
  final messageText = message == null ? null : Text(message);

  final effectiveStyle = adaptiveStyle.effectiveStyle(theme);
  switch (effectiveStyle) {
    // ignore: deprecated_member_use_from_same_package
    case AdaptiveStyle.cupertino:
    case AdaptiveStyle.iOS:
      return showCupertinoDialog(
        context: context,
        useRootNavigator: useRootNavigator,
        routeSettings: routeSettings,
        builder: (context) {
          final dialog = PopScope(
            canPop: canPop,
            onPopInvoked: onPopInvoked,
            child: CupertinoAlertDialog(
              title: titleText,
              content: messageText,
              actions: actions
                  .map(
                    (a) => a.convertToIOSDialogAction(
                      onPressed: (key) => pop(context: context, key: key),
                    ),
                  )
                  .toList(),
              // TODO(mono): Set actionsOverflowDirection if available
              // https://twitter.com/_mono/status/1261122914218160128
            ),
          );
          return builder == null ? dialog : builder(context, dialog);
        },
      );
    case AdaptiveStyle.macOS:
      final buttons = actions
          .map(
            (a) => a.convertToMacOSDialogAction(
              onPressed: (key) => pop(context: context, key: key),
            ),
          )
          .intersperse(const SizedBox(height: 8))
          .toList()
          .reversed
          .toList();
      return showMacosAlertDialog(
        context: context,
        useRootNavigator: useRootNavigator,
        routeSettings: routeSettings,
        builder: (context) {
          final Widget dialog = MacThemeWrapper(
            child: PopScope(
              canPop: canPop,
              onPopInvoked: onPopInvoked,
              child: MacosAlertDialog(
                title: titleText ?? const SizedBox.shrink(),
                message: messageText ?? const SizedBox.shrink(),
                primaryButton: const _DummyEmptyMacosPushButton(),
                suppress: Column(
                  crossAxisAlignment: CrossAxisAlignment.stretch,
                  children: buttons,
                ),
                appIcon: macOSApplicationIcon ??
                    AdaptiveDialog.instance.macOS.applicationIcon ??
                    const Icon(Icons.info),
              ),
            ),
          );
          return builder == null ? dialog : builder(context, dialog);
        },
      );
    case AdaptiveStyle.material:
      return showModal(
        context: context,
        useRootNavigator: useRootNavigator,
        routeSettings: routeSettings,
        configuration: FadeScaleTransitionConfiguration(
          barrierDismissible: barrierDismissible,
        ),
        builder: (context) {
          final dialog = PopScope(
            canPop: canPop,
            onPopInvoked: onPopInvoked,
            child: AlertDialog(
              title: titleText,
              content: messageText,
              actions: actions
                  .map(
                    (a) => a.convertToMaterialDialogAction(
                      onPressed: (key) => pop(context: context, key: key),
                      destructiveColor: colorScheme.error,
                      fullyCapitalized: fullyCapitalizedForMaterial,
                    ),
                  )
                  .toList(),
              actionsOverflowDirection: actionsOverflowDirection,
              scrollable: true,
            ),
          );
          return builder == null ? dialog : builder(context, dialog);
        },
      );
    case AdaptiveStyle.adaptive:
      assert(false);
      return Future.value();
  }
}