Making a Browser Window Fit an Image
I received an e-mail from a reader who had a simple question. He
had read my tutorials about opening a web page in a new window and
wanted to know if he could do the same to open an image in its own
window when the viewer clicked a thumbnail of the image.
He had already discovered that linking a thumbnail to an image
file opens the image in a full-sized window when the link is
clicked, just like navigating to a new page. Like this (you'll need
to use your [Back] button to come back)...
 

... but he wanted the image to open in a pop-up window of its
own, just like a pop-up page in my tutorial
Creating a New Window with
Javascript. He wanted the pop-up window to fit the image and all
his images were the same size. There was a gallery of thumbnail
images, and the idea was that the viewer would click on one of the
thumbnails to see the full-sized image appear in a small window of
its own. They would still be able to see the original window showing
the gallery behind,
so they could click on another thumbnail to change the image in the
small window.
The answer to his question was "yes" and I though I'd help out by writing a
sample of the necessary code. I've used my own images here, and
their full-size is 250 x 375 pixels. Here's the code for each
thumbnail (I've simplified the code a bit, and split the line to fit
on this page)... <img src="thumbnail.jpg" style=cursor:hand onClick=javascript:window.open(
'fullsize.jpg','blank','toolbar=no,width=250,height=375')>
Here's how it works...

Did it work OK for you? Well, that depends on what you did. I
found two problems...
Where Did the Window Go?
The code I used above is not hyperlink code. There are no <a href></a>
tags. Instead I added a self-contained JavaScript onClick
event. The procedure opens a new window of a specific size
(250x375) displaying the full-sized image. The window's name is
'blank' (because it has to have a name of some sort and it's usual
to call it 'blank' in these circumstances). I also added a style=cursor:hand
statement to change the user's mouse pointer so that it would look
like a hyperlink when the user pointed at it. This worked fine but it's not good
enough! If you click on the first thumbnail and view the full-sized
image, then close the small window before clicking on the
second thumbnail, everything works OK. But if you leave the small
window open and click on the second thumbnail, the small window
disappears! Actually, it doesn't disappear, but it seems to do so
because the act of clicking on another thumbnail brings the main
window to the front. The image in the small window does change
but it is now behind the main window and you can't see it. A minor
inconvenience, perhaps, but not good enough for me! And that isn't
all that's wrong... Why is the Image Off-Centre?
Did you notice that the border around the image is uneven? There
is a broad white border on the top and left sides, and a no border
on the bottom and right sides. How can that be... I specified in my
code the exact dimensions of the full-sized image. What has gone
wrong? The answer is simple. Browsers display their contents with
a standard top and left margin. Internet Explorer uses a top margin
of 15 pixels and a left margin of 10 pixels. On a page of text this
would go unnoticed, and the author could change the margin sizes
with a modification to the <body> tag. When an image alone is
displayed, it is offset by the standard border dimensions. My images
have been pushed 10 pixels across and 15 pixels down so that they
are not sitting in the centre of the window. Because each image
being displayed on its own and not on a page I can't give an
instruction to change the margins. One approach would be to increase
the size of the window so that the image at least appeared to be in
the centre, like this...

