Compact Definition Lists using CSS
<dl>
puts the term on one line with the description below. This uses a lot of height.
Can you make the term appear alongside the description?
Blast from the Past
HTML 4.01 defines but deprecates a compact
attribute. Using it on <dl>
:
<dl compact>
<dt>Foo
<dd>Ut et turpis vel mi hendrerit lobortis. Curabitur et sem eget elit cursus molestie.
<dt>Bar
<dd>Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Nullam turpis justo, adipiscing in, scelerisque et, porttitor in, nisl. In malesuada. Pellentesque placerat sem.
<dt>Baz
<dd>Cras sagittis pede in metus. In commodo nisl in nisi.
<dt>Quux
<dd>In venenatis scelerisque felis. Cras ultricies, pede non pretium adipiscing, leo neque aliquet lacus, et egestas leo felis sed lacus.
</dl>
In your browser, that markup looks like this:
- Foo
- Ut et turpis vel mi hendrerit lobortis. Curabitur et sem eget elit cursus molestie.
- Bar
- Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Nullam turpis justo, adipiscing in, scelerisque et, porttitor in, nisl. In malesuada. Pellentesque placerat sem.
- Baz
- Cras sagittis pede in metus. In commodo nisl in nisi.
- Quux
- In venenatis scelerisque felis. Cras ultricies, pede non pretium adipiscing, leo neque aliquet lacus, et egestas leo felis sed lacus.
Browser do nothing fancy with it. We can’t rely on this attribute.
Tabular display
Values
Tables were originally laid out using complicated custom algorithms. CSS2.1 defines tabular layout via the display
property. Support for these is not widespread.
I’ll create a demo if people are interested.
Running to the Rescue?
How about display: run-in;
from CSS2.1 on each <dt>
? The markup:
<dl class="compact">
<dt>Foo
<dd>Ut et turpis vel mi hendrerit lobortis. Curabitur et sem eget elit cursus molestie.
<dt>Bar
<dd>Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Nullam turpis justo, adipiscing in, scelerisque et, porttitor in, nisl. In malesuada. Pellentesque placerat sem.
<dt>Baz
<dd>Cras sagittis pede in metus. In commodo nisl in nisi.
<dt>Quux
<dd>In venenatis scelerisque felis. Cras ultricies, pede non pretium adipiscing, leo neque aliquet lacus, et egestas leo felis sed lacus.
</dl>
The CSS (in a <style>
block or external style sheet):
dl.compact {
margin: 0;
padding: 0;
}
dl.compact dt {
display: run-in;
}
The result in your browser:
- Foo
- Ut et turpis vel mi hendrerit lobortis. Curabitur et sem eget elit cursus molestie.
- Bar
- Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Nullam turpis justo, adipiscing in, scelerisque et, porttitor in, nisl. In malesuada. Pellentesque placerat sem.
- Baz
- Cras sagittis pede in metus. In commodo nisl in nisi.
- Quux
- In venenatis scelerisque felis. Cras ultricies, pede non pretium adipiscing, leo neque aliquet lacus, et egestas leo felis sed lacus.
The suggested default stylesheet for HTML has <dt>
and <dd>
as block
boxes, so run-in
should work. But nothing happened? That’s normal for now, in January 2008.
Looks like we can’t use this yet.
Whatever Floats your Boat
How about using float
on the <dt>
? Markup remains the same, with this CSS:
dl.compact {
margin: 0;
padding: 0;
}
dl.compact dt {
float: left;
margin: 0;
padding: 0 0.333em 0 0;
}
dl.compact dd {
margin: 0;
padding: 0;
}
It now looks like this:
- Foo
- Ut et turpis vel mi hendrerit lobortis. Curabitur et sem eget elit cursus molestie.
- Bar
- Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Nullam turpis justo, adipiscing in, scelerisque et, porttitor in, nisl. In malesuada. Pellentesque placerat sem.
- Baz
- Cras sagittis pede in metus. In commodo nisl in nisi.
- Quux
- In venenatis scelerisque felis. Cras ultricies, pede non pretium adipiscing, leo neque aliquet lacus, et egestas leo felis sed lacus.
This is like a compact dictionary.
Definition Grids
You can put the terms in one column with the descriptions in another using this CSS:
dl.compact, dt.compact, dd.compact {
margin: 0;
padding: 0;
}
dl.compact {
display: inline;
}
dl.compact dt {
clear: left;
float: left;
width: 10%;
}
dl.compact dd {
float: left;
width: 89%; /* 1% gap to avoid hitting both sides */
}
Here’s how it looks in your browser:
- Foo
- Ut et turpis vel mi hendrerit lobortis. Curabitur et sem eget elit cursus molestie.
- Bar
- Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Nullam turpis justo, adipiscing in, scelerisque et, porttitor in, nisl. In malesuada. Pellentesque placerat sem.
- Baz
- Cras sagittis pede in metus. In commodo nisl in nisi.
- Quux
- In venenatis scelerisque felis. Cras ultricies, pede non pretium adipiscing, leo neque aliquet lacus, et egestas leo felis sed lacus.
Analysis
This approach uses width
in %
:
- Successfully puts the terms in one column with descriptions in another.
- Difficult to use with
margin
,padding
orborder
nearby. - Columns widths won’t adjust to the length of their content.
- Columns widths remain proportional across different viewport widths.
- Rows height do adjust to the length of their content.
Recommendation
This technique has pros and cons. It is a reasonable compromise.