1 package tim.prune.gui.map;
4 import java.awt.Toolkit;
5 import java.io.IOException;
6 import java.io.InputStream;
8 import java.net.URLConnection;
9 import java.util.HashSet;
11 import tim.prune.GpsPrune;
14 * Class to asynchronously download a tile from a url
15 * and populate an Image object with the contents
17 public class TileDownloader implements Runnable
19 private MapTileManager _manager = null;
20 private URL _url = null;
21 private int _layer = 0;
22 private int _x = 0, _y = 0;
23 private int _zoom = 0;
24 /** Hashset of all blocked / 404 tiles to avoid requesting them again */
25 private static final HashSet<String> BLOCKED_URLS = new HashSet<String>();
26 /** Hashset of all currently loading tiles to avoid requesting them again */
27 private static final HashSet<String> LOADING_URLS = new HashSet<String>();
31 * Constructor (private)
32 * @param inManager parent manager for callback
33 * @param inUrl URL to load
34 * @param inLayer layer index from 0
35 * @param inX x coordinate of tile
36 * @param inY y coordinate of tile
37 * @param inZoom zoom level
39 private TileDownloader(MapTileManager inManager, URL inUrl, int inLayer, int inX, int inY, int inZoom)
49 * Trigger a download in a new thread
50 * @param inManager manager to callback when image is loaded
51 * @param inUrl URL to load
52 * @param inLayer layer index from 0
53 * @param inX x coordinate of tile
54 * @param inY y coordinate of tile
55 * @param inZoom current zoom level
57 public static synchronized void triggerLoad(MapTileManager inManager, URL inUrl, int inLayer,
58 int inX, int inY, int inZoom)
60 if (inManager != null && inUrl != null)
62 String url = inUrl.toString();
63 // System.out.println("Trigger load: " + url);
64 if (!BLOCKED_URLS.contains(url) && !LOADING_URLS.contains(url))
66 // System.out.println("Not blocked: " + url);
67 LOADING_URLS.add(url);
68 new Thread(new TileDownloader(inManager, inUrl, inLayer, inX, inY, inZoom)).start();
74 * Run method, called in separate thread
78 InputStream in = null;
81 // System.out.println("TD Running thread to get: " + _url.toString());
82 // Set http user agent on connection
83 URLConnection conn = _url.openConnection();
84 conn.setRequestProperty("User-Agent", "GpsPrune v" + GpsPrune.VERSION_NUMBER);
85 in = conn.getInputStream();
86 int len = conn.getContentLength();
89 byte[] data = new byte[len];
91 while (totalRead < len)
93 int numRead = in.read(data, totalRead, len-totalRead);
96 Image tile = Toolkit.getDefaultToolkit().createImage(data);
99 // Pass back to manager so it can be stored in its memory cache
100 _manager.notifyImageLoaded(tile, _layer, _x, _y, _zoom);
103 catch (IOException e)
105 System.err.println("IOE: " + e.getClass().getName() + " - " + e.getMessage());
106 synchronized(this.getClass())
108 BLOCKED_URLS.add(_url.toString());
110 try {in.close();} catch (Exception e2) {}
112 LOADING_URLS.remove(_url.toString());