skip to Main Content

I’m trying to create a layout in Flutter where all the children of a GridView fit within its container without scrolling. Here’s my code

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

class GridViewExample extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: Container(
          width: double.infinity,
          height: 40.h,
          constraints: BoxConstraints(maxHeight: 40.h),
          decoration: const BoxDecoration(
            color: Colors.blue,
            borderRadius: BorderRadius.only(
              topLeft: Radius.circular(15),
              topRight: Radius.circular(15),
            ),
            boxShadow: [
              BoxShadow(
                color: Color.fromRGBO(91, 138, 82, 0.15),
                offset: Offset(4, 0),
                blurRadius: 24,
              ),
            ],
          ),
          child: GridView.builder(
            physics: const NeverScrollableScrollPhysics(),
            shrinkWrap: true,
            gridDelegate: const SliverGridDelegateWithFixedCrossAxisCount(
              crossAxisCount: 3,
              childAspectRatio: 1.0,
              mainAxisSpacing: 10.0,
              crossAxisSpacing: 10.0,
            ),
            itemCount: 12,
            itemBuilder: (context, index) {
              return Container(
                decoration: BoxDecoration(
                  border: Border.all(width: 3.0),
                ),
              );
            },
          ),
        ),
      ),
    );
  }
}

void main() => runApp(MaterialApp(
  home: GridViewExample(),
));

In the code above, I’m using a GridView.builder inside a Container with a fixed height. I want the GridView to display all its children (12 items in total) without enabling scrolling. However, the grid still tries to scroll, and the items are not fitting as expected within the height constraint of the Container.

I’ve set the physics to NeverScrollableScrollPhysics() and shrinkWrap to true, but it doesn’t seem to solve the problem. How can I make sure all the children of the GridView fit within the container without any scrolling?

2

Answers


  1. The GridView doesn’t care about the child sizes. You have to set the childAspectRatio properly in the gridDelegate. Or you can use Wrap instead of GridView and child sizes will matter.
    In all the way you have to know the size of the container and a LayoutBuilder can be good for that. (constraints.maxWidth and constraints.maxHeight help you to calculate the childAspectRatio)

    Login or Signup to reply.
  2. As jkirtyan, mentioned LayoutBuilder be great to achieve your requirements. Here is code:

              LayoutBuilder(
                builder: (context, constraints) {
                  double itemHeight = (constraints.maxHeight - 30) / 4; // 4 rows, subtract 30 to fit space between rows
                  double itemWidth = constraints.maxWidth / 3; // 3 columns
    
                  return GridView.builder(
                    physics: const NeverScrollableScrollPhysics(),
                    shrinkWrap: true,
                    gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
                      crossAxisCount: 3,
                      childAspectRatio: itemWidth / itemHeight,
                      mainAxisSpacing: 10.0,
                      crossAxisSpacing: 10.0,
                    ),
                    itemCount: 12,
                    itemBuilder: (context, index) {
                      return Container(
                        decoration: BoxDecoration(
                          border: Border.all(width: 3.0),
                        ),
                      );
                    },
                  );
                },
              )
    

    First, we calculate itemHeight and itemWidth – to determine height for each row (and for each item in row, since rowHeight == itemHeight) and width for each column (and for each item in column, since columnWidth == itemWidth).

    Then, we use these numbers to calculate childAspectRatio (as jkirtyan proposed). You can also tweak these numbers (I mean, calculation of itemHeight and itemWidth) to leave more free space around your figures.

    Result is on the screenshot.

    result of code execution

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search