Search code examples
flutterdartsyncfusion

Column Resizing doesn't work in Syncfusion Flutter DataGrid?


I want to implement column resizing behavior using Flutter, and I am using the package syncfusion_flutter_datagrid: ^21.1.35, and my flutter version is 3.7.7, and dart version 2.19.4, and here are the full codes:

import 'package:flutter/material.dart';
import 'package:syncfusion_flutter_datagrid/datagrid.dart';

class TestFile extends StatefulWidget {
  @override
  _HomePageState createState() => _HomePageState();
}

class _HomePageState extends State<TestFile> {
  final List<Data> _data = [
    Data('John', 'Doe', 30),
    Data('Jane', 'Doe', 25),
    Data('Bob', 'Smith', 40),
    Data('Alice', 'Johnson', 35),
  ];

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: const Text('SfDataGrid Column Resizing Example')),
      body: SfDataGrid(
        source: _DataSource(data: _data),
        columnWidthMode: ColumnWidthMode.fill,
        allowColumnsResizing: true,
        columnResizeMode: ColumnResizeMode.onResize,
        columns: <GridColumn>[
          GridColumn(columnName: 'firstName', label: const Text('First Name')),
          GridColumn(columnName: 'lastName', label: const Text('Last Name')),
          GridColumn(columnName: 'age', label: const Text('Age')),
        ],
      ),
    );
  }
}

class _DataSource extends DataGridSource {
  final List<Data> data;

  _DataSource({required this.data});

  @override
  List<DataGridRow> get rows =>
      data.map((d) => DataGridRow(cells: [
        DataGridCell<String>(columnName: 'firstName', value: d.firstName),
        DataGridCell<String>(columnName: 'lastName', value: d.lastName),
        DataGridCell<int>(columnName: 'age', value: d.age),
      ])).toList();

  @override
  DataGridRowAdapter buildRow(DataGridRow row) {
    return DataGridRowAdapter(
      cells: row.getCells().map<Widget>((dataCell) {
        return Container(
          alignment: Alignment.center,
          padding: const EdgeInsets.all(8),
          child: Text(dataCell.value.toString()),
        );
      }).toList(),
    );
  }
}

class Data {
  final String firstName;
  final String lastName;
  final int age;

  Data(this.firstName, this.lastName, this.age);
}

I want to implement this feature just on Flutter web. I am using Chrome (Version 107.0.5304.110 (Official Build) (64-bit)) to run this project and also my OS is Ubuntu version 22.

enter image description here


Solution

  • You need to add few things as below:

    First, define column widths,

     late Map<String, double> columnWidths = {
    'name': double.nan,
    'lastname': double.nan,
    'age': double.nan
     };
    

    Second

    add callback for onColumnResizeUpdate and set columnResizeMode: ColumnResizeMode.onResizeEnd,

    onColumnResizeUpdate: (ColumnResizeUpdateDetails details) {
          setState(() {
            columnWidths[details.column.columnName] = details.width;
          });
          return true;
        },
    
        columnResizeMode: ColumnResizeMode.onResizeEnd,
    

    Third

    Add columnName to each GridColumn, the name should be the same you added in columnWidths Map

     GridColumn(
              width: columnWidths['name']!,
              columnName: 'name',
              label: const Text('First Name')),
    

    The full code here:

    import 'package:flutter/material.dart';
    import 'package:syncfusion_flutter_datagrid/datagrid.dart';
    
    class TestFile extends StatefulWidget {
      @override
      _HomePageState createState() => _HomePageState();
    }
    
    class _HomePageState extends State<TestFile> {
      final List<Data> _data = [
        Data('John Carter n Others', 'Doe', 30),
        Data('Jane', 'Doe', 25),
        Data('Bob', 'Smith', 40),
        Data('Alice', 'Johnson', 35),
      ];
    
      late Map<String, double> columnWidths = {
        'name': double.nan,
        'lastname': double.nan,
        'age': double.nan
      };
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(title: const Text('SfDataGrid Column Resizing Example')),
          body: SfDataGrid(
            source: _DataSource(data: _data),
            allowColumnsResizing: true,
            onColumnResizeUpdate: (ColumnResizeUpdateDetails details) {
              setState(() {
                columnWidths[details.column.columnName] = details.width;
              });
              return true;
            },
            columnResizeMode: ColumnResizeMode.onResizeEnd,
            columns: <GridColumn>[
              GridColumn(
                  width: columnWidths['name']!,
                  columnName: 'name',
                  label: const Text('First Name')),
              GridColumn(
                  width: columnWidths['lastname']!,
                  columnName: 'lastname',
                  label: const Text('Last Name')),
              GridColumn(
                  width: columnWidths['age']!,
                  columnName: 'age',
                  label: const Text('Age')),
            ],
          ),
        );
      }
    }
    
    class _DataSource extends DataGridSource {
      final List<Data> data;
    
      _DataSource({required this.data});
    
      @override
      List<DataGridRow> get rows => data
          .map((d) => DataGridRow(cells: [
                DataGridCell<String>(columnName: 'firstName', value: d.firstName),
                DataGridCell<String>(columnName: 'lastName', value: d.lastName),
                DataGridCell<int>(columnName: 'age', value: d.age),
              ]))
          .toList();
    
      @override
      DataGridRowAdapter buildRow(DataGridRow row) {
        return DataGridRowAdapter(
          cells: row.getCells().map<Widget>((dataCell) {
            return Container(
              alignment: Alignment.center,
              padding: const EdgeInsets.all(8),
              child: Text(dataCell.value.toString()),
            );
          }).toList(),
        );
      }
    }
    
    class Data {
      final String firstName;
      final String lastName;
      final int age;
    
      Data(this.firstName, this.lastName, this.age);
    }
    

    NOTE: The appearance of the column resizing indicator depends on the platform being used. On web and desktop platforms, the indicator becomes visible when the user hovers over the right end of the column and drags it. On mobile platforms, the indicator appears when the user long-presses the corresponding column header.