menu.htmlCoffee menuDrinkPriceEspresso2.50Latte3.75Hot onlytbody1<table>2 <caption>Coffee menu</caption>3 <tr><th>Drink</th><th>Price</th></tr>4 <tr><td>Espresso</td><td>2.50</td></tr>5 <tr><td>Latte</td><td>3.75</td></tr>6 <tr><td colspan="2">Hot only</td></tr>7</table>SCREEN READER3.75 · Price<th scope="col">opening tag + attributePricecontent</th>closing tag<table><caption><tr><th><td><tr>colspan="2"<tbody>Pricescope="col"
Front left: the HTML file and one header cell taken apartBack right: the browser, which draws the table as it readsChips: each tag travelling from its line to the part of the table it makesFront left: menu.html, a seven-line table on a card, and one header cell taken apart into opening tag with a scope attribute, content and closing tag. Back right: a web browser. Front right: a screen reader. As the browser reads each line, a tag chip hops from the line to the page and the table grows: the grid, the caption, the header row, two data rows and a cell that spans both columns. Then the browser adds tbody around the rows, the header Price travels down to 3.75, and scope points down its column. The figure draws faint lines between the cells so you can see the grid. Browsers draw no borders by default; a CSS rule such as th, td { border: 1px solid; } adds them.

A grid of data

  1. A table holds tabular data: values set out in rows and columns, where each value means something because of its row and its column. Here, a coffee menu of drinks and prices. Tables are for data, not page layout.

Rows and cells

Meaning for everyone

What happens

;; step 1/11 · tabular
file     menu.html   (7 lines)
  1  <table>
  2    <caption>Coffee menu</caption>
  3    <tr><th>Drink</th><th>Price</th></tr>
  4    <tr><td>Espresso</td><td>2.50</td></tr>
  5    <tr><td>Latte</td><td>3.75</td></tr>
  6    <tr><td colspan="2">Hot only</td></tr>
  7  </table>
table    rows across, columns down
         each value is read by its row AND its column

The figure draws faint lines between the cells so you can see the grid. Browsers draw no borders by default; a CSS rule such as th, td { border: 1px solid; } adds them. Each row is on one line here to keep the file short. You can also put every cell on its own line; the table comes out the same.