File: MapSource.java

package info (click to toggle)
gpsprune 17-1
  • links: PTS, VCS
  • area: main
  • in suites: jessie, jessie-kfreebsd
  • size: 3,984 kB
  • ctags: 5,218
  • sloc: java: 39,403; sh: 25; makefile: 17; python: 15
file content (167 lines) | stat: -rw-r--r-- 4,450 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
package tim.prune.gui.map;

import java.net.MalformedURLException;
import java.net.URL;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * Class to represent any map source, whether an OsmMapSource
 * or one of the more complicated ones.
 * Map sources may contain just one or several layers, and may
 * build their URLs in different ways depending on the source
 */
public abstract class MapSource
{
	/** File extensions */
	protected String[] _extensions = null;

	/** Regular expression for catching server wildcards */
	protected static final Pattern WILD_PATTERN = Pattern.compile("^(.*)\\[(.*)\\](.*)$");


	/**
	 * @return the number of layers used in this source
	 */
	public abstract int getNumLayers();

	/**
	 * @return the name of the source
	 */
	public abstract String getName();

	/**
	 * @return the base url for the specified layer
	 */
	public abstract String getBaseUrl(int inLayerNum);

	/**
	 * @return the site name for the specified layer
	 */
	public abstract String getSiteName(int inLayerNum);

	/**
	 * @return the file extension for the specified layer
	 */
	public final String getFileExtension(int inLayerNum) {
		return _extensions[inLayerNum];
	}

	/**
	 * Make the URL to get the specified tile
	 * @param inLayerNum number of layer, from 0 (base) to getNumLayers-1 (top)
	 * @param inZoom zoom level
	 * @param inX x coordinate of tile
	 * @param inY y coordinate of tile
	 * @return URL as string
	 */
	public abstract String makeURL(int inLayerNum, int inZoom, int inX, int inY);

	/**
	 * @return the maximum zoom level for this source
	 */
	public abstract int getMaxZoomLevel();

	/**
	 * Make a relative file path from the base directory including site name
	 * @param inLayerNum layer number
	 * @param inZoom zoom level
	 * @param inX x coordinate
	 * @param inY y coordinate
	 * @return relative file path as String
	 */
	public String makeFilePath(int inLayerNum, int inZoom, int inX, int inY)
	{
		return getSiteName(inLayerNum) + inZoom + "/" + inX + "/" + inY + "." + getFileExtension(inLayerNum);
	}

	/**
	 * Checks the given url for having the right prefix and trailing slash
	 * @param inUrl url to check
	 * @return validated url with correct prefix and trailing slash, or null
	 */
	public static String fixBaseUrl(String inUrl)
	{
		if (inUrl == null || inUrl.equals("")) {return null;}
		String urlstr = inUrl;
		// check prefix
		try {
			new URL(urlstr.replace('[', 'w').replace(']', 'w'));
			// There's a warning that this URL object isn't used, but it's enough to know the parse
			// was successful without an exception being thrown.
		}
		catch (MalformedURLException e)
		{
			// fail if protocol specified
			if (urlstr.indexOf("://") >= 0) {return null;}
			// add the http protocol
			urlstr = "http://" + urlstr;
		}
		// check trailing /
		if (!urlstr.endsWith("/")) {
			urlstr = urlstr + "/";
		}
		// Validate current url, return null if not ok
		try {
			URL url = new URL(urlstr.replace('[', 'w').replace(']', 'w'));
			// url host must contain a dot
			if (url.getHost().indexOf('.') < 0) {return null;}
		}
		catch (MalformedURLException e) {
			urlstr = null;
		}
		return urlstr;
	}

	/**
	 * Fix the site name by stripping off protocol and www.
	 * This is used to create the file path for disk caching
	 * @param inUrl url to strip
	 * @return stripped url
	 */
	protected static String fixSiteName(String inUrl)
	{
		if (inUrl == null || inUrl.equals("")) {return null;}
		String url = inUrl.toLowerCase();
		int idx = url.indexOf("://");
		if (idx >= 0) {url = url.substring(idx + 3);}
		if (url.startsWith("www.")) {url = url.substring(4);}
		// Strip out any "[.*]" as well
		if (url.indexOf('[') >= 0)
		{
			Matcher matcher = WILD_PATTERN.matcher(url);
			if (matcher.matches()) {
				url = matcher.group(1) + matcher.group(3);
				if (url.length() > 1 && url.charAt(0) == '.') {
					url = url.substring(1);
				}
			}
		}
		return url;
	}

	/**
	 * @return string which can be written to the Config
	 */
	public abstract String getConfigString();

	/**
	 * @return semicolon-separated list of base urls and extensions in order
	 */
	public String getSiteStrings()
	{
		StringBuilder sb = new StringBuilder();
		for (int i=0; i<getNumLayers(); i++)
		{
			String url = getBaseUrl(i);
			if (url != null)
			{
				sb.append(url);
				sb.append(';');
				sb.append(getFileExtension(i));
				sb.append(';');
			}
		}
		return sb.toString();
	}
}