The problem on the Gate Seal page
The Gate Seal product page for a maritime client needed to present detailed specifications without turning the layout into a wall of text or a table that looked like an export from Excel. The technical detail buyers cared about was present, but visually buried.
The requirement was to surface those details in a compact way, keep the implementation CSS-only, and make sure it still worked with keyboard navigation.
The hover-reveal pattern
The pattern below uses a hover-reveal on key specification rows. On desktop, moving the cursor over a spec row reveals additional context. With a keyboard, focusing the same row does the same thing. No JavaScript is required for the basic interaction.
Structurally, each spec item is a container with two layers of content:
- Always-visible summary (label and primary value)
- Hidden detail that appears on hover or focus
Here is a simplified version of the markup:
I wrote about this earlier in Why I Still Hand‑Code Every Hover State.
<div class="spec-list">
<button class="spec-item">
<div class="spec-main">
<span class="spec-label">Gate size</span>
<span class="spec-value">Up to 6 m</span>
</div>
<div class="spec-detail">
Custom diameters available for retrofit situations.
</div>
</button>
<button class="spec-item">
<div class="spec-main">
<span class="spec-label">Seal material</span>
<span class="spec-value">EPDM / NBR</span>
</div>
<div class="spec-detail">
Oil-resistant compounds for lock gates in heavy traffic.</div>
</button>
</div>The choice of <button> here is deliberate: it is naturally focusable, works with keyboard navigation, and is announced as an interactive element by assistive technology. In a production implementation, the button semantics can be adapted depending on whether you need a true button or a different element with role="button".
The CSS-only interaction
The interaction is controlled through :hover and :focus-visible, with a basic transition for a smoother reveal.
.spec-list {
display: grid;
gap: 0.75rem;
}
.spec-item {
width: 100%;
text-align: left;
border: 1px solid #d0d5dd;
border-radius: 4px;
padding: 0.75rem 1rem;
background: #ffffff;
cursor: pointer;
position: relative;
}
.spec-item:focus-visible {
outline: 2px solid #004b8d;
outline-offset: 2px;
}
.spec-main {
display: flex;
justify-content: space-between;
align-items: baseline;
gap: 1rem;
}
.spec-label {
font-weight: 500;
}
.spec-value {
color: #344054;
}
.spec-detail {
margin-top: 0.4rem;
font-size: 0.875rem;
color: #475467;
max-height: 0;
opacity: 0;
overflow: hidden;
transition: max-height 0.18s ease-out, opacity 0.18s ease-out;
}
.spec-item:hover .spec-detail,
.spec-item:focus-visible .spec-detail {
max-height: 6rem; /* large enough for typical copy */
opacity: 1;
}The detail block is always in the DOM and available to assistive technology, but visually collapsed until the user shows intent to inspect that spec with the mouse or the keyboard.
Keyboard and accessibility fallback
A pure hover interaction would be a problem for keyboard users and some assistive technologies. Mirroring the behavior on :focus-visible avoids that.
With the structure above:
More on this in my article Why I Rebuilt My Portfolio Navigation From Scratch (Twice).
- Each
.spec-itemis focusable and reachable via Tab. - The same detail that appears on hover also appears on focus-visible.
- The content is not injected; it is in the DOM and readable by screen readers regardless of the visual state.
If stricter control of what screen readers announce is required, aria-expanded attributes can be added and toggled with a small amount of JavaScript, but the base pattern does not depend on that. The important part is that there is no information that is only available on hover.
On touch devices, there is no hover, so the interaction degrades to a tap-to-focus behavior. The spec item receives focus when tapped, the detail appears, and tapping elsewhere moves focus away again. If that feels too subtle on mobile, details can be kept always visible below a certain breakpoint:
@media (max-width: 768px) {
.spec-detail {
max-height: none;
opacity: 1;
}
}This keeps specs compact and interactive on larger screens where hover exists, and straightforward on phones.
Read also The layout bug that vanished when I changed the copy.
Using this pattern on the Gate Seal page
On the Gate Seal page, this pattern can be applied to key specifications such as material options, mounting configurations, and maintenance notes. Core numbers stay visible, and the hover-reveal carries clarifications and edge-case notes.
The Gate Seal product page exists to support real purchasing decisions, so the interaction should be reserved for supplementary context rather than critical safety, pricing, or legal information. Those details should remain visible by default.
Subscribe to my newsletter to get the latest updates and news
Member discussion