/**
 *
 * @author a.novikov
 * @version 1.0.2
 *
 * Depends on library.js
 *
 * to get options use $(...).simpleForm('option', <option name>);
 * to set options use $(...).simpleForm({options object}); or $(...).simpleForm('option', <option name>, <option value>);
 *	options:
 *		successCallback				- callback, fires on success, receives responce body.
 *			example:
 *				var successCallback = function( data ) {
 *					alert( data );
 *				};
 *		errorArrayCallback	- callback, fires when errors received as array.
 *			example:
 *				var errorArrayCallback = function( errors ) {
 *					alert( errors.join(',') );
 *				};
 *		errorNestedCallback			- callback, fires when errors received as non array, in common it is nested objects.
 *			example:
 *				var errorNestedCallback = function( errors ) {
 *					alert( 'Some errors happened!' );
 *				};
 *		beforeHandleErrorsCallback:	- callback, fires before any error callback
 *		afterHandleErrorsCallback:	- callback, fires after any error callback
 *		errorCallback				- entire error callback, fires on any error, it manipulates with other error callbacks
 * 
 * to destroy form use $(...).simpleForm('destroy');
 *
 */

(function(Lib, $){
	var SimpleForm = function(form) {
		this.form = form;
		this.settings = {
			form: form,
			errorFieldClass: 'border_red',
			errorMessageClass: 'form_error_message',
			errorContainer: '.form_error_container',
			errorMessageText: 'Заполните, пожалуйста, поля, отмеченные звёздочкой',
			successCallback: function(data) {
				$(form).replaceWith("<div class='ajax_responce'>"+data+"</div>");
			},
			errorNestedCallback: function(errors) {
				var errorMessage = $("<div />").addClass(this.errorMessageClass).html(this.errorMessageText);

				$(form).find(this.errorContainer).append(errorMessage);
				
				for(var fieldName in errors) {
					$(form).find("[name='"+fieldName+"']").addClass(this.errorFieldClass);
				}
			},
			errorArrayCallback: function(errors) {
				Lib.ErrorHandlers.Ajax.handlerArray(errors);
			},
			beforeHandleErrorsCallback: function(errors) {
				$(form).find('.'+this.errorFieldClass).removeClass(this.errorFieldClass);
				$(form).find(this.errorContainer).empty();
			},
			afterHandleErrorsCallback: function(errors) {
				
			},
			errorCallback: function(errors) {
				this.beforeHandleErrorsCallback(errors);
				if ($.isArray(errors)) {
					this.errorArrayCallback(errors);
				}
				else {
					this.errorNestedCallback(errors);
				}
				this.afterHandleErrorsCallback(errors);
			}
		};

		this.bind();
	}

	SimpleForm.prototype = {
		bind: function() {
			var settings = this.settings;
			var form = this.form;

			$(form).ajaxForm(function(responceText) {
				var errorCallback = $.proxy(settings, 'errorCallback');
				var successCallback = $.proxy(settings, 'successCallback');
				Lib.Ajax.wrapText(responceText, successCallback, errorCallback);
			});
		},
		setOptions: function(options) {
			$.extend(this.settings, options);
		},
		setOption: function(option, value) {
			if ( !(option in this.settings) ) {
				$.error('Invalid option');
			}
			this.settings[option] = value;
		},
		getOption: function(option) {
			if ( !(option in this.settings) ) {
				$.error('Invalid option');
			}
			return this.settings[option];
		},
		destroy: function() {
			this.unbind();
		},
		unbind: function() {
			$(this.form).ajaxFormUnbind();
		}
	};
	
	var Adapter = function(simpleForm) {
		this.simpleForm = simpleForm;
	};
	
	Adapter.prototype = {
		init: function(options) {
			this.simpleForm.setOptions(options);
		},
		option: function(option, value) {
			var argCount = arguments.length;
			
			if (argCount == 1) {
				return this.simpleForm.getOption(option);
			}
			else if (argCount == 2) {
				this.simpleForm.setOption(option, value);
			}
			else {
				$.error('Invalid arguments');
			}
		},
		destroy: function() {
			this.simpleForm.destroy();
		}
	};

	Lib.bindClassToJQuery(SimpleForm, 'simpleForm', Adapter);

})(NLib, jQuery);
