Convert submit button to link

I have recently needed to replace the submit buttons on my forms with clickable links instead. I wanted the replacement to be completely compatible with my existing PHP server-side code. This means that where I checked for a button having been pressed on the server side, the same check would continue to work, and the same form elements would have been submitted.

Stripping away issues of screen formatting, I changed my button code generator to produce this

    <a  href="javascript:submitMe('buttonName');">buttonLabel</a>

instead of this

<input type="submit" name="buttonName" value="buttonLabel">

and in javascript I wrote this function


function submitMe(val)
{
    // create a form element that will show up in $_POST with the same
    // name as the old submit button
    simButton = document.createElement('INPUT');
    // note: creating the element within the form leaves that element
    // unrecognized by the submit() function for some browsers.
    // it is apparently necessary to create it at the document level then
    // append it
    simButton.type = 'hidden';
    simButton.setAttribute('Name',val);
    simButton.value ="simulated button";
    document.theForm.appendChild(simButton);
    if(isIE) // true if IE is browser. required for IE
    {
        document.theForm.innerHTML=document.theForm.innerHTML;
    }
    document.theForm.submit();
}

I have three questions:

  1. Does anyone know why the IE kludge is necessary?
  2. In my tests, on IE if a form element has the type “password”,
    the element, but not its contents, will be submitted.
    Does anyone else know of this and is there a fix? (I already
    have a workaround, but it’s very inelegant!)
  3. Are there obvious improvements that can be made to what I’ve done?

Hi jrisken,

I am not sure I am answering your question correctly but would it be better to use css to convert a submit button to a link. Please look at the code below

<html>
<style>
#buttonId{
background-color:transparent;
border-width:0;
cursor:default;
color:blue;
text-decoration: underline;
}
</style>
<body>

<form action=“form_action.asp”>
First name: <input type=“text” name=“FirstName” value=“Mickey” /><br />
Last name: <input type=“text” name=“LastName” value=“Mouse” /><br />
<input id=“buttonId” type=“submit” value=“Submit” />
</form>

<p>Click the “Submit” button and the input will be sent to a page on the server called “form_action.asp”.</p>

</body>
</html>

If this does not help you would it be possible for you to please rephrase your issue in some other words.

Yes. Well I already have a working application that uses submit buttons in the manner you describe. And I also have CSS that can make a link and a submit button look identical (but not shown in the example).

The issue is that when you click on a link and are taken to the server, none of the form elements are taken with you - only the things you have put in the href field.

There are valid styling reasons for simulating a submit button - mostly relating to shortcomings in IE; and the bit of code I posted makes it possible for the link to force submission of the form data in the same way that the submit button itself does. I put it up for people to look at because I had not been able to solve the problem in regard to POSTing passwords and I though someone might have inspiration or experience.

Hi jrisken,

I am a bit confused with this line

The issue is that when you click on a link and are taken to the server, none of the form elements are taken with you - only the things you have put in the href field.

I dont see any href in the sample that I pasted. Also the sample was basically a modification of the <input> tag expalination in w3schools.com. So I went there to test out what you said but the submit link seems to work just fine, it seems to be taking values from the from. Please take a look at the video in the link below.

http://www.screencast.com/t/MTJjYjY2OW

Please let me know what I am missing.

Well, in my posting there are three snippets of code - a submit-button snippet, a link-snippet and a javascript snippet.

The submiti button works fine. The link works fine for submitting the form - except for the password field in IE.

There’s a test at atest.usnpo.org/submittest/test.php if you’re interested. And here’s the code:


<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
<title>Substitute link for submit</title>
	<script language="javascript">	
		var isIE = document.all ? true : false; // additional check needed for decoding event logic
		function submitMe(val)
		{
			simButton = document.createElement('INPUT');
			simButton.type = 'hidden';
			simButton.setAttribute('Name',val);
			simButton.value ="simulated button";
			document.theForm.appendChild(simButton);	
			if(isIE)
			{
				document.theForm.innerHTML=document.theForm.innerHTML; // required for IE
			}
			document.theForm.submit();
		}
	</script>		
</head>
<body>
<?
	extract($_REQUEST);
	print "name contains '$theName' and password contains '$thePassword' and button name contains '$theButton'<br>";
?>
<form name='theForm'>
<input type="text" name="theName" value="abc"/>
<br />
<input type="password" name="thePassword" value="def"/>
<br />
<input type="submit" name="theButton" value="click me" />
<br />
<a href="javascript:submitMe('theButton');return(false);">No, no! click Me!</a>
</form>
</body>
</html>

Hi jrisken,

Thank you the sample. I guess my question now would be why are you going through the trouble of trying to make a link behave like a ‘submit button’ when you can achieve the same result by having a ‘submit button’ behave like a link. Please look at the code below.

