Tengo una tabla en la que estoy tratando de obtener encabezados fijos, siguiendo este artículo . Excepto que mi estilo de tabla tiene los encabezados con un borde en la parte superior e inferior.
La parte que no entiendo es que los bordes superior/inferior aplicados al th se desplazan con el resto de la tabla en lugar de quedarse con las celdas de encabezado "atascadas". ¿Hay algo que se pueda hacer al respecto?
La muestra de trabajo se puede encontrar aquí: https://codepen.io/smlombardi/pen/MNKqQY?editors=1100#0
let string = '' console.log("oj") for(let i=0; i<100; i++) { string += ` <tr> <td>Malcolm Reynolds</td> <td>Captain</td> <td>9035749867</td> <td>mreynolds</td> </tr> ` } document.getElementsByTagName('tbody')[0].innerHTML += string .table-sticky-container { height: 200px; overflow-y: scroll; border-top: 1px solid green; border-bottom: 1px solid green; } .table-sticky { th { position: sticky; top: 0; z-index: 2; border-top: 1px solid red !important; border-bottom: 2px solid red !important; } } <div class="table-sticky-container"> <table class="table table-sticky"> <thead class="thead-light"> <tr> <th scope="col">Name</th> <th scope="col">Title</th> <th scope="col">ID</th> <th scope="col">Username</th> </tr> </thead> <tbody> <tr> <td>Malcolm Reynolds</td> <td>Captain</td> <td>9035749867</td> <td>mreynolds</td> </tr> </tbody> </table> </div>Puedes añadir
.table { border-collapse: separate; }Pero desafortunadamente se ve mal, una mejor solución será agregar una solución usando un pseudo-elemento.
th:after, th:before { content: ''; position: absolute; left: 0; width: 100%; } th:before { top: -1px; border-top: 1px solid red; } th:after { bottom: -1px; border-bottom: 2px solid red; } .table-sticky-container { height: 200px; overflow-y: scroll; border-top: 1px solid green; border-bottom: 1px solid green; } .table-sticky th { position: -webkit-sticky; position: sticky; top: 0; z-index: 2; } th:after, th:before { content: ''; position: absolute; left: 0; width: 100%; } th:before { top: -1px; border-top: 1px solid red; } th:after { bottom: -1px; border-bottom: 2px solid red; } <link rel='stylesheet' href='https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/4.1.3/css/bootstrap.min.css'> <div class="table-sticky-container"> <table class="table table-sticky"> <thead class="thead-light"> <tr> <th scope="col">Name</th> <th scope="col">Title</th> <th scope="col">ID</th> <th scope="col">Username</th> </tr> </thead> <tbody> <tr> <td>Malcolm Reynolds</td> <td>Captain</td> <td>9035749867</td> <td>mreynolds</td> </tr> <tr> <td>Zoe Washburne</td> <td>First Officer</td> <td>8908980980</td> <td>zwashburne</td> </tr> <tr> <td>Kaylee Frye</td> <td>Engineer</td> <td>6678687678</td> <td>kfrye</td> </tr> <tr> <td>Malcolm Reynolds</td> <td>Captain</td> <td>9035749867</td> <td>mreynolds</td> </tr> <tr> <td>Zoe Washburne</td> <td>First Officer</td> <td>8908980980</td> <td>zwashburne</td> </tr> <tr> <td>Kaylee Frye</td> <td>Engineer</td> <td>6678687678</td> <td>kfrye</td> </tr> </tbody> </table> </div>la segunda solucion
.table { border-collapse: collapse; } .table-sticky thead th { position: -webkit-sticky; position: sticky; top: 0; z-index: 2; box-shadow: inset 0 1px 0 red, inset 0 -2px 0 red; }Otra solución funcional (probada en Chrome y FF más reciente): envuelva el contenido de th/td con divs y use esos bordes de divs en lugar de los bordes de las celdas.
<div class="wrapper"> <table> <thead> <tr> <th> <div class="cell">head1</div> </th> <th> <div class="cell">head2</div> </th> <th> <div class="cell">head3</div> </th> <th> <div class="cell">head4</div> </th> <th> <div class="cell">head5</div> </th> </tr> </thead> <tbody> <tr> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> </tr> <tr> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> </tr> <tr> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> <td> <div class="cell">1</div> </td> </tr> </tbody> </table> </div> table { border-collapse: collapse; table-layout: fixed; width: 500px; } .wrapper { height: 150px; overflow: auto; } td, th { width: 150px; height: 50px; text-align: center; font-size: 32px; padding: 0; } th { position: sticky; top: 0; left: 0; background-color: #fff; } .cell { border: 1px solid black; height: 100%; } td .cell { border-top: none; border-left: none; } th .cell { border-left: none; } td:first-child .cell, th:first-child .cell { border-left: 1px solid black; }Puedes añadir
.table { border-collapse: separate; border-spacing: 0; }No use border-collapse y dibuje las líneas de la siguiente manera:
td, th { border-bottom: 1px solid grey; border-right: 1px solid grey; } table { border-spacing: 0px; border-left: 1px solid grey } th { background-color:#c5e8ec; position: sticky; position: -webkit-sticky; border-top: 1px solid grey; top:0; }Aquí está CSB para la tabla de materiales mui, probado en Chrome, FF, Edge y Safari
https://codesandbox.io/s/mui-material-table-sticky-header-with-borders-fsmnd?file=/src/App.tsx
En este caso, la clave estaba en desarmar el borde colapsado en la mesa:
const TableSticky = (props: TableProps) => { const { sx, ...other } = props; return ( <Table sx={{ borderCollapse: "unset", borderLeft: border, ...sx, }} size="small" {...other} /> ); };También es inteligente usar postion: sticky en las columnas de encabezado en lugar de la tabla:
const HeadCell = (props: TableCellProps) => { const { sx, ...other } = props; const theme = useTheme(); return ( <TableCell sx={{ borderBottom: border, borderRight: border, borderTop: border, position: "sticky", top: 0, backgroundColor: theme.palette.background.default, ...sx }} {...other} /> ); };