2012-11-19 3 views
0

En raison de problèmes de performances et d'autres problèmes, je souhaite diviser mon code en fonctions séparées, car il ne s'agissait auparavant que d'une grande fonction ".ready". Je suis nouveau à javaScript/jquery mais je pensais que j'essaierais moi-même. J'ai fait exactement la façon dont je pensais que c'était fait mais ma console me dit que les choses ne sont pas définies donc je devine que j'ai des choses hors de portée. J'y ai lu plus en détail, mais je n'ai toujours rien trouvé.Diviser le code en fonctions

Mon code fonctionne bien pour l'instant mais je veux entrer dans le habbit du codage propre. Est-ce que quelqu'un peut indiquer où je vais mal afin que je puisse continuer?

Voici un exemple de ce que j'ai jusqu'à présent

//Global variables 
var randomWord = []; 
var listOfWords = []; 
var populationNumber = []; 
var attemptNumber = []; 
var completionNumber = []; 
var gridSize = []; 

generateGrid(); 

startMusic(); 

randomizeReward(); 


//Click event to start the game 
$(".start-btn-wrapper").click(function() { 
    startplay(); 
}); 
//Click event to restart the game 
$(".restart-btn").click(function() { 
    restartplay(); 
}); 

Merci

Fiddle: http://jsfiddle.net/QYaGP/

Fiddle HTML: http://jsfiddle.net/QYaGP/1/

+0

Pas un exemple de workoff complet dans jsfiddle sans le HTML, mais ma conjecture immédiate serait la suivante: vous êtes des variables de "portée globale" qui sont seulement globales à l'état prêt. Les fonctions en dehors du prêt n'ont pas accès à ces variables. Déplacez-les au-dessus de la fonction 'ready' de jquery pour qu'ils soient vraiment globaux et que ces autres fonctions puissent y accéder. –

+0

Ok, je vais essayer que Eli Gassert – IronSpoon

+0

