Advertisement
  1. Code
  2. BackboneJS

Vistas de Backbone y el DOM

Scroll to top
Read Time: 8 min

Spanish (Español) translation by Andrea Jiménez (you can also view the original English article)

Final product imageFinal product imageFinal product image
What You'll Be Creating

Resumen

Las vistas de Backbone proporcionan una convención útil y la abstracción de las interfaces de usuario.  Sin embargo, si queremos incluir funcionalidades que Backbone no soporta nativamente, tendremos que integrar nuestro propio código o librerías externas en nuestra aplicación Backbone. Y tendremos que tener cuidado para evitar conflictos entre Backbone y las librerías externa que incluyamos en nuestro applicación.

Introducción a Backbone

Backbone es una forma fantástica de organizar tu código del lado cliente. Con abstracciones como modelos, vistas y colecciones, Backbone le ayuda a los desarrolladores serios a escribir aplicaciones bien organizadas y escalables.

Aunque hay muchas alternativas a Backbone, incluidas Angular y Ember, Backbone le brinda a los desarrolladores una libertad increíble para escribir y organizar su código de manera natural y cómoda sin ser demasiado obstinados sobre cómo se ve el Modelo de objetos de documento (DOM).

Skinny en las vistas de Backbone

Las vistas son uno de los componentes más poderosos y flexibles de Backbone. Según los autores de Backbone:

Las vistas de Backbone son casi más convencionales que el código: no determinan nada acerca de tu HTML o CSS y pueden usarse con cualquier biblioteca de plantillas de JavaScript.

Se utilizan para manipular lo que los usuarios ven en su navegador, y facilitan la comunicación con los modelos. Como resultado, en el paradigma de Model-View-Controller, es útil pensar en las vistas de Backbone como vista y controlador.

Esto tiene graves implicaciones al desarrollar aplicaciones con una interacción significativa del usuario. De hecho, hay muchas situaciones en las que es posible que quieras utilizar alguna otra biblioteca para manipular el DOM. La visualización de datos y los juegos basados en plataformas web son dos ejemplos en los que es posible que prefieras que otra biblioteca controle algunas de las representaciones de vista orientadas al usuario. Como resultado, puedes considerar usar jQuery, d3.js, crossfilter o three.js para algunas de tus necesidades de manipulación de DOM.

Afortunadamente, hay maneras de hacer que Backbone funcione bien con estos otros manipuladores DOM.

Manipulación del modelo de objetos de documento en Backbone

 Antes de profundizar en esto, repasemos la manipulación DOM en Backbone. Comencemos con un objeto de vista básico.

1
var SomeView = Backbone.View.extend({ 
2
    // Some definition stuff here 

3
}); 
4
5
var aView = new SomeView();

Excelente. Ahora, vamos a decirle a la vista cómo renderizarse definiendo un método .render() .

1
var SomeView = Backbone.View.extend({ 
2
    // define how to render something 

3
    render: function() { 
4
        // get some HTML 

5
        var htmlContent = "<p>This some HTML that will be inserted into the DOM</p>"; 
6
        
7
        // insert the html

8
        this.$el.html(htmlContent); 
9
        
10
        // return an instance of the object for chaining

11
        return this; 
12
    } 
13
});

Aquí están sucediendo varias cosas, así que vayamos paso a paso.

Definición de un método .render() .

En primer lugar, definimos un método .render() que encapsule la lógica necesaria para renderizar HTML. Ten en cuenta que Backbone viene con un método .render()  listo para usar. Sin embargo, no hace nada. ¡Fue diseñado para sobrescribirse con lógica personalizada!

Obtener contenido HTML

El ejemplo anterior asume que obtienes HTML en alguna parte. Puedes utilizar guiones bajos _.template(). Alternativamente, podemos usar otras bibliotecas de plantillas, como Handlebars (mi preferida). Lo único que importa es que, de alguna manera, obtenemos algo de contenido HTML.

¿Qué diablos es el?

