/**
 * Draftfcb JavaScript Form Validation Class
 * Author: D. Liao <daniel.liao@draftfcb.com>
 * Requires functions provided by jquery.js
 */

function DraftfcbForm(objForm) {
    //constants

    //properties
    this.FormHandle = objForm;
    this.FormPassed = true;
    this.ErrorBox = null;
    this.BadDates = new Array( { M: 1, D: 30 }, { M: 1, D: 31 }, { M: 3, D: 31 }, { M: 5, D: 31 }, { M: 8, D: 31 }, { M: 10, D: 31 } );
    this.Rules = new Array();

    //methods
    this.Init = init;
    this.Validate = validate;
    this.Required = required;
    this.RuleTest = ruleTest;
    this.NoMatchNationality = noMatchNationality;
    this.DateNotPast = dateNotPast;
    this.ReturnIsLater = returnIsLater;
    this.DateValid = dateValid;
    this.IsLeapYear = isLeapYear;

    //call the initialization method
    this.Init();
  
    //initialization: set up event handlers in the form
    function init() {
    this.FormHandle.onsubmit = function() {
        try {
            handleSubmit();
        } catch(e) { }
        return formValidate();
        }
    }

    //the main validation method
    function validate() {
        var formPassed = true;
        for (var i = 0; i < this.Rules.length; i++) {
            var currRule = this.Rules[i];
            var rulePassed = this.RuleTest(currRule, i);
            if (!rulePassed) {
                $("#" + currRule.ErrorId).show();
                formPassed = false;
            } else {
                $("#" + currRule.ErrorId).hide();
            }
        }

        if (!formPassed) {
            this.ErrorBox.show();
        } else {
            this.ErrorBox.hide();
            try {
                handleTarget();
            } catch(e) { }
        }

//        window.location = "#";
        return formPassed;
    }

    //method to test required fields of various types for non-empty values
    function required(objElement) {
        switch(objElement.type) {
            case "text":
                return (!objElement.value == "");
                break;

            case "hidden":
                return (!objElement.value == "");
                break;

            case "checkbox":
                return objElement.checked;
                break;

            case "select-one":
                return (!objElement[objElement.selectedIndex].value == "");
                break;

            case "select-multiple":
                var hasSelections = false;
                for (var j=0; j<objElement.options.length; j++) {
                    if (objElement.options[j].selected) {
                        hasSelections = true;
                        break;
                    }
                }
                return hasSelections;
                break;

            default:
                return false;
        }
    }

    function ruleTest(objRule, intRuleIndex) {
        var rulePassed = false;
        if (objRule.Field) {
            if (this.FormHandle.elements[objRule.Field] !== undefined) {
                rulePassed = eval("this." + objRule.Method + "(this.FormHandle.elements['" + objRule.Field + "'])");
            } else {
                alert("debug: field '" + objRule.Field + "' not found in page.");
            }
        } else if (objRule.Params) {
            rulePassed = eval("this." + objRule.Method + "(" + intRuleIndex + ")");
        } else {
            alert("debug: no Field or Params found for validation rule");
        }

        return rulePassed;
    }

    // method to verify that 2 fields are non-matching in value
    function noMatchNationality(objElement) {
        if (objElement.selectedIndex) {
            if (objElement[objElement.selectedIndex].value == this.FormHandle.elements['NA'][this.FormHandle.elements['NA'].selectedIndex].value) {
                return false;
            }
        }

        return true;
    }

    function dateNotPast(objElement) {
        var fieldValue = objElement.value.split("/");
        var todaysDate = new Date();
        todaysDate = new Date(todaysDate.getFullYear(), todaysDate.getMonth(), todaysDate.getDate());
        var fieldDate = new Date(fieldValue[2], fieldValue[1] - 1, fieldValue[0]);
        return (fieldDate >= todaysDate);
    }

    function returnIsLater(intRulesIndex) {
        var objParams = this.Rules[intRulesIndex].Params;
        var startValue = this.FormHandle.elements[objParams.StartField].value.split("/");
        var startDate = new Date(startValue[2], startValue[1] - 1, startValue[0]);
        var endValue = this.FormHandle.elements[objParams.EndField].value.split("/");
        var endDate = new Date(endValue[2], endValue[1] - 1, endValue[0]);
        return (startDate <= endDate);
    }

    function dateValid(objElement) {
        var fieldDate = objElement.value.split("/");
        var fieldDay = (fieldDate[0]) ? fieldDate[0] : -1;
        var fieldMonth = (fieldDate[1]) ? fieldDate[1] - 1 : -1;
        var fieldYear = (fieldDate[2]) ? fieldDate[2] : -1;

        var datePassed = true;

        if (fieldDay == -1 || fieldMonth == -1 || fieldYear == -1) {
            datePassed = false;
        }

        if (fieldDay > 31 || fieldMonth > 11) {
            datePassed = false;
        }

        if (fieldYear.length !== 4) {
            datePassed = false;
        }

        for (var i=0; i<this.BadDates.length; i++) {
            var currBadDate = this.BadDates[i];
            if ((fieldMonth == currBadDate.M) && (fieldDay == currBadDate.D)) {
                datePassed = false;
                break;
            }
        }

        if (!this.IsLeapYear(fieldYear) && (fieldMonth == 1) && (fieldDay == 29)) {
            datePassed = false;
        }

        return datePassed;
    }

    function isLeapYear(intYear) {
        var isLeap = false;
        if ((intYear % 4) == 0) {
            if ((intYear % 100) == 0) {
                isLeap = ((intYear % 400) == 0);
            } else {
                isLeap = true;
            }
        }
        return isLeap;
    }

}
