Search code examples
html-tablesemantic-markup

Nested tables with related parent content


Having a semantics issue. I have a basic table with a standard header and footer. Each row contains an order, beneath each row I need to display another table, that will contain a break down of costs relating to that order. Additionally, these inner tables will be displayed with a jQuery accordion to hide and show when required (but I'm just concentrating on the HTML for now)

table containing the row "Order 1" followed by a row "Order 1 related table"

How can I semantically approach this in HTML?

<table>
    <thead>
        <th>Package number</th>
        <th>Date placed</th>
        <th>Placed by</th>
        <th>Total cost</th>
    </thead>
    <tr>
        <td>1</td>
        <td>Weds</td>
        <td>Jonno</td>
        <td>£15</td>
    </tr>
    <tr>
        <td colspan="4">
            <table>
                <thead>
                    <th>Part number</th>
                    <th>Description</th>
                    <th>Qty shipped</th>
                    <th>Weight</th>
                </thead>
                <tbody>
                    <td>18293</td>
                    <td>Blah blah blah</td>
                    <td>72</td>
                    <td>20Kg</td>
                </tbody>
            </table>
        </td>
    </tr>
    <tr>
        <td>2</td>
        <td>Thurs</td>
        <td>Jonno</td>
        <td>£1</td>
    </tr>
    <tr>
        <td>3</td>
        <td>Fri</td>
        <td>Jonno</td>
        <td>£7</td>
    </tr>
</table>

Here's a fiddle: http://jsfiddle.net/yuW7f/ - The problem here is that the row containing the inner table, is totally unrelated to the order row


Solution

  • If you are looking for a parent element you can use to group related rows, you can use <tbody> elements. A table can have multiple <tbody> elements:

    <table>
        <thead>
            <tr>
                <th>Package number</th>
                <th>Date placed</th>
                <th>Placed by</th>
                <th>Total cost</th>
            </tr>
        </thead>
        <tbody>
            <tr>
                <td>1</td>
                <td>Weds</td>
                <td>Jonno</td>
                <td>£15</td>
            </tr>
            <tr>
                <td colspan="4">
                    <table>
                        <thead>
                            <tr>
                                <th>Part number</th>
                                <th>Description</th>
                                <th>Qty shipped</th>
                                <th>Weight</th>
                            </tr>
                        </thead>
                        <tbody>
                            <tr>
                                <td>18293</td>
                                <td>Blah blah blah</td>
                                <td>72</td>
                                <td>20Kg</td>
                            </tr>
                        </tbody>
                    </table>
                </td>
            </tr>
        </tbody>
        <tr>
            <td>2</td>
            <td>Thurs</td>
            <td>Jonno</td>
            <td>£1</td>
        </tr>
        <tr>
            <td>3</td>
            <td>Fri</td>
            <td>Jonno</td>
            <td>£7</td>
        </tr>
    </table>
    

    Whether or not that makes your code more semantically correct is debatable. You could also give your rows classes to indicate whether the row is a summary row or a detail row, or attributes to indicate relationships to other rows. Semantically, it seems fine as it is to me.

    By the way, you are missing some <tr> elements. A <tbody>, <thead>, or <tfoot> element does not replace a <tr> element.