this my alert widget.

import 'package:audioplayers/audioplayers.dart';
import 'package:flutter/material.dart';
import 'package:flutter_animate/flutter_animate.dart';
import 'package:investment_com/abstract_provider.dart';
import 'package:investment_com/core/Config/Converter.dart';
import 'package:investment_com/core/enums/enums.dart';
import 'package:investment_com/features/service_invoices/presentation/providers/add_delete_update_services_invoices_provider.dart';
import 'package:lottie/lottie.dart';
import 'package:provider/provider.dart';

class AnimatedPopUpDialog<T> extends StatefulWidget {
  const AnimatedPopUpDialog({
    @required this.executeFunction,
    this.autoDismiss,
    this.duration,
    this.onOkTap,
    this.showRetryButton,
    this.lottieErrorAssetsName,
    this.lottieLoadingAssetsName,
    this.lottieSuccessAssetsName,
  });

  final Function() onOkTap;
  final Function() executeFunction;

  final String lottieSuccessAssetsName;
  final String lottieErrorAssetsName;
  final String lottieLoadingAssetsName;
  final bool showRetryButton;
  final bool autoDismiss;
  final Duration duration;

  @override
  State<AnimatedPopUpDialog<T>> createState() => _AnimatedPopUpDialogState<T>();
}

class _AnimatedPopUpDialogState<T> extends State<AnimatedPopUpDialog<T>> with TickerProviderStateMixin {
  AnimationController _controller;
  Animation<double> _iconScaleAnimation;
  Animation<double> _containerScaleAnimation;
  Animation<Offset> _yAnimation;
  AnimationController _textAnimation;
  AnimationController _retryRotateController;
  Animation<double> _retryRotateAnimation;

  AudioPlayer _player;
  Color circleColor = Converter.hexToColor("#2094cd").withOpacity(0.1);
  String _lottieName;
  bool _isFirstRun = true;
  bool isStateChanging = false;
  AbstractProvider _provider;
  @override
  void initState() {
    super.initState();

    Future.delayed(
      Duration.zero,
      () => widget.executeFunction(),
    );

    //? initialize the first state
    _lottieName = widget.lottieLoadingAssetsName;
    print(widget.lottieErrorAssetsName);

    //? initialize the Audio player and aninimation controllers

    _player = AudioPlayer();
    _controller = AnimationController(
      vsync: this,
      duration: const Duration(seconds: 1),
    );

    _textAnimation = AnimationController(
      vsync: this,
      duration: const Duration(seconds: 1),
    );

    _retryRotateController = AnimationController(
      vsync: this,
      duration: const Duration(milliseconds: 500),
    );

    _retryRotateAnimation = Tween<double>(
      begin: 0.1,
      end: 1.0,
    ).animate(
      CurvedAnimation(
        parent: _retryRotateController,
        curve: Curves.easeInOut,
      ),
    );

    _yAnimation = Tween<Offset>(
      begin: const Offset(0, 0),
      end: const Offset(0, -0.23),
    ).animate(
      CurvedAnimation(
        parent: _controller,
        curve: Curves.easeInOut,
      ),
    );

    _iconScaleAnimation = Tween<double>(
      begin: 4,
      end: 3,
    ).animate(
      CurvedAnimation(
        parent: _controller,
        curve: Curves.easeInOut,
      ),
    );

    _containerScaleAnimation = Tween<double>(
      begin: 3.0,
      end: 0.4,
    ).animate(
      CurvedAnimation(
        parent: _controller,
        curve: Curves.bounceOut,
      ),
    );

    //Start the animation
    _controller
      ..reset()
      ..forward().whenComplete(() {
        setState(() {
          circleColor = Colors.transparent;
        });
      });

    _textAnimation
      ..reset()
      ..forward();
  }

  @override
  void didChangeDependencies() {
    //Excute the function

    super.didChangeDependencies();
  }

  @override
  void dispose() {
    _controller.dispose();
    _textAnimation.dispose();
    _retryRotateController.dispose();
    super.dispose();
  }

  @override
  void deactivate() {
    _provider.reset();
    super.deactivate();
  }

