如何根据backbone.js中字段的值选择表单元素

时间:2013-11-28 07:08:32

标签: backbone.js coffeescript

我有一个动态表单,我从一个带有两个值的下拉字段开始:条形图和趋势图。如果选择条形图,我想显示尺寸值的多选下拉框,而如果选择趋势图,我想显示单选下拉框。

使用下面显示的模板和模型,只有在第一次保存模块后才会显示多选框。如何设置isBarChart变量,以便我可以使用它来确定在保存模块之前所显示的选择框是多选还是单选。

感谢。

从模板:

%div.select_module_type
  Module type:
  %select{ :class => "module_type" }
    {{#select module_type}}
    %option{ :value => '' }
    %option{ :value => 'bar_chart' } Bar chart
    %option{ :value => 'trend_chart' } Trend chart  
    {{/select}}


%div.select_dimension_value
  Dimension value:
  {{#if isBarChart}}
  %select.dimension_value{ 'multiple' => true }
    {{#select dimension_value}}
    {{/select}}
  {{else}}
  %select.dimension_value
    {{#select dimension_value}}
    {{/select}}
  {{/if}}

从模型中:

  isBarChart: ->
    return @get('module_type') == 'bar_chart'

从视图:

  showDimensionValuesSelector: (e) ->
    $(@el).find('div.select_dimension_value').hide()
    $(@el).find('div.date').hide()

    this_selector = $(@el).find('select.module_type')

    table = $(@el).find('select.table').val()
    return true if table == ''

    dimension_selector = $(@el).find('select.dimension[data-table="'+table+'"]')
    dimension = dimension_selector.val()
    return true if dimension == ''

    $(@el).find('div.select_dimension_value .preloader').css('display', 'inline')
    $(@el).find('select.dimension_value').hide()
    $(@el).find('select.dimension_value').html('')
    $(@el).find('div.select_dimension_value').show()
    $(@el).find('div.date[data-table="'+table+'"]').show()

    self = @
    $.get(
      '/dashboards/'+@model.get('dashboard_id')+'/dashboard_modules/dimension_values', 
      { table: table, dimension: dimension },
      (data, status, xhr) ->
        _.each(data, (item) ->
          if item.value != null and self.model.has('dimension_value') and item.value.toString() == self.model.get('dimension_value').toString()
            selected = 'selected="selected" '
          else
            selected = ''

          $(self.el).find('select.dimension_value').append('<option '+selected+'value="'+item.value+'">'+item.name+'</option>')
        )

        $(self.el).find('select.dimension_value').prepend('<option value=""></option>')
        $(self.el).find('select.dimension_value').show()
        $(self.el).find('div.select_dimension_value .preloader').hide()
      ,
      'json'
    )

1 个答案:

答案 0 :(得分:6)

由于您已经有型号,您只需在模型上设置该值而不将其保存到服务器:

在您看来

events: {
  'change .module_type': handleModuleTypeChange
},

handleModuleTypeChange: function() {
  this.model.set({
    module_type: this.$el.find('.module_type').val()
  });
}

然后听取您的模型更改,重新呈现模板:

//view initialize
initialize: function () {
  this.listenTo(this.model, 'change', this.render);
}

我不确定为什么必须在保存模型后渲染选择...如果是这种情况,您可能希望将Dimensions部分移动到新视图中。

=============================================== ===============

编辑:(2013年12月1日)

一个简单的jsfiddle:http://jsfiddle.net/8x7rU/

这是更改模型的DOM事件的简单示例,然后模型更改触发器视图呈现。

在这种情况下,当模型属性“module_type”发生更改时,将重新呈现整个视图。并且,通过更改“模块类型”下拉列表,视图将在模型上设置新的“module_type”值。

许多与DOM相关的逻辑实际上在模板中,当视图重新渲染时,模板知道模型的当前状态,然后相应地渲染。