Data Grid

A data grid is a component designed to display large volumes in a structured and organized manner. It structures data into rows and columns, making it easy for users to visualize, analyze, and interact with the information. The data grid also improves user experience by providing features like sorting, filtering, and editing.

Props

NameTypeDescriptionDefault
Required
columns

GridColumn[]being GridColumn:

{ key: string; label: string; resizable?: boolean; sortable?: boolean; sortFn?: (a: ReactNode, b: ReactNode) => number; draggable?: boolean; textEditable?: boolean; summaryKey?: string; alignment?: "left" | "right" | "center"; }
Each GridColumn object has the following properties:
  • key: Key that will be rendered from each row in rows.
  • label: Label that will be used for the column header.
  • resizable: Whether the column is resizable or not.
  • sortable: Whether the column is sortable or not.
  • sortFn: Custom function with the criteria for the column sorting.
  • draggable: Whether the column can be dragged or not to another position or not.
  • textEditable: Whether the column cells are editable or not.
  • summaryKey: Value that will be rendered from the summaryRow
  • alignment: Sets the alignment inside the cells.
-
Required
rows
GridRow[] | HierarchyGridRow[] | ExpandableGridRow[]

Each one of them being in order:

{ [key: string]: React.ReactNode | undefined; }

GridRow & { childRows?: HierarchyGridRow[] | GridRow[]; }

GridRow & { expandedContent?: React.ReactNode; expandedContentHeight?: number; }

List of rows that will be rendered in each cell based on the key in each column.-
expandablebooleanWhether the rows can expand or not.-
summaryRowGridRowExtra row that will be always visible.-
selectablebooleanWhether the rows are selectable or not.-
selectedRowsSet<string | number>Set of selected rows. This prop is mandatory if selectable is set to true. The uniqueRowId key will be used to identify the each row.-
onSelectRows(selectedRows: Set<number | string>) => voidFunction called whenever the selected values changes. This prop is mandatory if selectable is set to true.The uniqueRowId key will be used to identify the rows.-
uniqueRowIdstringThis prop indicates the unique key that can be used to identify each row. The value of that key can be either a number or a string. This prop is mandatory if selectable is set to true, expandable is set to true or rows is of type HierarchyGridRow[].-
onGridRowsChange(rows: GridRow[] | HierarchyGridRow[] | ExpandableGridRow[]) => voidFunction called whenever a cell is edited.-
onSort(sortColumn?: { columnKey: string, direction: 'ASC' | 'DESC' }) => voidFunction called whenever a column is sorted. Receives the sorted column and direction, or `undefined` if no sorting is applied.-
onPageChange(page: number) => voidFunction called whenever the current page is changed.-
showPaginatorbooleanIf true, paginator will be displayed.false
totalItemsnumberNumber of total items.-
showGoToPagebooleanIf true, a select component for navigation between pages will be displayed.true
itemsPerPagenumberNumber of items per page.5
itemsPerPageOptionsnumber[]An array of numbers representing the items per page options.-
itemsPerPageFunction(value: number) => voidThis function will be called when the user selects an item per page option. The value selected will be passed as a parameter.-

DxcDataGrid.ActionsCell

A compound component aimed to be used inside the table to display up to three actions.

Props

NameTypeDescriptionDefault
Required
actions
{ icon: string | SVG; title: string; onClick: () => void; disabled?: boolean; tabIndex?: number; }[] | { title: string; onClick: (value?: string) => void; disabled?: boolean; tabIndex?: number; options: Option[]; }[]

It represents a list of interactive elements that will work as buttons or as a dropdown. Those with an icon from Material Symbols or a SVG are treated as buttons. If any element lacks an icon and includes options, it is interpreted as a dropdown. Only the first action with options will be displayed and only up to 3 actions. In the case of the dropdown the click function will pass the value assigned to the option, click here for more details.

-

Examples

Basic usage

() => {
  const columns = [
    {
      key: "id",
      label: "ID",
      resizable: true,
      draggable: true,
    },
    {
      key: "complete",
      label: "% Complete",
      resizable: true,
      draggable: true,
      alignment: "right",
    },
  ];
  
  const rows = [
    {
      id: "Row 1",
      complete: 46, 
    },
    {
      id: "Row 2",
      complete: 51,
    },
    {
      id: "Row 3",
      complete: 40,
    },
    {
      id: "Row 4",
      complete: 10,
    },
  ];
  
  return (
    <DxcInset space="2rem">
      <DxcDataGrid columns={columns} rows={rows} uniqueRowId="id" />
    </DxcInset>
  );
}

Actions cell