Necesitamos un lugar para colocar el contenido HTML; para eso es el. Como .render(), el es un atributo que viene con las vistas de Backbone listas para usar. Hace referencia al elemento HTML (y a todos sus elementos secundarios) contenidos en esta vista. En el ejemplo anterior, no especificamos el. De forma predeterminada, el es un div. Sin embargo, podríamos haber configurado fácilmente el elemento padre así:

1
var SomeView = Backbone.View.extend({ 
2
    el: "article", ... 
3
}); 
4
5
var aView = new SomeView();
6
7
console.log(aView.el); // an empty "article" HTML element

También está $el, que es simplemente el envuelto en jQuery. Más adelante veremos que $el juega un papel importante en el dominio de las vistas de Backbone.

Devolviendo this...

Finalmente, devolvemos una referencia al objeto en sí para permitir el encadenamiento. Si bien no es estrictamente obligatorio, devolver this es una convención. Sin return this, necesitaríamos alguna forma de acceder al contenido HTML del elemento. El siguiente código muestra una solución alternativa.

1
/** 

2
 * If render() returns nothing, we are really 

3
 * accessing the `el` property of undefined, which does not 

4
 * exist!

5
 */
6
aView.render().el; // Should throw an error 

7
 
8
// Try accessing the HTML 

9
console.log(aView.el); // Should be empty (but defined!) 

10
11
// add HTML to the DOM of 'aView' 

12
aView.render(); 
13
14
// Try accessing the HTML again 

15
console.log(aView.el) // Should contain the HTML

¡Ay, no hay nada en la pantalla!

Buen punto. Aunque llamamos a .render(), no hay nada en la pantalla, ¿qué pasa?

Eso se debe a que todavía no hemos interactuado con el DOM. Todo lo que hicimos fue generar algo de HTML y representarlo en un objeto JavaScript llamado aView. Dado que ahora tenemos acceso al HTML generado, todo lo que tenemos que hacer es agregar o insertar el HTML en el DOM de tu aplicación web.

Para avanzar, también configuraremos una mini-aplicación para que cuando se cargue la página, aparezca la vista. A continuación se muestra cómo debe ser tu HTML y JavaScript.

Configuración básica de HTML

1
<html>
2
    <head>
3
        <meta charset="utf-8">
4
        <title>My Awesome Backbone App</title> 
5
        <!-- Include your CSS Here -->
6
        <link rel="stylesheet" type="text/css" href="/css/styles.css" />
7
        
8
        <!-- Include JS dependencies --> 
9
        <!-- Backbone depends on underscore and, in this example, 

10
             depends on jQuery. Please note the order of the 

11
             dependencies --> 
12
        <script src="/js/lib/jquery.js"></script>
13
        <script src="/js/lib/underscore.js"></script>
14
        <script src="/js/lib/backbone.js"></script>    
15
    </head>
16
    <body>
17
        <div class="app"></div> 
18
        <!-- Include your custom Backbone code in the below script -->
19
        <script src="/js/app.js"></script>            
20
    </body>
21
</html>

Esto es lo que está sucediendo en App.js

1
// Create a view 

2
var SomeView = Backbone.View.extend({ 
3
    initialize: function() {}, 
4
    render: function() { 
5
        var someHTML = "<p>This is some HTML</p>"; 
6
        this.$el.html(someHTML); 
7
        return this; 
8
    } 
9
}); 
10
11
// Create a router

12
var Router = Backbone.Router.extend({ 
13
    // define your routes 

14
    routes: { "": "home" }, 
15
    home: function() { 
16
        var aView = new SomeView(); 
17
        $('.app').html(aView.render().el); 
18
    } 
19
}); 
20
21
// Instantiate your router 

22
new Router(); 
23
24
// Start tracking history 

25
Backbone.history.start();

Ve a tu servidor/navegador local, carga la página ¡y tu aplicación debería estar ejecutándose!

Usando Backbone y jQuery simultáneamente

