Home > Back-end >  Flutter paginated data table column flex
Flutter paginated data table column flex

Time:06-15

How do I make the columns fill the space responsively? The default Table() has a columnWidths property to set a column to flex and it is responsive across devices:

     columnWidths: const <int, TableColumnWidth>{
        0: FlexColumnWidth(4),
        1: FlexColumnWidth(1),
      },

It's so simple but I can't figure out how to flex the column in PaginatedDataTable:

enter image description here

There is lots of empty space and the table looks very silly

Here is some of my code to recreate the issue:

class ResultsData extends DataTableSource {
  final List<Map<String, dynamic>> _data = [
    {'condition': "A1AT deficiency", 'risk': "High"},
    {'condition': "Type 2 diabetes", 'risk': "Medium"},
    {'condition': "Cystic fibrosis", 'risk': "Low"},
    {'condition': "Latex allergy", 'risk': "Low"},
    {'condition': "Tachycardia", 'risk': "Low"},
  ];

  @override
  bool get isRowCountApproximate => false;

  @override
  int get rowCount => _data.length;

  @override
  int get selectedRowCount => 0;

  @override
  DataRow getRow(int index) {
    return DataRow(
      cells: [
        DataCell(Text(_data[index]['condition'])),
        DataCell(Text(_data[index]['risk'])),
      ],
    );
  }
}

Widget resultTable(BuildContext context) {
  var data = ResultsData();

  return Expanded(
    child: Card(
      child: Column(
        children: [
          const ListTile(
            title: Text(
              'Your results',
              style: TextStyle(fontWeight: FontWeight.bold),
            ),
          ),
          Padding(
            padding: const EdgeInsets.all(5),
            child: PaginatedDataTable(
              showCheckboxColumn: false,
              rowsPerPage: 4,
              columns: <DataColumn>[
                DataColumn(
                  label: Flexible(
                    child: Text(
                      'Condition',
                      style: Theme.of(context).textTheme.titleSmall?.apply(
                        fontWeightDelta: 1,
                        color: Colors.black54,
                      ),
                    ),
                  ),
                ),
                DataColumn(
                  numeric: true,
                  label: Flexible(
                    child: Text(
                      'Risk',
                      style: Theme.of(context).textTheme.titleSmall?.apply(
                        fontWeightDelta: 1,
                        color: Colors.black54,
                      ),
                    ),
                  ),
                ),
              ],
              source: data,
            ),
          ),
        ],
      ),
    ),
  );
}

I just want it to fill the white space, preferibly with the first column 60% of the width, and the last column taking the remaining space

CodePudding user response:

Please add a wrapper container with width that of the device. Wrap the text with a centre widget and wrap the centre with an expanded widget. Please try this


const Color darkBlue = Color.fromARGB(255, 18, 32, 47);

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      theme: ThemeData.dark().copyWith(
        scaffoldBackgroundColor: darkBlue,
      ),
      debugShowCheckedModeBanner: false,
      home: Scaffold(
        body: Center(
          child: MyWidget(),
        ),
      ),
    );
  }
}

class MyWidget extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Container(
     width:MediaQuery.of(context).size.width,
      child: Padding(
              padding: const EdgeInsets.all(5),
              child: PaginatedDataTable(
              source: MyData(),
              header: const Text('My Products'),
              columns: const [
                DataColumn(label: Expanded(child: Center(child: Text('ID')))),
                DataColumn(label: Expanded(child: Center(child: Text('Name')))),
                DataColumn(label: Expanded(child: Center(child: Text('Price'))))
              ],
              columnSpacing: 100,
              horizontalMargin: 10,
              rowsPerPage: 8,
              showCheckboxColumn: false,
            ),
            ),
    );
  }
}
class MyData extends DataTableSource {
  // Generate some made-up data
  final List<Map<String, dynamic>> _data = List.generate(
      200,
      (index) => {
            "id": index,
            "title": "Item $index",
            "price": "10"
          });

  @override
  bool get isRowCountApproximate => false;
  @override
  int get rowCount => _data.length;
  @override
  int get selectedRowCount => 0;
  @override
  DataRow getRow(int index) {
    return DataRow(cells: [
      DataCell(Center(child: Text(_data[index]['id'].toString()))),
      DataCell(Center(child: Text(_data[index]["title"]))),
      DataCell(Center(child: Text(_data[index]["price"].toString()))),
    ]);
  }
}

preview

  • Related