Skip to content

Instantly share code, notes, and snippets.

@rosiehoyem
Last active August 29, 2015 14:11
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save rosiehoyem/a16089b31dd2e8ffd3bb to your computer and use it in GitHub Desktop.
Save rosiehoyem/a16089b31dd2e8ffd3bb to your computer and use it in GitHub Desktop.
Forms, Complex Data Models and AJAX
# /app/controllers/digitize_steps_controller.rb
...
responds_to :js
...
def form
end
...
# /app/helpers/process_steps_helper.rb
def show_partial(step_type_id)
if step_type_id == 1
render "digitize_steps/form", locals: {@process_step => @process_step}
elsif step_type_id == 2
render "subset_map_steps/form", locals: {@process_step => @process_step}
elsif step_type_id == 3
render "dissolve_steps/form", locals: {@process_step => @process_step}
elsif step_type_id == 4
render "transfer_poly_steps/form", locals: {@process_step => @process_step}
elsif step_type_id == 5
render "code_match_steps/form", locals: {@process_step => @process_step}
elsif step_type_id == 6
render "harmonize_steps/form", locals: {@process_step => @process_step}
elsif step_type_id == 7
render "regionalize_steps/form", locals: {@process_step => @process_step}
elsif step_type_id == 8
render "disaggregate_steps/form", locals: {@process_step => @process_step}
elsif step_type_id == 9
render "verify_steps/form", locals: {@process_step => @process_step}
elsif step_type_id == 10
render "lsib_align_steps/form", locals: {@process_step => @process_step}
else
end
end
# /app/views/digitize_steps/_form.html.erb
...
<%= fields_for :digitize_step, @process_step.build_digitize_step do |f| %>
...
<% end %>
# /app/views/digitize_steps/form.js.erb
$("#step-form").html("<%= j (render 'digitize_steps/form', locals: {@process_step => @process_step}) %>").show();
# /app/views/process_steps/form.js.erb
...
<div class="form-group">
<%= f.label :step_type, "Step Type", class: "col-sm-3 control-label" %>
<div class="input-group m-b">
<div class="btn-group">
<%= link_to 'Digitize', digitize_path, id: "digitize", remote: true, class: "btn btn-success btn-outline mpc" %>
<%= link_to 'Subset', subset_map_path, id: "subset", remote: true, class: "btn btn-success btn-outline" %>
<%= link_to 'Dissolve', dissolve_path, id: "dissolve", remote: true, class: "btn btn-success btn-outline" %>
<%= link_to 'TransferPoly', transfer_poly_path, id: "transfer-poly", remote: true, class: "btn btn-success btn-outline" %>
<%= link_to 'CodeMatch', code_match_path, id: "code-match", remote: true, class: "btn btn-success btn-outline" %>
</div>
<br />
<div class="btn-group">
<%= link_to 'Harmonize', harmonize_path, id: "harmonize", remote: true, class: "btn btn-success btn-outline" %>
<%= link_to 'Regionalize', regionalize_path, id: "regionalize", remote: true, class: "btn btn-success btn-outline mpc" %>
<%= link_to 'Disaggregate', disaggregate_path, id: "disaggregate", remote: true, class: "btn btn-success btn-outline" %>
<%= link_to 'Verify', verify_path, id: "verify", remote: true, class: "btn btn-success btn-outline" %>
<%= link_to 'LSIB Align', lsib_align_path, id: "lsib-align", remote: true, class: "btn btn-success btn-outline" %>
</div>
</div>
</div>
<%= f.hidden_field :step_type_id, { id: "step-type" } %>
<div id="step-form">
<%= show_step_partial(@process_step) %>
</div>
...
# /config/routes.rb
...
resources :final_tpop_maps do
get 'new/disaggregate_form', to: 'disaggregate_steps#form', as: 'new_disaggregate_form'
get 'new/regionalize_form', to: 'regionalize_steps#form', as: 'new_regionalize_form'
get 'new/harmonize_form', to: 'harmonize_steps#form', as: 'new_harmonize_form'
get 'new/lsib_align_form', to: 'lsib_align_steps#form', as: 'new_lsib_align_form'
get 'new/verify_form', to: 'verify_steps#form', as: 'new_verify_form'
get 'new/code_match_form', to: 'code_match_steps#form', as: 'new_code_match_form'
get 'new/transfer_poly_form', to: 'transfer_poly_steps#form', as: 'new_transfer_poly_form'
get 'new/dissolve_form', to: 'dissolve_steps#form', as: 'new_dissolve_form'
get 'new/subset_map_form', to: 'subset_map_steps#form', as: 'new_subset_map_form'
get 'new/digitize_form', to: 'digitize_steps#form', as: 'new_digitize_form'
get 'open_process', to: 'process_steps#open_process'
get 'complete_process', to: 'process_steps#complete_process'
resources :process_steps do
get 'disaggregate_form', to: 'disaggregate_steps#form'
get 'regionalize_form', to: 'regionalize_steps#form'
get 'harmonize_form', to: 'harmonize_steps#form'
get 'lsib_align_form', to: 'lsib_align_steps#form'
get 'verify_form', to: 'verify_steps#form'
get 'code_match_form', to: 'code_match_steps#form'
get 'transfer_poly_form', to: 'transfer_poly_steps#form'
get 'dissolve_form', to: 'dissolve_steps#form'
get 'subset_map_form', to: 'subset_map_steps#form'
get 'digitize_form', to: 'digitize_steps#form'
end
end
...
Continueing from my previous post on meta programing, to solve the issue of creating a complex nested form, I also utilized a Bootstrap button bar that triggered a nested AJAX partial.
1. To set this up, I created routes to wire-up to the buttons.
/config/routes.rb
[code]
I needed separate routes for the AJAX calls on the new and the edit forms. By nesting the edit form routes inside process_steps, I made the process_step id available, and thus made it possible to pass in the process_step object, which contains a reference to the type of step that should be nested in the form.
These separate sets of routes did not require separate methods in the controllers though. Each of the 10 step types only needed a `form` 'get' method in the controller. I also have to add `responds_to :js` at the top of the file to tell Rails I want my methods to also respond to javascript. For example:
/app/controllers/digitize_steps_controller.rb
[code]
Next I needed to load up some javascript into a view that corresponded to my controller methods. Again, using digitize_step as the example, this is a bit of javascript that will nest my digitize_step form into my process_step form.
/app/views/digitize_steps/form.js.erb
[code]
The important part of the process_steps form
/app/views/process_steps/form.js.erb
[code]
The `show_partial()` method is a helper method that, when the editing a process_step with already associated step_type, renders the correct nested form. I also pass in the `@process_step` object. Here is the helper method.
/app/helpers/process_steps_helper.rb
[code]
We're almost there. Finally, the step type forms used `fields_for` and the `@process_step` object.
/app/views/digitize_steps/_form.html.erb
[code]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment