Java - Applet 基础知识


Applet是在 Web 浏览中运行的 Java 程序。小程序可以是功能齐全的 Java 应用程序,因为它可以使用整个 Java API。

小程序和独立 Java 应用程序之间存在一些重要区别,包括以下内容 -

  • Applet 是扩展 java.applet.Applet 类的 Java 类。

  • main() 方法不会在 applet 上调用,并且 applet 类不会定义 main()。

  • Applet 被设计为嵌入 HTML 页面中。

  • 当用户查看包含小程序的 HTML 页面时,该小程序的代码就会下载到用户的计算机上。

  • 查看小程序需要 JVM。JVM 可以是 Web 浏览器的插件,也可以是单独的运行时环境。

  • 用户计算机上的 JVM 创建 applet 类的实例,并在 applet 的生命周期内调用各种方法。

  • Applet 具有由 Web 浏览器强制执行的严格安全规则。小程序的安全性通常被称为沙箱安全,将小程序比作在沙箱中玩耍的孩子,必须遵守各种规则。

  • 小程序所需的其他类可以在单个 Java Archive (JAR) 文件中下载。

小程序的生命周期

Applet 类中的四个方法为您提供了构建任何严肃的小程序的框架 -

  • init - 此方法用于小程序所需的任何初始化。在处理完 applet 标签内的 param 标签后调用它。

  • start - 该方法在浏览器调用 init 方法后自动调用。每当用户在离开其他页面后返回到包含小程序的页面时,也会调用它。

  • stop - 当用户离开小程序所在的页面时,会自动调用此方法。因此,它可以在同一个小程序中重复调用。

  • destroy - 仅当浏览器正常关闭时才会调用此方法。因为小程序应该存在于 HTML 页面上,所以在用户离开包含小程序的页面后,通常不应留下资源。

  • Paint - 在 start() 方法之后立即调用,并且在小程序需要在浏览器中重新绘制自身时调用。Paint()方法实际上继承自java.awt。

“你好,世界”小程序

以下是一个名为 HelloWorldApplet.java 的简单小程序 -

import java.applet.*;
import java.awt.*;

public class HelloWorldApplet extends Applet {
   public void paint (Graphics g) {
      g.drawString ("Hello World", 25, 50);
   }
}

这些导入语句将这些类带入我们的小程序类的范围 -

  • java.applet.Applet
  • java.awt.Graphics

如果没有这些 import 语句,Java 编译器将无法识别 Applet 类所引用的类 Applet 和 Graphics。

小程序类

每个 applet 都是java.applet.Applet 类的扩展。Applet 基类提供派生 Applet 类可以调用的方法,以从浏览器上下文获取信息和服务。

这些包括执行以下操作的方法 -

  • 获取小程序参数
  • 获取包含该小程序的 HTML 文件的网络位置
  • 获取小程序类目录的网络位置
  • 在浏览器中打印状态消息
  • 获取图像
  • 获取音频剪辑
  • 播放音频剪辑
  • 调整小程序的大小

另外,Applet 类提供了一个接口,查看器或浏览器可以通过该接口获取有关 applet 的信息并控制 applet 的执行。观众可以 -

  • 请求有关小程序的作者、版本和版权的信息
  • 请求小程序识别的参数的描述
  • 初始化小程序
  • 销毁小程序
  • 开始小程序的执行
  • 停止小程序的执行

Applet 类提供了每个方法的默认实现。这些实现可以根据需要被覆盖。

“Hello, World”小程序已经完成。唯一被重写的方法是paint方法。

调用小程序

可以通过在 HTML 文件中嵌入指令并通过 applet 查看器或支持 Java 的浏览器查看该文件来调用 applet。

<applet> 标签是在 HTML 文件中嵌入 applet 的基础。以下是调用“Hello, World”小程序的示例 -

<html>
   <title>The Hello, World Applet</title>
   <hr>
   <applet code = "HelloWorldApplet.class" width = "320" height = "120">
      If your browser was Java-enabled, a "Hello, World"
      message would appear here.
   </applet>
   <hr>
</html>

注意- 您可以参考HTML Applet 标签来了解有关从 HTML 调用 applet 的更多信息。

<applet> 标记的 code 属性是必需的。它指定要运行的 Applet 类。还需要宽度和高度来指定小程序运行的面板的初始大小。applet 指令必须以 </applet> 标记结束。

如果小程序采用参数,则可以通过在 <applet> 和 </applet> 之间添加 <param> 标记来传递参数值。浏览器会忽略小程序标记之间的文本和其他标记。

不支持 Java 的浏览器不处理 <applet> 和 </applet>。因此,出现在标签之间的任何内容(与 applet 无关)在不支持 Java 的浏览器中都是可见的。

