Articles | Dynamic Style
Sheets | back
Introduction
With the advent of Dynamic HTML, we have been able to
do a lot more with our scripts. Everything on the page becomes an object to be
manipulated. In this article, you will learn how to change a page's style sheet
on the fly.
Why would you want to do this? Well, you might be very
good at writing content but not so hot when it comes to page design - you could
give the user a choice of stylesheets and let him use the one he likes best. Or
your site might be part of several Web rings, so you might want a different
style depending on where the user was coming from.
For the purpose of this article, we'll use the first
example. We'll create a "Customize" page which enables the user to
browse through all the styles. He can then select the one he wants by pressing a
button. Why is this button necessary, you might ask. Well, most Web sites are
made up of more than one page, and so the other pages on the site will also need
to know which stylesheet to use. Pressing a button could store the choice in a
cookie which can be read by the other pages. This also ensures that the site
displays the user's preferred style the next time he visits.
At the moment the only browsers that support Cascading
Style Sheets are Microsoft Internet Explorer version 3 (very limited support -
does not support document.styleSheets), Microsoft Internet Explorer 4, and
Netscape Navigator version 4. Although there are differences in the two version
4 implementations. The major being is that the Document Object Model in Explorer
allows control over the documents style sheet through the new object styleSheet.
This allows the various styles to be altered without the page being reloaded.
To overcome the lack of this feature in Navigator we
will use Layers. We can use Layers in Navigator to show or hide parts of a
document. We can also use Layers to show the contents of another document in the
current document. It is this second feature of Layers that will be used in this
article.
Constructing the HTML
To avoid any of the HTML being shown in browsers that
do not support the features required by this Dynamic StyleSheet tool, we will
output all the necessary HTML using JavaScript. This allows us to control when
and where the HTML is shown.
The following JavaScript outputs the controls used in
the working example. Don't worry too much about the contents, accept to see that
firstly it will only be used in JavaScript 1.2 enabled browsers,
secondly it tests for the existence of either the document.styleSheets
or the document.layers objects.
The document.styleSheets object was introduced
in Explorer version 4, as a means to access any and all of the style sheets in
the current document. The document.layers object was introduced in
Navigator version 4 along with Layers. Rather than detect what browser is being
used, we detect what functionality the browser supports.
If the browser supports document.styleSheets
then we only need to output some sample HTML, if the browser does not support document.styleSheets
but supports document.layers then rather than output some sample HTML,
we need to include several versions of the same HTML using either <LAYER>
or <ILAYER>.
The document.styleSheets object allows dynamic
alteration of various styles without the need to reload the document. If we
simply used plain sample HTML when using Navigator we would need to reload the
page each time a style changed to see the effect. With the aid of layers we can
preload different verions of the HTML each with the required style already set.
When we need to show one style over another we simply hide all the previous
Layers, and reshow the required Layer.
When using the <LAYER> and </LAYER>
tags, the contents are not inline with the rest of the document, i.e. they can
be overlapped with other HTML elements. To reserve space in the document for a
Layer we need to use the alternative inline Layer <ILAYER> and </ILAYER>
tags.
When we want to show more than one Layer in a
particular spot of a document, but where we wish to swap between other hidden
Layers, only one of the Layers, the last, should use the alternative inline
Layer tags.
<HEAD>
<TITLE>Customise page</TITLE>
<SCRIPT LANGUAGE="JavaScript1.2" SRC="library.js"></SCRIPT>
</HEAD>
<BODY>
<SCRIPT LANGUAGE="JavaScript1.2"><!--
if (document.styleSheets || document.layers) {
document.write('<P>Please browse available styles using
the box below, and confirm your choice by pressing the
OK button.');
document.write('<FORM>');
document.write('<SELECT NAME="style" onChange=
"changeSheet(this.selectedIndex)">');
document.write('<OPTION>Style 1<\/OPTION>');
document.write('<OPTION>Style 2<\/OPTION>');
document.write('<OPTION>Style 3<\/OPTION>');
document.write('<\/SELECT>');
document.write('<INPUT TYPE="BUTTON" VALUE="OK"
onClick="Set_Cookie(\'stylesheet\',mySheet,expires)">');
document.write('<\/FORM>');
if (document.styleSheets) {
document.write('<H1>Headings will appear like this.<\/H1>');
document.write('<P><A HREF="javascript:alert
(\'just testing\')">Links will appear like this.<\/A>');
document.write('<P><CODE>Any quoted code will appear like this.
<\/CODE><BR>');
}
else if (document.layers) {
document.write('<LAYER SRC="style1.htm" NAME="style1"
VISIBILITY="show"><\/LAYER>');
document.write('<LAYER SRC="style2.htm" NAME="style2"
VISIBILITY="hide"><\/LAYER>');
document.write('<ILAYER SRC="style3.htm" NAME="style3"
VISIBILITY="hide"><\/ILAYER>');
}
checkStyle();
}
//--></SCRIPT>
</BODY>
</HTML>
|
Now that's out of the way, we can look at the form
being generated in the above code. The selectedIndex property of the selection
box returns a number between 0 and 2 (because there are 3 options). Therefore we
pass a value corresponding to the selected option to the changeSheet()
function. When the OK button is clicked the Set_Cookie()
function is called to store a cookie with the details of the selected Style
Sheet. The function is passed the name of the cookie to be stored stylesheet,
the value of the cookie held in mySheet and the date it will expire
held in expires - all detailed later.
In the above code each of the three layers has a SRC,
NAME and VISIBILITY attribute. The SRC attribute
loads the file reference as the contents of the Layer, the NAME
attribute enables us to refer to the Layer using JavaScript, the VISIBILITY
attribute controls where the Layer is hidden ('hide') or visible ('show').
The code above also loads a JavaScript source file library.js
which contains the source code of all the JavaScript functions referred to in
the code.
The JavaScript Functions
Using a JavaScript Source file enables us to keep all
the JavaScript needed to support the Dynamic Style Sheets in one single file. We
can then include a reference to it in all are other web pages. The contents of library.js
is described below.
First, we'll need some code to read and write the
cookie.
The two cookie functions Get_Cookie() and Set_Cookie()
are as described in the Chocolate Chip
Cookies article.
function Get_Cookie(name) {
var start = document.cookie.indexOf(name+"=");
var len = start+name.length+1;
if ((!start) && (name != document.cookie.substring
(0,name.length))) return null;
if (start == -1) return null;
var end = document.cookie.indexOf(";",len);
if (end == -1) end = document.cookie.length;
return unescape(document.cookie.substring(len,end));
}
function Set_Cookie(name,value,expires,path,domain,secure) {
document.cookie = name + "=" +escape(value) +
( (expires) ? ";expires=" + expires.toGMTString() : "") +
( (path) ? ";path=" + path : "") +
( (domain) ? ";domain=" + domain : "") +
( (secure) ? ";secure" : "");
}
|
The expiration date of our cookie is set to the value
of the expires variable, which is set to 365 days from now:
var expires = new Date();
expires.setTime(expires.getTime() + (365 * 24 * 60 * 60 * 1000 * 365));
|
Here is that global definition of the mySheet
variable. It originally holds the value of the stylesheet cookie.
mySheet = Get_Cookie('stylesheet');
if (mySheet != null)
document.write('<LINK REL="stylesheet" HREF="' + mySheet + '.css">');
else
document.write('<LINK REL="stylesheet" HREF="style1.css">');
|
Very simply, this runs the Get_Cookie()
function (using the cookie called 'stylesheet'). If the results of that
function are not equal to null, i.e. they are equal to something and
therefore the cookie exists, then a Style Sheet is loaded based on the value of
the 'stylesheet' cookie, otherwise the style1.css style sheet is loaded
by default.
The following checkStyle() function determines
which style is supposed to be shown based on the value of the mySheet
variable. If it is null, then the Style Sheet is left alone. For
browsers that support the document.styleSheets we change the href
of the documents first styleSheets object, using either style1.css or
style2.css or style3.css. For browsers that support the documents.layers
all the Layers are first hidden, then the required Layer is shown.
function checkStyle() {
if (mySheet != null) {
if (document.styleSheets)
document.styleSheets[0].href = mySheet + '.css';
else if (document.layers) {
document.layers['style1'].visibility = 'hide';
document.layers['style2'].visibility = 'hide';
document.layers['style3'].visibility = 'hide';
document.layers[mySheet].visibility = 'show';
}
}
}
|
The purpose of the following changeSheet()
function is to check what the user has selected in the selection box, and then
change the documents styleSheet . This means we need to take the currently
selected value of the selection box as a parameter (this.selectedIndex
because we are referring to it from inside its HTML code). The function also
sets the value of the global variable mySheet so that when the cookie
is written, it saves the details of the current Style Sheet being shown.
function changeSheet(choice) {
if (choice == 0) mySheet = 'style1';
if (choice == 1) mySheet = 'style2';
if (choice == 2) mySheet = 'style3';
if (document.styleSheets)
document.styleSheets[0].href = mySheet + '.css';
else if (document.layers) {
document.layers['style1'].visibility = 'hide';
document.layers['style2'].visibility = 'hide';
document.layers['style3'].visibility = 'hide';
document.layers[mySheet].visibility = 'show';
}
}
|
Test HTML
Well we've described the selection page and the
JavaScript source code, but how do we use it on our other pages.
Simple, all we need to do is add a reference to the
JavaScript source file library.js as in the following HTML:
<HTML>
<HEAD>
<TITLE>Test page</TITLE>
<SCRIPT LANGUAGE="JavaScript1.2" SRC="library.js"></SCRIPT>
</HEAD>
<BODY>
<H1>This is the test page</H1>
<P>Return to the <A HREF="custom.htm">custom page</A>
or return to the <A HREF="index.htm">article</A>
<P><CODE>"Too many cooks spoil the broth"</CODE><BR>
</BODY>
</HTML>
|
Source Code
You can view the source code of the HTML components:
You can view the source code of JavaScript source file:
You can also view the source code of CSS files:
Working Example
Click here for
a working example of the source code.
Conclusion
Dynamic Style Sheets can give us many new ideas to jazz
up our Web sites. As well as what I've done in this article, you could have a
different style every day of the week, or you could change the contents of
individual STYLE tags on your page to alter only certain areas. There are
countless possibilities.
Articles | Dynamic Style
Sheets |
back
|