package org.nzdl.gsdl.GsdlCollageApplet;
import java.applet.Applet;
import java.awt.*;
import java.net.*;
/**
*
* @author Katrina Edgar
* @author David Bainbridge
*
* Main class for the GsdlCollageApplet
* Processes the parameters passed through the Applet
* Builds an appropriate starting url from these parameters
* Creates a storage class for downloaded images
* Starts thread to download images and their associated url
* Starts thread to display downloaded images on the applet screen
*/
public class GsdlCollageApplet extends Applet {
/** Amount of error checking output produced
* Ranges from 0 - no output to 3 - maximum output */
protected int verbosity_ = 0;
/** Indicates whether java2 functionality should be used
* If true will allow advanced image processing techniques to occur,
* such as fading and colouring using pixel manipulation
* If false, images will maintain an alpha value of 1 (appear solid),
* newer images will simply be pasted on top of existing images
*/
protected boolean isJava2_ = true;
/** Number of nested links to follow When used with greenstone,
* controls to which level of the document links will be followed For
* example a maximum depth of 1 will mean only the top page of a
* document will be examined, while a depth of 2 will include sections
* within this document, 3 includes sections within sections, and so
* on */
protected int maxDepth_ = 3;
/** Maximum number of images to display on the canvas */
protected int maxDisplay_ = 25;
/** Maximum number of downloaded images to store
Prevents applet
* from using excessive amounts of bandwidth by downloading too many
* images simulataneously*/
protected int maxDownloads_ = Integer.MAX_VALUE;
/** Types of images permitted in the collage, for example gif, jpg,
* png... */
protected String imageType_ = ".jpg%.png";
/** Caption of the collage */
protected String caption_ = "";
/** Background color of applet screen */
protected Color bgcolor_ = new Color(150, 193, 155);
/** Time lapse between repainting of the applet */
protected int refreshDelay_ = 2000;
/** Stores an image and url pair and provides associated methods */
protected DownloadImages download_images_ = null;
/** Downloads images from a starting url, recursively follows nested
* links */
protected DownloadUrls download_thread_ = null;
/** Image processing and placement on applet screen */
protected DisplayImages display_thread_ = null;
/** Gets verbosity */
public int verbosity() { return verbosity_; }
/** Gets maximum depth for nested links */
public int maxDepth() { return maxDepth_; }
/** Gets maximum number of images to display */
public int maxDisplay() { return maxDisplay_;}
/** Gets maximum number of images to store during downloading */
public int maxDownloads() { return maxDownloads_; }
/** Gets the refresh delay used between repaint */
public int refreshDelay() { return refreshDelay_; }
/** Gets parameters from the applet code and stores locally.
* Forms a starting url for image retrieval to begin from.
* The starting url is formed either by:
* * Using the image_url parameter as provided, which is assumed to
* be a complete url
* * If this parameter does not exist, the assumption is that the
* collage is being incorporated with the Greenstone Digital Library
* Software. The starting url is formed by concatenating
* the gwcgi, collection and classifier parameters as provided.
* Then starts downloading and displaying images */
Thread paint ;
public void init()
{
if (verbosity_ >= 4) {
System.err.println("Attempting to retrieve parameters...");
}
// gets the parameters specified
String verbosity_param = getParameter("verbosity");
String is_java2_param = getParameter("isJava2");
String max_depth_param = getParameter("maxDepth");
String max_downloads_param = getParameter("maxDownloads");
String max_display_param = getParameter("maxDisplay");
String refresh_delay_param = getParameter("refreshDelay");
String image_type_param = getParameter("imageType");
String bgcolor_param = getParameter("bgcolor");
String caption_param = getParameter("caption");
String document_root = getParameter("documentroot");
String gwcgi = getParameter("gwcgi");
// Check it isn't null
if ((verbosity_param!=null) && (!verbosity_param.startsWith("_"))) {
verbosity_ = Integer.parseInt(verbosity_param);
}
else {
verbosity_ = 1;
}
if (verbosity_ >= 4) {
System.err.println("Got parameters.");
}
if (caption_param != null && !caption_param.startsWith("_")) {
caption_ = caption_param;
}
else {
if (verbosity_ >= 4) {
System.err.println("No Caption: setting to a space.");
}
caption_ = " ";
}
if ((bgcolor_param != null) && (!bgcolor_param.startsWith("_"))) {
if (bgcolor_param.startsWith("#")) {
bgcolor_ = Color.decode(bgcolor_param);
}
else {
String [] c = bgcolor_param.split(",");
if (c.length == 3)
bgcolor_ = new Color(Integer.parseInt(c[0]), Integer.parseInt(c[1]), Integer.parseInt(c[2]));
}
if (verbosity_ >= 4){
System.err.println("Set BG to be " + bgcolor_.toString());
}
}
else {
if (verbosity_ >= 4) {
System.err.println("No BG: setting to NZDL green.");
}
bgcolor_ = new Color(150, 193, 155);
}
if ((image_type_param != null) && (!image_type_param.startsWith("_"))) {
imageType_ = image_type_param;
}
if ((is_java2_param == null) || (is_java2_param.equals("auto")) || (is_java2_param.startsWith("_"))) {
String version = System.getProperty("java.version");
version = version.substring(0, version.lastIndexOf("."));
System.err.println("VERSION: " + version);
float ver = (new Float(version)).floatValue();
isJava2_ = (ver >= 1.2) ? true : false;
}
else {
isJava2_ = (is_java2_param.equals("true")) ? true : false;
}
if ((max_depth_param != null) && (!max_depth_param.startsWith("_"))) {
// System.err.println("maxDepth = " + max_depth_param);
maxDepth_ = Integer.parseInt(max_depth_param);
}
if ((max_downloads_param!=null) && (!max_downloads_param.startsWith("_"))) {
maxDownloads_ = Integer.parseInt(max_downloads_param);
System.out.println(" maxDownloads " + maxDownloads_ );
maxDownloads_=50;
}
if ((max_display_param!=null) && (!max_display_param.startsWith("_"))) {
maxDisplay_ = Integer.parseInt(max_display_param);
}
if ((refresh_delay_param!=null) && (!refresh_delay_param.startsWith("_"))) {
refreshDelay_ = Integer.parseInt(refresh_delay_param);
}
if (document_root !=null){
document_root = document_root.substring(1);
if (document_root.indexOf("/") > 0 ){
document_root = document_root.substring(0, document_root.indexOf("/"));
}
else{
document_root = gwcgi;
}
}
String image_url = getParameter("imageURL");
String image_ignore = getParameter("imageIgnorePrefix");
String href_musthave = getParameter("hrefMustHave");
String image_mustnothave = getParameter("imageMustNotHave");
// builds starting url when incorporated with Greenstone
if (image_url==null)
{
String gwcgi_param = getParameter("gwcgi");
gwcgi_param = tidy_URL(gwcgi_param, true);
String collection_param = getParameter("collection");
String classifier_param = getParameter("classifier");
image_url = gwcgi_param + "a=d";
image_url += "&c=" + collection_param;
image_url += "&cl=" + classifier_param;
}
MediaTracker trk = new MediaTracker(this);
// creates a class to store the image and it's associated url
download_images_ = new DownloadImages( this, verbosity_,isJava2_ );
// starts the download image thread with the starting url
download_thread_ = new DownloadUrls(this, download_images_,
image_url, href_musthave, image_mustnothave,
image_ignore, imageType_,document_root,verbosity_,trk);
// starts the display image thread with the currently downloaded images
display_thread_ = new DisplayImages(this, download_images_,isJava2_, bgcolor_);
}
/** Goes to the url associated with the image that is clicked on screen
* Displays the url containing the image in a new window */
public boolean mouseDown(Event event, int x, int y)
{
// determines which image was clicked on
CollageImage cimage = display_thread_.clickedOnImage(x,y);
// if they were clicking on an image (as opposed to background)
if (cimage != null)
{
System.err.println("Click on image: from url = " + cimage.from_url_);
try {
// displays the associated url in a new window
URL from_url = null;
java.util.regex.Pattern p = java.util.regex.Pattern.compile("cl=CL\\d(\\.\\d)*\\s");
java.util.regex.Matcher m = p.matcher(cimage.from_url_.trim()+" ");
if (m.find() ){
from_url = cimage.url_;
}
else{
from_url = new URL(cimage.from_url_ + "#" + cimage.name_);
}
getAppletContext().showDocument(from_url,"gsdlDoc");
}
catch (MalformedURLException e) {
e.printStackTrace();
}
}
return true;
}
/** Start threads for downloading and displaying images */
public void start()
{
download_thread_.start();
display_thread_.start();
paint = new Thread(new Runnable(){
public void run() {
try {
Thread curr_thread = Thread.currentThread();
while (curr_thread == paint) {
repaint();
Thread.sleep(2000);
curr_thread = Thread.currentThread();
}
} catch (Exception e) {
}
}
});
paint.start();
}
/** Stops threads for downloading and displaying images */
public void stop()
{
download_thread_.stop();
display_thread_.stop();
download_thread_ = null;
display_thread_ = null;
}
/** Destroys threads for downloading and displaying images */
public void destroyed()
{
download_thread_ = null;
display_thread_ = null;
}
/** Repaints the applet */
public void update(Graphics g)
{
// System.err.println("Update called");
paint(g);
}
/** Repaints the applet using the paint method of the thread that is
* currently displaying images */
public void paint(Graphics g) {
if (display_thread_!=null)
{
//display_thread_.display_collage();
display_thread_.paint(g);
}
else
{
System.err.println("Applet still trying to paint!!");
}
}
/** Ensures a URL address (as string) has a protocol, host, and file.
*
* If the URL is a CGI script URL, it should be tidied up so that it is
* appropriate to tage attrib=value pairs on the end. This means it
* must either end with a "?" or (if it contains a question-mark
* internally) end with a "&". */
String tidy_URL(String address, boolean isCGI) {
// System.err.println("tidy URL: " + address);
// make sure the URL has protocol, host, and file
if (address.startsWith("http")) {
// the address has all the necessary components
} else if (address.startsWith("/")) {
// there is not protocol and host
URL document = getDocumentBase();
String port = "";
if (document.getPort()!=-1) {
port = ":" + document.getPort();
}
address = "http://" + document.getHost() + port + address;
} else {
// this URL is relative to the directory the document is in
URL document = getDocumentBase();
String directory = document.getFile();
int end = directory.lastIndexOf('/');
String port = "";
if (document.getPort()!=-1) {
port = ":" + document.getPort();
}
directory = directory.substring(0,end + 1);
address = "http://" + document.getHost() + port + directory + address;
}
// if the URL is a cgi script, make sure it has a "?" in ti,
// and that it ends with a "?" or "&"
if (isCGI) {
if (address.indexOf((int) '?') == -1) {
address = address + "?";
} else if (!address.endsWith("?")) {
address = address + "&";
}
}
return address;
}
}