Javascript function to change input on forms


#1

I got the the input but I was wondering if I have to write a function for each input element or is there easy or more effective way to this in Javascript.

<html>
	<head>
				
	</head>
	<body>
		<br />
		<h3>Fun With the Form</h3>
		<p>Enter your information in the boxes. After you are satisfied with each entry, press the OK 
		button to see the information displayed below. Use the TAB key to move from box to box and don't
		be surprised by where the TABs take you.</p>
		
		<form id="myForm">
			<div style="width: 33%; float: left;">
				<fieldset>
					<label>First name:</label><br />
					<input type="text" name="firstname" id="firstname" size = "30" value = "" tabindex = "1" onfocus ="txt_onfocus(this)" onchange="txt_onchange(this)"/>
					<input type ="button" value = "ok" id="button1"/></button><br />
					<br />
				</fieldset>
			</div>
			
			<div style="width: 33%; float: left;">
				<fieldset>
					<label>Dream car:</label><br />
					<input type="text" name="car" id="car" size = "30" value = ""  tabindex = "4"/>
					<input type ="button" value = "ok" id="button2"/> </button><br /><br />
				</fieldset>
			</div>
			
			<div style="width: 33%; float: left;">
				<fieldset>
					<label>Dream Vacation:</label><br />
					<input type="text" name="vacation" id="vacation" size = "30" value = "" tabindex = "6"/>
					<input type ="button" value = "ok" id="button3"/></button><br /><br />
				</fieldset>
			</div>
			
			<div style="width: 33%; float: left;">
				<fieldset>
					<label>Nickname:</label><br />
					<input type="text" name="nickname" id="nickname" size = "30" value = "" tabindex = "3"/>
					<input type ="button" value = "ok" id="button4"/></button><br /><br />
				</fieldset>
			</div>
			
			<div style="width: 33%; float: left;">
				<fieldset>
					<label>Favorite meal:</label><br />
					<input type="text" name="meal" id="meal" size = "30" value = "" tabindex = "5"/>
					<input type ="button" value = "ok" id="button5"/></button><br /><br />
				</fieldset>
			</div>
			
			<div style="width: 33%; float: left;">
				<fieldset>
					<label>Last name:</label><br />
					<input type="text" name="lastname" id="lastname" size = "30" value = "" tabindex = "2"/>
					<input type ="button" value = "ok" id="button6"/></button><br /><br />
				</fieldset>
			</div>
			
			<div>
				<h3>Your information:</h3>
				<p>First name: <span id = "first_name">&nbsp;</span><br /></p>
				<p>Last name: <span id = "last_name">&nbsp;</span><br /></p>
				<p>Nickname: <span id = "nick_name">&nbsp;</span><br /></p>
				<p>Dream car: <span id = "dream_car">&nbsp;</span><br /></p>
				<p>Favorite meal: <span id = "favorite_meal">&nbsp;</span><br /></p>
				<p>Vacation desired: <span id = "vacation_spot">&nbsp;</span><br /></p>
			</div>
		</form>
		<script type="text/javascript" src="script.js"></script>
	</body>
</html>

SCRIPT FILE:

function txt_onfocus(txt) {

      txt.style.backgroundColor = "pink";
}

function txt_onchange(txt)
{
document.getElementById('first_name').innerHTML=txt.value;
}

Thanks for any imput.


#2

There’s a couple of ways to do this, some of which depends on what you’re trying to do and what’s supported. Its a little tricky because not all events are created equal in the HTML DOM. In fact you’re using 2 events that demonstrate that very thing, so we can use both approaches to solve your problem.

First off is using event bubbling with event delegation. Bubbling is the behavior of events as they start at one element but propagate and are able to be recognized through the parent hierarchy of that element. For example, if you have a button in a paragraph element, clicking on that button will also cause a click event handler on the paragraph to trigger. What’s nice about this is that if you have 3 buttons in your 1 paragraph, clicking any one of those 3 buttons will trigger the same, single event handler on the paragraph effectively giving you 3 event handlers for the price of one. This - and the act of making sure a button is clicked and not something else in the paragraph that you may not care about - is event delegation.

The problem with this is that not all events bubble. For example, in your code, you’re using onfocus and onchange. The change event bubbles, but focus does not. But we can at least handle the change event now with some event delegation. This simply means moving the onchange from the input up into the <form> element which is a common parent of all your inputs. Then that handler can be used to recognize a change in any form.

<form id="myForm" onchange="txt_onchange(this)">

We do need to make one change first, and that is changing the this being used. On the <form>, this is the form element and not an input. The event object we get in event handlers however lets us know which element was the original target of the event - which input was changed. That is referenced through event.target. Don’t confuse this with event.currentTarget which, in this case, is the form element. target is the original element that triggered the event, currentTarget is the element that is handling the event (the element with the event handler attached to it).

<form id="myForm" onchange="txt_onchange(event.target)">

For the focus event, because it doesn’t bubble, we can’t take the same approach. We can, however, simplify things by adding the event handlers programmatically through JavaScript. This means querying the DOM for the elements we want to apply the handler to, looping through them, and attaching them in code rather than HTML. We can identify the inputs using:

var inputs = document.querySelectorAll('#myForm input[type="text"]');

And using the forEach function, loop through each of them and add a handler, not unlike how it was defined in HTML:

inputs.forEach(function(input) {

  input.onfocus = function () {
  	txt_onfocus(this);
  };
  
});

Note that it is more common for people to use addEventListener to attach events through JavaScript, but for now, this is fine.

This is a little more work, but still a lot easier than adding all the event handlers yourself in the HTML. Plus this will automatically work for however many inputs you add to your document as long as they match the selector used in querySelectorAll.

One more thing to add: back in the onchange there was more work to do that was skipped over. While we covered how to handle the events, there’s till the problem of making sure that in the txt_onchange handler, that the right text was getting updated. We’re targeting the input correctly using event.target, but that doesn’t help us know where the value of that input is to be set. My suggestion - and there are different ways to approach this, but all effectively doing more or less the same thing - is to make the association from input to destination text through a naming convention. For example, the input named “firstname” can have its value given to the span with a name just like that, but slightly different (ids, what I’m referring to as “names” here, need to be unique) - something like “firstname-txt”. Then, in txt_onchange, we can get the target id using the id of the input. For example:

<p>First name: <span id="firstname-txt">&nbsp;</span>

would be the new HTML (changed for each span), and the updated handler function would be:

function txt_onchange(txt) {
  document.getElementById(txt.id + '-txt').innerHTML = txt.value;
}

Here is a fiddle of the finished, working version: https://jsfiddle.net/n347gu4b/


Also, @Ruth_Harris_Shumate, I’ve been editing your posts so far, but when you’re posting code, be sure to format it, either using the “Preformatted text” option in the forum editor toolbar, by indenting it 4 spaces, or surrounding your code with 3 ticks

```
like this
```

This is especially important with HTML because the forum may hide or try to parse your HTML as forum content. :slight_smile:

On top of I wanted to point out that you have a few errant </button> tags in your HTML as well. I removed them in the fiddle link. :wink:


#3

Wow! :thinking: I was so proud of myself to the little piece of code I did. I have never worked with forms in any programming language. Of course I haven’t programmed in 25 or so years. I am a librarian who does the web design for our libraries and thought learning Javascript would be benefit my design.
Thanks, you have given me lots to ponder on. Thanks for explaining how to post my code. I was a little confused by the directions.
Thanks again.


#4

You’re doing great! There’s a lot to learn. Expect to be confused (both with JavaScript and how the forums work) :wink: