In this chapter we are going to take VBScript straight to your Web site visitor's browser. We'll take a look at how VBScript and Internet Explorer can be combined on the client-side to create interesting and exciting HTML pages for your visitors .
Going straight for the client-side is the easiest , now-tech, no-special-server needed way to get VBScript enabled pages to the visitor. You can do it using any server, with no Active Server Pages (ASP) needed.
In this chapter you'll learn what you need to be able to deliver VBScript-enabled content straight to the browser, as well as find out how it works and what you can do with it. Let's start by exploring the tools you'll need to write client-side VBScript.
Creating HTML Web pages requires nothing more than a text editor to type in your HTML code and a Web browser to view it. To check that visitors to your Web site see things the way you intend, you'll need to use the same browser or browsers as they will be using. This is easy when you are dealing with Netscape Navigator or Opera because you can have many different versions installed on the one system. Internet Explorer (IE) is a different case. Because it couples so tightly with the operating system, you can only have one version of Internet Explorer per machine.
IE5 did have a compatibility mode that allowed you to launch IE5 acting as IE4. To use IE5's IE4 compatibility mode you did need to have IE4 installed on the machine prior to installing IE5, and choose the IE4 compatibility mode option during the IE5 setup. For more details, see Microsoft Knowledge Base article 197311. Note that IE6 has no such feature.
To thoroughly test your Web pages you need to test using the same operating systems as your users. The same version of a browser may support different features or behave differently depending on the operating system. For example, IE4 on the Mac does not support ActiveX. Never assume that because something works on one browser or platform then it will work on them all.
It is quite possible to create all your pages using Windows Notepad. Many do and this has the advantage of being simple to use and also it's free with Windows. However, creating a whole Web site ( especially if it is a large one) using just Notepad is needlessly complicated, when there are plenty of tools available specifically for Web page creation.
Most seasoned Web designers have some kind of HTML editor that they use and probably swear by. If you're planning on doing a lot of VBScripting and haven't decided on a tool to use, there are a few features that you might like to look out for. Features such as:
Syntax highlighting makes the VBScript code much easier to read by color -coding-specific language keywords. Automatic code completion gives a list of available properties and methods associated with a HTML tag or an ActiveX control. Event scripting lists the events available for a particular tag or ActiveX control and will even write the code framework to handle the event.
Be careful of WYSIWYG HTML editors. Many WYSIWYG Web page design applications also have a tendency to rearrange your carefully crafted HTML tags and code. Because of this, many developers start off by building the skeleton of the Web site using a WYSIWYG page design tool and then switch back to Notepad or another simpler text-based editor to hand-code the scripts.
Client-side scripting gives the Web developer two separate abilities :
It also provides the 'glue' with which to bind and work with ActiveX components embedded in the page.
Prior to Dynamic HTML (DHTML), the most important use of scripting was for the purposes of form validation. Forms have been supported since the very first browsers, back in the days when just being able to combine text and images on the same Web page was considered the pinnacle of excitement.
However, forms have always presented problems. The problem that most Web developers wish they could do something about was that there was no way to check whether the information the user had entered into a form field was actually valid-until after they had submitted it to the server. On receiving the submit form, the developer could easily check the validity of the data with a server-side component (usually a CGI program). However, it was always thought that it would be much more user-friendly and efficient to catch as many form errors as possible before getting to this stage. It would be much better if the user could be notified of any mistakes before the information was submitted to the server. Client-side scripting gives us the power to do precisely that.
Scripting in the earlier browsers also enabled a few simple special effects. The most popular amongst these were scrolling text in the status bar and image rollovers. However, once a page was loaded it was still essentially static. Some primitive responses to user interaction of the page were indeed possible, but nothing that could genuinely be called 'dynamic' was possible. Any elements that were on the page were there to stay and could not be changed. Adding new elements to an existing page was also impossible .
As you will see in the next chapter, all this changed with DHTML, particularly that supported by Microsoft's Internet Explorer 4, 5, and 6.Including script into your page simply involves using the < script > tag. In theory there is no restriction as to where you can place a script in an HTML page but normally you will place most of your scripts inside the < head > tag of an HTML page.
As a very simple example, the following script shows a message box when the page is loaded.
A sample page
Notice something important about this script-The script is not connected to any event in the browser and as such fires as soon as the browser reaches it when parsing the page.
The browser wars between Netscape and Microsoft have left us with a (sometimes confusing) array of scripting languages and standards.
The following table details which browser supports which languages.
JScript 1, VBScript 1
JScript 3, VBScript 3
JScript 5, VBScript 5
None-no browser of
JScript 5, VBScript 5
This table relates to Windows Platforms only. Internet Explorer for the Macintosh does not support VBScript.
Your choice of scripting language is ultimately limited by which browsers your pages must be compatible with. Although it is possible to include different client-side scripting languages in a page, it can quickly become confusing.
Things are a lot better nowadays than they were five years ago, with Internet Explorer currently commanding an enormous lead over the other browsers in terms of browser numbers in use. However, even with one browser having massive dominance over the others, it's still hard for developers to shed their browser burdens and develop for one browser alone. However, greater problems loom on the horizon for Web developers as a greater number of browsers (such as Opera and Mozilla) enter the market along with more diverse platforms ( especially Linux-based platforms).
There is one group of developers that have it easier than others when it comes to deciding what standards to support-the Intranet developer. The Intranet developer is in the enviable position of being able to know pretty well what browser and scripting language others are using and can develop pages and scripts that are perfectly suited to the target browser that is used. This makes the Intranet developer's job a lot easier than that of an Internet developer.
There are important differences between VBScript and VBA. VBScript is an untyped language, which means that all variables are variants and don't have an explicit type (such as integer or string).
In fact, they do have subtypes that you can (and often need to) use. Conversion functions such as CLng , CStr , and CInt make explicit the subtype you're dealing with.
If you are used to using VBA, one difference that you will certainly find when moving to VBScript is that error handling is a lot less powerful.
Most of the client-side scripting you do will involve handling events raised by objects in the page. It could be the onLoad event of the page itself, onSubmit event of a form, the onClick event of an image, or an event raised by an ActiveX control that you have embedded in your page. The reference section of the book includes a listing of objects and the events they support.
The easiest way to add an event handler in Internet Explorer is to define a Sub or Function to handle it inside a < script > block. The name for the Sub or Function must be of the form elementName_eventname . Also note in the following example the use of the VBScript Me object, which references the object (for example, an HTML tag or ActiveX control) that caused the event to fire.
A sample page
Clicking on the button generates the message box displayed in Figure 10-1.
An alternative way of doing the same thing is to use the for and event properties of the < script > tag. All the code inside the < script > tags will execute when the event fires.
A sample page
Different code, but as Figure 10-2 shows, the result is the same.
If you want to pass parameters to your event handling subroutine, then you must define a Sub or Function and call that in your element's onEvent embedded inside the tag. You must not name your subroutine elementName_EventName or the browser will get confused with the first way we saw above of defining the event.
Because we are calling a separate subroutine (and not directly defining an event handler), the Me object if used inside our subroutine won't point to the element that caused the event to fire. It will, however, behave 'correctly' in the procedure that calls the function; so from here we can pass Me to our Sub as one of its parameters.
A sample page Me,99">
Take note that in IE3 there is no other way to discover which element was used to fire a particular subroutine within the script.
Here, our subroutine is called DoSomething , and it's called from the onclick event of our input button with our two parameters. Me works fine in the event handler, but note however that if we were to try to refer directly to Me in the DoSomething procedure, it would have no meaning since the DoSomething procedure is a standalone Sub .
Figures 10-3 and 10-4 show the message boxes generated by this code.
Some events, such as those associated with link tags and forms, can be cancelled. If, for example, the user has entered an invalid value in a form, then we don't want the form to submit because we know that it will fail to process at the server-side if it contains bogus information. Instead, we want to stop the event in its tracks and notify the user.
To do this we normally need to return a value of False to cancel the action. As only functions (not subroutines) can have return values, we need to define our event handler code as a function.
A sample page containing a form
Enter a number from 1 to 10
Depending on the input, the script generates the appropriate message. The user can enter nothing, a number outside of the appropriate range or a number in the right range and the appropriate message is displayed accordingly . These are shown in Figures 10-5, 10-6, and 10-7 respectively.
With most events in a script it's quite obvious when they will fire. You click a button, and the onclick event fires. However, there are some events that don't fire as a direct response to user interaction. The window_onload event is a good example of this. Any script in your page outside of a subprocedure or function will fire as the page is parsed by the browser. But which comes first, the window_onload or the parsed code? Also if you have a frameset and frames , what will be the order the window_onloads fire?
Let's take a look at a simple example. You'll need to create three HTML pages: a page containing the frameset tags and a page for each of the frames.
First we have the frameset page, which we'll call EventOrder.htm .
A sample page containing script
</font> </span> <span style="background-color:#c0c0c0"> <font color="#000000"> <cke:body> </font> </span> <span style="background-color:#c0c0c0"> <font color="#000000"> <p>This page uses frames, but your browser doesn't </font> </span> <span style="background-color:#c0c0c0"> <font color="#000000"> support them.</p> </font> </span> <span style="background-color:#c0c0c0"> <font color="#000000"> </cke:body> </font> </span> <span style="background-color:#c0c0c0"> <font color="#000000">
Next we create the top frame page. Save this page as top.htm .
A sample page containing script
Finally, create the page for the bottom frame. Save this as bottom.htm.
A sample page containg script
If you load the page containing the frameset, then click the list events button, the text area will be filled with details of the window_onload events and embedded scripts, listed in the order they fired . This is shown in Figure 10-8.
It's perhaps worth noting that the differences between browsers include not just the events each HTML tag has but the order they fire in. For example, if you run this code in IE3 you'll find the order in which events fire is different from that of IE5 and IE6. Although the events we've used in our examples are the same for IE4, IE5, and IE6, you will find other differences between them.
The most common way on the Web to obtain information from the user is to use an HTML form populated with a variety of form elements (in case you're wondering, e-mail is another option). Using script, the HTML form can be manipulated and examined using its form object. An HTML page can have one or more forms that we can reference either by name or using the document object's forms array. In most cases it's easier just to refer to a form by name.
To insert an HTML form into a page the < form > tag is used along with the corresponding < /form > close tag.
The most important properties of the < form > tag are Action and Method . The Action property is the URL where the form will post to, for example an ASP page or a CGI script.
The Method property can be either post or get , and determines how the form's data is transmitted to the server when the form is submitted. If the Method property is set to get , then the data in the form's elements will be appended to the URL that was specified in the Action property. A form Method of post sends the form's data as a data stream to the server along with the http header.
Normally it is the form post method that is used most often. HTML 4.0 standard even deprecated the get method, although this doesn't stop it being used. The reason for this is because get places a character limit on how much data can be sent and is actually visible in the URL for your users to see, something which you may not want.
Having defined our form tags, we can then populate the form with the HTML controls (commonly referred to as elements ) available. The most common controls are:
The next thing we need to worry about is how we make sure what the user submits is valid data.
The most common criteria for validation of an input box that's being used for the entry of numerical data are:
We saw a simple example of this earlier on when we looked at cancelling events. The following example describes another approach. If the value entered by the user into form1 's element text1 is an integer between 1 and 10 , then a message box tells us that it's valid. At this point (in real life at least, but not as far as the example is concerned ) you would actually submit the form rather than inform the user using a message box the way we do here. The line "form1.submit" (which is currently commented out) in the following code will do this, although to use the code as supplied here you'll need to create the page some_form_handler.asp for yourself or provide an alternative way to process the form.
If the user has entered invalid data then the ValidInteger function returns a message describing the problem.
A sample page containg script
The outputs generated by the script contained in this form are again reliant upon the input that the user gives it via the input box. Again, this example isn't very sophisticated but does serve as a starting point for more complex and relevant form validation scripts.
The only check for validity you can make with a radio button group is that one element has been selected by the user. You can define one of the elements to be checked by default, simply by putting checked inside one of the radio buttons' tags.
In case you are not familiar with HTML, to define a group of radio buttons we simply create a number of radio buttons and give them the same name.
Some things are too important to be left to defaults, though. Take the example of a radio group for selecting a credit card type. By not using a default, you know that the user has made a positive choice in setting their credit card type. Otherwise there is a danger that they could have missed the question, and we would end up with invalid information.
A sample page containg script
The code in the page loops through each of the radio buttons in the group and checks to see if one is selected. We could also find out how many elements there are in a group using the length property.
When the form is actually posted, the value sent will only be the value of the selected radio button. So if radio button 3 is selected then radio1=AmericanExpress will be submitted to the server and nothing else.
An HTML select element can be used in the same way as a Visual Basic combo box or a list box, depending on its size property. If the size property is set to 1 then it acts just like a drop-down combo box, but if its size is set to more than 1 then it becomes a list box.
One common use of the select element is to allow the user to enter a date. It has enormous advantages over using a text box for dates, the main one being its clarity and ease of use for the user. Take the difference between American and British date formatting. Each country has a different format and this has enormous scope for causing problems (in Britain 11/07/2003 is interpreted as the 11th day of July 2003; in America this is November 7th of 2003). Using select controls you can unambiguously pass the date that you mean without trusting the user to get it the right way around.
In the following example we validate the date defined by the user selecting from select boxes. We need to ensure that they don't select an invalid date, such as the 31st April or the 29th of February in a nonleap year.
A sample page containg script
12345678910111213141516171829202122232425262728293031 JanFebMarAprMayJunJulAugSepOctNovDec 200320042005200620072008
Figure 10-9 shows the result on choosing a valid date, while Figure 10-10 shows the response to selecting an invalid date.
VBScript cannot exist within a vacuum . It is a tool with which to leverage and manipulate the environment of its current context or host, whether that be Windows Script Host and the Windows system, Active Server Pages and Internet Information Server, or a Web page and the browser. But what are we actually manipulating? The answer is that we are manipulating the Document Object Model.
The Document Object Model (DOM) is an all-encompassing term for the programmatic interface to the hierarchy of objects available within a browser and the Web page it displays. It maps out each object's associated properties, methods , and events. Objects include the browser itself, a frame's window, the document or Web page within that frame, and the HTML, XHTML, and XML tags within the page, as well as any plug-ins or embedded ActiveX controls. The DOM also includes a number of collections of objects, such as the forms collection we have already seen in use.
Every browser version has its own DOM, and they vary considerably between Microsoft's Internet Explorer and Netscape's Navigator. There is also considerable variation between different versions of the same browser.
In an effort to bring about a common standard for the DOM, the W3C (the body that deals with Web standards) has released a number of standards for defining the DOM. The W3C's DOM (Level 0) approximated to the level supported by version 3 browsers.
Level 1 DOM specifications, released in October 1998, struck a balance between IE4's DOM and that of Netscape 4's, though IE4's was much closer to the specification. The changes from the Level 0 DOM to Level 1, particularly those supported by IE4, were quite dramatic. The Level 1 specification makes every element within a page a programmable object and exposes its attributes as properties. Microsoft's DOM in IE4 went even further, allowing pages to be updated even after they have been loaded. This puts the 'Dynamic' in Dynamic HTML. Prior to this (with the exception of images), once the page was loaded into a browser no further changes were possible.
Level 2 was completed in November 2000. It extended on Level 1 with support for XML 1.0 with namespaces, adding support for Cascading Style Sheets (CSS), events such as user -interface events and tree manipulation events, and enhancing tree manipulation methods (tree ranges and traversal mechanisms). The DOM Level 2 HTML became a W3C Recommendation in January 2003.
The new DOM supported by IE5 and IE6 is a significantly evolutionary move on from that supported by IE4. Under IE4 almost all tags were programmable while under IE5 and IE6 all of the tags are individually programmable. Also, new methods introduced in IE5's DOM make dynamically manipulating the page easier in later versions of Internet Explorer than it was under IE4.
DOM Level 3 is currently under development. Level 3 will extend Level 2 by finishing support for XML 1.0 with namespaces, aligning the DOM Core with the XML Infoset, adding support for XML Base, and extending the user-interface events (keyboard). The Level 3 will also add support for validation, the ability to load, and save a document, will explore further mixed markup vocabularies and their implications on the DOM API ('Embedded DOM'), and will support XPath.You can find the latest information on DOM specification developments on the W3C's Web site at http://www.w3.org/DOM/ .
DOM specifications are all well and good, but as programmers it's the practical implementation we're interested in. Before leaving this chapter it's worth taking a look at the DOM as implemented by IE6.
The Window Object
Right at the top of the HTML, DOM hierarchy is the window object. If your page has no frames then there is just one window object. If the page contains frames then each frame has its own window object.
Each window object within a frameset has a parent window object, which is the window object of the page defining the frames. You can access any of the other window objects from script inside a page by using the window object's parent property. After you have a reference to the parent window object you can use that to access not only the window object's properties and methods, but also those of any HTML tags inside that window. You can also use it to access any global VBScript variables or functions.
Let's take a look at a simple frameset example. We will create three pages:
The first page we will call TopFrame.htm .
A sample page containg script
The second page we will call Lframe.htm .
The third page we will call Rframe.htm .
If you load Topframe.htm into your browser you can try out the buttons in the right frame. These demonstrate accessing script in the window object of the right frame, its parent's window, and the left frame.
In the first button's onclick we are accessing the window of the current frame, so we normally don't need to explicitly say it is the window object we are referring to as this is implied . In other words, sName is the same as window.sName . Bear in mind that there are some contexts you will need to explicitly state if it's the window object you are referring to.
When the second button is clicked, the top frame page (that is, the right window's parent object), is referenced. This is very handy for defining global variables and functions when you have a multiframe page.
For the third button we access the sName and SayWhoIsThis function contained in the left frame. When the button is clicked we do this by referencing the frame called Lframe contained by the right window's parent window object. As you can see, navigating the DOM can get a little complex at times and vigilance and care is needed to prevent mistakes.
The fourth button does exactly the same as the third but in a different way to demonstrate another of the DOM's important features: collections.
The window object has not only properties, methods, and events, but like many other objects in the DOM it also has collections. We know from the earlier example that a window object can have many child window objects, but where are these contained? The answer is in the frames collection. The frames collection is a zero-based array containing references to the frames defined by that window. So in button4 's code, you see that the left frame is window.parent.frames(0) , which is exactly the same as window.parent.Lframe .
Progressing along the DOM down the hierarchy, we come to the document object. Each window object will contain a document object. This can be referenced using the window object's document property. The document object acts as a container for all the document objects, such as HTML tags and ActiveX controls, inside your page. Just like the window object, the document object has a large number of collections associated with it.
Time to look at an example.
Here we create a simple page consisting of a paragraph and a table. Using script, we access collections and properties in the DOM by using the document.all collection to set references to various document objects in the page. An alternative would be to give all the tags names instead, but you'll find this isn't always possible. There will be times when you are unable know the name of a tag and need to access it using collections such as the all collection.
A sample page containg script
A boring paragraph
|Cell 1||Cell 2|
|Cell 3||Cell 4|
First, we dimension some variables, which we will set to reference document objects. You're probably thinking that we could reference the objects directly, but creating variables instead will make your code easier to read if you are accessing the property numerous times. Creating the reference to the window and document object is unnecessary for this example, but we've done it to emphasize what it is we are referencing in the DOM.
We set the variable theWindow to reference the window object for our page. Then we use object's document property to set a reference to the document for that page and to display the page's title.
We set the variable thePara to reference our paragraph contained in the document object. Why document.all(5) and not document.all(0) ? Well, the all collection of an object references all objects contained by that object. The document includes the html tag, head tags, the script tags, the body tags, and so on. The collection starts at zero and as our paragraph is the sixth tag in the page it is document.all(5) .
We then use the message box to show the innerText property of the paragraph object.
Next , we set theTable to reference the table in the page. It's the next tag after the paragraph, so it corresponds to document.all(6) . We show a message box with the table's tagName property. The tagName is simply the tag definition, so for < table > it's TABLE , for a < p > it's P , and so on. See Figure 10-11 to see an example of the output.
Next we set theRow to reference the second row in the table. We do this using the rows collection of the table object.
Finally we obtain a reference to the second cell in the row by using the all collection of the row object. We might have used the cells collection, but this example demonstrates that it's not just documents that have the all collection. In fact, all objects have it if they contain other objects.
Hopefully, the examples in this section have demonstrated how to access objects in the DOM, and also shown that the DOM is a hierarchical collection of objects, with each object in the hierarchy being both an object inside another object and also a container for other objects.
Validating forms client-side using VBScript was also demonstrated with a variety of common controls and types of data. Finally, we took a tour of the Document Object Model and the various standards associated with it, including those laid out by the W3C and implemented by Microsoft and Netscape.
In the next chapter you'll be shown lots of exciting techniques using the latest technologies available with IE5 and IE6.