查看器或浏览器在文档的位置查找已编译的 Java 代码。要以其他方式指定,请使用 <applet> 标记的 codebase 属性,如下所示 -

<applet codebase = "https://amrood.com/applets" code = "HelloWorldApplet.class"
   width = "320" height = "120">

如果小程序驻留在默认包以外的包中,则必须在代码属性中使用句点字符 (.) 来指定保存包,以分隔包/类组件。例如 -

<applet  = "mypackage.subpackage.TestApplet.class" 
   width = "320" height = "120">

获取小程序参数

以下示例演示如何使小程序响应文档中指定的设置参数。该小程序显示黑色和第二种颜色的棋盘图案。

第二颜色和每个方块的大小可以被指定为文档内的小应用程序的参数。

CheckerApplet 在 init() 方法中获取其参数。它还可以在paint()方法中获取其参数。然而,在小程序启动时获取值并保存设置一次,而不是每次刷新时,既方便又高效。

小程序查看器或浏览器调用它运行的每个小程序的 init() 方法。查看器在加载小程序后立即调用 init() 一次。(Applet.init() 的实现不执行任何操作。)覆盖默认实现以插入自定义初始化代码。

Applet.getParameter() 方法根据给定的参数名称获取参数(参数的值始终是字符串)。如果值为数字或其他非字符数据,则必须解析字符串。

以下是 CheckerApplet.java 的框架 -

import java.applet.*;
import java.awt.*;

public class CheckerApplet extends Applet {
   int squareSize = 50;   // initialized to default size
   public void init() {}
   private void parseSquareSize (String param) {}
   private Color parseColor (String param) {}
   public void paint (Graphics g) {}
}

以下是 CheckerApplet 的 init() 和私有 parseSquareSize() 方法 -

public void init () {
   String squareSizeParam = getParameter ("squareSize");
   parseSquareSize (squareSizeParam);
   
   String colorParam = getParameter ("color");
   Color fg = parseColor (colorParam);
   
   setBackground (Color.black);
   setForeground (fg);
}

private void parseSquareSize (String param) {
   if (param == null) return;
   try {
      squareSize = Integer.parseInt (param);
   } catch (Exception e) {
      // Let default value remain
   }
}

小程序调用 parseSquareSize() 来解析 squareSize 参数。parseSquareSize() 调用库方法 Integer.parseInt(),该方法解析字符串并返回整数。每当其参数无效时,Integer.parseInt() 就会引发异常。

因此,parseSquareSize() 捕获异常,而不是让小程序因错误输入而失败。

小程序调用 parseColor() 将颜色参数解析为 Color 值。parseColor() 执行一系列字符串比较,将参数值与预定义颜色的名称进行匹配。您需要实现这些方法才能使该小程序正常工作。

指定小程序参数

以下是嵌入了 CheckerApplet 的 HTML 文件示例。HTML 文件通过 <param> 标记指定小程序的两个参数。

例子

<html>
   <title>Checkerboard Applet</title>
   <hr>
   <applet code = "CheckerApplet.class" width = "480" height = "320">
      <param name = "color" value = "blue">
      <param name = "squaresize" value = "30">
   </applet>
   <hr>
</html>

注意- 参数名称不区分大小写。

应用程序转换为 Applet

将图形 Java 应用程序(即使用 AWT 并且可以通过 Java 程序启动器启动的应用程序)转换为可以嵌入网页中的小程序是很容易的。

以下是将应用程序转换为小程序的具体步骤。

  • 使用适当的标签创建一个 HTML 页面来加载小程序代码。

  • 提供 JApplet 类的子类。将此类公开。否则,无法加载小程序。

  • 删除应用程序中的主要方法。不要为应用程序构建框架窗口。您的应用程序将显示在浏览器中。

  • 将所有初始化代码从框架窗口构造函数移至小程序的 init 方法。您不需要显式构造 applet 对象。浏览器会为您实例化它并调用 init 方法。

  • 删除对 setSize 的调用;对于小程序,大小调整是通过 HTML 文件中的宽度和高度参数来完成的。

  • 删除对 setDefaultCloseOperation 的调用。小程序无法关闭;当浏览器退出时它终止。

  • 如果应用程序调用 setTitle,请消除对该方法的调用。小程序不能有标题栏。(当然,您可以使用 HTML 标题标签为网页本身添加标题。)

  • 不要调用 setVisible(true)。小程序会自动显示。

事件处理

Applet 从 Container 类继承一组事件处理方法。Container 类定义了多种方法,例如 processKeyEvent 和 processMouseEvent,用于处理特定类型的事件,然后定义了一个名为 processEvent 的包罗万象的方法。

