/* 
 * This is the main MVC client javascript file. 
 */

/*
 * authInfo contains the Session Data sent back to the client
 * on an Auth Status OR a sucessful login.
 */

var authInfo;
var managedCourse = 0;
var viewUser      = 0;
var entityState;
var fakingAge = -1;

var ROLE_STUDENT  = 'Student';
var ROLE_EDUCATOR = 'Educator';

var DEBUG = true;

var classicView = false;

var studentFullName = '';
var studentClassId  = '';
var firstEvent = '';

// Error Handler
tErr = new mvcErrorHandler();
tErr.setObject("mvcRender");

$(function(){ // Jquery starts

    $("#btnLogout").hide();
    $("body").hide();
    
    /*
     * Check our status... are we logged in?
     */

     mySSO = new ajaxSSO();
     mySSO.getAuthStatus(statusCallback, statusErrorCallback);
       
    /*
     * Login
     */
    $('#register').submit(function(event) {
        event.preventDefault();
        mySSO = new ajaxSSO();

        // Set the Site ID
        mySSO.setSiteId(authInfo.siteid);

        if($("#uname").val().length == 0 || $("#pwd").val().length == 0) {
            msgBox('warning', 'You must enter a user name and password');
        } else {
            var rslt = mySSO.ssoLogin($("#uname").val(), $("#pwd").val(), loginErrorCallback);
        }
        
        return false;
    });
    
    // Save course schedule
    $("#manage_course_schedule").submit(function(e)
    {
        e.preventDefault();
        $('[type="submit"]', this).attr('disabled', 'disabled');
        saveSchedule();
        $('[type="submit"]', this).removeAttr('disabled');        
    });
    
    /* Open/Close Videos */
    $('#openVideos').click(function(){
            showVids();
            return false;
    });

    $('#closeVideos').click(function(){
            hideVids();
            return false;
    });

    $('#newAlert').limit('1000','#charsLeft');
    
            
    /*
     *
    $('a.defined').hover(function(){
        alert("Hover");
        var defText = $(this).attr('rel');
        $('#defbox').html(defText);
        var defPos = $(this).position();
        var boxH = $('#momentDeets div.definitions').height();
        $('#momentDeets div.definitions').hide();
        $('#momentDeets div.definitions').css({
                'left' : ( defPos.left - 75 )+'px',
                'top' : ( defPos.top - ( boxH ) )+'px' 
        });
        $('#momentDeets div.definitions').show();
        return false;
    },
        function(e) {
            $("#defbox").empty();
            $('#momentDeets div.definitions').hide();
        }
    );
    */

}); // Jquery ends

function loadHelpTabs()
{   
    var searchin  = '#help';
    var cls       = 'current';
    $('.tabnav.clearfix li a', searchin).click(function()
    {                    
        $('.tabnav li a,div', searchin).removeClass(cls);        
        $($(this).attr('href')).addClass(cls);
        $(this).addClass(cls);
        return false;
    });    
}

/**
 * Logs the message in the console if the constant DEBUG is set to true
 */
function log(message)
{
    if (DEBUG == true) {
        if (typeof(console) !== 'undefined') {
            console.log(message);
        }        
    }
}

$('.defined').live('mouseenter', function(e){

    var $this = $(this);
    var pos = savePos = {left:e.pageX, top:e.pageY};
    $("#defbox").remove();

    $this.css({display:'inline-block'});

    var box = $('<div class="definitions"><div><dl id="defbox">' + $this.attr('rel') + '</div></div>');

    $('body').append(box);

    box.css({position:'relative'}).show().width($('#defbox').width());



    pos['top'] =  $this.offset().top - box.height();//pos.top - $('#defbox').height() - $this.height() - 30;
    pos['left'] = pos.left - ($('#defbox').width() / 2);

    box.offset(pos);

    $this.unbind('mouseleave').bind('mouseleave', function(e){
        
            box.remove();
        
    })


});

function setVidTab(which) {
    var tDiv = "#video" + which;
    var tHref = "#href_video" + which
    $('.tabnav li a').removeClass('current');
    $('.tabs div').removeClass('current');
    $(tDiv).addClass('current');
    $(tHref).addClass('current');
    return false;
}


function saveAct() {
    
    
    // Now process the save...
    if($("#nextBtnText").text() == "Resume Questions") {
        fakingAge = -1;
        getEntityHistory();
        // tRender.renderEntityTimelineAge(entityState.age_months, false);
        displayEntitySWF();
        return false;
    }
    
    /*
     *  Disable the button, provide some visual queue.
     *
    */
    $("#subDecision").attr("disabled", "disabled");
    $("#nextBtnText").empty();
    $("#nextBtnText").append("<div id='mvcLoader'><img src='/assets/images/basics/loading.gif' border='0' style='height: 16px;'/></div>");
    
    
    tEntity = new ajaxEntity;
    if($("#tt_activity_type").val() == "Event") {
       tEntity.saveEvent($("#tt_answer_id").val(), $("#tt_sched_id").val(), activitySaved, loginErrorCallback);
       return false;
    }
    if($("#tt_activity_type").val() == "Report") {
        tEntity.saveReport($("#tt_report_id").val(), $("#tt_sched_id").val(), activitySaved, loginErrorCallback);
        return false;
    }
    if($("#tt_activity_type").val() == "Question") {
       /*
        * Determine the selected answer
        */
       var ansNum = $("input[@name=answer]:checked").val();
              
       if (typeof ansNum != 'undefined') {
           tEntity.saveQuestion(ansNum, $("#tt_sched_id").val(), activitySaved, loginErrorCallback);
           return false;
       } else {          
           msgBox('warning', 'Please select an answer');
           $("#subDecision").removeAttr('disabled');
           $("#nextBtnText").empty();
           $("#nextBtnText").append("Next");
           return false;
       }
                     
    }
    if($("#tt_activity_type").val() == "Assignment") {
                     
       var answers = [];
       var saveIt = true;
       // Set this true and user's must enter something for each question.
       var enforceEntry = false;
       $('textarea[name^="def"],textarea[name^="alt"]').each(function(){           
           var data = $(this).data('info');
           if($(this).val().length < 10 && enforceEntry) {
               saveIt = false;
               msgBox("warning", "You must supply a full answer for each assigned question.");
               $("#subDecision").removeAttr('disabled');
               $("#nextBtnText").empty();
               $("#nextBtnText").append("Next");
               return false;
           }
           answers.push({name: data.name, id: data.id, value: $(this).val()});
       });
                                   
       if(saveIt) tEntity.saveAssignment($("#tt_assignment_id").val(), $("#tt_sched_id").val(), answers, activitySaved, loginErrorCallback);
       return false;
    }
    return false;
}

function showVids() {
    $('#momentDeets').hide();
    $('#momentVideos').show();
    return false;
}

function hideVids() {
    var player = $('#momentVideos object')[0];
    if (typeof player.sendEvent != 'undefined') {
        player.sendEvent('STOP');
    }
    $('#momentDeets').show();
    $('#momentVideos').hide();
    return false;
}
/*
 * Handles a newly added class.
 *
 * @param json A object with the result.
 *
 */
function classAdded(json) {

    if (json.result == 200) {
        tRender = new mvcRender();
        tRender.renderClassAdded(json);
    }
    
    // Should there be a case for failure here? JP
}

/*
 * Function deletes a class from this instructor's list.
 * @param cid int Course ID
 * @param cname string The Name of the course.
 */

function deleteClass(cid, cname) {

    input_box = confirm("Are you sure you want to delete this class?\nClass Name: " + cname + "\nThis will delete all students in this class as well.  Click Cancel or OK to Continue.");
    if (input_box == true){ // Output when OK is clicked
        myCourse = new ajaxCourse();
        myCourse.deleteCourse(cid, courseDeleted, childStatusErrorCallback)
    }
    return false;
    
}

/*
 * Function Handles the response from a course deletion
 */
