/* RJA 2000 January 23 modified for new data format 1998 September 06 this code taken from Apple Applet Runner Bar Chart example applet, plus some code from the Que book _Using Java, Special Edition_ (1996) */ /* * @(#)Chart.java 1.4 97/02/05 * * Copyright (c) 1994-1997 Sun Microsystems, Inc. All Rights Reserved. * * Sun grants you ("Licensee") a non-exclusive, royalty free, license to use, * modify and redistribute this software in source and binary code form, * provided that i) this copyright notice and license appear on all copies of * the software; and ii) Licensee does not utilize the software in a manner * which is disparaging to Sun. * * This software is provided "AS IS," without a warranty of any kind. ALL * EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND WARRANTIES, INCLUDING ANY * IMPLIED WARRANTY OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR * NON-INFRINGEMENT, ARE HEREBY EXCLUDED. SUN AND ITS LICENSORS SHALL NOT BE * LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING * OR DISTRIBUTING THE SOFTWARE OR ITS DERIVATIVES. IN NO EVENT WILL SUN OR ITS * LICENSORS BE LIABLE FOR ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, * INDIRECT, SPECIAL, CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER * CAUSED AND REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF * OR INABILITY TO USE SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE * POSSIBILITY OF SUCH DAMAGES. * * This software is not designed or intended for use in on-line control of * aircraft, air traffic, aircraft navigation or aircraft communications; or in * the design, construction, operation or maintenance of any nuclear * facility. Licensee represents and warrants that it will not use or * redistribute the Software for such purposes. */ import java.awt.Graphics; import java.awt.Color; import java.awt.Font; import java.awt.FontMetrics; import java.io.*; import java.lang.*; import java.net.URL; // RJA added import java.net.MalformedURLException; import java.net.UnknownServiceException; public class MyWebVisitStatsChart extends java.applet.Applet implements Runnable { static final int VERTICAL = 0; static final int HORIZONTAL = 1; static final int SOLID = 0; static final int STRIPED = 1; int orientation; String title; Font titleFont; FontMetrics titleFontMetrics; int titleHeight = 15; int columns; int values[]; Object colors[]; Object labels[]; int styles[]; int scale = 10; // multiplier for bar size int maxLabelWidth = 0; int barWidth; int barSpacing = 10; int max = 0; // RJA added int myWIDTH; // will be read from params, then stays constant int myHEIGHT; // will be read from params, then stays constant // needed because Netscape doesn't like // getSize().width, getSize().height int mySHRINK; // divide the values by this value so they will // fit on the the screen; should be autocalculated final int DEFAULT_SHRINK = 4; final int DEFAULT_WIDTH = 500; final int DEFAULT_HEIGHT = 200; int max_paint = -1; // index of maximum value to paint // RJA add separate thread for continuous updating protected Thread urlEaterThread; URL[] webStatURL; /* *********** init ***************** */ // RJA this sets up the initial parameters public void init() { String paramString; titleFont = new java.awt.Font("Courier", Font.PLAIN, 10); titleFontMetrics = getFontMetrics(titleFont); title = getParameter("title"); if (title == null) { title = "Chart"; } paramString = getParameter("columns"); if (paramString == null) { columns = 5; } else { columns = Integer.parseInt(paramString); } System.out.println( "columns " + columns ); paramString = getParameter("scale"); if (paramString == null) { scale = 10; } else { scale = Integer.parseInt(paramString); } paramString = getParameter("orientation"); if (paramString == null) { orientation = VERTICAL; } else if (paramString.toLowerCase().equals("vertical")) { orientation = VERTICAL; } else if (paramString.toLowerCase().equals("horizontal")) { orientation = HORIZONTAL; } else { orientation = VERTICAL; } // RJA added size params paramString = getParameter("WIDTH"); if (paramString == null) { myWIDTH = DEFAULT_WIDTH; } else { myWIDTH = Integer.parseInt(paramString); } paramString = getParameter("HEIGHT"); if (paramString == null) { myHEIGHT = DEFAULT_HEIGHT; } else { myHEIGHT = Integer.parseInt(paramString); } paramString = getParameter("SHRINK"); if (paramString == null) { mySHRINK = DEFAULT_SHRINK; } else { mySHRINK = Integer.parseInt(paramString); } webStatURL = new URL[columns]; values = new int[columns]; colors = new Color[columns]; labels = new String[columns]; styles = new int[columns]; // RJA we can process all the styles and colors and stuff first for ( int i = 0; i < columns; i++) { // parse the bar style paramString = getParameter("C" + (i+1) + "_style"); if (paramString == null || paramString.toLowerCase().equals("solid")) { styles[i] = SOLID; } else if (paramString.toLowerCase().equals("striped")) { styles[i] = STRIPED; } else { styles[i] = SOLID; } // parse the color attribute for this column paramString = getParameter("C" + (i+1) + "_color"); if (paramString != null) { if (paramString.equals("red")) { colors[i] = Color.red; } else if (paramString.equals("green")) { colors[i] = Color.green; } else if (paramString.equals("blue")) { colors[i] = Color.blue; } else if (paramString.equals("pink")) { colors[i] = Color.pink; } else if (paramString.equals("orange")) { colors[i] = Color.orange; } else if (paramString.equals("magenta")) { colors[i] = Color.magenta; } else if (paramString.equals("cyan")) { colors[i] = Color.cyan; } else if (paramString.equals("white")) { colors[i] = Color.white; } else if (paramString.equals("yellow")) { colors[i] = Color.yellow; } else if (paramString.equals("gray")) { colors[i] = Color.gray; } else if (paramString.equals("darkGray")) { colors[i] = Color.darkGray; } else { colors[i] = Color.gray; } } else { colors[i] = Color.gray; } } // end for // RJA get data here /* RJA This is the format of the data returned
This month: #
Last month: # We want to provide an array of URLs to check. For each URL an array will hold the values for yesterday, this month, and last month. Then they will be plotted in a bar graph. Then these numbers will be displayed in a table. Currently the code just does a bar graph for last month's values */ // RJA this code based in part on _Using Java, Special Edition_ // Chapter 27 - Content Handlers, pp. 587-588 "Reading the InputStream" String baseURL; baseURL = getParameter("BASE_URL"); if (baseURL == null) { System.err.println("no base url!"); // do we need more error handling here? } for ( int i = 0; i < columns; i++ ) { System.out.println("in get url loop, i = " + i); paramString = getParameter("C" + (i+1) + "_URL"); if (paramString != null) { try { webStatURL[i] = new URL( baseURL + paramString ); // RJA we can do the labels first // RJA hack to remove base URL to make short label labels[i] = webStatURL[i].toString().substring(baseURL.length()); maxLabelWidth = Math.max(titleFontMetrics.stringWidth((String)(labels[i])), maxLabelWidth); } catch (MalformedURLException e) { System.err.println( "Caught Malformed URL Exception" ); // should die here } catch (Exception e) { System.err.println( "Caught exception: " + e.toString() ); // should die here } // RJA can't resize panel within browser switch (orientation) { case VERTICAL: default: barWidth = maxLabelWidth; //resize(Math.max(columns * (barWidth + barSpacing), // titleFontMetrics.stringWidth(title)) + // titleFont.getSize() + 5, // (max * scale) + (2 * titleFont.getSize()) + 5 + titleFont.getSize()); break; case HORIZONTAL: barWidth = titleFont.getSize(); //resize(Math.max((max * scale) + titleFontMetrics.stringWidth("" + max), // titleFontMetrics.stringWidth(title)) + maxLabelWidth + 5, // (columns * (barWidth + barSpacing)) + titleFont.getSize() + 10); break; } // end switch } else { System.err.println("no urls to process"); // should die here } // end if } // end for } // end init /* *** start ***/ public void start() { urlEaterThread = new Thread(this); urlEaterThread.start(); } /* *** stop *** */ public void stop() { urlEaterThread.stop(); urlEaterThread = null; } /* *** run *** */ // RJA this guy eats the URLs one by one and updates the display as it gets // each data value public void run() { Thread.currentThread().setPriority(Thread.NORM_PRIORITY); Object contentObject; InputStream pageContent; StringBuffer outStringBuffer; String outString; // outString will contain the full data returned // we want to parse out the numbers for yesterday, this month, and last month // (should be using arrays) String lastMonthString; int urlmatchindex; int lastmonthindex; int endbodyindex; int endhtmlindex; Integer[] lastMonthCount = new Integer[columns]; int inputByte; // RJA this is the slow part for ( int i = 0; i < columns; i++ ) { try { contentObject = webStatURL[i].getContent(); // RJA used to check class of contentObject but // crusty Netscape gives a URLInputStream pageContent = (InputStream) contentObject; inputByte = pageContent.read(); outStringBuffer = new StringBuffer(); while( inputByte != -1 ) // end of stream is -1 { outStringBuffer.append( (char) inputByte ); inputByte = pageContent.read(); } pageContent.close(); outString = outStringBuffer.toString(); // take the substring starting at "Number of visits to URLs that match" urlmatchindex = outString.indexOf("Number of visits to URLs that match"); endhtmlindex = outString.indexOf("