Skip to main content

Building Layouts with Flex Widgets

1. Using Row Widget

Property Values Description
children List<Widget> Required. The list of child widgets to display in the row.
mainAxisAlignment MainAxisAlignment How the children should be placed along the main axis (horizontal). Default is MainAxisAlignment.start.
mainAxisSize MainAxisSize How much space the row should take along the main axis. Default is MainAxisSize.max.
crossAxisAlignment CrossAxisAlignment How the children should be aligned along the cross axis (vertical). Default is CrossAxisAlignment.center.
textDirection TextDirection The direction of the row. Default is TextDirection.ltr.
verticalDirection VerticalDirection The direction in which the row is laid out vertically. Default is VerticalDirection.down.

Example: Basic Row with Text Widgets

Row(
  children: [
    Text("Hello"),
    Text("World"),
  ],
)

Example: Row with MainAxisAlignment

Row(
  mainAxisAlignment: MainAxisAlignment.spaceEvenly,
  children: [
    Text("Left"),
    Text("Center"),
    Text("Right"),
  ],
)

Example: Row with CrossAxisAlignment

Row(
  crossAxisAlignment: CrossAxisAlignment.end,
  children: [
    Text("Tall"),
    Text("Short"),
  ],
)

2. Using Column Widget

Property Values Description
children List<Widget> Required list of child widgets to display vertically
mainAxisAlignment MainAxisAlignment.start (default)
MainAxisAlignment.center
MainAxisAlignment.end
MainAxisAlignment.spaceBetween
MainAxisAlignment.spaceAround
Alignment of children along the main axis (vertical in Column)
crossAxisAlignment CrossAxisAlignment.center (default)
CrossAxisAlignment.start
CrossAxisAlignment.end
Alignment of children along the cross axis (horizontal in Column)
mainAxisSize MainAxisSize.max (default)
MainAxisSize.min
Determines how much space the Column should take up in the main axis

Example: Basic Column with MainAxisAlignment

Column(
  mainAxisAlignment: MainAxisAlignment.spaceEvenly,
  children: [
    Container(
      height: 50,
      width: 100,
      color: Colors.blue,
    ),
    Container(
      height: 50,
      width: 100,
      color: Colors.red,
    ),
    Container(
      height: 50,
      width: 100,
      color: Colors.green,
    ),
  ],
)

Example: Column with CrossAxisAlignment.end

Column(
  crossAxisAlignment: CrossAxisAlignment.end,
  children: [
    Text('Left aligned text'),
    Text('Right aligned text'),
  ],
)

3. Using Flexible Widget

Property Values Description
flex int Defines how much space the Flexible widget should take up relative to other Flexible widgets in the same parent.
fit FlexFit.tight or FlexFit.loose Determines how the Flexible widget should size itself within its parent's layout constraints.

Example: Basic usage of Flexible widget

import 'package:flutter/material.dart';

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(title: Text("Flexible Example")),
        body: Row(
          children: [
            Flexible(
              flex: 1,
              child: Container(
                color: Colors.blue,
                height: 100,
                child: Center(child: Text("Flexible 1")),
              ),
            ),
            Flexible(
              flex: 2,
              child: Container(
                color: Colors.red,
                height: 100,
                child: Center(child: Text("Flexible 2")),
              ),
            ),
          ],
        ),
      ),
    );
  }
}
Note: The flex property defines the ratio of space distribution among Flexible widgets. In this example, the second Flexible widget takes twice as much space as the first one.

4. Using Expanded Widget

Property Values Description
flex 1 How much space the widget should take up relative to other Expanded widgets in the same parent
key Key? Unique identifier for the widget

Example: Basic Expanded Usage

import 'package:flutter/material.dart';

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(title: Text("Expanded Example")),
        body: Row(
          children: [
            Container(
              color: Colors.red,
              width: 100,
            ),
            Expanded(
              child: Container(
                color: Colors.blue,
                height: 100,
              ),
            ),
          ],
        ),
      ),
    );
  }
}

Example: Multiple Expanded Widgets

import 'package:flutter/material.dart';

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(title: Text("Multiple Expanded")),
        body: Row(
          children: [
            Container(
              color: Colors.red,
              width: 50,
            ),
            Expanded(
              flex: 2,
              child: Container(
                color: Colors.green,
                height: 100,
              ),
            ),
            Expanded(
              flex: 1,
              child: Container(
                color: Colors.yellow,
                height: 100,
              ),
            ),
          ],
        ),
      ),
    );
  }
}

5. Using Spacer Widget

Property Values Description
flex int Controls how much space the Spacer should take up relative to other Spacers in the same flex container. Defaults to 1.
spacing double Defines the amount of space to insert between the widget and its siblings. Defaults to 0.

Example: Basic Spacer Usage in a Row

Widget build(BuildContext context) {
  return Row(
    children: [
      Container(
        width: 50,
        height: 50,
        color: Colors.blue,
      ),
      Spacer(), // Expands to fill available space
      Container(
        width: 50,
        height: 50,
        color: Colors.red,
      ),
    ],
  );
}

Example: Multiple Spacers in a Column

Widget build(BuildContext context) {
  return Column(
    children: [
      Container(
        width: 100,
        height: 30,
        color: Colors.green,
      ),
      Spacer(flex: 2), // Takes up twice the space of other spacers
      Container(
        width: 100,
        height: 30,
        color: Colors.yellow,
      ),
      Spacer(flex: 1), // Takes up one unit of space
      Container(
        width: 100,
        height: 30,
        color: Colors.purple,
      ),
    ],
  );
}
Note: The Spacer widget is a convenient way to distribute space in a flex container. It's particularly useful when you want to push content to one side or align items in a specific way.