function courseDeleted(json) {
    if(json.result == 400) {
        //failed
        msgBox('error', json.message);
    } else {
        //getCourseList();
        var cdom = "#class-" + json.CourseId;
        $(cdom).remove();

        $('#studentRoster #filterByClass a[rel="'+json.CourseId+'"]').remove();
        $('#studentRoster tbody').empty();
        $('#studentRoster h2 span').text('Select Class');
    }
    
}

/*
 * Function fetches the current instructor's class list.
 */

function getCourseList() {
    
    if (authInfo.role == ROLE_EDUCATOR) {
        myCourse = new ajaxCourse();
        myCourse.listCourses(loadClassList, childStatusErrorCallback);
        return true;
    }
    
    return false;
}


/*
 * Handles callback for an Auth Status Request.
 *
 * @param json A Object with the relevant user/account information.
 */
function statusCallback(json) {

    if (json.result == 200) {
        // We are logged in.
        // Set the global variables for this user
        authInfo = json;       
        if(location.pathname == "/") window.location = "/dashboard.html";

        // Evaluate the current document name and do what is required.        
        evalLocation();
        
        /*
         * Set Our UI elements
         */
        setUserWelcome();
    } else if(json.result == 201) {
        // Do nothing... they need to stay here and log in.
        authInfo = json;
        if(location.pathname != "/") {
            window.location = "/";
        } else {
            $("body").show();
        }
    } else if(json.result == 400){
        // Need to re-direct to the SSO Check Login Page
        window.location = json.sso_check_login;
    } else if(json.result == 202) {
        // Login failed.
        $("#login_status").empty();
        $("#login_status").append("Login Failed. Try Again");
        authInfo = json;
        if(location.pathname != "/") {
            window.location = "/";
        } else {
            $("body").show();
        }
    }
}

function isSessionExpired(json) {
    if(json.result == "400" && json.message == "Session timed out.") window.location = "/dashboard.html";
    return false;
}

/*
 * Handles callback for an error on an Auth Request.
 *
 * @param a XMLHTTPRequest Object that generated the error.
 */

function loginErrorCallback(a) {
    var m = jQuery.parseJSON(a.responseText);
    if(!isSessionExpired(m)) {
        var msg = ('error', a.status + " message: " + a.statusText + " response text: " + a.responseText);
        tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, "An internal error has occurred and has been sent to support. Please reload the page and try again. If you continue to see this message contact support for assistance.");
    }
}

/*
 * Handles callback for an error on an Auth Status Request.
 *
 * @param a XMLHTTPRequest Object that generated the error.
 */

function statusErrorCallback(a) {
    var m = jQuery.parseJSON(a.responseText);
    if(!isSessionExpired(m)) {
        var msg = ('error', a.status + " message: " + a.statusText + " response text: " + a.responseText);
        tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, "An internal error has occurred and has been sent to support. Please reload the page and try again. If you continue to see this message contact support for assistance.");
    }
}
/*
 * Handles callback for an error on an Logout Request.
 *
 * @param a XMLHTTPRequest Object that generated the error.
 */

function logoutErrorCallback(a) {
    var m = jQuery.parseJSON(a.responseText);
    if(!isSessionExpired(m)) {
        var msg = ('error', a.status + " message: " + a.statusText + " response text: " + a.responseText);
        tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, "An internal error has occurred and has been sent to support. Please reload the page and try again. If you continue to see this message contact support for assistance.");
    }
}

/*
 * Handles callback for an error on adding a class.
 *
 * @param a XMLHTTPRequest Object that generated the error.
 */

function classAddErrorCallback(a) {
    var m = jQuery.parseJSON(a.responseText);
    if(!isSessionExpired(m)) {
        var msg = ('error', a.status + " message: " + a.statusText + " response text: " + a.responseText);
        tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, "An internal error has occured and has been sent to support. Please reload the page and try again. If you continue to see this message contact support for assistance.");
    }
}

/*
 * Handles callback for an error on getting child state.
 *
 * @param a XMLHTTPRequest Object that generated the error.
 */

function childStatusErrorCallback(a) {
    var m = jQuery.parseJSON(a.responseText);
    if(!isSessionExpired(m)) {
        var msg = ('error', a.status + " message: " + a.statusText + " response text: " + a.responseText);
        tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, "An internal error has occured and has been sent to support. Please reload the page and try again. If you continue to see this message contact support for assistance.");
    }
}


/*
 * Handles callback for any Ajax API Error
 *
 * @param a XMLHTTPRequest Object that generated the error.
 */

function defaultErrorCallback(a)
{
    var m = jQuery.parseJSON(a.responseText);
    if (isSessionExpired(m) !== true) {
        var msg = ('error', a.status + ' message: ' + a.statusText + ' response text: ' + a.responseText);
        tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, 'An internal error has occured and has been sent to support. Please reload the page and try again. If you continue to see this message contact support for assistance.');
    }
}

/*
 * Function implements logout.
 */
function doLogout() {
    mySSO = new ajaxSSO();

    mySSO.setSiteId(authInfo.siteid);
    mySSO.ssoLogout(logoutErrorCallback);

    return false;
}

/*
 * Function sets the user welcome message in the header
 */

function setUserWelcome() {
    
    if (authInfo.first_name.length > 7) {        
        $('#siteHead dl dd ul li.account').css('padding-top', '5px');
    }
    
    var welcome = "Welcome back " + authInfo.first_name + "!";
    $("#user_greeting").empty();
    $("#user_greeting").append(welcome);
}

/*
 * Function gets the current child state.
 */
function fetchChildState() {
    myEntity = new ajaxEntity();    
    (viewUser > 0) 
    ? myEntity.getEntityViewUserStatus(loadChildStatus, childStatusErrorCallback, viewUser)    
    : myEntity.getEntityStatus(loadChildStatus, childStatusErrorCallback);        
}

/*
 * Function loads child info into the dashboard UI
 *
 * @param json object The json object returned.
 */
function loadChildStatus(json) {
    if (typeof studentOverride == 'undefined') studentOverride = false;
    
    entityState = json;        
    // If the child isn't initalized, in all cases go to create.
    if( (entityState.initialized == false) && (location.pathname != '/create.html') && authInfo.role != ROLE_EDUCATOR) {
        window.location = '/create.html';
        return false;
    } else if (location.pathname == "/create.html" && entityState.initialized == true) {
        // If they go to create and the child IS initalized... go to dashboard
        window.location = "/dashboard.html";
        return false;
    } else if (location.pathname == "/dashboard.html" && studentOverride == false) {
        var tRender = new mvcRender();               
        if (authInfo.role == ROLE_STUDENT) {                                
            tRender.renderCourseInfo(entityState.class_id, entityState.class_name);                       
            tRender.studentGlobalClassAlert(entityState.global_alert); 
            tRender.addFeedbackButtons();
            tRender.addFacebookButtons();
            getEntityHistory();
        }          
        tRender.renderDashboardChildAge(json);        
    } else if(location.pathname == "/raise.html") {
        getEntityHistory();
        getEntityAgeVideos();
        updateChildAgeDisplay(json);
        var tRender = new mvcRender();
        tRender.studentGlobalClassAlertRaise(entityState.global_alert);
    } else if(location.pathname == "/student.html" || studentOverride == true) {
        displayStudentInfo();
        getEntityHistory();        
        getEntityAgeVideos();
        updateChildAgeDisplay(json);
    }
    $("body").show();
    return false;
}

function displayStudentInfo()
{
    var tRender = new mvcRender();
    tRender.studentInfo();    
}

function showStudentGlobalClassAlert(tRender)
{       
    if (entityState.global_alert !== null) {
        tRender.studentGlobalClassAlert(entityState.global_alert);
    }
}

/*
 *  Function loads the class list into the table.
 *
 *  @param json object JSON object from Ajax transaction.
 */
function loadClassList(json) {

    window.classList = json;
    showStudentClassSelect()
    tRender = new mvcRender();
    tRender.renderLoadClassList(json);

}

/**
 * Function manageClass is called when the user clicks on the manage class
 * button in the Instructor Dashboard.
 *
 * @param cid int The Course Id
 */
function manageClass(cid) {
    tCourse = new ajaxCourse;
    tCourse.setManagedCourse(cid, managedSet, loginErrorCallback);
    return false;
}

