The Files

Table 24-1 lists the different HTM files used to create the Web site. (It excludes files that this site is linked to, such as those in the SBN Workshop.) Table 24-2 lists the CSS and JS files used in the project, as well as their purposes and which files use them. Any reference to content pages in either table refers to the files main.htm, custom.htm, authors.htm, and links.htm.

Table 24-1 HTM Files Used to Create the Sample Web Site

File Description
default.htm

  • Creates the main frameset document
  • Reloads itself as the top frameset when loaded as part of a different frameset
  • Reads a cookie
  • Writes frames dynamically, based on a passed parameter (found after a hash mark in the URL)
  • Includes NOSCRIPT and NOFRAMES elements for early browsers
menu.htm

  • Creates left hand menu frame
  • Uses browser detection
  • Creates DHTML menu, custom event handlers, and custom styles and classes based on browser
  • Iterates through document.all
  • Loads itself in correct frameset
  • Creates main content frame
  • Uses a table and a form
  • Provides drop-down list navigation
custom.htm

  • Allows user to customize the look and feel of some pages
  • Uses forms
  • Uses browser detection provided by sniffer.js
  • Writes a cookie
authors.htm
  • Includes information about the authors

links.htm

  • Contains links to useful resources
Each of the content pages

  • Uses content.css
  • Uses legal.js to write copyright information
  • Uses frameit.js to load page in correct frameset

Table 24-2 CSS and JS Files Used to Create the Sample Web Site

File Used by Purpose
cookies.js default.htm Allows reading and writing cookies
custom.js Content pages (non-external pages in right hand frame) Handles style sheet customization
frameit.js Content pages Automatically loads content pages in correct frameset
legal.js Content pages Writes a copyright notice to the page
sniffer.js As needed Performs browser detection
menu.css menu.htm Sets basic formatting for the menu
content.css Content pages Sets basic formatting cascades with any custom formatting set through custom.htm

Now let's look at some of these pages in more depth.

default.htm

The default.htm page is the main frameset document for the site. Like most pages in the site, it begins with a number of linked JS scripts, which allow multiple pages to point to a single file that contains script. Linked JS scripts are supported in version 3.02 and later of Internet Explorer, as well as version 3 and later of Netscape Navigator. Support of this feature is the primary reason that we decided to target these browsers as the minimum requirement. This document can be found in the file named chap24\default.htm on the companion CD and is also shown here:

 <HTML> <HEAD> <TITLE>Dynamic HTML in Action, 2nd Edition</TITLE> <SCRIPT LANGUAGE="JavaScript" SRC="js/cookies.js"></SCRIPT> <SCRIPT LANGUAGE="JavaScript" SRC="js/sniffer.js"></SCRIPT> <SCRIPT LANGUAGE="JavaScript"> //----------------------------------------------------- // Make sure file is not hosted in a different frameset if ( top.location.href != window.location.href )   { top.location.href=window.location.href } //----------------------------------------------------- // Get any customization info about the user. var sCookie = GetCookie("CstmStyle"); var sCstmStyle = ( ( (sCookie != null) && bVer4 ) ? sCookie : null) //----------------------------------------------------- // Construct the frameset. If passed a target content frame, load it. // Otherwise, load main.htm // Get content of URL after any # var sPostHash=location.hash.substring(location.hash.indexOf(`#')+1); // Break up normal HTML tags to prevent premature ending of the script sFrmStart = ("<FRAM"+"ESET COLS=`200,*'><FRA" + "ME src=`menu.htm'>"); if (sPostHash=="") {sFrmMain="<FRA" + "ME src=`main.htm' NAME=`main'>"} else {sFrmMain = ( "<FR" + "AME src=`" + sPostHash + "` NAME=`main'>")} sFrmEnd = ("</FRA"+"MESET>"); document.write(sFrmStart + sFrmMain + sFrmEnd) </SCRIPT> <NOSCRIPT> <FRAMESET COLS=`200,*'> <FRAME src=`menu.htm'> <FRAME src=`main.htm' NAME=`main'> </FRAMESET> </NOSCRIPT> <NOFRAMES> This Web site requires a frames-capable browser. </NOFRAMES> </HEAD> </HTML> 

The two linked JS files in default.htm are cookies.js and sniffer.js. We will discuss these scripts in detail a little later in the chapter. The first explicit script in default.htm is as follows:

 //----------------------------------------------------- // Make sure file is not hosted in a different frameset if ( top.location.href != window.location.href )   { top.location.href=window.location.href } 

The first two lines of code are comments that describe the purpose of this block. Though not strictly necessary for the code to function, they make it far easier to read the code and understand its purpose. We can see from the comment that this text is supposed to ensure that default.htm is not being displayed as part of another frameset. Designers of sites who want to protect content often use this technique. For example, a news agency might wish to ensure that their news stories are not being presented in the frameset of another company's Web site.

Next comes the code that performs this action. If the URL of the top frame in the window (defined by top.location.href) does not match the URL of default.htm (the location of the current window, defined by window.location.href), the top window is explicitly set to point to default.htm. You can test this functionality by launching default2.htm in the chap24 folder on the companion CD: it attempts to load default.htm in a child frame, but it cannot.

NOTE
The name default.htm is common for files on the World Wide Web. Many Web servers are set up such that if a Web page of a particular name (such as default.htm, default.asp, or index.htm) exists in a specific directory, and a user goes to a URL that ends in that directory name (for example, www.w3.org/Style), the Web page is automatically displayed. The particular filenames can normally be configured in the server software.

The next block of code in default.htm reads any information stored in a cookie previously written by this site. The conditional operator ?: is used to assign the values returned by the cookie to the variable sCstmStyle if the cookie isn't empty and the user has a version 4 or later browser. Otherwise, sCstmStyle is set to null. Next, the frameset for the site is created. It is created dynamically out of a series of strings and then written to the screen with document.write. Though this process is somewhat complex, it allows us to do some nifty things. One of the features designed into the site is that content pages loaded outside of the default.htm frameset will load the correct frameset and point the content frame to the correct content file. When this happens, the exact URL that is loaded is default.htm followed by a hash mark (#) and the URL of the page that was incorrectly loaded.

The code that dynamically writes the frameset takes any value passed after the hash mark and uses it in the SRC attribute of a <FRAME>. If no such value is passed, the code simply points the SRC attribute to main.htm and the default frameset is created.

One other notable technique found in the creation of the frameset is that the text that makes up the <FRAME> and <FRAMESET> tags is split up into two distinct strings. The browser will notice some HTML tags in the middle of strings and will try to render them immediately, usually causing an Unterminated String Constant error in Internet Explorer and a lack of content in Netscape Navigator. The most problematic tags for this are <SCRIPT>, </SCRIPT>, <HEAD>, </HEAD>, <BODY>, </BODY>, <HTML> and </HTML>. This problem can be solved simply by breaking up the tag into two separate strings that are not read as a tag until the string is written to the screen. <FRAME> and <FRAMESET> are typically not as problematic as the above listed tags.

At the bottom of default.htm are <NOSCRIPT> and <NOFRAMES> tags. These are provided to give a small amount of backward support to really early browsers. Browsers that do not support frames and scripting will display a notice that the page requires a frames-capable browser.

Next we will look at the two included JS files used by default.htm.

sniffer.js

The sniffer.js file is used for browser detection. It contains a small amount of simple script and creates two Boolean variables. The first, bVer4, is set to true if the browser version is greater than or equal to 4. The second, bDoesDHTML is set to true only if the browser is both Internet Explorer and version 4 or later. This second variable will be used later, in menu.htm, to determine whether the expanding menu should be created. The following snifffer.js file can be found as chap24\js\sniffer.js on the companion CD.

 //---------------------------- // This file creates a number of variables describing the browser. var bVer4 = ( parseInt(navigator.appVersion) >= 4 ) var bDoesDHTML = ( (navigator.userAgent.indexOf("MSIE") >= 0) && bVer4) 

