/* Copyright (c) 2006 MetaCarta, Inc., published under the BSD license. * See http://svn.openlayers.org/trunk/openlayers/release-license.txt * for the full text of the license. */ /** * @class * * @requires OpenLayers/Layer/Markers.js * @requires OpenLayers/Ajax.js */ OpenLayers.Layer.GPX = OpenLayers.Class.create(); OpenLayers.Layer.GPX.prototype = OpenLayers.Class.inherit( OpenLayers.Layer.Markers, OpenLayers.Layer.Vector, { /** store url of text file * @type str */ url:null, icolor:null, /** @type Array(OpenLayers.Feature) */ features: null, /** @type OpenLayers.Feature */ selectedFeature: null, /** * @constructor * * @param {String} name * @param {String} location */ initialize: function(name, url, icolor, options) { var newArguments = new Array() newArguments.push(name, options); OpenLayers.Layer.Vector.prototype.initialize.apply(this, newArguments); OpenLayers.Layer.Markers.prototype.initialize.apply(this, [name]); this.url = url; this.icolor = icolor; this.features = new Array(); var results = OpenLayers.loadURL(this.url, null, this, this.requestSuccess, this.requestFailure); }, /** * */ destroy: function() { this.clearFeatures(); this.features = null; OpenLayers.Layer.Markers.prototype.destroy.apply(this, arguments); }, /** * @param {XMLHttpRequest} ajaxRequest */ requestSuccess:function(request) { var gpxns = "http://www.topografix.com/GPX/1/0"; var doc = request.responseXML; if (!doc || request.fileType!="XML") { doc = OpenLayers.parseXMLString(request.responseText); } if (typeof doc == "string") { doc = OpenLayers.parseXMLString(doc); } /* search and display track */ // var trk = OpenLayers.Ajax.getElementsByTagNameNS(doc, gpxns, "", "trk"); var trk = doc.getElementsByTagName("trk"); var featureTRK = []; for (var i = 0; i< trk.length; i++) { // var color = '#00FF00'; // Fix Color // var color=this.randomColor(); // Random Color var color=this.icolor; // Random Color for (var j = 0; j < trk[i].childNodes.length; j++) { switch (trk[i].childNodes[j].nodeName) { case 'topografix:color': color = '#' + OpenLayers.Util.getXmlNodeValue(trk[i].childNodes[j]); break; case 'trkseg': if (color == '') color=this.randomColor(); featureTRK.push(this.addLineGPX(trk[i].childNodes[j], color)); break; case '#text': break; case 'name': //FIXME: label the way break; default: // alert('unknown ' + trk[i].childNodes[j].nodeName); break; } } } this.addFeatures(featureTRK); /* search and display route */ // var rte = OpenLayers.Ajax.getElementsByTagNameNS(doc, gpxns, "", "rte"); var rte = doc.getElementsByTagName("rte"); var featureRTE = []; for (var i = 0; i< rte.length; i++) { var color = this.randomColor(); var style_green = { strokeColor: color, strokeOpacity: 1, strokeWidth: 4, pointRadius: 6, pointerEvents: "visiblePainted" }; var pointList = []; for (var j = 0; j < rte[i].childNodes.length; j++) { switch (rte[i].childNodes[j].nodeName) { case 'rtept': var feature = this.parseFeature(rte[i].childNodes[j]); if (feature) { pointList.push(feature); } break; default: break; } } featureRTE.push(new OpenLayers.Feature.Vector(new OpenLayers.Geometry.LineString(pointList),null,style_green)); }; this.addFeatures(featureRTE); /* search and display waypoint */ // var wpt = OpenLayers.Ajax.getElementsByTagNameNS(doc, gpxns, "", "wpt"); var wpt = doc.getElementsByTagName("wpt"); var featuresWPT = []; for (var i = 0; i< wpt.length; i++) { var data = {}; var point = this.setToMercator(wpt[i].getAttribute('lon'),wpt[i].getAttribute('lat')); var location = new OpenLayers.LonLat(point[0], point[1]); /* Provide defaults for title and description */ var title = "Untitled"; try { title = OpenLayers.Util.getNodes(wpt[i], 'name')[0].firstChild.nodeValue; } catch (e) { title="Untitled"; } /* GPX descriptions */ var description = "No description."; try { description = OpenLayers.Util.getNodes(wpt[i], 'desc')[0].firstChild.nodeValue; }catch (e) { var description = "No description."; } data.icon = OpenLayers.Marker.defaultIcon(); // data.popupSize = new OpenLayers.Size(250, 120); if ((title != null) && (description != null)) { // if (link) contentHTML += ''; // contentHTML += '

' + title + '

'; // if (link) contentHTML += '
'; contentHTML = '

' + title + '
' + description + '

'; data['popupContentHTML'] = contentHTML; } var featureWPT = new OpenLayers.Feature(this, location, data); featuresWPT.push(featureWPT); var marker = featureWPT.createMarker(); marker.events.register('click', featureWPT, this.markerClick); this.addMarker(marker); } // for (var i = 0; i < itemlist.length; i++) { //--- // // /* If no link URL is found in the first child node, try the // href attribute */ // try { // var link = OpenLayers.Util.getNodes(itemlist[i], "link")[0].firstChild.nodeValue; // } // catch (e) { // try { // var link = OpenLayers.Util.getNodes(itemlist[i], "link")[0].getAttribute("href"); // } // catch (e) {} // } // } }, /** * @param {Event} evt */ randomColor: function() { var hex=new Array("0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "A", "B", "C", "D", "E", "F"); var color = '#'; for (i=0;i<6;i++){ color += hex[Math.floor(Math.random()*hex.length)]; } return color; }, markerClick: function(evt) { sameMarkerClicked = (this == this.layer.selectedFeature); this.layer.selectedFeature = (!sameMarkerClicked) ? this : null; for(var i=0; i < this.layer.map.popups.length; i++) { this.layer.map.removePopup(this.layer.map.popups[i]); } if (!sameMarkerClicked) { var popup = this.createPopup(true); OpenLayers.Event.observe(popup.div, "click", function() { for(var i=0; i < this.layer.map.popups.length; i++) { this.layer.map.removePopup(this.layer.map.popups[i]); } }.bindAsEventListener(this)); this.layer.map.addPopup(popup); } OpenLayers.Event.stop(evt); }, addLineGPX: function(xmlNode, color) { var style_green = { strokeColor: color, strokeOpacity: 0.6, strokeWidth: 5, pointRadius: 6, pointerEvents: "visiblePainted" }; var pointList = []; for (var i = 0; i < xmlNode.childNodes.length; i++) { // for (var i = 0; i < 4; i++) { if (xmlNode.childNodes[i].nodeName == "trkpt") { var feature = this.parseFeature(xmlNode.childNodes[i]); if (feature) { pointList.push(feature); } } }; return new OpenLayers.Feature.Vector(new OpenLayers.Geometry.LineString(pointList),null,style_green); }, /** * This function is the core of the GPX parsing code in OpenLayers. * It creates the geometries that are then attached to the returned * feature, and calls parseAttributes() to get attribute data out. * @param DOMElement xmlNode */ parseFeature: function(xmlNode) { if (xmlNode.getAttribute('lat') && xmlNode.getAttribute('lon')) { var point = this.setToMercator(xmlNode.getAttribute('lon'),xmlNode.getAttribute('lat')); return new OpenLayers.Geometry.Point(point[0], point[1]); } return false; }, setToMercator: function(lon, lat) { x = parseFloat(lon); y = parseFloat(lat); var PI = 3.14159265358979323846; x = x * 20037508.34 / 180; y = Math.log (Math.tan ((90 + y) * PI / 360)) / (PI / 180); y = y * 20037508.34 / 180; return new Array(x,y); }, /** * */ clearFeatures: function() { if (this.features != null) { while(this.features.length > 0) { var feature = this.features[0]; OpenLayers.Util.removeItem(this.features, feature); feature.destroy(); } } }, requestFailure: function(request) { }, moveTo:function(bounds, zoomChanged, dragging) { OpenLayers.Layer.Vector.prototype.moveTo.apply(this, arguments); // OpenLayers.Layer.Markers.prototype.moveTo.apply(this, arguments); if (!dragging) { this.div.style.left = - parseInt(this.map.layerContainerDiv.style.left) + "px"; this.div.style.top = - parseInt(this.map.layerContainerDiv.style.top) + "px"; var extent = this.map.getExtent(); this.renderer.setExtent(extent); for(i=0; i < this.markers.length; i++) { marker = this.markers[i]; lonlat = this.map.getLayerPxFromLonLat(marker.lonlat); if (marker.icon.calculateOffset) { marker.icon.offset = marker.icon.calculateOffset(marker.icon.size); } var offsetPx = lonlat.offset(marker.icon.offset); marker.icon.imageDiv.style.left = offsetPx.x+parseInt(this.map.layerContainerDiv.style.left) + "px"; marker.icon.imageDiv.style.top = offsetPx.y+parseInt(this.map.layerContainerDiv.style.top) + "px"; } } if (!this.drawn || zoomChanged) { this.drawn = true; for(var i = 0; i < this.features.length; i++) { var feature = this.features[i]; this.drawFeature(feature); } } }, setMap: function(map) { // OpenLayers.Layer.Markers.prototype.setMap.apply(this, arguments); OpenLayers.Layer.prototype.setMap.apply(this, arguments); if (!this.renderer) { this.map.removeLayer(this); } else { this.renderer.map = this.map; this.renderer.setSize(this.map.getSize()); } }, /** @final @type String */ CLASS_NAME: "OpenLayers.Layer.GPX" });