Environment Generator Environment Generator -4 years ago 119
Javascript Question

Using this in method with jQuery

I have a problem catching my object data in jQuery methods:

this.start = function() {
var prepend = '<img id = "' + this.imageList[0].name + '" class = "desktop_image_slider_prepended_image" src = "res/img/' + this.imageList[0].name + '.png"></img>';
$("#desktop_image_slider").prepend(prepend);
this.boxList.shift(this.imageList[0]);
$("#" + this.boxList[this.boxList.length-1].name).animate({"width":"0%"}, 500);
$("#" + this.imageList[0].name).animate({"width":"11.1111111111%"}, 500, function() {
$("#" + this.boxList[this.boxList.length-1].name).remove();
this.imageList.push(this.boxList[this.boxList.length-1]);
this.boxList.splice(this.boxList.length-1, 1);
$timeout(function() {
this.start();
}, 1000);
});
}


It throws undefined. It is obviously taking something from jQuery not from my method. Is there a way to access my method?

Thanks!

Answer Source

The this referenced in your animate function event handler is referencing the calling event function. Not your global this. You can either use .bind(this) or use const _self = this; and then reference _self.imageList

This example uses const _self = this.

start = function() {
    var prepend = '<img id = "' + this.imageList[0].name + '" class = "desktop_image_slider_prepended_image" src = "res/img/' + this.imageList[0].name + '.png"></img>';
    $("#desktop_image_slider").prepend(prepend);
    this.boxList.shift(this.imageList[0]);
    $("#" + this.boxList[this.boxList.length-1].name).animate({"width":"0%"}, 500);
    var _self = this;
    $("#" + this.imageList[0].name).animate({"width":"11.1111111111%"}, 500, function() {
        $("#" + _self[_self.boxList.length-1].name).remove(); // _self is used instead of this
        _self.imageList.push(_self.boxList[_self.boxList.length-1]); // _self is used instead of this
        _self.boxList.splice(_self.boxList.length-1, 1); // _self is used instead of this
        $timeout(function() {
            _self.start(); // _self is used instead of this
        }, 1000);
    });
}

This example uses bind

this.start = function() {
    var prepend = '<img id = "' + this.imageList[0].name + '" class = "desktop_image_slider_prepended_image" src = "res/img/' + this.imageList[0].name + '.png"></img>';
    $("#desktop_image_slider").prepend(prepend);
    this.boxList.shift(this.imageList[0]);
    $("#" + this.boxList[this.boxList.length-1].name).animate({"width":"0%"}, 500);
    $("#" + this.imageList[0].name).animate({"width":"11.1111111111%"}, 500, function() {
        $("#" + this.boxList[this.boxList.length-1].name).remove();
        this.imageList.push(this.boxList[this.boxList.length-1]);
        this.boxList.splice(this.boxList.length-1, 1);
        $timeout(function() {
            this.start();
        }.bind(this), 1000); // set function's scope to `this`
    }.bind(this)); // set function's scope to `this`
Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download