Voici la chose: si vous ne pouvez pas comprendre pourquoi vous auriez besoin d'un framework comme Backbone, alors il y a de fortes chances que ce ne soit pas le cas! Peut-être travaillez-vous exclusivement sur des sites Web simples ou sur des thèmes WordPress de base; dans ces cas, un cadre JavaScript structuré sera probablement excessif.
Cependant, il y aura sûrement un jour où vous réaliserez que tout ce code spaghetti dans scénario
Les balises au bas de votre page sont soudainement devenues ingérables. De plus, en raison de la structure de votre code, il est également impossible de le tester. Haleter! Que faire?
Lorsque ce jour se produira - et cela se fera -, pointez votre navigateur sur Backbonejs.org et faites un pas en avant, au fur et à mesure que vous avancez au niveau suivant de votre maturité de programmation.
Pensez à Backbone comme un petit framework (5,6 Ko, compacté) qui structure vos applications. En mettant en œuvre sa propre variante du modèle MVC (en réalité, il ressemble plus à MV *), Backbone fournit les outils nécessaires pour séparer vos données de la présentation. Si vous y réfléchissez, la plupart d’entre nous tombons souvent lorsque nous essayons désespérément de conserver nos données. Cela aboutit généralement à d'innombrables requêtes DOM, car nous recherchons frénétiquement les valeurs nécessaires pour synchroniser la présentation et les données de notre application. Il doit y avoir un meilleur moyen!
"Sortez votre vérité du DOM". - Jeremy Ashkenas (Créateur de Backbone.js)
La solution, comme le créateur de Backbone.js, Jeremy Ashkenas, le préconise si souvent, est d'arrêter de lier vos données au DOM. Faites en sorte que votre vue reflète vos données, et non l'inverse!
En vérité, il est probablement préférable que vous ne tentiez même pas de convertir vos sensibilités MVC existantes
Vous verrez souvent Backbone, ainsi que de nombreux frameworks de frères et soeurs, appelés MV *, plutôt que MVC. Étant donné que les concepts de "contrôleur" et de "vue" côté serveur standard ne sont pas très bien transférés vers un framework JavaScript, cela peut souvent être source de confusion. C'est certainement fait pour moi!
En vérité, il est probablement préférable que vous n'essayiez même pas de convertir vos sensibilités MVC existantes; ça ne fera que vous embrouiller. Une "vue" dans Ruby on Rails n'est pas la même chose qu'une "vue" dans Backbone. Ou bien, un "contrôleur" dans CodeIgniter n'a pas vraiment d'équivalent dans Backbone. En fait, les contrôleurs n'existent pas dans Backbone! Au lieu de cela, Backbone emprunte des morceaux à d’autres frameworks, raison pour laquelle nous l’appelons souvent plus proche de MVP (Model, View, Presenter) ou MV *: ce n’est pas MVC, et pas tout à fait MVP; c'est sa propre saveur.
Commençons par déterminer comment la logique sera divisée dans notre application. Réajuster notre concept de la manière dont JavaScript doit être structuré peut prendre un certain temps, alors ne vous inquiétez pas si cela vous prend du temps..
Dans Backbone, les données sont représentées par un modèle. Par exemple, considérons un Photo
modèle. Ce modèle définira le schéma directeur d'une photo: quelle est la source de la photo, sa description, qui est représenté sur la photo, etc. Nous pouvons même appliquer une validation si nécessaire, via une option valider
méthode.
var Photo = Backbone.Model.extend (valeurs par défaut: src: 'images / placeholder.jpg', description: 'Mon image', personnes: []);
Avec le plan en place, nous pouvons maintenant configurer notre première photo en créant une nouvelle instance du Photo
modèle, comme si:
var photo = nouvelle photo (src: 'images_22 / connected-to-the-backbone.jpg', description: 'entre amis pour le dîner', personnes: ['John Doe', 'Rick James']);
Tada - vous avez créé votre premier modèle. Si vous devez extraire ou définir des informations à partir de cette instance de modèle, il vous suffit simplement d'utiliser les accesseurs et les calculateurs de Backbone:
photo.toJSON (); // objet contenant tous les accessoires photo.get ('src'); // images_22 / connected-to-the-backbone.jpg photo.set ('src', 'images / new-path.jpg'); photo.get ('src'); // images / new-path.jpg
Dans Backbone, en tant que meilleure pratique, une vue est responsable de la représentation d'un seul élément DOM et de tout enfant applicable, tel qu'un élément de liste, ou div
- tout ce que tu veux. Cela comprend l’enregistrement de tous les modèles applicables, l’écoute et la réponse aux événements, ainsi que la surveillance des modèles et collections associés pour y rechercher des modifications..
Créons une nouvelle vue pour la balise d'image, elle-même.
var ImageView = Backbone.View.extend (tagName: 'img', initialize: function () this.render ();, rendu: function () this. $ el.attr (src: this.model. get ('src'), alt: this.model.get ('description')););
Ne laissez pas ce code vous confondre. C'est assez lisible et élégant. Nous allons le faire étape par étape.
Pour commencer, tagName
spécifie l'élément DOM représenté par la vue. Dans ce cas, nous définissons la vue pour un seul img
élément, nous aurions tout aussi bien pu le lier à un élément qui existe déjà dans le DOM, via la el
propriété.
var ImageView = Backbone.View.extend (el: '# mon-image');
Dans les coulisses, Backbone récupère l’élément spécifié (#mon image
) du DOM, mettez-le en cache et mettez-le à disposition, via ImageView.el
et ImageView. $ El
. Comme on pouvait s'y attendre, la dernière version est l'élément encapsulé dans jQuery (ou éventuellement Zepto, si vous préférez cette bibliothèque à jQuery).
Ensuite, vous pouvez penser à la initialiser
méthode en tant que constructeur. Lorsqu'une nouvelle instance de cette vue est créée, cette méthode est automatiquement exécutée. C’est l’endroit idéal pour créer de nouvelles variables d’instance et souscrire à n’importe quel événement de modèle ou de contrôleur..
Enfin, le rendre
méthode est responsable de la construction de la sortie. Dans ce cas, il définira à la fois le src
et alt
des attributs de l'image égaux aux données stockées dans le modèle associé à la vue.
Créons une nouvelle instance de ImageView
, et transmettre des données. Dans une application réelle, ces données peuvent provenir d’un formulaire, ou de quelque chose de similaire..
var photo = nouvelle photo (src: 'images_22 / connected-to-the-backbone.jpg', description: 'entre amis pour le dîner', personnes: ['John Doe', 'Rick James']); var imageView = new ImageView (model: photo); imageView.el; //
Cela peut être incroyablement puissant, si vous y réfléchissez! Dans Backbone, il est simple de mettre à jour une vue lorsque son modèle respectif est modifié, en supposant une relation un à un. Écoutons lorsque les données (ou le modèle) sont modifiées. Quand c'est le cas, nous devrions mettre à jour l'élément en conséquence.
Le code suivant peut être ajouté à la initialiser
méthode du ImageView
.
initialize: function () // Ecoute la mise à jour du modèle this.model.on ('change', this.render, this); this.render (); , render: function () this. $ el.attr (src: this.model.get ('src'), alt: this.model.get ('description'));
Ne sous-estimez pas l'efficacité de cette implémentation de PubSub. Lorsqu'un modèle est modifié, il fait une annonce, pour ainsi dire. "Tous ceux qui sont intéressés - je viens d'être modifié!" Selon nous, avec une seule ligne de code, nous pouvons souscrire à cette annonce et réagir en conséquence, en mettant à jour les attributs de l'image..
this.model.on ('change', this.render, this);
Dans ce cas, nous appelons à nouveau le rendre
méthode, et générer à nouveau les attributs.
Testons-le.
var imageView = new ImageView (model: photo); imageView.el; // photo.set ('src', 'images_22 / connecté au backbone.jpg'); imageView.el //
Excellent! Si nécessaire, vous pouvez également attacher facilement des écouteurs d’événements de niveau DOM, via événements
objet que Backbone recherchera et définira automatiquement pour vous. Peut-être que vous souhaitez modifier l'image lorsque vous cliquez dessus:
événements: 'clic': 'éditer', éditer: function () // éditer l'image
Comme cette vue particulière représente un seul img
élément, on peut s'en tenir à Cliquez sur'
, Cependant, vous constaterez souvent que View.el
contient des enfants imbriqués. Dans ces cas, vous pouvez spécifier un sélecteur après le type d'événement, comme suit:
événements: 'click span': 'quelque chose', quelque chose: fonction ()
Le code ci-dessus, en utilisant View.el
en tant que contexte, attachera un événement de clic à un enfant envergure
s.
A quoi sert un modèle pour une seule photo? Stockons tous les modèles de photo dans un Photos
collection. Pensez aux collections comme des matrices avec du sucre ajouté et des méthodes pratiques, grâce à l'unique dépendance de Backbone, Underscore.js.
var Photos = Backbone.Collection.extend (model: Photo);
Ci-dessus, nous avons associé le Photos
collection avec le Photo
modèle que nous avons déjà créé. Ceci spécifie que tous les éléments de cette collection seront des instances du Photo
modèle.
Ensuite, nous créons notre instance et transmettons quelques modèles pour nous aider à démarrer. Dans ce cas, nous codons en dur les valeurs, mais vous pouvez tout aussi facilement extraire le JSON de votre serveur..
var photos = new Photos ([src: 'image1.jpg', description: 'Vacances 2012', src: 'image2.jpg', description: 'Mon meilleur ami', src: 'image3.jpg' , description: 'Fête d’anniversaire']);
Remarquez comment, cette fois, il semble que nous passions simplement quelques objets au Photos
collection. Cependant, dans les coulisses, chaque objet
dans le tableau
sera converti en Photo
modèle.
Semblables aux modèles, les collections annoncent toutes les modifications, par exemple lorsqu'un modèle est ajouté ou supprimé. Cela signifie que vous pouvez écouter, par exemple, lorsqu'un nouvel élément est ajouté à la collection. Lorsque cela se produit, vous pouvez compenser en mettant à jour le DOM en conséquence avec le nouvel élément..
this.collection.on ('add', this.appendItem);
En outre, comme indiqué ci-dessus, une collection fournit beaucoup de sucre. Par exemple, disons que nous devons saisir le src
propriété de chaque modèle de la collection. C'est un jeu d'enfant avec le cueillir
méthode!
photos.pluck ('src'); // ["image1.jpg", "image2.jpg", "image3.jpg"]
Remarquez comment, à tout moment, nos données sont disponibles. Nous n'avons jamais à interroger le DOM pour récupérer des valeurs. "Gardez votre vérité hors du DOM."
Reportez-vous à la documentation Underscore.js pour plus d'exemples d'utilisation..
À ce stade, nous avons une collection de photos, mais nous avons maintenant besoin d’une nouvelle vue qui sera responsable de la présentation du conteneur de photos. Rappelles toi, ImageView
n'est responsable que d'un seul élément d'image. Créons une nouvelle vue pour la liste de montage des photos.
var PhotosView = Backbone.View.extend (tagName: 'ul', className: 'photos', initialize: function () this.render ();, rendu: function () var imageView; this.collection.forEach (fonction (modèle) imageView = new ImageView (modèle: modèle); this. $ el.append ($ ('
Cette fois, nous créons la vue pour le wrapping
élément. Quand on appelle rendre()
, la méthode filtrera à travers tous les modèles contenus dans la collection associée (trois, dans notre cas), créera un nouveau ImageView
pour chacun - qui construit l'élément d'image - puis nous ajoutons cet élément d'image généré à la .Photos
liste non ordonnée.
Rappelez-vous: ne vous inquiétez pas des repeints ou des reflux.
PhotosView.el
n'a pas encore été injecté dans le DOM.
photosView.el.parentNode // null
Alors mettons tout cela ensemble!
// Créer une collection de modèles photo. var photos = new Photos ([src: 'image1.jpg', 'description': 'Vacances 2012', src: 'image2.jpg', 'description': 'Mon meilleur ami', src: ' image3.jpg ',' description ':' Fête d'anniversaire ']); // Crée un nouveau PhotosView et passe dans la collection de photos var photosView = new PhotosView (collection: photos); // Jetons notre liste de photos dans le DOM. $ ('body'). html (photosView.el);
Cela peut sembler déroutant au début, mais plus vous travaillerez avec Backbone, plus cela deviendra facile. Dans l’extrait de code précédent, nous commençons par créer une collection de Photo
des modèles. Ensuite, nous créons une nouvelle instance du PhotosView
récipient. Une fois rendue, cette vue filtre tous les éléments de sa collection respective, crée un nouveau ImageView
instances, et ajoute les éléments résultants à la liste non ordonnée. Enfin, nous prenons le fragment DOM résultant et le jetons dans le DOM. Pas trop dur, oui? Et regarde: structure!
Nous avons à peine effleuré la surface de ce dont Backbone est capable. Pour continuer votre apprentissage, référez-vous aux livres, screencasts et tutoriels suivants.
Backbone est parfois critiqué pour ne pas en offrir assez. Il n'applique aucune structure particulière et n'offre pas de composants d'interface utilisateur que vous pourriez recevoir de Dojo ou de jQuery UI. Ironiquement, malgré ces critiques, c'est ce qui rend Backbone si fantastique. Il ne vous impose pas ses opinions. Il fait un travail et un travail à merveille: structurer vos applications. Vous êtes alors libre de trouver le meilleur moyen d'adapter Backbone à vos projets existants..