
/*
 * Copyright (c) 1998 Kevan Stannard. All Rights Reserved.
 *
 * Permission to use, copy, modify, and distribute this software
 * and its documentation for NON-COMMERCIAL or COMMERCIAL purposes and
 * without fee is hereby granted. 
 * 
 * Please note that this software comes with
 * NO WARRANTY 
 *
 * BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED
 * BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
 * PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
 * TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME
 * THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 
 * 
 * IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER
 * PARTY WHO MAY MODIFY AND/OR REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
 * INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE
 * THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED
 * BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER
 * OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
 */

/*
 * Updates:
 * 28 April 1998
 * Modified to support frame links
 */

import java.applet.*;
import java.awt.*;
import java.net.*;

public class JZOOScrollingImages extends Applet implements Runnable
{
	// constants

	final int MAX_IMAGES = 100;

	// image data

	Image image[] = new Image[MAX_IMAGES];
	int imagex[] = new int[MAX_IMAGES];
	int imagey[] = new int[MAX_IMAGES];
	String imageName[] = new String[MAX_IMAGES];
	String imageLink[] = new String[MAX_IMAGES];
	String imageTarget[] = new String[MAX_IMAGES];
	int numImages = 0;

	// thread data

	Thread thread = null;

	// double buffer

	Image db;
	Graphics dbGraphics;

	// applet

	int appletWidth = 0;
	int appletHeight = 0;

	// status

	final int OK = 0;
	final int LOADING_IMAGES = 1;

	int status = -1;

	//  other

	boolean mouseOver = false;
	int mousex = 0;
	int mousey = 0;
	int imageFocus;

	boolean updateStatusBar = false;

	int firstImage = 0;
	int offset = 0;
	int speed = 1;

	String imageLoadString;

	public void init()
	{
		// get applet parameters

		appletWidth = Integer.valueOf(getParameter("width")).intValue();
		appletHeight = Integer.valueOf(getParameter("height")).intValue();

		// get other parameters

		imageLoadString = getParameter("imageLoadString");
		if (imageLoadString == null)
		{
			imageLoadString = "Loading Images ...";
		}

		String speedString = getParameter("speed");
		if (speedString == null)
		{
			speed = 1;
		}
		else
		{
			speed = Integer.valueOf(speedString).intValue();
		}

		for (int i=0; i<MAX_IMAGES; i++)
		{
			imageName[i]   = getParameter("image" + (i+1));
			imageLink[i]   = getParameter("link" + (i+1));
			imageTarget[i] = getParameter("target" + (i+1));

                        System.out.println(imageName[i]);
                        System.out.println(imageLink[i]);
                        System.out.println(imageTarget[i]);
                        System.out.println("---");

			if (imageName[i]==null || imageLink[i]==null)
			{
				break;
			}
			numImages++;
		}

		// allocate space for double buffer

		db = createImage(appletWidth, appletHeight);
		dbGraphics = db.getGraphics();
	}

	public void start()
	{
		if (thread == null)
		{
			thread = new Thread(this);
			thread.start();
		}

	}

	public void stop()
	{
		if (thread != null)
		{
			thread.stop();
			thread = null;
		}
	}

	public void update(Graphics g)
	{
		paint(dbGraphics);
		g.drawImage(db,0,0,null);
	}

	public void paint(Graphics g)
	{
		clearScreen(g);
		updateDisplay(g);
	}

	private void clearScreen(Graphics g)
	{
		g.setColor(Color.black);
		g.fillRect(0,0,appletWidth,appletHeight);
	}

	private void updateDisplay(Graphics g)
	{
		if (status == OK)
		{
			int xpos = 0;
			int ypos = 0;
			int currImage = firstImage;
			while (xpos-offset < appletWidth)
			{
				ypos = (appletHeight - image[currImage].getHeight(this))/2;
				g.drawImage(image[currImage],xpos-offset,ypos,null);

				if (imageFocus == currImage)
				{
					g.setColor(Color.white);
					g.drawRect(xpos-offset, ypos, image[currImage].getWidth(this)-1,image[currImage].getHeight(this)-1);
				}

				xpos += image[currImage].getWidth(this);
				if (numImages > 1)
				{
					currImage++;
					currImage %= numImages;
				}
			}
		}
		else
		if (status == LOADING_IMAGES)
		{
			g.setColor(Color.white);
			g.drawString (imageLoadString,20,20);
		}
	}

	public boolean mouseDown(Event evt, int x, int y)
	{
		if (imageFocus>=0)
		{
			try
			{
				//
				// get the url link
				//

				URL link = new URL(imageLink[imageFocus]);

				//
				// and the target link
				//

				String target = imageTarget[imageFocus];

				//
				// show the document
				//

				AppletContext context = getAppletContext();
				if (target == null)
				{
					context.showDocument(link);
				}
				else
				{
                                        System.out.println("showing: " + link + " " + target);
					context.showDocument(link, target);
				}
				return true;
			}
			catch (MalformedURLException e)
			{
				showStatus("Malformed URL: " + imageLink[imageFocus]);
				return false;
			}
		}
		return false;
	}

	public boolean mouseMove(Event  evt, int  x, int  y)
	{
		mouseOver = true;
		mousex = x;
		mousey = y;
		updateStatusBar = true;
		return true;
	}

	public boolean mouseEnter(Event  evt, int  x, int  y)
	{
		mouseOver = true;
		mousex = x;
		mousey = y;
		updateStatusBar = true;
		return true;
	}

	public boolean mouseExit(Event  evt, int  x, int  y)
	{
		mouseOver = false;
		return true;
	}


	public void run()
	{
		// load images

		MediaTracker tracker = new MediaTracker(this);

		for (int i=0; i<numImages; i++)
		{
			image[i] = getImage(getCodeBase(), imageName[i]);
			tracker.addImage(image[i],0);
		}

		status = LOADING_IMAGES;

		while (true)
		{
			if (status == LOADING_IMAGES)
			{
				if (tracker.checkAll(true))
				{
					status = OK;
				}
			}
			else
			if (status == OK)
			{
				// update offset and firstImage

				offset += speed;
				if (offset == image[firstImage].getWidth(this))
				{
					if (numImages > 1)
					{
						firstImage++;
						firstImage %= numImages;
					}
					offset = 0;
				}

				// update imageFocus

				if (mouseOver)
				{
					int xpos = 0;
					int currImage = firstImage;
					while (xpos-offset < appletWidth)
					{
						if (mousex < xpos - offset + (image[currImage].getWidth(this)))
						{
							break;
						}
						xpos += image[currImage].getWidth(this);
						if (numImages>1)
						{
							currImage++;
							currImage %= numImages;
						}
					}
					imageFocus = currImage;
				}
				else
				{
					imageFocus = -1;
				}

				// update status bar

				if (updateStatusBar)
				{
					if (imageFocus>=0)
					{
						showStatus(imageLink[imageFocus]);
					}
					else
					{
						showStatus("");
					}
				}
			}

			repaint();
			try
			{
				thread.sleep(20);
			}
			catch (InterruptedException e)
			{
			}
		}

	}


}
