Аплет ShowChart

Оглавление

Сетевые приложения
Адрес IP
Адрес URL
Класс URL
Сокеты
Потоковые сокеты
Класс Socket
Датаграммные сокеты
Связь с Web
Аплет ShowChart
Приложения SocketServ и SocketClient
Аплет Form

Назад Вперед

Попробуем теперь на практике применить технологию передачи файлов из каталога сервера Web в аплет для локальной обработки. Наше следующее приложение с названием ShowChart получает небольшой текстовый файл с исходными данными для построения круговой диаграммы, содержимое которого представлено ниже:

10,20,5,35,11,10,3,6,80,10,
20,5,35,11,10,3,6,80

В этом файле находятся численные значения углов для отдельных секторов диаграммы, причем сумма этих значений равна 360 градусам. Наш аплет принимает этот файл через сеть и рисует круговую диаграмму, показанную на рис. 2.

pic02.gif (3920 bytes)

Рис. 2. Круговая диаграмма, построенная на базе исходных данных, полученных через сеть

Файл исходных данных занимает всего 49 байт, поэтому он передается по сети очень быстро. Если бы мы передавали графическое изображение этой диаграммы, статическое или динамическое, подготовленное, например, расширением сервера CGI или ISAPI, объем передаваемых по сети данных был бы намного больше.

Исходные тексты аплета ShowChart

Исходный текст приложения ShowChart приведен в листинге 1.

Листинг 1. Файл ShowChart.java

import java.applet.*;
import java.awt.*;
import java.net.*;
import java.io.*;
import java.util.*;
public class ShowChart extends Applet
{
  URL SrcURL;
  Object URLContent;
  int errno = 0;
  String str;
  byte buf[] = new byte[200];
  public String getAppletInfo()
  {
    return "Name: ShowChart";
  }
  public void init()
  {
    try
    {
      SrcURL = new URL(
        "http://frolov/chart.txt");
      try
      {
        InputStream is = SrcURL.openStream();
        is.read(buf);
        str = new String(buf, 0);
      }  
      catch (IOException ioe)
      {
        showStatus("read exception");
        errno = 1;
      }
    }
    catch (MalformedURLException uex)
    {
      showStatus(
        "MalformedURLException exception");
      errno = 2;
    }
  }
  public void paint(Graphics g)
  {
    Integer AngleFromChart = new Integer(0);
    int PrevAngle = 0;
    int rColor, gColor, bColor;
    Dimension dimAppWndDimension = getSize();
    
    g.setColor(Color.yellow);
    g.fillRect(0, 0, 
      dimAppWndDimension.width  - 1, 
      dimAppWndDimension.height - 1);
    g.setColor(Color.black);
    g.drawRect(0, 0, 
      dimAppWndDimension.width  - 1, 
      dimAppWndDimension.height - 1);
    showStatus(str);
    StringTokenizer st =
       new StringTokenizer(str, ",\r\n");
    while(st.hasMoreElements())
    {
      rColor = (int)(255 * Math.random());
      gColor = (int)(255 * Math.random());
      bColor = (int)(255 * Math.random());
      g.setColor(new Color(rColor,
         gColor, bColor));
      String angle = 
        (String)st.nextElement();
      AngleFromChart = new Integer(angle) ;
      g.fillArc(0, 0, 200, 200, 
        PrevAngle, 
        AngleFromChart.intValue());
      PrevAngle += AngleFromChart.intValue();
    }
  }
}

Исходный текст документа HTML, созданного автоматически для нашего аплета, представлен в листинге 2.

Листинг 2. Файл ShowChart.tmp.html

<applet
  name="ShowChart"
  code="ShowChart"
  codebase=
  "file:/e:/Sun/Articles/vol12/src/ShowChart"
  width="200"
  height="200"
  align="Top"
  alt="If you had a java-enabled browser,
 you would see an applet here.">
  <hr>If your browser recognized