/**
 * Function managedSet is invoked when we set the managed class on the
 * server via AJAX.
 *
 * @param json object JSON returned from the AJAX request.
 */

function managedSet(json) {
    if(json.result == "200") {
        // Managed Class is set. Go to the manage course page.
        window.location = "/managecourse.html";
    } else {
        var msg = "Manage Class Call Failed!";
        var uMsg = "Failed to manage the class. Please try again. If you see this message again please contact support.";
        tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
    }
}

function getViewUser() {    
    entity = new ajaxEntity;
    entity.getViewUser(function(json){
        if (json.result == '200') {
            viewUser = json.uid;
        }
    }, loginErrorCallback);
    return false;
}

function getManaged() {
    tCourse = new ajaxCourse;
    tCourse.getManagedCourse(managedGot, loginErrorCallback);
    return false;
}

function managedGot(json) {
    if (json.result == '200') {
        // Get the course data
        managedCourse = json.cid;
        tCourse = new ajaxCourse;
        tCourse.getCourseSchedule(json.cid, gotSchedule, loginErrorCallback);


        tCourse.getGlobalAlert(managedCourse, function(json){
            if (json.result != '400' && json.alert != '') {
                $('#addGlobalAlert span').trigger('addedAlert');
            }
        }, loginErrorCallback);

        return true;
    }
    
    var msg = "Manage Class Call Failed!";
    var uMsg = "Failed to manage the class. Please try again. If you see this message again please contact support.";
    tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
    return false;
}

/**
 *  Method gotSchedule renders the schedule as returned from the AJAX request.
 *
 *  @param json object The JSON object returned from the request.
 */
function gotSchedule(json) {
    if (json.result == '200') {
        tRender = new mvcRender();
        tRender.renderGotSchedule(json);
        return true;        
    }
    var msg = "Manage Class Call Failed!";
    var uMsg = "Failed to get the class schedule. Please try again. If you see this message again please contact support.";
    tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);

    return false;
}

function saveSchedule() {
    var numStages = $("#num_stages").val();

    var schedJ = '{"schedule":[';
    var first = true;
    for (var i=0; i<=numStages; ++i) {
        // Build JSON string here...
        var elem = "#" + i + "_dpinput"
        var elem_name = $(elem).attr('name')
        var elem_date = $(elem).val();
        // get age months from the element name.
        var idx1 = elem_name.indexOf('[');
        var idx2 = elem_name.indexOf(']');
        elem_name = elem_name.slice((idx1 + 1), (idx2));
        if (first) {
            schedJ += '{"age_months":"' + elem_name + '",';
            first = false;
        } else {
            schedJ += ',{"age_months":"' + elem_name + '",';
        }
        schedJ += '"start_date":"' + elem_date + '"}';
    }
    
    schedJ += "]}";

    tCourse = new ajaxCourse;
    tCourse.saveSchedule(managedCourse, schedJ, function(json){
        if (json.result == '200') {
            tErr.throwError(msg, tErr.INFO, tErr.MESSAGEBOX, json.message);
            getManaged();
        } else if (json.result == '400') {
            var msg = "Failed to save class schedule.";
            var uMsg = "Failed to save the class schedule. (" + json.message + ") Please try again. If you see this message again please contact support.";
            tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
        }
        
    }, loginErrorCallback);
    return false;
}

/**
* Method editAssign allows an instructor to hide questions in an assigment.
*
* @param aId int Assignment Id
*/
function editAssign(assignment_id)
{
    toggleContent( function(){ 
                   $('body').addClass('teacher student-detail mvc');                    
                   getQuestions(assignment_id); 
                }
            );
           
    return false;
}

function getQuestions(assignmentId)
{
    $("#AssignQuestions").remove();    
    var question = new ajaxQuestionBank();
    question.getQuestions(assignmentId, showQuestionBank, defaultErrorCallback);    
}

function gotAssignment(json) {
    if (json.result != "400") {
        
        tRender = new mvcRender();
        tRender.renderGotAssignment(json);
        return true;
    } 

    var msg = "Failed to save a global alert.";
    var uMsg = "Failed to edit this global alert. Please try again. If you see this message again please contact support.";
    tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);

    return false;
}

function saveAssignments(assignmentId)
{                           
     var questions = [];  
     
     $("[type='checkbox']", 'table.sortable').each(function() {         
         var name     = $(this).attr('name');
         var current  = $(this).attr('checked');
         var original = $(this).data('original');
         if (current != original) {                          
             var id = $(this).val();                                       
             questions.push({id: id, name: name, value: current});             
         }                  
     });
            
    if (questions.length > 0) {
        var questionbank = new ajaxQuestionBank();
        questionbank.saveAssignments(assignmentId, questions, function(){        
            $("[type='checkbox']", 'table.sortable').each(function() {         
               $(this).data('original', $(this).attr('checked')); 
            });        
            msgBox('success', 'successfully saved!');    
        }, defaultErrorCallback);                
    }                              
}


function editCourseAlert() {
    tCourse = new ajaxCourse;
    tCourse.getGlobalAlert(managedCourse, gotGlobalAlert, loginErrorCallback);
    return false;
}

function gotGlobalAlert(json) {
    if (json.result != '400') {
        tRender = new mvcRender();
        tRender.renderGotGlobalAlert(json);
        return true;
    } 
    var msg = "Failed to edit a global alert.";
    var uMsg = "Failed to edit this global alert. Please try again. If you see this message again please contact support.";
    tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
    return false;
}

function saveGAlert() {
    var aMsg = $("#taAlert").val();
    tCourse = new ajaxCourse;
    tCourse.setGlobalAlert(aMsg, managedCourse, function(json) { glAlertSet(json, aMsg) }, loginErrorCallback);
    return false;
}


function glAlertSet(json, msg) {
    if (json.result == '200') {
        completeGenericPop();
        if (msg == '') {
            $('#addGlobalAlert').trigger('removedAlert');
        } else {
            $('#addGlobalAlert').trigger('addedAlert');
        }
        return true;
    } 
    var msg = "Failed to set a timeline alert.";
    var uMsg = "Failed to save this alert. Please try again. If you see this message again please contact support.";
    tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
    return false;
}

/**
 * Method saveTLAlert allows an instructor to edit an alert for a specific stage.
 *
 * @param aMonths int Stage - age in months
 */
function saveTLAlert(aMonths) {
    var aMsg = $("#taAlert").val();

    tCourse = new ajaxCourse;
    tCourse.setTimelineAlert(aMsg, managedCourse, aMonths, tlAlertSet, loginErrorCallback);
    return false;
}

function tlAlertSet(json) {
    if(json.result == '200') {
        tCourse = new ajaxCourse;
        tCourse.getCourseSchedule(managedCourse, gotSchedule, loginErrorCallback);
        completeGenericPop();
        return true;
    } 
    var msg = "Failed to save age based alert.";
    var uMsg = "Failed to save the alert. (" + json.message + ") Please try again. If you see this message again please contact support.";
    tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
    return false;
}

/**
 * Method addTLAlert allows an instructor to add an alert for a specific stage.
 *
 * @param aMonths int Stage - age in months
 */
function addTLAlert(aMonths) {
    tRender = new mvcRender();
    tRender.renderAddTLAlert(aMonths);
    return false;
}

/**
 * Method editTLAlert allows an instructor to add an alert for a specific stage.
 *
 * @param tAlert string The current alert text.
 * @param aMonths int Stage - age in months
 */
function editTLAlert(tAlert, aMonths) {
    tRender = new mvcRender();
    tRender.renderEditTLAlert(tAlert, aMonths);
    return false;
}
/**
 * function displayFooterChildReset() determines which user type is logged in and
 * either displays or hides the child reset link (found in the footer) using the
 * appropriate mvcRender methods.
 */
function displayFooterChildReset() {
    tRender = new mvcRender;
    if(authInfo.role == "Educator") {
        tRender.showFooterReset();
    } else {
        tRender.hideFooterReset();
    }
}

