javascriptruby-on-railsruby-on-rails-4ruby-on-rails-5cocoon-gem

execute javascript function after adding fields with cocoon


I'm developing my application in rails, in my app I'm extracting a form in a modal window through ajax, the form has a cocoon button to add nested records, the problem comes when adding new nested resources with cocoon those new fields do not respond to a javascript function that detects if the field changed the value

my application.js

function validateFileType(){
  $( ".file_to_upload" ).change(function() {
    alert( "Handler for .change() called." );
  });
}

part of my index.haml.erb:

  =link_to '<i class="fa fa-picture-o"></i>'.html_safe, adjuntar_archivos_path(:id => record), :remote => true

#adjuntar_archivos

my method in controller

  def adjuntar_archivos
    @billing = Billing.find_by_id(:id)
  end

my adjuntar_archivos.js.erb

$("#adjuntar_archivos").html("<%=j render :partial => 'adjuntar_archivos'%>");

$("#addDataModelModal").modal("show"); 

validateFileType();

my partial _adjuntar_archivos.html.haml

#addDataModelModal.modal.fade{"aria-hidden" => "true", "aria-labelledby" => "exampleModalLabel", role: "dialog", tabindex: "-1"}
  .modal-lg.modal-dialog{role: "document"}
    .modal-content
      = form_for(@billing, remote: true) do |f|
        .modal-header
          %h5#addDataModelModalLabel.modal-title Archivos adjuntos
          %button.close{"aria-label" => "Close", "data-dismiss" => "modal", type: "button"}
            %span{"aria-hidden" => "true"} ×
        .modal-body
          .links
            = link_to_add_association "<i class='fa fa-plus'></i> Añadir adjunto".html_safe, f, :billing_files, partial: 'billing_file_fields',:"data-association-insertion-node" => "tbody.adjuntos",:"data-association-insertion-method" => "prepend", class:"btn btn-success btn_naranja btn", id: "link_1"

          .row
            .col-md-12
              #payment_details
                %table.tabla_personalizada#tabla_detalle_pago
                  %thead
                    %tr
                      %th Descripción

                  %tbody.adjuntos
                    = f.fields_for :billing_files do |billing_file|
                      = render 'billing_file_fields', f: billing_file


        .modal-footer
          %button.btn.btn-secondary{"data-dismiss" => "modal", type: "button"} Close
          .text-center
            = f.submit 'Guardar', :class => 'pull-right btn btn-primary'

my partial _billing_file_fields.html.haml

%tr.nested-fields.detalle_pago
  %td= f.text_field :description, class: 'form-control file_to_upload'

how can i make the new fields created by cocoon also run the .change method of my javascript function?

UPDATE:

I have tried to execute the function within the partial "billing_file_fields.html.haml" in the following way:

%tr.nested-fields.detalle_pago
  %td= f.text_field :description, class: 'form-control file_to_upload'

- content_for :javascript do
  :javascript


    validateFileType();

but it still doesn't work


Solution

  • Try changing


        function validateFileType(){
            $( ".file_to_upload" ).change(function() {
                alert( "Handler for .change() called." );
            });
        }
    

    To


        function validateFileType(){
            $(document).on('change', ".file_to_upload" ).change(function() {
                alert( "Handler for .change() called." );
            });
        }
    

    The code will make sure that any element (even if the element is dynamically added) will have the given callback on change.

    NOTE: PLEASE MAKE SURE THAT THIS FUNCTION IS CALLED ONLY ONCE SO CONSIDER CALLING THIS FUNCTION IN index.haml.erb.