cookies.js

The cookies.js file is more complex than sniffer.js. It contains two functions: SetCookie is used to write a cookie, while GetCookie is used to retrieve a cookie. This file is listed below and can be found as chap24\js\cookies.js on the companion CD.

 //---------------------------- // This JS file contains basic tools for cookie manipulation. function SetCookie(sName,sVal,sExpires,sDomain,sPath,bSecure) { //------------------------------------- // Set a cookie.   document.cookie = ( sName + "=" + escape(sVal) +      ( (sExpires) ? "; expires=" + sExpires : "" ) +      ( (sDomain) ? "; domain=" + sDomain : "" ) +      ( (sPath) ? "; path=" + sPath : "" ) +      ( (bSecure) ? "; secure" : "" )    ); } function GetCookie(sName){ //------------------------------------- // Traverse the cookie, looking for the passed cookie name. // If found, return the value, else return null.   var sDelimName   = ( sName + "=" );   var iNameLength  = sDelimName.length;   var iCookieLength= document.cookie.length;   var iNameStart = 0;   while (iNameStart < iCookieLength){     var iNameEnd = (iNameStart + iNameLength);     if (document.cookie.substring(iNameStart, iNameEnd) == sDelimName){       // If name found, get the associated value.       // (from iNameEnd  to next ; or end of cookie)       var iValueEnd = document.cookie.indexOf (";", iNameEnd);       if (iValueEnd == -1){ iValueEnd = document.cookie.length }       return unescape(document.cookie.substring(iNameEnd, iValueEnd));     }     iNameStart = ( document.cookie.indexOf(" ", iNameStart) + 1 );     if (iNameStart == 0) break;    }   return null; } 

The SetCookie function is fairly straightforward and is used by custom.htm. It takes six arguments, the first two of which (sName and sVal) are required. The arguments are used to set the parameters of the cookie: sName is the cookie name, sVal is the value, sExpires is the expiration date, sDomain and sPath are the domain and path, and bSecure determines whether the cookie is only accessible over a secure connection. Each variable that starts with s accepts a string, while bSecure takes a Boolean value. If an empty string or null is passed for any of the optional arguments, it is not used. The value of the cookie is encoded with the escape method to ensure that it does not contain any problematic characters.

The GetCookie function is somewhat more complex. It takes the name of the cookie to be retrieved as its only argument. Because a cookie is in fact just a long string, this function uses many string manipulation tools to accomplish its goal. It essentially steps through the cookie string character by character, looking for the name of the value it is supposed to retrieve. When it finds the name, it extracts the text that follows until it reaches the next semicolon (used to mark the end of a cookie name=value pair) or the end of file. This extracted text corresponds to the value of the cookie and is returned. If the name is never found, null is returned.

NOTE
Many cookie retrieval functions use the split method to break up the string returned by a cookie. This process is easier than the method found in cookies.js, but it is not supported in some early browsers, including Internet Explorer 3.

main.htm