/*
 * Function evalLocation evaluates the current http path and
 * performs any page specific actions on load.
 * 
 * NOTE: fetchChildState shows the body once it makes sure the user
 * is on the correct page. If that function ISN'T CALLED you must
 * show the body here!!
 * 
 */
function evalLocation() {
    switch(location.pathname) {
        case "/managecourse.html":
            getManaged();
            $('#addGlobalAlert').bind('removedAlert', function(){
                $(this).find('span').text('+ Add A Global Class Alert');
            }).bind('addedAlert', function(){
                $(this).find('span').text('Edit the Global Class Alert');
            });
            $("body").show();
            break;
        case "/raise.html":
            fetchChildState();
            displayEntitySWF();
            displayFooterChildReset();
            break;
        case "/updates.html":
            loadUpdates();
            $("body").show();
            break;            
        case "/mvchelp.html":
            displayEntitySWF();
            loadHelpTabs();
            $("body").show();
            break;
        case "/dashboard.html":
            fetchChildState();
            var tRender = new mvcRender();
            if (authInfo.role == ROLE_STUDENT) {
                $('body').removeClass('teacher');
                $('body').addClass('students');
                tRender.studentDashBoardEntity();                
            } else if (authInfo.role == ROLE_EDUCATOR) {
                $('body').removeClass('students');
                $('body').addClass('teacher');
                tRender.renderNewCourse();
                getCourseList();
            }            
            break;
        case "/create.html":
            $('body').removeClass('teacher');
            fetchChildState();
            if (authInfo.role == ROLE_EDUCATOR) {               
                $('<li><a href="comment.html">Comment</a></li>').insertAfter('#siteFoot .first');                
            }
            displayTraitSelection();
            break;
        default:
            $("body").show();
            
    }
}

function getEntityHistory()
{    
    var tEntity = new ajaxEntity;
    // @todo Fix class ID = 0 when not instructor.
    // @todo renderEntityTimeline gets called twice on fresh load of page
    //          due to call below and in displayNextEvent.
    var eid = entityState.entity_id;
    if($("#nextBtnText").text() == "Resume Questions") {
        fakingAge = -1;
        tRender.renderEntityTimelineAge(entityState.age_months, false);
    }
    if (typeof(entityState) != 'undefined') {
        tEntity.getHistory(eid, renderEntityTimeline, loginErrorCallback, viewUser);
    } else {
    }
    // Load the next activity
    (viewUser > 0)
    ? tEntity.getViewUserNextActivity(displayNextActivity, loginErrorCallback, viewUser)
    : tEntity.getNextActivity(displayNextActivity, loginErrorCallback)

    return false;
}

/**
 * Load the age appropriate videos
 */
function getEntityAgeVideos()
{
    tEntity = new ajaxEntity;    
    (viewUser > 0)
    ? tEntity.entityViewUserAgeVideos(gotVideos, loginErrorCallback, fakingAge, viewUser)
    : tEntity.entityAgeVideos(gotVideos, loginErrorCallback, fakingAge);
    
    return false;    
}

function displayNextActivity(json) {

    /**
     * Evaluate the response.
     */
    // THIS IS A HACK
    if (location.pathname == "/raise.html" && typeof json.alert != 'undefined') {
        var msg = "Next Activity failed: " + json.alert + ".";
        var uMsg = "An internal error occurred and has been sent to support. (" + json.alert + ") Please try again. If you see this message again please contact support.";
        //tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
        //tErr.throwError(json.alert, tErr.INFO, tErr.MESSAGEBOX, json.alert);

            msgBox('info', json.alert, true);

    }

    if (typeof json.available != 'undefined' && json.available == false) {
        // Can't view this event yet
        tRender = new mvcRender;
        tRender.renderActivityUnavailable(json.date);
        return false;
    }

    var tEntity = new ajaxEntity();
    var eid = entityState.entity_id;

    if(typeof(json.errormsg) != 'undefined') {
        // Got an error
        msgBox('error', json.errormsg);
        return false;
    }
    if (entityState.age_months != json.age_months) evalLocation();

    tRender = new mvcRender;
    if (classicView == false) {
        tRender.renderActivity(json);        
        tRender.renderAnswerForm(json, viewUser);
        
        // Change this to admin check
        if (authInfo.is_admin) {

            var ent = new ajaxEntity();
            ent.getHistVars(null, function(json){
                gotHistVars(null, json);
            }, loginErrorCallback);

        }
    }         
    return false;
}

function updateAgeActivities(json) {
    tRender = new mvcRender();
    tRender.renderAgeActivities(json);
    return false;
}
function updateChildAgeDisplay(json) {
    tEntity = new ajaxEntity();
    if(tEntity.formatAge(json.age_months, "age") != tEntity.formatAge(entityState.age_months, "age")) {
        tEntity.entityImgDef(renderEntitySWF, loginErrorCallback);
    }
    entityState = json;
    tRender = new mvcRender();
    tRender.renderEntityTimelineAge(entityState.age_months);
    return false;
}

/**
 * Rendering Timeline and Questions
 * 
 * @param json object JSON response from getHistory()
 * @see tEntity.getHistory()
 * @return bolean
 */
function renderEntityTimeline(json) {
    tRender = new mvcRender();    
    tRender.renderEntityTimeline(json);    
    if (classicView == false) {
        tRender.renderAgeActivities(json, viewUser);
    } else {
        tRender.renderClassicViewAgeActivities(json);
    }
    
    return false;
}

function doRenderRemainingAgeTimeline(json) {
    var tRender = new mvcRender();
    var lastCompleteScheduleId  = $("#last_complete_schedule_id").val();    
    var lastCompleteScheduleAge = $("#last_complete_schedule_age").val();
    var currentAge              = (fakingAge == -1) ? entityState.age_months : fakingAge;            
    var blnStartCount           = false;
    if (  (lastCompleteScheduleId == 0) // if we are on the first activity for this age.
       || (currentAge > lastCompleteScheduleAge)
    ) {
        blnStartCount = true;
    }
    
    var m = 0;
    for (var i in json.schedule) {                
        
        if (blnStartCount) {
            ++m;
        }   
        
        if (json.schedule[i].SCHEDULE_ID == lastCompleteScheduleId) {            
            blnStartCount = true;
        }
                     
    }    
    // Render rest of set
    tRender.renderFillOutAgeTimeline(m);
}