为了对事件做出反应,小程序必须重写适当的特定于事件的方法。

例子

import java.awt.event.MouseListener;
import java.awt.event.MouseEvent;
import java.applet.Applet;
import java.awt.Graphics;

public class ExampleEventHandling extends Applet implements MouseListener {
   StringBuffer strBuffer;

   public void init() {
      addMouseListener(this);
      strBuffer = new StringBuffer();
      addItem("initializing the apple ");
   }

   public void start() {
      addItem("starting the applet ");
   }

   public void stop() {
      addItem("stopping the applet ");
   }

   public void destroy() {
      addItem("unloading the applet");
   }

   void addItem(String word) {
      System.out.println(word);
      strBuffer.append(word);
      repaint();
   }

   public void paint(Graphics g) {
      // Draw a Rectangle around the applet's display area.
      g.drawRect(0, 0, 
      getWidth() - 1,
      getHeight() - 1);

      // display the string inside the rectangle.
      g.drawString(strBuffer.toString(), 10, 20);
   }

   
   public void mouseEntered(MouseEvent event) {
   }
   public void mouseExited(MouseEvent event) {
   }
   public void mousePressed(MouseEvent event) {
   }
   public void mouseReleased(MouseEvent event) {
   }
   public void mouseClicked(MouseEvent event) {
      addItem("mouse clicked! ");
   }
}

现在,让我们这样称呼这个小程序 -

<html>
   <title>Event Handling</title>
   <hr>
   <applet code = "ExampleEventHandling.class" 
      width = "300" height = "300">
   </applet>
   <hr>
</html>

最初,小程序将显示“正在初始化小程序。启动小程序”。然后,一旦您在矩形内单击,也会显示“鼠标单击”。

显示图像

小程序可以显示 GIF、JPEG、BMP 等格式的图像。要在小程序中显示图像,可以使用 java.awt.Graphics 类中的drawImage() 方法。

以下是说明显示图像的所有步骤的示例 -

例子

import java.applet.*;
import java.awt.*;
import java.net.*;

public class ImageDemo extends Applet {
   private Image image;
   private AppletContext context;
   
   public void init() {
      context = this.getAppletContext();
      String imageURL = this.getParameter("image");
      if(imageURL == null) {
         imageURL = "java.jpg";
      }
      try {
         URL url = new URL(this.getDocumentBase(), imageURL);
         image = context.getImage(url);
      } catch (MalformedURLException e) {
         e.printStackTrace();
         // Display in browser status bar
         context.showStatus("Could not load image!");
      }
   }
   
   public void paint(Graphics g) {
      context.showStatus("Displaying image");
      g.drawImage(image, 0, 0, 200, 84, null);
      g.drawString("www.javalicense.com", 35, 100);
   }  
}

现在,让我们这样称呼这个小程序 -

<html>
   <title>The ImageDemo applet</title>
   <hr>
   <applet code = "ImageDemo.class" width = "300" height = "200">
      <param name = "image" value = "java.jpg">
   </applet>
   <hr>
</html>

播放音频

小程序可以播放由 java.applet 包中的 AudioClip 接口表示的音频文件。AudioClip 接口具有三种方法,包括 -

  • public void play() - 从头开始​​播放音频剪辑一次。

  • public void Loop() - 使音频剪辑不断重播。

  • public void stop() - 停止播放音频剪辑。

要获取 AudioClip 对象,必须调用 Applet 类的 getAudioClip() 方法。无论 URL 是否解析为实际的音频文件, getAudioClip() 方法都会立即返回。在尝试播放音频剪辑之前,不会下载音频文件。

以下是说明播放音频的所有步骤的示例 -

例子

import java.applet.*;
import java.awt.*;
import java.net.*;

public class AudioDemo extends Applet {
   private AudioClip clip;
   private AppletContext context;
   
   public void init() {
      context = this.getAppletContext();
      String audioURL = this.getParameter("audio");
      if(audioURL == null) {
         audioURL = "default.au";
      }
      try {
         URL url = new URL(this.getDocumentBase(), audioURL);
         clip = context.getAudioClip(url);
      } catch (MalformedURLException e) {
         e.printStackTrace();
         context.showStatus("Could not load audio file!");
      }
   }
   
   public void start() {
      if(clip != null) {
         clip.loop();
      }
   }
   
   public void stop() {
      if(clip != null) {
         clip.stop();
      }
   }
}

现在,让我们这样称呼这个小程序 -

<html>
   <title>The ImageDemo applet</title>
   <hr>
   <applet code = "ImageDemo.class" width = "0" height = "0">
      <param name = "audio" value = "test.wav">
   </applet>
   <hr>
</html>

您可以在 PC 上使用 test.wav 来测试上面的示例。