JavaScript tip: Variadic functions

Let’s say you have a table of data, and you have a requirement to hide some or all of the data by clicking some “hide” or “show” links. If your data is only one-tier, it’s pretty easy to do. You can wrap the rows that you want to hide or show in a <tbody> tag and use that tag to make the rows it contains display or disappear. Here’s an example.

But while a <table> can have multiple <tbody> tags, they have to be stacked, they can’t be nested.

Good:
<table>
  <tbody>
    <tr>...</tr>
    <tr>...</tr>
  </tbody>
  <tbody>
    <tr>...</tr>
    <tr>...</tr>
  </tbody>
</table>
Bad:
<table>
  <tbody>
    <tr>...</tr>
    <tbody> <!-- ack! -->
      <tr>...</tr>
      <tr>...</tr>
    </tbody>
    <tr>...</tr>
  </tbody>
</table>

So what to do when someone designs a table that has multiple levels of expand and collapse and asks you to build it?

(A valid answer is “ask them if they really honestly truly need that much info at one time, because I mean c’mon really? There isn’t an information architecture solution better than that? Are they crazy?” but alas, sometimes that doesn’t cut it.)

If you knew that every time you needed to hide the subcategory’s rows you’d be hiding the same number of rows, you could write a function that accepted exactly that number of rows:

function hide3rows('ID1', 'ID2', 'ID3'){
  document.getElementById('ID1').style.display="none";
  document.getElementById('ID2').style.display="none";
  document.getElementById('ID3').style.display="none";
}

But I tell you as soon as you do that, some pest is going to come along and change the requirements to more rows or fewer rows, or sometimes six rows and sometimes eight. And you certainly don’t want to spend your time building a library of hide1row(), hide2rows(), etc. because you need that free time to follow around the person who wrote these requirements so you can keep asking them if they are in fact crazy.

This is where variadic functions come in. A variadic function is one that accepts a variable number of arguments. Generally, it does the same thing to all of the arguments, like add them together, or print them, or in our case figure out which elements they refer to and change their display attribute from visible to hidden. Different languages support variadic functions in different ways. JavaScript actually makes them pretty easy to use, by treating the arguments passed to the function like an array, so we can check the arguments/array length and iterate over its elements.

function hideThings() {
  for (var i = 0; i &lt; arguments.length; i++) {
    document.getElementById(arguments[i]).style.display='none';
  }
}

Here’s our previous table modified to use this function.
Now we can call our hide function with as many or as few arguments as we need to hide. hideThings(‘mon’, ‘tue’, ‘wed’, ‘thu’, ‘fri’); is just as valid as hideThings(‘birthdays’); and we don’t need to clutter up our files with sixty five versions of the same function.

Javascript tip: Style display and table rows

It seems like about half the world knows this one, but the other half doesn’t.

Let’s say you have a table, and you want to be able to toggle various rows on and off. So you write yourself a couple of simple Javascript functions to hide and show your stuff.

function hide(thingID){
document.getElementById(thingID).style.display = 'none';
}

function show(thingID){
document.getElementById(thingID).style.display = 'block';
}

Here’s the problem: display:block turns a table row into a block element — which is to say it compresses the whole table row into one big chunk and stuffs it into the space for your first table cell in that row.

If you do your research, you’ll quickly learn that the W3C says you’re supposed to use “display:table-row” for tables. But when you change your “show” function to use the preferred method, all the standards-compliant browsers start working, but IE 7 and the other annoying old IE browsers you’re forced to support just flat out drop the rows.

The secret? So obvious almost no one thinks of it until they’re told:

function show(thingID){
document.getElementById(thingID).style.display = '';
}

By setting the display to effectively “ain’t got one”, you tell the browser to display the row the way it would have if you hadn’t messed with it. Which results in what you were looking for:

To check the results in your browser(s) of choice, feel free to fiddle with this test page.

Pet peeves: Review pages you can’t review

There’s security, and then there’s stupidity.

We’re all familiar by now with the security pattern where you set up 2-3 questions that “only you” will know the answer to (well, only you and people who know you really well, anyway) in addition to your username and password. It essentially sets up a two-password system. If you can’t answer the first password (your security question’s answer) you never get to the second password, thus securing it.

Or something.

I have a lot of problems with that security pattern, which I won’t get into here, because this post isn’t about the security, it’s about the stupidity. It’s security when you ask me to set up a double-password system. Since it’s critical information, it’s good design and good sense to ask me to review the information before I submit it, and print it for my records. One password is hard enough to remember, but this pattern essentially asks me to set up three.

It’s stupidity when you decide that your security policies need to be strong that when you ask me to review my information for accuracy, you obscure the answers to my questions.

And yet… that’s what we have here.
Asterisking out the answers to the security questions? Not helpful when part of reviewing is confirming that I spelled them right!
I’m willing to guess that the vast majority of people are not dumb enough to fill out a registration form for a medical billing website on the Jumbotron of their local stadium, or anywhere else that would allow a significant number of people to view the process. So why make that registration even harder by blocking the review of critical account-access-granting information? It’s security absurdity.

Hello world!

It’s obligatory to use that as the name of your first post, same as it is to use it for the first application you write in a new language.

At least, that’s what these fellas behind me with the suits, dark glasses, and baseball bats contend. 

Let’s go with that.