45

I have a stack widgets with two widgets inside. One of them draws the background, the other one draws on top of that. I want both widgets to have the same size.

I want the top widget, which is a column, to expand and fill the stack vertically to the size that is set by the background widget. I tried setting the MainAxis mainAxisSize: MainAxisSize.max but it didn't work.

How can I make it work?

Arash
  • 11,697
  • 14
  • 54
  • 81

5 Answers5

101

Use Positioned.fill

    Stack(
      children: [
        Positioned.fill(
          child: Column(
            children: [
              //...
            ],
          ),
        ),
        //...
      ],
    );

More info about Positioned in Flutter Widget of the Week

How does it work?

This is all about constraints. Constraints are min/max width/height values that are passed from the parent to its children. In the case of Stack. The constraints it passes to its children state that they can size themselves as small as they want, which in the case of some widgets means they will be their "natural" size. After being sized, Stack will place its children in the top left corner.
Positioned.fill gets the same constraints from Stack but passes different constraints to its child, stating the it (the child) must be of exact size (which meant to fill the Stack).

Positioned.fill() is the same as:

Positioned(
  top: 0,
  right: 0,
  left: 0,
  bottom:0,
  child: //...
)

For even more examples and info: How to fill a Stack widget and why? and Understanding constraints.

Alex.F
  • 5,648
  • 3
  • 39
  • 63
8

You can try wrapping the Column with a positioned widget. Set top to 0 and bottom to 0. This will make the column fill the stack vertically.

sample code:

Stack(
      children: <Widget>[
        // Background widget rep
        Container(
          color: Colors.pink,
        ),
        Positioned(
          top: 0,
          bottom: 0,
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: <Widget>[
              Text('madonna'),
              Text('flutter'),
            ],
          ),
        )
      ],
    )
nonybrighto
  • 8,752
  • 5
  • 41
  • 55
7

I think you could wrap you column in a container like this:

 Container(
   height: double.infinity,
   width: double.infinity,
   child: Column()
 ),
Alex Moran
  • 349
  • 3
  • 4
1

In my case, I thought that I needed to expand the container in the light blue color with an expanded widget inside the stack widget. Problems arose, especially since I was adding the stack widget in the column widget, and the way to make the container double.infinity dimensions I definitely had a problem with the vertical axis.

In the end, I managed to show it like this photo...

Column(
    children: [
      //filter
      Container(
        color: orange,
        height: 50,
        child: Row(
          mainAxisAlignment: MainAxisAlignment.spaceBetween,
          children: [
            Row(
              children: [
                Padding(
                  padding: const EdgeInsets.fromLTRB(20, 0, 20, 0),
                  child: Text(
                    'All',
                    style: getRegular(color: white.withOpacity(.6)),
                  ),
                ),
                Container(
                  color: white.withOpacity(.6),
                  width: 1,
                  height: 50,
                ),
                Padding(
                  padding: const EdgeInsets.fromLTRB(20, 0, 10, 0),
                  child: Text(
                    'Ready',
                    style: getRegular(color: white.withOpacity(.6)),
                  ),
                ),
                freeh(),
                Container(
                  color: white.withOpacity(.6),
                  width: 1,
                  height: 50,
                ),
              ],
            ),
            Row(
              children: [
                Icon(
                  filter,
                  color: white.withOpacity(.7),
                  size: 20,
                ),
                Text(
                  'FILTER',
                  style: getLight(
                    color: white.withOpacity(.7),
                  ),
                ),
                freeh(),
              ],
            ),
          ],
        ),
      ),
      Expanded(
        child: Stack(
          alignment: Alignment.topLeft,
          children: [
            Container(
              color: lightBlue, //here to use map>>>>
            ),
            Container(
              height: 35,
              width: 120,
              margin: const EdgeInsets.all(20),
              decoration: BoxDecoration(
                color: primary,
                borderRadius: BorderRadius.circular(20),
              ),
              child: Row(
                mainAxisAlignment: MainAxisAlignment.spaceEvenly,
                children: [
                  Icon(
                    FontAwesomeIcons.listUl,
                    color: white.withOpacity(.8),
                    size: 20,
                  ),
                  Text(
                    'List View',
                    style: getRegular(color: white.withOpacity(.8)),
                  )
                ],
              ),
            ),
          ],
        ),
      )
    ],
  ),

enter image description here

0

The accepted answer did not answer my issue completely. So, I put my code here in case you have a similar issue.

class NoContentView extends StatelessWidget {
  const NoContentView({Key? key, required this.message}) : super(key: key);

  final String message;

  @override
  Widget build(BuildContext context) {
    return Expanded(
      child: Stack(
        children: [
          Positioned.fill(
            child: FittedBox(
              child: const Image(image: AssetImage(AppImages.noReceiptsWeb), fit: BoxFit.fitWidth),
            ),
          ),
          MessageView(message: message),
        ],
      ),
    );
  }
}
Hesam
  • 52,260
  • 74
  • 224
  • 365