2012-04-22 11 views
5

Nella mia app ho una connessione socket.io che sta ascoltando il back-end e sta aggiornando i modelli tenuti dal browser dei client (che recupera il modello per id e chiama set sull'attributo del modello).backbone.js: aggiorna il modello, riordina e rielabora la collezione di modelli

Mi piacerebbe che la raccolta fosse ordinata, quindi ri-renderizzata nel suo insieme in modo da riflettere qualsiasi nuovo ordinamento sui modelli come risultato del set (la maggior parte degli esempi sembra essere intorno a singole viste che vengono ridisegnate). Qual è un metodo per raggiungere questo obiettivo?

NB Ho un layout backbone.js sollevato piuttosto letteralmente dall'app di esempio todo (questa è la prima app per backbone).

risposta

12

È possibile ottenere ciò che si desidera fornendo un metodo comparator per la raccolta.

Esempio:

ModelCollection = Backbone.Collection.extend({ 
    comparator: function(a, b) { 
     if (a.get("name") > b.get("name")) return 1; 
     if (a.get("name") < b.get("name")) return -1; 
     if (a.get("name") === b.get("name")) return 0; 
    }, 

    initialize: function() { 
     this.on('change:name', function() { this.sort() }, this); 
    } 
}); 

Il comparator in questo esempio causerà tua raccolta da ordinare in ordine crescente dall'attributo name dei modelli all'interno.

Si noti che la raccolta non verrà ordinata automaticamente quando si cambiano gli attributi di uno qualsiasi dei suoi valori models. Per impostazione predefinita, l'ordinamento avviene solo quando si creano nuovi modelli e si aggiungono alla raccolta; ma il comparatorsarà essere utilizzato dal metodo collection.sort.

Il codice sopra sfrutta questo impostando un listener di eventi che semplicemente riordina la collezione su qualsiasi change s agli attributi name del suo models.

Per completare il quadro, abbiamo istituito un listener di eventi appropriato nel View collegato con la raccolta per assicurarsi che ri-rendering su eventuali modifiche:

CollectionView = Backbone.View.extend({ 
    initialize: function() { 
     this.collection = new ModelCollection(); 
     this.collection.on('all', function() { this.render() }, this); 
    }, 

    render: function() { 
     this.$el.html(this.collection.toJSON()); 
    } 
}); 

il gioco è fatto :)


estratto rilevante dal Backbone documentation:

di default non c'è comparator per una collezione. Se si definisce uno comparator, verrà utilizzato per mantenere la raccolta in ordine ordinato. Ciò significa che man mano che i modelli vengono aggiunti, vengono inseriti nell'indice corretto in collection.models. Un comparatore può essere definito come sortBy (passa una funzione che accetta un singolo argomento), come sort (passa una funzione di confronto che prevede due argomenti) o come una stringa che indica l'attributo da ordinare. [...] Le raccolte con un numero comparator non verranno riordinate automaticamente se in seguito si modificano gli attributi del modello, quindi è possibile chiamare sort dopo aver modificato gli attributi del modello che avrebbero influito sull'ordine.

Problemi correlati