1

I am trying to replicate this animation with my appBar:

enter image description here

I know I can use SliverAppBar and simply animate the textSize. But how would I implement the logic for the image? It moves to the right and slightly shrinks.

This is what I have for the text:

  SliverAppBar(
    expandedHeight: 200,
    flexibleSpace: FlexibleSpaceBar(
      title: Text('Test', textScaleFactor: 1),
    ),
    pinned: true,
  ),

Any idea how I could solve this?

2
  • try SliverPersitentHeader Commented Jan 20, 2023 at 15:51
  • @pskink I found this answer on SO, but the animation is a bit different. I would like my widgets to animate to their place and size. Not that another widget simply appears Commented Jan 20, 2023 at 16:00

2 Answers 2

4

You play with SliverPersistentHeaderDelegate

class AppSliverPersistentHeaderDelegate extends SliverPersistentHeaderDelegate {
  @override
  Widget build(
      BuildContext context, double shrinkOffset, bool overlapsContent) {
    final t = shrinkOffset / maxExtent;
    return Stack(
      children: [
        Align(
          alignment: Alignment(0, .7), //perhaps it should also use lerp
          child: Text(
            "Title",
            style: TextStyle(fontSize: ui.lerpDouble(34, 14, t)),
          ),
        ),
        Align(
          alignment:
              Alignment.lerp(Alignment.topCenter, Alignment.topRight, t)!,
          child: Padding(
            padding: const EdgeInsets.all(8.0),
            child: Icon(Icons.settings),
          ),
        )
      ],
    );
  }

  @override
  double get maxExtent => 200;

  @override
  double get minExtent => kToolbarHeight;

  @override
  bool shouldRebuild(covariant SliverPersistentHeaderDelegate oldDelegate) {
    return false;
  }
}

And used on

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      home: Scaffold(
        body: CustomScrollView(
          slivers: [
            SliverPersistentHeader(
              pinned: true,
              delegate: AppSliverPersistentHeaderDelegate(),
            ),
            SliverToBoxAdapter(
              child: Container(
                height: 12222,
                color: Colors.red,
              ),
            )
          ],
        ),
      ),
    );
  }
}
Sign up to request clarification or add additional context in comments.

2 Comments

what exactly is lerp doing?
lerp is beautiful method choosing value in-between two based on t=> lerp(a, b, t) = a + (b — a) * t. I've import 'dart:ui' as ui;
0

You can try using AnimatedPositioned class which flutter already provide . Check this link

https://api.flutter.dev/flutter/widgets/AnimatedPositioned-class.html

You can use it and the change the position and size depending on a specific action .

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.