A lot of Flutter developers, both beginners and intermediates often struggle with responsive design in Flutter.
In this post, we will learn how to make responsive widgets in Flutter which are supported in different devices.
Introduction
For the purpose of learning responsive design, we will refer to the following UI design.

Basically, this is a Category screen with a list of categories placed in two columns.
Each Category card has a fixed width and height. Then there is space between the cards and horizontal padding as well.
Mistake That Lead To Unresponsive Widget Designs
The main reason which lead to unresponsive widget designs is making use of fixed heights and widths in Flutter widgets.
For example, in the design specs created by the designer in Figma, we see the following dimensions:

Please don’t mind my rough drawing by hand here since no scales were used 😛
Category Card specs:
- Height = 260
- Width = 170
- Horizontal Padding = 18
- Gap Between = 24
If we look at the total width occupied, it is going to be 400 units.
(2 x card width) + (2 X padding) + Gap Between = 400
Now if we use these exact widths while designing our Flutter widgets, then things are definitely going to break on small devices whose dimensions are smaller than 400.
This is wrong which leads to unresponsive widgets in Flutter.
Row(
children: [
Container(
height: 260,
width: 170,
color: Colors.grey,
padding: EdgeInsets.only(left: 18),
child: Column(
children: [
//card content for text and image
],
),
),
SizedBox(width: 24,),
Container(
height: 260,
width: 170,
color: Colors.grey,
padding: EdgeInsets.only(right: 18),
child: Column(
children: [
//card content for text and image
],
),
)
],
);

Solution To Build Responsive Widgets In Flutter
Clearly, we have now seen that using fixed widths and heights lead to pixel overflowing errors.
So, how do we get responsive design in Flutter widgets?
As mentioned before, the first thing to do is avoid using fixed widths
and heights
when designing widgets and start using ratios
.
In theory, we can assume the following ratio:
Height in Design / Width in Design = Height in Device / Width in Design
We already know the height and width of design spec. Now the question is how do we calculate the responsive height and width of device?
MediaQuery To The Rescue
In order to get the height and width of device where our Flutter app is running, we can make use of MediaQuery
which gives us access to the device’s size information.
Calculating Responsive Width In Flutter
final MediaQueryData mediaQueryData = MediaQuery.of(context);
final double deviceHeight = mediaQueryData.size.height;
final double deviceWidth = mediaQueryData.size.width;
Once we know the device’s width, we can calculate the card’s responsive width as follow:
final double responsiveWidth =
(deviceWidth / 2) - padding - (spaceBetween / 2);
Basically, we are dividing the total available space into two parts and subtracting the padding space to calculate the width here.
Download Free Books To Learn Flutter
Calculating Responsive Height In Flutter
Next, we can also get the responsive height
now using the responsive width
value from our previous equation:
final double responsiveHeight =
(heightInDesign / widthInDesign) * responsiveWidth;
Final Responsive Design In Flutter Code
We have now learnt how to calculate the responsive width and height of any widget. The final code base implementation for our current use case is here.
final MediaQueryData mediaQueryData = MediaQuery.of(context);
final double deviceWidth = mediaQueryData.size.width;
final double heightInDesign = 260;
final double widthInDesign = 170;
final double padding = 18;
final double spaceBetween = 24;
final double responsiveWidth =
(deviceWidth / 2) - padding - (spaceBetween / 2);
final double responsiveHeight =
(heightInDesign / widthInDesign) * responsiveWidth;
return SingleChildScrollView(
child: Padding(
padding: EdgeInsets.symmetric(
horizontal: padding,
),
child: Row(
children: [
Container(
height: responsiveHeight,
width: responsiveWidth,
color: Colors.grey,
child: Column(
children: [
//card content for text and image
],
),
),
SizedBox(
width: spaceBetween,
),
Container(
height: responsiveHeight,
width: responsiveWidth,
color: Colors.grey,
child: Column(
children: [
//card content for text and image
],
),
)
],
),
),
);

Using this technique, we can make any widget responsive in Flutter.
Best wishes~
You must be logged in to post a comment.