La flexibilidad de Backbone permite que el uso de bibliotecas de terceros manipule el DOM. Un escenario es cuando quieres usar jQuery y Backbone simultáneamente para manipular las vistas. A continuación se muestra un ejemplo actualizado.

1
var SomeView = Backbone.View.extend({ 
2
    
3
    // Manipulate DOM indirectly by creating HTML content in a 

4
    // Backbone View 

5
    render: function() { 
6
        var someHTML = "<p>Some HTML</p><p class='empty'><p>"; 
7
        this.$el.html(someHTML); 
8
        return this;
9
    }, 
10
    
11
    // Manipulate DOM directly from within the Backbone View

12
    renderWithJQuery: function() { 
13
        var otherHTML = "<p>Other HTML</p>"; 
14
        $('.app').append(otherHTML); 
15
        
16
        // may not make sense to return 'this' 

17
    }, 
18
    
19
    // another render method, to keep things interesting 

20
    specialRender: function() { 
21
        this.$('.empty').append("<span>No longer empty!</span>"); 
22
        return this; 
23
    } 
24
}); 
25
26
// Later in your app... 

27
28
// create the view 

29
var aView = new SomeView(); 
30
31
// change the DOM to reflect the newly created view 

32
$('.app').html(aView.render().el); 
33
34
// append more content directly to the DOM using jQuery within 

35
// a Backbone view object 

36
aView.renderWithJQuery();

El código anterior dará como resultado dos párrafos en la página. El primer párrafo contiene "Algo de HTML". El segundo párrafo contiene "Otro HTML".

Para poner a prueba tu conocimiento sobre esto, invierte las llamadas al método de la siguiente manera:

1
// SomeView is already defined 

2
3
var aView = new SomeView(); 
4
5
aView.renderWithJQuery(); 
6
7
$('.app').html(aView.render().el);

El código anterior dará como resultado un párrafo: "Algo de HTML". En ambos casos, también hay un elemento <p> sin nada en él. Discutiremos esto en un momento.

Manipular el DOM en las vistas de Backbone de manera eficiente

Comprender la magia de la manipulación (y transversal) eficiente del DOM requiere comprender this.$el y this.$(). Al usar this.$el, estamos ajustando la manipulación del DOM al contenido de la vista. Al usar this.$(), estamos examinando el recorrido de DOM al árbol DOM dentro de la vista.

Como resultado, en el contexto de Backbone, algunos usos de $() (en lugar de this.$()) podrían ser ineficientes. Por ejemplo, supongamos que queríamos cruzar el DOM para encontrar algún elemento. Podríamos usar cualquiera de los métodos comunes de recorrido DOM, incluido .find(), .children(), .closest(), .first(), y así sucesivamente.

Si sabemos, a priori, que el elemento que buscamos se encuentra en algún lugar dentro del DOM de la vista, entonces debemos usar this.$() para evitar buscar un árbol DOM más grande innecesariamente. Si el elemento que buscamos está fuera del DOM de la vista, entonces tendremos que usar $().

Por ejemplo, el método .specialRender() utiliza el recorrido DOM localizado para garantizar que buscamos elementos con la clase empty dentro del contexto de la vista. Si se encuentra, establece el contenido HTML de esos elementos para agregar un span y el texto "Ya no está vacío".

Conclusión

En este artículo revisamos las vistas de Backbone, discutimos cómo renderizar las vistas de Backbone en el DOM y exploramos cómo hacer que Backbone funcione bien con otras bibliotecas que quizás quieras utilizar para manipular el DOM. También aprendimos sobre el recorrido DOM localizado y los métodos identificados para cruzar el DOM de manera eficiente e ineficiente.

En la siguiente parte de este artículo profundizaremos en ejemplos más complicados de cómo hacer que varias bibliotecas trabajen juntas en la manipulación del DOM.

Advertisement
Did you find this post useful?
Want a weekly email summary?
Subscribe below and we’ll send you a weekly email summary of all new Code tutorials. Never miss out on learning about the next big thing.
Advertisement
Looking for something to help kick start your next project?
Envato Market has a range of items for sale to help get you started.