All I did was add 20 pixels to the width and 30 pixels to the height
of the window... <img src="thumbnail.jpg" style=cursor:hand onClick=javascript:window.open(
'fullsize.jpg','blank','toolbar=no,width=270,height=405')>
It looks OK but it's bugging me! Anyway, I haven't fixed the
disappearing window phenomenon. I need to think again... Is
There a Fix?
I have two problems: The small window should come to the
front when its contents change.
With JavaScript I can set the focus to the small window,
but I can't incorporate that into the embedded JavaScript that I
used to create the window. I would be able to do it if I used a
JavaScript function instead. I need to get rid of the browser's
margin.
The browser's margin setting is controlled by HTML inside the
<body> tag, so I need to display the image on a page. But I don't
want to create a separate page for each image. I can use JavaScript
to build a page on the fly, creating a temporary page on
which to display the image. To do this I would need to use a
JavaScript function. JavaScript Functions to the Rescue!
The first job was to write a function that would create a new
page displaying a specific image, then open the page in a new window
of a specific size, giving it the focus (i.e. making sure it is at
the front). This function could be "called" (i.e. made to run) when
the user clicked the thumbnail image. Here's the function I came up
with... <script language=javascript type="text/javascript">
<!--
function ShowMe(picURL){
newWindow=window.open('picURL','newWin','toolbar=no,width=250,height=375')
newWindow.document.write('<html><head><\/head><body topmargin="0"
leftmargin="0"><img src="'+picURL+'"><\/body><\/html>')
newWindow.focus()
}
//-->
</script>
I called the function ShowMe() and defined a single
argument (an argument is a variable bit of data that the function
needs) called picURL which represented the name and location
of the full-sized image file to be displayed.
The first statement in the function (newWindow=window.open(...
) creates a variable (newWindow) to which is applied the
JavaScript window.open object. This object causes a new
browser window to be opened according to the supplied parameters of
URL, name and attributes. For the moment the
URL is picURL (because it has to be something!); the Name is
newWin; the Attributes specify no toolbars and the size in
pixels of the fill-sized images.
The second statement (newWindow.document.write(... )
creates an HTML page in the window. It's a fairly simple page
containing just the <html>, <head> and <body> tags. The body tag
sets the margins to "0" to get rid of the unwanted white border. The
page content is a single <img> tag whose source is supplied by the
content of the argument picURL. [NOTE: I have broken this
long line for the purposes of showing it on this page. It should be
written as a single line.]
The final statement (newWindow.focus() ) simply gives the
focus to the window to make sure it it on top and visible to the
user.
All that remains is to arrange for the function to be called when
the user clicks on the picture. This can be done by specifying the
function, rather than a file, in the link tag:
<a href="javascript:ShowMe('fullsize1.jpg')"><img src="thumbnail1.jpg"></a>
<a href="javascript:ShowMe('fullsize2.jpg')"><img src="thumbnail2.jpg"></a>
<a href="javascript:ShowMe('fullsize3.jpg')"><img src="thumbnail3.jpg"></a>
For each image the URL of the full-size image is supplied as the
function's argument so, depending on which thumbnail is clicked, the
function created a new page displaying the correct full-sized image.
Try it out...
Adding a Title
The images I used here are of some friends of mine. Trevor
(who left us to live in cat heaven recently), Fatty (quite keen on
computers and seen here guarding some mice) and Woody (who lives
next-door but likes visiting). In my quest for perfection I
decided would like to add labels to the
full-sized images. When a browser displays an image on its own
there isn't the opportunity to add a caption, and the window's title
bar shows only the file path. But since I was displaying each image
on a web page of its own, I reckoned I could add modify my JavaScript function to
add a title to the window and some alternative text to the image.
I needed two more arguments. I already had picURL which tells
the page where to find the image. I added picTitle
for the page title and picText for the alternative text.
I wrote a new function that I called ShowMeMore. Here's the
code...
<script language=javascript type="text/javascript">
<!--
function ShowMeMore(picURL,picTitle,picText){
newWindow=window.open(picURL,'newWin','toolbar=no,width=250,height=375')
newWindow.document.write('<html><title>'+picTitle+'<\/title><head><\/head>
<body topmargin="0" leftmargin="0"><img src="'+picURL+'"
alt="'+picText+'"><\/body><\/html>')
newWindow.focus()
}
//-->
</script>
You can see that the function requires three arguments (picURL,
picTitle and picText) which are used to build the page
in the newWindow.document.write statement (NOTE: this line of
code has been split to fit on this page - it should be written as a
single line).
The function is called in the same way as before, this time
specifying the three arguments for each image...
<a href="javascript:ShowMeMore('trevor.jpg','Trevor','Trevor being a kitten'
)"><img border="0" src="trevor_sm.jpg"></a>
Try it out with this last set of thumbnails...
You can see the how the hyperlink calls the JavaScript function and
passes the arguments to it by pointing at each thumbnail in turn and
looking at the text shown in the status bar in the lower left corner
of the browser window.

And the Moral of the Story is...
This story found its way into my casebook because it started out as
a simple question that turned into a problem. The problem turned
into a quest for perfection, and when I fixed all the things that
needed fixing I realised that I had learnt a whole lot of things
that I hadn't realised I didn't know!
I left out the bit about the half-hour I spent trying to find out
why my function suddenly stopped working - only to find that I had
accidentally duplicated a bracket when pasting some code.
And I didn't mention that I resorted to trial-and-error to get the
right combination of double and single quotes in the code, when my
theory for what needed quotes and what didn't proved incorrect.
Nor did I mention my big smile of satisfaction when I clicked the
link and everything worked just the way I wanted it to!
Further Reading
If you want to know more about controlling browser windows, look at
these tutorials:
|