/*global Element, Ajax, $ */
/*
 * Prototype plugin for a simple feedback interface.
 *
 * Injected DOM elements
   - feedback-form-container
       \
        - feedback-form-comment
        - feedback-form-email
        - feedback-form-go
        - feedback-form-loading-image
   - feedback-result-container
        \
        - feedback-result-title
        - feedback-result-message
        - feedback-result-ok
*/

(function($) {
	Element.addMethods({
		feedback: function(element, _options) {
			var options = {
				url: '',
				method: 'GET',
				source: '',
				defaultComment: 'Please provide your comments here.',
                defaultEmail: 'Email (Optional)',
				loadingImage: '',
				alert: {
					successMessage: 'Your feedback is very valuable to us. We look forward to improving our services from your suggestions.',
					errorMessage: 'It seems we are experiencing server difficulties. Your feedback is very important to us please try submitting again.',
					autoPosition: true,
					cssStyle: {
						'position': 'absolute',
						'display': 'none'
					}
				}
			},
			feedbackElem = undefined,
			lastComment = undefined;

			function isCommentSubmittable() {
				return ! (feedbackElem.comment.getValue() && feedbackElem.comment.getValue() != options.defaultComment && feedbackElem.comment.getValue() != lastComment);
			}
			function hideAlert() {
				feedbackElem.resultContainer.hide();
				feedbackElem.submit.disabled = isCommentSubmittable();
				feedbackElem.comment.disabled = false;
				feedbackElem.email.disabled = false;
			}
			function showAlert(title, message) {
				var alertWindow = feedbackElem.resultContainer;

				feedbackElem.resultTitle.innerHTML = title;
				feedbackElem.resultMessage.innerHTML = message;

				// determine center coordinates for child alert
				if (options.alert.autoPosition) {
					var x = element.getHeight() / 2 - alertWindow.getHeight() / 2,
					y = element.getWidth() / 2 - alertWindow.getWidth() / 2;
					alertWindow.setStyle({
						'top': x + 'px',
						'left': y + 'px'
					});
				}
				feedbackElem.submit.disabled = true;
				feedbackElem.comment.disabled = true;
				feedbackElem.email.disabled = true;
				alertWindow.show();
			}
			function send() {
				if (feedbackElem.comment.getValue().empty()) {
					showAlert("Oops!", "I'm sorry but I cannot accept a comment with nothing in it");
					return;
				}
                if (feedbackElem.email.getValue() === options.defaultEmail) {
                    feedbackElem.email.clear();
                }
				// disable submit button until request is done
				feedbackElem.submit.disabled = true;

				// If the user specified a loading gif display before the ajax request
				if (options.loadingImage) {
					feedbackElem.loading.show();
				}
				new Ajax.Request(options.url, {
					method: options.method,
					parameters: {
						source: options.source,
						feedback_email: feedbackElem.email.getValue(),
						feedback_comments: feedbackElem.comment.getValue()
					},
					onSuccess: function(transport) {
						if (transport.responseText.match(/^ok/)) {
							lastComment = feedbackElem.comment.getValue();
							showAlert("Thank You!", options.alert.successMessage);
						}
						else {
							showAlert("Oops!", options.alert.errorMessage);
						}
						feedbackElem.loading.hide();
					},
					onFailure: function(transport) {
						showAlert("Oops!", options.alert.errorMessage);
						feedbackElem.loading.hide();
					}
				});
			}
			/*
                This is the HTML that will be injected into the div
                ---------------------------------------------------
                <div id="feedback-form-container">
                    <textarea id="feedback-form-comment"></textarea>
                    <p>Your e-mail (Optional)</p>
                    <input type="text" id="feedback-form-email" />
                    <input type="button" id="feedback-form-submit" value="Submit" />
                    <img id="feedback-form-loading-image" style="display: none;" />
                </div>
                <div id="feedback-result-container" style="display:none;">
                    <div id="feedback-result-title" style="width: 100%; overflow: hidden;"></div>
                    <p id="feedback-result-message"></p>
                    <input type="button" id="feedback-result-ok" value="Okay" />
                </div>
            */
			function init() {
				// Parse user options
				options = Object.extend(options, _options);

				if (!options.url) {
					throw "You forgot to define the url parameter to the feedback plugin";
				}
				else if (!options.source) {
					throw "You forgot to define the source parameter to the feedback plugin";
				}

				// Inject the feedback form and modal dialog HTML above
				element.innerHTML = '<div id="feedback-form-container"><img id="feedback-form-image" src="/images/wl/feedback/help_us_improve_03.gif" /><textarea id="feedback-form-comment"></textarea><input type="text" id="feedback-form-email" /><input type="button" id="feedback-form-submit" value="send" /><img id="feedback-form-loading-image" style="display: none;" /></div><div id="feedback-result-container" style="display:none;"><div id="feedback-result-title" style="width: 100%; overflow: hidden;"></div><p id="feedback-result-message"></p><input type="button" id="feedback-result-ok" value="Okay" /></div>';

				feedbackElem = {
                    container: $('feedback-container'),
					inputContainer: $('feedback-form-container'),
					email: $('feedback-form-email'),
					comment: $('feedback-form-comment'),
					submit: $('feedback-form-submit'),
					loading: $('feedback-form-loading-image'),
					resultContainer: $('feedback-result-container'),
					resultMessage: $('feedback-result-message'),
					resultTitle: $('feedback-result-title'),
					resultOK: $('feedback-result-ok')
				};

				// Set loading image source
				if (options.loadingImage) {
					feedbackElem.loading.src = options.loadingImage;
				}
				// Set the default comment if nothing is set
				if (!feedbackElem.comment.getValue()) {
					feedbackElem.comment.setValue(options.defaultComment);
				}
				// Set the default email if nothing is set
				if (!feedbackElem.email.getValue()) {
					feedbackElem.email.setValue(options.defaultEmail);
				}
				// Determine if we can submit
				feedbackElem.submit.disabled = isCommentSubmittable();
				lastComment = feedbackElem.comment.getValue();

				// Set style information
				// position main parent to be relative for the alert box
				if (options.alert.autoPosition) {
					element.setStyle({
						'position': 'relative'
					});
				}
				// apply style information from options
				feedbackElem.resultContainer.setStyle(options.alert.cssStyle);

				//Register handlers
				feedbackElem.resultOK.observe('click', hideAlert);
				feedbackElem.comment.observe('click', function() {
					if (feedbackElem.comment.getValue() == options.defaultComment) {
						feedbackElem.comment.clear();
					}
					feedbackElem.submit.disabled = isCommentSubmittable();
				});
                feedbackElem.comment.observe('blur', function() {
                    if (feedbackElem.comment.getValue() === '') {
						feedbackElem.comment.setValue(options.defaultComment);
					}
                });
                feedbackElem.email.observe('click', function() {
                    if (feedbackElem.email.getValue() == options.defaultEmail) {
						feedbackElem.email.clear();
					}
                });
                
                feedbackElem.email.observe('blur', function() {
                    if (feedbackElem.email.getValue() === '') {
						feedbackElem.email.setValue(options.defaultEmail);
					}
                });
                
				feedbackElem.comment.observe('keyup', function() {
					feedbackElem.submit.disabled = isCommentSubmittable();
				});
				feedbackElem.submit.observe('click', send);
                
                feedbackElem.container.style.visibility = 'visible';
			}

			init();
		}
	});
})($);


