function PaginationItem( parent, label, value ) {
	this.onClick		= function( evt ) {
		evt.preventDefault();
		evt.data.ref.parent.setCurrentPage( evt.data.ref.value );
	}
	this.render			= function() {
		var li	= jQuery( '<li />' );
		if ( this.selected ) {
			li.addClass( 'selected' );
			this.element	= jQuery( '<span>' + this.label + '</span>' );
		} else {
			this.element	= jQuery( '<a>' + this.label + '</a>' );
			this.element.bind( 'click', { ref: this }, this.onClick );
		}
		li.append( this.element );

		return li;
	}
	this.remove			= function() {
		var ref	= this;
		this.element.parent().fadeOut( function() {
			ref.disabled();
			ref.element.parent().remove();
		} );
	}
	this.disabled		= function() {
		if ( !this.element.hasClass( 'disabled' ) ) {
			this.element.addClass( 'disabled' );
		}
		this.element.unbind( 'click', this.onClick );

		return this;
	}
	this.enabled		= function() {
		this.element.removeClass( 'disabled' );
		this.element.bind( 'click', { ref: this }, this.onClick );

		return this;
	}
	this.setSelected	= function( bool ) {
		if ( this.element != null ) {
			if ( !bool ) {
				if ( this.selected ) {
					this.element.parent().removeClass( 'selected' );
					var r	= jQuery( '<a>' + this.label + '</a>' );
					this.element.replaceWith( r );
					this.element	= r;
					this.enabled();
				}
			} else {
				if ( !this.selected ) {
					this.element.parent().addClass( 'selected' );
					var r	= jQuery( '<span>' + this.label + '</span>' );
					this.element.replaceWith( r );
					this.element	= r;
					this.disabled();
				}
			}
		}

		this.selected	= bool;

		return this;
	}
	this.setValue	= function( value ) {
		this.value	= value;

		return this;
	}

	this.parent		= parent;
	this.label		= label;
	this.value		= value;
	this.element	= null;
	this.selected	= false;

	return this;
}
function PaginationBar( class_name, max_page ) {
	this.repaint		= function() {
		if ( this.items.length <= 1 ) {
			this.container.parent().slideUp();
			this.visible	= false;
			return true;
		}
		if ( !this.visible ) {
			this.container.parent().slideDown();
			this.visible	= true;
		}

		this.jump.prev.setValue( this.current_page - 1 );
		if ( 0 == this.current_page ) {
			this.jump.prev.disabled();
		} else {
			this.jump.prev.enabled();
		}

		for( var i=0; i<this.items.length; i++ ) {
			if ( i == this.current_page ) {
				this.items[ i ].setSelected( true );
			} else if ( this.items[ i ].selected ) {
				this.items[ i ].setSelected( false );
			}
		}

		this.jump.next.setValue( this.current_page + 1 );
		if ( this.max_page - 1 == this.current_page ) {
			this.jump.next.disabled();
		} else {
			this.jump.next.enabled();
		}
	}
	this.insertBefore	= function( jElement ) {
		jElement.before( this.container.parent().hide() );
		this.repaint();
	}
	this.insertAfter	= function( jElement ) {
		jElement.after( this.container.parent().hide() );
		this.repaint();
	}
	this.render			= function() {
		if ( null != this.container ) {
			this.container.remove();
		}
		this.container	= jQuery( '<ul class="' + this.class_name + '" />' ).wrap( jQuery( '<div class="pagination" />' ) );

		this.jump.prev	= new PaginationItem( this, '<', this.current_page - 1 );
		this.container.append( this.jump.prev.render() );

		for( var i=0; i<this.max_page; i++ ) {
			this.items[ i ]	= new PaginationItem( this, i + 1, i );
			var	li_node		= this.items[ i ].render();
			if ( i < this.max_page - 1 ) {
				li_node.append( '.' );
			}
			this.container.append( li_node );
		}

		this.jump.next	= new PaginationItem( this, '>', this.current_page + 1 );
		this.container.append( this.jump.next.render() );
	}
	this.getCurrentPage	= function() {
		return this.current_page;
	}
	this.setCurrentPage	= function( current_page ) {
		if ( this.current_page < 0 || this.current_page > this.max_page ) {
			return false;
		}
		if ( current_page == this.current_page ) {
			return false;
		}

		this.current_page	= current_page;

		this.notify( PaginationBar.Events.PaginationBarUpdate, {} );
	}
	this.setContainer	= function( jContainer ) {
		this.container	= jContainer;
	}
	this.setMaxPage		= function( max_page ) {
		this.max_page		= max_page;
		for( var i=0; i<this.items.length; i++ ) {
			if ( i < this.max_page ) {
				continue;
			}
			this.items[ i ].remove();
			this.items.splice( i, 1 );
			//	les lignes ci-dessous "unbind" l'element
			//	il faut trouver une autre solution
			/*
			if ( this.items.length > 0 ) {
				var element	= this.items[ this.items.length - 1 ].element;
				this.items[ this.items.length - 1 ].element.parent().empty().append( element );
			}
			*/
		}
		this.repaint();
	}

	this.container		= null;
	this.class_name		= class_name;
	this.current_page	= 0;
	this.max_page		= max_page;
	this.items			= [];
	this.visible		= false;
	this.jump			= {
		prev:	null,
		next:	null
	}

	jQuery.extend( this, new Observable() );
}
PaginationBar.Events	= {
	PaginationBarUpdate:		'onPaginationBarUpdate'
}
