Dynamic select value in ractive

2019-09-05 16:40发布

问题:

When using ractive this works fine:

<select value='{{sortColumn}}'>
  {{#each type}}
    <option>{{this}}</option>
  {{/each}}
</select>

As long as sortColumn itself is a fixed string. My question is, what if I want to create several selects, indexed by a upper level array, something like:

{{#each list}}
  <select value='{{sortColumn}}'>
    {{#type[.]}}
      <option>{{this}}</option>
    {{/}}
  </select>
{{/each}}

Where type is indexed by a list element. This works great in terms of rendering, I get the right options rendered. But the value of the select itself is replicated as sortColumn, and thus observing it will be triggered for each of the individual selects with the same function with nothing to distinguish them besides the values.

How to avoid this? Is it possible to attribute (and observe) different names to each select?

Thanks

回答1:

Yes, it's certainly possible - you can create a separate sortColumns object and use two-way binding with expressions like sortColumns[this].

var ractive = new Ractive({
  el: 'main',
  template: '#template',
  data: {
    list: [ 'a', 'b', 'c' ],
    type: {
      a: [ 1, 2, 3 ],
      b: [ 4, 5, 6 ],
      c: [ 7, 8, 9 ]
    },
    sortColumns: {}
  }
});
<script src="http://cdn.ractivejs.org/latest/ractive.js"></script>
<script id='template' type='text/html'>
  {{#each list}}
    <select value='{{sortColumns[this]}}'>
      {{#each type[this]}}
        <option>{{this}}</option>
      {{/each}}
    </select>
  {{/each}}
  
  <p><code>sortColumns: {{JSON.stringify(sortColumns)}}</code></p>
</script>

<main></main>

Alternatively, your list could be an array of objects that store their sortColumn locally:

var ractive = new Ractive({
  el: 'main',
  template: '#template',
  data: {
    list: [ 'a', 'b', 'c' ],
    type: {
      a: { sortColumn: 1, values: [ 1, 2, 3 ] },
      b: { sortColumn: 4, values: [ 4, 5, 6 ] },
      c: { sortColumn: 7, values: [ 7, 8, 9 ] }
    }
  }
});
<script src="http://cdn.ractivejs.org/latest/ractive.js"></script>
<script id='template' type='text/html'>
  {{#each list}}
    {{#with type[this]}}
      <select value='{{sortColumn}}'>
        {{#each values}}
          <option>{{this}}</option>
        {{/each}}
      </select>
    {{/with}}
  {{/each}}
  
  <p><code>type: {{JSON.stringify(type)}}</code></p>
</script>

<main></main>