web-dev-qa-db-de.com

Festlegen einer dynamischen Eigenschaft für ein Modell mit Backbone.js

Story: Ich habe viele Eigenschaften, die eingestellt werden müssen. Da sie Ähnlichkeiten aufweisen, wähle ich die Klasse aus, zu der das Eingabefeld als Eigenschaftsnamen gehört.

Problem: Eine dynamische Eigenschaft eines Objekts kann genau wie ein assoziatives Array festgelegt werden. Also könnte ich tun 

var customattribute = this.$el.parents('div').attr('id');
var value = $(e.currentTarget()).val();

this.model.attributes[customattribute] = value;

Dies würde jedoch kein Änderungsereignis des Modells auslösen. Ich könnte manuell ein Änderungsereignis auslösen, aber dies würde this.model.changedAttributes () nicht aktualisieren. Ich muss nur das geänderte Attribut festlegen, nicht jedes Attribut.

Das funktioniert natürlich auch nicht:

this.model.set(customattribute: value);

Wie würde ich mit diesem Problem umgehen?

Ich habe ALOT (200+) Attribute, die gesetzt werden können. Ich möchte nicht für jedes Attribut separate Ereignislistener erstellen, es sei denn, dies ist der einzige Weg.

Code:

var Display = Backbone.View.extend({
    className: 'display',
    events: {
        'slide .slider' : 'sliderHandler'
    },
    initialize: function(){
        _.bindAll(this, 'render', 'sliderHandler','update');
        this.model.on('change',this.update, this);
    },
    render: function(){
        this.$el.html(_.template(html, {}));
        this.$('.slider').slider();

        return this;
    },
    sliderHandler: function(e){
        var slider = $(e.currentTarget);
        var property = slider.parents('div').attr('id');
        var value = slider.slider('value');

        this.model.attributes[property] = value;            
    },
    update: function(){
        console.log(this.model.changedAttributes());
        //get changed attribute + value here

    },
});

Bearbeiten:

Die zwei untenstehenden Antworten haben es gelöst. Ordnen Sie die Attribute einem Objekt zu und geben Sie das Backbone weiter. Ich habe auch eine andere Lösung gefunden. Anstelle eines Objekts akzeptiert model.set () auch ein Array.

model.set(customattribute, value, customattribute2, value2);
15
Jareish

Ich bin nicht sicher, ob ich Ihr Problem vollständig verstanden habe, aber: Wenn Sie ein Attribut aktualisieren möchten, müssen Sie nur Folgendes tun:

this.model.set({
     customattribute: value
});

Wenn Sie möchten, dass die Einstellung kein Ereignis auslöst, können Sie eine unbeaufsichtigte Option wie die folgende übergeben:

this.model.set({
     customattribute: value
}, {silent:true});

Ich hoffe es hilft dir.

AKTUALISIERTE:

Ein anderer Weg:

 var map = {};
 map[customattribute] = value;
 this.model.set(map);
26
Aito

Du musst das tun

var attributeName = this.$el.parents('div').attr('id');
var value = $(e.currentTarget()).val();
var attribute = {};
attribute[attributeName] = value;
this.model.set(attribute);

wenn das Attribut "test" und value "value" war, wäre es das Gleiche wie

this.model.set({test: 'value'});

dies ist, was das Attribut richtig setzt und dank des Modelländerungsereignisses für Ihre Ansicht verbreitet

5
James Kyburz

Ab Backbone 0.9.0 (30. Januar 2012) , model.set ( source ) akzeptiert einen Schlüssel , einen Wert und ein Optionen Objekt.

this.model.set(attributeName, value, { silent: true });

ist äquivalent zu

var attr = {};
attr[attributeName] = value;
this.model.set(attr, { silent: true });
0
Emile Bergeron