Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

onchange display/change a partial

There is a drop down using select

<%= select("array", "folder", @rows.keys, {}, :onchange =>"?" )%>

There is a partial called "form"

<%= render "form"%>

I need to render the partial whenever there is a change in the selection. Please, let me know if there is a way to do it. I found that the remote_function is deprecated from rails 3.0. I have seen all possible links here with onchange and select tags but could not find a proper answer. I'm new to rails, jQuery and Ajax. Please help

Thanks

like image 434
user1455116 Avatar asked Dec 08 '22 23:12

user1455116


2 Answers

There is definitely a way to do this, and it's a bit of work, but it's quite easy once you get the hang of it.

First, you'll want to attach a jQuery function to the change event of your select box. This can be done by adding some javascript to your application.js file. We want to do this here so our javscript remains unobtrustive. You can try something like this in your application.js file:

$(document).ready(function(){
  $("#select_field_id").change(function(){
    var id = $(this).children(":selected").val();
    var params = 'some_id=' + id;
    $.ajax({
      url: "/some_controller/change_folder",
      data: params
    })
});

What this does is attach an anonymous function to the change event of a select field with id select_field_id. When that field is changed, the id of the selected option gets stored in the var id, and then we create a parameter for the request we'll send by doing var params = 'some_id=' + id;. some_id would be the id of whatever you're changing (so a folder_id if that's what you're using in your example).

Now we need to create the method that will handle this request in our controller. So going with the folder example, add this to the folder controller:

def change_folder
  @folder = Folder.find(params[:some_id])
  respond_to do |format|
    format.js
  end
end

This simply finds a folder based on the id sent in by your ajax request to change_folder. It will also be looking for a corresponding change_folder.js.erb or change_folder.js file to render.

Now we need to write up a change_folder.js.erb file. We need to replace the HTML on some part of your page with the new folder we got, so you should have some kind of div or other section with a unique id.

Inside change_folder.js.erb, we can write this:

$('#your_div').html("<%= escape_javascript(render(partial: "folder", 
locals: { :folder => @folder })).html_safe %>")

This will render a partial called _folder.html.erb that is in the same directory as the change_folder.js.erb file. The partial will need to use an @folder variable for displaying the fields, so you would need something like:

<%= @folder.name %>
<%= @folder.last_updated %>

Inside your _folder.html.erb partial. .name and .last_updated are of course just made up properties of a Folder model. You'll have to use whatever properties you have given to your Folder model instead.

That should get you going to where you need to be. Please let me know if you need anything clarified.

like image 117
Zajn Avatar answered Dec 28 '22 01:12

Zajn


why not render the form in the same page and hide and show it on change of select tag

<html> 
  <body>

  <!-- Your Select tag -->
  <select id="select_id"> 
    <option value="one" selected> One </option>
    <option value="two"> Two </option>
  </select>

  <!-- Here your a div inside with your form is placed -->
  <div id="myform" style="display:none">
    <form action="/someurl">
      .. ..
    </form> 

   <!-- JQuery code to  show the form -->
  <script type="text/javascript">
    $(document).ready(function() {
       $("select#select_id").bind("change",function() {
         if ($(this).val() == "one") 
          $("div#myform").show(); 
         else
          $("div#myform").hide(); 
       })
   })

  </script>

</html>

I you still want to make an ajax request I pretty simple too

$(document).ready(function() {
  $("select#select_id").bind("change",function() {
    if ($(this).val() == "one") {
     $.ajax({
        url : "/form_url",
        data : "html", 
        type: "GET",
        success : function(data) {
          $("div#myform").html(data)
        }
     }) 

  })
})

on the server side you need to respond_to the ajax request using format.js and render a template directed using render command or just define a .js.erb file

like image 26
Viren Avatar answered Dec 28 '22 02:12

Viren