Quand utiliserais-je JQuery.Callbacks?

Je regardais à travers de nouvelles choses ajoutées à jQuery 1.7 et j’ai vu qu’ils ont maintenant jQuery.Callbacks () http://api.jquery.com/jQuery.Callbacks/ .

La documentation vous montre comment utiliser jQuery.callbacks () mais pas les exemples applicables lorsque je souhaiterais les utiliser.

Il semble que vous puissiez append / supprimer des rappels dans une liste de rappels et que vous puissiez faire jQuery.callbacks (). Fire (args), mais cela déclenche simplement TOUS les rappels de cette liste. Peut-être que je manque quelque chose mais cela ne semble pas très utile.

Dans ma tête, lorsque j’ai vu cette nouvelle fonctionnalité pour la première fois, je pensais que vous pouviez l’utiliser avec des paires clé / valeur. Ce qui fournirait alors un moyen simple de gérer les fonctions de rappel en un seul endroit de votre application. Quelque chose comme

$.callbacks.add("foo", myFunction); 

et puis par exemple si je voulais appeler ce rappel à la fin de ma fonction, je pourrais faire quelque chose comme

 $.callbacks().fire("foo", args); 

Cependant, il ne semble pas que vous puissiez déclencher des rappels spécifiques, vous ne pouvez les déclencher qu’avec les arguments donnés ou aucun d’entre eux.

La chose la plus proche que j’ai vue était la possibilité de donner à la fonction .fire () un contexte pour définir la propriété “this”

 .fireWith(context, args) 

mais cela n’aide pas beaucoup non plus.

  1. Est-ce que je comprends mal la documentation?

  2. S’il s’agit de la fonctionnalité souhaitée, quels sont les exemples applicables où cela est utile?

Pour développer @Rockets, répondez un peu et éliminez une certaine confusion:

