Skip to content

Instantly share code, notes, and snippets.

@Rahiche

Rahiche/blog.md Secret

Created December 18, 2018 21:41
Show Gist options
  • Save Rahiche/18961be6a6db1cf93729953c3f3b56b7 to your computer and use it in GitHub Desktop.
Save Rahiche/18961be6a6db1cf93729953c3f3b56b7 to your computer and use it in GitHub Desktop.

Scrolling Animation

Animation library in Flutter is really Awesome but there are other types of aniamtion that depends on user interaction and today i will talk about one of them which is the scrolling animation, i will foucus on how you can acheive smooth scrolling animation then i will discuss the best practices.

Making sense of Scrolling Animation

So just to be clear there are two types of Scrolling Animation the first is a just a normal animation that happens when the user scroll to a specifc place and the second one depends on the overall amount of scrolling so that the value of the animation depends on how much the user scrolls and this artcile will foucs more on the second one;

Drive layout based on the scroll position

Every scrollable Widget in flutter has some kind of controller and all of them implement the ScrollController, in the next example i will use the Controller to read the current scroll offset of the widget and using that value will do some visual intercation.

for example let's do this: //add pic 1

Decalre the following variables in the State object :

https://gist.github.com/4051bd79cd99cfd0a68f27446f01e6af

NOTE : This example will work just if you know how many items in the list and they have fixed height.

Next , create the layout :

https://gist.github.com/7ff724fbbaf61d4a4abfad9d21bf1b0e

Now let's deal with the controller :

https://gist.github.com/fe54477a5f19c979143daea8b90e2e85

The only interesting part is in line 11 where we have the math to calcite the right width for the green Container.

Trigger Animation based on the scroll events

Imagine a cenarion where you want hide some widgets when the user scroll up/dwon with some in/out animations in this case you don't want to check every time the user scroll, What you really want is way to know if the user start/stoped scrolling and there is no better widget then NotificationListener for this becuase you can use it to listen for ScrollNotifications.

Example : Hide widgets(AppBar,FAB and BottomAppBar) when the user is scrolling and hide them when he stop. //todo : Add image 3

Step 1: Setup Layout

https://gist.github.com/82aeb05c5200139c17d03a052bedab9a

NOTES : 1.Using PreferredSize in the appBar is requred otherwise you should create your custom appBar 2.I used FittedBox just to avoid some scalling issues while aniamting.Delete it and you will see.

Step 2 : Setup Animation

I think you know the biorplate but just to be cleat i am goign to use a Tween(begin: 0.0, end: 50.0) for the aniamtion object, and next change the value 50.0 in all the previuos code to aniamtion.value,

https://gist.github.com/5ef23d9de529b27b186b0161044b8a79

Step 3 : Listen to Scroll Notifications

Wrap the ListView with NotificationListener of Type ScrollStartNotification and Another one for ScrollEndNotification

https://gist.github.com/cba46e40c22527b70582957d8a3773cb

Let me explain : If the user start scrolling then reverse the animation which means hide the widgets or make them smaller so they will becomes invisible and if the user stops moving show them again.

The previos example is good but it's a good UI practe so let's do a common UI pattern "Showing back-to top button when the user is scrolling dwon". in this example we will do the same Step 1 and 2 from the previous example and do some cahge in step 3:

//Todo: add image 4

https://gist.github.com/0ed252b0d547cbe61d7537ff93afb6ad

We use ScrollUpdateNotification to the scrollDelta so that we can decide if the user is scrolling up or dwon.and to make it easy to inverse the effect so for example if you want to show the widget's if the user is scrolling down just inverse the condtion from notification.scrollDelta < 0 to notification.scrollDelta < 0 and do the same for the other condition.

Use dynamic layout using LayoutBuilder

Every scrollable widget in flutter is built on top of Slivers and when it comes to Slivers we must use CustomScrollView which means you have only one controller for all your slivers but the problem is some slivers behaviuor is complex and you can't get the right numbers easly just by using a ScrollController for example : A SliverAppBar with pinned:true and floating:true so as an alternative we can use LayoutBuilder to get the box constains or simply how much space is available for us.so let's try to similate the next example :

//TODO : add iamge 5

Step 1 : Basic Layout

https://gist.github.com/cbcb21f902c954bff26f5cf417123b17

Step 2 : use LayoutBuilder

Wrap the Stack in line 9 with LayoutBuilder and implemnt the Builder and then declare a Two new doubles:

https://gist.github.com/eb83ba4ea1bc30ea4a99bff36714e68e

Step 3 : Aniamte The Widgets

https://gist.github.com/03d570e0a1ea872773b9471f7edebbb6

Complex Example

So for the Dinner Today you will try to make this: //Todo Add Image Okay for this one i will just give you the full code source and some notes and you try it if you want Note 1 : i used the same Setup from the preivuos example but i have two layers here the first contsins the Text and the Icon in the right and the secnd layer contant the CustomPainter

https://gist.github.com/3dbc7591d5cf03879fac7e04d30f171a

Note 2 : in the CustomPaint you will find to major parts: Before and After %50 in the first part we draw just the line and in the next one we draw both the Arc and the Polygon

Note 3 : it's just simple math i didn't use any formua i was just testing to get the ringht numbers and i think i can imporve in the future

Finnaly here is the code source for the last aniamtion it's still WIP but if you have any suggestions that would be great, see you in the next article

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment