手柄中的条件部分

时间:2012-02-28 15:41:37

标签: javascript templates ember.js handlebars.js

我有以下数据,我正在尝试提供给Handlebar模板

{
    "set-group": [
        {
            "label": "Source Data",
            "type": "select",
            "options": [
                {
                    "value": "Default Selections"
                },
                {
                    "value": "Other Selections"
                }
            ]
        },
        {
            "label": "Scale",
            "type": "radio",
            "options": [
                {
                    "value": "log",
                    "label": "Log",
                    "groupname": "group2"
                },
                {
                    "value": "linear",
                    "label": "Linear",
                    "groupname": "group2"
                }
            ]
        }
    ]
}

我创建并注册了2个Partials,一个模板“选择”表单元素,另一个模板“radio”输入。我不知道数据中将包含什么类型的表单元素,因此我需要某种帮助程序来检查type == select并为select选择适当的部分。我在创建这样的助手时遇到了麻烦。

我正在考虑将数据中的type = select替换为select = true,并使用if / else帮助程序检查true / false但我宁愿保持格式标准化

有什么想法吗?

2 个答案:

答案 0 :(得分:13)

我最终使用了这个助手

// Comparison Helper for handlebars.js
// Pass in two values that you want and specify what the operator should be
// e.g. {{#compare val1 val2 operator="=="}}{{/compare}}

Handlebars.registerHelper('compare', function(lvalue, rvalue, options) {

    if (arguments.length < 3)
        throw new Error("Handlerbars Helper 'compare' needs 2 parameters");

    operator = options.hash.operator || "==";

    var operators = {
        '==':       function(l,r) { return l == r; },
        '===':      function(l,r) { return l === r; },
        '!=':       function(l,r) { return l != r; },
        '<':        function(l,r) { return l < r; },
        '>':        function(l,r) { return l > r; },
        '<=':       function(l,r) { return l <= r; },
        '>=':       function(l,r) { return l >= r; },
        'typeof':   function(l,r) { return typeof l == r; }
    }

    if (!operators[operator])
        throw new Error("Handlerbars Helper 'compare' doesn't know the operator "+operator);

    var result = operators[operator](lvalue,rvalue);

    if( result ) {
        return options.fn(this);
    } else {
        return options.inverse(this);
    }
  });

来源:http://doginthehat.com.au/2012/02/comparison-block-helper-for-handlebars-templates/

答案 1 :(得分:2)

我构建了类似的东西:

// superclass for all form field views
App.FormFieldView = Ember.View.extend({
    classNames: 'formFieldView',
    field: null,
    ...
});

// form field with just text
App.FormFieldTextView = App.FormFieldView.extend({
    templateName: 'formfield-text',
    ...
});

// form field with checkbox
App.FormFieldCheckboxView = App.FormFieldView.extend({
    templateName: 'formfield-checkbox',
    ...
});

... and so on (have more types for date selector, select lists etc)

然后我有一个用于指定字段的字段类。诀窍是typeXXX字段,我用它来定义要渲染的内容。

// field definition in controller.
App.Field = Ember.Object.extend({ 
    label: null,
    required: true,
    value: null,
    typeText: function () { // defaults to typeText
        return !(this.get('typeDate') || this.get('typeSelect') 
                 || this.get('typeCheckbox')
                 || this.get('typeInfo'));
    }.property('typeDate', 'typeSelect', 'typeCheckbox', 'typeInfo').cacheable()
});

示例:

var fields = [
    App.Field.create({ label: 'First name',
                       valueBinding: 'App.model.firstName'
                     }),
    App.Field.create({ label: 'I have a valid work permit for working in India.',
                       valueBinding: 'App.model.validWorkingIndia',
                       typeCheckbox: true});
];

最后我的模板视图切换了这个数组:

      <fieldset>
        <dl>
          {{#each fields}}
            {{#if typeText}}
              {{view App.FormFieldTextView fieldBinding="this"}}
            {{/if}}
            {{#if typeCheckbox}}
              {{view App.FormFieldCheckboxView fieldBinding="this"}}
            {{/if}}

            ... more types here

          {{/each}}
        </dl>
      </fieldset>

表单控件的Handlebar模板:

  <script type="text/x-handlebars" data-template-name="formfield-text">
    <dt><label>
        {{field.label}}{{#if field.required}}*{{/if}}
    </label></dt>
    <dd>{{view Ember.TextField valueBinding="field.value"}}</dd>
  </script>

  <!-- dd/dt deliberately in the wrong order -->
  <script type="text/x-handlebars" data-template-name="formfield-checkbox">
    <dd class="checkbox">
      {{view Ember.Checkbox valueBinding="field.value"}}
    </dd>
    <dt class="checkbox"><label>{{field.label}}{{#if field.required}}*{{/if}}
        </label></dt>
  </script>