feduke-nukem / flutter_easy_dialogs

Easy dialogs library for Flutter
https://pub.dev/packages/flutter_easy_dialogs
MIT License
13 stars 0 forks source link

[Question]: Animation for showing/hiding a dialog #25

Closed DevTello closed 6 months ago

DevTello commented 7 months ago

What is your question?

How do I set up an animation for showing/hiding a dialog?

Code of Conduct

feduke-nukem commented 7 months ago

@DevTello, hello.

Do you mean setting up custom animation?

DevTello commented 7 months ago

Well, I need to set a Duration of showing and fading of a dialog, I managed to set up only decoration: const EasyDialogAnimation.fade()

feduke-nukem commented 7 months ago

Well, I need to set a Duration of showing and fading of a dialog, I managed to set up only decoration: const EasyDialogAnimation.fade()

Each dialog has a property named animationConfiguration of type EasyDialogAnimationConfiguration. Every applied animation is working according to this to look synchronized.

final content = Container(
  height: 150.0,
  color: Colors.blue[900],
  alignment: Alignment.center,
  child: Text(
    _selectedPosition.name,
    style: const TextStyle(
      color: Colors.white,
      fontSize: 30.0,
    ),
  ),
);

content
    .positioned(
      animationConfiguration:
          const EasyDialogAnimationConfiguration.bounded(
        duration: Duration(seconds: 1),
        reverseDuration: Duration(milliseconds: 500),
      ),
      autoHideDuration: _isAutoHide
          ? Duration(milliseconds: _autoHideDuration.toInt())
          : null,
    )
    .fade()
    .show();

To be able to configure durations independently you could create your own custom EasyDialogAnimation and override onShow/onHide methods to trigger independent AnimationController to control animation in a desired way.

Something like that:

final class IndependentFade<D extends EasyDialog> extends EasyDialogAnimation<D> {
  late final AnimationController _animationController;
  final Duration duration;
  final Duration reverseDuration;
  final TickerProvider vsync;

  IndependentFade({
    required this.duration,
    required this.reverseDuration,
    required this.vsync,
  });

  @override
  void init() {
    _animationController = AnimationController(
      duration: duration,
      reverseDuration: reverseDuration,
      vsync: vsync,
    );
  }

  @override
  void onShow() {
    super.onShow();

    _animationController.forward();
  }

  @override
  void onHide() {
    _animationController.reverse();
    super.onHide();
  }

  @override
  Widget call(D dialog) {
    return FadeTransition(
      opacity: CurvedAnimation(
        parent: _animationController,
        curve: curve,
      ),
      child: dialog.content,
    );
  }
}

For now it is required to explicitly pass vsync but technically each animation already has it under the hood. Maybe I should implement passing EasyDialogContext into lifecycle methods to avoid boilerplate.

DevTello commented 7 months ago

animationConfiguration: const EasyDialogAnimationConfiguration.bounded( duration: Duration(seconds: 1), reverseDuration: Duration(seconds: 1), ), forward duration plays 2x faster for me than reverseDuration, given they have the same Duration) is this the case for you?

feduke-nukem commented 7 months ago

animationConfiguration: const EasyDialogAnimationConfiguration.bounded( duration: Duration(seconds: 1), reverseDuration: Duration(seconds: 1), ), forward duration plays 2x faster for me than reverseDuration, given they have the same Duration) is this the case for you?

Could you provide sample code?

DevTello commented 6 months ago

Sorry for the delay, I'm overloaded a bit. Will do as soon as I can)

DevTello commented 6 months ago

Here you go. Subjectively these 2 sec are perceived as 1. Using Android 10

import 'package:flutter/material.dart';
import 'package:flutter_easy_dialogs/flutter_easy_dialogs.dart';

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

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: const MyHomePage(),
      builder: FlutterEasyDialogs.builder(),
    );
  }
}

class MyHomePage extends StatefulWidget {
  const MyHomePage({super.key});

  @override
  State<MyHomePage> createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  EasyDialog? _dialog;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
        appBar: AppBar(
          title: Text('Flutter Demo Home Page'),
        ),
        body: Center(
          child: MaterialButton(onPressed: showDialog, child: Text('Show')),
        ));
  }

  Future<void> showDialog() async {
    _dialog?.hide();
    _dialog = FullScreenDialog(
      animationConfiguration: const EasyDialogAnimationConfiguration.bounded(
        //plays 2x faster than reverseDuration for some reason
        duration: Duration(milliseconds: 2000),
        reverseDuration: Duration(milliseconds: 1000),
      ),
      decoration: const EasyDialogAnimation.fade(),
      content: Scaffold(
        body: SafeArea(
          child: Placeholder(child: Center(child: MaterialButton(onPressed: hideDialog, child: Text('Hide')))),
        ),
      ),
    )..show();
  }

  void hideDialog() {
    _dialog?.hide();
    _dialog = null;
  }
}
DevTello commented 6 months ago

Here is the link to the playground: https://flutlab.io/editor/bdca479b-172a-4311-81ef-fd0efc871343

feduke-nukem commented 6 months ago

Here is the link to the playground: https://flutlab.io/editor/bdca479b-172a-4311-81ef-fd0efc871343

Thanks.

I will take a close look as soon as possible.

feduke-nukem commented 6 months ago

Here is the link to the playground: https://flutlab.io/editor/bdca479b-172a-4311-81ef-fd0efc871343

Try to provide Curves.linear into const EasyDialogAnimation.fade(curve: Curves.linear).

The default curve is adding described "slow" behaviour.

DevTello commented 6 months ago

thanks, it helped, but not quite obvious)

feduke-nukem commented 6 months ago

thanks, it helped, but not quite obvious)

Probably I should set all curves as Linear by default.