Right now, I'm using the form_for.select
and options_for_select
rails helpers to create a select box with the data from the model. However, what I really need is a combobox like the one introduced with HTML5:
<input type=text list=browsers >
<datalist id=browsers >
<option> Google
<option> IE9
</datalist>
Is there a rails helper for creating such elements?
No, but it's quite easy to setup your own form builder helper method to achieve such a result, a simple example would be:
app/form_builders/combobox_form_builder.rb
class ComboboxFormBuilder < ActionView::Helpers::FormBuilder
include ActionView::Context # for nested content_tag
include ActionView::Helpers::FormTagHelper #for sanitize_to_id method access
def combobox_tag(name, options, opts= {})
@template.content_tag(:input, :name => name, :id => sanitize_to_id(name), :type => "text", :list => opts[:list_id]) do
content_tag(:datalist, :id => opts[:list_id]) {options}
end
end
end
After restarting your server you can implement your new combobox using the form builder by specifying a builder argument in your form_for call:
<%= form_for @foo, builder: ComboboxFormBuilder do |f| %>
<%= f.combobox_tag(:browser, options_for_select(["Firefox", "Chrome", "IE9"]), :list_id => "list")%>
<% end %>
Output HTML:
<input type="text" name="browser" list="list" id="browser">
<datalist id="list">
<option value="Firefox">Firefox</option>
<option value="Chrome">Chrome</option>
<option value="IE9">IE9</option>
</datalist>
Keep in mind that both IE & Safari do not offer support for the HTML5 Datalist.
<%= form_for @person do |f| %>
<%= f.label :first_name, "First Name" %>:
<%= f.text_field :first_name, list: 'first-name' %>
<datalist id="first-name">
<% Person.all.each do |person| %>
<option value="<%= person.first_name %>"></option>
<% end %>
</datalist>
<%= f.submit %>
<% end %>
You may also want to do distinct:
<% Person.select(:first_name).distinct.each do |person| %>
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With