In a Ruby on Rails app, say I have an Item and an Order model as follows:
class Item
:name
:default_price
end
class Order
:customer
:item_id
:order_price
end
On an Order form, I can automatically populate the order_price field with the default_price using javascript and a json call as follows:
$(function (){
$('#order_item_id').live("change", function(e) {
e.preventDefault();
$.ajax({
url: "/items/" + $(this).val(),
dataType: "json",
contentType: "application/json; charset=utf-8",
success: function(data) {
$('#order_price').val(data.item.default_price);
},
error: function(xhr,exception,status) {
//errors....
}
});
});
});
So far, so good. But now suppose I want to be able to list multiple items under a single order. In that case I could use a nested form and the following tables:
class Item
:name
:default_price
end
class Order
:customer
end
class OrderItem
:order_id
:item_id
:order_price
end
The problem is that each nested OrderItem record has the same select ID, and a random order_price ID, eg:
<div class="fields">
<ol>
<li> //first nested record
<select id="order_item_id"></select>
<input id="order_orderitems_attributes_0_orderprice"></input>
</li>
<li> //second nested record
<select id="order_item_id"></select>
<input id="order_orderitems_attributes_###randomnumber###_orderprice"></input>
</li>
</ol>
</div>
Clearly this causes problems for the javascript function.
How can I get my nested forms to play nicely with my javascript, so that selecting an item populates the corresponding price field?
I will need to pass an identifier for the nested record into the function so that the function runs when the select field is changed. I will also need to somehow identify the correct order-price field.
Anyone have any ideas?
Thanks!!!
EDIT
Actually, I can get this working by using the .next() selector to find the next DOM element. i.e., in the js function
$('#order_item_id').live("change", function(e) {
var current_price = $(this).next('.order-price')[0];
.....
success: function(data) {
$('current_price').val(data.item.default_price);
},
.....
but I’m feeling uncomfortable that each select field has the same ID. Is this something I should be concerned about? Are there any issues I should be thinking about?
EDIT 2
order form
<%= nested_form_for @order do |f| %>
.....order fields
<ol>
<%= f.fields_for :orderitems %>
</ol>
<p><%= f.link_to_add new_ico, :orderitems %></p>
<p><%= f.submit %></p>
<% end %>
orderitems partial
<li>
<%= select(:orderitem,:item_id,@items.collect{|s|[s.name, s.id]},:prompt=>"select") %>
<%= f.text_field :order_price, :class => "order-price" %>
</li>
So you want changing the selected item for a
selectupdate the input right after it, right? If so, you can change yoursuccesshandler to something like this:In order to make it more explicit that the input contains a specific value such as the order price, you can assign an HTML 5
data-attribute to it like this:This way the CSS selector in your JavaScript would become a little bit more intuitive:
Worth mentioning that the
data-attributes work even in HTML 4 if you are using a recent version of jQuery.