001 /* 002 * Copyright (c) Holger Pfaff - http://pfaff.ws 003 * 004 * This software maybe used for any purpose provided the 005 * above copyright notice is retained. It is supplied as is. 006 * No warranty expressed or implied - Use at your own risk. 007 */ 008 009 import java.util.Vector; 010 import java.util.Hashtable; 011 import java.util.Enumeration; 012 import java.util.PropertyResourceBundle; 013 014 /** 015 * (#)Util.java 016 * @author Holger Pfaff 017 * @version 3.2 19-Mar-2004<br><br> 018 * 019 * Various utility routines for use with j-awt 020 */ 021 022 public class Util { 023 024 /** 025 * Find index of Object within array 026 * 027 * @return index or -1 on failure 028 * 029 * @param array the array to search within 030 * @param obj the object to search for 031 */ 032 static int indexOf(Object[] array, Object obj) { 033 return indexOf(array, obj, 0); 034 } 035 036 /** 037 * Find index of Object within array 038 * starting at a specified index 039 * 040 * @return index or -1 on failure 041 * 042 * @param array the array to search within 043 * @param obj the object to search for 044 * @param start index to start from 045 */ 046 static int indexOf(Object[] array, Object obj, int start) { 047 if(array != null) { 048 for(int i = start; i < array.length; ++i) { 049 if(array[i].equals(obj)) return i; 050 } 051 } 052 return -1; 053 } 054 055 /** 056 * Convert an arbitrary array of Objects into a Vector 057 * 058 * @return resulting Vector 059 * 060 * @param array the array to convert 061 */ 062 static Vector array2Vector(Object[] array) { 063 return array2Vector(array, 0); 064 } 065 066 /** 067 * Convert an arbitrary array of Objects into a Vector 068 * starting at a specified index 069 * 070 * @return resulting Vector 071 * 072 * @param array the array to convert 073 * @param start the index to start from 074 */ 075 static Vector array2Vector(Object[] array, int start) { 076 Vector v = new Vector(); 077 if(array != null) { 078 for(int i = start; i < array.length; ++i) { 079 v.addElement(array[i]); 080 } 081 } 082 return v; 083 } 084 085 /** 086 * Convert an arbitrary Enumeration into an Array of Strings 087 * 088 * @return resulting String array 089 * 090 * @param e the enumeration to convert 091 */ 092 public static String[] enum2Array(Enumeration e) { 093 Vector v = enum2Vector(e); 094 String[] r = new String[v.size()]; 095 for(int i =0; i < r.length; ++i) { 096 r[i] = v.elementAt(i).toString(); 097 } 098 return r; 099 } 100 101 /** 102 * Convert an arbitrary Enumeration into a Vector 103 * 104 * @return resulting Vector 105 * 106 * @param e the enumeration to convert 107 */ 108 public static Vector enum2Vector(Enumeration e) { 109 Vector r = new Vector(); 110 while(e.hasMoreElements()) { 111 r.addElement(e.nextElement()); 112 } 113 return r; 114 } 115 116 /** 117 * Convert an arbitrary Enumeration into a single String 118 * separated with a specified delimiter character 119 * 120 * @return resulting String 121 * 122 * @param e the enumeration to convert 123 * @param dl the delimiter to use 124 */ 125 public static String enum2String(Enumeration e, String dl) { 126 String r = e.hasMoreElements() ? e.nextElement().toString() : ""; 127 while(e.hasMoreElements()) { 128 r += dl + e.nextElement().toString(); 129 } 130 return r; 131 } 132 133 /** 134 * Invoke an arbitrary method of an Object<br> 135 * <code>Util.invoke(myclass, "printx hello world")</code> would call 136 * method printx of object myclass with "printx" "hello" "world" as arguments. 137 * Method printx should be defined as <code>public void printx(Vector argv)</code> 138 * 139 * @param o class instance to use 140 * @param argv the argument vector as blank separated string 141 */ 142 static void invoke(Object o, String argv) { 143 invoke(o, new StringSplitter(argv, " ", false).toVector()); 144 } 145 146 /** 147 * Invoke an arbitrary method of an Object<br> 148 * 149 * @param o class instance to use 150 * @param argv the arguments as a Vector list 151 */ 152 static void invoke(Object o, Vector argv) { 153 try { 154 Class argt[] = {Vector.class}; 155 Object args[] = {argv}; 156 o.getClass().getMethod((String) argv.elementAt(0), argt).invoke(o, args); 157 } catch(Exception x) { 158 Debug.debug(Util.class, x); 159 } 160 } 161 162 /** 163 * Get contents of a properties file as a Hashtable. Tries to load 164 * <name>.properties first then <name>_<lang>.properties. If that fails 165 * try to load default lang "en". Depending on JVM used the properties 166 * file has to reside within the jar archive of the current applet 167 * 168 * @return Hashtable containing key/value pairs from properties files 169 * 170 * @param name name of properties to load 171 * @param lang language of properties to load 172 */ 173 static Hashtable getResourceHash(String name, String lang) { 174 Hashtable h = new Hashtable(); 175 Util.putResourceHash(name, h, h); 176 if(Util.putResourceHash(name + "_" + lang, h, null) == null) { 177 Util.putResourceHash(name + "_en", h, null); 178 } 179 return h; 180 } 181 182 /** 183 * Convert content of a specific property file to a hashtable. This method 184 * get called by getResourceHash() to actually do the work. 185 * 186 * @return Hashtable containing key/value pairs from properties file 187 * 188 * @param name name of properties to load 189 * @param h hashtable to put values in 190 * @param dh default hashtable to return in case of errors 191 */ 192 static Hashtable putResourceHash(String name, Hashtable h, Hashtable dh) { 193 try { 194 PropertyResourceBundle r = new PropertyResourceBundle(Util.class.getResourceAsStream(name + ".properties")); 195 for(Enumeration e = r.getKeys(); e.hasMoreElements(); ) { 196 String k = (String) e.nextElement(); 197 h.put(k, r.getObject(k)); 198 } 199 return h; 200 } catch(Exception x) { 201 Debug.debug(Util.class, x); 202 return dh; 203 } 204 } 205 206 /** 207 * Do shell-style pattern matching for ?, \, [], and * characters. 208 * Negate a class with ^ is also possible. Char ranges should work fine 209 * as long as you stick to ascii chars. As java uses Unicode all other 210 * ranges might not work as expected. 211 * Original version written in C by Rich $alz. 212 * 213 * @return 0 = false, no match 1 = true, matches 2 = abort, no match, invalid syntax 214 * 215 * @param text text to find pattern in 216 * @param pattern pattern to search for 217 * 218 */ 219 static int match(String text, String pattern) { 220 char[] T = text.toCharArray(); 221 char[] P = pattern.toCharArray(); 222 int t = 0; // current pointer within <text> 223 int p = 0; // current pointer within <pattern> 224 int m = 0; // does it match (0,1,2) 225 for(; p < P.length; t++, p++) { 226 if(t == T.length && P[p] != '*') return 2; 227 switch(P[p]) { 228 case '\\': // literal match with following character. Fallthrough 229 p++; 230 default: // match one char 231 if(p == P.length || T[t] != P[p]) return 0; 232 continue; 233 case '?': // match anything 234 continue; 235 case '*': // match everything 236 while(++p < P.length && P[p] == '*') continue; // consecutive stars act just like one 237 if(p == P.length) return 1; // trailing star matches everything 238 while(t < T.length) { // match the rest recursive 239 if((m = match(text.substring(t++), pattern.substring(p))) != 0) return m; 240 } 241 return 2; 242 case '[': // match char ranges (beware: java uses unicode!) 243 char l = ' '; 244 int r = p < P.length - 2 && P[p + 1] == '^' ? 1 : 0; 245 if(r == 1) p++; // inverted matching ? 246 for(m = 0; ++p < P.length && P[p] != ']'; l = P[p]) { 247 if(P[p] == '-' ? ++p <= P.length && T[t] <= P[p] && T[t] >= l : T[t] == P[p]) m = 1; 248 } 249 if(m == r) return 0; 250 continue; 251 } 252 } 253 return t == T.length ? 1 : 0; 254 } 255 }