The main.htm page is the home content page used on the Web site. It starts with two linked script files, frameit.js and custom.js. In addition, legal.js is used at the bottom of the Web page. The following main.htm file can be found as chap24\main.htm on the companion CD.

 <HTML> <HEAD> <LINK REL="STYLESHEET" TYPE="text/css" HREF="css/content.css"> <SCRIPT LANGUAGE="JavaScript" SRC="js/frameit.js"></SCRIPT> <SCRIPT LANGUAGE="JavaScript" SRC="js/custom.js"></SCRIPT> </HEAD> <BODY> <TABLE CELLSPACING="0" CELLPADDING="0">   <TR>     <TD ALIGN="CENTER">       <IMG SRC="img/book.jpg" WIDTH="104" HEIGHT="130"            ALT="Book Cover Image" BORDER="1" ALIGN="LEFT">       <H2>Dynamic HTML in Action, 2<SUP>nd</SUP> Edition</H2>       <FORM>       <SELECT onchange="var sVal=this.options[this.selectedIndex].value;                         if (sVal != `-'){window.location.href=sVal}                         else{this.selectedIndex=0;return false}">         <OPTION VALUE="-">Select a Destination         <OPTION VALUE="-">--------------------         <OPTION VALUE="../sitebuilder/default.htm">SBN Home         <OPTION VALUE="../workshop/default.htm">SBN Workshop         <OPTION VALUE="../Gallery/default.htm">SBN Gallery         <OPTION VALUE="../tools/">Tools         <OPTION VALUE="authors.htm">About the Authors         <OPTION VALUE="links.htm">Links         <OPTION VALUE="custom.htm">Customize       </SELECT>       </FORM>     </TD>   </TR>   <TR>     <TD>       <P>Welcome to the home page for       <I>Dynamic HTML in Action, 2<SUP>nd</SUP> Edition</I>.       <P>This site gives you access to many of the resources mentioned in       the book. From here you can view the electronic version of the       book, see the sample files for each chapter, get quick access to       some of the tools we discuss, view the Site Builder Network       Workshop, and even find out more about the authors! Click on an       item in the Table of Contents on the left and enjoy!     </TD>   </TR> </TABLE> <SCRIPT LANGUAGE="JavaScript" SRC="js/legal.js"></SCRIPT> </BODY> </HTML> 

One of the most interesting features of main.htm is the drop-down list box that can be used for navigation. When a user selects one of the items in the select box (other than the instructions at the top and the separator line), the page automatically navigates to the selected location.

All of this functionality is accomplished in the onchange event handler on the SELECT element. When one of the options is chosen, the value of that option is assigned to the sVal variable with the code sVal=this.options[this.selectedIndex].value. (See Chapter 23 for an explanation of this code.) If the user selects the separator line, the value of sVal will be set to a dash character (-) and the SELECT element is set to display the first item in the list with the code this.selectedIndex=0. Otherwise, the window navigates to the chosen item.

frameit.js

The frameit.js file is used by the content pages of the site. When any of the pages linking to frameit.js are loaded outside the context of the correct frameset, this script loads default.htm and passes to it the name of the file that was incorrectly loaded. There are many situations in which this can be useful. For example, a link returned by a search engine to a Web page will normally cause the page to be loaded in a window by itself. A script like frameit.js ensures the page is loaded in the proper context of our sample site's frameset. The following frameit.js file can be found as chap24\js\frameit.js on the companion CD.

 //--------------------------------------------------------------- // This script should be included in files destined for the main frame. // It ensures the file appears in the proper frameset if loaded by itself. sLoc=window.location.href; if (top.location.href==sLoc){   //-------------------------------------------------------------   // Retrieve file name only-NS3 does not allow "file://" in URL   iLastBack = sLoc.lastIndexOf(`\\');   iLastForw = sLoc.lastIndexOf(`/');   iLastSlash=( (iLastForw > iLastBack) ? iLastForw : iLastBack );   sFName = sLoc.substring(iLastSlash+1);   //-------------------------------------------------------------   // Navigate to default.htm and pass it the name of the current file.   top.location.href="default.htm#"+sFName; } 