  @override
  Widget build(BuildContext context) {
    return Consumer<T>(
      builder: (context, value, child) {
        _provider = value as AbstractProvider;
        updateUiState();
        return WillPopScope(
          onWillPop: () async => _provider.dataState != DataState.loading,
          child: ClipRRect(
              borderRadius: BorderRadius.circular(20),
              child: Container(
                  height: 350,
                  decoration: BoxDecoration(
                    color: Colors.white,
                  ),
                  child: ConstrainedBox(
                      constraints: BoxConstraints(minWidth: 100, minHeight: 100, maxWidth: 100),
                      child: Stack(
                        children: [
                          Column(
                            mainAxisAlignment: MainAxisAlignment.center,
                            crossAxisAlignment: CrossAxisAlignment.center,
                            mainAxisSize: MainAxisSize.min,
                            children: [
                              const SizedBox(
                                height: 200,
                              ),
                              if (!isStateChanging && _provider.canPlayTheAnimation)
                                Row(
                                  mainAxisAlignment: MainAxisAlignment.center,
                                  children: [
                                    Text(
                                      '${tanslatedDataState(_provider.dataState)}',
                                      textAlign: TextAlign.center,
                                      style: const TextStyle(
                                        fontSize: 14,
                                        fontWeight: FontWeight.bold,
                                        color: Colors.black,
                                      ),
                                    ).animate(controller: _textAnimation).fadeIn().slideX(),
                                  ],
                                )
                              else
                                SizedBox(height: 15),
                              const SizedBox(
                                height: 50,
                              ),
                              Row(
                                mainAxisAlignment: MainAxisAlignment.center,
                                children: [
                                  if (_provider.dataState == DataState.loading && !isStateChanging)
                                    ElevatedButton(
                                      style: ButtonStyle(
                                        backgroundColor: MaterialStatePropertyAll(Colors.red[400]),
                                        shadowColor: MaterialStatePropertyAll(Colors.transparent),
                                      ),
                                      onPressed: () {
                                        if (widget.onOkTap != null) widget.onOkTap();
                                        Navigator.pop(context);
                                      },
                                      child: Text('Cancel'),
                                    ).animate(controller: _textAnimation).fadeIn().slideX(),
                                ],
                              ),
                              if (_provider.dataState != DataState.loading && !isStateChanging)
                                Row(
                                  mainAxisAlignment: MainAxisAlignment.spaceEvenly,
                                  children: [
                                    ElevatedButton(
                                      style: ButtonStyle(
                                        backgroundColor: MaterialStatePropertyAll(Converter.hexToColor("#2094cd")),
                                        shadowColor: MaterialStatePropertyAll(Colors.transparent),
                                      ),
                                      onPressed: () {
                                        if (widget.onOkTap != null) widget.onOkTap();
                                        Navigator.pop(context);
                                      },
                                      child: Text('OK'),
                                    ).animate(controller: _textAnimation).fadeIn().slideX(),
                                    if (_provider.dataState == DataState.failure &&
                                        widget.showRetryButton &&
                                        !_provider.canPlayTheAnimation)
                                      ElevatedButton(
                                        style: ButtonStyle(
                                            backgroundColor: MaterialStatePropertyAll(Colors.transparent),
                                            shadowColor: MaterialStatePropertyAll(Colors.transparent),
                                            side: MaterialStatePropertyAll(
                                                BorderSide(color: Converter.hexToColor("#2094cd")))),
                                        onPressed: () async {
                                          _retryRotateController.forward();
                                          isStateChanging = true;
                                          await _provider.setLoadingState();
                                          _changeToLoading();

                                          widget.executeFunction();

                                          ///Excute the onRetry function after tje animation is complete
                                          ///if it is not null

                                          _retryRotateController.reset();
                                        },
                                        child: Row(
                                          children: [
                                            RotationTransition(
                                                turns: _retryRotateAnimation,
                                                child: Icon(Icons.restart_alt_sharp,
                                                    color: Converter.hexToColor("#2094cd"))),
                                            Text('Retry', style: TextStyle(color: Converter.hexToColor("#2094cd"))),
                                          ],
                                        ),
                                      ).animate(controller: _textAnimation).shimmer().slideX(),
                                  ],
                                )

                              // if (isStateChanging) SizedBox(height: 60)
                            ],
                          ),
                          Positioned.fill(
                            child: Padding(
                              padding: const EdgeInsets.only(top: 25, left: 40, right: 40),
                              child: SlideTransition(
                                position: _yAnimation,
                                child: ScaleTransition(
                                  scale: _containerScaleAnimation,
                                  child: Container(
                                    decoration: BoxDecoration(
                                      shape: BoxShape.circle,
                                      color: circleColor,
                                    ),
                                    child: ScaleTransition(
                                      scale: _iconScaleAnimation,
                                      child: isStateChanging
                                          ? SizedBox.shrink()
                                          : InkWell(
                                              onTap: () {
                                                context
                                                    .read<AddDeleteUpdateServicesInvoicesProvider>()
                                                    .updateCreatingState(DataState.done);
                                              },
                                              child: Lottie.asset('assets/lottie/$_lottieName.json', reverse: true)),
                                    ),
                                  ),
                                ),
                              ),
                            ),
                          )
                        ],
                      )))),
        );
      },
    );
  }

  String tanslatedDataState(DataState state) {
    switch (state) {
      case DataState.loading:
        return 'جاري التنفذي';

      case DataState.done:
        return 'تمت العملية بنجاح';

      case DataState.failure:
        return 'حدث خطأ';

      case DataState.notSet:
        break;
      case DataState.empty:
        break;
      case DataState.hasData:
        break;
      case DataState.offline:
        return 'تأكد من  جودة الانترنت';
    }
    return '';
  }

