1 | // License: GPL. For details, see LICENSE file.
|
---|
2 | package org.openstreetmap.josm.data.imagery.vectortile.mapbox;
|
---|
3 | import static org.openstreetmap.josm.tools.I18n.tr;
|
---|
4 |
|
---|
5 | import java.io.IOException;
|
---|
6 | import java.io.InputStream;
|
---|
7 | import java.nio.file.InvalidPathException;
|
---|
8 | import java.util.List;
|
---|
9 | import java.util.Objects;
|
---|
10 | import java.util.stream.Collectors;
|
---|
11 |
|
---|
12 | import javax.json.Json;
|
---|
13 | import javax.json.JsonException;
|
---|
14 | import javax.json.JsonObject;
|
---|
15 | import javax.json.JsonReader;
|
---|
16 |
|
---|
17 | import org.openstreetmap.josm.data.imagery.ImageryInfo;
|
---|
18 | import org.openstreetmap.josm.data.imagery.JosmTemplatedTMSTileSource;
|
---|
19 | import org.openstreetmap.josm.data.imagery.vectortile.mapbox.style.MapboxVectorStyle;
|
---|
20 | import org.openstreetmap.josm.data.imagery.vectortile.mapbox.style.Source;
|
---|
21 | import org.openstreetmap.josm.gui.ExtendedDialog;
|
---|
22 | import org.openstreetmap.josm.gui.MainApplication;
|
---|
23 | import org.openstreetmap.josm.gui.util.GuiHelper;
|
---|
24 | import org.openstreetmap.josm.gui.widgets.JosmComboBox;
|
---|
25 | import org.openstreetmap.josm.io.CachedFile;
|
---|
26 | import org.openstreetmap.josm.tools.Logging;
|
---|
27 |
|
---|
28 | /**
|
---|
29 | * Tile Source handling for Mapbox Vector Tile sources
|
---|
30 | * @author Taylor Smock
|
---|
31 | * @since 17862
|
---|
32 | */
|
---|
33 | public class MapboxVectorTileSource extends JosmTemplatedTMSTileSource {
|
---|
34 | private final MapboxVectorStyle styleSource;
|
---|
35 |
|
---|
36 | /**
|
---|
37 | * Create a new {@link MapboxVectorTileSource} from an {@link ImageryInfo}
|
---|
38 | * @param info The info to create the source from
|
---|
39 | */
|
---|
40 | public MapboxVectorTileSource(ImageryInfo info) {
|
---|
41 | super(info);
|
---|
42 | MapboxVectorStyle mapBoxVectorStyle = null;
|
---|
43 | try (CachedFile style = new CachedFile(info.getUrl());
|
---|
44 | InputStream inputStream = style.getInputStream();
|
---|
45 | JsonReader reader = Json.createReader(inputStream)) {
|
---|
46 | JsonObject object = reader.readObject();
|
---|
47 | // OK, we may have a stylesheet. "version", "layers", and "sources" are all required.
|
---|
48 | if (object.containsKey("version") && object.containsKey("layers") && object.containsKey("sources")) {
|
---|
49 | mapBoxVectorStyle = MapboxVectorStyle.getMapboxVectorStyle(info.getUrl());
|
---|
50 | }
|
---|
51 | } catch (IOException | InvalidPathException | JsonException e) {
|
---|
52 | Logging.trace(e);
|
---|
53 | }
|
---|
54 | this.styleSource = mapBoxVectorStyle;
|
---|
55 | if (this.styleSource != null) {
|
---|
56 | final Source source;
|
---|
57 | List<Source> sources = this.styleSource.getSources().keySet().stream().filter(Objects::nonNull)
|
---|
58 | .collect(Collectors.toList());
|
---|
59 | if (sources.size() == 1) {
|
---|
60 | source = sources.get(0);
|
---|
61 | } else if (!sources.isEmpty()) {
|
---|
62 | // Ask user what source they want.
|
---|
63 | source = GuiHelper.runInEDTAndWaitAndReturn(() -> {
|
---|
64 | ExtendedDialog dialog = new ExtendedDialog(MainApplication.getMainFrame(),
|
---|
65 | tr("Select Vector Tile Layers"), tr("Add layers"));
|
---|
66 | JosmComboBox<Source> comboBox = new JosmComboBox<>(sources.toArray(new Source[0]));
|
---|
67 | comboBox.setSelectedIndex(0);
|
---|
68 | dialog.setContent(comboBox);
|
---|
69 | dialog.showDialog();
|
---|
70 | return (Source) comboBox.getSelectedItem();
|
---|
71 | });
|
---|
72 | } else {
|
---|
73 | // Umm. What happened? We probably have an invalid style source.
|
---|
74 | throw new InvalidMapboxVectorTileException(tr("Cannot understand style source: {0}", info.getUrl()));
|
---|
75 | }
|
---|
76 | if (source != null) {
|
---|
77 | this.name = name + ": " + source.getName();
|
---|
78 | // There can technically be multiple URL's for this field; unfortunately, JOSM can only handle one right now.
|
---|
79 | this.baseUrl = source.getUrls().get(0);
|
---|
80 | this.minZoom = source.getMinZoom();
|
---|
81 | this.maxZoom = source.getMaxZoom();
|
---|
82 | if (source.getAttributionText() != null) {
|
---|
83 | this.setAttributionText(source.getAttributionText());
|
---|
84 | }
|
---|
85 | }
|
---|
86 | }
|
---|
87 | }
|
---|
88 |
|
---|
89 | /**
|
---|
90 | * Get the style source for this Vector Tile source
|
---|
91 | * @return The source to use for styling
|
---|
92 | */
|
---|
93 | public MapboxVectorStyle getStyleSource() {
|
---|
94 | return this.styleSource;
|
---|
95 | }
|
---|
96 | }
|
---|