$Button = new Class() ({
	__init__: function ($button) {
		this.initCache($button);

		if (! this.$button.hasClass('ui-button ui-widget')) {
			this.initText();
			this.initIcons();
			this.initContainer(this.getButtonLabelType(this.getIconType(), this.hasText()));
		}
		
		return this.$button;
	},

	initCache: function ($button) {
		if (! ($button instanceof jQuery)) {
			$button = jQuery($button);
		}

		this.$button = $button;
		this.$text = $button.children('.ui-button-text');
		this.$alt = $button.children('.ui-button-alt');
		this.$icons = $button.children('[class|=ui-icon]');
	},

	initText: function () {
		if (! this.hasText()) {
			// .icon-only, set tooltip on <button>, then hide ui-button-text <span>
			this.$button.attr('title', this.$alt.text());
			this.$alt.addClass('ui-button-text');
		}
	},
	
	initContainer: function (buttonLabelType) {
		if (buttonLabelType.match(/^ui-button-text-icon/)) {
			// backwards compat. (ui-1.8.4 added specificity on this class, so we need to add the base AND targetted class)
			buttonLabelType += ' ui-button-text-icon';
		}

		// initialize classes on <button>
		this.$button.addClass('ui-button ui-widget ui-state-default ' + buttonLabelType);
		
		if (this.$button.attr('selected') !== undefined || this.$button.data('selected') !== undefined) {
			this.$button.addClass('ui-state-active');
		}

		if (this.$button.attr('disabled') !== undefined || this.$button.data('disabled') !== undefined) {
			this.$button.addClass('ui-state-disabled');
		}
	},

	initIcons: function () {
		// .icon-primary == left  // .icon-secondary == right
		this.$icons.filter(':eq(0)').addClass('ui-icon ui-button-icon-primary');
		this.$icons.filter(':eq(1)').addClass('ui-icon ui-button-icon-secondary');
	},
	
	hasText: function () { return this.$text.length !== 0; },
	getIconType: function () {
		if (this.$icons.length > 1) {
			return 'both';
		}

		if (! this.$icons.length) {
			return;
		}

		return this.$icons.hasClass('ui-button-icon-primary') ? 'primary' : 'secondary';
	},



	getButtonLabelType: function (iconType, hasText) {
		var singleIcon = iconType && iconType !== 'both';
		var type = '';

		if (hasText && singleIcon) {
			type = 'text-icon-' + iconType;
		} else if (hasText) {
			type = iconType ? 'icons' : 'text-only';
		} else {
			type = iconType === 'both' ? 'icons-only' : 'icon-only';
		}

		return 'ui-button-' + type;
	}
});

$Button.Static({
	create: function (buttonType, label, primaryIcon, secondaryIcon, iconsOnly) {
		var $button = jQuery('<'+buttonType+'>');
		
		if (label) { jQuery('<span>').addClass('ui-button-' + (iconsOnly ? 'alt' : 'text')).html(label === undefined ? '&nbsp;' : label).appendTo($button); }
		if (primaryIcon) { jQuery('<span>').html('&nbsp;').addClass(primaryIcon).appendTo($button); }
		if (secondaryIcon) { jQuery('<span>').html('&nbsp;').addClass(secondaryIcon).appendTo($button); }
		
		return new $Button($button);
	},

	initializeAllButtons: function () {
		jQuery('button > .ui-button-text, a > .ui-button-text, button > [class|=ui-icon], a > [class|=ui-icon]').each(function (i, e) {
			// instantiating this $Button class will set everything up as it should be
			var $button = new $Button(jQuery(e).parent());
		});
	},

	initializeLiveButtonEvents: function () {
		jQuery('.ui-state-default:not(.ui-state-disabled)')
			.live('focus',		function () { jQuery(this).addClass('ui-state-focus'); })
			.live('blur',		function () { jQuery(this).removeClass('ui-state-focus'); })
			.live('mousedown',	function () { jQuery(this).addClass('ui-state-active'); })
			.live('mouseup',	function () { jQuery(this).removeClass('ui-state-active'); })
			.live('mouseover',	function () { jQuery(this).addClass('ui-state-hover'); })
			.live('mouseout',	function () { 
				if (jQuery(this).attr('selected') === undefined && ! jQuery(this).hasClass('ui-tabs-selected')) {
					jQuery(this).removeClass('ui-state-hover ui-state-active ui-state-focus');
				}
			});
	}
});

$Checkbox = new Class() ({
	__init__: function ($checkbox) {
		if (! $checkbox) {
			return this;
		}
		
		var c = $checkbox.data('$Checkbox');
		if (c) {
			return c;
		}
		
		this.$checkbox = null;
		this.$container = null;
		
		this.add($checkbox);
	},
	
	add: function ($checkbox) {
		this.render($checkbox);
		this.bind($checkbox);
		this.handleCheckboxChange($checkbox);
	},
	
	toggleChecked: function () {
		this.checked(! this.checked());
	},
	
	toggleEnabled: function () {
		this.enabled(! this.enabled());
	},
	
	check:		function () { this.checked(true); },
	uncheck:	function () { this.checked(false); },
	checked: function (checked) {
        console.log(checked);
		if (checked === undefined) {
			return Boolean(this.$checkbox.attr('checked'));
		}

		this.$checkbox[checked ? 'attr' : 'removeAttr']('checked', 'checked');
		this.$container[checked ? 'addClass' : 'removeClass']('checked');
	},
	
	enable:		function () { this.enabled(true); },
	disable:	function () { this.enabled(false); },
	enabled: function (enabled) {
		if (enabled === undefined) {
			return ! this.$checkbox.attr('disabled');
		}
		
		this.$checkbox[(! enabled) ? 'attr' : 'removeAttr']('disabled', 'disabled');
		this.$container[(! enabled) ? 'addClass' : 'removeClass']('disabled');
	},
	
	render: function ($checkbox) {
		var $container = $checkbox.parent();
		
		if (this.$checkbox && this.$container) {
			$checkbox = this.$checkbox.add($checkbox);
			$container = this.$container.add($container);
		}
		
		this.$checkbox = $checkbox.data('$Checkbox', this);
		this.$container = $container.addClass('ui-button-checkbox');
	},
	
	bind: function ($checkbox) {
		var self = this;
		$checkbox.bind('change click', function () { self.handleCheckboxChange(jQuery(this)); });
	},
	
	handleCheckboxChange: function ($checkbox) {
		this.checked(Boolean($checkbox.attr('checked')));
		this.enabled(! $checkbox.attr('disabled'));
	}
});

$ThiIconLarge = {
	create: function (type, label, value, labelSuccess, valueSuccess) {
		var $container = jQuery('<span>').addClass('thi-icon-large').addClass(type);
		
		if (label) {
			jQuery('<span>').addClass('label').addClass(labelSuccess === undefined ? '' : (labelSuccess ? 'success' : 'failure')).html(label).appendTo($container);
		}
		
		if (value) {
			jQuery('<span>').addClass('value').addClass(valueSuccess === undefined ? '' : (valueSuccess ? 'success' : 'failure')).html(value).appendTo($container);
		}
		
		return $container;
	}
};

