How to stay in the this context during an ajax call (jquery + coffescript)

大憨熊 提交于 2020-01-04 03:24:13

问题


I made a class :

class @GameMap
    options : {
        'width' : 100,
        'height' : 100,
        'tileWidth' : 45,
        'tileHeight' : 20,
        'scale' : 5,
        'moveDistance' : 100, #Distance to move with the map controlers
        'showErrorMessages' : true,
        'zindexDecorElementBase' : 99999,
        'zindexGroudElementBase' : 88888
    }

    lang : {
        'errContainerMissing' : "L'élement pour créer la carte n'existe pas"
    }

    constructor: (@element) ->
      this.run()

    run: ->
      this.loadDatas()

    loadDatas: (top,left) ->
      $.ajax(
          url: "/map/getnewcoord",
          data: {
             map_width : this.options.width,
             map_height : this.options.height,
             tile_height : this.options.tileHeight,
             tile_width : this.options.tileWidth,
             window_large : $('.map-windows').width(),
             window_height:  $('.map-windows').height(),
             top : top ,
             left : left
          },
          success: (data) ->
            $.each(data,(index,item) ->
              this.createTile(item.posX,item.posY);
            )
      )

    createTile: (m,n) ->
       #We are in the tile reference
       yDelta = Math.round((options.width ) * options.tileHeight );
       console.log('pass')

  $ ->
    gamemap = new GameMap("#map .block-map")

But i got the error

this.createTile is not a function

It's because the "this" is not the "this" of my class but one of item return by my json call.

How can i do to keep the "this" of my class in the ajax success callback function?


回答1:


Here's the CoffeeScript way to do it:

      success: (data) =>
        $.each(data,(index,item) =>
          this.createTile(item.posX,item.posY);
        )

This compiles to something very similar to alex's answer, but is, I think, much more readable. The => operator defines a function while using the this that was present when it was defined, rather than when it was called.

While we're at it, you may find it more readable to use @ instead of this:

          @createTile(item.posX,item.posY);



回答2:


Keep a reference to this.

A lot of people use a pattern such as var that = this (or self if it reads better for you).

Then, in your inner function, replace references to this with that, which will be the parent function's this.

Alternatively, you can wrap the anonymous function definitions with $.proxy()...

fn = $.proxy(fn, this);

...which will ensure the this inside is always the parent's this. $.proxy() is a cross browser way of achieving bind() (which isn't implemented in the older IEs or Safari).




回答3:


You can pass the context as param to the ajax() method:

$.ajax({ /*...,*/ context: this/*, ...*/ });

http://api.jquery.com/jQuery.ajax/



来源:https://stackoverflow.com/questions/8552270/how-to-stay-in-the-this-context-during-an-ajax-call-jquery-coffescript

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!