2

I'm having some trouble with scoping in javascript. I'm using a jquery plugin to write a class that is a wrapper for our dropdown controls.

the problem is in the loadJsonList function, the call to this.addOption(s.itemValue, s.itemText); does not work as the method doesn't exist. I know JS has odd scoping but I've no idea how i can run that function in that scope??

jQuery.Class.extend("DDL",
{
    id: '',
    isTelerik: false
},
{
    init: function (newid) {
        this.Class.id = newid;

    },
    getValue: function () {
        return $('#' + this.Class.id).val();
    },
    getText: function () {
        return $('#' + this.Class.id + ' :selected').text();
    },
    setValue: function (newValue) {
        try {
            $('#' + this.Class.id).val(newValue);
        } catch (err) {
            alert(err);
        }
    },
    setText: function (newText) {
        try {
            $('#' + this.Class.id + ' :selected').text(newText);
        } catch (err) {
            alert(err);
        }
    },
    loadJsonList: function (list, param1, param2, param3) {
        this.clearItems();

        //init the service
        var j = new JsonRPC();

        // get the cut down data table
        var dt = j.getDropDownData(list, param1, param2, param3);

        // parse the datatable and load it into the telerik combo box
        jQuery.each(dt, function (i, s) {
            this.addOption(s.itemValue, s.itemText);
        });
    },
    addOption: function (value, text) {
        $('#' + this.Class.id).append('<option value="' + value + '">' + text + '</option>');
    },
    removeOption: function (value) {
        $('#' + this.Class.id + ' option[value="' + value + '"]').remove();
    },
    clearItems: function () {
        $('#' + this.Class.id + ' option').remove();
    }
});
1
  • 1
    To be slightly pedantic, when talking about this you're not talking about scoping but binding. Commented Nov 18, 2010 at 3:03

3 Answers 3

3

Simple one. JavaScript uses function level scoping, so you save a reference to the this variable under some other name:

loadJsonList: function (list, param1, param2, param3) {
        // save a reference for use in the each function later
        var self = this; 
        this.clearItems();

        //init the service
        var j = new JsonRPC();

        // get the cut down data table
        var dt = j.getDropDownData(list, param1, param2, param3);

        // parse the datatable and load it into the telerik combo box
        jQuery.each(dt, function (i, s) {
            // use self instead of this!
            self.addOption(s.itemValue, s.itemText);
        });
    },
Sign up to request clarification or add additional context in comments.

Comments

2

this in that function's scope is not equal to the same this of your object, you need to assign an alias variable to it in the surrounding scope in order to access it inside the inner function:

var self = this;     
jQuery.each(dt, function (i, s) {
     self.addOption(s.itemValue, s.itemText);
});

Comments

0

What you are looking for is jQuery's proxy method (http://api.jquery.com/jQuery.proxy):

// Description: Takes a function and returns a new one that will always have a particular context.
jQuery.proxy( function, context )

So in your above example you'd use it as follows:

loadJsonList: function (list, param1, param2, param3) {

   // ...

   jQuery.each(dt, jQuery.proxy(function (i, s) {
       this.addOption(s.itemValue, s.itemText);
   }, this));
},

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.