/*
 * ImageLoader v3.0 beta
 *     image preloader class for DHTML-Javascript 1.1 and
 *     DHTML-JScript 2.0
 *
 * by: Hyperion <noog@libero.it>
 *
 * Report bugs to the author
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public License
 * as published by the Free Software Foundation
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License for more details:
 * <URL: http://www.gnu.org/copyleft/lesser.html>
 *
 * NOTE: removing (but not modifying) the comments inside the code,
 * not including this block, won't be considered an actual modification
 * of the program
 */

/*
 * IMPORTANT: this file is distributed for historical purposes only. You
 * should use the latest release instead (preloader.js)
 */

function ImageLoader(){
/* private symbols */
	var _srcs = new Array();
	var _imgs = new Array();
	var _count = 0;
	var _done = 0;
	var _userdata = null;
	var _cancel = false;
	var _onerror_proc = null;
	var _onload_proc = null;
	var _oncomplete_proc = null;

/* private functions */
	/* stub for images' onerror event */
	function _onerror_stub(){
		if(_cancel){
			return false;
		}
		else{
			if(_onerror_stub.caller){
				cur = _onerror_stub.caller.id;
			}
			else{
				cur = -1;
			}

			var ret = _onerror_proc(cur, ++ _done, _count, _done / _count, _srcs[cur], _imgs[cur], _userdata);

			if(ret || (typeof(ret) == "undefined")){
				(_done == _count)?_oncomplete_proc(_userdata):void(0);
				return true;
			}
			else{
				_oncomplete_proc(_userdata);
				_abort();
				return false;
			}
		}
	}
	/* stub for images' onload event */
	function _onload_stub(){
		if(_cancel){
			return false;
		}
		else{
			if(_onload_stub.caller){
				cur = _onload_stub.caller.id;
				time = _onload_stub.caller.timestamp;
			}
			else{
				cur = -1;
				time = new Date();
			}

			var ret = _onload_proc(
				cur,
				++ _done,
				_count,
				_done / _count,
				_srcs[cur],
				_imgs[cur],
				time,
				(new Date()) - time,
				_userdata
			);

			if(ret || (typeof(ret) == "undefined")){
				(_done == _count)?_oncomplete_proc(_userdata):void(0);
				return true;
			}
			else{
				_oncomplete_proc(_userdata);
				_abort();
				return false;
			}
		}
	}
	/* stops & destroys any image */
	function _abort(){
		for(_i in _imgs) _imgs[_i] = null;
		_count = _done = 0;
		_cancel = true;
	}
	/* class entry point */
	function _main(args){
		if(args.length == 1) for(_i in args[0]){
			_srcs[_count] = args[0][_i];
			_count ++;
		}
		else for(var _i = 0; _i < args.length; _i ++, _count ++){
			_srcs[_count] = args[_i];
		}
	}

/* public events */
	/* fired when an image fails to load */
	this.onerror = function (cur, done, count, perc, src, img, userdata){return true}
	/* fired when an image successfully loads */
	this.onload = function (cur, done, count, perc, src, img, started, elapsed, userdata){return true}
	/* fired at the end of image loading */
	this.oncomplete = function (userdata){}

/* public functions */
	/* store pointers to event handlers and start loading images */
	this.load = function (vData){
		_onerror_proc = this.onerror;
		_onload_proc = this.onload;
		_oncomplete_proc = this.oncomplete;

		_userdata = vData;
		_cancel = false;

		for(_i in _srcs){
			_imgs[_i] = new Image();

			_imgs[_i].onerror = function (){_onerror_stub()};
			_imgs[_i].onload = function (){_onload_stub()};
			_imgs[_i].onerror.id = _imgs[_i].onload.id = _i;
			_imgs[_i].onload.timestamp = new Date();

			_imgs[_i].src = _srcs[_i];
		}
	}
	/* destroys images */
	this.unload = function (){
		if(arguments.length > 0) for(_i = 0; _i < arguments.length; _i ++){
			_imgs[_i] = null;
		}
		else for(_i in _imgs) _imgs[_i] = null;
	}
	/* exports _abort() */
	this.abort = _abort;
	/* destroys private objects */
	this.free = function (){
		_imgs = null;
		_srcs = null;
		_userdata = null;
	}
/* jump to the entry point */
	_main(arguments);
}
