var Quiz = {
	
    /**
     * Part one of set up: adds listener(s) and loads stuff etc. Second phase of
     * initialisation is done once storage values are ready for use i.e. VLE
     * object calls this object's methods as callbacks.
     */
	init: function() {
		var submit_button = document.getElementById("submit_quiz_button"),
		    that = this;		
		
		this.reSizeIframe();
		if (submit_button !== null) {
			if (typeof window.addEventListener === 'function') {			
                submit_button.addEventListener('click', function(evt) {
                    return that.collectAndPassDataToStorage(evt);
                }, false);
			} else if (typeof document.attachEvent === 'function') {				
				submit_button.attachEvent("onclick", function(evt) {
				    return that.collectAndPassDataToStorage(evt);
				});
			} else {
                submit_button["onclick"] = function(evt) {
                    return that.collectAndPassDataToStorage(evt);	
                };			
			}
		}
		
	},
	
	/**
	 * Resize the iframe to fit the contents
	 */
	reSizeIframe: function () {
	    var activity_container = document.getElementById("container");
	    
	    frame_height = activity_container.offsetHeight + 20,
	    iframe = window.frameElement;

	    if (iframe !== null) {
	    	iframe.height = frame_height;
	    }		
	},
	
	/**
	 * Get server value,  if set, of the same name as document.body.id and passes this value
	 * on to another method that sets up the state of the app, mirror's below for local storage
	 * @return {Function}
	 */
    getVleData: function() {
    	var that = this;
    	
    	return function (values) {  		
            if (values !== null && values[document.body.id] !== "") {  // Second condition handles VLE bug
            	that.setUpCheckboxes(values[document.body.id]);	
            }
    	};
     },
    
    /**
     * Gets a local storage value, if set, of the same name as document.body.id and passes this
     * value on to another method that sets up the state of the app
     * @return {Function}
     */
    getLocalData: function() {
        var that = this;
    
        return function(message) {
        	var local_storage_value = null;
            if (message === null) {
            	if (window.localStorage) {
            		local_storage_value = window.localStorage.getItem(document.body.id);          		
            		if (local_storage_value !== null) {
                    	that.setUpCheckboxes(local_storage_value);           			
            		}
            	}           	
            } else {
            	alert("Error saving data.  Check connection's OK.");
            }
        };
    },
    
    /** Checks previously checked checkboxes.
     * @param String checked_checkboxes Comma separated list of the checked checkboxes
     */
    setUpCheckboxes: function(checked_checkboxes) { 	
    	var checkbox_array = checked_checkboxes.split(","),
    	i = 0,
    	max = checkbox_array.length,
    	checkbox = {},
    	feedback_counter = 0;
 	
    	for (; i < max; i += 1) {
    	    checkbox = document.getElementById("a" + checkbox_array[i]);
    	    if (checkbox !== null) {
        	    checkbox.checked = true;
        	    feedback_counter += 1;
    	    }		
    	}
    	
    	this.setFeedback(feedback_counter);
    },
    
    /**
     * Set feedback option.  Counts checked checkboxes and displays a rating statement.
     * @param {Number} ticked_checkbox_count Number of checked checkboxes
     */
    setFeedback: function(ticked_checkbox_count) {
    	var feedback_elem = {},
    	feedback_class = " feedback",
    	answer_container = document.getElementById("answer_container"),
    	answers = answer_container.getElementsByTagName("p"),
	    checkboxes_container = document.getElementById("assertiveness-quiz"),
	    checkboxes = checkboxes_container.getElementsByTagName("input"),
    	i = 0,
    	max = answers.length,
    	feedback = {},
    	remembered_lower_boundary = 0;

    	// Reset all feedback paragraphs
    	for (; i < max; i += 1) {
            answers.item(i).className = "rating";
    	}
    	
    	// Reveal feedback dependent on how many checkboxes are checked.
    	// Loop through the answers and find the one that should be shown given the
    	// amount of checkboxes checked
    	for (i = 0; i < max; i += 1) {		
    		feedback = this.parseFeedbackId(answers[i].id);
    		// Need to interject to set the last boundary in case it was omitted
    		if (i === (max - 1)) {  			
    			if (isNaN(feedback['boundary'])) {  				
    			    feedback['boundary'] = checkboxes.length;
    			}
    		}
    		if (ticked_checkbox_count >= remembered_lower_boundary &&
    				ticked_checkbox_count <= feedback['boundary']) {			
    			feedback_elem = document.getElementById(feedback['id']);
    			feedback_elem.className += feedback_class;
    			remembered_lower_boundary = feedback['boundary'] + 1;
    		}
    	}
    	
    	this.reSizeIframe();
    },
    
    /**
     * Collects the data to save and passes it to various storage places
     * @param Object evt
     */
    collectAndPassDataToStorage: function(evt) {
    	var server_data = {},
    	    checkboxes_container = document.getElementById("assertiveness-quiz"),
    	    checkboxes = checkboxes_container.getElementsByTagName("input"), // Contains checkboxes
    	    i = 0,
    	    max = checkboxes.length,
    	    checkbox_values = [];
    	 	    
	    // Loop through all the checkboxes and add the position of the checked ones to an array
        for (; i < max; i += 1) {
        	if (checkboxes.item(i).type === 'checkbox') {
        	    if (checkboxes.item(i).checked === true) {
        	        checkbox_values.push(i);	
        	    }	
        	}
        }
        
        // Set feedback
        this.setFeedback(checkbox_values.length);
        
        // Pass values as string for storing
    	server_data[document.body.id] = checkbox_values.join(",");   	
        VLE.set_server_data(true, server_data, function() {
        	// Success, don't need to do anything
        }, this.saveLocalData(server_data));  	
    },
    
    /**
     * Saves the checkboxes' state locally if VLE storage isn't present and VLE object's message is null
     * @param Object server_data The name/value pairs to save to local storage
     */
    saveLocalData: function(server_data) {
        var i = "";
        return function(message) {
        	if (message === null) {
                if (window.localStorage) {
            		for (i in server_data) {
            		    if (server_data.hasOwnProperty(i)) {
            		    	if (server_data[i] === "") {
            		    		window.localStorage.removeItem(i);
            		    	} else {
                		    	window.localStorage.setItem(i, server_data[i]);            		    		
            		    	}
            		    }
            		}
            	}        		
        	}      	
        };
    },
    
    /** Parse the ID of the feedback tags. Splits the string on the first hyphen and returns
     * it an object of the id and the upper boundary for showing that particular feedback
     * @param {String} raw_id
     * @return {Object} The ID of the feedback and its upper boundary
     */
    parseFeedbackId: function (raw_id) {
    	var split_id = raw_id.split('-'),
    	    formatted_id = {},
    	    i = 0,
    	    max = split_id.length;
    	
    	formatted_id.id = raw_id; // This might change at some point
    	formatted_id.boundary = parseInt(split_id[1], 10);

        return formatted_id;
    }
};

Quiz.init();

// App saves state so makes sense for the call to VLE object start the action...
VLE.get_server_data(true, [document.body.id], (Quiz.getVleData()), (Quiz.getLocalData()));