the applet tag,
you would see an applet here.
  <hr>
</applet>
Описание исходного текста аплета ShowChart

Аплет ShowChart получает содержимое файла исходных данных для построения круговой диаграммы с помощью класса URL. Как вы увидите, для получения содержимого этого файла оно создает поток ввода явным образом.

Поля класса ShowChart

В классе ShowChart определены пять полей.

URL SrcURL;
Object URLContent;
int errno = 0;
String str;
byte buf[] = new byte[200];

Поле SrcURL класса URL хранит адрес URL файла исходных данных для круговой диаграммы. В поле URLContent типа Object будет переписано содержимое этого файла. В поле errno хранится текущий код ошибки, если она возникла, или нулевое значение, если все операции были выполнены без ошибок.

Поле str хранит принятую строку, которая предварительно записывается во временный буфер buf.

Метод init

Во время инициализации метод init создает объект класса URL для файла исходных данных:

SrcURL = new URL("http://frolov/chart.txt");

Здесь для упрощения исходного текста мы указали адрес URL файла данных непосредственно в программе, однако вы можете передать этот адрес аплету через параметр в документе HTML.

Далее для нашего объекта URL мы создаем поток ввода и получаем содержимое файла (то есть исходные данные для построения диаграммы):

InputStream is = SrcURL.openStream();
is.read(buf);

Принятые данные записываются в буфер buf и затем преобразуются к типу String с помощью соответствующего конструктора:

str = new String(buf, 0);

Если при создании объекта класса URL возникло исключение, метод init записывает в поле errno код ошибки, равный 2, записывая при этом в строку состояния браузера сообщение "MalformedURLException exception".

В том случае, когда объект класса URL создан успешно, а исключение возникло в процессе чтения содержимого файла, в поле errno записывается значение 1, а в строку состояния браузера - сообщение "read exception".

Метод paint

После раскрашивания фона окна аплета и рисования вокруг него рамки метод paint приступает к построению круговой диаграммы. Принятые данные отображаются в строке состояния браузера:

showStatus(sChart);

Далее создается разборщик строки исходных данных:

StringTokenizer st = 
  new StringTokenizer(sChart, ",\r\n");

В качестве разделителей для этого разборщика указывается запятая, символ возврата каретки и перевода строки.

Рисование секторов диаграммы выполняется в цикле, условием выхода из которого является завершение разбора строки исходных данных:

while(st.hasMoreElements())
{
  . . .
}

Для того чтобы секторы диаграммы не сливались, они должны иметь разный цвет. Цвет сектора можно было бы передавать вместе со значением угла через файл исходных данных, однако мы применили более простой способ раскаршивания секторов - в случайные цвета. Мы получаем случайные компоненты цвета сектора, а затем выбираем цвет в контекст отображения:

rColor = (int)(255 * Math.random());
gColor = (int)(255 * Math.random());
bColor = (int)(255 * Math.random());
g.setColor(new Color(rColor,
   gColor, bColor));

С помощью метода nextElement мы получаем очередное значение угла сектора и сохраняем его в переменной angle:

String angle = (String)st.nextElement();

Далее с помощью конструктора класса Integer это значение преобразуется в численное:

AngleFromChart = new Integer(angle);

Рисование сектора круговой диаграммы выполняется с помощью метода fillArc:

g.fillArc(0, 0, 200, 200, 
  PrevAngle, AngleFromChart.intValue());

В качестве начального значения угла сектора используется значение из переменной PrevAngle. Сразу после инициализации в эту переменную записывается нулевое значение.

Конечный угол сектора задается как AngleFromChart.intValue(), то есть указывается значение, полученное из принятого по сети файла исходных данных.

После завершения рисования очередного сектора круговой диаграммы начальное значение PrevAngle увеличивается на величину угла нарисованного сектора:

PrevAngle += AngleFromChart.intValue();
Назад Вперед