﻿/// <reference name="MicrosoftAjax.js"/>

Type.registerNamespace("Tensator");

Tensator.Configurator = function(element) {
    Tensator.Configurator.initializeBase(this, [element]);

    this._optionChangedHandler = null;
    this._optionPopulatedHandler = null;
    this._quantityChangedHandler = null;
    this._attributeQuantityChangedHandler = null;
    this._optionDisposing = null;

    this._optionControls = null;
    this._quantityControlContainers = null;
    this._quantityControls = null;
    this._priceElement = null;
    this._quantityElement = null;
    this._maxQuantity = null;
    this._quantityControlsToShow = null;
    this._quantityValues = null;

    this._imagesToDisplay = null;
    this._selectedOptions = null;

    this._lastResponse = null;

    this._usernameElement = null;
    this._passwordElement = null;
    this._configurationNameElement = null;

    this._configNotesElement = null;

    this._saveConfiguration = null;
    this._isComplete = false;
    this._canBuyOnline = false;
    this._loading = false;
    this._minumumValues = false;
}

Tensator.Configurator.prototype = {
    initialize: function() {
        Tensator.Configurator.callBaseMethod(this, 'initialize');

        this._optionChangedHandler = Function.createDelegate(this, this.optionChanged);
        this._optionPopulatedHandler = Function.createDelegate(this, this.optionPopulated);
        this._optionDisposing = Function.createDelegate(this, this.optionDisposing);

        this.showChildOptions();
        this.updateSelectedOptions();
        this.updateImages();

        var element; var i; var controls = this.get_optionControls();
        for (i = 0; i < controls.length; i++) {
            element = $find(controls[i].toString());
            if (element != null) {
                element.add_selectionChanged(this.optionChanged);
                element.add_populated(this._optionPopulatedHandler);
                element.add_disposing(this._optionDisposing);
            }
        }

        element = this.get_quantityElement();
        if (element != null) {
            this._quantityChangedHandler = Function.createDelegate(this, this.quantityChanged);
            $addHandler(element, "change", this._quantityChangedHandler);
        }

        this._attributeQuantityChangedHandler = Function.createDelegate(this, this.attributeQuantityChanged);
        controls = this.get_quantityControls();
        for (i = 0; i < controls.length; i++) {
            element = $get(controls[i].toString());
            if (element != null) {
                $addHandler(element, "change", this._attributeQuantityChangedHandler);
            }
        }

        var saveConfig = $find(this.get_saveConfiguration());
        if (saveConfig != null) {
            saveConfig.set_OnOkScript('$find(\'ucConfigurator\').saveConfiguration();');
            saveConfig.set_OnCancelScript('$find(\'ucConfigurator\').cancelConfiguration();');
        }
    },
    dispose: function() {
        var saveConfig = $find(this.get_saveConfiguration());
        if (saveConfig != null) {
            saveConfig.set_OnOkScript(null);
            saveConfig.set_OnCancelScript(null);
        }

        var element = this.get_quantityElement();
        if (element != null) {
            $removeHandler(element, "change", this._quantityChangedHandler);
        }

        var controls = this.get_quantityControls();
        for (i = 0; i < controls.length; i++) {
            element = $get(controls[i].toString());
            $removeHandler(element, "change", this._attributeQuantityChangedHandler);
        }

        for (i = 0; i < controls.length; i++) {
            element = $find(controls[i].toString());
            if (element != null) {
                element.remove_selectionChanged(this.optionChanged);
                element.remove_populated(this._optionPopulatedHandler);
                element.remove_disposing(this._optionDisposing);
            }
        }

        $clearHandlers(this.get_element());

        delete this._optionPopulatedHandler;
        delete this._optionChangedHandler;
        delete this._quantityChangedHandler;
        delete this._attributeQuantityChangedHandler;

        Tensator.Configurator.callBaseMethod(this, 'dispose');
    },
    //properties
    get_optionControls: function() {
        return this._optionControls;
    },
    set_optionControls: function(value) {
        if (this._optionControls !== value)
            this._optionControls = value;
    },
    get_quantityControlContainers: function() {
        return this._quantityControlContainers;
    },
    set_quantityControlContainers: function(value) {
        if (this._quantityControlContainers !== value)
            this._quantityControlContainers = value;
    },
    get_quantityControls: function() {
        return this._quantityControls;
    },
    set_quantityControls: function(value) {
        if (this._quantityControls !== value)
            this._quantityControls = value;
    },
    get_priceElement: function() {
        return this._priceElement;
    },
    set_priceElement: function(value) {
        if (this._priceElement !== value)
            this._priceElement = value;
    },
    get_quantityElement: function() {
        if (this._quantityElement != null)
            return $get(this._quantityElement);
        else
            return null;
    },
    set_quantityElement: function(value) {
        if (this._quantityElement !== value)
            this._quantityElement = value;
    },
    get_maxQuantity: function() {
        return this._maxQuantity;
    },
    set_maxQuantity: function(value) {
        if (this._maxQuantity !== value)
            this._maxQuantity = value;
    },
    get_quantityControlsToShow: function() {
        return this._quantityControlsToShow;
    },
    set_quantityControlsToShow: function(value) {
        if (this._quantityControlsToShow !== value)
            this._quantityControlsToShow = value;
    },
    get_imagesToDisplay: function() {
        return this._imagesToDisplay;
    },
    set_imagesToDisplay: function(value) {
        if (this._imagesToDisplay !== value)
            this._imagesToDisplay = value;
    },
    get_selectedOptions: function() {
        return this._selectedOptions;
    },
    set_selectedOptions: function(value) {
        if (this._selectedOptions !== value)
            this._selectedOptions = value;
    },
    get_saveConfiguration: function() {
        return this._saveConfiguration;
    },
    set_saveConfiguration: function(value) {
        if (this._saveConfiguration !== value)
            this._saveConfiguration = value;
    },
    get_usernameElement: function() {
        return this._usernameElement;
    },
    set_usernameElement: function(value) {
        if (this._usernameElement !== value)
            this._usernameElement = value;
    },
    get_passwordElement: function() {
        return this._passwordElement;
    },
    set_passwordElement: function(value) {
        if (this._passwordElement !== value)
            this._passwordElement = value;
    },
    get_configurationNameElement: function() {
        return this._configurationNameElement;
    },
    set_configurationNameElement: function(value) {
        if (this._configurationNameElement !== value)
            this._configurationNameElement = value;
    },
    get_isComplete: function() {
        if (!this._isComplete) {
            alert('Your configuration is incomplete.  Please make sure that you have completed all steps before adding to your basket.');
            return false;
        }

        if (!this.checkQuantityValues()) {

            return false;
        }

        if (!this.get_canBuyOnline()) {
            alert('Your configuration is not available to buy online.');
            return false;
        }

        return this._isComplete;
    },
    set_isComplete: function(value) {
        if (this._isComplete !== value)
            this._isComplete = value;
    },
    get_canBuyOnline: function() {
        return this._canBuyOnline;
    },
    set_canBuyOnline: function(value) {
        if (this._canBuyOnline !== value)
            this._canBuyOnline = value;
    },
    get_quantityValues: function() {
        return this._quantityValues;
    },
    set_quantityValues: function(value) {
        if (this._quantityValues !== value)
            this._quantityValues = value;
    },
    get_minumumValues: function() {
        return this._minumumValues;
    },
    set_minumumValues: function(value) {
        if (this._minumumValues !== value)
            this._minumumValues = value;
    },
    get_configNotesElement: function() {
        return this._configNotesElement;
    },
    set_configNotesElement: function(value) {
        if (this._configNotesElement !== value)
            this._configNotesElement = value;
    },

    //methods
    addCommas: function(strValue) {
        var objRegExp = new RegExp('(-?[0-9]+)([0-9]{3})');

        //check for match to search criteria
        while (objRegExp.test(strValue)) {
            //replace original string with first group match, a comma, then second group match
            strValue = strValue.replace(objRegExp, '$1,$2');
        }
        return strValue;
    },
    getSelectedValues: function() {
        var element; var i; var control; var controls = this.get_optionControls();
        var kvp; var result = new Array(); var visibleCount = 0;

        for (i = 0; i < controls.length; i++) {
            control = $find(controls[i].toString());
            if (control != null) {
                element = control.get_element();

                if (element.parentNode.style.display != 'none')
                    visibleCount += 1;

                kvp = { 'Key': Number(control.get_Category()),
                    'Value': element.options[element.selectedIndex].value
                };
                if (kvp.Value != '-1' && kvp.Value != '')
                    Array.add(result, kvp);
            }
        }

        controls = this.get_quantityControls();
        for (i = 0; i < controls.length; i++) {
            control = $get(controls[i].toString());
            if (control != null) {
                if (control.parentNode.style.display != 'none') {
                    visibleCount += 1;

                    kvp = { 'Key': Number(control.attributes['attributeid'].value),
                        'Value': control.value
                    };

                    if (control.value.trim().length > 0) {
                        Array.add(result, kvp);
                    }
                }
            }
        }

        this.set_isComplete(visibleCount == result.length);

        return Sys.Serialization.JavaScriptSerializer.serialize(result);
    },
    updateSelectedValues: function(quantity, selectedValues, context, updateValues) {
        if (updateValues == null)
            updateValues = true;

        configurator.UpdateSelectedValues(
                quantity,
                selectedValues,
                updateValues,
                context.methodCallComplete,
                context.methodCallError,
                context
            );
    },
    //event handlers
    optionPopulated: function(sender, e) {
        var count = sender.get_element().options.length;
        var element = $get('pnl' + sender.get_id());

        if (count > 1) { element.style.display = ''; }
        else { element.style.display = 'none'; }
    },
    optionChanged: function(sender, e) {
        $get('cMessages').innerHTML = '';

        var ucConfig = $find('ucConfigurator');
        var selectedValues = ucConfig.getSelectedValues();

        var updateValues = false;
        if (e.get_oldValue() != null) { updateValues = true; }

        
        var quantity = 1;

        if (ucConfig.get_quantityElement() != null)
            quantity = ucConfig.get_quantityElement().value;
        
        //if (updateValues)
        ucConfig.updateSelectedValues(quantity, selectedValues, ucConfig, updateValues);
    },
    attributeQuantityChanged: function(sender, e) {
        var selectedValues = this.getSelectedValues();
        var quantity = 1;
        if (this.get_quantityElement() != null)
            quantity = this.get_quantityElement().value;

        this.updateSelectedValues(quantity, selectedValues, this);
    },
    checkQuantity: function(returnQuantity) {
        var ucConfig = $find('ucConfigurator');

        var quantity = 1;
        if (this.get_quantityElement() != null)
            quantity = this.get_quantityElement().value;

        var maxQuantity = this.get_maxQuantity();
        var updateValues = true;



        if (maxQuantity != null) {

            if (quantity >= maxQuantity) {
                quantity = maxQuantity - 1;

                var element = ucConfig.get_quantityElement();
                element.value = quantity;

                var message = 'For orders of ' + maxQuantity + '+ units please contact Sales Support on +44 (0) 1908 684600 for prices and lead times';
                $get('cMessages').innerHTML = message;
            }
        }

        if (returnQuantity) {
            return quantity;
        }
        else {
            return null;
        }
    },
    quantityChanged: function(sender, e) {
        var ucConfig = $find('ucConfigurator');
        var selectedValues = ucConfig.getSelectedValues();
        var quantity = ucConfig.checkQuantity(true);
        if (quantity != null) {
            ucConfig.updateSelectedValues(quantity, selectedValues, ucConfig);
        }
    },
    optionDisposing: function(sender, e) {
        var element; var i; var controls = this.get_optionControls();
        for (i = 0; i < controls.length; i++) {
            element = $find(controls[i]);
            if (element != null) {
                element.remove_selectionChanged(this.optionChanged);
                element.remove_populated(this._optionPopulatedHandler);
                element.remove_disposing(this._optionDisposing);
            }
        }
    },
    checkQuantityValues: function() {
        var atrribueId; var result = true; var control; var item;
        var controlsToShow = this.get_quantityControls(); var isQuantity;
        var minimumValues = this.get_minumumValues(); var attributeId; var done = false;

        if (minimumValues != null) {
            for (q = 0; q < controlsToShow.length; q++) {

                control = $get(controlsToShow[q]);
                if (control != null) {
                    if (control.parentElement.style.display != 'none') {

                        for (i = 0; i < minimumValues.length; i++) {
                            attributeId = control.attributes['attributeid'].value;
                            item = control.attributes['item'].value; isQuantity = control.attributes['isquantity'].value

                            if (isNaN(control.value) && isQuantity == 'True') { done = true; result = false; break; }

                            if (attributeId == minimumValues[i].Key && minimumValues[i].Value > control.value) {
                                alert(item + ' requires a minium of ' + minimumValues[i].Value);
                                done = true; result = false; break;
                            }
                        }

                        if (done)
                            break;

                    }

                }

            }
        }

        return result;
    },
    // this is only for the quantity controls - as the ddl are controled from the cdd handlers
    showChildOptions: function() {
        var controls = this.get_quantityControlContainers(); var controlsToShow = this.get_quantityControlsToShow();
        var display = ''; var control;

        for (i = 0; i < controls.length; i++) {
            var found = false;
            element = $get('pnl' + controls[i]);

            if (controlsToShow != null) {
                for (q = 0; q < controlsToShow.length; q++) {
                    if (controlsToShow[q] == controls[i]) {
                        found = true; break;
                    }
                }

                if (found) { display = ''; }
                else { display = 'none'; }

                if (element != null) { element.style.display = display; }
            }
        }
    },
    updateImages: function() {
        var images = this.get_imagesToDisplay();
        for (i in images) {
            element = $get('img' + images[i].Key);
            if (element != null)
                element.src = images[i].Value;
        }
    },
    updateSelectedOptions: function() {
        var selectedOptions = this.get_selectedOptions();
        var images = this.get_imagesToDisplay();
        if (images.length > 0) {
            for (i in selectedOptions) {
                if (images[i]) {
                    element = $get('span' + images[i].Key);
                    if (element != null)
                        element.innerHTML = selectedOptions[i].Value;
                }
            }
        }
    },
    methodCallComplete: function(result, userContext, methodName) {
        var found; var q; var i; var element; var clientResult = Sys.Serialization.JavaScriptSerializer.deserialize(result);

        var currentValues = userContext.getSelectedValues();
        var returnedValues = Sys.Serialization.JavaScriptSerializer.serialize(clientResult.ResponseValues);

        if (currentValues == returnedValues) {
            var quantity = 1;
            if (userContext.get_quantityElement() != null)
                quantity = userContext.get_quantityElement().value;

            userContext.set_minumumValues(clientResult.MinimumValues);

            userContext.get_priceElement().innerHTML = userContext.addCommas((clientResult.Price * quantity).toFixed(2));
            userContext.set_quantityControlsToShow(clientResult.QuantityControls);
            userContext.showChildOptions();

            userContext.set_imagesToDisplay(clientResult.Images);
            userContext.updateImages();

            userContext.set_selectedOptions(clientResult.SelectedOptions);
            userContext.updateSelectedOptions();

            userContext.set_maxQuantity(clientResult.MaxQuantity);
            userContext.checkQuantity(false);

            element = userContext.get_configNotesElement();
            if (element != null && element != undefined && clientResult.Notes != null) {
                element.innerHTML = clientResult.Notes;
            }

            for (i in clientResult.SelectedOptions) {
                element = $get('span' + clientResult.Images[i].Key);
                if (element != null)
                    element.innerHTML = clientResult.SelectedOptions[i].Value;
            }

            userContext.set_canBuyOnline(clientResult.CanBuyOnline);
            if (clientResult.CanBuyOnline) {
                element = $get('divNotOnline').style.display = 'none';
            } else {
                element = $get('divNotOnline').style.display = '';
            }
        }
    },
    saveConfigurationValid: function() {
        var result = true;
        var message = '';
        if (this.get_usernameElement().value.trim() == '') {
            result = false;
            message += 'Please enter your username.\r\n';
        }
        if (this.get_passwordElement().value.trim() == '') {
            result = false;
            message += 'Please enter your password.\r\n';
        }
        if (this.get_configurationNameElement().value.trim() == '') {
            result = false;
            message += 'Please a name for your configuration.\r\n';
        }

        if (!result) {
            alert(message);
            $find(this.get_saveConfiguration()).show();
        }
        return result;
    },
    resetSaveConfiguration: function() {
        this.get_usernameElement().value = '';
        this.get_passwordElement().value = '';
        this.get_configurationNameElement().value = '';
    },
    saveConfiguration: function() {
        if (this.saveConfigurationValid()) {
            configurator.SaveCurrentConfiguration(
                this.get_usernameElement().value.toString(),
                this.get_passwordElement().value.toString(),
                this.get_configurationNameElement().value.toString(),
                this.saveConfigurationCallComplete,
                this.methodCallError,
                this
            );
        }
    },
    cancelConfiguration: function() {
        this.resetSaveConfiguration();
    },
    saveConfigurationCallComplete: function(result, userContext, methodName) {
        var state = Sys.Serialization.JavaScriptSerializer.deserialize(result);
        if (state.Key) {
            userContext.resetSaveConfiguration();
            alert(state.Value);
        }
        else {
            alert(state.Value);
            $find(userContext.get_saveConfiguration()).show();
        }


    },
    methodCallError: function(error, userContext, methodName) {
        if (error !== null) {
            alert(error.get_message());
        }
    }
}
Tensator.Configurator.registerClass('Tensator.Configurator', Sys.UI.Control);

if (typeof(Sys) !== 'undefined') Sys.Application.notifyScriptLoaded();

