Routino SVN Repository Browser

Check out the latest version of Routino: svn co http://routino.org/svn/trunk routino

ViewVC logotype

Annotation of /trunk/web/www/routino/visualiser.js

Parent Directory Parent Directory | Revision Log Revision Log


Revision 933 - (hide annotations) (download) (as text)
Wed Dec 7 19:16:35 2011 UTC (13 years, 3 months ago) by amb
File MIME type: application/javascript
File size: 19117 byte(s)
Move the map preferences (N/S/E/W range, zoom range and URLs) to a separate
file.

1 amb 569 //
2     // Routino data visualiser web page Javascript
3     //
4     // Part of the Routino routing software.
5     //
6 amb 623 // This file Copyright 2008-2011 Andrew M. Bishop
7 amb 569 //
8     // This program is free software: you can redistribute it and/or modify
9     // it under the terms of the GNU Affero General Public License as published by
10     // the Free Software Foundation, either version 3 of the License, or
11     // (at your option) any later version.
12     //
13     // This program is distributed in the hope that it will be useful,
14     // but WITHOUT ANY WARRANTY; without even the implied warranty of
15     // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16     // GNU Affero General Public License for more details.
17     //
18     // You should have received a copy of the GNU Affero General Public License
19     // along with this program. If not, see <http://www.gnu.org/licenses/>.
20     //
21    
22    
23     //
24     // Data types
25     //
26    
27 amb 577 var data_types=[
28     "junctions",
29     "super",
30     "oneway",
31 amb 623 "turns",
32 amb 577 "speed",
33     "weight",
34     "height",
35     "width",
36     "length"
37     ];
38 amb 569
39    
40     //
41     // Junction styles
42     //
43    
44     var junction_colours={
45     0: "#FFFFFF",
46     1: "#FF0000",
47     2: "#FFFF00",
48     3: "#00FF00",
49     4: "#8B4513",
50     5: "#00BFFF",
51     6: "#FF69B4",
52     7: "#000000",
53     8: "#000000",
54     9: "#000000"
55     };
56    
57     var junction_styles={};
58    
59    
60     //
61     // Super styles
62     //
63    
64     var super_node_style,super_segment_style;
65    
66    
67     //
68 amb 623 // Oneway and turn restriction styles
69 amb 569 //
70    
71     var hex={0: "00", 1: "11", 2: "22", 3: "33", 4: "44", 5: "55", 6: "66", 7: "77",
72     8: "88", 9: "99", 10: "AA", 11: "BB", 12: "CC", 13: "DD", 14: "EE", 15: "FF"};
73    
74 amb 623 var turn_restriction_style;
75 amb 569
76 amb 623
77 amb 577 ////////////////////////////////////////////////////////////////////////////////
78     ///////////////////////////////// Map handling /////////////////////////////////
79     ////////////////////////////////////////////////////////////////////////////////
80 amb 569
81     var map;
82 amb 933 var layerMap=[], layerVectors, layerBoxes;
83 amb 569 var epsg4326, epsg900913;
84 amb 577 var map_args;
85 amb 569
86     var box;
87    
88     //
89     // Initialise the 'map' object
90     //
91    
92     function map_init(lat,lon,zoom)
93     {
94 amb 933 // Map properties (North/South and East/West limits and zoom in/out limits are now in mapprops.js
95     // Map URLs are now in mapprops.js
96 amb 569
97     //
98     // Create the map
99     //
100    
101     epsg4326=new OpenLayers.Projection("EPSG:4326");
102     epsg900913=new OpenLayers.Projection("EPSG:900913");
103    
104     map = new OpenLayers.Map ("map",
105     {
106     controls:[
107     new OpenLayers.Control.Navigation(),
108     new OpenLayers.Control.PanZoomBar(),
109     new OpenLayers.Control.ScaleLine(),
110     new OpenLayers.Control.LayerSwitcher()
111     ],
112    
113     projection: epsg900913,
114     displayProjection: epsg4326,
115    
116 amb 933 minZoomLevel: mapprops.zoomout,
117     numZoomLevels: mapprops.zoomin-mapprops.zoomout+1,
118     maxResolution: 156543.0339 / Math.pow(2,mapprops.zoomout),
119 amb 569
120 amb 577 maxExtent: new OpenLayers.Bounds(-20037508.34, -20037508.34, 20037508.34, 20037508.34),
121 amb 933 restrictedExtent: new OpenLayers.Bounds(mapprops.westedge,mapprops.southedge,mapprops.eastedge,mapprops.northedge).transform(epsg4326,epsg900913),
122 amb 569
123     units: "m"
124     });
125    
126     map.events.register("moveend", map, mapMoved);
127    
128 amb 933 // Add map tile layers
129 amb 569
130 amb 933 for(var l=0;l < mapprops.mapdata.length;l++)
131     {
132     layerMap[l] = new OpenLayers.Layer.TMS(mapprops.mapdata[l].label,
133     mapprops.mapdata[l].baseurl,
134     {
135     emptyUrl: mapprops.mapdata[l].errorurl,
136     type: 'png',
137     getURL: limitedUrl,
138     displayOutsideMaxExtent: true,
139     buffer: 1
140     });
141     map.addLayer(layerMap[l]);
142     }
143 amb 569
144 amb 577 // Get a URL for the tile; limited to map restricted extent.
145 amb 569
146     function limitedUrl(bounds)
147     {
148     var z = map.getZoom() + map.minZoomLevel;
149    
150 amb 577 if (z>=7 && (bounds.right < map.restrictedExtent.left ||
151     bounds.left > map.restrictedExtent.right ||
152     bounds.top < map.restrictedExtent.bottom ||
153     bounds.bottom > map.restrictedExtent.top))
154 amb 569 return this.emptyUrl;
155    
156     var res = map.getResolution();
157     var y = Math.round((this.maxExtent.top - bounds.top) / (res * this.tileSize.h));
158     var limit = Math.pow(2, z);
159    
160     if (y < 0 || y >= limit)
161     return this.emptyUrl;
162    
163     var x = Math.round((bounds.left - this.maxExtent.left) / (res * this.tileSize.w));
164    
165     x = ((x % limit) + limit) % limit;
166     return this.url + z + "/" + x + "/" + y + "." + this.type;
167     }
168    
169     // Add a vectors layer
170    
171     layerVectors = new OpenLayers.Layer.Vector("Markers");
172     map.addLayer(layerVectors);
173    
174 amb 577 for(var colour in junction_colours)
175 amb 569 junction_styles[colour]=new OpenLayers.Style({},{stroke: false, pointRadius: 2,fillColor: junction_colours[colour]});
176    
177     super_node_style =new OpenLayers.Style({},{stroke: false, pointRadius: 3,fillColor : "#FF0000"});
178     super_segment_style=new OpenLayers.Style({},{fill: false , strokeWidth: 2,strokeColor: "#FF0000"});
179    
180 amb 623 turn_restriction_style=new OpenLayers.Style({},{fill: false, strokeWidth: 2,strokeColor: "#FF0000"});
181    
182 amb 569 // Add a boxes layer
183    
184 amb 572 layerBoxes = new OpenLayers.Layer.Boxes("Boundary");
185 amb 569 map.addLayer(layerBoxes);
186    
187     box=null;
188    
189 amb 572 // Set the map centre to the limited range specified
190    
191 amb 577 map.setCenter(map.restrictedExtent.getCenterLonLat(), map.getZoomForExtent(map.restrictedExtent,true));
192 amb 572 map.maxResolution = map.getResolution();
193    
194 amb 569 // Move the map
195    
196     if(lon != 'lon' && lat != 'lat' && zoom != 'zoom')
197     {
198 amb 933 if(lon<mapprops.westedge) lon=mapprops.westedge;
199     if(lon>mapprops.eastedge) lon=mapprops.eastedge;
200    
201     if(lat<mapprops.southedge) lat=mapprops.southedge;
202     if(lat>mapprops.northedge) lat=mapprops.northedge;
203    
204     if(zoom<mapprops.zoomout) zoom=mapprops.zoomout;
205     if(zoom>mapprops.zoomin) zoom=mapprops.zoomin;
206    
207 amb 569 var lonlat = new OpenLayers.LonLat(lon,lat).transform(epsg4326,map.getProjectionObject());
208    
209     map.moveTo(lonlat,zoom-map.minZoomLevel);
210     }
211     }
212    
213    
214     //
215     // Map has moved
216     //
217    
218     function mapMoved()
219     {
220     var centre = map.getCenter().clone();
221    
222     var lonlat = centre.transform(map.getProjectionObject(),epsg4326);
223    
224     var zoom = this.getZoom() + map.minZoomLevel;
225    
226 amb 577 map_args="lat=" + lonlat.lat + ";lon=" + lonlat.lon + ";zoom=" + zoom;
227    
228     updateCustomURL();
229     }
230    
231    
232     //
233     // Update custom URL
234     //
235    
236     function updateCustomURL()
237     {
238 amb 569 var router_url=document.getElementById("router_url");
239     var link_url =document.getElementById("link_url");
240     var edit_url =document.getElementById("edit_url");
241    
242 amb 577 router_url.href="customrouter.cgi?" + map_args;
243     link_url.href="customvisualiser.cgi?" + map_args;
244     edit_url.href="http://www.openstreetmap.org/edit?" + map_args;
245 amb 569 }
246    
247    
248 amb 577 ////////////////////////////////////////////////////////////////////////////////
249     /////////////////////////////// Server handling ////////////////////////////////
250     ////////////////////////////////////////////////////////////////////////////////
251    
252 amb 569 //
253     // Display data statistics
254     //
255    
256     function displayStatistics()
257     {
258     // Use AJAX to get the statistics
259    
260     OpenLayers.loadURL("statistics.cgi",null,null,runStatisticsSuccess);
261     }
262    
263    
264     //
265 amb 577 // Success in running data statistics generation.
266 amb 569 //
267    
268     function runStatisticsSuccess(response)
269     {
270     var statistics_data=document.getElementById("statistics_data");
271     var statistics_link=document.getElementById("statistics_link");
272    
273     statistics_data.innerHTML="<pre>" + response.responseText + "</pre>";
274    
275     statistics_link.style.display="none";
276     }
277    
278    
279     //
280     // Get the requested data
281     //
282    
283     function displayData(datatype)
284     {
285 amb 577 for(var data in data_types)
286     hideshow_hide(data_types[data]);
287 amb 569
288     if(datatype != "")
289     hideshow_show(datatype);
290    
291     // Delete the old data
292    
293     layerVectors.destroyFeatures();
294    
295     if(box != null)
296     layerBoxes.removeMarker(box);
297     box=null;
298    
299     // Print the status
300    
301     var div_status=document.getElementById("result_status");
302     div_status.innerHTML = "No data displayed";
303    
304     // Return if just here to clear the data
305    
306     if(datatype == "")
307     return;
308    
309     // Get the new data
310    
311     var mapbounds=map.getExtent().clone();
312     mapbounds.transform(epsg900913,epsg4326);
313    
314     var url="visualiser.cgi";
315    
316     url=url + "?lonmin=" + mapbounds.left;
317     url=url + ";latmin=" + mapbounds.bottom;
318     url=url + ";lonmax=" + mapbounds.right;
319     url=url + ";latmax=" + mapbounds.top;
320     url=url + ";data=" + datatype;
321    
322     // Print the status
323    
324     div_status.innerHTML = "Fetching " + datatype + " data ...";
325    
326     // Use AJAX to get the data
327    
328     switch(datatype)
329     {
330     case 'junctions':
331     OpenLayers.loadURL(url,null,null,runJunctionsSuccess,runFailure);
332     break;
333     case 'super':
334     OpenLayers.loadURL(url,null,null,runSuperSuccess,runFailure);
335     break;
336     case 'oneway':
337     OpenLayers.loadURL(url,null,null,runOnewaySuccess,runFailure);
338     break;
339 amb 623 case 'turns':
340     OpenLayers.loadURL(url,null,null,runTurnsSuccess,runFailure);
341     break;
342 amb 569 case 'speed':
343     case 'weight':
344     case 'height':
345     case 'width':
346     case 'length':
347     OpenLayers.loadURL(url,null,null,runLimitSuccess,runFailure);
348     break;
349     }
350     }
351    
352    
353     //
354     // Success in getting the junctions.
355     //
356    
357     function runJunctionsSuccess(response)
358     {
359     var lines=response.responseText.split('\n');
360    
361 amb 577 // This won't update the browser window
362     // var div_status=document.getElementById("result_status");
363     // div_status.innerHTML = "Processing " + (lines.length-2) + " junctions ...";
364 amb 569
365     var features=[];
366    
367 amb 577 for(var line=0;line<lines.length;line++)
368 amb 569 {
369 amb 572 var words=lines[line].split(' ');
370 amb 569
371     if(line == 0)
372     {
373     var lat1=words[0];
374     var lon1=words[1];
375     var lat2=words[2];
376     var lon2=words[3];
377    
378     var bounds = new OpenLayers.Bounds(lon1,lat1,lon2,lat2).transform(epsg4326,map.getProjectionObject());
379    
380     box = new OpenLayers.Marker.Box(bounds);
381    
382     layerBoxes.addMarker(box);
383     }
384     else if(words[0] != "")
385     {
386     var lat=words[0];
387     var lon=words[1];
388     var count=words[2];
389    
390     var lonlat= new OpenLayers.LonLat(lon,lat).transform(epsg4326,epsg900913);
391    
392     var point = new OpenLayers.Geometry.Point(lonlat.lon,lonlat.lat);
393    
394     features.push(new OpenLayers.Feature.Vector(point,{},junction_styles[count]));
395     }
396     }
397    
398     layerVectors.addFeatures(features);
399    
400 amb 577 var div_status=document.getElementById("result_status");
401 amb 569 div_status.innerHTML = "Processed " + (lines.length-2) + " junctions";
402     }
403    
404    
405     //
406     // Success in getting the super-node and super-segments
407     //
408    
409     function runSuperSuccess(response)
410     {
411     var lines=response.responseText.split('\n');
412    
413 amb 577 // This won't update the browser window
414     // var div_status=document.getElementById("result_status");
415     // div_status.innerHTML = "Processing " + (lines.length-2) + " super-nodes/segments ...";
416 amb 569
417     var features=[];
418    
419     var nodepoint;
420    
421 amb 577 for(var line=0;line<lines.length;line++)
422 amb 569 {
423 amb 572 var words=lines[line].split(' ');
424 amb 569
425     if(line == 0)
426     {
427     var lat1=words[0];
428     var lon1=words[1];
429     var lat2=words[2];
430     var lon2=words[3];
431    
432     var bounds = new OpenLayers.Bounds(lon1,lat1,lon2,lat2).transform(epsg4326,map.getProjectionObject());
433    
434     box = new OpenLayers.Marker.Box(bounds);
435    
436     layerBoxes.addMarker(box);
437     }
438     else if(words[0] != "")
439     {
440     var lat=words[0];
441     var lon=words[1];
442     var type=words[2];
443    
444     var lonlat= new OpenLayers.LonLat(lon,lat).transform(epsg4326,epsg900913);
445    
446     var point = new OpenLayers.Geometry.Point(lonlat.lon,lonlat.lat);
447    
448     if(type == "n")
449     {
450     nodepoint=point;
451    
452     features.push(new OpenLayers.Feature.Vector(point,{},super_node_style));
453     }
454     else
455     {
456 amb 577 var segment = new OpenLayers.Geometry.LineString([nodepoint,point]);
457 amb 569
458 amb 577 features.push(new OpenLayers.Feature.Vector(segment,{},super_segment_style));
459 amb 569 }
460     }
461     }
462    
463     layerVectors.addFeatures(features);
464    
465 amb 577 var div_status=document.getElementById("result_status");
466 amb 569 div_status.innerHTML = "Processed " + (lines.length-2) + " super-nodes/segments";
467     }
468    
469    
470     //
471     // Success in getting the oneway data
472     //
473    
474     function runOnewaySuccess(response)
475     {
476     var lines=response.responseText.split('\n');
477    
478 amb 577 // This won't update the browser window
479     // var div_status=document.getElementById("result_status");
480     // div_status.innerHTML = "Processing " + (lines.length-2) + " oneway segments ...";
481 amb 569
482     var features=[];
483    
484 amb 577 for(var line=0;line<lines.length;line++)
485 amb 569 {
486 amb 572 var words=lines[line].split(' ');
487 amb 569
488     if(line == 0)
489     {
490     var lat1=words[0];
491     var lon1=words[1];
492     var lat2=words[2];
493     var lon2=words[3];
494    
495     var bounds = new OpenLayers.Bounds(lon1,lat1,lon2,lat2).transform(epsg4326,map.getProjectionObject());
496    
497     box = new OpenLayers.Marker.Box(bounds);
498    
499     layerBoxes.addMarker(box);
500     }
501     else if(words[0] != "")
502     {
503     var lat1=words[0];
504     var lon1=words[1];
505     var lat2=words[2];
506     var lon2=words[3];
507    
508     var lonlat1= new OpenLayers.LonLat(lon1,lat1).transform(epsg4326,epsg900913);
509     var lonlat2= new OpenLayers.LonLat(lon2,lat2).transform(epsg4326,epsg900913);
510    
511     //var point1 = new OpenLayers.Geometry.Point(lonlat1.lon,lonlat1.lat);
512     var point2 = new OpenLayers.Geometry.Point(lonlat2.lon,lonlat2.lat);
513    
514     var dlat = lonlat2.lat-lonlat1.lat;
515     var dlon = lonlat2.lon-lonlat1.lon;
516     var dist = Math.sqrt(dlat*dlat+dlon*dlon)/10;
517     var ang = Math.atan2(dlat,dlon);
518    
519     var point3 = new OpenLayers.Geometry.Point(lonlat1.lon+dlat/dist,lonlat1.lat-dlon/dist);
520     var point4 = new OpenLayers.Geometry.Point(lonlat1.lon-dlat/dist,lonlat1.lat+dlon/dist);
521    
522 amb 577 var segment = new OpenLayers.Geometry.LineString([point2,point3,point4,point2]);
523 amb 569
524     var r=Math.round(7.5+7.9*Math.cos(ang));
525     var g=Math.round(7.5+7.9*Math.cos(ang+2.0943951));
526     var b=Math.round(7.5+7.9*Math.cos(ang-2.0943951));
527     var colour = "#" + hex[r] + hex[g] + hex[b];
528    
529     var style=new OpenLayers.Style({},{strokeWidth: 2,strokeColor: colour});
530    
531 amb 577 features.push(new OpenLayers.Feature.Vector(segment,{},style));
532 amb 569 }
533     }
534    
535     layerVectors.addFeatures(features);
536    
537 amb 577 var div_status=document.getElementById("result_status");
538 amb 569 div_status.innerHTML = "Processed " + (lines.length-2) + " oneway segments";
539     }
540    
541    
542     //
543 amb 623 // Success in getting the turn restrictions data
544     //
545    
546     function runTurnsSuccess(response)
547     {
548     var lines=response.responseText.split('\n');
549    
550     // This won't update the browser window
551     // var div_status=document.getElementById("result_status");
552     // div_status.innerHTML = "Processing " + (lines.length-2) + " turn restrictions ...";
553    
554     var features=[];
555    
556     for(var line=0;line<lines.length;line++)
557     {
558     var words=lines[line].split(' ');
559    
560     if(line == 0)
561     {
562     var lat1=words[0];
563     var lon1=words[1];
564     var lat2=words[2];
565     var lon2=words[3];
566    
567     var bounds = new OpenLayers.Bounds(lon1,lat1,lon2,lat2).transform(epsg4326,map.getProjectionObject());
568    
569     box = new OpenLayers.Marker.Box(bounds);
570    
571     layerBoxes.addMarker(box);
572     }
573     else if(words[0] != "")
574     {
575     var lat1=words[0];
576     var lon1=words[1];
577     var lat2=words[2];
578     var lon2=words[3];
579     var lat3=words[4];
580     var lon3=words[5];
581    
582     var lonlat1= new OpenLayers.LonLat(lon1,lat1).transform(epsg4326,epsg900913);
583     var lonlat2= new OpenLayers.LonLat(lon2,lat2).transform(epsg4326,epsg900913);
584     var lonlat3= new OpenLayers.LonLat(lon3,lat3).transform(epsg4326,epsg900913);
585    
586     var point1 = new OpenLayers.Geometry.Point(lonlat1.lon,lonlat1.lat);
587     var point2 = new OpenLayers.Geometry.Point(lonlat2.lon,lonlat2.lat);
588     var point3 = new OpenLayers.Geometry.Point(lonlat3.lon,lonlat3.lat);
589    
590     var segments = new OpenLayers.Geometry.LineString([point1,point2,point3]);
591    
592     features.push(new OpenLayers.Feature.Vector(segments,{},turn_restriction_style));
593     }
594     }
595    
596     layerVectors.addFeatures(features);
597    
598     var div_status=document.getElementById("result_status");
599     div_status.innerHTML = "Processed " + (lines.length-2) + " turn restrictions";
600     }
601    
602    
603     //
604 amb 569 // Success in getting the speed/weight/height/width/length limits
605     //
606    
607     function runLimitSuccess(response)
608     {
609     var lines=response.responseText.split('\n');
610    
611 amb 577 // This won't update the browser window
612     // var div_status=document.getElementById("result_status");
613     // div_status.innerHTML = "Processing " + (lines.length-2) + " limits ...";
614 amb 569
615     var features=[];
616    
617     var nodelonlat;
618    
619 amb 577 for(var line=0;line<lines.length;line++)
620 amb 569 {
621 amb 572 var words=lines[line].split(' ');
622 amb 569
623     if(line == 0)
624     {
625     var lat1=words[0];
626     var lon1=words[1];
627     var lat2=words[2];
628     var lon2=words[3];
629    
630     var bounds = new OpenLayers.Bounds(lon1,lat1,lon2,lat2).transform(epsg4326,map.getProjectionObject());
631    
632     box = new OpenLayers.Marker.Box(bounds);
633    
634     layerBoxes.addMarker(box);
635     }
636     else if(words[0] != "")
637     {
638     var lat=words[0];
639     var lon=words[1];
640     var number=words[2];
641    
642     var lonlat= new OpenLayers.LonLat(lon,lat).transform(epsg4326,epsg900913);
643    
644     if(number == undefined)
645     {
646     var point = new OpenLayers.Geometry.Point(lonlat.lon,lonlat.lat);
647    
648     nodelonlat=lonlat;
649    
650     features.push(new OpenLayers.Feature.Vector(point,{},junction_styles[1]));
651     }
652     else
653     {
654     var dlat = lonlat.lat-nodelonlat.lat;
655     var dlon = lonlat.lon-nodelonlat.lon;
656     var dist = Math.sqrt(dlat*dlat+dlon*dlon)/60;
657    
658     var point = new OpenLayers.Geometry.Point(nodelonlat.lon+dlon/dist,nodelonlat.lat+dlat/dist);
659    
660     features.push(new OpenLayers.Feature.Vector(point,{},
661     new OpenLayers.Style({},{externalGraphic: 'icons/limit-' + number + '.png',
662     graphicYOffset: -9,
663     graphicWidth: 19,
664     graphicHeight: 19})));
665     }
666     }
667     }
668    
669     layerVectors.addFeatures(features);
670    
671 amb 577 var div_status=document.getElementById("result_status");
672 amb 569 div_status.innerHTML = "Processed " + (lines.length-2) + " limits";
673     }
674    
675    
676     //
677     // Failure in getting data.
678     //
679    
680     function runFailure(response)
681     {
682     var div_status=document.getElementById("result_status");
683     div_status.innerHTML = "Failed to get visualiser data!";
684    
685     window.alert("Failed to get visualiser data!\n" + response.statusText);
686     }