The majority of the script is only activated if top.location.href is equal to window.location.href (which is only true when the current page is not contained in any frames). If this is the case, the script extracts the name of the current file from the current URL by taking everything after the last slash or backslash. The browser is then pointed to a new URL containing default.htm, a hash mark (#), and the name of the current content file found above. The hash mark is normally used to indicate a bookmark, but in this case it is used as a method of passing an argument to an HTML page. The content of the URL after the hash mark can be accessed with the location.hash property. A similar and useful property is location.search, which returns any text after a question mark in the URL.

legal.js

Many Web sites have components that are used on most or all of the pages in the site. One common example is a legal notice at the bottom of every page. The legal.js file is a simple file designed to make it easy to keep an up-to-date legal notice at the bottom of our sample site's content pages. You need to change only the text in legal.js whenever the copyright notice needs to be updated, instead of needing to change every page in the site. This technique is also useful for including other shared content, such as a navigation bar or advertising banner. One additional advantage of this technique is that the JS file will be cached on the client and downloaded only when there is an update. Because the data does not have to be re-downloaded with every page, the result is a faster-performing Web site, especially if there is a fairly large amount of content replicated on every page. The following legal.js file can be found as chap24\js\legal.js on the companion CD.

 //---------------------------- // This file writes a copyright notice to the page. sCpy=("<P><FONT SIZE=`-1'>"+       "&#169;1999  Eric Schurman and Bill Pardi. All rights reserved."+       "</FONT>") document.write(sCpy) 

NOTE
This goal of including common content is often accomplished on the server instead of the client with server-side includes. Most Web servers support a technology in which a link can be made from within a Web page that points to a second file on the server. This second file is then incorporated into the first at the location of the link. The advantage of this technique is that it does not require any scripting on the client—only standard HTML is sent to the browser.

menu.htm

The menu.htm page provides the navigation for the Web site. Let's look at the code used in this page. This code can be found in the file chap24\menu.htm on the companion CD.

 <HTML> <HEAD> <LINK REL="STYLESHEET" TYPE="text/css" HREF="css/menu.css"> <TITLE>Menu</TITLE> <SCRIPT LANGUAGE="JavaScript"> //---------------------------------------------- // If loaded by itself, load default.htm instead. if (top.location.href == window.location.href)   { top.location.href="default.htm" } </SCRIPT> <SCRIPT LANGUAGE="JavaScript" SRC="js/sniffer.js"></SCRIPT> <SCRIPT LANGUAGE="JavaScript"><!-- //----------------------------------------------- // If browser supports this type of DHTML, hide menu items, do mouseover // style effects and images, and and make the expanding menus. if(bDoesDHTML){   sStyle=(".off{display:none} .on{display:block}" +           "a:link {text-decoration:none}" +           "a:visited {text-decoration:none}" +           "a:hover {text-decoration:underline; color:red}" +           "a:active {text-decoration:underline; color:red}")   document.write("<STYLE>"+sStyle+"</STYLE>");   window.onload=Function("MakeExpanding()"); } function MakeExpanding(){   //--------------------------------------   // Add click handler to all items of class L1.   var oDA=document.all;   for (i in oDA){     if (oDA[i].className=="L1"){       oDA[i].onclick=Function("ToggleMenu(this)");       oDA[i].href="javascript:;"     }   } } function ToggleMenu(oHead){   var oAll=document.all;   iIndex=oHead.sourceIndex;   if (oAll(iIndex+4).className=="off"){     oAll(iIndex).src="img/open.gif";     oAll(iIndex+4).className="on";   }   else {     oAll(iIndex).src="img/closed.gif";     oAll(iIndex+4).className="off";   } } //--> </SCRIPT> </HEAD> <BODY LEFTMARGIN="0" TOPMARGIN="0" TEXT="black" BGCOLOR="#CCCCFF"> <CENTER><FONT SIZE="+3"><B>TOC</B></FONT></CENTER> <TABLE CELLSPACING="0" CELLPADDING="0">   <TR><TD><img src="/books/3/39/1/html/2/images/grayvellip.jpg" width=3 height=13 border=0quot;1"></TD>     <TD>      <BR><A HREF="main.htm" TARGET="main"><B>Home</B></A>      <BR><A HREF="authors.htm" TARGET="main"><B>About the Authors</B></A>      <BR><A HREF="links.htm" TARGET="main"><B>Useful Links</B></A>      <BR><A HREF="../tools/" TARGET="main"><B>Tools</B></A>      <BR><A HREF="custom.htm" TARGET="main"><B>Customize</B></A>       </TD>   </TR> </TABLE> <A CLASS="L1" TITLE="Site Builder Network" TARGET="main"> <img src="/books/3/39/1/html/2/images/grayvellip.jpg" width=3 height=13 border=0"9" BORDER="0" ><B>Site Builder Network</B></A><BR> <TABLE CELLPADDING="0" CLASS="off">   <TR><TD><img src="/books/3/39/1/html/2/images/grayvellip.jpg" width=3 height=13 border=0"1"></TD>       <TD>         <FONT SIZE="-1">         <A HREF="../SiteBuilder/default.htm" TARGET="main">Home</A><BR>         <A HREF="../workshop/default.htm" TARGET="main">Workshop</A><BR>         <A HREF="../Gallery/default.htm" TARGET="main">Gallery</A><BR>         </FONT>     </TD>   </TR> </TABLE> <A CLASS="L1" TITLE="Access to each chapter's files" TARGET="main"> <img src="/books/3/39/1/html/2/images/grayvellip.jpg" width=3 height=13 border=0"9" BORDER="0" ><B>Code Listings</B></A><BR> <TABLE CELLPADDING="0" CLASS="off">   <TR><TD><img src="/books/3/39/1/html/2/images/grayvellip.jpg" width=3 height=13 border=0"1"></TD>       <TD>         <FONT SIZE="-1">         <A HREF="../chap01/" TARGET="main">Chapter 1</A><BR>         <A HREF="../chap02/" TARGET="main">Chapter 2</A><BR>                  <A HREF="../chap23/" TARGET="main">Chapter 23</A><BR>         <A HREF="../chap24/" TARGET="main">Chapter 24</A><BR>         </FONT>     </TD>   </TR> </TABLE> </BODY> </HTML> 

NOTE
All of the links in this site are either absolute (specifying the entire URL) or relative (specifying a location relative to the current Web page). If these pages had been hosted on an actual Web server, we would have used a variation of absolute links to point to files on the site. It is possible to specify a directory off the root of a particular Web site simply by prefacing the directory name with a forward slash. Thus, an anchor on any page on the microsoft.com Web site can refer to a file found at microsoft.com/ie/ie.htm simply by using the code HREF="/ie/ie.htm". Another example is that any page at any directory level can refer to a file named main.css in a css directory off the root of the site by using the path /css/main.css. The same option can be used by SCRIPT blocks to link to JS files. One key advantage of this is that an HTM file can be moved to any directory and these links will not break. (We did not use this technique in this chapter because it does not work on a CD in Netscape Navigator.) In addition, most Web server software will let virtual roots or virtual directories be created. These are directories at any level of the directory tree that are treated as though they lived off the root of the current Web server. These directories can be accessed using the method described above.

Because menu.htm is not terribly useful by itself, the first block of script in the file simply ensures that the file is loaded in the correct frameset. Next, sniffer.js is loaded and a test is performed to check if the browser supports the necessary functionality for the expandable menu. If it does, two things happen.

First a new style sheet is written to the page. This style sheet contains the .on and .off classes that are used to make menu items display and disappear. Note that the tables containing second level menu items have the .off class. When this style sheet is written to the page, the second-level menu items are not displayed as the page loads. If the style sheet is not written to the page, the tables are displayed normally. The style sheet also contains rules that prevent an anchor from being underlined until the mouse moves over it, at which time they are underlined and highlighted.

Next the line window.onload=Function("MakeExpanding()"); causes the MakeExpanding function to be called when the window finishes loading. This function completes preparation for the expanding menus. Note that the normal HTML on the page does not have event handlers or any code to cause the expanding menus to function. The MakeExpanding function adds the necessary code to the page. It accomplishes this by iterating through the all collection and checking every element on the page. If an element has the class L1 (as do the anchors surrounding the level one headings), it is assigned an event handler that causes it to call the ToggleMenu function when clicked. It is also assigned an HREF attribute of javascript:;. If an anchor does not have an HREF attribute, it appears like normal text—not underlined and not clickable. Giving it an HREF attribute makes it clickable. However, we don't want a click on the anchor to cause the browser to navigate away from the current page, so we use an HREF that causes the page to do nothing. When an HREF contains a value that begins with http: the browser navigates to the specified location. When it contains a value starting with javascript: the browser executes the code that follows. Thus, the anchor <A HREF="javascript:alert(`hi')">Show alert</A> would cause an Alert dialog box to appear containing the text hi. This functionality is supported in version 3.02 and later of Internet Explorer and version 3 and later of Netscape. The semicolon in JavaScript is a command that essentially means "do nothing." Therefore, the HREF javascript:; causes the anchor to be clickable, but does not tell it to do anything when clicked. The MakeExpanding function adds an onclick event handler that actually handles calling the ToggleMenu function to expand and collapse the menu. The ToggleMenu function toggles the expanding items open and closed and changes the arrow image to point down or point right. It accepts one parameter—the anchor that was clicked—and it determines the index of the item in the all collection. The image to be changed and the table to be displayed or hidden are always a set number of items after this index. They are accessed through the all collection, and the menu item is toggled on or off depending on the current state.

