001// License: GPL. For details, see LICENSE file. 002package org.openstreetmap.josm.io.remotecontrol.handler; 003 004import static org.openstreetmap.josm.tools.I18n.tr; 005 006import java.util.Arrays; 007 008import org.openstreetmap.josm.Main; 009import org.openstreetmap.josm.data.imagery.ImageryInfo; 010import org.openstreetmap.josm.data.imagery.ImageryInfo.ImageryType; 011import org.openstreetmap.josm.data.imagery.ImageryLayerInfo; 012import org.openstreetmap.josm.gui.layer.ImageryLayer; 013import org.openstreetmap.josm.gui.util.GuiHelper; 014import org.openstreetmap.josm.io.remotecontrol.PermissionPrefWithDefault; 015import org.openstreetmap.josm.tools.Utils; 016 017/** 018 * Adds an imagery (WMS/TMS) layer. For instance, {@code /imagery?title=...&type=...&url=...}. 019 * @since 3715 020 */ 021public class ImageryHandler extends RequestHandler.RawURLParseRequestHandler { 022 023 /** 024 * The remote control command name used to add an imagery layer. 025 */ 026 public static final String command = "imagery"; 027 028 @Override 029 public String getPermissionMessage() { 030 return tr("Remote Control has been asked to load an imagery layer from the following URL:") 031 + "<br>" + args.get("url"); 032 } 033 034 @Override 035 public String[] getMandatoryParams() { 036 return new String[]{"url"}; 037 } 038 039 @Override 040 public String[] getOptionalParams() { 041 return new String[] {"title", "type", "cookies", "min_zoom", "max_zoom"}; 042 } 043 044 @Override 045 public PermissionPrefWithDefault getPermissionPref() { 046 return PermissionPrefWithDefault.LOAD_IMAGERY; 047 } 048 049 protected static ImageryInfo findBingEntry() { 050 for (ImageryInfo i : ImageryLayerInfo.instance.getDefaultLayers()) { 051 if (ImageryType.BING.equals(i.getImageryType())) { 052 return i; 053 } 054 } 055 return null; 056 } 057 058 protected ImageryInfo buildImageryInfo() { 059 String url = args.get("url"); 060 String title = args.get("title"); 061 String type = args.get("type"); 062 final ImageryInfo bing = ImageryType.BING.getTypeString().equals(type) ? findBingEntry() : null; 063 if ((title == null || title.isEmpty()) && bing != null) { 064 title = bing.getName(); 065 } 066 if (title == null || title.isEmpty()) { 067 title = tr("Remote imagery"); 068 } 069 String cookies = args.get("cookies"); 070 final ImageryInfo imgInfo = new ImageryInfo(title, url, type, null, cookies); 071 if (bing != null) { 072 imgInfo.setIcon(bing.getIcon()); 073 } 074 String minZoom = args.get("min_zoom"); 075 if (minZoom != null && !minZoom.isEmpty()) { 076 try { 077 imgInfo.setDefaultMinZoom(Integer.parseInt(minZoom)); 078 } catch (NumberFormatException e) { 079 Main.error(e); 080 } 081 } 082 String maxZoom = args.get("max_zoom"); 083 if (maxZoom != null && !maxZoom.isEmpty()) { 084 try { 085 imgInfo.setDefaultMaxZoom(Integer.parseInt(maxZoom)); 086 } catch (NumberFormatException e) { 087 Main.error(e); 088 } 089 } 090 return imgInfo; 091 } 092 093 @Override 094 protected void handleRequest() throws RequestHandlerErrorException { 095 final ImageryInfo imgInfo = buildImageryInfo(); 096 if (Main.isDisplayingMapView()) { 097 for (ImageryLayer layer : Main.map.mapView.getLayersOfType(ImageryLayer.class)) { 098 if (layer.getInfo().equals(imgInfo)) { 099 Main.info("Imagery layer already exists: "+imgInfo); 100 return; 101 } 102 } 103 } 104 GuiHelper.runInEDT(new Runnable() { 105 @Override 106 public void run() { 107 try { 108 Main.main.addLayer(ImageryLayer.create(imgInfo)); 109 } catch (IllegalArgumentException e) { 110 Main.error(e, false); 111 } 112 } 113 }); 114 } 115 116 @Override 117 protected void validateRequest() throws RequestHandlerBadRequestException { 118 String url = args != null ? args.get("url") : null; 119 String type = args != null ? args.get("type") : null; 120 String cookies = args != null ? args.get("cookies") : null; 121 try { 122 ImageryLayer.create(new ImageryInfo(null, url, type, null, cookies)); 123 } catch (IllegalArgumentException e) { 124 throw new RequestHandlerBadRequestException(e.getMessage(), e); 125 } 126 } 127 128 @Override 129 public String getUsage() { 130 return "adds an imagery layer (e.g. WMS, TMS)"; 131 } 132 133 @Override 134 public String[] getUsageExamples() { 135 final String types = Utils.join("|", Utils.transform(Arrays.asList(ImageryInfo.ImageryType.values()), 136 new Utils.Function<ImageryInfo.ImageryType, String>() { 137 @Override 138 public String apply(ImageryInfo.ImageryType x) { 139 return x.getTypeString(); 140 } 141 })); 142 return new String[] { 143 "/imagery?title=osm&type=tms&url=https://a.tile.openstreetmap.org/%7Bzoom%7D/%7Bx%7D/%7By%7D.png", 144 "/imagery?title=landsat&type=wms&url=http://irs.gis-lab.info/?" + 145 "layers=landsat&SRS=%7Bproj%7D&WIDTH=%7Bwidth%7D&HEIGHT=%7Bheight%7D&BBOX=%7Bbbox%7D", 146 "/imagery?title=...&type={"+types+"}&url=....[&cookies=...][&min_zoom=...][&max_zoom=...]" 147 }; 148 } 149}