source: josm/trunk/src/org/openstreetmap/josm/actions/downloadtasks/DownloadOsmTask.java@ 2477

Last change on this file since 2477 was 2477, checked in by Gubaer, 14 years ago

fixed #3921: Autojump to downloaded area

  • Property svn:eol-style set to native
File size: 6.6 KB
Line 
1// License: GPL. Copyright 2007 by Immanuel Scholz and others
2package org.openstreetmap.josm.actions.downloadtasks;
3
4import static org.openstreetmap.josm.tools.I18n.tr;
5
6import java.io.IOException;
7import java.util.Collection;
8import java.util.concurrent.Future;
9import java.util.logging.Logger;
10
11import org.openstreetmap.josm.Main;
12import org.openstreetmap.josm.data.Bounds;
13import org.openstreetmap.josm.data.coor.LatLon;
14import org.openstreetmap.josm.data.osm.DataSet;
15import org.openstreetmap.josm.data.osm.DataSource;
16import org.openstreetmap.josm.data.osm.visitor.BoundingXYVisitor;
17import org.openstreetmap.josm.gui.PleaseWaitRunnable;
18import org.openstreetmap.josm.gui.layer.Layer;
19import org.openstreetmap.josm.gui.layer.OsmDataLayer;
20import org.openstreetmap.josm.gui.progress.ProgressMonitor;
21import org.openstreetmap.josm.io.BoundingBoxDownloader;
22import org.openstreetmap.josm.io.OsmServerLocationReader;
23import org.openstreetmap.josm.io.OsmServerReader;
24import org.openstreetmap.josm.io.OsmTransferException;
25import org.xml.sax.SAXException;
26
27/**
28 * Open the download dialog and download the data.
29 * Run in the worker thread.
30 */
31public class DownloadOsmTask extends AbstractDownloadTask {
32 private static final Logger logger = Logger.getLogger(DownloadOsmTask.class.getName());
33
34 private Bounds currentBounds;
35 private DataSet downloadedData;
36 private DownloadTask downloadTask;
37
38 private void rememberDownloadedData(DataSet ds) {
39 this.downloadedData = ds;
40 }
41
42 public DataSet getDownloadedData() {
43 return downloadedData;
44 }
45
46 public Future<?> download(boolean newLayer, Bounds downloadArea, ProgressMonitor progressMonitor) {
47
48 downloadTask = new DownloadTask(newLayer,
49 new BoundingBoxDownloader(downloadArea), progressMonitor);
50 currentBounds = new Bounds(downloadArea);
51 // We need submit instead of execute so we can wait for it to finish and get the error
52 // message if necessary. If no one calls getErrorMessage() it just behaves like execute.
53 return Main.worker.submit(downloadTask);
54 }
55
56 /**
57 * Loads a given URL from the OSM Server
58 * @param True if the data should be saved to a new layer
59 * @param The URL as String
60 */
61 public Future<?> loadUrl(boolean new_layer, String url, ProgressMonitor progressMonitor) {
62 downloadTask = new DownloadTask(new_layer,
63 new OsmServerLocationReader(url),
64 progressMonitor);
65 currentBounds = new Bounds(new LatLon(0,0), new LatLon(0,0));
66 return Main.worker.submit(downloadTask);
67 }
68
69 public void cancel() {
70 if (downloadTask != null) {
71 downloadTask.cancel();
72 }
73 }
74
75 private class DownloadTask extends PleaseWaitRunnable {
76 private OsmServerReader reader;
77 private DataSet dataSet;
78 private boolean newLayer;
79
80 public DownloadTask(boolean newLayer, OsmServerReader reader, ProgressMonitor progressMonitor) {
81 super(tr("Downloading data"), progressMonitor, false);
82 this.reader = reader;
83 this.newLayer = newLayer;
84 }
85
86 @Override public void realRun() throws IOException, SAXException, OsmTransferException {
87 try {
88 if (isCanceled())
89 return;
90 dataSet = reader.parseOsm(progressMonitor.createSubTaskMonitor(ProgressMonitor.ALL_TICKS, false));
91 } catch(Exception e) {
92 if (isCanceled()) {
93 logger.warning(tr("Ignoring exception because download has been cancelled. Exception was: {0}" + e.toString()));
94 return;
95 }
96 if (e instanceof OsmTransferException) {
97 rememberException(e);
98 } else {
99 rememberException(new OsmTransferException(e));
100 }
101 DownloadOsmTask.this.setFailed(true);
102 }
103 }
104
105 protected OsmDataLayer getEditLayer() {
106 if (!Main.isDisplayingMapView()) return null;
107 return Main.map.mapView.getEditLayer();
108 }
109
110 protected int getNumDataLayers() {
111 int count = 0;
112 if (!Main.isDisplayingMapView()) return 0;
113 Collection<Layer> layers = Main.map.mapView.getAllLayers();
114 for (Layer layer : layers) {
115 if (layer instanceof OsmDataLayer) {
116 count++;
117 }
118 }
119 return count;
120 }
121
122 protected OsmDataLayer getFirstDataLayer() {
123 if (!Main.isDisplayingMapView()) return null;
124 Collection<Layer> layers = Main.map.mapView.getAllLayersAsList();
125 for (Layer layer : layers) {
126 if (layer instanceof OsmDataLayer)
127 return (OsmDataLayer) layer;
128 }
129 return null;
130 }
131
132 @Override protected void finish() {
133 if (isFailed() || isCanceled())
134 return;
135 if (dataSet == null)
136 return; // user canceled download or error occurred
137 if (currentBounds == null)
138 return; // no data retrieved
139 if (dataSet.allPrimitives().isEmpty()) {
140 rememberErrorMessage(tr("No data found in this area."));
141 // need to synthesize a download bounds lest the visual indication of downloaded
142 // area doesn't work
143 dataSet.dataSources.add(new DataSource(currentBounds, "OpenStreetMap server"));
144 }
145 rememberDownloadedData(dataSet);
146 int numDataLayers = getNumDataLayers();
147 if (newLayer || numDataLayers == 0 || (numDataLayers > 1 && getEditLayer() == null)) {
148 // the user explicitly wants a new layer, we don't have any layer at all
149 // or it is not clear which layer to merge to
150 //
151 OsmDataLayer layer = new OsmDataLayer(dataSet, OsmDataLayer.createNewName(), null);
152 Main.main.addLayer(layer);
153 } else {
154 OsmDataLayer target;
155 target = getEditLayer();
156 if (target == null) {
157 target = getFirstDataLayer();
158 }
159 target.mergeFrom(dataSet);
160 BoundingXYVisitor v = new BoundingXYVisitor();
161 v.visit(currentBounds);
162 Main.map.mapView.recalculateCenterScale(v);
163 target.onPostDownloadFromServer();
164 }
165 }
166
167 @Override protected void cancel() {
168 setCanceled(true);
169 if (reader != null) {
170 reader.cancel();
171 }
172 }
173 }
174}
Note: See TracBrowser for help on using the repository browser.