views:

1352

answers:

3

Have JSP page with dynamically generated HTML table with unknown number of rows.

Have property on backend, that sets maximum number of rows, e.g: max_rows=15.

How to limit number of rows for HTML table to max_rows value? Other part of table should be accessible by vertical scroll,it means that user see 15 rows and if to scroll down, that it will be seen other rows of table.

It can be done empirically by calculating average height of row and using max-height property for div-wrapper, but i think this approach is not very stable.

So it's needed to rely on row count. Perhaps there is plugin for such case or it's standard CSS or HTML solution?

Thank you for advise.

A: 

Put your table in a div block and use CSS to specify the height and overflow property of the div.

<style type="text/css">
.table_outer { height: 15em; overflow: auto; }
</style>

<div class="table_outer">
  <table>
     ...table content...
  </table>
</div>

This way the div has a fixed height and the browser will add a scrollbar when the content of the div block is too height.

I have set the height to 15em, which corresponds with 15 * font-height. When using borders, paddings and stuff this height is incorrect. But it can be calculated more properly (in px) for your design.

Veger
Oh I did not see you already thought of this. Although I *do* think it is stable and supported by most/all browsers.
Veger
Yes, it's stable, but i'm afraid that column height may vary because of long text within, and it may cause some inaccuracy.
sergionni
Indeed. You could use JavaScript to find the height of the first 15 rows, add these values, modify div height. But this sounds *very* unstable to me...
Veger
+1  A: 

There is no way to do this with only CSS and HTML, you need javascript too. Get the height of the top 15 rows, and limit the height of a wrapping div to that height. Set overflow: auto on the div to get your scrollbars.

Don't forget to set a default height on the div as a fallback if javascript is turned off.

Emil Stenström
+1  A: 

This can be done with standard HTML, CSS and a bit of javascript. It can be made to degrade gracefully for clients with javascript turned off too. By that I mean, they'll just see the original table, unmodified by scrollbars. Try something like this:

<html>
<head>
    <style type="text/css">
        table {
            width:  100%;
            border-collapse: collapse;
        }
        td {
            border: 1px solid black;
        }
        .scrollingTable {
            width: 30em;
            overflow-y: auto;
        }
    </style>
    <script type="text/javascript">
        function makeTableScroll() {
            // Constant retrieved from server-side via JSP
            var maxRows = 4;

            var table = document.getElementById('myTable');
            var wrapper = table.parentNode;
            var rowsInTable = table.rows.length;
            var height = 0;
            if (rowsInTable > maxRows) {
                for (var i = 0; i < maxRows; i++) {
                    height += table.rows[i].clientHeight;
                }
                wrapper.style.height = height + "px";
            }
        }
    </script>
</head>
<body onload="makeTableScroll();">
    <div class="scrollingTable">
        <table id="myTable">
            <tr>
                <td>blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
            </tr>
            <tr>
                <td>Here is some long text that should wrap: blah blah blah blah blah blah blah blah blah blah blah blah blah blah blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
            </tr>
            <tr>
                <td>blah</td>
                <td>blah</td>
                <td>blah</td>
                <td>blah</td>
            </tr>
            <tr>
                <td>blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
            </tr>
            <tr>
                <td>blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
            </tr>
            <tr>
                <td>blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
                <td>blah blah</td>
            </tr>
            <tr>
                <td>blah</td>
                <td>blah</td>
                <td>blah</td>
                <td>blah</td>
            </tr>
        </table>
    </div>
</body>
</html>

This was tested in Firefox, Chrome and IE 7, but it should work all modern browsers. Note that it doesn't matter how tall the content of each row is, or how much padding each cell has. If you don't want to use border-collapse:collapse on your table, then you'll have to add code in the for loop to take cellspacing into account.

If you have thicker borders, then replace the javascript function with this one:

function makeTableScroll() {
    // Constant retrieved from server-side via JSP
    var maxRows = 4;

    var table = document.getElementById('myTable');
    var wrapper = table.parentNode;
    var rowsInTable = table.rows.length;
    try {
        var border = getComputedStyle(table.rows[0].cells[0], '').getPropertyValue('border-top-width');
        border = border.replace('px', '') * 1;
    } catch (e) {
        var border = table.rows[0].cells[0].currentStyle.borderWidth;
        border = (border.replace('px', '') * 1) / 2;
    }
    var height = 0;
    if (rowsInTable > maxRows) {
        for (var i = 0; i < maxRows; i++) {
            height += table.rows[i].clientHeight + border;
        }
        wrapper.style.height = height + "px";
    }
}

The try/catch in there handles the differences between IE and other browsers. The code in the catch is for IE.

DaveS
looks promising, i will write feedback as soon test this solution for my case
sergionni
works well,thanks for assistance
sergionni