(function($) {
    $.fn.vipPhoneList = function(options) {
        var opts = $.extend({}, $.fn.vipPhoneList.defaults, options);
        var priceSlider;
        var root  = $(this);
        var brands;
        var tariffGroups;
        var propertyGroups;
        var models = {};
        var phones;
        var phoneCriteria;
        return this.each(function() {
            function initialize(){
                $.getJSON('/php/phones/data.php?action=initList&origin_page_id=' + pageId, function(data){
                    brands = data.data.brands;
                    tariffGroups = data.data.tariffGroups;
                    propertyGroups = data.data.propertyGroups;
                    phoneCriteria = data.data.phoneCriteria;
                    phones = data.data.phones;
                    initModels();
                    populateTariffSelect(tariffGroups);
                    initUi();
                    populateList(phones);
                    setHeights();
                    dump('<p>initialized</p>')
                });
            }
            function initUi(){
                initModels();
                initSlider();
                initCriteria();
                populateBrands();
                initEvents();
                $(root).find("#amount").val('$' + $(root).find("#slider-range").slider("values", 0) + ' - $' + $(root).find("#slider-range").slider("values", 1));
                dump('<p>ui initialized</p>');
            }
            function populateBrands(){
                for(var i=0;i<brands.length;i++){
                    var cleanBrand = brands[i].name.replace(/[^\w\s]/, '');
                    if (options.urlBrand && brands[i].name == options.urlBrand){
                        $('#brand').append('<option selected=\"selected\" value="' + brands[i].Id + '">' + brands[i].name + '</option>');
                    } else {
                        $('#brand').append('<option value="' + brands[i].Id + '">' + brands[i].name + '</option>');
                    }
                }
            }
            function initModels(){
                for(var i=0; i<brands.length;i++){
                    models[brands[i].Id] = [];
                }
                for(i=0; i<phones.length;i++){
                    models[phones[i].brand_id].push(phones[i]);
                }
            }
            function initCriteria(){
                var customCheckboxes = {};
                for(i=0;i<propertyGroups.length;i++){
                    customCheckboxes['group_' + propertyGroups[i].Id] = Array();
                }
                for(i=0;i<propertyGroups.length;i++){
                    for(j=0;j<phoneCriteria.length;j++){
                        if (getPropertyById(phoneCriteria[j].property_id).group_id == propertyGroups[i].Id){
                            customCheckboxes['group_' + propertyGroups[i].Id].push(phoneCriteria[j]);
                        }
                    }
                }
                var html = '';
                for(i=0;i<propertyGroups.length;i++){
                    if (customCheckboxes['group_' + propertyGroups[i].Id].length){
                        html += '<h3>' + propertyGroups[i].name + '</h3><ul class="clearfix">';
                        for(j=0;j<customCheckboxes['group_' + propertyGroups[i].Id].length;j++){
                            var prop = getPropertyById(customCheckboxes['group_' + propertyGroups[i].Id][j].property_id);
                            var propertyId = prop.Id;

                            html += '<li><input type="checkbox" class="criteria_checkbox" id="criteria_' + propertyId + '" /><label for="criteria_' + propertyId + '">' + prop.name + '</label></li>'
                        }
                        html += '</ul><div class="clear"></div>'
                    }
                }
                $(root).find('.advancedSearch').html(html);
            /*
                 *
                 *
                 *
                 *
                 *

               <h3>Naziv kategorije</h3>
<ul>
<li><a href="#"></a></li>
<li><a href="#"></a></li>
<li><a href="#"></a></li>
<li><a href="#"></a></li>
</ul>
<div class="clear"></div>



                var onDelimiter = parseInt(phoneCriteria.length / 4);
                if (onDelimiter < 1){
                    onDelimiter = 1;
                }
                var previousUl = 0;
                for(var i=0;i<phoneCriteria.length;i++){
                    var propertyId = phoneCriteria[i].property_id;
                    var prop = getPropertyById(propertyId);
                    if (previousUl + onDelimiter == i){
                        previousUl = i;
                        $(root).find('.advancedSearch ul:last').after('<ul></ul>');
                    }
                    $(root).find('.advancedSearch ul:last').append('<li><input type="checkbox" class="criteria_checkbox" id="criteria_' + propertyId + '" /><label for="criteria_' + propertyId + '">' + prop.name + '</label></li>');
                }*/
            }
            function initSlider(){
                $('body:eq(0)').append('<div class="handlePrice" id="minHandleDiv"></div>');
                $('body:eq(0)').append('<div class="handlePrice" id="maxHandleDiv"></div>');
                var my_tariffs = [];
                for(i=0;i<tariffGroups.length;i++){
                    for(j=0;j<tariffGroups[i].tariffs.length;j++){
                        my_tariffs.push(tariffGroups[i].tariffs[j]);
                    }
                }
                var minMax = getMaxMinTariffs(my_tariffs);
                priceSlider = $(root).find("#priceRange").slider({
                    range: true,
                    min: minMax[0],
                    max: minMax[1],
                    values: [minMax[0], minMax[1]],
                    change  : function(event,ui){
                        filter();
                    },
                    slide: function(event, ui) {
                        updatePriceHandles(event, ui)
                    }
                });
                setPriceHandles();
            }
            function setPriceHandles(){
	      $('#priceRange .ui-slider-handle').each(function(i, element){
		    
                    var value = priceSlider.slider('values')[i];
                    var currentDiv = $('.handlePrice').eq(i);
                    $(currentDiv).html(value + ' ' + opts.lang.RSD);
                    var xCoord = parseInt(($(element).offset().left + ($(element).width()/2)) - ($(currentDiv).width()/2), 10);
                    var yCoord = parseInt($(element).offset().top - $(currentDiv).height() - 10, 10);
                    $(currentDiv).css('left', xCoord + 'px');
                    $(currentDiv).css('top', yCoord + 'px');
                })
            }
            function updatePriceHandles(event, ui){
                var minHandleDiv = $('#minHandleDiv');
                var maxHandleDiv = $('#maxHandleDiv');

                var currentDiv = minHandleDiv;
                var otherDiv = maxHandleDiv;
                var index = 0;
                
                var value = ui.value;
                if (value == ui.values[1]){
                    index = 1;
                    currentDiv = maxHandleDiv;
                    otherDiv = minHandleDiv;
                }
                
                $(currentDiv).html(value + ' ' + opts.lang.RSD);
                var xCoord = parseInt(($(ui.handle).offset().left + ($(ui.handle).width()/2))- ($(currentDiv).width()/2), 10);
                var yCoord = parseInt($(ui.handle).offset().top - $(currentDiv).height(), 10) - 10;
                if (index == 0){
                    if (xCoord + $(currentDiv).width() > $(otherDiv).offset().left) {
                        $(maxHandleDiv).css('top', parseInt(yCoord - 15) + 'px');
                    } else {
                        $(maxHandleDiv).css('top', yCoord + 'px');
                    }
                } else {
                    if ($(otherDiv).offset().left + $(otherDiv).width() > xCoord) {
                        yCoord -= 15;
                    }
                }

                $(currentDiv).css('left', xCoord + 'px');
                $(currentDiv).css('top', yCoord + 'px');
            //dump('updated price handles (' + xCoord + 'x' + yCoord + ')');
            }
            function getMaxMinTariffs(tariffs){
                var max = -1
                var min = 1000000000000000;
                if (!(tariffs[0] && tariffs[0].Id)){
                    tariffs = [tariffs];
                }
                for(var i=0;i<tariffs.length;i++){
                    for(var j=0;j<phones.length;j++){
                        for(var k=0;k<phones[j].tariffGroups.length;k++){
                            for(var l=0;l<phones[j].tariffGroups[k].tariffs.length;l++){
                                if (tariffs[i].Id == phones[j].tariffGroups[k].tariffs[l].Id){
                                    var price = Number(phones[j].tariffGroups[k].tariffs[l].tariff_value.activation_fee);
                                    if (price < min){
                                        min = price;
                                    }
                                    if (price > max){
                                        max = price;
                                    }
                                }
                            }
                        }
                    }
                }
                if (max == -1 && min == 1000000000000000){
                    max = 0;
                    min = 0;
                }
                return [min, max];
            }
            function setSliderLimits(min, max){
                if (min == 0 && max==0){
                    return;
                } else {
                    if (min == max){
                        min = 0;
                    }
                }
                var values = priceSlider.slider("values");
                priceSlider.slider("option", "min", min);
                priceSlider.slider("option", "max", max);
                if (values[0] < min){
                    priceSlider.slider("values", 0, min);
                }
                else if (values[0] > max){
                    priceSlider.slider("values", 0, max);
                }
                if (values[1] < min){
                    priceSlider.slider("values", 1, min);
                }
                else if (values[1] > max){
                    priceSlider.slider("values", 1, max);
                }
                var newValues = priceSlider.slider("values");
                if (newValues[0] == newValues[1]){
                    if (newValues[0] == max){
                        priceSlider.slider("values", 0, min);
                    } else if (newValues[0] == min){
                        priceSlider.slider("values", 1, max);
                    }
                }
                dump('resetting slider limits');
            }
            function populateList(phoneArray, ul, callback){
                if (!ul){
                    ul = $('#phoneList');
                    $(ul).html('');
                }
		
                for(var i=0;i<phoneArray.length;i++){
                    var elem = document.createElement('li');
                    elem.innerHTML = getPhoneHtml(phoneArray[i]);
                    $(elem).attr('id', 'phone_' + phoneArray[i].Id).attr('data-id', phoneArray[i].Id);
                    $(ul).append(elem);
                }
                dump('phone list populated');
                if (callback){
                    callback.call();
                }
            }
            function getPhoneHtml(phone){
                var html = '<a class="phone_item" href="' + getPhoneHref(phone) +  '">';
                //var whString = ' height="100"';
                html += '<img class="phone_image" src="' + phone.list_image + '" alt="' + phone.model + '" />';
                html += '<div class="phone_name">' + getBrandById(phone.brand_id).name + ' ' + phone.model + '</div>';
                html += '</a>';
                return html;
            }
            function setHeights(ul){
            /*if (!ul){
                    ul = $('#phoneList');
                }
                var maxHeight = 0;
                $(ul).find('li').each(function(i, elem){
                    if ($(elem).height() > maxHeight){
                        maxHeight = $(elem).height();
                    }
                });
                $('#phoneList li').height(maxHeight);*/
            }

            function doSorting(filterPhones){
                if (filterPhones){
                    var newPhones = filterPhones;
                } else {
                    newPhones = phones;
                }
                if ($('#filterSort').val() == 'brand'){
                    newPhones.sort(function(a,b){
                        var brandA = a.brand.toLowerCase();
                        var brandB = b.brand.toLowerCase();
                        if (brandA < brandB) {
                            return -1
                        }
                        if (brandA > brandB) {
                            return 1
                        }
                        return 0;
                    });
                } else if ($('#filterSort').val() == 'price'){
                    newPhones.sort(function(a,b){
                        var priceA = parseFloat(a.price);
                        var priceB = parseFloat(b.price);
                        if (priceA < priceB) {
                            return -1
                        }
                        if (priceA > priceB) {
                            return 1
                        }
                        return 0;
                    });
                }
                return newPhones;
            }
            function filter(e){
                dump('filtering');
                var start = new Date().getTime();
                var newPhones = phones;
                var startItems = $(root).find('#phoneList li').length;
                if (e){
                    var element = e.target;
                    if ($(element).attr('id') == 'filterSort'){
                        newPhones = doSorting(newPhones);

                    } else if ($(element).attr('id') == 'brand'){
                        if ($(element).val() != '0'){
                            var brandModels = models[$(element).val()];
                            $(root).find('#model').html('<option value="0">' + opts.lang.Select_model + '</option>');
                            $(root).find('#model').attr('disabled', false);
                            for(var i=0;i<brandModels.length;i++){
                                $(root).find('#model').append('<option value="' + brandModels[i].Id + '">' + brandModels[i].model + '</option>');
                            }
                        } else {
                            $(root).find('#model').html('<option value="0">' + opts.lang.Select_model + '</option>');
                        }
                    } else if ($(element).attr('id') == 'tariff'){
                        var tariff_id = $(element).val();
                        if (tariff_id){
                            var tariffs = [getTariffById(tariff_id)];
			} else {
			  tariffs = [false];
			}
                        if (!tariffs[0]){
			  tariffs = [];
                            for(i=0;i<tariffGroups.length;i++){
                                if (tariffGroups[i].tariffs.length){
                                    for(j=0;j<tariffGroups[i].tariffs.length;j++){
                                        tariffs.push(tariffGroups[i].tariffs[j]);
                                    }
                                }
                            }
			}
                        var minMax = getMaxMinTariffs(tariffs);
			//var slValues = priceSlider.slider("values");
                        //if (minMax[0] != 0 && minMax[1] != 0){
                            setSliderLimits(minMax[0], minMax[1]);
			    priceSlider.slider("values", 0, minMax[0]);
			    priceSlider.slider("values", 1, minMax[1]);
                            setPriceHandles();
			//}
			
                        
                    } 
                }
                var numPhones = newPhones.length
                if ($('#brand').val()){
                    newPhones = filterByBrand($('#brand').val(), newPhones);
                    dump("brand filtered, from " + numPhones + " to " + newPhones.length + " phones");
                    numPhones = newPhones.length
                }
                if ($('#model').val() && !$('#model').attr('disabled')){
                    newPhones = filterByModel($('#model').val(), newPhones);
                    dump("model filtered, from " + numPhones + " to " + newPhones.length + " phones");
                    numPhones = newPhones.length
                }
                
                if ($('#tariff').val() && !$('#tariff').attr('disabled')){
                    newPhones = filterByTariff($('#tariff').val(), newPhones);
                    dump("tariff filtered, from " + numPhones + " to " + newPhones.length + " phones");
                    numPhones = newPhones.length
                }

                newPhones = applyCustomFilters(newPhones);
                dump("custom filters applied, from " + numPhones + " to " + newPhones.length + " phones");
                numPhones = newPhones.length

                var min = priceSlider.slider("values")[0];
                var max = priceSlider.slider("values")[1];
                newPhones = filterByPriceRange(min, max, newPhones);
                dump("price range filtered, from " + numPhones + " to " + newPhones.length + " phones");
                numPhones = newPhones.length
                
                var endItems = newPhones.length;
                if (endItems){
                    doFiltering(newPhones);
                } else {
                    $('#phoneList li').fadeOut(400, function(){
                        $('#phoneList').html('');
                    });
                    var response = '{"code":null,"message":null,"user_message":["' + opts.lang.No_phones_matching_criteria + '"],"data":{},"type":"error"}'
                    $.fn.ajaxResponse(response);
                }
                dump('phones before: ' + startItems + ', after: ' + endItems);
                dump('time: ' + parseFloat(new Date().getTime() - start) + 'ms');
                dump('<hr />');
            }

            function populateTariffSelect(tariffGroups){
                var html = '<option value="0">' + opts.lang.Select_tariff + '</option>';
                for(var i=0;i<tariffGroups.length;i++){
                    if (tariffGroups[i].tariffs.length){
                        html += '<optgroup label="' + getObjectLangValue(tariffGroups[i], 'name') + '">';
                        for(var j=0;j<tariffGroups[i].tariffs.length;j++){
                            html += '<option value="' + tariffGroups[i].tariffs[j].Id + '">' + getObjectLangValue(tariffGroups[i].tariffs[j], 'name') + '</option>';
                        }
                        html += '</optgroup>';
                    }
                }
                $('#tariff').html(html);
            }
            function getObjectLangValue(object, property_name){
                var value = object[property_name];
                if (versionId == 2){
                    if (object[property_name + '_en']){
                        return object[property_name + '_en'];
                    }
                }
                return value;
            }
            function filterByPriceRange(min, max, filterPhones){
                if (!filterPhones){
                    filterPhones = phones;
                }
                var newPhones = [];
                var phoneShouldGo;
                for(i=0;i<filterPhones.length;i++){
                    phoneShouldGo = false;
                    for(j=0;j<filterPhones[i].tariffGroups.length;j++){
                        for(k=0;k<filterPhones[i].tariffGroups[j].tariffs.length;k++){
                            var price = Number(filterPhones[i].tariffGroups[j].tariffs[k].tariff_value.activation_fee);
                            if (filterPhones[i].tariffGroups[j].tariffs[k].Id == $('#tariff').val() || $('#tariff').val() == 0){
                                if (price >= min && price <= max){
                                    phoneShouldGo = true;
                                }
                            }
                        }
                    }
                    if (phoneShouldGo){
                        newPhones.push(filterPhones[i]);
                    }
                }
                return newPhones;
            }
            function filterByBrand(brand_id, filterPhones){
                if (!filterPhones){
                    filterPhones = phones;
                }
                if (!brand_id || brand_id == "0"){
                    return filterPhones;
                }
                var newPhones = [];
                for(var i=0;i<filterPhones.length;i++){
                    if (filterPhones[i].brand_id == brand_id){
                        newPhones.push(filterPhones[i]);
                    }
                }
                return newPhones;
            }
            function filterByModel(model_id, filterPhones){
                if (!filterPhones){
                    filterPhones = phones;
                }
                if (!model_id || model_id == "0"){
                    return filterPhones;
                }
                var newPhones = [];
                for(var i=0;i<filterPhones.length;i++){
                    if (filterPhones[i].Id == model_id){
                        newPhones.push(filterPhones[i]);
                    }
                }
                return newPhones;
            }
            function filterByTariff(tariff_id, filterPhones){
                if (!filterPhones){
                    filterPhones = phones;
                }
                if (!tariff_id || tariff_id == "0"){
                    return filterPhones;
                }
                var newPhones = [];
                for(var i=0;i<filterPhones.length;i++){
                    for(var j=0;j<filterPhones[i].tariffGroups.length;j++){
                        for(var k=0;k<filterPhones[i].tariffGroups[j].tariffs.length;k++){
                            if (filterPhones[i].tariffGroups[j].tariffs[k].Id == tariff_id){
                                newPhones.push(filterPhones[i]);
                            }
                        }
                    }
                }
                return newPhones;
            }

            function applyCustomFilters(currentPhones){
                var newPhones = currentPhones;
                var value
                var property_id;
                $('.criteria_checkbox:checked').each(function(i, element){
                    property_id = $(element).attr('id').replace(/criteria_/, '');
                    value = 1;
                    newPhones = customFilter(property_id, value, newPhones);
                });
                return newPhones
            }

            function customFilter(property_id, value, currentPhones){
                var newPhones = [];
                dump('filtering property id: ' + property_id + ', on ' + currentPhones.length + ' phones');

                for(var i=0;i<currentPhones.length;i++){
                    for(var j=0;j<currentPhones[i].propertyGroups.length;j++){
                        if (currentPhones[i].propertyGroups[j].properties){
                            for(var k=0;k<currentPhones[i].propertyGroups[j].properties.length;k++){
                                if (currentPhones[i].propertyGroups[j].properties[k].Id == property_id && currentPhones[i].propertyGroups[j].properties[k].property_value.property_value){
                                    newPhones.push(currentPhones[i]);
                                }
                            }
                        }
                    }
                }
                dump('filtered , returning ' + newPhones.length + ' phones');
                return newPhones
            }

            function doFiltering(newPhones){
                $('#tempPhoneUl').remove();
                $('#lists').append('<ul id="tempPhoneUl" class="phoneList" style="display: none"></ul>');
                populateList(newPhones, $('#tempPhoneUl'), function(){
                    try {
                        if ($('#tempPhoneUl li').length){
                            $('#phoneList').quicksand($('#tempPhoneUl li'), {}, function(){
				  
                                });
                        } else {
                            $('#phoneList li').fadeOut(400, function(){
                                $('#phoneList').html('');
                            });
                        }
                    }
                    catch (e){
                        dump(e.message);
                    }
                });
            }









            function getBrandById(id){
                for(var i=0;i<brands.length;i++){
                    if (brands[i].Id == id){
                        return brands[i];
                    }
                }
                return false;
            }

            function getTariffById(id){
                for(var i=0;i<tariffGroups.length;i++){
                    for(j=0;j<tariffGroups[i].tariffs.length;j++){
                        if (tariffGroups[i].tariffs[j].Id == id){
                            return tariffGroups[i].tariffs[j];
                        }
                    }
                }
                return false;
            }
            function getPropertyById(id){
                for(var i=0;i<propertyGroups.length;i++){
                    for(var j=0;j<propertyGroups[i].properties.length;j++){
                        if (propertyGroups[i].properties[j].Id == id){
                            return propertyGroups[i].properties[j];
                        }
                    }
                }
                return false;
            }



            function initEvents(){
                $(root).find('#toggleAdvanced').click(function(e){
                    e.preventDefault();
                    $(root).find('.advancedSearch').toggle();
                });
                $('.filterSelect').change(filter);
                $('#filterSort').change(filter);
                $('.criteria_checkbox').change(filter);
                if (options.urlBrand){
                    $('#brand').triggerHandler("change");
                }

            }



            function dump(msg){
                $('#debug a').before('<div>' + msg + '</div>');
            }


            function getPhoneHref(phone){
                var key;
                if (versionId == 1){
                    return phone.page_href_sr;
                } else {
                    return phone.page_href_en;
                }
            }
            function getUrlTitle(title){
                var patterns = [/&[.]{2,5};/, /č/, /Č/, /ć/, /Ć/, /č/, /š/, /Š/, /ž/, /Ž/, /Đ/, /đ/, /\s/, /[^\w\-]+/];
                var replacements = ["-", "c", "C", "c", "C", "c", "s", "S", "z", "Z", "Dj", "dj", "-", ""];
                for(i=0;i<patterns.length;i++){
                    while(title.match(patterns[i])){
                        title = title.replace(patterns[i], replacements[i]);
                    }
                }
                return title;
            }

            initialize();
        });
    };
    $.fn.vipPhoneList.defaults = {
        lang : {
            Select_one: 'Select_one'
        }
    };
})(jQuery);