/** 
 * Depreciated... remove after checking for referneces.
 * render.renderStudentList
 * 
function displayEntityTimeline(json) {

    tEntity = new ajaxEntity;
    var tlTemplate = tEntity.getTimelineMonths();

    var temp1 = '<li class="{class}"><a href="#" onclick="return tlJump({sched_idx}}">{age}<span>{age_unit}</span></a></li>';
    var class1 = "oldyear lalign hand_cursor";
    var cl_future = "newyear ralign";
    var cl_current = "current";
    var lHist = 0;

    var strHTML = "";
    var tHTML = "";
    
    // Iterate throught the json history...
    first = true;
    /**
     * We need to display only the LAST activity in each age group.
     *
    var histIdRendered = 0;
    for(var i in json.history) {
        var tJ = json.history[i];
        if(i > 0) {
            var tJOld = json.history[(i-1)];
            if(tEntity.formatAge(tJOld.age_months, "age") != tEntity.formatAge(tJ.age_months, "age")) {
                // Render tJOld
                // Renderable age?
                if(tEntity.formatAge(tJOld.age_months, "age")) {
                    tJ = tJOld;
                    tHTML = temp1;
                    if(tJ.age_months == entityState.age_months) while(tHTML.indexOf("{class}") != -1) tHTML = tHTML.replace("{class}", cl_current);
                    if(first) {
                        while(tHTML.indexOf("{class}") != -1) tHTML = tHTML.replace("{class}", class1);
                        first = false;
                    } else {
                        while(tHTML.indexOf("{class}") != -1) tHTML = tHTML.replace("{class}", "");
                    }
                
                    while(tHTML.indexOf("{age}") != -1) tHTML = tHTML.replace("{age}", tEntity.formatAge(tJ.age_months, "age"));
                    while(tHTML.indexOf("{age_unit}") != -1) tHTML = tHTML.replace("{age_unit}", tEntity.formatAge(tJ.age_months, "unit"));
                    while(tHTML.indexOf("{sched_idx}") != -1) tHTML = tHTML.replace("{sched_idx}", tJ.history_id);
                    lHist = tJ.age_months;
                    strHTML += tHTML
                    histIdRendered = tJ.history_id;
                }
            }
        }
    }
    /**
     * Now, always render the last one as current... unless it was rendered...
     *
    if(histIdRendered != tJ.history_id) {
        tHTML = temp1;
        if(tEntity.formatAge(tJ.age_months,"age") == tEntity.formatAge(entityState.age_months,"age")) while(tHTML.indexOf("{class}") != -1) tHTML = tHTML.replace("{class}", cl_current);
        if(first) {
            while(tHTML.indexOf("{class}") != -1) tHTML = tHTML.replace("{class}", class1);
            first = false;
        } else {
            while(tHTML.indexOf("{class}") != -1) tHTML = tHTML.replace("{class}", "");
        }
        while(tHTML.indexOf("{age}") != -1) tHTML = tHTML.replace("{age}", tEntity.formatAge(tJ.age_months, "age"));
        while(tHTML.indexOf("{age_unit}") != -1) tHTML = tHTML.replace("{age_unit}", tEntity.formatAge(tJ.age_months, "unit"));
        while(tHTML.indexOf("{sched_idx}") != -1) tHTML = tHTML.replace("{sched_idx}", tJ.history_id);
        lHist = tJ.age_months;
        strHTML += tHTML
    }


    // Ok... now we iterate through the tlTemplate until we get PAST the lHist
    for(var m = 1; m < tlTemplate.length; ++m) {
        tHTML = temp1;
        if(Number(tlTemplate[m]) <= Number(lHist)) {
            // do nothing
        } else {
            if(tlTemplate[m] == entityState.age_months) while(tHTML.indexOf("{class}") != -1) tHTML = tHTML.replace("{class}", cl_current);

            while(tHTML.indexOf("{class}") != -1) tHTML = tHTML.replace("{class}", cl_future);
            while(tHTML.indexOf("{age}") != -1) tHTML = tHTML.replace("{age}", tEntity.formatAge(tlTemplate[m], "age"));
            while(tHTML.indexOf("{age_unit}") != -1) tHTML = tHTML.replace("{age_unit}", tEntity.formatAge(tlTemplate[m], "unit"));
            while(tHTML.indexOf("{sched_idx}") != -1) tHTML = tHTML.replace("{sched_idx}", -1);
            strHTML += tHTML;
        }
    }

    $("#e_timeline").empty();
    $("#e_timeline").append(strHTML);
    
    // Prepare for scroll...

    var ctW = $('#childTimeline').width();

    if (ctW > 622) {
            setUpScroll(790);
    }
    else {
            setUpScroll(440);
    }
}
*/

function setUpScroll(w){

    var tlWidth = $('#childTimeline .child-wrap1 ol.years li').length*88;

    $('#childTimeline .child-wrap1 ol.years').width(tlWidth);

    $('#childTimeline .child-wrap1 a.prev').click(function(){
            var position = $('#childTimeline .child-wrap1 ol.years').position();
            if ( position.left != 0 && !$('#childTimeline .child-wrap1 ol.years').is(':animated') ) {  // Are we at the beginning?  Is the list still animating?
                    $('#childTimeline .child-wrap1 ol.years').animate({
                            "left": position.left + w
                    }, {queue: true, duration: 1000});
            };
            return false;
    });

    $('#childTimeline .child-wrap1 a.next').click(function(){
            var position = $('#childTimeline .child-wrap1 ol.years').position();
            if ( position.left > (0-(tlWidth-w)) && !$('#childTimeline .child-wrap1 ol.years').is(':animated') ) {  // Are we at the end?  Is the list still animating?
                    $('#childTimeline .child-wrap1 ol.years').animate({
                            "left": position.left - w
                    }, {queue: true, duration: 1000});
            };
            return false;
    });

    /* Go to current age */

    var current = $('#childTimeline ol.years li.current').position();
    var m = Math.floor(current.left/w);
    $('#childTimeline .child-wrap1 ol.years').css('left',-(m*w));

}

function activitySaved(json) {
    
    if (json.result == '200') {
        // Load the next activity
        tEntity.getHistory(entityState.entity_id, renderEntityTimeline, loginErrorCallback, viewUser);
        tEntity.getNextActivity(displayNextActivity, loginErrorCallback, viewUser);
        return true;
    } 
    var msg = "Failed to save an activity.";
    var uMsg = "Failed to save this activity. Please try again. If you see this message again please contact support.";
    tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
    return false;
}

/**
 * Ajax call to get the parameters to render the Child Image
 * 
 * @return boolean;
 */
function displayEntitySWF() {
    tEntity = new ajaxEntity();
    (viewUser > 0)
    ? tEntity.entityViewUserImgDef(renderEntitySWF, loginErrorCallback, viewUser)
    : tEntity.entityImgDef(renderEntitySWF, loginErrorCallback);        
    return false;
}

function renderEntitySWF(json) {

    tRender = new mvcRender();
    result = false;
    if (json.result == '200' && json.attrstring != "false") {
        result = true;
    }
    
    tRender.renderEntitySWF(json, result);    
    return result;
}


function gotVideos(json) {
    tRender = new mvcRender();
    tRender.renderAgeVideos(json, "#momentVideos");
}

function submitComment() {
    tRender = new mvcRender();
    tCourse = new ajaxCourse();
    tRender.renderSubmitComment();
    setTimeout("tCourse.saveComment($('#newAlert').val(), commentSaved, loginErrorCallback)", 1000);

    return false;
}

function commentSaved(json) {
    tRender = new mvcRender();

    if (json.result == '200') {
        tRender.renderSubmitCommentSuccess(finCommentSavedGood);
    } else if(json.result == '400') {
        tRender.renderSubmitCommentFail(finCommentSavedBad);
    }
}

function finCommentSavedGood() {
    tRender = new mvcRender();
    tRender.renderSubCommSuccShow();
}

function finCommentSavedBad() {
    tRender = new mvcRender();
    tRender.renderSubCommFailShow();
}

/**
 * Start a new registration page.
 *
 */
function displayNewRegistration() {

    if (typeof $(document).data('entity') == 'undefined')
    {
        $(document).data('entity', new ajaxEntity());
    }

    var entity = $(document).data('entity');
    log(entity);
    var tRender = new mvcRender();
    tRender.renderNewRegistration();
    
    var skipCourse = false;
    
    // Check to see if we need to skip de Course
    $("button[name='skip']").click(function(){
       skipCourse = true;
       $("form[name='register']").submit();
    });
    
    $("button[name='submit']").click(function(){
       skipCourse = false;
       $("form[name='register']").submit();
    });    
    
    $('#register').bind('submit', function(e) { // Bind to the submit off the newly created form
                 
        e.preventDefault(); // Stop the form from submitting.
                        
        courseId = $("input[name='courseid']").val();
                        
        if (gender = getSelectedGender()) {
            entity.registrationInfo.gender = gender;            
        } else {                        
            msgBox('warning', 'Please select Your Gender');
            return false;
        }
        if (pgender = getPartnerSelectedGender()) {
            entity.registrationInfo.partner_gender = pgender;
        } else {
            msgBox('warning', 'Please select Your Partner\'s Gender');
            return false;
        }
                
        if ((skipCourse == false) && (courseId != '')) {                                               
            entity.isValidCourseId(courseId, function(json){
            if ((json.result == '200') && (json.valid == true)) {    
                entity.registrationInfo.classID = courseId;
                displayTraitSelection(); // Jump to Appearance
            } else {
                msgBox('warning', 'Invalid Course ID');
                return false;
            }
            }, function(json){
                var msg = "Failed to validate a course id.";
                var uMsg = "An error occurred validating the course id. Please try again. If you see this message again please contact support.";
                tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
                return false;
        });
                                   
        } else if (skipCourse == true) {
            entity.registrationInfo.classID = 'none';
            displayTraitSelection(); // Jump to Appearance
        } else {
            if(authInfo.role == ROLE_STUDENT) {
                msgBox('info', 'Please enter your Class ID or click Skip to add it later');
            } else {
                entity.registrationInfo.classID = 'none';
                displayTraitSelection();
            }
            return false;
        }                                                                        
    });

}

