Overview:
Whether in ArcGIS for JS or openlayers, when the poi point is more, the display of the foreground page is a big problem in efficiency. After a period of research, found that Baidu map on the issue of the treatment of the idea is better: will show the POI point in the server-side generation of images, the page only call pictures will be more efficient. This article describes how to implement a POI point in the Java background in real-time generation on the server side and in the Openlayers2 display.
Post-Implementation effects:
Technical difficulties:
To achieve the server-side generation of poi points, the difficulty is to calculate the screen coordinates of the coordinate points with the parameters of the foreground request. For this, an article on the Internet solves this problem, the article reads as follows:
Geographic coordinates define rules: The x-axis (which represents longitude) increments to the right, and the y-axis (latitude) increases upward, just like the plane coordinates learned in primary school. Left and down rules. Screen coordinates define rules: The x-axis increments to the right, and the y-axis increments downward. As you can see, the difference between geographic coordinates and screen coordinates is simply that the y-axis increments in the opposite direction (which is different). It is emphasized here that in order to guarantee the accuracy, the degree of geographical coordinates is *3600 converted into seconds, all the values are computed by double, and the final result is converted to int. 1 already know the height (y) and width (h) of the screen, the range of geographical coordinates (MAXLON,MINLON,MAXLAT,MINLAT), here we know these known parameters. 2 We can figure out the longitude and latitude represented by each pixel (this is called a scale factor). Formula: ScaleX = ((Maxlon-minlon) *3600)/h----------The number of longitude seconds per pixel on the x-axis; formula: ScaleY = ((Maxlat-minlat) *3600)/y---------- The number of latitude seconds per pixel on the y-axis, and the two scale factor is the relationship between the two coordinate systems. 3 It's a simple step, which is to figure out the coordinates of any point in the geographic coordinate area (Lon,lat) on the screen. Formula: ScreenX = lon*3600/scalex;---------screen coordinates x-axis coordinate formula: ScreenY = Lat*3600/scaley;---------screen coordinates y-axis coordinates and the last step, And that's what we're going to do with that geographic area full of screens. 4 and then we need the geographic area to occupy a screen what should we do? Formula: MinX = Minlon*3600/scalex; left-most formula: Miny = Minlat*3600/scaley; Area Upper Top 5 The local geographic area fills the entire screen, we need to use the third step to calculate the ScreenX and Screeny two parameters, the formula for any point in the area is as follows: Formula: X = Screenx-minx = (Lon-minlon) *3600/ ScaleX; formula: Y = Screenmaxlat-screenlat = (Maxlat-lat) *3600/scaley;6 Summary: The final formula for the latitude-to-screen coordinates is as follows: Formula: X = (Lon-minlon) *3600/scale X; formula: Y = (Maxlat-lat) *3600/scaley; then we can launch the screen coordinates by the formula above the latitude coordinate formula as follows: Formula:Lon = X * scalex/3600 + Minlon; formula: lat = maxlat-y* scaley/3600;
Encoding Implementation:
Background poi image Real-time generation with a servlet implementation, the foreground call with WMS to invoke, the specific code is as follows:
Package Com.lzugis.web;import Javax.imageio.imageio;import Java.awt.color;import java.awt.image;import Java.awt.image.bufferedimage;import Java.io.bufferedinputstream;import Java.io.bytearrayinputstream;import Java.io.file;import Java.io.fileinputstream;import Java.io.ioexception;import Java.io.InputStream;import Java.io.outputstream;import Java.util.arraylist;import Java.util.list;import javax.servlet.ServletException; Import Javax.servlet.annotation.webservlet;import Javax.servlet.http.httpservlet;import Javax.servlet.http.httpservletrequest;import javax.servlet.http.httpservletresponse;/** * servlet implementation Class Poiservices */@WebServlet (description = "poi to wms", Urlpatterns = {"/map/poi"}) public class Poiservices extends H Ttpservlet {private static final long serialversionuid = 1L; /** * @see javax.servlet.http.httpservlet#httpservlet () */public poiservices () {super (); TODO auto-generated Constructor stub}/** * @see Javax.servleT.http.httpservlet#doget (javax.servlet.http.HttpServletRequest request, Javax.servlet.http.HttpServletResponse Response) */protected void doget (HttpServletRequest request, httpservletresponse response) throws Servletexception, IOException {//TODO auto-generated method Stubthis.dopost (request,response);} /** * @see Javax.servlet.http.httpservlet#dopost (javax.servlet.http.HttpServletRequest request, Javax.servlet.http.HttpServletResponse response) */protected void DoPost (HttpServletRequest request, HttpServletResponse response) throws Servletexception, IOException {//TODO auto-generated method stub String bbox= reques T.getparameter ("BBOX"); String width= request.getparameter ("width"); String height= request.getparameter ("height"); int w = integer.parseint (width), h = integer.parseint (height); String[] Extent = Bbox.split (","); Double xmin = double.parsedouble (Extent[0]), ymin = Double.parsedouble (extent[1]), xmax = Double.parsedouble (exten T[2]), ymax = DOuble.parsedouble (Extent[3]); Double ScaleX = ((xmax-xmin) *3600)/w, ScaleY = ((ymax-ymin) *3600)/h; list<string> geoData = new arraylist<string> (); /*geodata.add ("87.5758285931,43.7822116460"); Geodata.add ("91.1629975040,29.7104204643"); Geodata.add ("116.4575803581078,40.04054437977018"); Geodata.add ("103.584297498,36.1190864503"); */Geodata.add ("116.294,39.9742"); Geodata.add ("116.306,39.9754"); ...... BufferedImage image = New BufferedImage (w, H,BUFFEREDIMAGE.TYPE_INT_RGB); Java.awt.Graphics2D g2d = Image.creategraphics (); Image = G2d.getdeviceconfiguration (). Createcompatibleimage (W,h, Java.awt.Transparency.TRANSLUCENT); G2d.dispose (); G2d = Image.creategraphics (); for (int i=0;i<geodata.size (); i++) {String Lonlat = Geodata.get (i). toString (); String lon = Lonlat.split (",") [0], lat = Lonlat.split (",") [1]; Double x = double.parsedouble (lon), y = double.parsedouble (LAT); Double SCRx = (x-xmin) *3600/scalex, scry = (ymax-y) *3600/scaley; Image img = imageio.read (New File ("C:/icon.png")); G2d.drawimage (IMG, (int) SCRX, (int) scry, NULL, NULL); } g2d.setstroke (New Java.awt.BasicStroke (10)); Release Object G2d.dispose (); Save file OutputStream os = Response.getoutputstream (); try {String poiimg = "C:/wms.png"; Imageio.write (Image, "PNG", New File (poiimg)); int count = 0; byte[] buffer = new byte[1024 * 1024]; InputStream instream = new Bufferedinputstream (new FileInputStream (poiimg)); while ((count = instream.read (buffer))! =-1) {os.write (buffer, 0, count); } os.flush (); Instream.close (); Os.close (); } catch (IOException e) {e.printstacktrace (); }}}
Description:
The data of Beijing Metro station is used as the test data here.
Foreground call:
var poiurl = "Http://localhost:8081/lzugis/map/poi"; var poilayer = new OpenLayers.Layer.WMS ("Poilayer", Poiurl, { layers: "", transparent:true }, { C10/>opacity:1, singletile:true }); Map.addlayer (Poilayer);
Follow-up:
As a poi, it is necessary to have a mouse event, this part of the content is being studied, the latter will be updated gradually.
A solution for a large number of POI points