<!DOCTYPE html PUBLIC “-//W3C//DTD XHTML 1.0 Transitional//EN” “http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd”>
<html xmlns=“http://www.w3.org/1999/xhtml”>
<head>
<meta http-equiv=“Content-Type” content=“text/html; charset=iso-8859-1” />
<title>Substitute link for submit</title>
<!–<script language=“javascript”>
var isIE = document.all ? true : false; // additional check needed for decoding event logic
function submitMe(val)
{
simButton = document.createElement(‘INPUT’);
simButton.type = ‘hidden’;
simButton.setAttribute(‘Name’,val);
simButton.value =“simulated button”;
document.theForm.appendChild(simButton);
if(isIE)
{
document.theForm.innerHTML=document.theForm.innerHTML; // required for IE
}
document.theForm.submit();
}
</script>–>
<style>
#buttonId{
background-color:transparent;
border-width:0;
cursor:default;
color:blue;
text-decoration: underline;
}
</style>
</head>
<body>
<?
extract($_REQUEST);
print “name contains ‘$theName’ and password contains ‘$thePassword’ and button name contains ‘$theButton’<br>”;
?>
<form name=‘theForm’>
<input type=“text” name=“theName” value=“abc”/>
<br />
<input type=“password” name=“thePassword” value=“def”/>
<br />
<input type=“submit” name=“theButton” value=“click me” />
<br />
<input id=“buttonId” type=“submit” name=“theButton” value=“No, no! click Me!” />
<br />
<!–<a href=“java_script:submitMe(‘theButton’);return(false);”>No, no! click Me!</a>–>
</form>
</body>
</html>

I am still not sure what I am missing and I can’t really think of anything else.

What you’re missing is that there are problems with IE’s visual formatting of buttons in general. I have some forms in which the button’s ‘value’ - that is, the name it displays on the screen, is rather long. The buttons are on the right edge of the form, and the form pretty much fills the available width of the screen.

With Firefox, Chrome, Safari, etc. the buttons take up exactly as much room as you allow them. With IE, the buttons want to have extra space around the button text, and the longer the legend, the wider the space.

You can overcome this problem with “overflow:hidden”. But that ‘hidden’ space then pushes the right edge of the form as far to the right as though the button were visibly wide.

div’s don’t have that problem. And I can wrap a div around a link and format it to look exactly like a button. The result is much greater consistency in a crowded form across browsers

Hi jrisken,

I am sorry I dont know how to help you. This is as close as I got

<!DOCTYPE html PUBLIC “-//W3C//DTD XHTML 1.0 Transitional//EN” “http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd”>
<html xmlns=“http://www.w3.org/1999/xhtml”>
<head>
<meta http-equiv=“Content-Type” content=“text/html; charset=iso-8859-1” />
<title>Substitute link for submit</title>
<script language=“javascript”>
function buttonClick(){
document.theForm.submit();
}
</script>
</head>
<body>
<?
extract($_REQUEST);
print “name contains ‘$theName’ and password contains ‘$thePassword’ and button name contains ‘$theButton’<br>”;
?>
<form name=‘theForm’>
<input type=“text” name=“theName” value=“abc”/>
<br />
<input type=“password” name=“thePassword” value=“def”/>
<br />
<input type=“submit” name=“theButton” value=“click me” />
<br />
<!–<a href=“java_script:submitMe(‘theButton’);return(false);”>No, no! click Me!</a>–>
<div onclick=“buttonClick()”>No, no! click Me!</div>
</form>
</body>
</html>

This seems work great if you mouse click on the text “No, No!click me”. However since there is no <a> tag you cant tab or use keyboard to get it to work.

Thanks! It had not occurred to me to just do a div.

FWIW, in another forum another helpful user posted a better way to add the name of the entity being clicked to the submit() package. Both methods are workarounds, but his method was better and it preserved the password field, ir present, which mine did not. It will work either with my link

<a href=“javascript:submitMe(‘buttonName’);”>buttonLabel</a>

or with your div

<div onclick=“submitMe(‘buttonName’);”>buttonLabel</div>

Here it is:


function submitMe(val)
{
    simButton = hidden(val);
    document.theForm.appendChild(simButton);
    document.theForm.submit();
}
function hidden(val)
{
	var elm = null;
	try {
		elm=document.createElement('<input type="hidden" name="'+val+'" value="simulated button">');
		}
	catch(e) {
		elm = document.createElement('input');
		elm.setAttribute('type', 'hidden');
		elm.name=val;
		elm.value='simulated button';
		}
	return elm;
}

Thanks jrisken

It is always good learn something new especially since I am quite new to all this.

Fang’s solution seems to work well, but it exposes a different problem:

Calling document.theForm.submit() does submit the form, but if there was “onsubmit=foobar()” in the form’s definition, foobar() is not executed. (I don’t know why and I don’t care except in the most abstract sense.

The solution is to create two elements instead of one. The first element contains the name of the button being replaced. But the second element is an actual submit button called simB. And at the end we execute document.theForm.simB.click(). This method causes the onsubmit associated with the form to be executed.

Here’s the new code:


function submitMe(theName)
{
	// create a form element with the same name as the submit button it replaces
    simButton = addElem(theName,'hidden');
    document.theForm.appendChild(simButton);
    // then create a real submit subbton ...
    simButton=addElem("simB",'submit');
    document.theForm.appendChild(simButton);
    // ...which we will click
    document.theForm.simB.click();
    // because the following line does not necesarily execute an 'onbumit' associated with the containing form
   // document.a.submit();
}
function addElem(theName,btype)
{
	var elm = null;
	try {
	    // for IE
	    elm=document.createElement('<input type="'+btype+'" name="'+theName+'" value="simulated button" style="display:none">');
	}
	catch(e) {
	    // for everybody else
	    elm = document.createElement('input');
	    elm.setAttribute('type', btype);
	    elm.setAttribute('style','display:none');
	    elm.name=theName;
	    elm.value='simulated button';
	}
	return elm;
}