Introduction to JavaScript Fall 2009 Class 8

esse quam videri
Jump to: navigation, search

Doing Something with Each Item in a Collection

So far, we've used jQuery to find groups of elements on the page, and then take those elements and add styles or event handlers to them. Sometimes, you might want to do something a little bit more complicated with elements that you find with jQuery. For example, you might want to check if each item that you found has a specific class on it. jQuery has a special function called each that takes in a function that will called for each item that was found with a jQuery selector. Just like with event handler functions the function that you give to jQuery points back to the element it's tied to using the this keyword.

This example shows how to use jQuery to get all of the inputs in a form and then check which of the elements has a class called required:

  var inputs = jQuery('input');
  inputs.each(checkClass);
  
  function checkClass()
  {
     if (jQuery(this).hasClass('required'))
     {
        alert('required!');
     }
  }

There are a few things happening here. The first is that I'm finding all of the input tags on the page using jQuery('input'). The next thing I do is call the each function on the collection of inputs. The jQuery each function takes in a function that will be called for each element that was found. In this case, it will be each of the inputs that was found on the page. Inside of the function, I can refer to each input using the this keyword. I'm wrapping this with a jQuery object and then using the hasClass function to check if the has a class with the name required. If the item does have the class, the browser will alert the user with a message that says "required!".

Shortening the Code a Bit

The example above works fine, but, last week, I mentioned that things could be shortened a bit. First, I didn't need to create a temporary variable to hold the input, because I only used the inputs that I found once when I looped through them. And I didn't need to create the checkClass function since I justed that once as well. Here is shortened version of the code that does the exact same thing as the original.

  jQuery('input').each(function()
  {
     if (jQuery(this).hasClass('required'))
     {
         alert('required');
     } 
  });

See how I called the each function right after finding the inputs on the page? Also, notice that I'm just passing in an anonymous function to the each function. The function doesn't need to have a name, it just needs to get created and passed to the each function so that it can be called. Often, you will be able to shorten your using the techniques that I used to shorten the code above.

Get the Values From a Form

Above, I showed you how you can loop through a collection of items and call a function for each item. For today's activity we'll be checking a form for any requird fields that aren't filled out. To do this, we'll need to get the value of each field and check that the value isn't empty.

If you want to get the value of an input element, you'll need to find the element first. Then, once you've found the input element, you can use the val function to get the value of the element.

So, say I have a form that looks like this:

  <form>
      <input id="first-name" name="first-name" />
      <input id="last-name" name="last-name" />
  </form>

If I want to get the value of the first-name input, I can get to it like this:

  var firstName = jQuery('#first-name').val();

Similarly, I can get to the last name input value like this:

  var lastName = jQuery('#last-name').val();

In both cases, I'm simply finding the element and pulling the value out of it with val.

Triming Whitespace

Sometimes, you may need to make sure that you're not getting any extra information that you don't want from an input. For example, a user might accidentally put a space at the end of the value they entered in a textbox. You probably don't want that extra space, but, by default JavaScript will include it. So, if a user enters "Matthew " in the textbox, you'll get that extra space at the end.

jQuery includes a function called trim to get rid of any extra whitespace at the beginning or end of a string:

  var lastName = jQuery.trim(jQuery('#last-name'));

In the example above, if the last-name input has any extra whitespace at the beginning or the end, the trim function will get rid of it.

Adding New Elements to the Page

In past classes, we've modified the HTML on the page using jQuery's html function. This has worked fine, but sometimes you want to do things that are a little bit more complicated. Let's say that you had an unordered list of items on the page and you wanted to use JavaScript to add a new item to the list. Right now, the only way you could do that would be to modify the HTML inside of the list:

  // DON'T DO THIS!!!!!
  var listHTML = jQuery('#my-list').html();
  listHTML = listHTML + "<li>New List Item</li>";
  jQuery('#my-list').html(listHTML);
  // DON'T DO THIS!!!!!

Doing things this way works, but does it's not very pretty. jQuery offers a better way.

Creating Elements With jQuery

So far, we've been using jQuery to select items on the page using their tag names, ids or css classes. That's not all you can do with jQuery though. You can also use jQuery to create new elements for your page. To do this, you simply need to pass a string of HTML to the jQuery function. jQuery will take the string of HTML and create a new element with it:

  var newListItem = jQuery('<li>My new list item</li>');

The variable called newListItem is now set to a list item element that says My new list item inside of it. The next step is actually adding the element to the page

Adding Elements to the Page

jQuery offers a number of ways to add elements to your page. We will cover a few simple ones today.

Suppose there's an unordered list that already has two items in it:

  <ul id="my-list">
     <li>Item 1</li>
     <li>Item 2</li>
  </ul>

Above, I created a new element called myListItem. If I want to add it to the end of my-list I can use jQuery to find the list and then use the append function to add the list item to the end:

  var newListItem = jQuery('<li>My new list item</li>');
  var list = jQuery('#my-list');
  
  list.append(newListItem);

I can even shorten it up a little bit:

  jQuery('#my-list').append(jQuery('<li>My new list item</li>'));

Similarly, if I want to add the new list item to the beginning of the list, before all of the other list items, I can use the prepend function:

  jQuery('#my-list').prepend(jQuery('<li>My new list item</li>'));

jQuery's append and prepend functions will both take one element and modify it by adding a new element to it. This gives you the same result as modifying the element's HTML, but also gives you more flexibility. Any new element that you create with jQuery can also be modified by jQuery, which includes adding class names, new attributes and event handlers.

Functions that Return Things

Early in the class we talked a little bit about how you can create functions and how you can return things from those functions. Some of the functions we've created as event handlers have included a line that says return false;, but I haven't really explained that line yet.

JavaScript functions are useful for encapsulating pieces of code that you want to run. Sometimes that code needs to send something back to the original code that called the function. The return keyword allows you to return one value back from the function.

Today's activity involves checking a form to make sure that all of the elements are filled out. A useful function for the activity might be a function that returns true if all of the fields are filled out and returns false if any of the fields are empty. The basic structure of that function would look like this:

  function allFilledOut()
  {
     if (all of the fields are filled out)
     {
        return true;
     }
     else
     {
        return false;   
     }
  }

This code, of course, doesn't do anything yet because the if statement isn't actual code. However, the important part is the structure. I'm checking to make sure that all of the fields are filled out. If that statement turns out to be true, then the function returns true. Otherwise, the function returns false. Later, if I wanted to use the new allFilledOut function, I could call it in another piece of code and use the value that was returned:

  var completed = allFilledOut();
  if (completed)
  {
     alert('The form is complete!');
  }
  else
  {
      alert('You still have things to fill out!')';
  }

There are a few things to notice here. One is that I'm storing the return value of the allFilledOut function in a variable called completed. So, this variable will either be true or false after the function runs. Do I really need to create this variable though? Notice that I've also named my function allFilledOut. It might make sense to just put a call to that function right in my if statement like this:

  if (allFilledOut())
  {
     alert('The form is complete!'); 
  }
  else
  {
      alert('You still have things to fill out!')';
  }

Now the if statement looks more like a statement in English: if all of the fields are filled out then do one thing, or else do the other thing. When you're creating functions that return true or false, it helps to name the functions in a way that makes your code read like you might write it out in regular English.

Functions don't have to only return true and false values though. You can also use them return anything. For example, I might want a function that takes in a list of words and returns them as one string, separated by commas:

  function makeList(wordOne, wordTwo, wordThree)
  {
      var list = wordOne + ", " + wordTwo + ", " + wordThree;
      return list;
  }
  
  // Food should equal "pizza, burgers, popcorn"
  var food = makeSentence('pizza', 'burgers', 'popcorn'); 

The function called makeList takes in 3 parameters and builds a string that has all three parameters joined together as a list.

Activity 1

For tonight's activity, we will be creating a page that has a form that allows you add new messages to a page. There are two JavaScript files associated with this activity. The first one, called validation.js, will handle validating the form field. In this case, if a form field has a class of required on it, the field will need to be filled out before the message can be added. If the user leaves any fields blank, they should get an error message and the required fields that were left blank should get a class called error added to them.

The second JavaScript file, called messages.js will add new messages to the list on the right.

The template for tonight's activity can be found here.

Assignment 5

Due Friday November 6th at 10pm

So far, I've given you a template for each of your assignments. For this assignment, I want you to come up with a page and some JavaScript code that goes with the page on your own.

Your page needs to have a textbox that will take in the url for an image. I suggest using Google Images to find some example images to try out. There should be a submit button and if the user clicks the submit button without putting something in the textbox they should get an error message.

If the user has filled out the textbox, when they click the submit button a new image should be created and added to the page. You can create a placeholder div tag that will hold all of the images. After the image is added, it should be animated so that it shrinks down to a smaller size.

If you have a different idea for a jQuery assignment that uses a form, adds elements to the page based on the form and animates them once they are added, please email me. If it meets the requirements you can do something else that's more interesting to you.