For HTML tables, you can use the
border
attribute to suggest the width of a border around the
table and each cell. There are
other methods defined in HTML 4 to suggest
cell borders (or "rules", as they are called there)
as separate from the overall border for the entire table. Such methods don't
work e.g. on Netscape 4 for example, though, and moreover they cannot
be used to suggest that borders should appear around a single cell only,
or even on one side or some sides of a cell only.
This document briefly discusses some HTML hacks like nested tables that might
be used, and then the more reasonable style sheet (CSS) approach.
For simplicity, let us consider a trivial table with three cells:
<table border="1" cellspacing="0" cellpadding="4"> <tr> <td>one</td> <td>two</td> <td>three</td> </tr> </table>
This is how it looks like on your browser:
one | two | three |
The cellspacing
and
cellpadding
attributes are mostly not relevant to our discussion, though you probably
want to tune their values to suit your table content.
But note that using style
sheets you could suggest padding properties for an individual cell if you like.
So you could e.g. set cellpadding
to zero and use the
CSS padding properties
to suggest the paddings you like, with the implication that in
non-CSS browsing situations there would be no padding.
Now let's first assume that we would like to remove the borders except for those
surrounding the second cell. There is no direct way to do that in HTML.
But one possible approach is to set border="0"
and
construct a border for the second cell by making the cell content a single-cell
table, with a border of its own:
<table border="0" cellspacing="0" cellpadding="4"> <tr> <td>one</td> <td><table border="1" cellpadding="4"> <tr><td>two</td></tr></table></td> <td>three</td> </tr> </table>
This is how it looks like on your browser:
one |
|
three |
Nested tables
are valid HTML. The reason I call using nested tables a hack here is that
the inner table isn't really much of a table, and it is used for presentational
purposes only, and it distorts the logical structure - that is, the
markup does not correspond to the intrinsic structure of the data.
But it's a fairly innocuous hack. Used with syntactically correct markup and
with all the end tags like </td>
written explicitly, to avoid
Netscape bugs, it should be fairly safe. But not totally safe. It is
possible that some programs will process the document according to the way
you have indicated in your markup, and therefore treats the content cell as a table,
whatever that might mean in each content.
What if you would like to affect the appearance of the border:
its color and shape? Well, using a modification of the nested tables trick,
you could make the border solid and have a specific
color. (Under the usual caveats of course; a browser might be
configured to ignore colors suggested on pages, or the monitor might be
incapable of displaying the suggested color, etc.) The idea is to use
padding inside a cell for creating the impression of a colored border.
This means that you would use border="0"
for the inner table
too but use
a nonzero cellpadding
for outer table to create some border-like
space between the cell content (the inner table) and the invisible
(or zero-width, just as you like it) cell border, and
a bgcolor
attributes for coloring that space.
<table border="0" cellspacing="4" cellpadding="2"> <tr> <td>one</td> <td bgcolor="#006600"> <table border="0" cellpadding="4" cellspacing="0"> <tr><td bgcolor="#ffffff">two</td> </tr></table></td> <td>three</td> </tr> </table>
This is how it looks like on your browser:
one |
|
three |
It's somewhat complicated. Note that the cellpadding
attribute
of the outer table specifies the width of the "border" whereas the
cellpadding
attribute for the inner table specifies the padding
around its content. The bgcolor
attribute for the cell
("#ffffff"
, i.e. white, in our example)
should normally be the same as the overall page background or the table
background color, but it could be different too, of course,
if you wish to achieve a special effect.
Things get even more complicated if you wish to make just one side, or just some sides, of the the cell bordered. Let's consider a simple case where you would like to have a border just on the left side of the cell. Then you could just add a "dummy cell" into the table and try to make that cell look like a border - for example, a two pixels wide empty cell which has the dark green background. This raises some problems, but they are discussed separately in the document Empty cells in HTML tables, so here we just make use of the technique explained there:
<table border="0" cellspacing="4" cellpadding="0"> <tr> <td>one</td> <td bgcolor="#006600" width="2"><img src="../images/transp.gif" width="2" alt=""></td> <td>two</td> <td>three</td> </tr></table>
This is how it looks like on your browser:
one | ![]() |
two | three |
Note that cellpadding
has been set to zero,
since that attribute affects
the "dummy cell" too, and a nonzero value would
make it wider than you want. (If you use
<td width="2">
for example, a browser could still,
quite meaningfully, use a wider cell if the cell padding requirements alone
make it necessary.) So the spacing between cell contents, including the
"dummy" cell and its neighbors, comes from the cellspacing
attribute alone. This may cause problems, since cellspacing
affects in vertical direction too, so the spacing between rows
might become too large. As you may guess, nested tables could be used
as a workaround. (You could make the cell content a table, consisting just
of the dummy cell and the real cell content.) But I think it's time
to move to methods which are not inherently that hackish, though they too
require some tricks if you wish to achieve maximal browser coverage.
Using stylesheets (CSS),
it is in principle very easy to suggest borders for a cell.
You would just assign a style sheet rule to it, using the
border
property, or related properties.
Using an "embedded" style sheet in a style
attribute
(not the best way, but will do for our illustration), you could write
just
<td style="border:solid 2px #060">
You wouldn't then use any border
attribute in HTML,
expecting the border to default to zero,
or you might explicitly write <table border="0">
. Note
that in color specifications in CSS, you can use handy short forms like
#060
for #006600
(which is acceptable too in CSS).
If you would like to have a border just on the left size, you would
simply use border-left
instead of border
there.
Here's a simple test, with left border suggested for the second cell:
one | two | three |
If you're using, say, Internet Explorer 4 or Opera 4, you'll probably see the border there, unless your browser settings prevent that. On Netscape 4, you won't. On the other hand, you might be perfectly satisfied with having your table shown the preferred way in most browsing situations and without that border in a minority of cases. (After all, you can never control such things as an author, anyway.) Then you can keep your markup and your style sheet simple and nice and logical.
But it is possible to cover Netscape 4 too, with some added
complexity. Among the many
bugs in CSS implementation on Netscape 4, there are
two problems that are particularly relevant here:
Netscape has problems with applying styles to table cells, and
it does not support properties like border-left
.
As a workaround to the former, we can wrap the cell content into
div
markup and assign the style sheet rules to it.
As to the latter, we can use the border
shorthand property
(which partly works on Netscape) to suggest a border with the desired color
and border style but zero width, and use the
border-left-width
property (which, oddly enough, partly
works on Netscape) to suggest that the left border have a nonzero width:
<table border="0" cellspacing="0" cellpadding="4"><tr> <td>one</td> <td><div style= "border: solid 0 #060; border-left-width:2px; padding-left:0.5ex"> two</div></td> <td>three</td> </tr></table>
This is how it looks like on your browser:
one | two |
three |
The padding-left
property is used here to prevent the border from hitting
the content. Since the border is not for the td
element now but
for the div
element inside it, the cellpadding
affects
the padding between that border and the (invisible) cell border, not between
the border and the content of the div
element. But this is really
no problem, since padding-left
is well supported by
CSS enabled browsers.
What might be a problem is that the border might not
extend vertically to fill the entire cell, since it's a border for
div
element inside the td
element and
the cellpadding
attribute affects the padding vertically too.
If this is a problem, consider setting cellpadding
to zero
and using CSS for any padding you like.
Note that in a style sheet (inside a style
element, not
attribute, or in a separate file) you could simply write, say,
td, th { padding: 0.5ex; }
to set the default padding inside all cells to 0.5ex
,
and then perhaps override that for some cells if desired.
To end with a word of warning: It is advisable to
close all table-related elements explicitly with
end tags like </td>
, </th>
,
</tr>
and </table>
, even though
some of them are formally optional according to HTML specifications.
I have managed to crash Netscape with a fairly simple construct just because
I did not follow that advice.
Date of last update: 2000-11-16
Jukka Korpela