views:

142

answers:

3

Having an HTML page with a simple table and js code to do show / hide on it:

<html xmlns="http://www.w3.org/1999/xhtml"&gt;
<head>
    <title>title</title>
    <script type="text/javascript">


    function showErrorSteps()
    {        
        var el = document.getElementById("t1");

        if(el.style.display=="none")
        {
            el.style.display="block";
        }
        else
        {
     el.style.display="none";
        }                                       
    }

    </script>
</head>
<body>

<br />
<span onclick="showErrorSteps()">[click]</span>
<br />
<br />

<table id="t1" border="1" width="100%" style="table-layout: fixed">
<tr>
    <td>s</td>
    <td>d</td>
    <td>a</td>
</tr>
</table>        
</body>
</html>

What happens is that on Mozilla the table gets resized after you click twice(even with the table-layout: fixed css). IE works fine.

+6  A: 

Tables shouldn't be set to display: block. Table rows and cells shouldn't either. They have different display values. My advice? Don't do it this way. Use a class:

.hidden {
  display: none;
}

and dynamically add it and remove it from the table to avoid problems of setting the right display type on an element that you show.

Edit: To clarify the comment as to why do it this way and what's going on. Try this:

<table>
<tr>
  <td>Cell 1</td>
  <td style="display: block;">Cell 2</td>
</tr>
</table

It will (or should) screw up your table layout. Why because a <td> element, by default, has display: table-cell not block. Tables are the same. They have display: table.

Unsetting CSS attributes is... problematic.

Thus you are best off using classes to set and unset attributes. It's easier to change (the class resides in a CSS file and isn't code), avoids problems like setting the value back to the correct original value and generally provides a cleaner solution, especially when used with a library like jQuery. In jQuery, you can do:

$("table").toggleClass("hidden");

Done.

Or you can use addClass() and removeClass() if that's more appropriate. For example:

<input type="button" id="hide" value="Hide Table">
...
<table id="mytable">
...

and

$(function() {
  $("#hide").click(function() {
    if ($("#mytable").is(".hidden")) {
      $("#hide").val("Hide Table");
      $("#mytable").removeClass("hidden");
    } else {
      $("#hide").val("Show Table");
      $("#mytable").addClass("hidden");
    }
  });
});

And there you have a robust, succinct and easy-to-understand solution (once you get your head around the jQuery syntax, which doesn't take that long).

Messing about with Javascript directly is so 2002. :-)

cletus
This works although I must admit I don't understand why it works.
AnthonyWJones
@cletus: What is the default value for display for a Table, its not Block.
AnthonyWJones
Simple. Because having the class it's display will be none and not having the class it's display will be as per element default. There's no persistence. I keep telling people class manipulation is better than style manipulation but will they listen ;)
annakata
"display:table"
annakata
thx, that worked!
Bogdan Gavril
A: 

This might be because you set the style.display to "block". Try to set it to "". You should also set the table width using CSS. (width: 100%;)

Lennart
+1  A: 

This is not a direct answer to your question, but a serious recommendation. I have recently discovered the joys of JQuery. All this kind of stuff can be done effortlessly and there is extensive online examples and references available.

If you haven’t got time to get into it now then I’m sure someone will offer a solution here, but I would recommend anyone who does anything beyond the most cursory JavaScript DOM manipulation to consider JQuery (or a similar framework).

JQuery offers browser independent Hide(), Show() and Toggle() methods. Here’s one of my favourite references.

Andy McCluggage
Thanks, I'll look into it. I actually work at a .net win forms project, so I don't really interact with html, except when I want to do some fancy reporting.
Bogdan Gavril