La raison pour laquelle il pourrait être nécessaire d’utiliser les $.Callbacks est multiple:

  1. L’utilisateur a beaucoup de code dans une fonction et veut le diviser
  2. Ils prennent ces informations et les envoient via la fonction de rappel jQuery qui leur permet ensuite de diviser leur code en éléments plus faciles à gérer.
    Donc (par exemple) si vous regardez le code de @ Rocket :

     var clickCallbacks = $.Callbacks(); clickCallbacks.add(function() { //one one function piece //parse and do something on the scope of `this` var c = parseInt(this.text(), 10); this.text(c + 1); }); clickCallbacks.add(function(id) { //add a second non-related function piece //do something with the arguments that were passed $('span', '#last').text(id); }); $('.click').click(function() { var $ele = $(this).next('div').find('[id^="clickCount"]'); clickCallbacks.fireWith($ele, [this.id]); //do two separate but related things. }); 
  3. Ce que vous pouvez maintenant faire, ce sont de multiples lots de fonctions de rappel que vous pouvez maintenant appeler chaque fois que vous estimez que cela est nécessaire sans avoir à apporter autant de modifications à votre code.

Je peux voir que les rappels sont utiles lorsque vous mettez à jour différents éléments DOM en utilisant la même méthode.

Voici un exemple ringard: http://jsfiddle.net/UX5Ln/

 var clickCallbacks = $.Callbacks(); clickCallbacks.add(function() { var c = parseInt(this.text(), 10); this.text(c + 1); }); clickCallbacks.add(function(id) { $('span', '#last').text(id); }); $('.click').click(function() { var $ele = $(this).next('div').find('[id^="clickCount"]'); clickCallbacks.fireWith($ele, [this.id]); }); 

Il met à jour le compteur de clics et le dernier clic lorsque vous cliquez sur quelque chose.

Un système de pub / sous-système jQuery (presque) prêt à l’emploi

C’est à mon humble avis l’application la plus intéressante, et comme il n’était pas clairement indiqué dans les réponses (bien que certaines fassent allusion à l’utilisation), je l’ajoute à ce message relativement ancien.

NB: L’utilisation est clairement indiquée, avec un exemple, dans les documents jQuery , mais je suppose qu’elle a été ajoutée après la publication de la question.

Pub / Sub , alias le motif de l’observateur , est un motif qui favorise un couplage lâche et une responsabilité unique dans une application. Plutôt que d’avoir des objects appelant directement les méthodes d’autres objects, les objects s’abonnent à la place à une tâche ou à une activité spécifique et sont avertis lorsque cela se produit. Pour une explication plus détaillée des avantages de l’utilisation du modèle Pub / Sub, vous pouvez vérifier Pourquoi utiliser le modèle Publish / Subscribe (dans JS / jQuery)? .

Bien sûr, cela était possible avec des événements personnalisés utilisant sortinggger , .on() et .off() , mais je trouve jQuery.Callbacks beaucoup plus adapté à la tâche, produisant un code plus propre.

Voici l’extrait de code de la documentation jQuery :

 var topics = {}; jQuery.Topic = function( id ) { var callbacks, method, topic = id && topics[ id ]; if ( !topic ) { callbacks = jQuery.Callbacks(); topic = { publish: callbacks.fire, subscribe: callbacks.add, unsubscribe: callbacks.remove }; if ( id ) { topics[ id ] = topic; } } return topic; }; 

Et un exemple d’utilisation:

 // Subscribers $.Topic( "mailArrived" ).subscribe( fn1 ); $.Topic( "mailArrived" ).subscribe( fn2 ); $.Topic( "mailSent" ).subscribe( fn1 ); // Publisher $.Topic( "mailArrived" ).publish( "hello world!" ); $.Topic( "mailSent" ).publish( "woo! mail!" ); // Here, "hello world!" gets pushed to fn1 and fn2 // when the "mailArrived" notification is published // with "woo! mail!" also being pushed to fn1 when // the "mailSent" notification is published. /* output: hello world! fn2 says: hello world! woo! mail! */ 

Il semble que $.Callbacks commencé comme un détail d’implémentation: un moyen de gérer des listes de fonctions et d’appeler toutes les fonctions d’une liste donnée avec les mêmes arguments. Un peu comme les delegates de multidiffusion de C #, avec des fonctionnalités supplémentaires, telles que les indicateurs que vous pouvez transmettre pour personnaliser le comportement de la liste.

Un bon exemple pourrait être que jQuery utilise $.Callbacks interne pour implémenter son événement ready . bindReady() initialise une liste de rappel:

 readyList = jQuery.Callbacks( "once memory" ); 

Notez les indicateurs memory et memory , qui garantissent que la liste de rappel ne sera appelée qu’une seule fois, et que les fonctions ajoutées après l’appel de la liste seront appelées immédiatement.

Ensuite, ready() ajoute le gestionnaire spécifié à cette liste:

 ready: function( fn ) { // Attach the listeners jQuery.bindReady(); // Add the callback readyList.add( fn ); return this; } 

Enfin, la liste de rappel est déclenchée lorsque le DOM est prêt:

 readyList.fireWith( document, [ jQuery ] ); 

Tous les gestionnaires ready sont appelés dans le contexte du même document avec la même référence à l’object jQuery global. Ils ne peuvent être appelés qu’une seule fois, et les gestionnaires supplémentaires passés à ready() seront appelés immédiatement à partir de ce moment-là, grâce à $.Callbacks .

Je ne vois aucune mention spécifique de la mise en contexte, mais comme vous pouvez passer un nombre arbitraire d’arguments, cela pourrait être utile. Vous pouvez également créer votre propre convention pour passer un indicateur en tant que premier argument et faire en sorte que les écouteurs renvoient false immédiatement s’ils ne sont pas destinés à gérer la liste d’arguments restante.

J’ai rencontré des cas où quelque chose comme cela pouvait être utile, mais j’ai plutôt utilisé bind () et sortinggger () avec des événements personnalisés. Imaginez un système de messagerie (un chat ou un client de messagerie Web) sur lequel vous interrogez un service pour obtenir de nouveaux messages. Une fonction peut consister à définir un nombre dans une plage ou à afficher un grognement en cas de problème. Un autre pourrait mettre à jour une grid. Avec les déclencheurs, vous devez déclencher l’événement pour chaque écouteur et “dérouler” les arguments passés de eventData, avec des rappels, il ne s’agit que d’un seul feu et vos écouteurs sont des fonctions javascript simples avec une liste d’arguments simple.

Les rappels ne sont pas exactement révolutionnaires, mais ils réduiront le code et le rendront plus propre.

Je travaille sur une application avec beaucoup de logique métier et au moins 11 services externes. Cela aide vraiment à garder les choses claires si vous pouvez écrire vos propres classes et comportements de contrôle de stream en utilisant quelque chose comme Callbacks au lieu d’essayer de forcer votre volonté sur l’implémentation différée.