Module: Formtastic::Helpers::InputsHelper
- Includes:
- LocalizedString
- Included in:
- FormBuilder
- Defined in:
- lib/formtastic/helpers/inputs_helper.rb
Overview
#inputs is used to wrap a series of form items in a <fieldset>
and <ol>
, with each item
in the list containing the markup representing a single #input.
#inputs is usually called with a block containing a series of #input methods:
<%= semantic_form_for @post do |f| %>
<%= f.inputs do %>
<%= f.input :title %>
<%= f.input :body %>
<% end %>
<% end %>
The HTML output will be something like:
<form class="formtastic" method="post" action="...">
<fieldset>
<ol>
<li class="string required" id="post_title_input">
...
</li>
<li class="text required" id="post_body_input">
...
</li>
</ol>
</fieldset>
</form>
It's important to note that the semantic_form_for
and #inputs blocks wrap the
standard Rails form_for
helper and FormBuilder, so you have full access to every standard
Rails form helper, with any HTML markup and ERB syntax, allowing you to "break free" from
Formtastic when it doesn't suit:
<%= semantic_form_for @post do |f| %>
<%= f.inputs do %>
<%= f.input :title %>
<li>
<%= f.text_area :body %>
<li>
<% end %>
<% end %>
Instance Method Summary collapse
-
#inputs(*args, &block) ⇒ Object
#inputs creates an input fieldset and ol tag wrapping for use around a set of inputs.
Methods included from LocalizedString
Instance Method Details
#inputs(*args, &block) ⇒ Object
#inputs creates an input fieldset and ol tag wrapping for use around a set of inputs. It can be called either with a block (in which you can do the usual Rails form stuff, HTML, ERB, etc), or with a list of fields (accepting all default arguments and options). These two examples are functionally equivalent:
# With a block:
<% semantic_form_for @post do |form| %>
<% f.inputs do %>
<%= f.input :title %>
<%= f.input :body %>
<% end %>
<% end %>
# With a list of fields (short hand syntax):
<% semantic_form_for @post do |form| %>
<%= f.inputs :title, :body %>
<% end %>
# Output:
<form ...>
<fieldset class="inputs">
<ol>
<li class="string">...</li>
<li class="text">...</li>
</ol>
</fieldset>
</form>
Quick Forms
Quick, scaffolding-style forms can be easily rendered for rapid early development if called without a block or a field list. In the case an input is rendered for most columns in the model's database table (like Rails' scaffolding) plus inputs for some model associations.
In this case, all inputs are rendered with default options and arguments. You'll want more control than this in a production application, but it's a great way to get started, then come back later to customise the form with a field list or a block of inputs. Example:
<% semantic_form_for @post do |form| %>
<%= f.inputs %>
<% end %>
Nested Attributes
One of the most complicated parts of Rails forms comes when nesting the inputs for attrinbutes on associated models. Formtastic can take the pain away for many (but not all) situations.
Given the following models:
# Models
class User < ActiveRecord::Base
has_one :profile
accepts_nested_attributes_for :profile
end
class Profile < ActiveRecord::Base
belongs_to :user
end
Formtastic provides a helper called semantic_fields_for
, which wraps around Rails' built-in
fields_for
helper for backwards compatibility with previous versions of Formtastic, and for
a consistent method naming API. The following examples are functionally equivalent:
<% semantic_form_for @user do |form| %>
<%= f.inputs :name, :email %>
<% f.semantic_fields_for :profile do |profile| %>
<% profile.inputs do %>
<%= profile.input :biography %>
<%= profile.input :twitter_name %>
<% end %>
<% end %>
<% end %>
<% semantic_form_for @user do |form| %>
<%= f.inputs :name, :email %>
<% f.fields_for :profile do |profile| %>
<% profile.inputs do %>
<%= profile.input :biography %>
<%= profile.input :twitter_name %>
<% end %>
<% end %>
<% end %>
#inputs also provides a DSL similar to fields_for
/ semantic_fields_for
to reduce the
lines of code a little:
<% semantic_form_for @user do |f| %>
<%= f.inputs :name, :email %>
<% f.inputs :for => :profile do %>
<%= profile.input :biography %>
<%= profile.input :twitter_name %>
<%= profile.input :shoe_size %>
<% end %>
<% end %>
The :for
option also works with short hand syntax:
<% semantic_form_for @post do |form| %>
<%= f.inputs :name, :email %>
<%= f.inputs :biography, :twitter_name, :shoe_size, :for => :profile %>
<% end %>
#inputs will always create a new <fieldset>
wrapping, so only use it when it makes sense
in the document structure and semantics (using semantic_fields_for
otherwise).
All options except :name
, :title
and :for
will be passed down to the fieldset as HTML
attributes (id, class, style, etc).
When nesting inputs()
inside another inputs()
block, the nested content will
automatically be wrapped in an <li>
tag to preserve the HTML validity (a <fieldset>
cannot be a direct descendant of an <ol>
.
280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 |
# File 'lib/formtastic/helpers/inputs_helper.rb', line 280 def inputs(*args, &block) wrap_it = @already_in_an_inputs_block ? true : false @already_in_an_inputs_block = true title = field_set_title_from_args(*args) = args. [:class] ||= "inputs" [:name] = title skipped_args = Array.wrap .delete(:except) out = begin if [:for] # Nested form inputs_for_nested_attributes(*(args << ), &block) elsif block_given? field_set_and_list_wrapping(*(args << ), &block) else legend = args.shift if args.first.is_a?(::String) args = default_columns_for_object - skipped_args if @object && args.empty? contents = fieldset_contents_from_column_list(args) args.unshift(legend) if legend.present? field_set_and_list_wrapping(*((args << ) << contents)) end end out = template.content_tag(:li, out, :class => "input") if wrap_it @already_in_an_inputs_block = wrap_it out end |