6. Understanding MainAxisAlignment Options

Option Description Usage
MainAxisAlignment.start Aligns children to the start of the main axis (left in horizontal, top in vertical). mainAxisAlignment: MainAxisAlignment.start
MainAxisAlignment.end Aligns children to the end of the main axis (right in horizontal, bottom in vertical). mainAxisAlignment: MainAxisAlignment.end
MainAxisAlignment.center Centers children along the main axis. mainAxisAlignment: MainAxisAlignment.center
MainAxisAlignment.spaceBetween Distributes children with equal spacing between them, first child at the start, last at the end. mainAxisAlignment: MainAxisAlignment.spaceBetween
MainAxisAlignment.spaceAround Distributes children with equal space around each child, first and last child spaced from edges. mainAxisAlignment: MainAxisAlignment.spaceAround
MainAxisAlignment.spaceEvenly Distributes children with equal space between and around them. mainAxisAlignment: MainAxisAlignment.spaceEvenly

Example: MainAxisAlignment.center

Row(
  mainAxisAlignment: MainAxisAlignment.center,
  children: [
    Text('Left'),
    Text('Center'),
    Text('Right'),
  ],
)

Example: MainAxisAlignment.spaceBetween

Row(
  mainAxisAlignment: MainAxisAlignment.spaceBetween,
  children: [
    Text('Start'),
    Text('Middle'),
    Text('End'),
  ],
)

7. Understanding CrossAxisAlignment Options

Option Description Usage
CrossAxisAlignment.start Aligns children to the start of the cross axis (top for vertical, left for horizontal). crossAxisAlignment: CrossAxisAlignment.start
CrossAxisAlignment.end Aligns children to the end of the cross axis (bottom for vertical, right for horizontal). crossAxisAlignment: CrossAxisAlignment.end
CrossAxisAlignment.center Aligns children to the center of the cross axis. crossAxisAlignment: CrossAxisAlignment.center
CrossAxisAlignment.stretch Stretches children to fill the cross axis (default behavior for Column/Row). crossAxisAlignment: CrossAxisAlignment.stretch
CrossAxisAlignment.baseline Aligns children based on their text baseline (requires textBaseline to be set). crossAxisAlignment: CrossAxisAlignment.baseline

Example: CrossAxisAlignment.center

Column(
  crossAxisAlignment: CrossAxisAlignment.center,
  children: [
    Text('Hello'),
    Text('World'),
  ],
)

Example: CrossAxisAlignment.stretch

Row(
  crossAxisAlignment: CrossAxisAlignment.stretch,
  children: [
    Container(width: 50, color: Colors.red),
    Container(width: 100, color: Colors.blue),
  ],
)

8. Using MainAxisSize

Property Values Description
mainAxisSize MainAxisSize.min, MainAxisSize.max Defines how much space the flex widget should take along the main axis.

Example: Setting MainAxisSize to Max

Column(
  mainAxisSize: MainAxisSize.max,
  children: [
    Text('Hello'),
    Text('World'),
  ],
)

Example: Setting MainAxisSize to Min

Row(
  mainAxisSize: MainAxisSize.min,
  children: [
    Text('Hello'),
    Text('World'),
  ],
)

9. Using TextDirection and VerticalDirection

Property Values Description
textDirection TextDirection.ltr, TextDirection.rtl Defines the text direction for layout and rendering. NEW in Flutter 3.0+
verticalDirection VerticalDirection.down, VerticalDirection.up Controls the direction of children in a vertical layout. NEW in Flutter 3.0+

Example: Using TextDirection in a Row

Row(
  textDirection: TextDirection.rtl,
  children: [
    Text('Hello'),
    Text('World'),
  ],
)

Example: Using VerticalDirection in a Column

Column(
  verticalDirection: VerticalDirection.up,
  children: [
    Text('Child 1'),
    Text('Child 2'),
  ],
)
Note: TextDirection.rtl reverses the order of children in horizontal layouts like Row. VerticalDirection.up changes the order of children in vertical layouts like Column.

10. Nesting Row and Column Widgets

Flutter's layout system allows nesting Row and Column widgets to create complex UIs. This nesting enables flexible, responsive designs by combining horizontal and vertical arrangements.

Widget Description Use Case
Row Arranges children horizontally in a linear fashion. Horizontal alignment of buttons, icons, or text elements.
Column Arranges children vertically in a linear fashion. Vertical stacking of widgets like lists or form elements.

Example: Basic Nesting

Container(
  child: Column(
    children: [
      Row(
        children: [
          Icon(Icons.star),
          Text('Starred Item'),
        ],
      ),
      Text('Additional content below'),
    ],
  ),
)

Example: Responsive Nested Layout

Container(
  child: Column(
    children: [
      Row(
        mainAxisAlignment: MainAxisAlignment.spaceBetween,
        children: [
          Text('Header'),
          Icon(Icons.menu),
        ],
      ),
      Expanded(
        child: Column(
          children: [
            Text('Content Area'),
            Row(
              mainAxisAlignment: MainAxisAlignment.center,
              children: [
                Text('Left'),
                Text('Right'),
              ],
            ),
          ],
        ),
      ),
    ],
  ),
)
Note: Use Expanded or Flexible inside nested layouts to control how space is distributed among children.

Was this article helpful?