  void updateUiState() {
    Future.delayed(Duration.zero, () async {
      _provider.compaerStates();
      print(_provider.dataState);
      // print(widget.lottieErrorAssetsName);
      switch (_provider.dataState) {
        case DataState.loading:
          if (_provider.playAnimation && _provider.canPlayTheAnimation) {
            _provider.playAnimation = false;
            await _changeToLoading();
          }

          break;
        case DataState.done:
          if (_provider.playAnimation && _provider.canPlayTheAnimation) {
            _provider.playAnimation = false;
            await _changeToSucces();
          }
          break;

        case DataState.failure:
          if (_provider.playAnimation && _provider.canPlayTheAnimation) {
            _provider.playAnimation = false;
            await _changeToError();
          }
          break;
        case DataState.offline:
          if (_provider.playAnimation && _provider.canPlayTheAnimation) {
            _provider.playAnimation = false;
            await _changeToOffline();
          }
          break;

        case DataState.notSet:
          break;
        case DataState.empty:
          break;
        case DataState.hasData:
          break;
      }
    });
  }

  Future<void> _changeToError() async {
    setState(() {
      isStateChanging = true;
      _controller.reverse();
      circleColor = Converter.hexToColor('#f33342');
      _textAnimation..reverse();
      _lottieName = widget.lottieErrorAssetsName;
    });
    await _player.play(AssetSource('sounds/error.wav'));
    await Future.delayed(Duration(seconds: 1));

    _controller
      ..forward().whenComplete(() {
        circleColor = Colors.transparent;
        setState(() {});
        _textAnimation..forward();
      });
    await Future.delayed(Duration(seconds: 4));
    setState(() {
      isStateChanging = false;
    });
    _provider.completeAnimation();
  }

  Future<void> _changeToOffline() async {
    setState(() {
      isStateChanging = true;
      _controller.reverse();
      circleColor = Colors.blue[800];
      _textAnimation..reverse();
      _lottieName = 'offline';
    });
    await Future.delayed(Duration(seconds: 1));

    _controller
      ..forward().whenComplete(() {
        circleColor = Colors.transparent;
        setState(() {});
        _textAnimation..forward();
      });
    await Future.delayed(Duration(seconds: 4));
    setState(() {
      isStateChanging = false;
    });
    _provider.completeAnimation();
  }

  Future<void> _changeToSucces() async {
    setState(() {
      isStateChanging = true;
    });
    _controller.reverse();
    circleColor = Colors.blue[300];
    _textAnimation..reverse();
    await _player.play(AssetSource('sounds/success.mp3'));
    await Future.delayed(Duration(seconds: 1));
    _lottieName = widget.lottieSuccessAssetsName;
    print('$_lottieName +++++++=');
    setState(() {});
    isStateChanging = false;
    _controller
      ..forward().whenComplete(() {
        circleColor = Colors.transparent;
        setState(() {});
        _textAnimation.forward();
      });
    await Future.delayed(Duration(seconds: 4));

    _provider.completeAnimation();

    //Dismiss the dialog
    if (widget.autoDismiss) autoDismiss();
  }

  Future<void> _changeToLoading() async {
    print('isStateChanging $isStateChanging');
    _textAnimation
      ..reverse()
      ..stop();
    _retryRotateController.forward();
    isStateChanging = true;
    setState(() {});
    _controller.reverse();
    circleColor = Converter.hexToColor("#2094cd").withOpacity(0.1);
    await _player.play(AssetSource('sounds/loading.wav'));
    await Future.delayed(Duration(seconds: 1));
    _lottieName = widget.lottieLoadingAssetsName;

    _controller
      ..forward().whenComplete(
        () {
          circleColor = Color.fromRGBO(0, 0, 0, 0);
          setState(() {});

          _textAnimation..forward();
        },
      );
    setState(() {
      isStateChanging = false;
    });
    await Future.delayed(Duration(seconds: 3));
    print('isStateChanging $isStateChanging');

    _provider.completeAnimation();
  }

  void autoDismiss() {
    Future.delayed(widget.duration, () => Navigator.of(context).pop());
  }
}


this my provider handling the ui state.
import 'package:flutter/material.dart';
import 'package:investment_com/core/enums/enums.dart';

abstract class AbstractProvider extends ChangeNotifier {
  DataState dataState = DataState.loading;
  DataState oldState = DataState.notSet;

  String message = "";
  bool playAnimation = true;

  bool canPlayTheAnimation = true;

  void compaerStates() async {
    if (oldState != dataState && canPlayTheAnimation) {
      print('yes i can');
      await Future.delayed(Duration(seconds: 2));

      print('${dataState.name} VS ${oldState.name}');
      playAnimation = true;
      oldState = dataState;
      canPlayTheAnimation = false;
      notifyListeners();
    }
  }

  Future<void> setLoadingState() async {
    await Future.delayed(Duration(seconds: 2));
    dataState = DataState.loading;
    notifyListeners();
  }

  void completeAnimation() async {
    canPlayTheAnimation = true;
    notifyListeners();
  }

  void reset() {
    dataState = DataState.notSet;
    oldState = DataState.notSet;
    playAnimation = true;
    canPlayTheAnimation = true;
  }
}



how to await the animate tho complete to play other animation while the data state is upditing