Chapter 29. Scripting Selection Boxes

The HTML specification provides the <select/> element so page authors can add a menu of options to a form. The menu the <select/> element generates can look like a drop-down list from which you can select only one item, or like a list box that allows you to select multiple items. These selection boxes have one or more <option/> elements inside the opening and closing <select> tags. The following HTML shows an example:

<select id="dayOfTheWeek" name="dayOfTheWeek" size="5">
    <option value="0">Sunday</option>
    <option value="1">Monday</option>
    <option value="2">Tuesday</option>
    <option value="3">Wednesday</option>
    <option value="4">Thursday</option>
    <option value="5" selected="selected">Friday</option>
    <option value="6">Saturday</option>
</select>

The number of options visible in the browser is determined by the <select/> element's size attribute, and it is this attribute that determines how the browser renders the <select/> element. If size is greater than 1, the browser renders the element as a list box showing the specified number of options at a time. If size is 1 or isn't specified, the browser renders the selection box as a drop-down list.

The <select/> element DOM object has a property called options, a collection of <option/> element objects. Every <option/> element inside the <select/> element is an item in the options collection. So, using the previous <select/> element, you can access the <option/> element for Monday, like this:

var dayOfWeek = document.getElementById("dayOfTheWeek");

var mondayOption = dayOfWeek.options[1];
alert(mondayOption.value); // 1

This code first gets the <select/> element object from the DOM via the getElementById() method (you can also access a <select/> element object through its containing form). Then, using the options collection, the code gets the <option/> element object at the second position and assigns the <option/> object to the mondayOption variable. The final line of this code uses the <option/> object's value property, which gets the value contained within the element's value attribute—1 in this case.

You can get the option that is currently selected by combining the options collection with the <select/> object's selectedIndex property, like this:

var selectedDay = dayOfWeek.options[dayOfWeek.selectedIndex]; // Friday option

alert(selectedDay.value); // 5

Because the <option/> element for Friday has the selected attribute, it is rendered as the selected option in the menu, and the <select/> object's selectedIndex property gets the index of that option in the options collection.

You can also use the selectedIndex property to change the selected option by assigning it the index of the option you want to select. Let's say you want Tuesday to be the selected day. The <option/> element for Tuesday is at index position 2. So, to change the selected option to Tuesday, you could use the following code:

dayOfWeek.selectedIndex = 2;

After this code executes, the browser changes the selected option from Friday to Tuesday.

After you have a reference to an <option/> object, you can retrieve two more pieces of information about that option other than its value. You can use the index property of the <option/> to get its position in the options collection, or you can use its text property to get or set new text associated with it. Most of the time, however, you simply want its value.

As with most everything in the DOM, you're not stuck with whatever is hardcoded into the HTML. You can add and remove options from <select/> elements as you need to.

REMOVING OPTIONS

Options are extremely easy to remove from a selection box. To remove an option you simply assign a value of null at the desired index position in the options collection, like this:

dayOfWeek.options[4] = null;

This code removes the Thursday option from the <select/> element. Fortunately, removing an <option/> object from the options collection automatically reorders the remaining options by shifting down the ones at higher index positions. Now the option for Friday is at index 4 and Saturday is at index 5. You don't have to write any code to reposition and reorder the remaining <option/> elements; the DOM does it for you.

You can also remove an option with the <select/> object's remove() method. It accepts a numeric value as an argument specifying the index position you want to remove. So, instead of setting the Thursday <option/> to null, you could do this:

dayOfWeek.remove(4);

Now that Thursday is gone from the week, the world is in disarray. We had better put it back...

ADDING OPTIONS

Creating an <option/> element object is easy. Simply call the Option() constructor and pass it two arguments:

var thursOption = new Option("Thursday", 4);

This code creates a new <option/> object. Its text is Thursday and its value is 4. Now that you have created an option, it's time to add it to the <select/> element. Unfortunately, adding options to a <select/> object isn't as straightforward as removing them.

One way that you can add a new <option/> object is by assigning the new object at a particular index in the options collection. In doing so, however, you actually overwrite an existing option. Look at the following code:

dayOfWeek.options[4] = thursOption;

This code assigns the new <option/> object to the element at index 4. You may remember that the <option/> object at position 4 is now the Friday option. So what this code actually does is overwrite the Friday option with the new Thursday option. Oops. You can, however, add a new option to the end of the options collection without overwriting anything, like this:

dayOfWeek.options[dayOfWeek.options.length] = thursOption;

