function _body_defineSheet(cssStr, id) {
	var style = document.getElementById(id);
	if (style == null) {
		style = document.createElement("style");
		style.setAttribute("type", "text/css");
		style.setAttribute("id", id);
		if(style.styleSheet){// IE
			style.styleSheet.cssText = cssStr;
		} else {
			var cssText = document.createTextNode(cssStr);
			style.appendChild(cssText);
		}
		document.getElementsByTagName("head")[0].appendChild(style);
	}
}

var PeriodicalExecuterNamed = Class.create();

PeriodicalExecuterNamed.ids = new Array();

PeriodicalExecuterNamed.finish = function(key) {
	if (PeriodicalExecuterNamed.ids[key] != undefined && PeriodicalExecuterNamed.ids[key] != null) {
	    clearInterval(PeriodicalExecuterNamed.ids[key]);
		PeriodicalExecuterNamed.ids[key] = null;
	}
}

PeriodicalExecuterNamed.prototype = {
  initialize: function(callback, frequency, key) {
    this.callback = callback;
    this.frequency = frequency;
	this.key = key;
    this.currentlyExecuting = false;
	
    this.registerCallback();
  },

  registerCallback: function() {
	this.finish();
	if (this.frequency > 0) {
    	PeriodicalExecuterNamed.ids[this.key] = setInterval(this.onTimerEvent.bind(this), this.frequency * 1000);
	}
	this.onTimerEvent();
  },

  finish: function() {
	  PeriodicalExecuterNamed.finish(this.key);
  },
  
  onTimerEvent: function() {
    if (!this.currentlyExecuting) {
      try {
        this.currentlyExecuting = true;
        this.callback();
      } finally {
        this.currentlyExecuting = false;
      }
    }
  }
}
