////////////////////////////////////
// Register namespaces
////////////////////////////////////
Type.registerNamespace("MySpaceApps");
Type.registerNamespace("MySpaceApps.Surfaces");
Type.registerNamespace("MySpaceApps.Caja");

/////////////////////////////////////
// Utility functions
/////////////////////////////////////
function clearElementText(elm) {
    elm.value = "";    
}

function appAccountValidatePassword(sender, args)
{
    var isValid = true;
    var errorMessage = "";
    var acctPassword = (args.Value)+"";
    if(acctPassword.length < 6) {
        isValid = false;
        errorMessage = "Password is too short.";
    }
    else if(acctPassword.length > 10) {
        isValid = false;
        errorMessage = "Password is too long.";
    }
    // todo - iterate through password and check for one letter and one (puctuation or number)
    else {
        isValid = true;
    }
    
    args.IsValid = isValid;
    sender.innerHTML = errorMessage;
}

function appAccountValidateUri(sender, args) {
    var uriRegex= /(ftp|http|https):\/\/(\w+:{0,1}\w*@)?(\S+)(:[0-9]+)?(\/|\/([\w#!:.?+=&%@!\-\/]))?/
      var isValid = uriRegex.test(args.Value);
      if(!isValid) {
          sender.innerHTML = "Invalid Uri";
      }
}


function appAccountValidateShortDesc(sender, args) {
    var isValid = true;
    var errorMessage = "";
    var shortDesc = (args.Value)+"";
    if(shortDesc.length > 100) {
        errorMessage = "Short Desc is too long";
    }
    else {
        isValid = true;
    }
    args.IsValid = isValid;
    sender.innerHTML = errorMessage;
}


// Util
function MySpaceAppsTrace(msg) {
    if($get("TraceConsole") != null) {
        Sys.Debug.trace('[' + MySpaceAppsTrace.caller.name + '] ' + msg);
    }
}
function MySpaceAppsTraceDump(obj, msg){
    if($get("TraceConsole") != null) {
        Sys.Debug.traceDump(obj, '[' + MySpaceAppsTraceDump.caller.name + '] ' + msg + ": ");
    }
}

// SurfaceInfo
MySpaceApps.SurfaceInfo = function(surfaceName, width, height) {
    this._surfaceName = surfaceName;
    this._width = width;
    this._height = height;
}

MySpaceApps.SurfaceInfo.prototype = {
    getSurfaceName: function() {
      return this._surfaceName;
    },   
    setSurfaceName: function(surfaceName) {
        this._surfaceName = surfaceName;
    },
    getWidth: function() {
          return this._width;
    },
    setWidth: function(width) {
        this._width = width;
    },
    getHeight: function() {
          return this._height;
    },
    setHeight: function(height) {
     this._height = height;
    }
}
MySpaceApps.SurfaceInfo.registerClass("MySpaceApps.SurfaceInfo", null, Sys.IDisposable);
// default surfaces
MySpaceApps.Surfaces.Canvas = new MySpaceApps.SurfaceInfo("canvas", 800, 500);
MySpaceApps.Surfaces.ProfileLeft = new MySpaceApps.SurfaceInfo("profile.left", 300, 190);
MySpaceApps.Surfaces.ProfileRight = new MySpaceApps.SurfaceInfo("profile.right", 430, 270);
MySpaceApps.Surfaces.Home = new MySpaceApps.SurfaceInfo("home",290,190);

// this function sets the default width / height on a profile surface when
// the radio button is toggled
MySpaceApps.Surfaces.getDefaultSurfaceInfo = function(surfaceName, txtWidth, txtHeight) {
    txtWidthElement = $get(txtWidth);
    txtHeightElement = $get(txtHeight);
    
    // degrade gracefully
    if(txtWidthElement == null || txtHeightElement == null) {
        return;
    }
    
    if(surfaceName == "profile.left")
    {
        txtWidthElement.value = MySpaceApps.Surfaces.ProfileLeft.getWidth();
        txtHeightElement.value = MySpaceApps.Surfaces.ProfileLeft.getHeight();
    }
    else if(surfaceName == "profile.right")
    {
        txtWidthElement.value = MySpaceApps.Surfaces.ProfileRight.getWidth();
        txtHeightElement.value = MySpaceApps.Surfaces.ProfileRight.getHeight();
    }
}

/////////////////////////////////////
// Surface Editor
/////////////////////////////////////
MySpaceApps.Surfaces.SurfaceEditor = function(surface) {
    this._surface = surface;
    this._rbHtmlId = "rbHtml";
    this._rbFlashId = "rbFlash";
    this._rbIFrameId = "rbExternalIframe";
    this._txtSourceId = "tbRawText";
    this._txtSource = $get("tbRawText");
    this._hasErrors = false;
    this._saveForm = false;
}

MySpaceApps.Surfaces.SurfaceEditor.prototype = {
    
    _jsName: function(name) {
        return this._surface + "_" + name;
    },

    _hideSpinner: function() {
        $get(this._surface + "_spinner").style.visibility = "hidden";
    },
    
    _showSpinner: function() {
        $get(this._surface + "_spinner").style.visibility = "visible";
    },
    
    toggleSaveButton: function() {
        $get(this._surface + "_savebutton").disabled = !$get(this._surface + "_savebutton").disabled;
    },
    
    setStatusMessage: function(statusStr, warningCount) {
        var msg = "";
        if(statusStr == "Success") {
            msg = "Your source contains no errors or warnings.";   
        }
        else if(statusStr == "SuccessWithWarnings") {
            msg = "Your source contains " + warningCount + " warning(s) that were corrected.";
        }
        else if(statusStr == "Failure") {
            msg = "Your source contains errors. Please correct and try again.";
        }
        this._hideSpinner();
    },
    
    toggleLink: function(linkElementId, displayId, showLinkText, hideLinkText) {
        displayElement = $get(displayId);
        linkElement = $get(linkElementId);
        
        if(displayElement.style.display == "none") {
            linkElement.innerHTML = hideLinkText;   
            $("#" + displayId).show();
        }
        else {
            linkElement.innerHTML = showLinkText;
            $("#" + displayId).hide();
        }
    },
    
    // toggles between flash and html panels
    toggleDisplay: function() {
        var rbHtml = $get(this._rbHtmlId);
        var rbFlash = $get(this._rbFlashId);
        $("#li_uploadsource,#li_inputsource,#li_iframesource,#li_flashinfo,#li_osversion,#li_osfeatures,.flashhelptext").hide();
        if(rbHtml.checked) {
            $("#li_uploadsource,#li_inputsource,#li_flashinfo,#li_osversion,#li_osfeatures,.flashhelptext").show();
            //$("#li_iframesource").hide();
        } else if (rbFlash.checked){
            $("#li_uploadsource,.flashhelptext").show();
           // $("#li_inputsource,#li_iframesource,#li_flashinfo").hide();
        } else {
            $("#li_iframesource").show();
            //$("#li_uploadsource,#li_inputsource,#li_flashinfo").hide();
        }
    },
    
    validate: function() {
        this._showSpinner();
        
        // call web service
        var txtSource = "" + $get(this._txtSourceId).value;
        txtSource = txtSource.replace(/^\s+|\s+$/g, ''); 
        if(txtSource.length == 0) {
            this.setStatusMessage("Success", 0);
        }
    },
    
    save: function() {
        this._saveForm = true;
        var rbHtml = $get(this._rbHtmlId);
        this._hasErrors = false;
        this.submitSource();
        return true;
    },
    
    submitSource: function() {
        if(this._saveForm) {
            if(this._hasErrors) {
                alert("Your code has errors! Please fix and try again.");
                return;
            }
            var form = $get("aspnetForm");
            form.action = form.action + "#tab_" + this._surface + "_surface";
            this._saveButton.click();
        }
    }
}

MySpaceApps.Surfaces.SurfaceEditor.registerClass("MySpaceApps.Surfaces.SurfaceEditor");


//////////////////////////////////////////////////////
// CAJA controls
//////////////////////////////////////////////////////
MySpaceApps.Caja.CajaControl = function(surface, saveButtonName, rbHtmlId, rbFlashId, rbIFrameId, txtSourceId, cbUseCajaId) {
    this._surface = surface;
    this._rbHtmlId = rbHtmlId;
    this._rbFlashId = rbFlashId;
    this._rbIFrameId = rbIFrameId;
    this._txtSourceId = txtSourceId;
    this._txtSource = $get(txtSourceId);
    this._tblId = this._surface + "_caja_table";
    if(MySpace.Web.Developer.Services.Caja != null) {
        this._cajaService = MySpace.Web.Developer.Services.Caja.CajaService;
    }
    
    this._hasErrors = false;
    this._saveButton = document.aspnetForm[ saveButtonName ];
    this._saveForm = false;
    this._validateButton = $get(this._surface + "_validatebutton");
    this._cbUseCajaId = cbUseCajaId;
}

// CajaControl members
MySpaceApps.Caja.CajaControl.prototype = {

    _displayBlock: function(id) {
        if(typeof(id) == "string") {
            $get(id).style.display = "block";
        }
        else {
            id.style.display = "block";
        }
    },
    
    _displayNone: function(id) {
        if(typeof(id) == "string") {
            $get(id).style.display = "none";
        }
        else {
            id.style.display = "none";
        }
    },

    _jsName: function(name) {
        return this._surface + "_" + name;
    },

    _hideSpinner: function() {
        $get(this._surface + "_spinner").style.visibility = "hidden";
    },
    
    _showSpinner: function() {
        $get(this._surface + "_spinner").style.visibility = "visible";
    },
    
    toggleSaveButton: function() {
        $get(this._surface + "_savebutton").disabled = !$get(this._surface + "_savebutton").disabled;
    },
    
    setStatusMessage: function(statusStr, warningCount) {
        var msg = "";
        if(statusStr == "Success") {
            msg = "Your source contains no errors or warnings.";   
        }
        else if(statusStr == "SuccessWithWarnings") {
            msg = "Your source contains " + warningCount + " warning(s) that were corrected.";
        }
        else if(statusStr == "Failure") {
            msg = "Your source contains errors. Please correct and try again.";
        }
        $get(this._surface + "_caja_summary").innerHTML = msg;
        this._displayBlock(this._jsName("caja_tab"));
        this._displayNone(this._jsName("caja_table"));
        this._hideSpinner();
    },
    
    setCajaOutput: function(statusStr, output) {
        var txtCajaOutput = $get(this._jsName("cajoled_code"));
        txtCajaOutput.value = output;
    },
    
    toggleLink: function(linkElementId, displayId, showLinkText, hideLinkText) {
        displayElement = $get(displayId);
        linkElement = $get(linkElementId);
        
        if(displayElement.style.display == "none") {
            linkElement.innerHTML = hideLinkText;   
            this._displayBlock(displayElement);
        }
        else {
            linkElement.innerHTML = showLinkText;
            this._displayNone(displayElement);
        }
    },
    
    // displays the table of caja warnings
    toggleCajaTable: function() {
        this._displayBlock(this._jsName("caja_table"));
    
    },
    
    // display the cajoled code
    toggleCajoledCode: function() {
        this._displayBlock(this._jsName("cajoled_code"));
        $get(this._jsName("show_cajoled_code_link")).innerHTML = "Hide cajoled code";
    },
    
    // toggles between flash and html panels
    toggleDisplay: function() {
        var rbHtml = $get(this._rbHtmlId);
        var rbFlash = $get(this._rbFlashId);

        $get(this._jsName("li_uploadsource")).style.display = "none";
        $get(this._jsName("li_inputsource")).style.display = "none";
        $get(this._jsName("li_iframesource")).style.display = "none";
        $("#" + this._jsName("li_osversion")).hide();
        $("#" + this._jsName("li_flashinfo")).hide();
        
        if(rbHtml.checked) {
            $get(this._jsName("li_uploadsource")).style.display = "block";
            $get(this._jsName("li_inputsource")).style.display = "block";
            $("#" + this._jsName("li_osversion")).show();
            $("#" + this._jsName("li_flashinfo")).show();
            this._validateButton.style.visibility = "visible";
        } else if (rbFlash.checked){
            $get(this._jsName("li_uploadsource")).style.display = "block";
            this._validateButton.style.visibility = "hidden";
        } else {
            $get(this._jsName("li_iframesource")).style.display = "block";
            this._validateButton.style.visibility = "hidden";
        }
    },
    
    validate: function() {
        this._showSpinner();
        
        // call web service
        var txtSource = "" + $get(this._txtSourceId).value;
        txtSource = txtSource.replace(/^\s+|\s+$/g, ''); 
        if(txtSource.length == 0) {
            this.setStatusMessage("Success", 0);
        }
        else {
            this._cajaService.Cajole(txtSource, this.cajoleSuccessCallback, 
                this.cajoleFailureCallback, this); 
        }
    },
    
    save: function() {
        this._saveForm = true;
        
        var rbHtml = $get(this._rbHtmlId);
        if(!rbHtml.checked || !this._bUseCaja()) {
            this._hasErrors = false;
            this.submitSource();
            return true;
        }
        this.validate();
    },
    
    _bUseCaja: function() {
        return $get(this._cbUseCajaId) != null && 
                $get(this._cbUseCajaId).checked;
    },

    cajole: function(saveForm) {

    },
    
    submitSource: function() {
        if(this._saveForm) {
            if(this._hasErrors) {
                alert("Your code has errors! Please fix and try again.");
                return;
            }
            var form = $get("aspnetForm");
            form.action = form.action + "#tab_" + this._surface + "_surface";
            /*
            if(this._bUseCaja()){
                this._txtSource.value = $get(this._jsName("cajoled_code")).value;
            }
            */
            this._saveButton.click();
        }
    },
    
    cajoleSuccessCallback: function(result, cajaControl) {
        MySpaceAppsTraceDump(cajaControl, "caja Control");
        MySpaceAppsTraceDump(result, "success");
        
        var messageContainer = $get(cajaControl._tblId);
        // clear previous rows
        rows = messageContainer.rows;
        while(rows.length > 1) {
            messageContainer.deleteRow(rows.length - 1);
        }
        
        var warningCount = 0;
        
        if(result.CajaMessages == null || result.CajaMessages.length == 0) {
            messageContainer.style.display = "none"
        }
        else {
            messageContainer.style.display = "block";
            // write warnings rows
            for(var i = 0; i < result.CajaMessages.length; i++) {
                var cajaMessage = result.CajaMessages[i];
                
                var skipRow = false;
                if(cajaMessage.MessageType) {
                    var typeStr = MySpace.Caja.Client.CajaMessageType.toString(cajaMessage.MessageType);
                    if("Exception" == typeStr) {
                        skipRow = true;
                    }
                }
                
                if(!skipRow) {
                    var newRow = messageContainer.insertRow(i+1);
                    cajaControl._appendToRow(newRow, cajaMessage);
                }
            }
            
            warningCount = result.CajaMessages.length;
        }
        
        var statusStr = MySpace.Caja.Client.CajaStatus.toString(result.Status);
        cajaControl.setStatusMessage(statusStr, warningCount);
        cajaControl.setCajaOutput(statusStr, result.CajoledOutput);
        cajaControl._hasErrors = result.HadError;

        cajaControl.submitSource();
        return;
    }, 
    
    cajoleFailureCallback: function(result, cajaControl) {
        alert("failure: " + result);
    },
    
    // private functions
     
    _appendToRow: function(row, cajaMessage) {
        var i = 0; 
        this._appendCell(row, i++, cajaMessage.Type);
        this._appendCell(row, i++, cajaMessage.Message);
        
        var lineNum = cajaMessage.LineNumber;
        if(lineNum > 0) {
            lineNum = lineNum - 1;
        }
        
        this._appendCell(row, i++, lineNum);
        this._appendCell(row, i++, cajaMessage.CharNumber); 
    },
    
    _appendCell: function(row, cellNumber, content) {
        var newCell = row.insertCell(cellNumber);
        newCell.innerHTML = content;
    }
}

MySpaceApps.Caja.CajaControl.registerClass("MySpaceApps.Caja.CajaControl");

var cajaControls = new Array();

function validateAppSource() {
    alert("validating app source...");
    for(var i = 0; i < cajaControls.length; i++) {
        cajaControls[i].cajole();
    }
    return false;
}

MySpaceApps.Caja.addControl = function(cajaControl) {
    cajaControls.push(cajaControl);
    MySpaceAppsTrace("caja control.length = " + cajaControls.length);
}

Sys.Application.add_init(cajaInit);
function cajaInit() {
}


///////////////////////////////////////////////////////////////////////////
