Hero Animation Not Working in Flutter Hero Animation Not Working in Flutter dart dart

Hero Animation Not Working in Flutter


Checked your code so the hero animation is working but its happening to fast because of the transition duration is only 300 milliseconds.

To achieve the below result you can make a Custom MaterialPageRoute.

Before

@override  Duration get transitionDuration => const Duration(milliseconds: 300);

After

@override  Duration get transitionDuration => const Duration(milliseconds: 1000);

Also, you can play with the CurvedAnimation

new CurvedAnimation(                parent: routeAnimation,                curve: Curves.elasticIn,              )

demo

CustomRoute.dart

import 'package:flutter/cupertino.dart';import 'package:flutter/foundation.dart';import 'package:flutter/gestures.dart';import 'package:flutter/material.dart';import 'package:flutter/rendering.dart';import 'package:flutter/widgets.dart';final Tween<Offset> _kBottomUpTween = new Tween<Offset>(  begin: const Offset(0.0, 1.0),  end: Offset.zero,);// Offset from offscreen to the right to fully on screen.final Tween<Offset> _kRightMiddleTween = new Tween<Offset>(  begin: const Offset(1.0, 0.0),  end: Offset.zero,);// Offset from offscreen below to fully on screen.class AppPageRoute extends MaterialPageRoute<String> {  @override  final bool maintainState;  @override  final WidgetBuilder builder;  CupertinoPageRoute<String> _internalCupertinoPageRoute;  AppPageRoute({    @required this.builder,    RouteSettings settings: const RouteSettings(),    this.maintainState: true,    bool fullscreenDialog: false,  })  : assert(builder != null),        assert(settings != null),        assert(maintainState != null),        assert(fullscreenDialog != null),        super(          settings: settings,          fullscreenDialog: fullscreenDialog,          builder: builder,        ) {    assert(opaque); // PageRoute makes it return true.  }  @override  Color get barrierColor => null;  @override  Duration get transitionDuration => const Duration(milliseconds: 1000);  CupertinoPageRoute<String> get _cupertinoPageRoute {    assert(_useCupertinoTransitions);    _internalCupertinoPageRoute ??= new CupertinoPageRoute<String>(      builder: builder,      fullscreenDialog: fullscreenDialog,      hostRoute: this,    );    return _internalCupertinoPageRoute;  }  bool get _useCupertinoTransitions {    return _internalCupertinoPageRoute?.popGestureInProgress == true ||        Theme.of(navigator.context).platform == TargetPlatform.iOS;  }  @override  Widget buildPage(BuildContext context, Animation<double> animation, Animation<double> secondaryAnimation) {    final Widget result = builder(context);    assert(() {      if (result == null) {        throw new FlutterError('The builder for route "${settings.name}" returned null.\n'            'Route builders must never return null.');      }      return true;    }());    return result;  }  @override  Widget buildTransitions(      BuildContext context, Animation<double> animation, Animation<double> secondaryAnimation, Widget child) {    if (_useCupertinoTransitions) {      return _cupertinoPageRoute.buildTransitions(context, animation, secondaryAnimation, child);    }    return new _CustomPageTransition(routeAnimation: animation, child: child, fullscreenDialog: fullscreenDialog);  }}class _CustomPageTransition extends StatelessWidget {  final Animation<Offset> _positionAnimation;  final Widget child;  final bool fullscreenDialog;  _CustomPageTransition({    Key key,    @required Animation<double> routeAnimation,    @required this.child,    @required this.fullscreenDialog,  })  : _positionAnimation = !fullscreenDialog            ? _kRightMiddleTween.animate(new CurvedAnimation(                parent: routeAnimation,                curve: Curves.elasticIn,              ))            : _kBottomUpTween.animate(new CurvedAnimation(                parent: routeAnimation, // The route's linear 0.0 - 1.0 animation.                curve: Curves.elasticIn,              )),        super(key: key);  @override  Widget build(BuildContext context) {    return new SlideTransition(      position: _positionAnimation,      child: child,    );  }}

Push new Route

 Future goToHomePage() async {    await new Future.delayed(const Duration(milliseconds: 4000));    Navigator.of(context).push(new AppPageRoute(builder: (BuildContext context) => new HomePage()));  }

You can use Custom MaterialPageRoute for the splash screen and for other routes MaterialPageRoute.

Hope it helps


// main.dart classimport 'package:flutter/material.dart';import 'package:flutter/scheduler.dart' show timeDilation;import 'package:flutter_test7/photo_hero.dart';import 'package:flutter_test7/second_page.dart';class HeroAnimation extends StatelessWidget {  Widget build(BuildContext context) {    timeDilation = 2.5; // 1.0 means normal animation speed.    return new Scaffold(      appBar: new AppBar(        title: const Text('Basic Hero Animation'),      ),      body: new Center(        child: new PhotoHero(          photo: 'images/flippers-alpha.png',          width: 300.0,          onTap: () {            Navigator.of(context).pushNamed('/second_page');          },        ),      ),    );  }}void main() {  runApp(    new MaterialApp(      home: new HeroAnimation(),      routes: <String, WidgetBuilder>{        '/second_page': (context) => new SecondPage()      },    ),  );}// photo_hero.dart classimport 'package:flutter/material.dart';class PhotoHero extends StatelessWidget {  const PhotoHero({Key key, this.photo, this.onTap, this.width})      : super(key: key);  final String photo;  final VoidCallback onTap;  final double width;  Widget build(BuildContext context) {    return new SizedBox(      width: width,      child: new Hero(        tag: photo,        child: new Material(          color: Colors.transparent,          child: new InkWell(            onTap: onTap,            child: new Image.asset(              photo,              fit: BoxFit.contain,            ),          ),        ),      ),    );  }}// second_page.dart classimport 'package:flutter/material.dart';import 'package:flutter_test7/photo_hero.dart';class SecondPage extends StatefulWidget {  @override  _SecondPageState createState() => new _SecondPageState();}class _SecondPageState extends State<SecondPage> {  @override  Widget build(BuildContext context) {    return new Scaffold(      appBar: new AppBar(        title: const Text('Flippers Page'),      ),      body: new Container(        color: Colors.lightBlueAccent,        padding: const EdgeInsets.all(16.0),        alignment: Alignment.topLeft,        child: new PhotoHero(          photo: 'images/flippers-alpha.png',          width: 100.0,          onTap: () {            Navigator.of(context).pop();          },        ),      ),    );  }}

Hope this helps.


Hero animation is quite easy to implement in Flutter. You just need to import the package package:flutter/scheduler.dart in your landing page. See below code

import 'package:flutter/scheduler.dart' show timeDilation;

Remember to add timeDilation variable and assign it a value to speed up or slow down the animation in seconds. Add these just after your build method as in example below

Widget build(BuildContext context) {    timeDilation = 2;

For better animation, just use a custom animation