Changeset 28485 in osm for applications/editors/josm
- Timestamp:
- 2012-07-14T10:53:58+02:00 (12 years ago)
- Location:
- applications/editors/josm/plugins/wikipedia/src/org/wikipedia
- Files:
-
- 1 added
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
applications/editors/josm/plugins/wikipedia/src/org/wikipedia/WikipediaToggleDialog.java
r28483 r28485 7 7 import java.awt.event.MouseAdapter; 8 8 import java.awt.event.MouseEvent; 9 import java.io.IOException;10 import java.io.UnsupportedEncodingException;11 import java.net.URL;12 import java.net.URLDecoder;13 import java.net.URLEncoder;14 import java.util.ArrayList;15 9 import java.util.Arrays; 16 import java.util.Collection;17 10 import java.util.Collections; 18 import java.util.HashMap;19 11 import java.util.HashSet; 20 12 import java.util.List; 21 import java.util.Map;22 import java.util.Scanner;23 13 import java.util.Set; 24 import java.util.regex.Matcher;25 import java.util.regex.Pattern;26 14 import javax.swing.AbstractAction; 27 15 import javax.swing.DefaultListCellRenderer; … … 30 18 import javax.swing.JList; 31 19 import javax.swing.JOptionPane; 32 import javax.xml.parsers.DocumentBuilderFactory;33 import javax.xml.xpath.XPathConstants;34 import javax.xml.xpath.XPathExpression;35 import javax.xml.xpath.XPathFactory;36 20 import org.openstreetmap.josm.Main; 37 21 import org.openstreetmap.josm.actions.search.SearchAction; … … 53 37 import org.openstreetmap.josm.tools.LanguageInfo; 54 38 import org.openstreetmap.josm.tools.OpenBrowser; 55 import org.openstreetmap.josm.tools.Utils; 56 import org.w3c.dom.Document; 57 import org.w3c.dom.NodeList; 39 import org.wikipedia.WikipediaApp.WikipediaEntry; 58 40 59 41 public class WikipediaToggleDialog extends ToggleDialog implements MapView.EditLayerChangeListener, DataSetListenerAdapter.Listener { … … 115 97 }; 116 98 117 static class WikipediaLangArticle { 118 119 final String lang, article; 120 121 public WikipediaLangArticle(String lang, String article) { 122 this.lang = lang; 123 this.article = article; 124 } 125 126 public static WikipediaLangArticle parseFromUrl(String url) { 127 if (url == null) { 128 return null; 129 } 130 // decode URL for nicer value 131 url = decodeURL(url); 132 // extract Wikipedia language and 133 final Matcher m = Pattern.compile("https?://(\\w*)\\.wikipedia\\.org/wiki/(.*)").matcher(url); 134 if (!m.matches()) { 135 return null; 136 } 137 return new WikipediaLangArticle(m.group(1), m.group(2)); 138 } 139 } 140 141 static class WikipediaEntry implements Comparable<WikipediaEntry> { 142 143 final String name, description; 144 final String wikipediaLang, wikipediaArticle; 145 final LatLon coordinate; 146 private Boolean wiwosmStatus; 147 148 public WikipediaEntry(String name, String description, LatLon coordinate) { 149 this.name = name; 150 this.description = description; 151 this.coordinate = coordinate; 152 153 final WikipediaLangArticle wp = WikipediaLangArticle.parseFromUrl(getHrefFromDescription()); 154 if (wp == null) { 155 System.err.println("Could not extract Wikipedia tag from: " + getHrefFromDescription()); 156 } 157 this.wikipediaLang = wp == null ? null : wp.lang; 158 this.wikipediaArticle = wp == null ? null : wp.article; 159 } 160 161 public WikipediaEntry(String name, String wikipediaLang, String wikipediaArticle) { 162 this.name = name; 163 this.description = null; 164 this.wikipediaLang = wikipediaLang; 165 this.wikipediaArticle = wikipediaArticle; 166 this.coordinate = null; 167 } 168 169 protected final String getHrefFromDescription() { 170 if (description == null) { 171 return null; 172 } 173 final Matcher m = Pattern.compile(".*href=\"(.+?)\".*").matcher(description); 174 if (m.matches()) { 175 return m.group(1); 176 } else { 177 System.err.println("Could not parse URL from: " + description); 178 return null; 179 } 180 } 181 182 protected final Tag createWikipediaTag() { 183 return new Tag("wikipedia", wikipediaLang + ":" + wikipediaArticle); 184 } 185 186 private void updateWiwosmStatus() { 187 try { 188 final String url = "http://toolserver.org/~master/osmjson/getGeoJSON.php?action=check" 189 + "&lang=" + wikipediaLang 190 + "&article=" + encodeURL(wikipediaArticle); 191 System.out.println("Wikipedia: GET " + url); 192 final Scanner scanner = new Scanner(new URL(url).openStream()); 193 wiwosmStatus = scanner.hasNextInt() && scanner.nextInt() == 1; 194 } catch (IOException ex) { 195 throw new RuntimeException(ex); 196 } 197 } 198 199 public void setWiwosmStatus(Boolean wiwosmStatus) { 200 this.wiwosmStatus = wiwosmStatus; 201 } 202 203 public Boolean getWiwosmStatus() { 204 return wiwosmStatus; 205 } 206 207 @Override 208 public String toString() { 209 return name; 210 } 211 212 @Override 213 public int compareTo(WikipediaEntry o) { 214 return name.compareTo(o.name); 215 } 216 } 217 218 private void setWikipediaEntries(Collection<WikipediaEntry> entries) { 219 Collection<String> articleNames = new ArrayList<String>(); 220 for (WikipediaEntry i : entries) { 221 articleNames.add(i.wikipediaArticle); 222 } 223 Map<String, Boolean> status = new HashMap<String, Boolean>(); 224 if (!articleNames.isEmpty()) { 225 final String url = "http://toolserver.org/~master/osmjson/getGeoJSON.php?action=check" 226 + "&lang=" + wikipediaLang.get() 227 + "&articles=" + encodeURL(Utils.join(",", articleNames)); 228 System.out.println("Wikipedia: GET " + url); 229 230 try { 231 final Scanner scanner = new Scanner(new URL(url).openStream()).useDelimiter("\n"); 232 while (scanner.hasNext()) { 233 //[article]\t[0|1] 234 final String line = scanner.next(); 235 final String[] x = line.split("\t"); 236 if (x.length == 2) { 237 status.put(x[0], "1".equals(x[1])); 238 } else { 239 System.err.println("Unknown element " + line); 240 } 241 } 242 } catch (Exception ex) { 243 throw new RuntimeException(ex); 244 } 245 } 246 99 private void setWikipediaEntries(List<WikipediaEntry> entries) { 100 Collections.sort(entries); 101 WikipediaApp.updateWIWOSMStatus(wikipediaLang.get(), entries); 247 102 model.clear(); 248 103 for (WikipediaEntry i : entries) { 249 i.setWiwosmStatus(status.get(i.wikipediaArticle));250 104 model.addElement(i); 251 105 } … … 265 119 LatLon min = Main.map.mapView.getLatLon(0, Main.map.mapView.getHeight()); 266 120 LatLon max = Main.map.mapView.getLatLon(Main.map.mapView.getWidth(), 0); 267 final String bbox = min.lon() + "," + min.lat() + "," + max.lon() + "," + max.lat(); 268 // construct url 269 final String url = "http://toolserver.org/~kolossos/geoworld/marks.php?" 270 + "bbox=" + bbox + "&LANG=" + wikipediaLang.get(); 271 System.out.println("Wikipedia: GET " + url); 272 // parse XML document 273 final XPathExpression xpathPlacemark = XPathFactory.newInstance().newXPath().compile("//Placemark"); 274 final XPathExpression xpathName = XPathFactory.newInstance().newXPath().compile("name/text()"); 275 final XPathExpression xpathCoord = XPathFactory.newInstance().newXPath().compile("Point/coordinates/text()"); 276 final XPathExpression xpathDescr = XPathFactory.newInstance().newXPath().compile("description"); 277 Document doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(new URL(url).openStream()); 278 NodeList nodes = (NodeList) xpathPlacemark.evaluate(doc, XPathConstants.NODESET); 279 // construct WikipediaEntry for each XML element 280 List<WikipediaEntry> entries = new ArrayList<WikipediaEntry>(nodes.getLength()); 281 for (int i = 0; i < nodes.getLength(); i++) { 282 final String[] coord = xpathCoord.evaluate(nodes.item(i)).split(","); 283 if (coord.length <= 2) { 284 continue; 285 } 286 final String name = xpathName.evaluate(nodes.item(i)); 287 final String descr = xpathDescr.evaluate(nodes.item(i)); 288 entries.add(new WikipediaEntry(name, descr, 289 new LatLon(Double.parseDouble(coord[1]), Double.parseDouble(coord[0])))); 290 } 291 Collections.sort(entries); 121 List<WikipediaEntry> entries = WikipediaApp.getEntriesFromCoordinates( 122 wikipediaLang.get(), min, max); 292 123 // add entries to list model 293 124 setWikipediaEntries(entries); … … 308 139 @Override 309 140 public void actionPerformed(ActionEvent e) { 310 try { 311 final String category = JOptionPane.showInputDialog( 312 Main.parent, 313 tr("Enter the Wikipedia category")); 314 if (category == null) { 315 return; 316 } 317 final String url = "http://toolserver.org/~daniel/WikiSense/CategoryIntersect.php?" 318 + "wikilang=" + wikipediaLang.get() 319 + "&wikifam=.wikipedia.org" 320 + "&basecat=" + encodeURL(category) 321 + "&basedeep=3&templates=&mode=al&format=csv"; 322 System.out.println("Wikipedia: GET " + url); 323 final Scanner scanner = new Scanner(new URL(url).openStream()).useDelimiter("\n"); 324 final List<WikipediaEntry> entries = new ArrayList<WikipediaEntry>(); 325 while (scanner.hasNext()) { 326 final String article = scanner.next().split("\t")[1].replace("_", " "); 327 entries.add(new WikipediaEntry(article, wikipediaLang.get(), article)); 328 } 329 Collections.sort(entries); 330 setWikipediaEntries(entries); 331 setTitle(/* I18n: [language].Wikipedia.org: [category] */ tr("{0}.Wikipedia.org: {1}", wikipediaLang.get(), category)); 332 } catch (IOException ex) { 333 throw new RuntimeException(ex); 334 } 141 final String category = JOptionPane.showInputDialog( 142 Main.parent, 143 tr("Enter the Wikipedia category")); 144 if (category == null) { 145 return; 146 } 147 List<WikipediaEntry> entries = WikipediaApp.getEntriesFromCategory(wikipediaLang.get(), category); 148 setWikipediaEntries(entries); 149 setTitle(/* I18n: [language].Wikipedia.org: [category] */ tr("{0}.Wikipedia.org: {1}", wikipediaLang.get(), category)); 335 150 } 336 151 } … … 346 161 public void actionPerformed(ActionEvent e) { 347 162 if (list.getSelectedValue() != null) { 348 WikipediaEntry entry = (WikipediaEntry) list.getSelectedValue(); 349 final String url; 350 if (entry.getHrefFromDescription() != null) { 351 url = entry.getHrefFromDescription(); 352 } else { 353 url = "http://" + entry.wikipediaLang + ".wikipedia.org/wiki/" 354 + encodeURL(entry.wikipediaArticle.replace(" ", "_")); 355 } 163 final String url = ((WikipediaEntry) list.getSelectedValue()).getBrowserUrl(); 356 164 System.out.println("Wikipedia: opening " + url); 357 165 OpenBrowser.displayUrl(url); … … 405 213 if (Main.main != null && Main.main.getCurrentDataSet() != null) { 406 214 for (final OsmPrimitive p : Main.main.getCurrentDataSet().allPrimitives()) { 407 articles.addAll(getWikipediaArticles(p)); 408 } 409 } 410 } 411 412 protected Collection<String> getWikipediaArticles(OsmPrimitive p) { 413 Collection<String> r = new ArrayList<String>(); 414 final Map<String, String> tags = p.getKeys(); 415 // consider wikipedia=[lang]:* 416 final String wp = tags.get("wikipedia"); 417 if (wp != null && wp.startsWith("http")) { 418 //wikipedia=http... 419 final WikipediaLangArticle item = WikipediaLangArticle.parseFromUrl(wp); 420 if (item != null && wikipediaLang.get().equals(item.lang)) { 421 r.add(item.article.replace("_", " ")); 422 } 423 } else if (wp != null) { 424 //wikipedia=[lang]:[article] 425 String[] item = decodeURL(wp).split(":", 2); 426 if (item.length == 2 && wikipediaLang.get().equals(item[0])) { 427 r.add(item[1].replace("_", " ")); 428 } 429 } 430 // consider wikipedia:[lang]=* 431 final String wpLang = tags.get("wikipedia:" + wikipediaLang.get()); 432 if (wpLang != null && wpLang.startsWith("http")) { 433 //wikipedia:[lang]=http... 434 final WikipediaLangArticle item = WikipediaLangArticle.parseFromUrl(wpLang); 435 if (wikipediaLang.get().equals(item.lang)) { 436 r.add(item.article.replace("_", " ")); 437 } 438 } else if (wpLang != null) { 439 //wikipedia:[lang]=[lang]:[article] 440 //wikipedia:[lang]=[article] 441 String[] item = decodeURL(wpLang).split(":", 2); 442 r.add(item[item.length == 2 ? 1 : 0].replace("_", " ")); 443 } 444 return r; 215 articles.addAll(WikipediaApp.getWikipediaArticles(wikipediaLang.get(), p)); 216 } 217 } 445 218 } 446 219 … … 472 245 list.repaint(); 473 246 } 474 475 public static String decodeURL(String url) {476 try {477 return URLDecoder.decode(url, "UTF-8");478 } catch (UnsupportedEncodingException ex) {479 throw new IllegalStateException(ex);480 }481 }482 483 public static String encodeURL(String url) {484 try {485 return URLEncoder.encode(url, "UTF-8");486 } catch (UnsupportedEncodingException ex) {487 throw new IllegalStateException(ex);488 }489 }490 247 }
Note:
See TracChangeset
for help on using the changeset viewer.