3 May 2011
This article assumes no prior knowledge of JavaScript. However, you should be familiar with the basics of building web pages with HTML and CSS.
Any text editor can be used to write JavaScript.
Beginning
JavaScript is one of the most important languages used in web development. It has many uses ranging from checking the values submitted by forms to controlling interactive widgets, such as tabbed panels, accordions, and flyout menus. It's also used to create photo galleries, and to fetch new information from the web server to refresh content without the need to reload the page—a combination of technologies commonly known as Ajax.
Along with HTML and CSS, knowledge of JavaScript is a key skill that anyone involved in building websites should acquire. Yet many web designers never do. JavaScript has a reputation for being too difficult; and graphic designers frequently insist that their role is to design, not to program. Even if you never do any JavaScript programming yourself, it's important to understand how the structure of your web pages affects the job of the JavaScript programmer. What's more, JavaScript has become easier to use thanks to code libraries such as jQuery.
This is the first in a series of articles designed to help you get started with JavaScript and jQuery. It describes the basic features of the language that you need to know before diving into jQuery.
In spite of the similarity of names, JavaScript is not Java. The languages are not related. Java is frequently used to program games, mobile phones, and other devices, such as the Amazon Kindle. Although Java can be used in websites, it's rarely used that way.
JavaScript, on the other hand, is a lightweight, yet powerful language that normally runs inside a web browser. Its role is to provide access to different elements of the page so that they can be removed or updated. It can also create new elements, change the style of existing elements, or extract information from them. For example, it can read the values entered into a form, perform a calculation, and display the result. It can also send a request to the web server for more information, and update part of the page without needing to reload it.
JavaScript performs these tasks by accessing the Document Object Model (DOM). The DOM is a structure similar to a family tree. If the HTML markup of your page is invalid or too complex, the JavaScript code can't navigate the family tree. Similarly, if you break simple rules, such as not using the same ID more than once in any page, JavaScript becomes confused and simply gives up.
JavaScript is an event-driven language. Some events are triggered automatically. For example the load event is triggered when the page finishes loading in the browser, and it's frequently used to initialize flyout menus and other widgets. Other events are triggered by the user, the most common being the click event when the user clicks the main mouse button, or taps on a touch-sensitive screen. Other common events include mouseover and mouseout, when the user hovers over an element, and submit, when a form is submitted.
Events are being triggered all the time. An event is triggered every time you move the mouse, scroll the page, or press a key. It would be chaos if the browser had to respond to every event. Instead, you as the developer, create functions to handle specific events, and you associate them with the page elements that you want to respond to the event. This is known as binding an event handler.
Event handler functions sit and wait—or listen—for the event. When the appropriate event is triggered, the event handler jumps into action and performs its designated task, such as opening or closing a flyout menu, submitting a form, or changing the style of an element.
Rather than talk in abstract terms, let's look at JavaScript in action.
As the name suggests, a function does something. It's a series of commands that performs whatever task (or tasks) you tell it to do. The most common way to define a function is to use the keyword function followed by the function name, a pair of parentheses, and a block of code wrapped in curly braces. You can give functions almost any name you like, but it must begin with a letter, underscore (_), or the dollar sign. Also, the name must not contain any spaces or hyphens. JavaScript is case-sensitive, so it's common to give functions descriptive names using an uppercase letter for the second and subsequent words ("camel case"); for example, changeFontSize.
To keep the code as simple as possible, the following example just changes the text color of an unordered list. You can find the finished code in change_01.html in the example files, but to give yourself a feel for writing JavaScript, I recommend that you open Dreamweaver (or any other text editor) and type the code yourself.
<h1> heading, an unordered list, and a paragraph (see Figure 1). The unordered list has the ID fruits.
</head> tag, and add a <script> tag. The page has an HTML5 DOCTYPE, so you don't need to add type="text/javascript". Browsers automatically assume that the code inside a <script> block is JavaScript.<script> block. So, leave a blank line, and then type </script>.Note that Dreamweaver doesn't autocomplete the tag when you type </.You need to complete it manually. This is because the same combination of characters might occur in the script.
<script> block, enter the following code:function changeFontSize() {
}
This defines a function called changeFontSize(). You often pass information as arguments to a JavaScript function. The arguments go between the parentheses after the function name. This function doesn't take any arguments, but the parentheses must still be used. The body of the function goes between the curly braces. You'll add that next.
getElementById(). Press Enter/Return to insert the code.getElementById() expects an ID as its argument. Type a quotation mark (single or double, it doesn't matter). If you're using Dreamweaver CS5.5, it automatically presents you with a list of IDs on the current page (see Figure 3).
fruits ID. Then type a closing parenthesis followed by a semicolon. If you're using another program, you need to complete the code manually. In either case, you should now have the following code in your function definition:
function changeFontSize() {
var list = document.getElementById('fruits');
}
The line of code you have just typed uses the keyword var to create a variable called list, which stores a reference to the page element with the ID fruits. The reference to fruits is obtained by a JavaScript method called document.getElementById().
Note: Methods are essentially the same as functions, except that they belong to objects. You'll learn about objects later. Don't let the terminology confuse you. If it helps, just think of a method as being a special type of function.
list.style.fontSize = '20px';
If you're using a recent version of Dreamweaver, you'll have noticed code hints popping up each time you typed a period. What this line of code does is change the size of the text in the list element—in other words, the unordered list with the ID fruits.
You probably recognize fontSize as similar to the CSS font-size property. JavaScript doesn't allow hyphens in names. So, the hyphen is removed and the word after the hyphen is capitalized.
The complete function definition should now look like this:
function changeFontSize() {
var list = document.getElementById('fruits');
list.style.fontSize = '20px';
}
If you have experience with other programming languages, most of this section should be familiar. But for the benefit of complete beginners, I'll explain the basic terminology. At first, it might seem like jargon overload, but it will make the rest of this tutorial easier to follow.
The first line inside the changeFontSize() function definition creates a variable called list. Variables are an important part of all programming languages. A variable usually stores a value that you don't necessarily know in advance. The name of the variable remains the same, but its value might change. To take an example from everyday life, your bank balance is similar to a variable. The amount changes frequently, but the name "balance" always remains the same.
When defining a variable inside a function, you should always use the var keyword. Doing so tells the JavaScript engine that you want the variable to be used only inside the function. Omitting var can produce unpredictable results in more complex scripts.
The same rules apply to variable names as to functions, namely:
The value is assigned to the variable using an equal sign. The value on the right of the equal sign is assigned to the variable on the left.
The first line in the changeFontSize() function uses document.getElementById('fruits') to assign the variable a reference to the fruits unordered list. This introduces you to three important features of JavaScript—objects, dot notation, and passing arguments to a function.
In simple terms, an object is a variable that contains zero or more other values known as properties and methods. A property is similar to variable, and a method is essentially the same as a function. You access the properties and methods of an object using dot notation. The object comes first, followed by a dot or period, and then by the property or method. In this case, getElementById() is a method of the document object.
To name of getElementById() is self-explanatory: it gets a reference to an element using the element's ID. You put the ID in quotes between the parentheses after the method's name. This is known as passing an argument. Because the argument is in quotes, JavaScript treats it as literal text. In programming terms, literal text is known as a string (because it's a string of characters). It doesn't matter whether you use single or double quotes for strings, but the quotes must match.
The second line in the changeFontSize() function takes dot notation a step further. It accesses the style object of the element stored in the list variable, and then accesses its fontSize property like this: list.style.fontSize. The value assigned is a string containing the new size. In other words, the second line sets the CSS font-size property of the fruits list to 20px.
There's one final point to notice. Each command ends with a semicolon. Technically speaking, the semicolon is optional, because JavaScript automatically treats the end of a line that contains a command as the end of the command. If you accidentally break a line of code, JavaScript treats it as a complete command, causing your script to fail. Always ending commands with a semicolon makes errors easier to find.
That's enough theory for now. Let's get back to the code and make the function do something.
Using the function
The simplest way to use a function is to bind it to an element using an HTML attribute, such as onClick.
<a> tag. Then type onClick="changeFontSize()". The final paragraph should now look like this in Code view:<p><a href="javascript:;" onClick="changeFontSize()">Change list font size</a>.</p>
You can check your code against change_02.html in the sample files.
Detecting errors when your script doesn't work
We all make mistakes, and you tend to make a lot when you're learning a new subject. If there's a problem with your code, the script usually fails without any indication of what went wrong. All recent browsers have built-in tools to help you debug your code. You can find them in the following locations:
Introduce a deliberate mistake into the changeFontSize() function to see the error message generated by the browser's error console.
getElementById() to use an uppercase D like this: var list = document.getElementByID('fruits');
The error messages generated by your browser might be worded differently from Figure 5, but they all basically say the same thing: getElementByID() isn't a valid function. As a beginner, working out why an error occurs isn't always easy, but one of the most common mistakes is misspelling the name of a function or method. JavaScript is case-sensitive.
All error consoles, except the one in Opera, provide a link, which takes you to the line that contains the error.
The changeFontSize() function increases the font size, but the only way to change it back to its original size is to reload the page. To improve the function, you need to detect the current font size so that the function can decide which size to change it to.
In common with other programming languages, JavaScript uses conditions to determine what action to take. You place the condition in parentheses preceded by the if keyword. The code associated with the condition is placed in a pair of curly braces after the condition. In pseudo-code, it looks like this:
if (condition) {
code to execute if condition is true
}
If the condition is true, the code is executed. If it's false, the code is ignored.
When the condition is false, you can use the else keyword to introduce alternative code. Again, in pseudo-code, it looks like this:
if (condition) {
code to execute if condition is true
} else {
code to execute if condition is false
}
You can also chain conditions using else if:
if (first condition) {
code to execute if first condition is true
} else if (second condition) {
code to execute if first condition is false, but second is true
} else {
code to execute if both conditions are false
}
Note: You might see scripts that omit the curly braces after a condition. This works only when there is a single command following the condition, and is not recommended. Always use curly braces. They make the logic of your script easier to understand.
The condition is often a comparison, such as two values being equal, or one being larger than the other. The following table lists the main comparison operators.
Table 1. Comparison operators
Operator |
Name |
Example |
Meaning |
== |
Equality |
a == b |
a and b both have the same value. |
!= |
Inequality |
a != b |
a and b have different values. |
> |
Greater than |
a > b |
a is greater than b. |
>= |
Greater than or equal to |
a >= b |
a is greater than or equal to b. |
< |
Less than |
a < b |
a is less than b. |
<= |
Less than or equal to |
a <= b |
a is less than or equal to b. |
Let's improve the changeFontSize() function to toggle between the normal and larger font sizes.
style object to change the value of a CSS property has the effect of using an inline style. Because the original HTML doesn't use an inline style for the fruits unordered list, list.style.fontSize doesn't have a value when the page first loads. So, one way to write the condition is to check that list.style.fontSize is an empty string—in other words, it has no value. An empty string is a pair of quotes with nothing between them. Change the function like this:function changeFontSize() {
var list = document.getElementById('fruits');
if (list.style.fontSize == '' || list.style.fontSize == '16px') {
list.style.fontSize = '20px';
} else {
list.style.fontSize = '16px';
}
}
If list.style.fontSize has no value, it's changed to 20px. Otherwise, it's changed to 16px.
Note: One of the most common mistakes is using a single equal sign instead of two when comparing values. A single equal sign assigns a value. Two equal signs compare values.
list.style.fontSize is no longer an empty string. It's 16px. The simple way to fix this is to use the inequality operator (see Table 1) like this:function changeFontSize() {
var list = document.getElementById('fruits');
if (list.style.fontSize != '20px') {
list.style.fontSize = '20px';
} else {
list.style.fontSize = '16px';
}
}
If list.style.fontSize is not 20px, it's set to 20px. Otherwise, it's set to 16px.
Using logical operators with conditions
Although there was a simple solution to the problem with the condition in changeFontSize(), it's often necessary to test multiple conditions. You do so using logical operators, which are listed in Table 2.
Table 2. Logical operators
Operator |
Name |
Description |
&& |
Logical AND |
Both conditions must be true. If the condition on the left fails, the condition on the right is never tested. |
|| |
Logical OR |
Either condition must be true. The condition on the right is tested only if the condition on the left is false. |
! |
Logical NOT |
When placed in front of a true/false value, this reverses its meaning. So, a true value becomes "not true"—in other words, false. |
The changeFontSize() function has been rewritten in change_04.html to demonstrate the use of the logical OR operator. The code looks like this:
function changeFontSize() {
var list = document.getElementById('fruits');
if (list.style.fontSize == '' || list.style.fontSize == '16px') {
list.style.fontSize = '20px';
} else {
list.style.fontSize = '16px';
}
}
The condition now tests if list.style.fontSize is either an empty string or 16px. If you test change_04.html, you'll see it toggles the font size between 16px and 20px.
Note: You need to repeat the full condition on both sides of the logical operator. You cannot just repeat the value like this:
// THIS WILL NOT WORK
if (list.style.fontSize == '' || '16px') {
Unlike the logical AND and logical OR operators, the logical NOT operator is used with a single condition. It's extremely useful because JavaScript treats most values as implicitly true or false, as the next section explains.
Understanding true and false values
Values that are either true or false are known as Booleans (after the nineteenth century English mathematician, George Boole, whose work is considered to be the basis of modern computer logic). JavaScript has two Boolean values, the case-insensitive keywords true and false.
The comparison operators in Table 1 produce a Boolean result—or to use the technical expression, they return true or false. In addition to Boolean values, JavaScript supports the concept of values that are implicitly true or false. These are sometimes referred to as truthy and falsy values.
JavaScript regards the following values as implicitly false:
null)NaN)0 or '0''')All other values, apart from the keyword false, are regarded as true.
Note: Wrapping the keywords true and false in quotes converts them into strings. Only an empty string is false, so 'false' is treated as true. Beware!
When the page with the changeFontSize() function first loads, list.style.fontSize returns an empty string, so it's implicitly false. This means that you can rewrite the version of the function in change_04.html like this (the code is in change_05.html):
function changeFontSize() {
var list = document.getElementById('fruits');
if (!list.style.fontSize || list.style.fontSize == '16px') {
list.style.fontSize = '20px';
} else {
list.style.fontSize = '16px';
}
}
Prefixing list.style.fontSize with the logical NOT operator (an exclamation mark) has the effect of saying "if list.style.fontSize is false treat it as true."
Using the logical NOT operator with implicitly true and false values is very common in JavaScript. It's frequently used with values that you expect to be true. For example, you might have a variable called checked. You can read if (!checked) as "if not checked."
The changeFontSize() function is rather inflexible because the ID of the fruits unordered list is hard-coded into the first line. To reuse it with other elements, you need to pass the ID as an argument to the function.
changeFontSize() in the function definition. This tells the function to expect an argument (or parameter) called id. A parameter is similar to a variable, so it's not wrapped in quotes and follows the same naming rules as a variable (see "JavaScript basics" earlier in this tutorial).'fruits' between the parentheses of getElementById(), and replace it with id. Make sure you delete the quotation marks, because id is being used as a variable to represent the value passed as an argument to the function. The first two lines of the function definition should look like this:function changeFontSize(id) {
var list = document.getElementById(id);
This has the effect of passing to getElementById() whatever value is passed as the argument to changeFontSize().
changeFontSize() in the link that triggers the onClick event. The link should look like this:<a href="javascript:;" onClick="changeFontSize('fruits')">
Note: The onClick attribute wraps changeFontSize() in double quotes, so you must use single quotes around fruits. When using quotes inside a string, you should always use the opposite type to the outer pair of quotes. Otherwise, the code will break. If you can't avoid using the same type of quotes, inner quotes should be preceded by a backslash.
fruits, save the page, and test it again. It no longer works, because the function can't find an element with the ID fruit.fruits, and save the page. You can compare your code, if necessary, with change_06.html.
The changeFontSize() function toggles between two font sizes. The final change you'll make to it in this whirlwind tour of JavaScript is to iterate through several different sizes. To do so, you'll store the sizes as an array and use a loop to go through each size in turn. This section is more complex than before, so don't try to rush it.
An array is a collection of related values that can be referred to by a single variable. There are two ways to create an array. One is to use the Array() constructor like this:
var friends = new Array('Tom', 'Dick', 'Harry');
The other way is to create what's known as an array literal like this:
var friends = ['Tom', 'Dick', 'Harry'];
Using square brackets to create an array literal is quicker, and tends to be more widely used nowadays.
Each item—or array element—is automatically numbered. To refer to an array element, you put its number in square brackets after the name of the array. However, in common with most programming languages, the numbers begin at zero. So, friends[1] refers to the second array element (Dick) rather than the first element, which is friends[0].
The usual reason for storing elements in an array is to perform the same task on each one or to select a value from the set. Loops are used to iterate through each item in an array. JavaScript has several types of loops, but for the purposes of this tutorial, I'm going to use only one: the for loop.
In pseudo-code, a for loop looks like this:
for (initialization; condition; increment) {
code to execute each time the loop runs
}
Between the parentheses are three statements separated by semicolons:
All arrays have a length property, which returns the total number of elements in the array. The following code gets the number of items in the friends array:
var numFriends = friends.length;
There are three elements in the friends array. So, numFriends is 3.
Because array elements are numbered from zero, you set the condition to run while the counter is less than the array length. The counter variable lets you access each array element in turn like this:
for (var i = 0; i < numFriends; i++) {
do something with friends[i]
}
The first time the loop runs, i is 0, which makes friends[i] equivalent to friends[0]. The value of i is then incremented by one, giving access to the next array element, friends[1]. Then i is incremented to 2, giving access to friends[2]. The counter is incremented again, but i is no longer less than 3, so the loop stops.
Looping through an array of font sizes
With that information under your belt, it's time to tackle the final version of the changeFontSize() function. This exercise pulls together many features of JavaScript, including declaring multiple variables, creating an array literal, looping through an array, conditional logic, simple arithmetic calculation, and joining values as a string.
if and else blocks. You should be left with the following code:function changeFontSize(id) {
var list = document.getElementById(id);
}
var and ending with a semicolon. Alternatively, you can create a comma-separated list of variable declarations. That's the approach I'm going to take.getElementById(id), and replace it with a comma. Then create a new line and indent the code so that it's vertically aligned with list. Declare the new variables like this:function changeFontSize(id) {
var list = document.getElementById(id),
fontSize = list.style.fontSize,
sizes = [16, 20, 24, 28],
len = sizes.length,
i;
}
This stores the value of list.style.fontSize as fontSize. It then creates an array literal called sizes containing four numbers, and stores the length of the array as len. Finally, it creates the counter variable i, but doesn't assign it a value.
You don't need to indent the code like this, but it makes it easier to read. This is also one of the rare occasions when inserting a new line before the semicolon doesn't break the code. The comma at the end of each line tells the JavaScript engine that it's a list of variables. You should also note that the numbers aren't in quotes. JavaScript treats numbers differently from strings.
function changeFontSize(id) {
var list = document.getElementById(id),
fontSize = list.style.fontSize,
sizes = [16, 20, 24, 28],
len = sizes.length,
i;
if (!fontSize) {
list.style.fontSize = sizes[1] + 'px';
}
}
This uses the logical NOT operator with fontSize. If fontSize doesn't have a value, JavaScript treats it as implicitly false. The logical NOT operator reverses the meaning of a true/false value, so the code in the curly braces is executed the first time the function is triggered.
JavaScript uses the plus sign (+) both for simple addition and to join text together. So, the line of code inside the braces takes the value of the second element in the sizes array (20), and adds the string 'px' to it. This value (20px) is then assigned to list.style.fontSize.
You're probably wondering why you need to use list.style.fontSize when you have created fontSize as a variable. It's because fontSize only stores the existing value. To change the size of the font in the page, you need to assign the value to the unordered list's style object.
fontSize variable contains the current size. So, you need to loop through the array to find a match for the current size, and change the font to the next size up. However, when you get to the end of the array, there isn't a next size up. You need to go back to the first size again. Amend the code as shown here, and then I'll explain it in more detail:function changeFontSize(id) {
var list = document.getElementById(id),
fontSize = list.style.fontSize,
sizes = [16, 20, 24, 28],
len = sizes.length,
i;
if (!fontSize) {
list.style.fontSize = sizes[1] + 'px';
} else {
for (i = 0; i < len; i++) {
if (i == len - 1) {
list.style.fontSize = sizes[0] + 'px';
} else if (fontSize == sizes[i] + 'px'){
list.style.fontSize = sizes[i + 1] + 'px';
break;
}
}
}
}
The for loop inside the else code block contains another set of conditions. The first condition checks if the counter is the same as len minus one—in other words, 3. There are four elements in the sizes array. Counting from zero, the final element is sizes[3]. If it is, there are no more array elements. So, the code builds the font size from the first array element (sizes[0]).
If the loop isn't at the last element in the array, the second condition is evaluated. It checks if the current array element plus 'px' matches fontSize. If it doesn't, the code is ignored, and the loop runs again until it finds a match. When it does, it builds the string from the next element in the sizes array by adding one to the value of the counter. When a match is found, the loop isn't needed any more, so the break keyword brings it to a halt.
This tutorial has introduced you to many of the main concepts in JavaScript, but it only begins to scratch the surface of a vast—and often complex—subject. It has been designed to give you the basic knowledge needed to understand the concepts in the next article, which deals with the popular jQuery framework. The advantage of using jQuery is that it smooths out inconsistencies between browsers and hides much of the complexity that puts many web designers off learning JavaScript.
To learn more about JavaScript in detail, visit the excellent guide in the Mozilla Developer Network.
There's also a comprehensive series of articles in the "JavaScript core skills" section of the Web Standards Curriculum hosted by Opera.
This work is licensed under a Creative Commons Attribution-Noncommercial-Share Alike 3.0 Unported License. Permissions beyond the scope of this license, pertaining to the examples of code included within this work are available at Adobe.
Tutorials and samples |
| 04/23/2012 | Resolution/Compatibility/liquid layout |
|---|---|
| 04/20/2012 | using local/testing server with cs5 inserting images look fine in the split screen but do not show |
| 04/18/2012 | Ap Div help |
| 04/23/2012 | Updating |