Most of us use the Google Maps app in our day to day life. It is a real savior app when we are lost but it has also got a cool feature of exploring nearby places. I am sure you must have tried it at least once.

A nice user experience allows us to explore a place, without leaving the actual place on the map. It has got a card view like something at the bottom. When you drag it upwards in order to explore more, it covers the entire screen and comes on top of the map. You can scroll through the more content if you drag it more in an upward direction. The whole explore view can be put at the bottom if you swipe down. I really like this user experience.

Question -

How do we develop similar experiences in Flutter? Will you try it on your own? Will you use any Third-party library?

Answer -

Luckily, the Flutter team is working very hard for us to develop widgets for such user experience. A big shout out for Flutter Team.👏

🎤 Presenting the DraggableScrollableSheet

DraggableScrollableSheet is a widget that holds a scrollable widget allowing to drag and resize it until a particular limit (fraction of height) is reached and then enable scrolling on contents inside like this.

Basic UI structure

DraggableScrollableSheet(

builder: (BuildContext context, myscrollController) {

return Container(

color: Colors.tealAccent[200],

child: ListView.builder(

controller: myscrollController,

itemCount: 25,

itemBuilder: (BuildContext context, int index) {

return ListTile(

title: Text(

'Dish $index',

style: TextStyle(color: Colors.black54),

));

},

),

);

},

)

Let’s look at it’s properties:

builder: (){}

DraggableScrollableSheet requires at least a builder that can create a child widget to show. It uses the scrollController to apply to drag and scrolling on the child widget.

In the above code, we have used one container with a list view inside, That creates a number of items and that’s it. You have got DraggableScrollableSheet working.

At this point I want you to figure out something. Did you notice any strange thing?

How this widget is able to show up some of its portions initially and after dragging it vertically up and down?

Let’s reveal some secrets…

Just place a cursor and hold Ctrl (PC) ⌘(Mac) and click on the widget. (Go to the widget definition in short)

You can see some default values applied to properties named as

initialChildSize , minChildSize , maxChildSize

The values applied there, are in the percentage(%) of the height of the parent.

You can always override this default values like this.

DraggableScrollableSheet(

initialChildSize: 0.3,

minChildSize: 0.2,

maxChildSize: 1.0,

builder: (BuildContext context, myscrollController) {

return Container(

color: Colors.tealAccent[200],

child: ListView.builder(

controller: myscrollController,

itemCount: 25,

itemBuilder: (BuildContext context, int index) {

return ListTile(

title: Text(

'Dish $index',

style: TextStyle(color: Colors.black54),

));

},

),

);

},

)

initialChildSize —

This property defines how much a portion of DraggableScrollableSheet should display on the screen initially to let users know that there is something that they can interact with. For example, in the above code, we have set it to initialChildSize: 0.3

Meaning, DraggableScrollableSheet will display its child in 30% of the parent's height at the bottom initially. Let’s see it in action.

maxChildSize —

This property defines how much a portion of DraggableScrollableSheet should display its child when fully dragged and start scrolling after that. This gives users an opportunity to look into more content inside. Setting maxChildSize: 1.0 will display its child in 100% of the parent's height when dragging upwards.

minChildSize —

This property defines how much a portion of DraggableScrollableSheet should display its child when the user drags it down and trying to put this widget to its original place. Setting minChildSize: 0.2 will force contents to show up in 20% of the parent's height when the user is done with exploring contents inside and trying to swipe down widget.

How this all works together.

At very first user will see a specified portion of DraggableScrollableSheet’s child and then he/she will be able to drag and scroll it between specified min and max child size. Pretty simple. Isn’t it?

How it is different from BottomSheet and can be considered as Advanced version of it.

DraggableScrollableSheet gives more flexibility to developers. App owners can create a more engaging experience with DraggableScrollableSheet than BottomSheet. You can’t drag and then scroll BottomSheet.

What can we expect more in this widget?

As of writing this article, this widget does not have snap behavior. Meaning when you drag it in an upward direction, It goes up to the specified maxChildSize and then starts scrolling. Instead, there should be something like sheet should stop expanding at multiple points while dragging and should start scrolling when maxChildSize is reached. New property something like this should be introduced

snapAt:[0.3,0.7]

where points to stop sheet while dragging is given in percentage of parent’s height.

Here is the full working gist of the demo.