En savoir plus sur la portée variable de JavaScript et de lire sur [programmation fonctionnelle] (http://eloquentjavascript.net/chapter6.html) –

Répondre

0

Vous devez commencer à passer des informations en les fonctions que vous définissez. Si vos fonctions n'ont pas d'arguments, vous devrez utiliser des variables définies globalement, des références codées en dur aux sélections de jquery, etc. pour que tout soit fait.

Ainsi, à titre d'exemple, vous avez une fonction

function replaySound() { 
    $("#hintSound").attr('src', listOfWords[randomWord].hintSound); 
    hintSound.play(); 
} 

Cela va effectivement jouer le son détaillé dans listOfWords[randomWord] par l'élément #hintSound. Vous pouvez le faire via:

function playSound(selector, wordlistEntry) { 
    $(selector).attr('src', wordlistEntry.hintSound); 
    $(selector)[0].play(); 
} 

Et puis au lieu d'appeler replaySound(), vous appelez:

playSound('#hintSound', listOfWords[randomWord]); 

De cette façon, le comportement que vous voulez est enveloppé dans la fonction, mais la Les détails, c'est-à-dire les données dont vous avez besoin, sont transmis via les arguments. Cela vous permet de réutiliser la fonction pour jouer n'importe quel son en utilisant n'importe quel sélecteur, pas seulement #hintSound.

Vous constaterez en même temps que vous avez besoin de commencer à choisir le comportement d'une fonction dans le code qui l'appelle, plutôt que dans la fonction. C'est bien, parce que le contexte de ce que vous essayez d'atteindre est dans le code appelant, pas dans la fonction. C'est ce qu'on appelle la «séparation des préoccupations»; vous essayez de garder la logique sur une chose donnée confinée à une zone, plutôt que de la répandre dans de nombreuses fonctions. Mais vous voulez toujours des fonctions pour vous permettre d'encapsuler le comportement. Cela vous permet de changer de comportement proprement et facilement, sans avoir à tout réécrire chaque fois qu'une partie de la logique change. Le résultat devrait être que vous trouvez que plusieurs fonctions ont effectivement fait la même chose, mais avec des spécificités différentes, donc vous pouvez simplement avoir une fonction à la place et la réutiliser. C'est le principe Do not Repeat Yourself, qui est également important.

+0

Pourriez-vous me donner un exemple de mon code s'il vous plaît? @Phil H – IronSpoon

0

Si vous êtes préoccupé par les performances, je voudrais utiliser un framework tel que AngularJS. Vous pouvez injecter du code modularisé. Mieux encore, avec MVC, votre vue est liée à votre modèle. En changeant le modèle, la vue se met automatiquement à jour.

De même, arrêtez d'utiliser des sélecteurs de classe. Utilisez des sélecteurs d'identifiant. Ils sont beaucoup plus rapides. Vous voulez également précharger des sélecteurs (même avec des sélecteurs de classe). De cette façon, vous recherchez uniquement le DOM une fois:

var ele = $('#elementId'); 

$(ele).doSomething(); 

De cette façon, vous avez une référence à l'élément DOM. Vous pouvez utiliser une structure de données pour stocker toutes vos références en dehors de la portée mondiale:

var elementReferences = {}; //declaration 
elementReferences.mainPage = {}; //use 
elementReferences.mainPage.root = $('#mainPage'); //load the root div of a page segment 
elementReferences.mainPage.title = $(elementReferences.mainPage.root).children('#title'); //load the title 

elementReference.mainPage.form = $(elementReferences.mainPage.root).children('#form'); //load the form 

Maintenant, vous pouvez faire ceci:

$(elementReference.mainPage.form).whatever(); 

et il n'a pas à rechercher les DOM de l'élément . Ceci est particulièrement utile pour les applications plus volumineuses.

Si vous placez une fonction dans document.ready, selon votre violon, vous ne pouvez accéder à cette fonction que dans le cadre de l'appel document.ready. Vous voulez vraiment pouvoir charger/décharger des fonctions dynamiquement dans la portée dans laquelle ils sont requis, où angularjs entre en jeu.

Vous aussi, pour la plupart, vous voulez supprimer vos fonctions et variables de la portée globale et les mettre dans des conteneurs qui sont triés par leurs dépendances et leur utilisation. Ceci est la programmation orientée objet 101. Au lieu d'avoir un tas de tableaux assis dans le cadre global où ils pourraient être écrasés par erreur par un autre développeur, vous voulez les mettre dans un conteneur:

var arrays = {}; //create the object 

arrays.whatever1 = []; 
arrays.whatever2 = []; 

De toute évidence, vous allez probablement vouloir un nom plus descriptif que "tableaux". Les fonctions fonctionnent de la même manière:

var ajax = {}; //ajax object 
var ajax.get = function(){ 
}; 
var ajax.post = function(){ 
}; 
var ajax.delete = function(){ 
}; 

Cela favorise généralement un code plus propre qui est plus réutilisable et plus facile à entretenir. Vous voulez passer une bonne partie de votre temps à écrire une spécification qui documente entièrement l'architecture globale avant de commencer le développement. NE JAMAIS sauter le pistolet si vous pouvez l'aider. Passez du temps à faire des recherches approfondies et à planifier l'ensemble de la situation et à voir comment tout se déroule au lieu d'essayer de l'agencer et de la comprendre au fur et à mesure. Vous passez moins de temps à réinventer la roue quand vous le faites de cette façon.

Il a été développé par google, il devrait donc exister depuis longtemps. Je ne sais pas si vous êtes le responsable de l'architecture de votre système, mais si la performance/la réutilisation est un problème dans votre entreprise, cela vaut vraiment la peine d'y jeter un coup d'œil. Je serais plus qu'heureux de vous donner un aperçu de la plupart de ce que je sais en termes d'architecture logicielle et d'ingénierie. Juste MSG moi si vous êtes intéressé. Toujours heureux d'aider!