Tale of two submit buttons!
Two different action as per users’ preference, on the same data provided. For (dumb) example: User can choose to be greeted either in Spanish or in French.
User action vs Form data
Form data passed, to the form action, depends on the user interaction.
user action | form data passed |
---|---|
clicks on Hola button | name=Sarbbottam&greeting=Hola |
clicks on Bonjour button | name=Sarbbottam&greeting=Bonjour |
tabs to the Hola button and presses enter in the physical keyboard |
name=Sarbbottam&greeting=Hola |
tabs to the Bonjour button and presses enter in the physical keyboard |
name=Sarbbottam&greeting=Bonjour |
while being in the name field (editable fields), presses enter in the physical keyboard or Go in the soft keyboard* |
name=Sarbbottam&greeting=Hola |
</sup> *Pressing/tapping the enter/Go
button, triggers the click event on first submit button (the submit button that appears first in the DOM).
Form action handler, can rely on the value of greeting
parameter to take desired action.
Example - Two submit button
See the Pen greeting-no-js by Sarbbottam Bandyopadhyay (@sarbbottam) on CodePen.
Form action handler is relying on the value of the greeting
parameter(name of the submit button) to greet the user.
What problem might arise?
So far so good, but if the form submit action is trapped click event of the submit buttons is trapped and the form is submitted via JavaScript, the greeting
parameter will not be part of the form data.
However, if the form submit event is trapped and the form is submitted via JavaScript, the clicked button will be part of the serialized form data. Thanks to Adam Brunner for the pointer.
See the Pen greeting-js-buggy by Sarbbottam Bandyopadhyay (@sarbbottam) on CodePen.
Since the greeting
parameter is not present the form action handler behavior is buggy.
Proposed solution
Instead of listening to submit button click, listening to form submit resolves the issue. Sweet and simple.
But the whole idea of the previously proposed solution was to detect which submit button was clicked.
The submit button clicked can be detected with document.activeElement
.
See the Pen greeting-js-proper by Sarbbottam Bandyopadhyay (@sarbbottam) on CodePen.
(Previously) Proposed solution (not optimal)
Using a hidden input
to track the user action (the button clicked).
Before the form is submitted via JavaScript, the name and value of the proxy-submit-button
is updated.
See the Pen greeting-js-proper by Sarbbottam Bandyopadhyay (@sarbbottam) on CodePen.
If for any reason JavaScript is not executed, the proxy-submit-button
element will not be passed to the form action as it does not have any name and greeting
parameter will always be passed to the form action.
If JavaScript is functional, then proxy-submit-button
will be named as greeting
and its value will be updated to the value of the submit button clicked*. Thus at a time only one parameter named greeting
will be passed to the form action.
</sup> *Pressing/tapping the enter/Go
button, triggers the click event on first submit button (the submit button that appears first in the DOM).
Wrap up
Technically, the proposed solution holds good for any number of submit buttons but more than two submit button might not be a desired user experience.
Thanks to Chris Coyier for the mention, Adam Brunner for the suggestion and internet for its feedback.
@chriscoyier @sarbbottam Why wouldn't you just use a form submit event instead of a click handler? http://t.co/IhGCmxUvo2
— Adam Brunner (@clcpolevaulter) November 5, 2014
If you have enjoyed reading this post you can follow me on twitter @sarbbottam and learn about any new posts. Opinions expressed are solely my own and do not express the views or opinions of my employer.