Use a table when content has tabular relationships, such as the items, prices, quantities, and totals in a checkout cart. CSS Grid is for page layout; using tables for general web layout weakens semantics and accessibility. section 2.1 section 8.1
A cart that fits a phone
Start with one HTML table containing a header row and item rows. Keep that HTML for every screen size. A conventional row needs too much horizontal space on a phone, so change its presentation at narrow widths rather than replacing the table. section 8.1 section 8.3.1
Inside `@media(max-width: 549px)`, turn each item row into a card-like stack:
- Set `tr` and `td` to `display: block`; their default displays are `table-row` and `table-cell`. section 8.3.1
- Float the item image left and add a right margin so the other content wraps with some breathing room. section 8.3.1
- Move `thead` offscreen. For cells with `data-name`, use `td[data-name]::before` and `content: attr(data-name) ':'` to show a label beside the right-aligned value. section 8.3.1
- Give the footer row a flex layout to separate its label and total. At 550px and wider, the mobile rules no longer apply and the standard table layout returns. section 8.3.1 section 8.4
Listing 8.21 Mobile table CSS
th, td, td[data-name]::before {
color: #3a3a3a;
font-weight: normal;
font-size: .875em;
}
@media(max-width: 549px) {
td, tr { display: block }
table td > img {
float: left;
margin-right: 10px;
}
thead {
position: absolute;
left: -9999rem;
}
td {
text-align: right;
padding: 5px;
vertical-align: baseline;
}
td[data-name]::before {
content: attr(data-name) ":";
float: left;
}
tfoot tr {
display: flex;
justify-content: space-between;
align-items: baseline;
}
tfoot th { padding: 5px }
}
table { width: 100% }
The complete CSS shows how the mobile-only card treatment fits alongside the table’s shared styles. section 8.3.1











