Wickham's HTML & CSS tutorial
View in Firefox, Safari, Opera and IE but IE6 often needs different solutions. In general IE7 and IE8 display like Firefox apart from the HTML5 and CSS3 features. The IE9 & above updates are mainly related to HTML 5 and CSS3 issues and display to a large extent like other main browsers. Google Chrome is based on the same WebKit engine as Safari.
Some of the examples are provided just to show problems, others show solutions that work in most major browsers. Use the example that suits you.
problems warning: works in some situations or some browsers or needs care to display as you wish OK in Firefox, Safari, Opera, Google Chrome and IE
Tables date back to the early days of html. w3.org says Tables should not be used purely as a means to layout document content as this may present problems when rendering to non-visual media. Additionally, when used with graphics, these tables may force users to scroll horizontally to view a table designed on a system with a larger display. To minimize these problems, authors should use style sheets to control layout rather than tables. However, tables are still useful for their main purpose which is to show tabular data.
Older methods of coding in HTML without stylesheets used codes inside the html tags using the = sign and " as in <table border="1">. However, although this method of coding still works in many cases it is better to use the CSS method with HTML where possible.
The CSS method of coding uses style with a colon : between the attribute and the value.
If used in the body html tag it is like this:-
<table style="border: 1px solid black">
If used in the head of an html page the code is:-
<style> table { border: 1px solid black; } </style>. A semi-colon ; is used between each attribute where there are several as in <style> table { border: 1px solid black; margin: 10px; } </style> although not required at the end before the closing } it is probably a good idea to do this so that when adding extra attributes it is not forgotten.
However, rowspan and colspan still seem to be given values as ="2" or any other number required.
In old HTML tables cell spacing is the space between cells in a table. Cell padding is the extra space inside a cell between the contents and the border of the cell. You can set these values with the cellspacing and cellpadding attributes, which take a value representing the size in pixels, or you can use style sheets.
The style sheet equivalents of cellspacing and cellpadding are border-spacing (for the table element as a whole) and padding (for td and th cells).
See the CSS table model here.
1 Simple two column table.
Two column table with table border and td cell borders Stylesheet code:- .example { style="width: 730px; border: 1px solid blue; border-spacing: 15px; } |
|
Table cell stylesheet code:- .example td { border: 1px solid black; padding: 3px; } and .leftcell { width: 40%; } | Right cell |
The code (only the brown text; don't copy/paste the dark green text) for the above is:-
<table class="example"><tr>
<td colspan="2">
<b>Two column table with table border and td cell borders</b><br>
Stylesheet code:- .example { width: 730px; border: 1px solid blue; border-spacing: 15px; }
</td>
</tr><tr>
<td class="leftcell">
Table cell stylesheet code:- .example td { border: 1px solid black; padding: 3px; } and .leftcell { width: 40%; }
</td>
<td>
Right cell
</td>
</tr>
</table>
Note that in Firefox the border-spacing is correctly shown above as 15px but IE only shows the default 2px spacing. IE needs the additional old HTML method of coding cellspacing as in example 2.
2 Simple two column table where the table tag in the html file has cellspacing="15" in addition to the stylesheet code of border-spacing: 15px like this:- <table class="example" cellspacing="15">
Two column table with table border and td and th cell borders Stylesheet code for table class:- .example { width: 730px; border: 1px solid blue; border-spacing: 15px; } |
|
---|---|
Table cell stylesheet code:- .example td, th { border: 1px solid black; padding: 3px; } and .leftcell { width: 40%; } | Right cell |
Left cell | Table cells expand down to suit text. Any other td cells in the same row will also be the same height and content will centralise vertically - see left cell. Cells will have the same width as widest cell in the same table column. To create cells with a different width, start a new table. <tr> is a row separator; <td> and <th> are cell separators. The number of cells in a table width must be the same for the whole table so use colspan="2" or another number where a wider cell spanning two or more is required. |
<td class="leftcell" style="background-color: pink;"> | Right cell |
In addition this example uses <th colspan="2"> instead of <td colspan="2"> for the first cell. Note that this is used for headings which centralise text by default and display bold text by default. It is also useful for analysis as it separates data from headings.
The code (only the brown text; don't copy/paste the dark green text) is:-
<table class="example" cellspacing="15">
<tr>
<th colspan="2">
Two column table with table border and td and th cell borders
Stylesheet code for table class:- .example { width: 730px; border: 1px solid blue; border-spacing: 15px; }
</th>
</tr><tr>
<td class="leftcell">
Table cell stylesheet code:- .example td, th { border: 1px solid black; padding: 3px; } and .leftcell { width: 40%; }
</td>
<td>
Right cell
</td>
</tr><tr>
<td class="leftcell">
Left cell
</td>
<td>
Table cells expand down to suit text. Any other td cells in the same row will also be the same height and content will centralise vertically - see left cell.
Cells will have the same width as widest cell in the same table column.
To create cells with a different width, start a new table.
<tr> is a row separator; <td> and <th> are cell separators.
The number of cells in a table width must be the same for the whole table so use colspan="2" or another number where a wider cell spanning two or more is required.
</td>
</tr><tr>
<td class="leftcell" style="background-color: pink;">
<td class="leftcell" style="background-color: pink;">
</td>
<td>
Right cell
</td>
</tr>
</table> <!--end of simple two column table-->
3 The width has not been stated in this example so the table is only as wide as it needs to be for the contents of the widest cell in each column or the default maximum of 100% which in this case would be 730px as it is contained by the div for the whole page.
<table style="text-align: right; border: 10px solid pink;"> | |
This cell only has an olive border:- <td style="border: 5px solid olive; padding: 5px 25px;"> more text on the next row |
right cell text |
The top and right cells have no padding. The small apparent padding is the default border-spacing between the cell and adjacent cell or table border.
4 This demonstrates the effect of border-collapse if several cells have borders.
as item 3 but no text-align: right; | |
as item 3 more text the on next row |
right cell text |
as item 3 but no text-align: right; | |
as item 3 more text on the next row |
right cell text |
The style for the table in the right example has border-collapse: collapse; which applies to the whole table but there is a priority given to types of border and where they are situated as described here.
Note that both tables were put in a containing div <div style="float: left;"> and no border or padding to enable the tables to show side-by-side
5 If you have a two or three divs of different and flexible height and you have a containing div with a background-color or image but no height stated, you will find that the background does not extend down as far as the bottom of the div with the greatest height (it will if you give a height). There are solutions to this here.
However, if you use tables the background-color of the table and each cell will extend the full height of the table even if one cell does not have much content and the height will remain flexible.
Divs in a containing div with a background:-
Equivalent arrangement in a table:-
width: 240px; background-color: pink; (no height stated) more text more text more text more text |
Azure cell width: 240px; (no height stated) |
Yellow cell width: 210px; (no height stated) more text more text |
6 Table cells without a width stated will determine their own width. In the example below, which is nearly the same as the one above, the widths have been removed from the pink and azure cells but the yellow one remains width: 210px. The table has a fixed width of 730px and has shown the longest sentence of the pink and azure cells and then apportioned pro rata the space in each cell at the end of the sentences.
It is up to you whether you want to fix cell widths or leave it to be apportioned in a way you cannot foresee. The widths of other cells in the same column will also be affected by apportionment and all cells in a column will be the same width, based in some way on the widest content in each column, or equalised if they add up to more than the available table width.
background-color: pink; (no height stated) (no width stated) more text more text more text |
Azure cell (no width or height stated) |
Yellow cell width: 210px; (no height stated) more text more text |
Where you want a narrow space between cells you have several options:-
Use the cellspacing or border-spacing properties which will show the space as the color of the general background.
Use additional narrow columns.
Where you are using very narrow columns, such as to create a spacer column say 2px wide, inserting any character even will create a default width based on the character which will almost certainly be more than 2px as even characters 1px wide have a space each side so these narrow cells are best filled with a 2px wide image with the same color as the general background instead of a character or nothing at all. The image only needs to be 1px high as it is only there to create a width and the cell height will automatically be the same as for adjoining cells with content. It is generally advisable to put something in a cell as browsers don't like to render empty cells; Internet Explorer does it differently from Netscape.
If you want the narrow cell to have a different color then a background color or background image that repeats would be needed. However, this doesn't solve the problem of the empty cell unless you have a 1px high image of the same color in the cell over the background image.
If you want the narrow space to have a different color make the border on one side of a cell with content a different color to create a divider:-
<td style="border-right: 2px solid #aaaaaa;">cell content</td>
There is also a border-image property as described in w3c.org but this is for CSS3 and many browsers will not operate this feature yet.
Other examples of cell widths is shown on dwfaq.com.
7 valign="top" is useful for keeping content of one cell at the top if another cell has a lot of content.
Table has width: 530px; but no height specified Left td below has valign="top". |
|
Cell with unlimited height for main content More text More text More text More text More text More text More text More text More text More text |
8 Tables can be nested. You might have a containing table for the whole page, a series of tables with different cell column wdths and a table in one cell for a special purpose such as a photo with a border. However, divs are recommended for page layout in preference to tables. You can put a table in a div, a div in a table cell or a table in a table cell.
Containing table with two cells below each with a table and photo | |||
---|---|---|---|
|
|
9 A small table nested inside the left cell below causes unwanted padding.
Table has width: 600px; but no height specified Left td below has valign="top" and a small table in it three td cells wide. Border of small table is shown to indicate position. The telephone numbers only occupy two cells so have to have a blank third cell to match the employee list above unless a second small table is provided for them. |
||||||||||||||||||||||||
|
Cell with unlimited height for main content. Short paragraphs in this cell cause a problem in IE and FF. IE and FF put padding next to the table in left cell. Cell width works properly if there is no table in cell. Long paragraphs in this cell cure the problem. A more correct solution is to use css divs for layout and a table only for the data. More text More text More text More text More text |
10 A small table nested inside the left cell below still causes unwanted padding in IE although Firefox obeys the cell width.
Table has width: 600px; but no height specified Left td below has valign="top" and a small table in it three td cells wide. Border of small table is shown to indicate position. The telephone numbers only occupy two cells so have to have a blank third cell to match the employee list above unless a second small table is provided for them. |
||||||||||||||||||||||||
|
Cell with unlimited height for main content. Short paragraphs in this cell cause a problem in IE. IE puts padding next to the table in left cell. style="width: 170px;" has been added to left cell it does not delete padding in IE but does work in Firefox. padding: 0; added to left cell style does not work. Cell width works properly if there is no table in cell. Long paragraphs in this cell cure the problem. A more correct solution is to use css divs for layout and a table only for the data. more text more text |
11 Long paragraphs in the right cell below get rid of unwanted padding as seen in the examples above but to avoid problems it is recommended that css div boxes are used for layout with a table only used for data.
Table has width: 600px; but no height specified Left td below has valign="top" and a small table in it three td cells wide. Border of small table is shown to indicate position. The telephone numbers only occupy two cells so have to have a blank third cell to match the employee list above unless a second small table is provided for them. |
||||||||||||||||||||||||
|
Cell with unlimited height for main content; this cell needs lots of text in a single paragraph as in this example to use up remaining width otherwise it sets padding next to the table in the left cell. A more correct solution is to use css divs for layout and a table only for the data. More text More text More text More text More text More text More text More text More text |
12 A table can be used for an image that is wider than the screen resolution where another cell is required to the right of it.
If you are setting up a template for extra-large images with unknown width using div boxes, you would not be able to set a width for a containing div so the image would scroll out to the right but any div further right would move to the line below to stay in view unless the divs were in a containing div with a defined width.
A table has the useful feature that cells expand in width and height as necessary. This means that an image of any size could be put in a cell and cells further right or above and below would expand as necessary without moving below to stay in view.
Header | |
Right column
div in td width: 120px; to set width more text more text |
|
Footer |
The code (only the brown text; don't copy/paste the dark green text) is:-
<table style="border: 1px solid black; background-color: #c0c0c0"><tr>
<td colspan="2" style="background-color: pink;">Header</td>
</tr><tr>
<td><img src="images/henblackbird.jpg" alt="Hen Blackbird"></td>
<td valign="top" style="background-color: #f5f5dc">
<div style="width: 120px;">Right column<br>div in td width: 120px; to set width<br>more text<br>more text</div>
</td>
</tr><tr>
<td colspan="2" style="background-color: azure;">Footer</td>
</tr></table>
13 The example below shows how rowspan and colspan are used.
Left cell <td rowspan="3"> | Top middle cell <td colspan="2"> | Right cell <td rowspan="3"> | |
Middle middle cell left | Middle middle cell right | ||
Bottom middle cell <td colspan="2"> |
The code (only the brown text; don't copy/paste the dark green text) is:-
<table class="example"><tr>
<td rowspan="3">
Left cell <td rowspan="3">
</td>
<td colspan="2">
Top middle cell <td colspan="2">
</td>
<td rowspan="3">
Right cell <td rowspan="3">
</td>
</tr><tr>
<td>
Middle middle cell left
</td>
<td>
Middle middle cell right
</td>
</tr><tr>
<td colspan="2">
Bottom middle cell <td colspan="2">
</td>
</tr></table>
14 This example explains why you can get a problem only in IE with an image in a table which is just a bit wider than the screen resolution. In this case use a resolution of 1024*768 to see the effect with an image 1018 px wide.
15 I've shown below how divs can replicate a table layout which is very useful if you want to center a div vertically inside another and you don't want to give a height to the nested div. The usual methods of centering vertically by using position: absolute; height: ??px; margin-top: -??px; with the negative margin-top half the div height can't work if you have a fluid height. Margin-top to set the div at the center of a container will also be no use with a div with fluid height if someone increases text size and therefore increases the height of the div as it will no longer be centered vertically.
Display: table doesn't work in IE6 or IE7. I've used a conditional comment which puts #div4 and #div5 side by side at the top in IE6 and IE7, but I can't replicate the vertical centering unless I add a margin-top which would become wrong if text size is increased. Horizontal centering of the display: table-row #div1a inside the display: table container in IE6 and IE7 has been done by adding a width and margin: auto;
Text in #div4
Text in #div4
Text in #div4
Text in #div4
Text in #div5
If you increase text size only, #div4 and #div5 will increase in height but remain centered vertically.
CSS (the padding 3px and borders 1px to divs are in my general stylesheet):-
The above should be in the page head section or, without the style tags, in a separate stylesheet. The following conditional comment lt ie 8 (less than IE8) should be inserted in the head section after the main style tag or stylesheet link.
HTML markup:-
#div4 content here
#div5 content here
Note that, like a table, the lime divs are also centered horizontally in their containers. I used margin: auto in the style for #divs4 and #div5, which together with a width, centers them inside #div2 and #div3. I could have used align="center" in the markup for #div2 and #div3 instead of margin: auto in the styles for #div4 and #div5, which does work to center the inner #div4 and #div5, but this is old-fashioned table code so I didn't include it above and it doesn't validate.
Notes
The stylesheet for this site which you will probably need to look at is here.
See w3.org's HTML Tables here and see w3.org's XHTML Table Module here.
The body of this page has margin: 20px. The examples above are in a containing div with width: 730px; and margin: auto; so that the page centralises at large screen resolutions.
A lot of codes have been put in html tags in my examples rather than in a stylesheet or in a style in the head. I have done this for the convenience of the viewer so that most (but not all) codes are in one place and the stylesheet does not always have to be viewed in addition. When coding your own page you should try to put as much as possible in a stylesheet and link with id or class to the html tag.
Remember that when a Doctype is included above the head before the html tag (as it should be) then the overall width of a div is its defined width plus borders, margins and padding widths.
If there are differences between Firefox and IE6 that cannot be overcome with one code, code first to get a satisfactory solution in Firefox then create an IF style which will only apply to IE6:-
for instance, if margin-top: 20px; in Firefox needs to be margin-top: 30px; in IE6 then put the following in the head of the html/xhtml page:-
<!--[if ie 6]>
<style type="text/css"> div { margin-top: 30px; } </style>
<![endif]-->
or if there are many different styles, create a separate stylesheet:-
<!--[if ie 6]>
<link rel="stylesheet" href="ie6.css" type="text/css">
<![endif]-->
IE6 will contain just the amended styles such as div { margin-top: 30px; } and others (no head or body tags or Doctype).
When looking at a page source for this site you may see code like <p>Little Egret</p> instead of <p>Little Egret</p>. The code < is because in that instance the code is to be displayed on the screen as text. If the < symbol was placed in the code a browser would activate the code and it would not display as text. Such code is not normally required when writing html code tags which are to be activated.
© Wickham 2006 updated 2011