4umi.com/web/javascript/tablehilite

Rows across tables

Table Javascript

The rows of the three tables below each have onclick, onmouseover and onmouseout event handlers set by the Javascript after page load. On every event, a classname is added or removed from the corresponding rows in each table.

The html for the tables is free of script, but to keep the document tree compatible across browsers, there should be no whitespace between <tr> tags. A carriage return between one </tr> and the next <tr> creates a textnode in Mozilla browsers, but is ignored by ie.

The test tables

Move your mouse over a table to see the current row highlighted in all three tables. Click a row to highlight it even more!

JULI T F L S M T O T F L S M T O T F L S M T O T F L S M T O T F L
12345678910111213141516171819202122232425262728293031
Row 1 nNN  eee  fffff  nnnn         F
Row 2   FFee  nNN  eee  fffff  nnnn  
Row 3 n        FFee  nNN  eee  fffff 
Row 4 ff  nnnn        FFee  nNN  eee 
Row 5 ee  fffff  nnnn        FFee  nN
AUG S M T O T F L S M T O T F L S M T O T F L S M T O T F L S M T
12345678910111213141516171819202122232425262728293031
Row 1 Fee  nNN  eee  fffff  nnnn     
Row 2       FFee  nNN  eee  fffff  nn
Row 3  nnnn     U  FFee  nNN  eee  ff
Row 4  fffff  nnnn         FFee  nNN  
Row 5 N  eee  fffff  nnnn        FFee
SEP O T F L S M T O T F L S M T O T F L S M T O T F L S M T O T
123456789101112131415161718192021222324252627282930
Row 1    FFee  nNN  eee  fffff  nnnn
Row 2 nn     U  FFee  nNN  eee  ffff
Row 3 fff  nnnn   NNU  FFee  nNN  ee
Row 4 eee Ffeffe  nnnn     UU FFee  
Row 5   nNN  eee  fffff  nnnn     U 

The script

The initialization is done by the anonymous function at the end (if all necesary tags and elements are placed before it in the source, the code can run without waiting for the window.onload event to fire). It loops through all the tables the document has to offer, and attaches three anonymous functions to the three events firing on each of the rows, except the first, which is a header row.

The function called onmouseout checks for the className before toggling, as the user may well be holding his mouse over one of the tables during the initialization!

function toggleclass( el, name ) {
 name = ' ' + name;
 var s = el.className;
 el.className = s.indexOf( name )<0 ? s + name : s.replace( name, '' );
}

function multiplerows( el, name ) {
 var t = document.getElementsByTagName( 'table' ), i = t.length, r = 0;
 while( ( el = el.previousSibling ) ) { r++; }
 while(i--) { toggleclass( t[i].rows[r], name ); }
}

(function() {
 var t = document.getElementsByTagName( 'table' ), i = t.length, j, k;
 while( i-- ) {
  j = t[i].rows.length;
  while( --j > 1 ) {
   k = t[i].rows[j];
   k.onclick = function() { multiplerows( this, 'clicked' ); };
   k.onmouseover = function() { multiplerows( this, 'hovered' ); };
   k.onmouseout = function() {
    if( this.className.indexOf( 'hovered' )>-1 ) { multiplerows( this, 'hovered' ); } };
  }
 }
})();

The stylesheet

As a click occurs only when the mouse is already over an element, it is important to place the class definition for the clicked state after the one for the mouseover state in the cascade of styles.

.neutral { background: none; }
.hovered { background: yellow; }
.clicked { background: gold; }