shearichard
shearichard

Reputation: 8372

ember-bootstrap - rendering "radio" inputs

Using the Ember addon ember-bootstrap I can make a set of radio buttons like this :

{{form.element controlType="radio" label="Fruit Type" property="radio" options=radioOptions optionLabelPath="label"}}

with a Controller that looks like this :

export default Controller.extend({

  init() {
    this._super(...arguments);
    this.radioOptions = [
      {
        label: 'Citrus',
        value: 'C',
        inline: true
      },
      {
        label: 'Non-Citrus',
        value: 'N',
        inline: true
      }
    ];
  }

});

The relevant doco is here https://www.ember-bootstrap.com/#/components/forms .

However what I can't do is provide a custom value to each radio button so that I end up with rendered HTML like this :

  <label>Citrus</label>  
  <input type="radio" value="C">
  <label>Non-Citrus</label>  
  <input type="radio" value="N">

I have looked at "Custom Controls" on https://www.ember-bootstrap.com/#/components/forms but I can't see how that applies to this case.


EDIT: Just to be clearer about why I want to do this I want to display the readable label (eg "Citrus") but have the non-readable value ("C") available to send back to the server (because the server thinks in terms of "C" or "N".

It's not essential I could send "Citrus" back and map it around on the server but I just thought this would be very straightforward.

Looking at the part of the doco starting with "You can also just customize the existing control component:" on https://www.ember-bootstrap.com/#/components/forms it does seem like you should be able to do the sort of thing I'm after but the example shown doesn't address the use of a value attribute and I can't figure out how to .

Upvotes: 1

Views: 405

Answers (2)

Neil Wheatley
Neil Wheatley

Reputation: 71

I had exactly the same issue but I finally solved it. You have to use form.element in block mode. Why is it also necessary to also write an action to update the value? I have no idea!

In my implementation, I'm using Ember changesets and my property is called usageType. I hope it's clear enough to adapt for your needs.

I'm also using Ember Truth Helpers, which is what the {{eq opt.value el.value}} part is. It sets checked to true if the input value is equal to the current-selected value.

# my-component.js

actions: {
  selectUsageType(option) {
      return this.set('changeset.usageType', option);
    }
}
# usage-type-options.js (imported in component JS)

[{
  label: 'First label',
  value: 'A'
},
{
  label: 'Second label',
  value: 'B'
}]

# Etc.
# my-component.hbs

# I'm not using angle-bracket invovation here, oops

{{#form.element
  property="usageType"
  label="My label" as |el|
}}
  {{#each usageTypeOptions as |opt|}}
    <div class="form-check">
      <input
        type="radio"
        class="form-check-input"
        id="{{el.id}}-{{opt.value}}"
        checked={{eq opt.value el.value}}
        onchange={{action "selectUsageType" opt.value}}
      >
      <label for="{{el.id}}-{{opt.value}}" class="form-check-label">
        {{opt.label}}
      </label>
    </div>
  {{/each}}
{{/form.element}}

Upvotes: 1

Joe Hany
Joe Hany

Reputation: 1015

You don't need to have the HTML rendered like that. if you want to access the checked radio, simply it is the property name dot value like radio.value.

Here how to get it in the on submit action:

  actions: {
    onSubmit() {
      alert(this.radio.value)
    }
  }

Upvotes: 2

Related Questions