Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to customize Material-ui Table Row and Columns (Sticky)

I have a unique situation in which I need not only the header but the first row and first three columns to persist when scrolling down and/or to the right due to an overflow of columns.

Material-UI Table allows for me to keep the header sticky when scrolling down without negatively affecting overflow, like in this example: https://codesandbox.io/s/209r3p0l3y

In my table the header does stick, but the first row must stick when scrolling down but not stick when scrolling left (the same behavior). This is to keep the overflow of values remaining consistent with the header labels. The first row (although not a header) will be compared to the rest of the rows of data when scrolling down and to the right. Also, this is the case for the first 3 columns. The other columns must remain matching with the header labels and first-row content, but the first 3 columns remain fixed to the left as this is done.

Is overlapping multiple MUI tables truly the best and/or only plausible solution? I cannot think of a less hacky solution and wonder if anyone has encountered this when limited to MUI Tables or developing unique table behavior.

like image 901
Franklinc Avatar asked Jun 27 '18 20:06

Franklinc


People also ask

Is material UI table responsive?

Material Table is not responsive.

What is sticky column?

Sticky columns enable you to display specific columns at all times while the user scrolls the Grid horizontally. This specific column will be scrollable as well, however, it will fix its position to the left/right when it reaches left/right Grid border.

How do you use MUI table?

Installing Material UI to your React app Firstly, create a new project using Create React App. Once the project setup is completed, navigate to the project's root folder. Finally, add the dependencies to use Material UI in your app. Note: On v5, Material-UI changed its name and is available in NPM under @mui/material.


1 Answers

You can make it without any library. All you you have to do is override it, and make it as you need.

I give you the example in this.

import React from "react";
import {
  makeStyles,
  TableContainer,
  TableBody,
  TableCell,
  TableHead,
  TableRow,
  Table,
  withStyles
} from "@material-ui/core";

const useStyles = makeStyles((theme) => ({
  root: {
    width: "100%",
    marginTop: theme.spacing(3)
  },
  head: {
    backgroundColor: "#fff",
    minWidth: "50px"
  },
  tableContainer: {
    maxHeight: "400px"
  },
  cell: {
    minWidth: "100px"
  }
}));

const StickyTableCell = withStyles((theme) => ({
  head: {
    backgroundColor: theme.palette.common.black,
    color: theme.palette.common.white,
    left: 0,
    position: "sticky",
    zIndex: theme.zIndex.appBar + 2
  },
  body: {
    backgroundColor: "#ddd",
    minWidth: "50px",
    left: 0,
    position: "sticky",
    zIndex: theme.zIndex.appBar + 1
  }
}))(TableCell);

const StyledTableCell = withStyles((theme) => ({
  head: {
    backgroundColor: theme.palette.common.black,
    color: theme.palette.common.white
  },
  body: {
    fontSize: 14
  }
}))(TableCell);

const StyledTableRow = withStyles((theme) => ({
  root: {
    "&:nth-of-type(odd)": {
      backgroundColor: theme.palette.action.hover
    }
  }
}))(TableRow);

const App = () => {
  let id = 0;
  function createData(name, calories, fat, carbs, protein) {
    id += 1;
    return { id, name, calories, fat, carbs, protein };
  }

  const data = [
    createData("Frozen yoghurt", 159, 6.0, 24, 4.0),
    createData("Ice cream sandwich", 237, 9.0, 37, 4.3),
    createData("Eclair", 262, 16.0, 24, 6.0),
    createData("Cupcake", 305, 3.7, 67, 4.3),
    createData("Gingerbread", 356, 16.0, 49, 3.9),
    createData("Frozen yoghurt", 159, 6.0, 24, 4.0),
    createData("Ice cream sandwich", 237, 9.0, 37, 4.3),
    createData("Eclair", 262, 16.0, 24, 6.0),
    createData("Cupcake", 305, 3.7, 67, 4.3),
    createData("Gingerbread", 356, 16.0, 49, 3.9),
    createData("Frozen yoghurt", 159, 6.0, 24, 4.0),
    createData("Ice cream sandwich", 237, 9.0, 37, 4.3),
    createData("Eclair", 262, 16.0, 24, 6.0),
    createData("Cupcake", 305, 3.7, 67, 4.3),
    createData("Gingerbread", 356, 16.0, 49, 3.9),
    createData("Frozen yoghurt", 159, 6.0, 24, 4.0),
    createData("Ice cream sandwich", 237, 9.0, 37, 4.3),
    createData("Eclair", 262, 16.0, 24, 6.0),
    createData("Cupcake", 305, 3.7, 67, 4.3),
    createData("Gingerbread", 356, 16.0, 49, 3.9)
  ];

  const classes = useStyles();

  return (
    <div>
      Sticky Header + Column
      <TableContainer className={classes.tableContainer}>
        <Table stickyHeader aria-label="sticky table">
          <TableHead>
            <TableRow>
              <StickyTableCell className={classes.head}>
                <StyledTableCell className={classes.head} numeric>
                  Dessert (100g serving)
                </StyledTableCell>
                <StyledTableCell className={classes.head} numeric>
                  Calories
                </StyledTableCell>
              </StickyTableCell>
              <StyledTableCell className={classes.head} numeric>
                Calories
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Fat (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Carbs (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
              <StyledTableCell className={classes.head} numeric>
                Protein (g)
              </StyledTableCell>
            </TableRow>
          </TableHead>
          <TableBody>
            {data.map((n) => {
              return (
                <StyledTableRow key={n.id}>
                  <StickyTableCell>
                    <StyledTableCell
                      numeric
                      align="right"
                      className={classes.cell}
                    >
                      {n.name}
                    </StyledTableCell>
                    <StyledTableCell
                      numeric
                      align="right"
                      className={classes.cell}
                    >
                      {n.calories}
                    </StyledTableCell>
                  </StickyTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.fat}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.carbs}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.protein}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.calories}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.fat}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.carbs}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.protein}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.calories}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.fat}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.carbs}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.protein}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.carbs}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.protein}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.calories}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.fat}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.carbs}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.protein}
                  </StyledTableCell>
                  <StyledTableCell
                    numeric
                    align="center"
                    className={classes.cell}
                  >
                    {n.protein}
                  </StyledTableCell>
                </StyledTableRow>
              );
            })}
          </TableBody>
        </Table>
      </TableContainer>
    </div>
  );
};

export default App;

this is codesandbox link: Codesanbox React + Material-UI Sticky Header and Column

like image 67
darkscripter Avatar answered Sep 19 '22 15:09

darkscripter