仅设置表单提交时输入的字段的主干模型属性

Posted

技术标签:

【中文标题】仅设置表单提交时输入的字段的主干模型属性【英文标题】:Only set the Backbone Model attributes of fields entered on form submit 【发布时间】:2015-10-22 21:44:23 【问题描述】:

我正在为data-binding 试用Backbone.StickIt 插件,我的问题是在初始渲染时我显示模型默认值nameemail。如果我只在联系表单中输入我的姓名,姓名和电子邮件都会重新呈现,如何只设置输入的值?那么如果 email value === '' 不设置/呈现这个?

小提琴:http://jsfiddle.net/kyllle/e6z7gbta/

JS

var FormView = Backbone.View.extend(

    template: _.template( $('.js-form-template').html() ),

    events: 
        'submit': 'onFormSubmit'
    ,

    render: function() 
        this.$el.html( this.template( this.model.toJSON() ) );

        return this;
    ,

    onFormSubmit: function(event) 
        event.preventDefault();

        var nameValue = this.$('input[id=name]').val(),
            emailValue = this.$('input[id=email]').val();

        this.model.set(
            'name': nameValue,
            'email': emailValue
        );
    
);

var UserView = Backbone.View.extend(

    bindings: 
        '.js-name': 'name',
        '.js-email': 'email'
    ,

    template: _.template( $('.js-user-template').html() ),

    render: function() 
        this.$el.html( this.template( this.model.toJSON() ) );

        this.stickit();

        return this;
    
);

模板

<script type="text/template" class="js-user-template">
    <h1>User Details</h1>
    <p>Name: <span class="js-name"><%= name %></span></p>
    <p>Email: <span class="js-email"><%= email %></span></p>
</script>

<script type="text/template" class="js-form-template">
    <h1>Contact Form</h1>
    <form action="/">
        <fieldset>
            <label for="name">Name</label>
            <input type="text" id="name" class="form-text" />
        </fieldset>

        <fieldset>
            <label for="email">Email</label>
            <input type="email" id="email" class="form-text" />
        </fieldset>

        <fieldset class="form-actions">
            <input type="submit" value="Submit" />
        </fieldset>
    </form>
</script>

【问题讨论】:

【参考方案1】:

如果我理解正确,您只需要在为模型设置值之前添加一个简单的验证,而不是一次盲目地更新模型:

console.clear();

// Classes
var ContactModel = Backbone.Model.extend(
  defaults: 
    'name': 'Joe Bloggs',
    'email': 'joe@bloggs.com'
  
);
var FormView = Backbone.View.extend(

  template: _.template($('.js-form-template').html()),

  events: 
    'submit': 'onFormSubmit'
  ,

  render: function() 
    this.$el.html(this.template(this.model.toJSON()));

    return this;
  ,

  onFormSubmit: function(event) 
    event.preventDefault();

    var nameValue = this.$('input[id=name]').val(),
      emailValue = this.$('input[id=email]').val();
    
    //Validate the input before setting
    if (nameValue) this.model.set(
      'name': nameValue
    );
    if (emailValue) this.model.set(
      'email': emailValue
    );
  
);

var UserView = Backbone.View.extend(

  bindings: 
    '.js-name': 'name',
    '.js-email': 'email'
  ,

  template: _.template($('.js-user-template').html()),

  initialize: function() 
    //this.listenTo(this.model, 'change:name', this.render);
  ,

  render: function() 
    this.$el.html(this.template(this.model.toJSON()));

    this.stickit();

    return this;
  
);

// Setup
var contactModel = new ContactModel();

var formView = new FormView(
  model: contactModel
);

var userView = new UserView(
  model: contactModel
);

// Add to DOM
$('.js-ctn').append(
  userView.render().el,
  formView.render().el
);
@import url(http://fonts.googleapis.com/css?family=Roboto:300,400,500);
 body 
  font-family: Roboto;
  color: #191919;

a 
  color: #191919;

form fieldset 
  margin: 0 0 20px 0;
  font-size: 14px;

form fieldset.form-actions 
  margin: 0;

form fieldset label 
  display: block;
  margin: 0 0 5px 0;
  font-weight: bold;

form fieldset input.form-text 
  display: block;
  width: 50%;
  padding: 5px;
  font-size: 14px;
  border: 1px solid #ddd;
  background: #f5f5f5;
  -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, .05);
  -moz-box-shadow: inset 0 1px 2px rgba(0, 0, 0, .05);
  -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, .05);
  -webkit-border-radius: 4px;
  -moz-border-radius: 4px;
  border-radius: 4px;

form fieldset input.form-text:focus 
  border: 1px solid #ccc;
  background: #fff;

form fieldset p.form-help 
  margin: 5px 0 0 0;
  font-size: 12px;
  color: #999;

form input[type="submit"] 
  margin: 0;
  padding: 5px 10px;
  font-size: 12px;
  font-weight: bold;
  border: 1px solid #ccc;
  background: #eee;
  -webkit-border-radius: 4px;
  -moz-border-radius: 4px;
  border-radius: 4px;

form input[type="submit"]:hover,
form input[type="submit"]:focus 
  border: 1px solid #bbb;
  background: #e5e5e5;

form input[type="submit"]:active 
  border: 1px solid #ccc;
  background: #eee;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/underscore.js/1.8.3/underscore-min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/backbone.js/1.2.2/backbone-min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/backbone.stickit/0.8.0/backbone.stickit.min.js"></script>
<div class="js-ctn"></div>

<script type="text/template" class="js-user-template">
  <h1>User Details</h1>
  <p>Name: <span class="js-name"><%= name %></span>
  </p>
  <p>Email: <span class="js-email"><%= email %></span>
  </p>
</script>

<script type="text/template" class="js-form-template">
  <h1>Contact Form</h1>
  <form action="/">
    <fieldset>
      <label for="name">Name</label>
      <input type="text" id="name" class="form-text" />
    </fieldset>

    <fieldset>
      <label for="email">Email</label>
      <input type="email" id="email" class="form-text" />
    </fieldset>

    <fieldset class="form-actions">
      <input type="submit" value="Submit" />
    </fieldset>
  </form>
</script>

【讨论】:

我不确定我需要做的只是使用一些条件句还是缺少 Backbone 或 StickIt 提供的东西

以上是关于仅设置表单提交时输入的字段的主干模型属性的主要内容,如果未能解决你的问题,请参考以下文章

.Net Core Ajax 表单提交不返回非绑定模型属性

春季提交表单后的空字段

如何确保在禁用时提交 <select> 表单字段?

验证输入字段后如何提交表单

提交表单将所有空输入及其关联的隐藏输入字段设置为禁用

提交表单 ASP.NET 时清除所有输入字段