/**
* Get the gender selected
*/
function getSelectedGender() {
 var gender = $('input[name="gender"]:checked').val();
 if (typeof gender != 'undefined') {
     return gender;
 }
 
 return false;
}

/**
* Get the partner's gender selected
*/
function getPartnerSelectedGender() {
 var gender = $('input[name="partner_gender"]:checked').val();
 if (typeof gender != 'undefined') {
     return gender;
 }

 return false;
}
/**
 * Display the trait selection page. This will poll the entity to find out what info it still needs, then tell render to ask for it
 */
function displayTraitSelection() {

    $('body').removeClass('dashboard').addClass('create-child');

    if (typeof $(document).data('entity') == 'undefined')
    {
        $(document).data('entity', new ajaxEntity());
    }
    
    var entity = $(document).data('entity');

    var tRender = new mvcRender();
    var needed = entity.getNeededRegistrationInfo();
    
    switch (needed) {
        case 'completed':
                // All the information we need
                entity.saveNewRegistration();
            break;
        case 'tos':
            var product = new ajaxProduct();
            product.getTOS(tRender.renderShowLicense, defaultErrorCallback);
            break;
        case 'gender':
        case 'classID':
            // Send them back to the first step (if they are a student) because they should have this information
            displayNewRegistration();
            break;
        case 'race':
                entity.getTraitOptions(needed, tRender.renderRaceSelection, function(){log('failed to get trait option');});
            break;
        case 'skintone':
                entity.getTraitOptions(needed, tRender.renderSkintoneSelection, function(){log('failed to get trait option');});
            break;
        case 'eyecolor':
                entity.getTraitOptions(needed, tRender.renderEyeColorSelection, function(){log('failed to get trait option');});
            break;
        case 'haircolor':
                entity.getTraitOptions(needed, tRender.renderHairColorSelection, function(){log('failed to get trait option');});
            break;
        case 'personality':
                entity.getTraitOptions(needed, tRender.renderPersonalitySelection, function(){log('failed to get trait option');});
            break;
        case 'personalityTest':
                entity.getTraitOptions(needed, tRender.renderPersonalityQuiz, function(){log('failed to get trait option');});
            break;
        case 'cognitiveTest':
                entity.getTraitOptions(needed, tRender.renderCognitiveQuiz, function(){log('failed to get trait option');});
            break;
        case 'eGender':
                pickGender();
        case 'name':
                tRender.getName(entity.registrationInfo.eGender);
            break;
        default:
            //Somethign is wrong, shoudn't be here
            log(entity);
            break;
    }
}

/**
 * Show the next question needed, scrolling 
 * 
 */
  function nextQuestion(){

        // Get the container
        var container = $('#quizQuestions ol');

        // Make sure we don't do anything while it's still animated (double clicking the button, etc)
        if (container.is(':animated')) {
            return false;
        }

        // Get the currently displayed LI
        var current = container.find('li.currentScroll');
        // If we don't have a current one, that means we are here for the first time
        if (current.length == 0) {
            current = container.find('li:first-child').addClass('currentScroll');
        }

        // Get the (new) current position (the question we are on)
        var pos = container.children().index(current.next('li')) + 1;

        // Update the display of what question we are on.
        $('#qN').text(pos);

        // Get the height to move
        var heightToMove = current.outerHeight();

        // Make the next li the current li.
        current.removeClass('currentScroll').next('li').addClass('currentScroll');

        // Animate the container sliding up
        container.animate(
            {"top": container.position().top - heightToMove},
            750
        );

        // If the new current is going to be the last, change the button to submit instead of just scrolling.
        if (pos == container.children().length) {
            $('form.quiz').attr({"onsubmit":"return true;"})
            $('form.quiz fieldset.buttons a.btn3').hide();
            $('form.quiz fieldset.buttons button').show();
        }

        return false;
    }

/**
 * Save the answer to a trait question
 **/
function saveTraitAnswer(trait, radio) {

    var val = $('input[name="' + radio + '"]:checked').val();
    if (typeof val != 'undefined') {
        var entity = $(document).data('entity');
        entity.registrationInfo[trait] = val;
        displayTraitSelection();
    } else {
        msgBox('info', 'Please select an option to continue.');
    }
}

/**
 * Save the answer to a quiz question
 **/
function saveTestAnswers(type){
    var qn = 5;
    if (type == 'personalityTest') {
        var qn = 20;
    }
    var answers = {};
    for (var i = 1; i <= qn; i++) {
        var key = ((type=='personalityTest')?'mp':'ca') + i
        answers[key] = $('input[name="mp_' + i + '"]:checked').val();
    }
    var entity = $(document).data('entity');
    entity.registrationInfo[type] = answers;
    displayTraitSelection();
}

/**
 * Randomly generate a gender for the student as the system doesn't currently model hormone level variations
 **/
function pickGender() {
    // Randomly select gender
    $(document).data('entity').registrationInfo.eGender = Math.floor(Math.random() * 10) % 2? 'MALE':'FEMALE';
    displayTraitSelection();
}

function saveName(name) {
    $(document).data('entity').registrationInfo.name = name;
    displayTraitSelection();
}

function newRegistrationSaveSuccess(){
    window.location = '/dashboard.html';
}

function newRegistrationSaveFailure(){
    var msg = "Failed to save new Registration.";
    var uMsg = "Failed to create your child. Please try again. If you see this message again please contact support.";
    tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
}

function tosAccepted() {
    $(document).data('entity').registrationInfo.tos = true;
    displayTraitSelection();
}

/**
 * Get and render the selected item from the entity history.
 * 
 * @param hId int The history id for this activity.
 * @param sId int The schedule id for this activity.
 * @param tDiv string The DOM ID clicked on.
 */
function gotoActivity(hId, sId, tDiv) {
    var tEntity = new ajaxEntity();
    tEntity.entityHistMoment(hId, function(json){
        gotHistMoment(hId, json);
    }, loginErrorCallback, viewUser);
    return false;
}

function gotoClassicActivity(hid)
{
    var tEntity = new ajaxEntity();    
    tEntity.entityHistMoment(hid, function(json) {                        
                        tRender = new mvcRender();
                        tRender.renderClassicViewActivity(hid, json);                                                
                    }, loginErrorCallback, viewUser);
}

/**
 * 
 * @param json object JSON object containing the response
 */
function gotHistMoment(hid, json) {
    tRender = new mvcRender();
    if (json.result == '200') {
        tRender.renderActivity(json);
        tRender.renderAnswerForm(json, viewUser);
        if(fakingAge != -1) tRender.renderEntityTimelineAge(fakingAge, true);
        if(fakingAge == -1) tRender.renderEntityTimelineAge(entityState['age_months'], true);

            // Change this to admin check
        if (authInfo.is_admin) {

            var ent = new ajaxEntity();
            ent.getHistVars(hid, function(json){
                gotHistVars(hid, json);
            }, loginErrorCallback);

        }
        

        return true;
    } 
    var msg = "Failed to fetch a moment from the API.";
    var uMsg = "Failed to fetch this activity. Please try again. If you see this message again please contact support.";
    tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
    return false;
}


function gotHistVars(hid, json) {
    var render = new mvcRender();

    if (json.rows[0]['ENTITY_HISTORY_ID'] != hid || json.rows.length == 1) {

        // The theory here is that if the first array isn't the same as our history id, then there is none
        // Which means either it was a non-history generating event, or we haven't answers the question yet
        // Either way, that means we pass one array in for both values'
        render.renderHistVarComparison(json.rows[0], json.rows[0]);
        
    } else {

        render.renderHistVarComparison(json.rows[0], json.rows[1]);
        
    }
    
}


