Building Responsive UIs in Flutter: Adapting to Any Screen Size and Orientation

Creating a responsive UI in Flutter is essential for developing applications that look good on various screen sizes and orientations. This involves designing layouts that can adapt to different devices, such as smartphones, tablets, and desktops, ensuring a consistent and pleasant user experience.

Key Concepts for Responsive UI in Flutter

  1. Flexible Widgets:

    • Use widgets like Flexible, Expanded, and Spacer to create layouts that can adjust to different screen sizes.

    • These widgets help distribute available space and adjust the size of child widgets dynamically.

  2. MediaQuery:

    • MediaQuery provides information about the size, orientation, and pixel density of the current device's screen.

    • It is useful for making layout decisions based on the available screen space.

  3. LayoutBuilder:

    • LayoutBuilder allows you to build responsive layouts by providing the constraints of the parent widget.

    • You can create different layouts based on the constraints.

  4. AspectRatio:

    • AspectRatio helps maintain a specific aspect ratio for a widget.

    • It is useful for creating consistent layouts on different screen sizes.

  5. OrientationBuilder:

    • OrientationBuilder allows you to build different layouts based on the device's orientation (portrait or landscape).
  6. Responsive Packages:

    • Use packages like flutter_screenutil or responsive_builder to simplify the process of creating responsive UIs.

Example: Responsive UI with MediaQuery

Here's an example demonstrating how to create a responsive layout using MediaQuery:

import 'package:flutter/material.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: ResponsiveHomePage(),
    );
  }
}

class ResponsiveHomePage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    var screenSize = MediaQuery.of(context).size;

    return Scaffold(
      appBar: AppBar(title: Text('Responsive UI Example')),
      body: Center(
        child: Container(
          width: screenSize.width * 0.8,
          height: screenSize.height * 0.6,
          color: Colors.blue,
          child: Center(
            child: Text(
              'Screen Width: ${screenSize.width}\nScreen Height: ${screenSize.height}',
              style: TextStyle(color: Colors.white, fontSize: 24),
              textAlign: TextAlign.center,
            ),
          ),
        ),
      ),
    );
  }
}

Example: Using LayoutBuilder

Here's an example demonstrating how to use LayoutBuilder to create a responsive layout:

import 'package:flutter/material.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: ResponsiveHomePage(),
    );
  }
}

class ResponsiveHomePage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text('Responsive UI Example')),
      body: LayoutBuilder(
        builder: (context, constraints) {
          if (constraints.maxWidth > 600) {
            return _buildWideContainers();
          } else {
            return _buildNarrowContainers();
          }
        },
      ),
    );
  }

  Widget _buildWideContainers() {
    return Row(
      mainAxisAlignment: MainAxisAlignment.spaceEvenly,
      children: <Widget>[
        Container(width: 100, height: 100, color: Colors.red),
        Container(width: 100, height: 100, color: Colors.green),
        Container(width: 100, height: 100, color: Colors.blue),
      ],
    );
  }

  Widget _buildNarrowContainers() {
    return Column(
      mainAxisAlignment: MainAxisAlignment.spaceEvenly,
      children: <Widget>[
        Container(width: 100, height: 100, color: Colors.red),
        Container(width: 100, height: 100, color: Colors.green),
        Container(width: 100, height: 100, color: Colors.blue),
      ],
    );
  }
}

Example: Using OrientationBuilder

Here's an example demonstrating how to use OrientationBuilder to create a responsive layout:

import 'package:flutter/material.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: ResponsiveHomePage(),
    );
  }
}

class ResponsiveHomePage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text('Responsive UI Example')),
      body: OrientationBuilder(
        builder: (context, orientation) {
          if (orientation == Orientation.portrait) {
            return _buildPortraitLayout();
          } else {
            return _buildLandscapeLayout();
          }
        },
      ),
    );
  }

  Widget _buildPortraitLayout() {
    return Column(
      mainAxisAlignment: MainAxisAlignment.center,
      children: <Widget>[
        Container(width: 100, height: 100, color: Colors.red),
        Container(width: 100, height: 100, color: Colors.green),
        Container(width: 100, height: 100, color: Colors.blue),
      ],
    );
  }

  Widget _buildLandscapeLayout() {
    return Row(
      mainAxisAlignment: MainAxisAlignment.center,
      children: <Widget>[
        Container(width: 100, height: 100, color: Colors.red),
        Container(width: 100, height: 100, color: Colors.green),
        Container(width: 100, height: 100, color: Colors.blue),
      ],
    );
  }
}

Example: Using flutter_screenutil Package

Here's an example demonstrating how to use the flutter_screenutil package to create a responsive layout:

First, add flutter_screenutil to your pubspec.yaml file:

dependencies:
  flutter:
    sdk: flutter
  flutter_screenutil: ^5.0.0

Then, use it in your code:

import 'package:flutter/material.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return ScreenUtilInit(
      designSize: Size(375, 812),
      builder: () => MaterialApp(
        home: ResponsiveHomePage(),
      ),
    );
  }
}

class ResponsiveHomePage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text('Responsive UI Example')),
      body: Center(
        child: Container(
          width: 0.8.sw, // 80% of screen width
          height: 0.6.sh, // 60% of screen height
          color: Colors.blue,
          child: Center(
            child: Text(
              'Responsive Container',
              style: TextStyle(color: Colors.white, fontSize: 24.sp),
              textAlign: TextAlign.center,
            ),
          ),
        ),
      ),
    );
  }
}

Summary

Creating a responsive UI in Flutter involves using flexible widgets, MediaQuery, LayoutBuilder, OrientationBuilder, and other tools to adapt to different screen sizes and orientations. By leveraging these techniques and tools, you can ensure that your Flutter applications provide a consistent and pleasant user experience across all devices.

Did you find this article valuable?

Support Michael Piper by becoming a sponsor. Any amount is appreciated!