Reputation: 46667
I can't seem to get a :remote
form with multiple submit controls to work under Rails 3. The following code:
<%= form_tag({:action => 'debug'}, {:remote => true}) do %>
<%= submit_tag "Foo" %>
<%= submit_tag "Bar" %>
<% end %>
Produces a form with two buttons, but the resulting AJAX POST doesn't contain a commit
parameter to say which one was pressed. If I leave :remote => true
out, the normal POST does contain the commit
parameter.
Is there any way to make this work, or is it just a bug?
Upvotes: 3
Views: 2223
Reputation: 11
I tried your solution and it worked for Firefox, but then the application did not work any more for IE and Safari. Now I found another solution: Simply putting the value of the submit button into a hidden input field by a small javascript.
<input id="selected_button" type="hidden" name="commit" value=""/>
<script>
function identify_button( el ) {
window.document.getElementById( 'selected_button' ).value = el.value;
}
</script>
<input class="button"
type="submit"
name="commit"
value="Save"
onclick="identify_button( this )" );"
/>
<input class="button"
type="submit"
name="commit"
value="OK"
onclick="identify_button( this )" );"
/>
Upvotes: 1
Reputation: 46667
After some playing about, I think I've found a solution.
The problem is that rails.js
uses serializeArray()
on the form
element containing the clicked submit
control; but the form's serialized data doesn't contain that control. However, JQuery or Javascript is keeping track of the original event in the call-chain, which was technically a "submit" event on the appropriate control.
So I've edited rails.js as follows:
callRemote: function (e) { /* Note - new parameter e */
var el = this,
method = el.attr('method') || el.attr('data-method') || 'GET',
url = el.attr('action') || el.attr('href'),
dataType = el.attr('data-type') || 'script';
if (url === undefined) {
throw "No URL specified for remote call (action or href must be present).";
} else {
if (el.triggerAndReturn('ajax:before')) {
var data = el.is('form') ? el.serializeArray() : [];
/********************/
/* Note new if-test */
/********************/
if (e)
{
data.push({name: e.originalEvent.explicitOriginalTarget.name,
value: e.originalEvent.explicitOriginalTarget.value})
}
/* Function continues as before */
... and further down ...
$('form[data-remote]').live('submit', function (e) {
$(this).callRemote(e);
e.preventDefault();
});
This has the effect of adding in the name-value pair of the clicked button before firing off the AJAX.
I'm a bit new to Javascript, so do let me know if any of this is horrendously wrong!
Upvotes: 1