Установка области действия анонимной функции this в методах jQuery / ajax - PullRequest
2 голосов
/ 24 января 2010

Как отмечается в этом сообщении в блоге , вы можете установить область действия this в анонимной функции в Javascript.

Есть ли более элегантный способ определения области this в анонимном вызове функции на success запроса AJAX (т. Е. Без использования that)?

Например:

var Foo = {

  bar: function(id) {

    var that = this;

    $.ajax({
      url: "www.somedomain.com/ajax_handler",
      success: function(data) {
        that._updateDiv(id, data);
      }
    });

  },

  _updateDiv: function(id, data) {

    $(id).innerHTML = data;

  }

};

var foo = new Foo;
foo.bar('mydiv');

Использование вызова, но все еще необходимо назвать область действия родительского объекта that.

success: function(data) {
    (function() {
      this._updateDiv(id, data);
    }).call(that);
}

Ответы [ 2 ]

6 голосов
/ 24 января 2010

Функция $.ajax() предоставляет краткое средство сделать это уже в виде параметра context :

$.ajax({
  url: "www.somedomain.com/ajax_handler",
  context: this,
  success: function(data) {
    this._updateDiv(id, data);
  }
});

Хотя методы Контуры CMS больше подходят для общего использования.

6 голосов
/ 24 января 2010

В jQuery 1.4 у вас есть метод $.proxy, вы можете просто написать:

 //...
 bar: function(id) {
    $.ajax({
      url: "someurl",
      success: $.proxy(this, '_updateDiv')
    });
  },
  //...

$.proxy принимает объект, который будет использоваться в качестве значения this, и может принимать либо строку (член этого объекта), либо функцию, и он будет возвращать новую функцию, которая всегда будет иметь конкретный объем.

Другой альтернативой является функция bind, теперь часть стандарта ECMAScript Fifth Edition является лучшей:

//...
  bar: function(id) {
    $.ajax({
      url: "someurl",
      success: function(data) {
        this._updateDiv(id, data);
      }.bind(this)
    });
  },
//...

Эта функция будет доступна изначально в ближайшее время, когда механизмы JavaScript полностью реализуют стандарт ES5, а пока вы можете использовать следующую 8-строчную реализацию:

// The .bind method from Prototype.js 
if (!Function.prototype.bind) { // check if native implementation available
  Function.prototype.bind = function(){ 
    var fn = this, args = Array.prototype.slice.call(arguments),
        object = args.shift(); 
    return function(){ 
      return fn.apply(object, 
        args.concat(Array.prototype.slice.call(arguments))); 
    }; 
  };
}
...