This code uses the length property to assign the thursOption object to the very end of the options collection—putting Thursday after Saturday. Oops again. While this may be fine in some cases, it hardly makes sense to have a list of days out of order. You could write code to reorder the options and put them in the correct order, but that requires a lot of extra code (and your author is lazy).

For this reason <select/> objects have a method called add(), which allows you to add an <option/> object at a specified position. This method accepts two arguments: the option to add, and the existing option before which you want to place it. So adding the new option for Thursday can look like this:

var fridayOption = dayOfWeek.options[4]; // Friday

dayOfWeek.add(thursOption, fridayOption);

This code gets the <option/> object for Friday, which is found at index position 4. Then a call to add() adds the new <option/> for Thursday before the <option/> for Friday. All three affected <option/> objects (Thursday, Friday, and Saturday) are reorganized and given new index positions. The <option/> for Thursday is back at index 4, Friday is at index 5, and Saturday is at index 6.

All is well again...unless you try to run this code in Internet Explorer (IE) 7 (or IE8 non-standards mode). IE7 craps out (yes, that's a technical term) when add() is called.

It's not that IE7 (and IE8 in non-standards mode) doesn't have the add() method for <select/> objects. It does, but it expects the second argument to be the index at which you want to put the new option. So for IE7 the code would look like this:

dayOfWeek.add(thursOption, 4);

This code inserts the new Thursday option at index position 4, and IE7 then reorganizes the options collection, pushing the Friday and Saturday options to positions 5 and 6, respectively.

This is a problem, but it's a problem with an easy solution: exception handling. This is actually a topic covered in Lesson 37, and as such it won't be given much coverage here. When a browser craps out (again, it's technical) because of JavaScript code, the JavaScript engine throws an exception. The term "throw" is used throughout computer science, and in this case it means the engine essentially generates an exception, or error, during the execution of a program.

Exceptions happen. They're a part of programming, so a process called exception handling is used to handle code that may throw an exception. The process goes something like this:

  • You try to execute code that can cause an exception. If it works, great! If not, an exception is thrown, and...

  • You catch the exception and execute code that is typically safe to execute—such as code to send a message to the user or achieve the same results as the code that caused the exception.

To put this process into code, you use the try...catch statement shown here:

try {
    dayOfWeek.add(thursOption, fridayOption);
} catch (exceptionObject) {
    dayOfWeek.add(thursOption, 4);
}

This code uses try...catch by trying to execute the add() method by passing the Friday <option/> object. If that code throws an exception, code execution drops to the catch block and executes add() by specifying the index position 4. Now, when the browser executes this code, the new Thursday <option/> is placed in the correct position regardless of the browser used to execute the code.

Note

Don't worry about the exceptionObject in the previous code. Exception handling is covered in more detail in Lesson 37.

All right, so let's apply some of this information to the form you've been working with since Lesson 27.

TRY IT

In this lesson, you learn to script selection boxes by getting the selected option, getting data related to that option, and adding and removing options.

Lesson Requirements

For this lesson, you need a text editor; any plain text editor will do. For Microsoft Windows users, Notepad is available by default on your system or you can download Microsoft's free Visual Web Developer Express (www.microsoft.com/express/web/) or Web Matrix (www.asp.net/webmatrix/). Mac OS X users can use TextMate, which comes as part of OS X, or download a trial for Coda (www.panic.com/coda/). Linux users can use the built-in VIM.

You also need a modern web browser. Choose any of the following:

  • Internet Explorer 8+

  • Google Chrome

  • Firefox 3.5+

  • Apple Safari 4+

  • Opera 10+

Create a subfolder called Lesson29 in the JS24Hour folder you created in Lesson 1. Store the files you create in this lesson in the Lesson29 folder.

Step-by-Step

  1. Type the following HTML:

    <html>
    <head>
        <title>Lesson 29: Example 01</title>
    </head>
    <body>
    <form name="theForm" action="" onsubmit="validateForm(event)">
        <p>
            Name: <input type="text" name="txtName" />
        </p>
        <p>
            Age: <input type="text" name="txtAge" />
        </p>
        <p>
            Email: <input type="text" name="txtEmail" />
        </p>
        <p>
            Password: <input type="password" name="txtPassword1" />
        </p>
        <p>
            Retype Password: <input type="password" name="txtPassword2" />
        </p>
    <p>
            Your Favorite Day: <select id="dayOfTheWeek" name="dayOfTheWeek">
                               </select>
        </p>
    
        <input name="btnSubmit" type="submit" value="Submit" />
    </form>
    <script type="text/javascript" src="eventutility.js"></script>
    <script type="text/javascript">
    function isEmpty(value) {
        return (value === "");
    }
    
    function validateForm(event) {
        var theForm = document.theForm,
        var txtName = theForm.txtName;
        var txtAge = theForm.txtAge;
        var txtEmail = theForm.txtEmail;
        var txtPassword1 = theForm.txtPassword1;
        var txtPassword2 = theForm.txtPassword2;
        var button = theForm.btnSubmit;
        var age = parseInt(txtAge.value);
    
        button.disabled = true;
    
        // validate name field
        if (!isEmpty(txtName.value)) {
    
            // validate age
            if (!isNaN(age) && age > 0) {
    
                // validate email field
                if (txtEmail.value.indexOf("@") > 0) {
    
                    // validate password - pass 1
                    if (!isEmpty(txtPassword1.value)) {
    
                        // validate password - pass 2
                        if (txtPassword1.value === txtPassword2.value) {
                            return;
                        } else {
                            alert("Passwords do not match. Please reenter them.");
                            txtPassword1.focus();
                            txtPassword1.select();
                        }
    
                    } else {
                        alert("Password cannot be blank.");
                        txtPassword1.focus();
                        txtPassword1.select();
                    }
    
                } else {
                    alert("Please enter a valid email address.");
    txtEmail.focus();
                    txtEmail.select();
                }
    
            } else {
                alert("Please enter your age.");
                txtAge.focus();
                txtAge.select();
            }
    
        } else {
            alert("Please enter your name.");
            txtName.focus();
        }
    
        button.disabled = false;
        eventUtility.preventDefault(event);
    }
    </script>
    </body>
    </html>

    Save this as lesson29_example01.htm. It is almost the same as the HTML page at the end of Lesson 28, but it now has a <select/> element with an id and name of dayOfTheWeek. It is empty, so you need to write a function to populate the <select/> element with options.

  2. Add a function called populateDays(), and inside the function create an array called days containing the seven days of the week. Also add a line at the end of the <script/> element to execute populateDays(). The new code is bold:

    <html>
    <head>
        <title>Lesson 29: Example 01</title>
    </head>
    <body>
    <form name="theForm" action="" onsubmit="validateForm(event)">
        <p>
            Name: <input type="text" name="txtName" />
        </p>
        <p>
            Age: <input type="text" name="txtAge" />
        </p>
        <p>
            Email: <input type="text" name="txtEmail" />
        </p>
        <p>
            Password: <input type="password" name="txtPassword1" />
        </p>
        <p>
            Retype Password: <input type="password" name="txtPassword2" />
        </p>
        <p>
            Your Favorite Day: <select id="dayOfTheWeek" name="dayOfTheWeek">
                               </select>
    </p>
    
        <input name="btnSubmit" type="submit" value="Submit" />
    </form>
    <script type="text/javascript" src="eventutility.js"></script>
    <script type="text/javascript">
    function populateDays() {
        var days = [ "Sunday", "Monday", "Tuesday", "Wednesday",
            "Thursday", "Friday", "Saturday" ];
    }
    
    function isEmpty(value) {
        return (value === "");
    }
    
    function validateForm(event) {
        // removed for printing
    }
    
    populateDays();
    </script>
    </body>
    </html>
  3. Now create a few more variables. Get the <select/> element by using the getElementById() method and assign it to a variable called dayOfWeek. Also, create a variable to contain today's day by creating a new Date object and calling the getDay() method. The new code is bold:

    <html>
    <head>
        <title>Lesson 29: Example 01</title>
    </head>
    <body>
    <form name="theForm" action="" onsubmit="validateForm(event)">
        <p>
            Name: <input type="text" name="txtName" />
        </p>
        <p>
            Age: <input type="text" name="txtAge" />
        </p>
        <p>
            Email: <input type="text" name="txtEmail" />
        </p>
        <p>
            Password: <input type="password" name="txtPassword1" />
        </p>
        <p>
            Retype Password: <input type="password" name="txtPassword2" />
        </p>
        <p>
            Your Favorite Day: <select id="dayOfTheWeek" name="dayOfTheWeek">
                               </select>
    </p>
    
        <input name="btnSubmit" type="submit" value="Submit" />
    </form>
    <script type="text/javascript" src="eventutility.js"></script>
    <script type="text/javascript">
    function populateDays() {
        var days = [ "Sunday", "Monday", "Tuesday", "Wednesday",
            "Thursday", "Friday", "Saturday" ]
        var dayOfWeek = document.getElementById("dayOfTheWeek");
        var today = (new Date()).getDay();
    }
    
    function isEmpty(value) {
        return (value === "");
    }
    
    function validateForm(event) {
        // removed for printing
    }
    
    populateDays();
    </script>
    </body>
    </html>

    Notice the code for the today variable. The code new Date() is encapsulated within a pair of parentheses. This is a trick used by professionals when they don't need a particular object for more than one piece of data. In the case of this script you don't need anything from the Date object except the value returned by getDay(). So an anonymous Date object is created and the getDay() method is called on that anonymous object. Remember that getDay() returns a numeric value associated with the day of the week. Sunday is 0, Monday is 1, Tuesday is 2, and so on.

  4. Loop through the days array and add an option for each day. Use the index variable i as an option's value:

    <html>
    <head>
        <title>Lesson 29: Example 01</title>
    </head>
    <body>
    <form name="theForm" action="" onsubmit="validateForm(event)">
        <p>
            Name: <input type="text" name="txtName" />
        </p>
        <p>
            Age: <input type="text" name="txtAge" />
        </p>
        <p>
            Email: <input type="text" name="txtEmail" />
        </p>
    <p>
            Password: <input type="password" name="txtPassword1" />
        </p>
        <p>
            Retype Password: <input type="password" name="txtPassword2" />
        </p>
        <p>
            Your Favorite Day: <select id="dayOfTheWeek" name="dayOfTheWeek">
                               </select>
        </p>
    
        <input name="btnSubmit" type="submit" value="Submit" />
    </form>
    <script type="text/javascript" src="eventutility.js"></script>
    <script type="text/javascript">
    function populateDays() {
        var days = [ "Sunday", "Monday", "Tuesday", "Wednesday",
            "Thursday", "Friday", "Saturday" ];
        var dayOfWeek = document.getElementById("dayOfTheWeek");
        var today = (new Date()).getDay();
    
    for (var i = 0; i < days.length; i++) {
            var length = dayofWeek.options.length;
    
            dayOfWeek.add(new Option(days[i], i), length);
        }
    }
    
    function isEmpty(value) {
        return (value === "");
    }
    
    function validateForm(event) {
        // removed for printing
    }
    
    populateDays();
    </script>
    </body>
    </html>

    The bold code shows the for loop iterating over the days array. For each element in the array a new Option object is created and added to the <select/> element. Note that the length of the options collection is retrieved and passed as the second parameter to add(). This adds the new <option/> object at the end of the options collection. This code works in all browsers, so you don't have to worry about catching any exceptions.

  5. Finally, set the selected option to today's date using the selectedIndex property. New code is in bold:

    <html>
    <head>
        <title>Lesson 29: Example 01</title>
    </head>
    <body>
    <form name="theForm" action="" onsubmit="validateForm(event)">
        <p>
            Name: <input type="text" name="txtName" />
        </p>
        <p>
            Age: <input type="text" name="txtAge" />
        </p>
        <p>
            Email: <input type="text" name="txtEmail" />
        </p>
        <p>
            Password: <input type="password" name="txtPassword1" />
        </p>
        <p>
            Retype Password: <input type="password" name="txtPassword2" />
        </p>
        <p>
            Your Favorite Day: <select id="dayOfTheWeek" name="dayOfTheWeek">
                               </select>
        </p>
    
        <input name="btnSubmit" type="submit" value="Submit" />
    </form>
    <script type="text/javascript" src="eventutility.js"></script>
    <script type="text/javascript">
    function populateDays() {
        var days = [ "Sunday", "Monday", "Tuesday", "Wednesday",
            "Thursday", "Friday", "Saturday" ];
        var dayOfWeek = document.getElementById("dayOfTheWeek");
        var today = (new Date()).getDay();
    
        for (var i = 0; i < days.length; i++) {
            var length = dayofWeek.options.length;
    
            dayOfWeek.add(new Option(days[i], i), length);
        }
    
        dayOfWeek.selectedIndex = today;
    }
    
    function isEmpty(value) {
        return (value === "");
    }
    
    function validateForm(event) {
        // removed for printing
    }
    
    populateDays();
    </script>
    </body>
    </html>

    This new line of code uses the value contained within the today variable to select the current day from the drop-down list.

    Be sure to save the file and run it in any modern browser. You'll find that it works like a charm.

To get the sample code files, you can download Lesson 29 from the book's website at www.wrox.com.

Note

Please select Lesson 29 on the DVD to view the video that accompanies this lesson.

Step-by-Step
..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.140.195.225