Add method to get arbitrary data from RapiD

Signed-off-by: Taylor Smock <taylor.smock@kaart.com>
pull/1/head
Taylor Smock 2019-10-04 10:34:45 -06:00
rodzic b8ad1c37f4
commit 2fd298a24c
Nie znaleziono w bazie danych klucza dla tego podpisu
ID klucza GPG: 625F6A74A3E4311A
5 zmienionych plików z 199 dodań i 11 usunięć

Wyświetl plik

@ -9,6 +9,7 @@ import org.openstreetmap.josm.gui.preferences.PreferenceSetting;
import org.openstreetmap.josm.plugins.Plugin;
import org.openstreetmap.josm.plugins.PluginInformation;
import org.openstreetmap.josm.plugins.rapid.backend.RapiDAction;
import org.openstreetmap.josm.plugins.rapid.backend.RapiDArbitraryAction;
import org.openstreetmap.josm.plugins.rapid.backend.RapiDDataUtils;
import org.openstreetmap.josm.plugins.rapid.backend.RapiDMoveAction;
@ -27,6 +28,7 @@ public final class RapiDPlugin extends Plugin {
final JMenu dataMenu = MainApplication.getMenu().dataMenu;
MainMenu.add(dataMenu, new RapiDAction(), false);
MainMenu.add(dataMenu, new RapiDMoveAction(), false);
MainMenu.add(dataMenu, new RapiDArbitraryAction(), true);
RapiDDataUtils.addRapiDPaintStyles();

Wyświetl plik

@ -1,3 +1,4 @@
// License: GPL. For details, see LICENSE file.
package org.openstreetmap.josm.plugins.rapid.backend;
import static org.openstreetmap.josm.tools.I18n.tr;

Wyświetl plik

@ -0,0 +1,155 @@
// License: GPL. For details, see LICENSE file.
package org.openstreetmap.josm.plugins.rapid.backend;
import static org.openstreetmap.josm.gui.help.HelpUtil.ht;
import static org.openstreetmap.josm.tools.I18n.tr;
import java.awt.BorderLayout;
import java.awt.GridBagLayout;
import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.util.Optional;
import javax.swing.JCheckBox;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import org.openstreetmap.josm.actions.JosmAction;
import org.openstreetmap.josm.data.Bounds;
import org.openstreetmap.josm.data.coor.LatLon;
import org.openstreetmap.josm.data.gpx.GpxData;
import org.openstreetmap.josm.data.gpx.WayPoint;
import org.openstreetmap.josm.data.osm.BBox;
import org.openstreetmap.josm.data.osm.DataSet;
import org.openstreetmap.josm.gui.ExtendedDialog;
import org.openstreetmap.josm.gui.MainApplication;
import org.openstreetmap.josm.gui.MapView;
import org.openstreetmap.josm.gui.datatransfer.ClipboardUtils;
import org.openstreetmap.josm.gui.layer.GpxLayer;
import org.openstreetmap.josm.gui.widgets.JosmTextField;
import org.openstreetmap.josm.gui.widgets.SelectAllOnFocusGainedDecorator;
import org.openstreetmap.josm.plugins.rapid.RapiDPlugin;
import org.openstreetmap.josm.spi.preferences.Config;
import org.openstreetmap.josm.tools.GBC;
import org.openstreetmap.josm.tools.OsmUrlToBounds;
import org.openstreetmap.josm.tools.Shortcut;
/**
* @author Taylor Smock
*/
public class RapiDArbitraryAction extends JosmAction {
private static final long serialVersionUID = 9048113038651190619L;
private final JosmTextField lowerLat = new JosmTextField();
private final JosmTextField upperLat = new JosmTextField();
private final JosmTextField leftLon = new JosmTextField();
private final JosmTextField rightLon = new JosmTextField();
private final JCheckBox checkbox = new JCheckBox();
public RapiDArbitraryAction() {
super(RapiDPlugin.NAME, null, tr("Get arbitrary data from RapiD"), Shortcut.registerShortcut("data:rapid",
tr("Data: Arbitrary {0} Data", tr("Get arbitrary data from RapiD")), KeyEvent.VK_R,
Shortcut.ALT_CTRL_SHIFT), true);
}
@Override
public void actionPerformed(ActionEvent e) {
showDownloadDialog();
}
static class RapiDArbitraryDialog extends ExtendedDialog {
private static final long serialVersionUID = 2795301151521238635L;
RapiDArbitraryDialog(String[] buttons, JPanel panel) {
super(MainApplication.getMainFrame(), tr("Get arbitrary data from RapiD"), buttons);
setButtonIcons("ok", "cancel");
configureContextsensitiveHelp(ht("/Action/DownloadArbitraryRapiDData"), true);
setContent(panel);
setCancelButton(2);
}
}
public void showDownloadDialog() {
final Optional<Bounds> boundsFromClipboard = Optional.ofNullable(ClipboardUtils.getClipboardStringContent())
.map(OsmUrlToBounds::parse);
if (boundsFromClipboard.isPresent() && Config.getPref().getBoolean("jumpto.use.clipboard", true)) {
setBounds(boundsFromClipboard.get());
} else if (MainApplication.isDisplayingMapView()) {
final MapView mv = MainApplication.getMap().mapView;
setBounds(mv.getState().getViewArea().getCornerBounds());
}
final JPanel panel = new JPanel(new BorderLayout());
panel.add(new JLabel("<html>" + tr("Enter Lat/Lon to download RapiD data.") + "<br>" + "</html>"),
BorderLayout.NORTH);
SelectAllOnFocusGainedDecorator.decorate(lowerLat);
SelectAllOnFocusGainedDecorator.decorate(leftLon);
final JPanel p = new JPanel(new GridBagLayout());
panel.add(p, BorderLayout.NORTH);
p.add(new JLabel(tr("Lower Latitude")), GBC.eol());
p.add(lowerLat, GBC.eol().fill(GBC.HORIZONTAL));
p.add(new JLabel(tr("Left Longitude")), GBC.eol());
p.add(leftLon, GBC.eol().fill(GBC.HORIZONTAL));
p.add(new JLabel(tr("Upper Latitude")), GBC.eol());
p.add(upperLat, GBC.eol().fill(GBC.HORIZONTAL));
p.add(new JLabel(tr("Right Longitude")), GBC.eol());
p.add(rightLon, GBC.eol().fill(GBC.HORIZONTAL));
p.add(new JLabel(tr("Crop to bbox?")));
p.add(checkbox, GBC.eol());
final String[] buttons = { tr("Download"), tr("Cancel") };
BBox bbox = new BBox();
while (!bbox.isInWorld()) {
final int option = new RapiDArbitraryDialog(buttons, panel).showDialog().getValue();
if (option != 1) {
return;
}
try {
bbox = new BBox();
bbox.add(new LatLon(Double.parseDouble(lowerLat.getText()), Double.parseDouble(leftLon.getText())));
bbox.add(new LatLon(Double.parseDouble(upperLat.getText()), Double.parseDouble(rightLon.getText())));
} catch (NumberFormatException e) {
JOptionPane.showMessageDialog(MainApplication.getMainFrame(),
tr("Could not parse Latitude or Longitude. Please check."), tr("Unable to parse Lon/Lat"),
JOptionPane.ERROR_MESSAGE);
bbox = new BBox();
}
}
if (checkbox.isSelected()) {
final GpxData data = new GpxData();
data.addWaypoint(new WayPoint(bbox.getBottomRight()));
data.addWaypoint(new WayPoint(bbox.getTopLeft()));
MainApplication.getLayerManager().addLayer(new GpxLayer(data, tr("{0}: Crop Area", RapiDPlugin.NAME)));
}
final DataSet data = RapiDDataUtils.getData(bbox);
final RapiDLayer layer = RapiDAction.getLayer(true);
final DataSet rapidData = layer.getDataSet();
boolean locked = rapidData.isLocked();
if (locked) {
rapidData.unlock();
}
rapidData.mergeFrom(data);
if (locked) {
rapidData.lock();
}
}
private void setBounds(Bounds b) {
if (b != null) {
final LatLon min = b.getMin();
final LatLon max = b.getMax();
lowerLat.setText(Double.toString(min.lat()));
leftLon.setText(Double.toString(min.lon()));
rightLon.setText(Double.toString(max.lon()));
upperLat.setText(Double.toString(max.lat()));
}
}
}

Wyświetl plik

@ -11,6 +11,7 @@ import java.util.Arrays;
import java.util.Collection;
import java.util.List;
import java.util.TreeSet;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Future;
import org.openstreetmap.josm.data.coor.LatLon;
@ -19,6 +20,7 @@ import org.openstreetmap.josm.data.osm.DataSet;
import org.openstreetmap.josm.data.osm.Node;
import org.openstreetmap.josm.data.osm.OsmPrimitive;
import org.openstreetmap.josm.data.osm.Relation;
import org.openstreetmap.josm.data.osm.UploadPolicy;
import org.openstreetmap.josm.data.osm.Way;
import org.openstreetmap.josm.data.preferences.sources.ExtendedSourceEntry;
import org.openstreetmap.josm.data.preferences.sources.MapPaintPrefHelper;
@ -61,14 +63,12 @@ public final class RapiDDataUtils {
}
for (final Future<?> future : futures) {
try {
int count = 0;
while (!future.isDone() && !future.isCancelled() && count < 100) {
Thread.sleep(100);
count++;
}
future.get();
} catch (final InterruptedException e) {
Logging.debug(e);
Thread.currentThread().interrupt();
} catch (ExecutionException e) {
Logging.debug(e);
}
}
}
@ -109,9 +109,16 @@ public final class RapiDDataUtils {
private static DataSet getDataReal(BBox bbox) {
InputStream inputStream = null;
final DataSet dataSet = new DataSet();
final String urlString = getRapiDURL();
String urlString = getRapiDURL();
if (DetectTaskingManager.hasTaskingManagerLayer()) {
urlString += "&crop_bbox={crop_bbox}";
}
dataSet.setUploadPolicy(UploadPolicy.DISCOURAGED);
try {
final URL url = new URL(urlString.replace("{bbox}", bbox.toStringCSV(",")));
final URL url = new URL(urlString.replace("{bbox}", bbox.toStringCSV(",")).replace("{crop_bbox}",
DetectTaskingManager.getTaskingManagerBBox().toStringCSV(",")));
final HttpClient client = HttpClient.create(url);
final StringBuilder defaultUserAgent = new StringBuilder();
defaultUserAgent.append(client.getHeaders().get("User-Agent"));
@ -123,7 +130,8 @@ public final class RapiDDataUtils {
Logging.debug("{0}: Getting {1}", RapiDPlugin.NAME, client.getURL().toString());
final Response response = client.connect();
inputStream = response.getContent();
dataSet.mergeFrom(OsmReader.parseDataSet(inputStream, null));
final DataSet mergeData = OsmReader.parseDataSet(inputStream, null);
dataSet.mergeFrom(mergeData);
response.disconnect();
} catch (UnsupportedOperationException | IllegalDataException | IOException e) {
Logging.debug(e);
@ -135,6 +143,7 @@ public final class RapiDDataUtils {
Logging.debug(e);
}
}
dataSet.setUploadPolicy(UploadPolicy.BLOCKED);
}
return dataSet;
}

Wyświetl plik

@ -12,6 +12,8 @@ import org.junit.Rule;
import org.junit.Test;
import org.openstreetmap.josm.TestUtils;
import org.openstreetmap.josm.data.coor.LatLon;
import org.openstreetmap.josm.data.gpx.GpxData;
import org.openstreetmap.josm.data.gpx.WayPoint;
import org.openstreetmap.josm.data.osm.BBox;
import org.openstreetmap.josm.data.osm.DataSet;
import org.openstreetmap.josm.data.osm.Node;
@ -19,11 +21,13 @@ import org.openstreetmap.josm.data.osm.OsmPrimitive;
import org.openstreetmap.josm.data.osm.Way;
import org.openstreetmap.josm.data.preferences.sources.MapPaintPrefHelper;
import org.openstreetmap.josm.data.preferences.sources.SourceEntry;
import org.openstreetmap.josm.gui.MainApplication;
import org.openstreetmap.josm.gui.layer.GpxLayer;
import org.openstreetmap.josm.testutils.JOSMTestRules;
public class RapiDDataUtilsTest {
@Rule
public JOSMTestRules test = new JOSMTestRules().preferences();
public JOSMTestRules test = new JOSMTestRules().preferences().main().projection();
/**
* This gets data from RapiD. This test may fail if someone adds the data to
@ -36,6 +40,23 @@ public class RapiDDataUtilsTest {
Assert.assertEquals(1, ds.getWays().size());
}
/**
* This gets data from RapiD. This test may fail if someone adds the data to
* OSM.
*/
@Test
public void testGetDataCropped() {
final BBox testBBox = getTestBBox();
GpxData gpxData = new GpxData();
gpxData.addWaypoint(new WayPoint(new LatLon(39.0738798, -108.5709922)));
gpxData.addWaypoint(new WayPoint(new LatLon(39.0732914, -108.5707436)));
GpxLayer gpx = new GpxLayer(gpxData);
MainApplication.getLayerManager().addLayer(gpx);
final DataSet ds = new DataSet(RapiDDataUtils.getData(testBBox));
Assert.assertEquals(1, ds.getWays().size());
Assert.assertEquals(2, ds.getNodes().size());
}
@Test
public void testAddSourceTags() {
final Way way1 = TestUtils.newWay("highway=residential", new Node(new LatLon(0, 0)),
@ -50,8 +71,8 @@ public class RapiDDataUtilsTest {
public static BBox getTestBBox() {
final BBox testBBox = new BBox();
testBBox.add(new LatLon(39.076, -108.547));
testBBox.add(new LatLon(39.078, -108.545));
testBBox.add(new LatLon(39.0734162, -108.5707107));
testBBox.add(new LatLon(39.0738791, -108.5715723));
return testBBox;
}