zookastos
zookastos

Reputation: 935

JQuery binding gone wrong in loop

I have this JQuery code that tries to create JQuery sliders in for loop -

function initSliderUI(){
    $('.opt-range-slider').each(function(){
        $this = $(this);
        elementId = $this.attr('id');
        filterUIObj = getFilterUIObjFromOptionId(elementId);
        filterName = filterUIObj.getAttribute('data-filter-name');
        addSliderUI(filterName, elementId, getSliderFilterRangeArray(filterName));
    });
}
//this is not working due to binding problems
function addSliderUI(type, elementId, dataArray){
    filterUIObj = getFilterUIObjFromOptionId(elementId);
    filterUIObj.data[1].data[0].data[0].data[0].setData(dataArray[0] + ' - ' + dataArray[dataArray.length-1]);
    $('#'+elementId).slider({
        range: true,
        min: 1,
        max: dataArray.length,
        step: 0.001,
        values: [1, dataArray.length],
        change: function (event, ui) {
            if(dataArray.length > 1){
                $filteredRows = applyRangeFilter(type, dataArray[Math.round(ui.values[0])-1], dataArray[Math.round(ui.values[1])-1]);
                toggleApplicantFilteredRows($filteredRows);
                //problem is in this line below (filterUIObj)
                filterUIObj.data[1].data[0].data[0].data[0].setData(getSliderFilterRangeText(type, dataArray[Math.round(ui.values[0])-1], dataArray[Math.round(ui.values[1])-1]));
            }
        },
        slide: function (event, ui) {
            //problem is in this line below (filterUIObj)
            filterUIObj.data[1].data[0].data[0].data[0].setData(getSliderFilterRangeText(type, dataArray[Math.round(ui.values[0])-1], dataArray[Math.round(ui.values[1])-1]));
        },
        start: function (event, ui) {},
        stop: function (event, ui) {}
    });
}

In my loop I am taking some elements with class 'opt-range-slider' and binding them to Slider (..) widget of jquery. While doing so, I am passing some of my custom class object "filterUIObj". This object is being passed correctly in initSliderUI(...). But when I am sliding my slider, whatever is supposed to happen in "slide: function (event, ui) {...}" is happening to the last "filterUIObj" object in the loop.

So, assume I have just 2 sliders. When I am sliding my first slider, data is being updated in the second slider text.

Where am I going wrong? Is there a work around? I cannot bind them separately because the number of objects having slider is decided on runtime, so it has to be for each loop.

EDIT - added some helper functions

function getFilterUIObjFromOptionId(optId){
    return generatedIds[$('#'+optId).closest('.filter').attr('id')];
}

Upvotes: 0

Views: 49

Answers (1)

Tomalak
Tomalak

Reputation: 338208

In Javascript, all variables that are not declared with var become top-level globals. When declared with var they become function-scoped.

There is no useful situation where you would ever want to declare global variables within a function body, so leaving out var is pretty much always a mistake. It leads to different functions all writing to the same variable and usually does not end well.

A static analyzer like jshint (also available as an online tool) would have pointed out the error. You should make a habit of using such a tool to check your code for avoidable mistakes.

Upvotes: 1

Related Questions