Quand dois-je utiliser _.bindAll () dans Backbone.js?

J'apprends backbone.js, et je me sens confus à ce sujet: je suis en train de suivre le didacticiel: http://arturadib.com/hello-backbonejs/

Comme vous pouvez le voir dans le premier exemple (1.js):

(function($){ var ListView = Backbone.View.extend({ el: $('body'), // attaches `this.el` to an existing element. initialize: function(){ _.bindAll(this, 'render'); // fixes loss of context for 'this' within methods this.render(); // not all views are self-rendering. This one is. }, render: function(){ $(this.el).append("<ul> <li>hello world</li> </ul>"); } }); var listView = new ListView(); })(jQuery); 

Mais si je commente la phrase: _.bindAll(this, 'render'); , Cela va toujours fonctionner. J'ai cherché dans google et quelqu'un a dit que la méthode bindAll() est nécessaire puisque si j'ai changé mon contexte, l'appel de this.render peut ne pas être disponible. Je me sens confus sur le «contexte». Et peut-on aussi m'expliquer quand l'appel ( this.render ) ne sera pas disponible?

Pour l'exemple que vous avez donné _.bindAll(this, 'render'); _bindAll() pas nécessaire, mais si vous avez des fonctions de rappel où this peut être changé en contexte d'autre chose, alors _bindAll() peut être pratique.

Par exemple:

 initialize: function(){ _.bindAll(this, 'render', 'clickFunc'); }, events: { 'click .someElement': 'clickFunc' }, clickFunc: function(e) { /** If you remove the clickFunc from the list of events in bindAll, 'this' will refer to the element that invoked the event. Adding the clickFunc event in the _.bindAll, ensures that 'this' stays as the view. */ this /** <-- our focal point */ } 
  • Toutes les méthodes listées comme valeurs de propriété dans les événements hash de votre vue sont automatiquement liées par votre backbone
  • Toute méthode que vous utilisez manuellement comme gestionnaire d'événements à partir de modèles ou de collections devrait être liée manuellement via bindAll
    • OU vous pouvez fournir un contexte lorsque vous enregistrez la liaison
    • OU vous pouvez utiliser la fonction EMCA 5.bind pour obtenir le même résultat

fragment:

 events: { 'click .win': 'win', 'click .lose': 'lose' }, initialize: function () { //win and lose are automatically bound for you //because they are in the events property //refresh must be manually bound this.model.on('change', this.refresh); //which you can do ECMA5 style if you like this.model.on('change', this.refresh.bind(this)); //OR you can provide a context backbone style this.model.on('change:foo', this.fooChange, this); //However, since you pretty much never want an unbound function //in a view, you can just stick this in all your initialize methods //and call it done //Note this will bind all functions in your view class if you don't //pass specific method names. I recommend this form. _.bindAll(this); }, win: function () {...}, lose: function () {...}, refresh: function () {...}, fooChange: function() {...} 

OOOOORRRR utilise simplement des flèches CoffeeScript et graisse et résolvez-le proprement au niveau de la langue.

Dans ce cas, vous n'avez pas besoin de _.bindAll , mais disons que votre vue comporte une méthode qui provoque un redistributeur et que vous faites quelque chose comme ceci:

 .., myMethod: function() { this.$('.someselector').change(this.render); }, 

Si vous n'avez pas _.bindAll pour render , votre contexte serait désactivé.

Regardons _.bindAll ce que _.bindAll fait de underscore.js documents officiels .

  _.bindAll = function(obj) { var i, length = arguments.length, key; if (length <= 1) throw new Error('bindAll must be passed function names'); for (i = 1; i < length; i++) { key = arguments[i]; obj[key] = _.bind(obj[key], obj); } return obj; }; 

Ce qu'il fait, c'est de lier automatiquement toutes ses fonctions à son contexte correct. (Où sa fonction est déclarée plutôt que invoquée.

Personnellement, je pense que c'était une convention pour l'ancienne version de Backbone.js pour lier ses events , ou les auditeurs d'action DOM. Étant donné que les nouvelles versions de Backbone View lient automatiquement et délient les auditeurs dans les events . Trouvez plus par recherche Binding "this" ici

J'espère que cela vous aidera.