() => {
const actions = [
    {
      icon: "delete",
      title: "Delete",
      onClick: () => {},
    },
    {
      title: "edit",
      onClick: (value) => {},
      options:[
        {
          value: "1",
          label: "Edit",
        },
        {
          value: "2",
          label: "Mark as selected",
        },
      ]
    },
  ];
  const columns = [
    {
      key: "id",
      label: "ID",
      resizable: true,
      draggable: true,
    },
    {
      key: "complete",
      label: "% Complete",
      resizable: true,
      draggable: true,
      alignment: "right",
    },
    {
        key: "actions",
        label: "Actions",
        alignment: "center",
    },
  ];
  
  const rows = [
    {
      id: "Row 1",
      complete: 46,
      actions: <DxcDataGrid.ActionsCell actions={actions} />,
    },
    {
      id: "Row 2",
      complete: 51,
      actions: <DxcDataGrid.ActionsCell actions={actions} />,
    },
    {
      id: "Row 3",
      complete: 40,
      actions: <DxcDataGrid.ActionsCell actions={actions} />,
    },
    {
      id: "Row 4",
      complete: 10,
      actions: <DxcDataGrid.ActionsCell actions={actions} />,
    },
  ];
  
  return (
    <DxcInset space="2rem">
      <DxcDataGrid columns={columns} rows={rows} uniqueRowId="id" />
    </DxcInset>
  );
}

Selectable data grid

() => {
  const columns = [
    {
      key: "id",
      label: "ID",
      resizable: true,
      draggable: true,
    },
    {
      key: "complete",
      label: "% Complete",
      resizable: true,
      draggable: true,
      alignment: "right",
    },
  ];
  
  const rows = [
    {
      id: "Row 1",
      complete: 46, 
    },
    {
      id: "Row 2",
      complete: 51,
    },
    {
      id: "Row 3",
      complete: 40,
    },
    {
      id: "Row 4",
      complete: 10,
    },
  ];
  
  const [selectedRows, setSelectedRows] = useState(new Set());
  return (
    <DxcInset space="2rem">
      <DxcDataGrid
          columns={columns}
          rows={rows}
          uniqueRowId="id"
          selectable
          selectedRows={selectedRows}
          onSelectRows={setSelectedRows}
        />
    </DxcInset>
  );
}

Expandable data grid

() => {
  const columns = [
    {
      key: "id",
      label: "ID",
      resizable: true,
      draggable: true,
    },
    {
      key: "complete",
      label: "% Complete",
      resizable: true,
      draggable: true,
      alignment: "right",
    },
  ];
  
  const rows = [
    {
      id: "Row 1",
      complete: 46,
      expandedContent: "Expanded content"
    },
    {
      id: "Row 2",
      complete: 51,
      expandedContent: "Expanded content",
      expandedContentHeight: 100
    },
    {
      id: "Row 3",
      complete: 40,
    },
    {
      id: "Row 4",
      complete: 10,
    },
  ];
  
  return (
    <DxcInset space="2rem">
      <DxcDataGrid columns={columns} rows={rows} expandable uniqueRowId="id" />
    </DxcInset>
  );
}

Hierarchical data grid

() => {
  const columns = [
    {
      key: "name",
      label: "Label",
      summaryKey: "label"
    },
    {
      key: "value",
      label: "Value",
      alignment: "right",
      summaryKey: "total"
    },
  ];
  
  const rows = [
    {
        name: "Root Node 1",
        value: "1",
        id: "a",
        childRows: [
            {
                name: "Child Node 1.1",
                value: "1.1",
                id: "aa",
                childRows: [
                {
                    name: "Grandchild Node 1.1.1",
                    value: "1.1.1",
                    id: "aaa",
                },
                {
                    name: "Grandchild Node 1.1.2",
                    value: "1.1.2",
                    id: "aab",
                },
                ],
            },
            {
                name: "Child Node 1.2",
                value: "1.2",
                id: "ab",
            },  
        ],
    },
    {
        name: "Root Node 2",
        value: "2",
        id: "b",
        childRows: [
            {
                name: "Child Node 2.1",
                value: "2.1",
                id: "ba",
                childRows: [
                {
                    name: "Grandchild Node 2.1.1",
                    value: "2.1.1",
                    id: "baa",
                },
                ],
            },
            {
                name: "Child Node 2.2",
                value: "2.2",
                id: "bb",
            },
            {
                name: "Child Node 2.3",
                value: "2.3",
                id: "bc",
            },
        ],
    },
  ];

  const summaryRow = { label: "Total", total: 100, id: "summary" }

  return (
    <DxcInset space="2rem">
      <DxcDataGrid columns={columns} rows={rows} summaryRow={summaryRow} uniqueRowId="id" />
    </DxcInset>
  );
}

Hierarchical and selectable data grid

