+ try
+ {
+ HttpURLConnection conn = (HttpURLConnection) inTileUrl.openConnection();
+ conn.setRequestProperty("User-Agent", "GpsPrune v" + GpsPrune.VERSION_NUMBER);
+ int status = conn.getResponseCode();
+ if (status == 200)
+ {
+ return conn.getInputStream();
+ }
+ else if (status == 404)
+ {
+ throw new SrtmSourceException("Tile not found: "+conn.getURL());
+ }
+ else
+ {
+ throw new SrtmSourceException("Invalid response from server: " +status+conn.getContent());
+ }
+ }
+ catch (IOException e)
+ {
+ throw new SrtmSourceException("Error while downloading tile from "+inTileUrl+": "+e.getMessage());
+ }
+ }
+
+ /**
+ * Helper for downloadTile()
+ * @param inStream Stream to read from, typically from HTTP connection
+ * @param outputFile Where to save the data being read
+ */
+ protected boolean readToFile(InputStream inStream, File outputFile)
+ throws SrtmSourceException
+ {
+ try
+ {
+ FileOutputStream outStream = new FileOutputStream(outputFile);
+
+ byte[] buffer = new byte[4096];
+ int read = 0;
+ while ((read = inStream.read(buffer)) != -1)
+ {
+ outStream.write(buffer, 0, read);
+ }
+ // Make sure streams are closed
+ try {inStream.close();} catch (Exception e) {}
+ try {outStream.close();} catch (Exception e) {}
+ return true;
+ }
+ catch (IOException e)
+ {
+ throw new SrtmSourceException("Error downloading tile:" + e.getMessage());
+ }
+ }
+
+ /**
+ * Helper for getTileHeights
+ * @param inStream Stream to read from, assumed to have been advanced
+ * to the appropriate tile
+ * @param tileSize the expected tileSize (square of getRowSize; assumed
+ * to have been checked by the caller)
+ * @return the tile heights
+ */
+ protected int[] slurpTileHeigths(ZipInputStream inStream, int tileSize)
+ throws IOException
+ {
+ int[] heights = new int[tileSize];
+ int dataSize = 2 * tileSize;
+ byte[] buffer = new byte[dataSize];
+ // Read entire file contents into one byte array
+ int alreadyRead = 0;
+ while (alreadyRead < dataSize)
+ {
+ alreadyRead += inStream.read(buffer, alreadyRead, dataSize - alreadyRead);
+ }
+ for (int i = 0; i < tileSize; i++)
+ {
+ // Bytes are signed. Cast high-order to int with sign
+ // extension, and clamp low-order to its unsigned range
+ heights[i] = buffer[2 * i] * 256 + (0xff & buffer[2 * i + 1]);
+ }
+ // Close stream
+ inStream.close();
+ return heights;