Reduce duplication in common forms
Our form partials include a lot of repeated HTML code, much of which is boilerplate.
Here's an example from the admin settings:
%fieldset
%legend Account and Limit Settings
.form-group
.col-sm-offset-2.col-sm-10
.checkbox
= f.label :gravatar_enabled do
= f.check_box :gravatar_enabled
Gravatar enabled
.form-group
= f.label :default_projects_limit, class: 'control-label col-sm-2'
.col-sm-10
= f.number_field :default_projects_limit, class: 'form-control'
.form-group
= f.label :max_attachment_size, 'Maximum attachment size (MB)', class: 'control-label col-sm-2'
.col-sm-10
= f.number_field :max_attachment_size, class: 'form-control'
and from the user profile:
.col-lg-9
.form-group
= f.label :layout, class: 'label-light' do
Layout width
= f.select :layout, layout_choices, {}, class: 'form-control'
.help-block
Choose between fixed (max. 1200px) and fluid (100%) application layout.
.form-group
= f.label :dashboard, class: 'label-light' do
Default dashboard
= f.select :dashboard, dashboard_choices, {}, class: 'form-control'
.form-group
= f.label :project_view, class: 'label-light' do
Project view
= f.select :project_view, project_view_choices, {}, class: 'form-control'
.help-block
Choose what content you want to see on a project's home page.
It would be nice to be able to reduce these down so the decisions about HTML element wrapping, classes, etc, were taken in a common place.
This is commonly accomplished in Rails using Form Builders: http://api.rubyonrails.org/classes/ActionView/Helpers/FormBuilder.html
You can extend your f
instance so that calls like f.select
automatically include a label, surrounding HTML tags, etc. You choose the form builder to use when calling form_for
, or you can configure a default builder to use.
You can also introduce new methods and blocks, so for instance, you could do:
= f.legend "Account and Limit settings" do |f|
= f.check_box :gravatar_enabled # No "Gravatar description" label provided - it can be inferred from the symbol
= f.number_field :default_projects_limit
= f.number_field :max_attachment_size, label: "Max attachment size (MB)"
This could generate the same HTML as we get at present, but is 4 instead of 15 lines.