Classes in this File | Line Coverage | Branch Coverage | Complexity | ||||
ResourceLoader |
|
| 2.5384615384615383;2.538 |
1 | /* $Id: ResourceLoader.java 18319 2010-04-20 23:50:51Z euluis $ | |
2 | ***************************************************************************** | |
3 | * Copyright (c) 2009 Contributors - see below | |
4 | * All rights reserved. This program and the accompanying materials | |
5 | * are made available under the terms of the Eclipse Public License v1.0 | |
6 | * which accompanies this distribution, and is available at | |
7 | * http://www.eclipse.org/legal/epl-v10.html | |
8 | * | |
9 | * Contributors: | |
10 | * tfmorris | |
11 | ***************************************************************************** | |
12 | * | |
13 | * Some portions of this file was previously release using the BSD License: | |
14 | */ | |
15 | ||
16 | // Copyright (c) 1996-2006 The Regents of the University of California. All | |
17 | // Rights Reserved. Permission to use, copy, modify, and distribute this | |
18 | // software and its documentation without fee, and without a written | |
19 | // agreement is hereby granted, provided that the above copyright notice | |
20 | // and this paragraph appear in all copies. This software program and | |
21 | // documentation are copyrighted by The Regents of the University of | |
22 | // California. The software program and documentation are supplied "AS | |
23 | // IS", without any accompanying services from The Regents. The Regents | |
24 | // does not warrant that the operation of the program will be | |
25 | // uninterrupted or error-free. The end-user understands that the program | |
26 | // was developed for research purposes and is advised not to rely | |
27 | // exclusively on the program for any reason. IN NO EVENT SHALL THE | |
28 | // UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR DIRECT, INDIRECT, | |
29 | // SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES, INCLUDING LOST PROFITS, | |
30 | // ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF | |
31 | // THE UNIVERSITY OF CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF | |
32 | // SUCH DAMAGE. THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY | |
33 | // WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF | |
34 | // MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE | |
35 | // PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND THE UNIVERSITY OF | |
36 | // CALIFORNIA HAS NO OBLIGATIONS TO PROVIDE MAINTENANCE, SUPPORT, | |
37 | // UPDATES, ENHANCEMENTS, OR MODIFICATIONS. | |
38 | ||
39 | package org.argouml.application.helpers; | |
40 | ||
41 | import java.util.ArrayList; | |
42 | import java.util.HashMap; | |
43 | import java.util.Iterator; | |
44 | import java.util.List; | |
45 | ||
46 | import javax.swing.Icon; | |
47 | import javax.swing.ImageIcon; | |
48 | ||
49 | /** | |
50 | * This class manages the resource locations needed within the application. | |
51 | * Already loaded resources are cached. The resources can be searched in | |
52 | * different locations. | |
53 | * <p> | |
54 | * Derived from org.tigris.gef.util.ResourceLoader with formatting and | |
55 | * variable naming changed to conform to ArgoUML coding standard. | |
56 | * <p> | |
57 | * We use a local copy to reduce coupling to GEF and so that GEF isn't trying | |
58 | * to do uplevel accesses to the application resources (which won't work in | |
59 | * environments that enforce strict partitioning between projects eg Eclipse). | |
60 | * | |
61 | * @author Original Author: Thorsten Sturm | |
62 | */ | |
63 | ||
64 | // NOTE: This is package scope to force callers to use ResourceLoaderWrapper | |
65 | 0 | class ResourceLoader { |
66 | 900 | private static HashMap<String, Icon> resourceCache = |
67 | new HashMap<String, Icon>(); | |
68 | 900 | private static List<String> resourceLocations = new ArrayList<String>(); |
69 | 900 | private static List<String> resourceExtensions = new ArrayList<String>(); |
70 | ||
71 | public static ImageIcon lookupIconResource(String resource) { | |
72 | 47187 | return lookupIconResource(resource, resource); |
73 | } | |
74 | ||
75 | public static ImageIcon lookupIconResource(String resource, String desc) { | |
76 | 174742 | return lookupIconResource(resource, desc, null); |
77 | } | |
78 | ||
79 | public static ImageIcon lookupIconResource(String resource, | |
80 | ClassLoader loader) { | |
81 | 0 | return lookupIconResource(resource, resource, loader); |
82 | } | |
83 | ||
84 | /** | |
85 | * This method tries to find an ImageIcon for the given name in all known | |
86 | * locations. The file extension of the used image file can be any of the | |
87 | * known extensions. | |
88 | * | |
89 | * @param resource | |
90 | * Name of the image to be looked after. | |
91 | * @param desc | |
92 | * A description for the ImageIcon. | |
93 | * @param loader | |
94 | * The class loader that should be used for loading the resource. | |
95 | * @return ImageIcon for the given name, null if no image could be found. | |
96 | */ | |
97 | public static ImageIcon lookupIconResource(String resource, String desc, | |
98 | ClassLoader loader) { | |
99 | 174742 | resource = toJavaIdentifier(resource); |
100 | 174742 | if (isInCache(resource)) { |
101 | 59939 | return (ImageIcon) resourceCache.get(resource); |
102 | } | |
103 | ||
104 | 114803 | ImageIcon res = null; |
105 | 114803 | java.net.URL imgURL = lookupIconUrl(resource, loader); |
106 | ||
107 | 114803 | if (imgURL != null) { |
108 | 107095 | res = new ImageIcon(imgURL, desc); |
109 | 107095 | synchronized (resourceCache) { |
110 | 107095 | resourceCache.put(resource, res); |
111 | 107095 | } |
112 | } | |
113 | 114803 | return res; |
114 | } | |
115 | ||
116 | /** | |
117 | * Search for the given resource with one of the registered extensions, in | |
118 | * one of the registered locations. The URL of the first found is returned. | |
119 | * | |
120 | * @param resource | |
121 | * base name of resource to search for | |
122 | * @param loader | |
123 | * class loader to use | |
124 | * @return URL representing first location the resource was found or null if | |
125 | * it was not found in any of the registered locations. | |
126 | */ | |
127 | static java.net.URL lookupIconUrl(String resource, | |
128 | ClassLoader loader) { | |
129 | 114803 | java.net.URL imgURL = null; |
130 | 114803 | for (Iterator extensions = resourceExtensions.iterator(); |
131 | 131168 | extensions.hasNext();) { |
132 | 123460 | String tmpExt = (String) extensions.next(); |
133 | 123460 | for (Iterator locations = resourceLocations.iterator(); |
134 | 615090 | locations.hasNext();) { |
135 | 598725 | String imageName = |
136 | locations.next() + "/" + resource + "." + tmpExt; | |
137 | // System.out.println("[ResourceLoader] try loading " + imageName); | |
138 | 598725 | if (loader == null) { |
139 | 598725 | imgURL = ResourceLoader.class.getResource(imageName); |
140 | } else { | |
141 | 0 | imgURL = loader.getResource(imageName); |
142 | } | |
143 | 598725 | if (imgURL != null) { |
144 | 107095 | break; |
145 | } | |
146 | 491630 | } |
147 | 123460 | if (imgURL != null) { |
148 | 107095 | break; |
149 | } | |
150 | 16365 | } |
151 | 114803 | return imgURL; |
152 | } | |
153 | ||
154 | /** | |
155 | * Adds a location (path) to the list of known locations. Locations are | |
156 | * searched in the order they are added, so for best performance add the | |
157 | * most likely locations first. | |
158 | * | |
159 | * @param location | |
160 | * String representation of the new location. | |
161 | */ | |
162 | public static void addResourceLocation(String location) { | |
163 | 6300 | if (!containsLocation(location)) { |
164 | 6300 | resourceLocations.add(location); |
165 | } | |
166 | 6300 | } |
167 | ||
168 | /** | |
169 | * Add an extension to the list of known extensions. Extensions are searched | |
170 | * in the order they are added, so for best performance add the most likely | |
171 | * extensions first. | |
172 | * | |
173 | * @param extension | |
174 | * String representation of the new extension. | |
175 | */ | |
176 | public static void addResourceExtension(String extension) { | |
177 | 1800 | if (!containsExtension(extension)) { |
178 | 1800 | resourceExtensions.add(extension); |
179 | } | |
180 | 1800 | } |
181 | ||
182 | /** | |
183 | * This method removes a location from the list of known locations. | |
184 | * | |
185 | * @param location | |
186 | * String representation of the location to be removed. | |
187 | */ | |
188 | public static void removeResourceLocation(String location) { | |
189 | 0 | for (Iterator iter = resourceLocations.iterator(); iter.hasNext();) { |
190 | 0 | String loc = (String) iter.next(); |
191 | 0 | if (loc.equals(location)) { |
192 | 0 | resourceLocations.remove(loc); |
193 | 0 | break; |
194 | } | |
195 | 0 | } |
196 | 0 | } |
197 | ||
198 | /** | |
199 | * This method removes a extension from the list of known extensions. | |
200 | * | |
201 | * @param extension String representation of the extension to be removed. | |
202 | */ | |
203 | public static void removeResourceExtension(String extension) { | |
204 | 0 | for (Iterator iter = resourceExtensions.iterator(); iter.hasNext();) { |
205 | 0 | String ext = (String) iter.next(); |
206 | 0 | if (ext.equals(extension)) { |
207 | 0 | resourceExtensions.remove(ext); |
208 | 0 | break; |
209 | } | |
210 | 0 | } |
211 | 0 | } |
212 | ||
213 | public static boolean containsExtension(String extension) { | |
214 | 1800 | return resourceExtensions.contains(extension); |
215 | } | |
216 | ||
217 | public static boolean containsLocation(String location) { | |
218 | 6300 | return resourceLocations.contains(location); |
219 | } | |
220 | ||
221 | public static boolean isInCache(String resource) { | |
222 | 174742 | return resourceCache.containsKey(resource); |
223 | } | |
224 | ||
225 | /* | |
226 | * Strip all characters out of <var>s</var> that could not be part of a | |
227 | * valid Java identifier. Return either the given string (if all characters | |
228 | * were valid), or a new string with all invalid characters stripped out. | |
229 | * This allows automatic conversion of strings containing punctuation and | |
230 | * spaces to a resource name that can be looked up. | |
231 | */ | |
232 | public static final String toJavaIdentifier(String s) { | |
233 | 174742 | int len = s.length(); |
234 | 174742 | int pos = 0; |
235 | 1711214 | for (int i = 0; i < len; i++, pos++) { |
236 | 1599152 | if (!Character.isJavaIdentifierPart(s.charAt(i))) break; |
237 | } | |
238 | 174742 | if (pos == len) { |
239 | 112062 | return s; |
240 | } | |
241 | ||
242 | 62680 | StringBuffer buf = new StringBuffer(len); |
243 | 62680 | buf.append(s.substring(0, pos)); |
244 | ||
245 | // skip pos, we know it's not a valid char from above | |
246 | 524419 | for (int i = pos + 1; i < len; i++) { |
247 | 461739 | char c = s.charAt(i); |
248 | 461739 | if (Character.isJavaIdentifierPart(c)) { |
249 | 407178 | buf.append(c); |
250 | } | |
251 | } | |
252 | 62680 | return buf.toString(); |
253 | } | |
254 | } /* end class ResourceLoader */ | |
255 |