هل يمكنني ربط مدخلات النماذج للنماذج في backbone.js دون تتبع أحداث الضباب يدويًا؟

StackOverflow https://stackoverflow.com/questions/4074636

سؤال

لدي تطبيق Backbone.js (www.github.com/juggy/job-board) حيث أرغب في ربط مدخلات النموذج الخاصة بي مباشرة بالنموذج الخاص بي (la sproutcore).

هل من الممكن مع backbone.js (أو أدوات أخرى) دون تتبع كل أحداث طمس فعليًا على المدخلات وتحديث النموذج يدويًا؟ هذا يبدو وكأنه الكثير من رمز الغراء.

شكرًا،
جوليان

هل كانت مفيدة؟

المحلول

لست متأكدًا من قيام SC بذلك ، لكن ربما يستمعون إلى الأحداث أيضًا.

window.SomeView = Backbone.View.extend({
  events: {
    "change input.content":  "contentChanged"
  },
  initialize: function() {
    _.bindAll(this, 'contentChanged');
    this.inputContent = this.$('input.content');
  },
  contentChanged: function(e) {
    var input = this.inputContent;

    // if you use local storage save 
    this.model.save({content: input.val()});

    // if you send request to server is prob. good idea to set the var and save at the end, in a blur event or in some sync. maintenance timer.
    // this.model.set({content: input.val()});
  }
});

نصائح أخرى

هناك طريقة أجمل للتعامل مع هذا إذا كان النموذج الخاص بك يتضمن الكثير من الخصائص فيه.

SampleView = Backbone.View.extend({
    el: "#formEl",

    events: {
        "change input": "changed",
        "change select": "changed"
    },

    initialize: function () {
        _.bindAll(this, "changed");
    },

    changed:function (evt) {
       var changed = evt.currentTarget;
       var value = $(evt.currentTarget).val();
       var obj = {};
       obj[changed.id] = value;
       this.model.set(obj);
    }
 });

هناك اعتماد على عناصر الإدخال الخاصة بك التي لها معرف مثل ما هو اسم الخاصية في النموذج الخاص بك.

أعتقد أن هذه طريقة أنظف (وربما أسرع) لإنشاء كائن من عنصر إدخال

changed: function(evt) {
  var target = $(evt.currentTarget),
      data = {};
  data[target.attr('name')] = target.val();
  this.model.set(data);
},

بدون jquery:

changed: function(evt) {
  var target = evt.currentTarget,
      data = {};
  data[target.name] = target.value;
  this.model.set(data);
},

هل جربت العمود الفقري. modelbinder؟ إنها أداة لطيفة أن تفعل ما تحتاجه: https://github.com/theironcook/backbone.modelbinder

أنا أعمل على Corset ، مكتبة نموذج لـ Backbone.js مستوحاة من وحدة نماذج Django ، ولكنها أقل طموحًا في نطاقها. لا تزال تعمل على العمل ، لكنها ستنتهي على github عندما يكون على الأقل شبه مستقر وعملي.

الهدف من مشد هو الحصول على فئات الحقل الفرعية بسهولة بحيث يمكنك إنشاء مدخلات معقدة لحالات الاستخدام الأكثر تعقيدًا (تختار المتتالي ، إلخ). يجعل هذا النهج كل حقل كعرض منفصل ، ومرتبط طريقة عرض النموذج بنموذج ويستخدم أحداث التغيير ، أو أحداث طمس أو إرسال الأحداث لتحديث النموذج (قابل للتكوين ، الافتراض الافتراضي). كل طريقة عرض لها وظيفة getData قابلة للتجاوز والتي تنطلق في الخرائط الافتراضية إلى وظيفة jQuery .Val ().

باستخدام الافتراضات المعقولة ودالة modelformfactory ، نستخدم Corset (أو المجموعة الفرعية منه فعليًا حتى الآن) للتطوير السريع ، وتحديد نموذج باستخدام أسماء السمات المعقولة ، واستخدم ModelformFactory ولديك تعديل واجهة المستخدم الفورية.

لقد قمت بإنشاء التقنية التالية على موقعي

class FooView extends MyView

  tag: "div"

  modelBindings:

    "change form input.address" : "address"
    "change form input.name"    : "name"
    "change form input.email"   : "email"

  render: ->

    $(@el).html """
      <form>
        <input class="address"/>
        <input class="name"/>
        <input class="email"/>
      </form>
    """

    super

    @


# Instantiate the view 
view = new FooView
  model: new Backbone.Model

$("body").html(view.el) 

لقد قمت بتفصيل الامتدادات إلى العمود الفقري الذي تحتاج إلى صنعه على مدونتي

http://xtargets.com

يستخدم نفس النمط التعريفي مثل خاصية الأحداث لعناصر النماذج الربط لنمذجة السمات

وهنا هو الكود الفعلي الذي ينفذ الفصل لك في Coffescript

class MyView extends Backbone.View

  render: ->

    if @model != null
      # Iterate through all bindings
      for selector, field of @modelBindings
        do (selector, field) =>
          console.log "binding #{selector} to #{field}"
          # When the model changes update the form
          # elements
          @model.bind "change:#{field}", (model, val)=>
            console.log "model[#{field}] => #{selector}"
            @$(selector).val(val)

          # When the form changes update the model
          [event, selector...] = selector.split(" ")
          selector = selector.join(" ")
          @$(selector).bind event, (ev)=>
            console.log "form[#{selector}] => #{field}"
            data = {}
            data[field] = @$(ev.target).val()
            @model.set data

          # Set the initial value of the form
          # elements
          @$(selector).val(@model.get(field))

    super

    @

appologies إذا كنت لا تحب Coffescript. أفعل. الجميع مختلف :)

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top