Avi Kaminetzky
Avi Kaminetzky

Reputation: 1538

Persist jQuery On Submission Failure - Rails

In the form I created, when a user selects "Member type" from a dropdown menu, specific div's are displayed in accordance with that member type using jQuery. For example, selecting "Youth Member" will display input fields for "DOB" and "Hour".

The problem I've been experiencing is that on a failed form submission, the member dropdown menu will retain the selected member type (just as all form fields are pre-populated with the users failed input) while failing to display the associated div's (unless another member type is selected).

My assumption is that I might be able to pre-populate the rendered form (render 'new') form with no selection for member type. However, this approach sounds very messy.

Any help would be appreciated.

New form view:

<% provide(:title, 'Create form') %>
<h1>Create a new form</h1>
<div class="col-md-12">
    <%= simple_form_for(@form, html: { class: 'form-horizontal' }) do |f| %>

      <%= render 'shared/error_messages' %>

      <%= f.input :first_name, error: false %>
      <%= f.input :last_name, error: false %>
      <%= f.input :email, error: false %>
      <%= f.input :phone, error: false %>
      <%= f.input :address, error: false %>
      <%= f.input :member_type, collection: Form::MEMBERSHIPS, include_blank: true, error: false %>

      <div id="children">
        <%= f.input :children, collection: Form::CHILDREN, error: false, include_blank: true %>
      </div>

      <div id="kollel">
        <p>Please provide proof of Kollel Attendence</p>
        <%= f.input :date, start_year: Time.now.year - 5, end_year: Time.now.year, label: "Please enter date began Kollel", error: false, include_blank: true %>
      </div>

      <div id="youth">
        <p>For 16 years old and younger; please provide valid ID</p>
        <%= f.input :dob, start_year: Time.now.year - 17, end_year: Time.now.year, label: "Please enter DOB", error: false, include_blank: true %>
      </div>

      <div id="hour">
        <%= f.input :hour, collection: Form::HOURS, error: false, include_blank: true %>
      </div>

      <%= render 'layouts/signature' %>
      </br></br>
      <%= f.hidden_field :base64 %>

      <p>FOR OFFICE USE ONLY:</p>

      <%= f.input :interaction, label: "Interaction type", collection: Form::INTERACTIONS, error: false %>

      <div id="new">
        <%= f.input :new_tag, error: false %>
        <%= f.input :deposit, label: "Cash deposit", error: false %>
        <%= f.input :notes, error: false %>
      </div>

      <div id="exchange">
        <%= f.input :new_tag, error: false %>
        <%= f.input :returned_tag, error: false %>
        <%= f.input :notes, error: false %>
      </div>

      <div id="refund">
        <%= f.input :returned_tag, error: false %>
        <%= f.input :deposit, label: "Cash refund", error: false %>
        <%= f.input :notes, error: false %>
      </div>

      <%= f.submit "Create form", class: "btn btn-primary", id: "save-form" %>
    <% end %>
</div>

jQuery code:

$('#kollel, #youth, #hour, #children').hide();

    $("#form_member_type").change(function() {
      var selected = $('#form_member_type').find(":selected").val();
      if (selected == "Kollel discount: $35") {
        $('#children, #youth').hide();
        $('#kollel, #hour').show();
      } else if (selected == "Youth member: $35") {
        $('#kollel, #children').hide();
        $('#youth, #hour').show();
      } else if (selected == "Monthly with children (Friday's): $55 + $16 per child") {
        $('#kollel, #youth, #hour').hide();
        $('#children').show();
      } else {
        $('#kollel, #youth, #hour, #children').hide();
      }
    });

    $('#new, #exchange, #refund').hide();

    $('#form_interaction').change(function() {
      var selected = $('#form_interaction').find(':selected').val();
      if (selected == "NEW") {
        $('#exchange, #refund').hide();
        $('#new').show();
      } else if (selected == "EXCHANGE") {
        $('#new, #refund').hide();
        $('#exchange').show();
      } else if (selected == "REFUND") {
        $('#new, #exchange').hide();
        $('#refund').show();
      }
    });

Form Controller:

class FormsController < ApplicationController
  before_action :logged_in_user
  before_action :admin_user, only: :destroy

  def index
    @forms = Form.paginate(page: params[:page], :per_page => 20)
  end

  def show
    @form = Form.find(params[:id])
    respond_to do |format|
      format.html
      format.pdf do
        render :pdf => @form.last_name + '_' + @form.first_name + '_' + @form.created_at.strftime("%d %b %Y"),
        :template => 'forms/show.pdf.erb',
        :show_as_html => params[:debug].present?
      end
    end
  end

  def new
    @form = Form.new
  end

  def create

    @form = Form.new(form_params)

    signature = Paperclip.io_adapters.for(params[:form][:base64])
    signature.original_filename = "signature.png"
    @form.signature = signature

    if @form.save
      flash[:success] = "The form has been successfully created!"
      redirect_to @form
    else
      render 'new'
    end
  end

  def edit
    @form = Form.find(params[:id])
  end

  def update
    @form = Form.find(params[:id])
    if @form.update_attributes(form_params)
      flash[:success] = "Form has been updated!"
      redirect_to @form
    else
      render 'edit'
    end
  end

  def destroy
    Form.find(params[:id]).destroy
    flash[:success] = "Form deleted"
    redirect_to forms_path
  end

  private

  def form_params
    params.require(:form).permit(:first_name, :last_name, :email, :phone, :address, :member_type, :date, :base64, :children, :hour, :interaction, :new_tag, :returned_tag, :deposit, :notes)
  end
end

Upvotes: 1

Views: 86

Answers (1)

YesItsMe
YesItsMe

Reputation: 1789

I am assuming the logic is since it's bound to change event that doesn't occur here it remains hidden

Maybe try Function that toggles the div according the selected input, and on change call the function.

Jquery execute onchange event on onload

Upvotes: 1

Related Questions