Backbone.View "el" confusión


97

¿Cómo se deben elmanejar las vistas ? Tiene que estar configurado, de lo contrario, los eventos no se activan (ver aquí ).

¿Pero debería ser un elemento que ya está en la página? En mi aplicación, renderizo una plantilla (jQuery Templates) en un Fancybox. ¿Qué debería elser en ese caso?


11
Pensé: soy el único que está jugando con la elcosa.
Yugal Jindle

eles como gf. nadie puede entenderlos completamente.
Mahi

Respuestas:


121

Una vista el es donde tiene lugar todo el enlace de eventos. No tiene que usarlo, pero si desea que la red troncal active eventos, debe hacer su trabajo de renderizado en el. Una vista el es un elemento DOM pero no tiene por qué ser un elemento preexistente. Se creará si no extrae uno de su página actual, pero tendrá que insertarlo en la página si alguna vez desea verlo hacer algo.

Un ejemplo: tengo una vista que crea elementos individuales

window.ItemView = Backbone.View.extend({
    tagName: "li", //this defaults to div if you don't declare it.
    template: _.template("<p><%= someModelKey %></p>"),
    events: {
         //this event will be attached to the model elements in
         //the el of every view inserted by AppView below
        "click": "someFunctionThatDoesSomething"
    },
    initialize: function () { 
        _.bindAll(this, "render");
        this.render();
    },
    render: function () {
        this.el.innerHTML = this.template(this.model.toJSON());
        return this;
    }
});
window.AppView = Backbone.View.extend({
    el: $("#someElementID"), //Here we actually grab a pre-existing element
    initialize: function () { 
        _.bindAll(this, "render");
        this.render(new myModel());
    },
    render: function (item) { 
        var view = new ItemView({ model: item });
        this.el.append(view.render().el);
    }
});

La primera vista simplemente crea los elementos de la lista y la segunda vista realmente los coloca en la página. Creo que esto es bastante similar a lo que sucede en el ejemplo de Tareas pendientes en el sitio backbone.js. Creo que la convención es convertir el contenido en el. Entonces el el sirve como un lugar de aterrizaje o un contenedor para colocar su contenido de plantilla. Backbone luego vincula sus eventos a los datos del modelo dentro de él.

Cuando se crea una vista que se puede manipular el EL de cuatro maneras utilizando el:, tagName:, className:, y id:. Si ninguno de estos se declara, el predeterminado es un div sin id o clase. Tampoco está asociado con la página en este momento. Puede cambiar la etiqueta a otra cosa usando tagName (por ejemplo tagName: "li", le dará un el de <li></li>). También puede configurar el id y la clase de el. Aún así, el no es parte de tu página. La propiedad el le permite realizar una manipulación muy fina del objeto el. La mayor parte del tiempo utilizo unel: $("someElementInThePage")que en realidad une toda la manipulación que hace a el en su vista a la página actual. De lo contrario, si desea ver que todo el trabajo duro que ha realizado en su vista se muestre en la página, deberá insertarlo / adjuntarlo a la página en otro lugar de su vista (probablemente en renderizado). Me gusta pensar en el como el contenedor que manipula toda tu vista.


¡Gracias por la aclaración y el ejemplo! Creo que no siempre está claro cuál debería ser el el en determinadas situaciones y el desarrollador tiene que "sentirlo". ¡Sus explicaciones ciertamente ayudaron! Sin embargo, una pregunta: no define un el en su ItemView, pero accede a él en la función de renderizado. esto funcionara? ¿Existe algún tipo de el predeterminado si no lo define explícitamente?
Manuel Meurer

3
Por defecto, el es una etiqueta "div" sin id o clase. Es un objeto DOM que no está vinculado a su página DOM. Por lo general, lo inserto / añado a la página en la función de procesamiento o en la función de procesamiento de una vista principal.
LeRoy

Actualicé mi respuesta con una descripción de las propiedades que definen el.
LeRoy

5
Supongo que mi único problema al tomar un elemento preexistente con el: $ ("# someElementID") es que su vista probablemente sepa más de lo que debería, lo que dificulta su reutilización. ver "Desacoplar vista de DOM ..." coenraets.org/blog/2012/01/…
Scott Coates

@scoarescoare ya que está agregando la propiedad el en la instanciación, la vista en sí no sabe más de lo que debería, permanece modular y puede aceptar cualquier $ (el) que desee entregar. Así que esto realmente lo hace bastante reutilizable.
Metagrafista

6

Un poco viejo ahora, pero yo también estaba confundido, por lo que para otras personas que lleguen aquí, este violín podría ayudar: http://jsfiddle.net/hRndn/2/

var MyView = Backbone.View.extend({

    events: {
        "click .btn" : "sayHello",
    },

    sayHello : function() {
        alert("Hello");
    },


    render : function() {
        this.$el.html("<input type='button' class='btn' value='Say Hello'></input>");

    }
});

$(function() {
    myView = new MyView({el:"#parent_id"});
    myView.render();
});

He seguido este modelo y desearía no haberlo hecho. Para destruir una vista y eliminar los enlaces, la convención de la red troncal es view.remove (). Eso destruye $ el y lo elimina del DOM, por lo que cuando necesita mostrar la vista nuevamente, $ el no existe.
JJ

@Mark, ¿qué pasa si estoy usando una arquitectura compuesta como marionette ... todavía necesito tener view's el?
2013

su código de violín no funciona, ya que el enlace debe ser jsfiddle.net/hRndn
Izzy

@Mahi Sí, tienes razón. Probablemente pegué un enlace incorrecto, lo siento. Este funciona: jsfiddle.net/hRndn/127
Izzy

1

Desea que su 'el' haga referencia a un elemento que contiene un elemento hijo que tiene cualquier evento que desencadena un cambio en su vista. Puede ser tan ancho como una etiqueta de "cuerpo".


Hmm, eso tampoco lo aclara. La mayoría de las veces, los elementos que podrían desencadenar un cambio en mi vista están dentro de la plantilla que la vista representa, por lo que antes de que se represente, estos elementos aún no existen.
Manuel Meurer
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.