本教程是针对JDK 8编写的。本页中描述的示例和实践不利用后续版本引入的改进,并且可能使用已不再可用的技术。
请参阅Java语言变化,了解Java SE 9及以后版本的更新语言特性的概述。
请参阅JDK发行说明,了解所有JDK版本的新功能、增强功能以及已删除或弃用选项的信息。
当使用Java网络启动协议(JNLP)启动时,富互联网应用程序(RIA)可以在用户的许可下访问客户端。考虑文本编辑器小程序示例,以了解如何使用基于JNLP API的服务。文本编辑器有一个文本区域和标有“打开”、“保存”和“另存为”的按钮。文本编辑器可以用来打开现有的文本文件,进行编辑,并将其保存回磁盘。
下面显示了文本编辑器小程序。
TextEditor
和TextEditorApplet
类布置用户界面并将其显示为小程序。 FileHandler
类包含与使用基于JNLP API的服务相关的核心功能。
请记住,本主题中描述的技术也适用于Java Web Start应用程序。
要使用JNLP服务,首先检索对该服务的引用。 FileHandler
类的initialize
方法检索JNLP服务的引用,如以下代码片段所示:
private static synchronized void initialize() { ... try { fos = (FileOpenService) ServiceManager.lookup("javax.jnlp.FileOpenService"); fss = (FileSaveService) ServiceManager.lookup("javax.jnlp.FileSaveService"); } catch (UnavailableServiceException e) { ... } }
在获取所需服务的引用之后,调用服务的方法来执行必要的操作。FileHandler类的open方法调用FileOpenService类的openFileDialog方法来显示文件选择器。open方法返回所选文件的内容。
public static String open() { initialize(); try { fc = fos.openFileDialog(null, null); return readFromFile(fc); } catch (IOException ioe) { ioe.printStackTrace(System.out); return null; } }
类似地,FileHandler类的save和saveAs方法调用FileSaveService类的相应方法,以使用户能够选择文件名并将文本区域的内容保存到磁盘上。
public static void saveAs(String txt) { initialize(); try { if (fc == null) { // 如果尚未保存 // 另存为与保存相同 save(txt); } else { fc = fss.saveAsFileDialog(null, null, fc); save(txt); } } catch (IOException ioe) { ioe.printStackTrace(System.out); } }
运行时,当RIA尝试打开或保存文件时,用户会看到一个安全对话框,询问他们是否允许该操作。只有用户允许RIA访问他们的环境,操作才会继续进行。
下面显示了FileHandler类的完整源代码。
// 在编译期间将javaws.jar添加到类路径中 import javax.jnlp.FileOpenService; import javax.jnlp.FileSaveService; import javax.jnlp.FileContents; import javax.jnlp.ServiceManager; import javax.jnlp.UnavailableServiceException; import java.io.*; public class FileHandler { static private FileOpenService fos = null; static private FileSaveService fss = null; static private FileContents fc = null; // 检索JNLP服务的引用 private static synchronized void initialize() { if (fss != null) { return; } try { fos = (FileOpenService) ServiceManager.lookup("javax.jnlp.FileOpenService"); fss = (FileSaveService) ServiceManager.lookup("javax.jnlp.FileSaveService"); } catch (UnavailableServiceException e) { fos = null; fss = null; } } // 显示打开文件对话框并使用FileOpenService读取所选文件 public static String open() { initialize(); try { fc = fos.openFileDialog(null, null); return readFromFile(fc); } catch (IOException ioe) { ioe.printStackTrace(System.out); return null; } } // 显示保存文件对话框并使用FileSaveService保存文件 public static void save(String txt) { initialize(); try { // 如果未提供文件名,则显示保存对话框 if (fc == null) { fc = fss.saveFileDialog(null, null, new ByteArrayInputStream(txt.getBytes()), null); // 文件已保存,完成 return; } // 仅当已知文件名时使用此选项 if (fc != null) { writeToFile(txt, fc); } } catch (IOException ioe) { ioe.printStackTrace(System.out); } } // 显示另存为文件对话框并使用FileSaveService保存文件 public static void saveAs(String txt) { initialize(); try { if (fc == null) { // 如果还未保存,则保存为和保存操作相同 save(txt); } else { fc = fss.saveAsFileDialog(null, null, fc); save(txt); } } catch (IOException ioe) { ioe.printStackTrace(System.out); } } private static void writeToFile(String txt, FileContents fc) throws IOException { int sizeNeeded = txt.length() * 2; if (sizeNeeded > fc.getMaxLength()) { fc.setMaxLength(sizeNeeded); } BufferedWriter os = new BufferedWriter(new OutputStreamWriter(fc.getOutputStream(true))); os.write(txt); os.close(); } private static String readFromFile(FileContents fc) throws IOException { if (fc == null) { return null; } BufferedReader br = new BufferedReader(new InputStreamReader(fc.getInputStream())); StringBuffer sb = new StringBuffer((int) fc.getLength()); String line = br.readLine(); while (line != null) { sb.append(line); sb.append("\n"); line = br.readLine(); } br.close(); return sb.toString(); } }
javax.jnlp
包中类的Java代码时,需要将<你的JDK路径>/jre/lib/javaws.jar
包含在类路径中。在运行时,Java Runtime Environment软件会自动将这些类提供给RIA应用程序。
下载文本编辑器小程序示例的源代码以进行更进一步的实验。