function tlJump(startAge) {
            //console.log('Age IS:', startAge, entityState.age_months);
    if (   (startAge > entityState.age_months) 
        || (startAge == fakingAge)
        || ((startAge == entityState.age_months) && (fakingAge == -1 || entityState.age_months == fakingAge))) {                
        return false;
    }
        
    fakingAge = startAge;
    tEntity = new ajaxEntity();
    tRender = new mvcRender();
    tEntity.getNextTimelineMonths(startAge);
    // @todo Need new entity method to get 
    
    
    tEntity.getHistory(entityState.entity_id, renderEntityTimeline, loginErrorCallback, viewUser);


    // Load the age appropriate videos
    // @todo This needs to handle fakingAge
    // tEntity.entityAgeVideos(entityState.class_id, gotVideos, loginErrorCallback);
    
    tRender.renderEntityTimelineAge(fakingAge, true);
    displayEntitySWF();
    getEntityAgeVideos();
    return false;
}

function showChangeCourse()
{    
    if (authInfo.role != ROLE_EDUCATOR) {
        entity   = new ajaxEntity();
        tRender  = new mvcRender();    
        tRender.renderChangeCourseId(entityState.class_id, entityState.class_name);
        return true;        
    } 
    
    msgBox('info',"Educators can't change / assign a course");
    return false;
}

function changeCourseId(courseId) {           
   newCourseId = $('input[name="courseID"]').val();
   
   if ((newCourseId != '') && (isNaN(newCourseId) !== true)) {
       
       result = true;
       
       if (newCourseId !== 1) {
           changeCourseAjaxCall(newCourseId);
       } else {
           completeGenericPop();
       }
       
              
   } else if (newCourseId == '') {
       if (courseId != 1) {
           if (confirm("Are you sure you want to unassign Course ID: " + courseId + "?")) {
               unassignCourseAjaxCall(courseId);                          
           }                        
       }
       completeGenericPop();     
   } else {
       msgBox('warning', 'The Course ID needs to be Numeric');
       return false;       
   }
                    
}

function changeCourseAjaxCall(newCourseId) {   
   entity = new ajaxEntity();      
   entity.changeCourseId(newCourseId, function(json){
   if (json.result == '200') {       
       entityState.class_id     = json.class_id;
       entityState.global_alert = json.global_alert;         
       completeGenericPop();
       r  = new mvcRender();
       r.studentGlobalClassAlert(entityState.global_alert);       
       r.renderCourseInfo(json.class_id, json.class_name);
   } else if (json.result == '400') {
       msgBox('error', json.message);    
   }
   
   }, defaultErrorCallback);    
}

function unassignCourseAjaxCall(courseId)
{   
   entity = new ajaxEntity();
   entity.unassignCourse(function(json){
   if (json.result == "200") {
       entityState.class_id = json.courseid;
       msgBox('success', 'Unassigned Course ID: ' + courseId);
       r  = new mvcRender();
       r.renderCourseInfo(1, '');       
       return true;
   }
   }, function(json) {
       var msg = "Failed to remove course id from entity.";
        var uMsg = "Failed to unassign the course id: " + courseId + ". Please try again. If you see this message again please contact support.";
        tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
       return false;
   });    
}

function getStudents(classId) {
    if (authInfo.role == ROLE_EDUCATOR) {
        var course = new ajaxCourse();
        course.getStudents(classId, function(json){
            $('#filterByClass').data('rows', json.content.length);
            var render = new mvcRender();
            render.renderStudentList(json.content);
        });
    }
    // @todo error message need it?
}


function showQuestionBank(json)
{    
    var render = new mvcRender();
    render.renderQuestionBank(json);
}

function showStudentClassSelect() {

    if (typeof classList == 'undefined') {
        // No classlist cached from the other display, load it
    }

    var render = new mvcRender();    
    var select = render.renderGetStudentSelectBox(classList.rows);
    render.renderStudentSelectBox(select);
}


function showResetInstructorEntity()
{
    entity   = new ajaxEntity();
    tRender  = new mvcRender();    
    tRender.renderResetEntity(function(){ // Yes Button        
        resetInstructorEntity();
        completeGenericPop();        
        fetchChildState();
    }, function(){ // No Button
        completeGenericPop(); 
    }, 1);
    return false;      
}

function showResetEntityInStudentView(uId, classId)
{
    entity   = new ajaxEntity();
    tRender  = new mvcRender();    
    tRender.renderResetEntity(function(){ // Yes Button                
        resetStudentEntity(uId); // Reset Entity
        $('.dashboard-link').trigger('click'); // Go Back to the Dashboard
        $('#studentRoster tbody').empty();
        getStudents(classId);
        completeGenericPop();
    }, function(){ // No Button
        completeGenericPop(); 
    }, 2);
    return false;    
}

function showResetEntityInRosterList(uId, classId) {    
    entity   = new ajaxEntity();
    tRender  = new mvcRender();    
    tRender.renderResetEntity(function(){ // Yes Button        
        resetStudentEntity(uId); // Reset Entity
        $('#studentRoster tbody').empty();
        getStudents(classId);
        completeGenericPop();
    }, function(){ // No Button        
        completeGenericPop(); 
    }, 2);
    return false;
}


function resetInstructorEntity() {   
   if (authInfo.role == ROLE_EDUCATOR) {
       entity = new ajaxEntity();       
       entity.resetInstructorEntity(function(json){
       if (json.result == '200') {           
           //@todo successfully saved alert
       }
       }, function(json) {           
           var msg = "Failed to reset the child.";
            var uMsg = "Failed to reset this child. Please try again. If you see this message again please contact support.";
            tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
           return false;
       });
   }
}

function resetStudentEntity(uId)
{   
   if (authInfo.role == ROLE_EDUCATOR) {
       entity   = new ajaxEntity();       
       uId = (typeof uId != 'undefined') ? uId : '';

       entity.resetStudentEntity(uId, function(json){
           if (json.result == '200') {
               //@todo show a successfully saved alert
           }
       }, function(json) {           
           var msg = "Failed to reset the child.";
           var uMsg = "Failed to reset this child. Please try again. If you see this message again please contact support.";
           tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
           return false;
       });
   }
   
   return false;
}

/**
* Send the user that we want to view (student) to the server then start the page transition
*
* @param uid int The user id
* @param first string The student's first name
* @param last string The student's last name
*/
function setViewUser(uid, first, last) {   
    entity = new ajaxEntity();
    entity.setViewUser(uid, function(json) {           
           if (json.result == '200') {                              
               toggleContent(function(){                                      
                   $('body').addClass('students moment mvc student-detail');
                    var render = new mvcRender();
                    render.addDefaultTimelineHTML();
                    studentOverride = true;
                    getViewUser();
                    fetchChildState();
                    displayEntitySWF();
                    studentOverride = false;                    
                });
                return false;
           }
           }, function() {
                var msg = "Failed to set the view entity.";
                var uMsg = "Failed to view this child. Please try again. If you see this message again please contact support.";
                tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
           });    
   return false;
}

/**
 * Hide the content (dashboard), replacing or restoring as needed. Page changes without url changes.
 * @param transitionCallback function The function to call when the transition is complete.
 **/
function toggleContent(transitionCallback, backupDivName) {
    
    if (typeof $(document).data('contentBack') == 'undefined') {
        $(document).data('contentBack', {});
    }

    /* By default we are backing up the dashboard */
    var backupDiv = (typeof backupDivName == 'undefined') ? 'dashboard-backup' : backupDivName + '-backup';
    var content = $('#content');
    var content_bak = $(document).data('contentBack')[backupDiv];

    if (backupDiv == 'dashboard-backup') {
        $(document).data('contentBack', {});
    } else {
        $(document).data('contentBack')[backupDiv] = void(0);
    }
    

    /* Get the parent of the content div */
    var parent = content.parent();


    if (typeof content_bak == 'undefined') {
        /* The backed up data does not exist, so we are switching away from it */

        /* Remove the current content */
        content.detach();

        /* Create a new content area */
        parent.append($("<div id='content'></div>").attr('class', content.attr('class')));

        /* If we are working with the dashboard backup, bind links back to the dashboard */
        if (backupDiv == 'dashboard-backup') {
            $('.dashboard-link').die().live('click', function(e){   
                classicView = false;
                e.preventDefault();
                toggleContent(function(){});
            });
        }

        /* Backup the body classes for this state */
        content.data('body-class-backup', $('body').attr('class'));
        
        /* Remove body backup classes */
        $('body').removeAttr('class');

        /* Store it in the data */
        $(document).data('contentBack')[backupDiv] = content;

    } else {
        /* The backed up data does exist, which means we are supposed to switch back to it */

        /* Remove the current content */
        content.remove();

        /* Restore body backup classes */
        $('body').removeAttr('class').attr('class', content_bak.data('body-class-backup'));

        /* Reinsert the backed up content */
        parent.append(content_bak);

        /* If we are working with the dashboard, destroy the bindings for dashboard links */
        if (backupDiv == 'dashboard-backup') {
            $('.dashboard-link').die();
        }
    }

    transitionCallback();
}

