ZebraStripes
Join the DZone community and get the full member experience.
Join For Free
/*
* This script requires:
* 1. Prototype version 1.5 or greater
* - Homepage: http://prototype.conio.net/
* - Download: http://script.aculo.us/downloads
* 2. DomReady addon for Prototype
* - Homepage: http://www.vivabit.com/bollocks/2006/06/21/a-dom-ready-extension-for-prototype
* - Download: http://www.vivabit.com/code/domready/domready.js
*/
/*
* I needed something capable of not just unobtrusively running when a page
* was loaded but also easily being called at my whim as a part of an Ajax
* transaction.
*/
var ZebraStripes = {
/*
* Call this function when you want something striped. It will figure out
* how to stripe the element.
*/
stripe: function(el) {
el = $(el);
switch (el.tagName) {
case "TABLE":
this._stripeTable(el);
break;
case "OL":
case "UL":
this._stripeNormalList(el);
break;
case "DL":
this._stripeDefinitionList(el);
break;
}
},
/***************************************************************************
* Everything below here is psuedo-private
**************************************************************************/
/*
* This class name will be applied to the odd numbered elements
*/
_altClassName: "alt",
/*
* This property persists the data that tells the object whether
* to stripe (_isEven == false) or unstripe (_isEven == true) an element
*/
_isEven: true,
/*
* Cycles the _isEven property of this object between true and false
*/
_cycle: function() {
this._isEven = ! this._isEven;
},
/*
* As a part of the Ajax-friendliness, it is important that we remove the
* alt class from elements as well as add it.
*/
_stripeElement: function(el) {
el = $(el);
if (this._isEven) {
el.removeClassName(this._altClassName);
} else {
el.addClassName(this._altClassName);
}
},
/*
* This works to stripe the child nodes of TABLE, TBODY, OL and UL elements.
*/
_stripeElements: function(els) {
els = $(els);
if (els.length == 0) {
return
}
var parent = els[0].parentNode;
this._isEven = true;
for (var i = 0; i < els.length; i++ ) {
if ((parent == els[i].parentNode) && (els[i].visible)) {
this._stripeElement(els[i]);
this._cycle();
}
}
},
/*
* TBODY is not necessary, but I recommend it. I debated about striping
* THEAD and TFOOT, but chose not to. Might be added later.
*/
_stripeTable: function(table) {
table = $(table);
if (table.getElementsByTagName("tbody")) {
var tableBodies = table.getElementsByTagName("tbody");
for (var i = 0; i < tableBodies.length; i++) {
this._stripeElements(tableBodies[i].getElementsByTagName("tr"));
}
} else {
this._stripeElements(table.getElementsByTagName("tr"));
}
},
/*
* This stripes OL and UL since they both have LI and only LI child nodes.
*/
_stripeNormalList: function(list) {
list = $(list);
this._stripeElements(list.getElementsByTagName("li"));
},
/*
* I have seen other function out there that can stripe DL, but they all
* assumed that each DT would have only one DD following it. That is not
* always the case, and not the case in the project that spawned this
* javascript.
*/
_stripeDefinitionList: function(list) {
list = $(list);
Element.cleanWhitespace(list);
var children = list.childNodes;
var previousDt;
for (var i = 0; i < children.length; i++) {
switch (children[i].tagName) {
case "DT":
if (children[i].visible) {
this._stripeElement(children[i]);
this._cycle();
}
previousDt = children[i];
break;
case "DD":
if (previousDt.visible) {
this._stripeElement(children[i]);
}
break;
}
}
}
};
/*
* This function will go ahead and stripe all the elligible elements on the
* page when the page first loads.
*/
function initZebraStripes() {
var toStripe = $$("dl.striped")
.concat($$("ol.striped"))
.concat($$("table.striped"))
.concat($$("ul.striped"));
toStripe.each(
function(el) {
ZebraStripes.stripe(el);
}
);
}
Event.onDOMReady(initZebraStripes);
// Or you could substitute a different loader:
//Event.observe(window, 'load', initZebraStripes)
Opinions expressed by DZone contributors are their own.
Comments