1 /* 2 * $Id$ 3 * 4 * Copyright (c) 2017, Oracle and/or its affiliates. All rights reserved. 5 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 6 * 7 * This code is free software; you can redistribute it and/or modify it 8 * under the terms of the GNU General Public License version 2 only, as 9 * published by the Free Software Foundation. Oracle designates this 10 * particular file as subject to the "Classpath" exception as provided 11 * by Oracle in the LICENSE file that accompanied this code. 12 * 13 * This code is distributed in the hope that it will be useful, but WITHOUT 14 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 15 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 16 * version 2 for more details (a copy is included in the LICENSE file that 17 * accompanied this code). 18 * 19 * You should have received a copy of the GNU General Public License version 20 * 2 along with this work; if not, write to the Free Software Foundation, 21 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 22 * 23 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 24 * or visit www.oracle.com if you need additional information or have any 25 * questions. 26 */ 27 package com.sun.javatest.tool.jthelp; 28 29 import com.sun.javatest.ProductInfo; 30 import com.sun.javatest.tool.Preferences; 31 32 import javax.swing.*; 33 import java.awt.*; 34 import java.awt.event.ActionEvent; 35 import java.awt.event.ActionListener; 36 import java.awt.event.KeyEvent; 37 import java.io.*; 38 import java.net.URL; 39 import java.nio.charset.StandardCharsets; 40 import java.util.Enumeration; 41 import java.util.HashMap; 42 import java.util.Scanner; 43 import java.util.jar.JarEntry; 44 import java.util.jar.JarFile; 45 46 public class JTHelpBroker implements HelpBroker{ 47 48 private static final String HELP_DIR_NAME = "jthelp"; 49 private static final String HELP_VERSION_NAME = "version"; 50 private static final String HELP_FILE_PREFIX = "/com/sun/javatest/help/default/"; 51 private static final String HELP_FILE_NAME = "map.xml"; 52 private HashMap<String, String> helpMap; 53 54 public JTHelpBroker(){ 55 this(HelpBroker.class.getResource(HELP_FILE_PREFIX+HELP_FILE_NAME)); 56 } 57 58 private JTHelpBroker(URL url){ 59 helpMap = HelpSet.readHelpMap(url); 60 } 61 62 public void enableHelpKey(final Component component, String helpID){ 63 if (component instanceof JComponent) { 64 KeyStroke keystroke = KeyStroke.getKeyStroke(KeyEvent.VK_F1, 0, false); 65 ((JComponent)component).registerKeyboardAction(new ActionListener() { 66 @Override 67 public void actionPerformed(ActionEvent e) { 68 displayCurrentID(ContextHelpManager.getHelpIDString(component)); 69 } 70 }, keystroke, JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT); 71 } 72 ContextHelpManager.setHelpIDString(component, helpID); 73 } 74 75 private boolean isHelpUpToDate(){ 76 File helpDir = new File(Preferences.getPrefsDir(), HELP_DIR_NAME); 77 if (!helpDir.exists()) { 78 return false; 79 } 80 File helpVersion = new File(helpDir, HELP_VERSION_NAME); 81 try { 82 Scanner scanner = new Scanner(helpVersion, StandardCharsets.UTF_8.name()); 83 String version = scanner.nextLine(); 84 if (version == null || !version.equals(ProductInfo.getVersion()+ProductInfo.getBuildNumber())){ 85 return false; 86 } 87 } catch (IOException e) { 88 return false; 89 } 90 91 92 return true; 93 } 94 95 private void unpackHelpIfNeeded(){ 96 97 if (isHelpUpToDate()){ 98 return; 99 } 100 101 JTHelpProgressBar jtHelpProgressBar = new JTHelpProgressBar(new ProgressTask()); 102 jtHelpProgressBar.createAndShowGUI(); 103 104 } 105 106 public void displayCurrentID(String helpID){ 107 108 unpackHelpIfNeeded(); 109 110 try { 111 File helpDir = new File(Preferences.getPrefsDir(), HELP_DIR_NAME); 112 String helpPage = helpMap.get(helpID) != null ? helpMap.get(helpID) : "jthelp.html"; 113 StringBuilder address = new StringBuilder(); 114 address.append("file:").append(helpDir.getAbsolutePath()).append(HELP_FILE_PREFIX).append(helpPage); 115 URL url = new URL(address.toString()); 116 Desktop.getDesktop().browse(url.toURI()); 117 } catch (Exception e) { 118 System.err.println("Cannot open JavaTest help file:"); 119 System.err.println(e.getMessage()); 120 } 121 } 122 123 class ProgressTask extends SwingWorker<Void, Void> { 124 @Override 125 public Void doInBackground() { 126 try { 127 File jarFile = new File(HelpBroker.class.getProtectionDomain().getCodeSource().getLocation().toURI()); 128 File destDir = new File(Preferences.getPrefsDir(), HELP_DIR_NAME); 129 File helpVersion = new File(destDir, HELP_VERSION_NAME); 130 131 JarFile jar = new JarFile(jarFile); 132 Enumeration enumEntries = jar.entries(); 133 134 int total = 0; 135 while (enumEntries.hasMoreElements()) { 136 JarEntry file = (JarEntry) enumEntries.nextElement(); 137 if (isHelpFile(file)) { 138 total++; 139 } 140 } 141 142 if (destDir.exists()){ 143 destDir.delete(); 144 } 145 146 destDir.mkdir(); 147 148 int progress = 0; 149 setProgress((int) (progress * 100.0 / total)); 150 enumEntries = jar.entries(); 151 152 while (enumEntries.hasMoreElements()) { 153 JarEntry file = (JarEntry) enumEntries.nextElement(); 154 File f = new java.io.File(destDir + java.io.File.separator + file.getName()); 155 if (isHelpFile(file)) { 156 f.getParentFile().mkdirs(); 157 InputStream is = jar.getInputStream(file); 158 FileOutputStream fos = new java.io.FileOutputStream(f); 159 while (is.available() > 0) { 160 fos.write(is.read()); 161 } 162 fos.close(); 163 is.close(); 164 progress++; 165 setProgress((int) (progress * 100.0 / total)); 166 } 167 } 168 169 try(PrintWriter out = new PrintWriter(new OutputStreamWriter(new FileOutputStream(helpVersion), StandardCharsets.UTF_8))){ 170 out.println(ProductInfo.getVersion()+ProductInfo.getBuildNumber()); 171 } 172 173 } 174 catch (Exception e){ 175 System.err.println("Cannot unpack JavaTest help files"); 176 System.err.println(e.getMessage()); 177 } 178 179 return null; 180 } 181 182 private boolean isHelpFile(JarEntry file) { 183 return (file.getName().endsWith(".html") 184 || file.getName().endsWith(".gif") 185 || file.getName().endsWith(".css")); 186 } 187 188 } 189 190 }