() => {
  const columns = [
    {
      key: "name",
      label: "Label",
      summaryKey: "label"
    },
    {
      key: "value",
      label: "Value",
      alignment: "right",
      summaryKey: "total"
    },
  ];
  
  const rows = [
    {
        name: "Root Node 1",
        value: "1",
        id: "a",
        childRows: [
            {
                name: "Child Node 1.1",
                value: "1.1",
                id: "aa",
                childRows: [
                {
                    name: "Grandchild Node 1.1.1",
                    value: "1.1.1",
                    id: "aaa",
                },
                {
                    name: "Grandchild Node 1.1.2",
                    value: "1.1.2",
                    id: "aab",
                },
                ],
            },
            {
                name: "Child Node 1.2",
                value: "1.2",
                id: "ab",
            },  
        ],
    },
    {
        name: "Root Node 2",
        value: "2",
        id: "b",
        childRows: [
            {
                name: "Child Node 2.1",
                value: "2.1",
                id: "ba",
                childRows: [
                {
                    name: "Grandchild Node 2.1.1",
                    value: "2.1.1",
                    id: "baa",
                },
                ],
            },
            {
                name: "Child Node 2.2",
                value: "2.2",
                id: "bb",
            },
            {
                name: "Child Node 2.3",
                value: "2.3",
                id: "bc",
            },
        ],
    },
  ];

  const [selectedRows, setSelectedRows] = useState(new Set());
  return (
    <DxcInset space="2rem">
      <DxcDataGrid
          columns={columns}
          rows={rows}
          uniqueRowId="id"
          selectable
          selectedRows={selectedRows}
          onSelectRows={setSelectedRows}
        />
    </DxcInset>
  );
}

Paginator

() => {
  const columns = [
    {
      key: "id",
      label: "ID",
      resizable: true,
      draggable: true,
    },
    {
      key: "complete",
      label: "% Complete",
      resizable: true,
      draggable: true,
      alignment: "right",
    },
  ];
  
  const rows = [
    {
      id: "Row 1",
      complete: 46, 
    },
    {
      id: "Row 2",
      complete: 51,
    },
    {
      id: "Row 3",
      complete: 40,
    },
    {
      id: "Row 4",
      complete: 10,
    },
  ];
  
  return (
    <DxcInset space="2rem">
      <DxcDataGrid columns={columns} rows={rows} uniqueRowId="id" showPaginator itemsPerPage={2} />
    </DxcInset>
  );
}

Custom sorting

() => {
  const columns = [
    {
      key: "id",
      label: "ID",
      resizable: true,
      draggable: true,
      sortable: true,
    },
    {
      key: "complete",
      label: "% Complete",
      resizable: true,
      draggable: true,
      sortable: true,
      alignment: "right",
    },
  ];
  
  const rows = [
    {
      id: "Row 1",
      complete: 46, 
    },
    {
      id: "Row 2",
      complete: 51,
    },
    {
      id: "Row 3",
      complete: 40,
    },
    {
      id: "Row 4",
      complete: 10,
    },
  ];

  
  const [itemsPerPage, setItemsPerPage] = useState(2);
  const [rowsControlled, setRowsControlled] = useState(rows.slice(0, itemsPerPage));
  const [page, setPage] = useState(0);

  return (
    <DxcInset space="2rem">
      <DxcDataGrid
          columns={columns}
          rows={rowsControlled}
          uniqueRowId="id"
          onSort={(sortColumn) => {
            if (sortColumn) {
              const { columnKey, direction } = sortColumn;
              console.log("Sorting the column " + columnKey + " by " + direction);
              setRowsControlled((currentRows) => {
                return currentRows.sort((a, b) => {
                  if (direction === "ASC") {
                    return a[columnKey] < b[columnKey] ? -1 : a[columnKey] > b[columnKey] ? 1 : 0;
                  } else {
                    return a[columnKey] < b[columnKey] ? 1 : a[columnKey] > b[columnKey] ? -1 : 0;
                  }
                });
              });
            } else {
              console.log("Removed sorting criteria")
              setRowsControlled(rows.slice(page * itemsPerPage, page * itemsPerPage + itemsPerPage));
            }
          }}
          onPageChange={(page) => {
            const internalPage = page - 1;
            setPage(internalPage);
            setRowsControlled(rows.slice(internalPage * itemsPerPage, internalPage * itemsPerPage + itemsPerPage));
          }}
          showPaginator
          itemsPerPage={itemsPerPage}
          itemsPerPageOptions={[2, 4]}
          itemsPerPageFunction={(n) => 
            {
              setItemsPerPage(n);
              setRowsControlled(rows.slice(0, n));
            }
          }
          totalItems={rows.length}
        />
    </DxcInset>
  );
}