When You Don’t Know What’s in the Table
Responsive data tables have been a stumbling block since the early days of responsive design. Native <table> elements have a minimum width based on their content, which can easily exceed the viewport of a small screen.

But not every table deserves the same treatment. If that overflowing table on the left were scrollable, the experience might actually be acceptable. In fact, that's the approach used here on CSS-Tricks for the base table styles covering any blog post that may contain a table. It's the safest route when you have no idea what content the table holds.
The core mechanism is simple: wrap the table in a <div> with overflow: auto;. That allows the table to exceed the parent's width without breaking the layout—it triggers a scrollbar instead. But as Adrian Roselli points out, there's more to it. The wrapper needs to be focusable and labeled so keyboard and assistive technology users can access the scrollable area:
<div role="region" aria-labelledby="Caption01" tabindex="0">
<table>
<caption id="Caption01">Appropriate caption</caption>
<!-- ... -->
</table>
</div>
With that in place, the scrolling and focus styles can be applied:
[role="region"][aria-labelledby][tabindex] {
overflow: auto;
}
[role="region"][aria-labelledby][tabindex]:focus {
outline: .1em solid rgba(0,0,0,.1);
}
When Further Engineering Makes Sense
For cases where you know exactly what the table contains and how it will be used, a more elaborate responsive strategy can work. One classic approach is applying display: block to many of the table's elements, causing each row's data to stack vertically. Pseudo-elements can then supply the column labels.
This works well when a single row of content makes sense on its own. It fails when the table's purpose is cross-referencing data across columns—stacking rows destroys that comparison. So, while there's a rich set of options for responsive tables with known content, the default solution for an unknown one remains the same: make it swipeable.



