2010-09-29 13 views
1

Je suis nouveau sur javascript et je suis à la recherche de code de démo de Raphaël. Je suis confus par la façon dont cela fonctionne ...Comment/quand cette fonction anonyme est invoquée?

if (R) { 
    (function (dx, dy, R, value) { 
     var color = "hsb(" + [(1 - R/max) * .5, 1, .75] + ")"; 
... 

D'après ce que je peux voir c'est une fonction anonyme déclarant qui prend 4 arguments. Comment cette fonction est invoquée quand cette fonction n'a pas de nom ??

page de démonstration .. http://raphaeljs.com/github/dots.html

fichier JS .. http://raphaeljs.com/github/dots.js

+0

le fichier js est un peu long, et je ne pouvais pas trouver 'if (R) {' dedans. pouvez-vous poster plus de code ici? – jrharshath

+0

Désolé, je pensais que je n'aurais pas inclus assez de code pour comprendre ce qui se passait, c'est pourquoi je me suis connecté à la source. Il a été répondu quand même maintenant, merci! Le fichier JS n'est pas * long * - seulement quelques écrans pleins - la partie citée est juste à mi-chemin. –

Répondre

2

Pour répondre brièvement à votre question, il est invoqué immédiatement après la déchiffrement.

Tu as oublié une partie importante, la fin de la définition de la fonction:

})(leftgutter + X * (j + .5) - 60 - R, Y * (i + .5) - 10, R, data[o]); 

Ce que cela dit est }, qui met fin à la fonction, ), qui met fin à la parenthèse qui a ouvert avec (function. Si ce qui reste ressemble à une liste d'arguments, c'est parce que c'est le cas.

Un exemple illustratif:

(function(arg){ alert(arg); })("Hi!"); 
1

vous ne contient pas assez de code pour le dire. en regardant la source, cette méthode est exécutée immédiatement. en ignorant le contenu de la fonction, il ressemble à ce

(function (dx, dy, R, value) { 

// ... stuff 

dot[0].onmouseover = function() { 
    if (bg) { 
     bg.show(); 
    } else { 
     var clr = Raphael.rgb2hsb(color); 
     clr.b = .5; 
     dt.attr("fill", Raphael.hsb2rgb(clr).hex); 
    } 
    lbl.show(); 
}; 

// more stuff 

})(leftgutter + X * (j + .5) - 60 - R, Y * (i + .5) - 10, R, data[o]); 

Tout cela se passe dans une boucle, et les variables sont référencées dans une méthode de gestionnaire d'événements. la méthode anonyme crée une nouvelle portée de sorte que les valeurs au moment de l'exécution de la boucle soient conservées, plutôt que de laisser chaque gestionnaire d'événement pointer sur la toute dernière valeur que la variable contient.

1

C'est appelé 28 lignes plus loin:

... 
    })(leftgutter + X * (j + .5) - 60 - R, Y * (i + .5) - 10, R, data[o]); 

si ce sont les quatre arguments.

Si vous ne donnez pas de nom à une fonction, la seule chose que vous pouvez faire est de l'appeler ici ou de la passer à quelqu'un d'autre. Ceci est assez standard si vous êtes familier avec les écouteurs d'événement:

window.addEventListener("load", function(event) { 
    document.body.innerHTML = "hello"; 
}, false); 

Dans ce cas, il est utilisé pour contrôler la portée des variables, afin de garantir que leurs valeurs ne sont pas réutilisés après une itération de la boucle complète. De nombreuses bibliothèques enveloppent le script entier dans un bloc de fonction, uniquement pour créer une nouvelle étendue. (Contrairement à d'autres langues accolades, un bloc { } ne seul pas créer un nouveau champ d'application.)

(function() { 
    var foo; // guaranteed to not leak or interfere with someone else's foo 
    // 6000 lines ... 
})(); 

En savoir plus sur JavaScript Scope and Closures.

+0

Merci, je vais lire sur les auditeurs d'événements. –

1

Une fonction anonyme est créé et appelé à la volée. Une version simplifiée serait

function(a){<some method code>}(x); 

Dans ce la valeur x est passée comme a dans la fonction.Dans votre exemple, la fonction est invoquée plus tard:

(function (dx, dy, R, value) { 
    var color = "hsb(" + [(1 - R/max) * .5, 1, .75] + ")"; 
    ... 
})(leftgutter + X * (j + .5) - 60 - R, Y * (i + .5) - 10, R, data[o]);