One other notable technique in menu.htm is that some of the HTML tags are broken up so that the ending > character is on the following line, immediately preceding the < character of the next tag. If a line break or a space separates either two tags within an anchor or the contents of an anchor from the opening <A> tag, an underlined extra space is visible. On a normal Web page, we would probably have simply put both tags on the same line, but this was not an option because of line length limits in this book. In any case, breaking a tag across multiple lines is a fairly common technique.

custom.htm

The custom.htm file allows the user to customize the appearance of some pages on the site. The changes can then be saved as a cookie to the user's system and retained for future use. This file can be found as chap24\custom.htm on the companion CD, and the page is shown in Figure 24-2.

 <HTML> <HEAD> <LINK REL="STYLESHEET" TYPE="text/css" HREF="/chap24/css/content.css"> <SCRIPT LANGUAGE="JavaScript" SRC="js/frameit.js"></SCRIPT> <SCRIPT LANGUAGE="JavaScript" SRC="js/custom.js"></SCRIPT> <SCRIPT LANGUAGE="JavaScript" SRC="js/sniffer.js"></SCRIPT> <SCRIPT LANGUAGE="JavaScript"> <!-- var sFontFamly = "body,td{font-family:arial;} " var sFontColor = "body,td{color:black;} " var sBackColor = "body,td{background-color:white;} " function Commit(){    if (bVer4){     //------------------------------     // Check to make sure style choices OK, then save.     if ( sFontColor.substr(sFontColor.lastIndexOf(":") ) ==          sBackColor.substr(sBackColor.lastIndexOf(":") ) ){       alert("Please make sure the font and background colors differ.")     }     else{       top.sCstmStyle=(sFontFamly+sFontColor+sBackColor);       top.SetCookie("CstmStyle",top.sCstmStyle,                     "Fri, 31 Dec 2010 23:59:59 UTC","","","");       location.reload();     }   }   else{alert("These features require a version 4 or later browser.")} } function Select(oWhich, oItem){   //------------------------------   // If a legitimate item (not with value -) is selected, assign its   // value to the variable passed as oWhich.   var sItem = oItem.options[oItem.selectedIndex].value;   if (sItem != `-'){ eval(oWhich+"=sItem") }   else{ oItem.selectedIndex=0;return false } } //--> </SCRIPT> </HEAD> <BODY BGCOLOR="White" TEXT="Black"> <H1>Personalization</H1> <P>This page allows users of version 4 and later browsers to personalize the look and feel of many of the pages in this site. Information about any changes made is stored in cookies. <FORM> <BR>Select a Font <SELECT ONCHANGE="Select(`sFontFamly',this)">   <OPTION VALUE="body,td{font-family:arial;} ">Arial   <OPTION VALUE="body,td{font-family:times;} ">Times   <OPTION VALUE="body,td{font-family:courier;} ">Courier </SELECT> <BR>Select a Font Color <SELECT ONCHANGE="Select(`sFontColor',this)">   <OPTION VALUE="body,td{color:black;} ">Black   <OPTION VALUE="body,td{color:blue;} ">Blue   <OPTION VALUE="body,td{color:red;} ">Red   <OPTION VALUE="body,td{color:white;} ">White </SELECT> <BR>Select a Background Color <SELECT ONCHANGE="Select(`sBackColor',this)">   <OPTION VALUE="body,td{background-color:white;} ">White   <OPTION VALUE="body,td{background-color:blue;} ">Blue   <OPTION VALUE="body,td{background-color:red;} ">Red   <OPTION VALUE="body,td{background-color:black;} ">Black </SELECT> <BR><INPUT TYPE="BUTTON" VALUE="Commit Changes"            onclick="Commit()"> <BR><INPUT TYPE="BUTTON" VALUE="Reset to Default"            onclick="top.sCstmStyle=``;location.reload()"> </FORM> <SCRIPT LANGUAGE="JavaScript" SRC="js/legal.js"></SCRIPT> </BODY> </HTML> 

click to view at full size.

Figure 24-2. This page allows customization by the user.

When the user selects an option from one of the drop-down lists, the chosen value is saved to either the sFontFamly, sFontColor, or sBackColor variable. When the Commit Changes button is clicked, the Commit function is run. This function first checks to see whether the chosen background and font colors conflict. If they do not, the chosen options are saved in a variable in the top frame and to a cookie. The page is then refreshed. The variables in the top frame are referenced by prefixing the variable with top. Other frames could have been referenced by substituting the name of the frame for top. The name of the frame can be set by the NAME attribute in a <FRAME> tag. The keyword parent is used to refer to the parent of the current frameset, which in this case would have been the same as top.

The cookie is set by calling the SetCookie function, which was loaded in the top frame. Note that one of the parameters for SetCookie is an explicit date that follows the Universal Coordinated Time (UTC) format. To guarantee that you have a UTC-compliant date, use a JavaScript DATE object and the getUTCDate method.

custom.js

The custom.js file is a very simple file used by the content pages. It checks to see whether any custom style has been specified and if so, writes a style sheet to the page. You can find this file as chap24\js\custom.js on the companion CD.

 //---------------------------- // Write any custom style sheet specified by user. if ( top.sCstmStyle != null ) {   document.write("<STYLE>"+top.sCstmStyle+"</STYLE>") } 

authors.htm and links.htm

These are very simple content pages that have no special features. They contain HTML as well as links to frameit.js, custom.js, and legal.js.

Well, that's it. If you made it all the way through the book, you should have a pretty solid idea of how to work with many of the most popular technologies found on the Web. Browsers, the Web, and the Internet as a whole are a tremendously exciting area, from the perspectives of both users and programmers. The future promises to be at least as exciting as the past, given the increasing globalization of the Web, the spread of corporate intranets, the growing availability of high-speed connections from home, and the constantly changing set of available tools and technologies. Whether your interest is as simple as creating a personal home page or as complex as creating a full-blown, database-driven, intranet Web site, Web page development should be a fun and rewarding endeavor.



Dynamic HTML in Action
Dynamic HTML in Action
ISBN: 0735605637
EAN: 2147483647
Year: 1999
Pages: 128
Authors: Eric M Schurman, William J Pardi
BUY ON AMAZON

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net