/**
 * Save a uid to the session for use in assignments.html
 * @param uid int The user id
 */
function setViewAssignments(uid) {
    entity = new ajaxEntity();
    entity.setViewUser(uid, function(json) {
           if (json.result == '200') {
               toggleContent(loadAssignments);
           }
           }, function() {
                var msg = "Failed to set the view entity.";
                var uMsg = "Failed to view this child. (" + json.message + ") Please try again. If you see this message again please contact support.";
                tErr.throwError(msg, tErr.SEVERE, tErr.MESSAGEBOX, uMsg);
   });
}

/**
 * Get a list of assignments from the server using the uid stored previously with setViewAssignments
 */
function loadAssignments() {
    entity = new ajaxEntity();
    entity.getAssignments(function(json){
        var render = new mvcRender();
        render.renderAssignments(json);
    }, function(){
        // error
    });
}

function loadUpdates()
{        
    product = new ajaxProduct();
    product.getUpdates(function(json){
        var render = new mvcRender();
        render.renderUpdates(json);
    }, function(){
        // error
    });
}

/**
 * Get a list of feedback for a student given the student's ID
 */
function loadFeedback(sID) {
    entity = new ajaxEntity();
    entity.getFeedback(sID, function(json){
        var render = new mvcRender();
        toggleContent(function(){render.renderFeedback(json)});
    }, function(){
        // error
    });
}

/**
* Return a reasonable string for displaying months
 */
function calcMonths(months) {
    var result = 0;
    if (months < 24) {
        result = months + ' Months';
    } else {
        result = Math.floor(months / 12) + ' Years';

        var extra = months % 12;
        if (extra > 0) {
            if (extra > 1) {
                result += ' ' + extra + ' Months';
            } else {
                result += ' ' + extra + ' Month';
            }
        }
    }
    return result;
}

function showClassicView()
{    
    toggleContent(function(){       
       classicView = true;
       $("body").addClass("teacher student-detail mvc");       
       render = new mvcRender();
       render.breadCrumbs('Student Detail');
       render.showStudentDetail();   
       getEntityHistory();       
    }, 'classicView');
                
}

function showView()
{
   classicView = false;    
   toggleContent(function(){},'classicView');
}

function getRosterCsv(classId)
{
    course = new ajaxCourse();
    course.getRosterCsv(classId);   
}

/**
 * Returns a string with the No. of months and years.
 */
function monthsToStr(m)
{
    if (m <= 24) {
        return m + ' months';
    } else {
        if ((m%12) == 0) {
            return (m/12) + ' years';
        } else {
            var j = m - (m%12);
            j = j/12;
            return j + ' years, ' + (m%12) + ' months';
        }
    }    
}

/**
 * Gets the Current date in m/d/Y format
 */
function getCurrentDate()
{
    var cdate = new Date();    
    var month = (cdate.getMonth() < 9) ? '0' + (cdate.getMonth() + 1) : cdate.getMonth() + 1;
    var day   = (cdate.getDate() < 10) ? '0' + (cdate.getDate()) : cdate.getDate();       
    return month + '/' + day + '/' + cdate.getFullYear();
}

function addQuestion(assignmentId)
{    
    render = new mvcRender();
    render.addEditQuestion(assignmentId);
}

function saveQuestion(assignmentId, questionId)
{       
    var edit = false;
    
    if (typeof questionId != 'undefined')  {
        edit = true;
    } else {
        questionId = '';
    }
        
    var question   = $('#newQuestion', '#tlalert').val();    
    var categoryId = $('option:selected','#categoryList').val();
    var category   = $('option:selected','#categoryList').text();
    var notshared  = $('[name="notshared"]:checked','#tlalert').val().toString();
    
    
    // Validation
    if (question == '') {
        msgBox('warning', 'Please fill out the question text');
        return false;
    }
    
    if ($('input:[name="newCategory"]').length > 0) {
        msgBox('warning', 'Please save category first');
        return false;
    }
                        
    $('table.sortable', "#AssignQuestions").data(
        'newquestion', {
            'question'     : question,
            'category_id'  : categoryId,
            'category'     : category,
            'question_id'  : questionId,
            'assignment_id': assignmentId,
            'notshared'    : notshared
         }
    );
        
    var questionbank = new ajaxQuestionBank();
            
    if (edit) {        
        questionbank.saveQuestion(question, categoryId, assignmentId, questionId, notshared, function(json){
            if (json.result == 200) {
                var data = $('table.sortable', "#AssignQuestions").data('newquestion');                 
                var row  = $('table.sortable tr#alt' + data.question_id, "#AssignQuestions");
                
                                
                row.data('info', {         
                   question_id: data.question_id,
                   category_id: data.category_id,
                   notshared: data.notshared,
                   question: data.question                                                        
                });
                                                                                
                row.find('.question').text(data.question);
                row.find('.category').text(data.category);                               
                row.find('.sharedstatus').text((notshared == 1) ? '(private)' : '(shared)');                
                
                completeGenericPop();
            } else {
                msgBox('warning', json.mvxMessage);
            }
            
        }, defaultErrorCallback);  
    } else {        
        questionbank.addQuestion(question, categoryId, assignmentId, notshared, function(json){
            if (json.result == 200) {
                render = new mvcRender();
                render.renderQuestionRow(json, 'new');        
                completeGenericPop();                        
            } else {
                msgBox('error', json.mvxMessage);
            }
            
        }, defaultErrorCallback);                
    }
}


function editQuestion(questionId, assignmentId)
{           
    var question = $('table.sortable tr#alt' + questionId, '#AssignQuestions');
    var json = question.data('info');        
    render = new mvcRender();
    render.addEditQuestion(assignmentId, json);    
}

function confirmDeleteQuestion(questionId, assignmentId)
{
    render = new mvcRender();
    render.deleteQuestion(questionId, assignmentId);
}

function deleteQuestion(questionId, assignmentId)
{
    var questionbank = new ajaxQuestionBank();
    questionbank.deleteQuestion(questionId, assignmentId, function(json){
        if (json.result == 200) {
            $('#alt' + json.question_id,'#AssignQuestions').remove();         
            $('.sortable', "#AssignQuestions").trigger('update').trigger('applyWidgets');
            completeGenericPop();
        } else {
            completeGenericPop();
            $("[name='alt'][type='checkbox']", 'table.sortable').each(function(){              
                if ($(this).val() == json.question_id) {                    
                    $(this).removeAttr('checked');
                    $(this).data('original', false);
                }   
            });
            
            msgBox('info', json.mvxMessage);
        }
    }, defaultErrorCallback);
}

function saveEntityVar() {
    if($("#txt_var_collect").val().length == 0) {
        alert("You must provide a response.");
        return false;
    } else {
        tEntity = new ajaxEntity();
        tEntity.setVariable($("#var_name").val(), $("#txt_var_collect").val(), $("#var_data_type").val(), savedEntityVar, loginErrorCallback);
        return false;
    }
}

function savedEntityVar(json) {
    tRender = new mvcRender();

    // Call Render function to replace variable in content with value
    tRender.replaceVarInContent(json.variable, json.value);
    completeGenericPop();
}


