//<----------------START GLOBAL VARIABLE DECLARATION-------------------------------------------------->
var map; var geocoder; var custMarker; var baseMarker; var imageDirectory; var baseIcon; 
var custImage; var points; var xmlDoc; var directionsPanel; var directions;
var curMarker; var toSite; var contextmenu; var sortedPlaces; var googleMapKey; var afterLoadCallBack;
var locationsPath; var defaultLatitude; var defaultLongitude; var defaultZoom; var loadDirections;
var pinTypes; var mapToTypes; var defaultMapType; var mapTypeControl; var mapControl; var showTraffic;
//<----------------END GLOBAL VARIABLE DECLARATION---------------------------------------------------->

//<----------------START OBJECT DEFINITION----------------------------->
//define custom object to represent a place
function Place(){
    this.name = "";
    this.address = "";
    this.city = "";
    this.state = "";
    this.zip = "";
    this.phone = "";
    this.web = "";
    this.lat = "";
    this.lon = "";
    this.photo = "";
    this.pinType = "default";
    this.toString = toString;
}
//define a custom toString() method for our Place object
function toString(){
    return this.state + " " + this.name;
}
//<----------------END OBJECT DEFINITION-------------------------------->

//Load string tokenizer
String.prototype.tokenize = tokenize;
//call the configuration function
configureMap();

//CONFIGURATION FUNCTION
function configureMap(){
    var confXML;
    var req;
    try{
        
        // branch for native XMLHttpRequest object
        if (window.XMLHttpRequest) {
            req = new XMLHttpRequest();            
        // branch for IE/Windows ActiveX version
        } else if (window.ActiveXObject) {
            req = new ActiveXObject("Microsoft.XMLHTTP");            
        } else {
            alert("Your browser is not compatible with this page");
            return;
        }       
        req.open("GET", "./config.xml", false);
        req.send(null);         
        confXML = req.responseXML;
                
        var x = confXML.getElementsByTagName('mapkey');
        if(x.length > 0){
            googleMapKey = x[0].firstChild.data;
        }

        var mapsource = "http://maps.google.com/maps?file=api&v=2&key=" + googleMapKey;
        document.write('<script type="text/javascript" src="' + mapsource + '"></script>'); 
        
        //load GeoApi
        document.write('<script language="JavaScript" src="http://j.maxmind.com/app/geoip.js"></script>');      
        
        x = confXML.getElementsByTagName('locationspath');
        if(x.length > 0){
            locationsPath = x[0].firstChild.data;
        }                   

        //now we want to create the center GLatLng for the map
        var lat; var lng;
        x = confXML.getElementsByTagName('defaultlatitude');        
        if(x.length > 0){
            lat = x[0].firstChild.data;
        } 

        x = confXML.getElementsByTagName('defaultlongitude');        
        if(x.length > 0){
            lng = x[0].firstChild.data;
        }
        if(lat != null){
            defaultLatitude = lat;
        }
        if(lng != null){
            defaultLongitude = lng;
        }

        //now get the map zoom level
        x = confXML.getElementsByTagName('defaultzoom');
        defaultZoom = 5;
        if(x.length > 0){
            defaultZoom = parseInt(x[0].firstChild.data);
        }       	
        
        //get pin types
        pinTypes = confXML.getElementsByTagName('pintype');	        

        //get map to types
        x = confXML.getElementsByTagName('maptotypes');
        if(x.length > 0){
            mapToTypes = x[0].firstChild.data.tokenize(',',' ',true);                    
        } 
        
        //get loadDirections boolean
        x = confXML.getElementsByTagName('loaddirections');
        if(x.length > 0){
            loadDirections = x[0].firstChild.data;                    
        }         
        //get default map type
        x = confXML.getElementsByTagName('defaultmaptype');
        if(x.length > 0){
            defaultMapType = x[0].firstChild.data;                    
        }
        //get map type control
        x = confXML.getElementsByTagName('maptypecontrol');
        if(x.length > 0){
            mapTypeControl = x[0].firstChild.data;                    
        }
        
        x = confXML.getElementsByTagName('mapcontrol');
        if(x.length > 0){
            mapControl = x[0].firstChild.data;                    
        }
        
        x = confXML.getElementsByTagName('showtraffic');
        if(x.length > 0){
            showTraffic = x[0].firstChild.data;                    
        }
		
        x = confXML.getElementsByTagName('centerongeocoding');
        if(x.length > 0){
            centerOnGeocoding = x[0].firstChild.data;                    
        }
		
        x = confXML.getElementsByTagName('displaygeocoding');
        if(x.length > 0){
            displayGeocoding = x[0].firstChild.data;                    
        }
    } catch (e) {        
	alert("Error in configureMap().... " + e.name + " " + e.message);        
    }   
}

//INITIALIZATION FUNCTION - Call this function to load map onto a div named "map"
//you can provide a div named "route" for the directions to be loaded onto
//you can also provide a div name "miles" for the direction summary to be load onto
function loadMap(callBack) {    
    try {        
		if (GBrowserIsCompatible()) {            
			// Create and Center a Map
			map = new GMap2(document.getElementById("map"));             
			if(centerOnGeocoding == 'true'){
				map.setCenter(new GLatLng(geoip_latitude(),geoip_longitude()), defaultZoom);   
			}else{
				map.setCenter(new GLatLng(defaultLatitude,defaultLongitude), defaultZoom);
			}
			map.addMapType(G_PHYSICAL_MAP);
			map.addControl(new GScaleControl());         
			map.enableDoubleClickZoom();
			map.enableContinuousZoom();
			map.enableScrollWheelZoom(); 
		
			if(showTraffic == "true"){
				map.addOverlay(new GTrafficOverlay());
			}           
	
			//determine map control
			if(mapControl == "GSmallMapControl"){
				map.addControl(new GSmallMapControl(),new GControlPosition(G_ANCHOR_BOTTOM_RIGHT, new GSize(10, 20)));
			}else{
				map.addControl(new GLargeMapControl(),new GControlPosition(G_ANCHOR_BOTTOM_RIGHT, new GSize(10, 20)));
			}
	   
			//determine map type
			if(mapTypeControl == "GMenuMapTypeControl"){
				map.addControl(new GMenuMapTypeControl());
			}else if(mapTypeControl == "GHierarchicalMapTypeControl"){
				map.addControl(new GHierarchicalMapTypeControl());
			}else if(mapTypeControl == "GMapTypeControl"){
				map.addControl(new GMapTypeControl());
			}else {
				map.addControl(new GMapTypeControl());
			}           
			//set default map type
			if(defaultMapType == "G_SATELLITE_MAP"){
				map.setMapType(G_SATELLITE_MAP);
			}else if(defaultMapType == "G_HYBRID_MAP"){
				map.setMapType(G_HYBRID_MAP);
			}else if(defaultMapType == "G_PHYSICAL_MAP"){
				map.setMapType(G_PHYSICAL_MAP);
			}else{
				map.setMapType(G_NORMAL_MAP);
			}           
			//add a listener to disable page scrolling while scroll zooming on the map
			GEvent.addDomListener(map.getContainer(), "DOMMouseScroll", wheelevent);
			map.getContainer().onmousewheel = wheelevent;
			
			//initialize some variables
			custImage = "./images/custMarker.png";
			geocoder = new GClientGeocoder();
			directionsPanel = document.getElementById("route");     
			directions = new GDirections(map,directionsPanel);
			baseMarker = new GMarker(new GLatLng(43.034499,-79.106260));
			baseIcon = baseMarker.getIcon();           
			sites = new Array();
			toSite = true;
			afterLoadCallBack = callBack;
		
			//get address from ip and place in address box
			var inputMsg = "Type your ZIP Code or address here...";
			if(displayGeocoding == 'true'){
				inputMsg = geoip_city() + ", " + geoip_region() + " " + geoip_postal_code();
			}
			document.getElementById("addressBox").setAttribute("value", inputMsg);
			// === create the context menu div ===
			contextmenu = document.createElement("div");          
			contextmenu.style.visibility="hidden";
			contextmenu.style.background="#ffffff";
			contextmenu.style.border="1px solid #8888FF";
			contextmenu.style.padding="2px";
	
			contextmenu.innerHTML = '<a href="javascript:placeMarker(true);"><div width="50" class="context">Directions from here</div></a>'
				+ '<a href="javascript:placeMarker(false);"><div width="50" class="context">Directions to here</div></a>'
				+ '<a href="javascript:zoomIn()"><div width="50" class="context">Zoom in</div></a>'
				+ '<a href="javascript:zoomOut()"><div width="50" class="context">Zoom out</div></a>'
				+ '<a href="javascript:zoomInHere()"><div width="50" class="context">Zoom in here</div></a>'
				+ '<a href="javascript:zoomOutHere()"><div width="50" class="context">Zoom out here</div></a>'
				+ '<a href="javascript:centreMapHere()"><div width="50" class="context">Center map here</div></a>';  
			map.getContainer().appendChild(contextmenu);
	
			
			//add a load listener to the GDirections object
			GEvent.addListener(directions, "load", function() {
				try{                        
					var miles = directions.getSummaryHtml();                         
					document.getElementById('miles').innerHTML = miles;
				
					if(toSite == true){                        
						directions.getRoute(0).getStartGeocode().address = custMarker.getTitle();
						directions.getRoute(0).getEndGeocode().address = curMarker.getTitle();                                
					}else{
						directions.getRoute(0).getStartGeocode().address = curMarker.getTitle();
						directions.getRoute(0).getEndGeocode().address = custMarker.getTitle();    
					}
					
				} catch (er) {
					alert(er.name + " " + er.message);
				}	 
			});           
				
			//add "addoverlay" listener to hide directions markers
			GEvent.addListener(directions, "addoverlay", function(){               
				for(i=0; i < directions.getNumRoutes() + 1; i++){
					var m = directions.getMarker(i);
					map.removeOverlay(m);                                             
				}  
				//BUG WORKAROUND - hide the images in the route dive for now because they come back as null
				$("#route IMG").hide();                
			});    
			
			//call funtion to import xml file and load the site markers
			importXML();  	    
			
			GEvent.addListener(map, "singlerightclick", function(point, src, marker) {
				try{
					clickedPixel = point;
					var x=point.x;
					var y=point.y;
					if (x > map.getSize().width - 120) { x = map.getSize().width - 120 }
					if (y > map.getSize().height - 100) { y = map.getSize().height - 100 }
					var pos = new GControlPosition(G_ANCHOR_TOP_LEFT, new GSize(x,y));  
					pos.apply(contextmenu);
					contextmenu.style.visibility = "visible";                    
					
				} catch (er) {
					alert(er.name + " " + er.message);
				}	 
			});
			
			// === If the user clicks on the map, close the context menu ===
			GEvent.addListener(map, "click", function() {
				contextmenu.style.visibility="hidden";
			});
		
			GEvent.addListener(map, "mouseout", function() {
				contextmenu.style.visibility="hidden";
			});   
		
			GEvent.addListener(map, "dragstart", function(){
				GEvent.trigger(map,"click");
			}); 
		}
		else{
			alert("Your browser is not compatible!");
		}
    } catch (e) {
        alert("Error in loadMap().... " + e.name + " " + e.message);
    }	 
}

//this function imporst the XML file
function importXML() {
    try{
        var req = GXmlHttp.create();
        req.onreadystatechange = function () {                        
            if (req.readyState == 4){                       
                xmlDoc = req.responseXML;
                loadPoints();   
            }                 
        };       
        req.open("GET", locationsPath, true);
        req.send("");
    } catch (e) {
        alert("Error in importXML().... " + e.name + " " + e.message);
    }	
}

//this function is called in the importXML() once the XML file is loaded;
function loadPoints(){
    try{        
		//get all the site elements from the xml doc
		var x = xmlDoc.getElementsByTagName('site');        
			sortedPlaces = new Array();
			   
		//loop through the nodes
		for (i=0;i<x.length;i++) {   
				var place = new Place();
			//loop through the child nodes and put markers on the map
			for (j=0;j<x[i].childNodes.length;j++) {
				if (x[i].childNodes[j].nodeType != 1){
					continue;
				}					
				var node = x[i].childNodes[j];
	
				if(node.nodeName == "name" && node.firstChild) {                        
					place.name = node.firstChild.data;
				}
				else if(node.nodeName == "address" && node.firstChild) {
					place.address = node.firstChild.data;
				}
				else if(node.nodeName == "city" && node.firstChild) {
					place.city = node.firstChild.data;
				}
				else if(node.nodeName == "state" && node.firstChild) {
					place.state = node.firstChild.data;
				}
				else if(node.nodeName == "zip" && node.firstChild) {
					place.zip = node.firstChild.data;
				}
				else if(node.nodeName == "phone" && node.firstChild) {
					place.phone = node.firstChild.data;
				}
				else if(node.nodeName == "web" && node.firstChild) {
					place.web = node.firstChild.data;
				}
				else if(node.nodeName == "lat" && node.firstChild) {
					place.lat = node.firstChild.data;
				}
				else if(node.nodeName == "long" && node.firstChild) {
					place.lon = node.firstChild.data;                    
				}  
				else if(node.nodeName == "photo" && node.firstChild) {
					place.photo = node.firstChild.data;                    
				} 
				else if(node.nodeName == "type" && node.firstChild) {
					place.pinType = node.firstChild.data;                                
				}                        
			}            
			
			sortedPlaces[i] = place;
			
			//we have the data for a mark so create it
			var point = new GLatLng(place.lat,place.lon); 
			var divString = "";   
		
			// create the icon we will user sites
			var icon = new GIcon(baseIcon);      
			icon.image = "/image/default.png";     
			var visible = true;
		
			for(var y=0; y < pinTypes.length; y++){
				var type = pinTypes[y].getAttribute("type");
				var image = pinTypes[y].getAttribute("image");
				var vis = pinTypes[y].getAttribute("visible");                
			
				if(type == place.pinType){
					icon.image = image;
					visible = vis; 
				}	    
			}            
			sites[i] = new GMarker(point,{icon: icon, clickable: true, title: place.name});           
			sites[i].place = place;
				
			map.addOverlay(sites[i]);
			if(visible == "false"){                
				sites[i].hide();
			}
		
			divString = "<div class=\"balloon\">";
			if(place.photo != ""){
				divString = divString + "<a href=\"http://" + place.web + "\" target=\"_blank\"><img src=\"" + place.photo + "\" title=\"" + place.name + "\" height=\"65\" width=\"80\" border=\"0\" /></a><br />";
			}
			divString = divString + place.name;
			if(place.address != ""){
				divString = divString + "<br />" + place.address;
			}
			divString = divString + "<br />" + place.city + ", " + place.state;
			if(place.zip != ""){
				divString = divString + "<br />" + " " + place.zip;
			}
			if(place.phone != ""){
				divString = divString + "<br />" + place.phone;
			}
			if(place.web != ""){
				divString = divString + "<br />" + "<a href=\"http://" + place.web + "\" target=\"_blank\">" + place.web + "</a>";
			}		
			sites[i].bindInfoWindowHtml(divString +
					"<br>Get Directions:<br><a id=\"" + i + "\" title=\"Click to get directions to this point\" href=\"#\" onclick=\"javascript: setCurrentMarker(this.id); getDirections(true);\">To Here</a>" +
					" - <a id=\"" + i + "\" title=\"Click to get directions from this point\" href=\"#\" onclick=\"javascript: setCurrentMarker(this.id); getDirections(false);\">From Here</a></div>");
				
			//this listener will cause a "click" event on the marker causing it to display it's info window
			GEvent.addListener(sites[i], "mouseover", function(){
				GEvent.trigger(this,"click");
			});           
		
			GEvent.addListener(sites[i], "dblclick", function(){
				map.zoomIn();
			});    
		 
		} 
        
        //this calls the function that was passed in with the loadMap function - mostly that will be used to display
        //the places on a div after all the places are added to the map
        if(afterLoadCallBack){
            afterLoadCallBack();
        }
        
        //now get location info and locate the closest dealer
        if(loadDirections == "true"){
            setTimeout(function(){
                var geoCity = geoip_city();
                var geoRegion = geoip_region();
                var geoZip = geoip_postal_code();
                showAddress(geoCity + ", " + geoRegion + ", " + geoZip);
            },5000);  
        }    
    } catch (e) {
        alert("An error occurred in loadPoints...." + e.name + " " + e.message);
    }	 
}

//this funtion is called from an event listener to place a marker (by calling "showAddress(address)")
function placeMarker(toSt){
    try{
        contextmenu.style.visibility="hidden";
        toSite = toSt;
        var p = map.fromContainerPixelToLatLng(clickedPixel);           
        showAddress(p.toUrlValue());

    } catch (e) {
        alert("An error occurred in placeMarker...." + e.name + " " + e.message);
    }       	 
}

//this function reverse geocodes an address and places a marker on the map
function showAddress(address) {        
    if (geocoder) {       
        geocoder.getLocations(address, function(response) {
            if (!response || response.Status.code != 200) {            
                switch(response.Status.code){                
                    case G_GEO_MISSING_ADDRESS:
                        alert("Address is missing. Error code: " + G_GEO_MISSING_ADDRESS);
                        break;
                    case G_GEO_UNKNOWN_ADDRESS:
                        alert("Address is unknown. Error code: " + G_GEO_UNKNOWN_ADDRESS);
                        break;
                    case G_GEO_UNAVAILABLE_ADDRESS:
                        alert("Address is unavailable. Error code: " + G_GEO_UNAVAILABLE_ADDRESS);
                        break;
                    case G_GEO_UNKNOWN_DIRECTIONS:
                        alert("Directions are unknown. Error code: " + G_GEO_UNKNOWN_DIRECTIONS);
                        break;
                }              
            } else {
                try{              
                    var place = response.Placemark[0];
                    var point = new GLatLng(place.Point.coordinates[1],
                    place.Point.coordinates[0]);                        
                    if(custMarker != null){
                        map.removeOverlay(custMarker); 
                    }                           

                    var icon = new GIcon(baseIcon);
                    icon.image = custImage;       
                    custMarker = new GMarker(point,{icon: icon, draggable: true, clickable: true, title: place.address});                
                    map.addOverlay(custMarker);
                    custMarker.bindInfoWindowHtml("<div class=\"balloon\">" + place.address + "<br><br>Get Directions To/From Site:<br><a href=\"#\" onclick=\"javascript: getDirections(false);\">To Here</a>" +
                        " - <a href=\"#\" onclick=\"javascript: getDirections(true);\">From Here</a></div>");                        

                    //now load the directions
                    getDirections(toSite);

                    //listen for the custMarker "dragend" event
                    GEvent.addListener(custMarker, "dragend", function(){
                        showAddress(custMarker.getPoint().toUrlValue());                                
                    });

                    //this listener will cause a "click" event on the marker causing it to display it's info window
                    GEvent.addListener(custMarker, "mouseover", function(){
                        GEvent.trigger(this,"click");
                    });

                    GEvent.addListener(custMarker, "dragstart", function(){
                        custMarker.closeInfoWindow();                               
                    });
					
                } catch (e) {
                    alert("An error occurred in showAddress...." + e.name + " " + e.message);
                }
            }
        } );
    }
}


//this function get directions between the customer marker and the current site marker
function getDirections(toSt) {
    try{
        // now we want to find the closest site	      
        var closest = 0;
        var d = 0;                       
        var pnt = custMarker.getPoint();                      
    
        //loop through all the sites to find the closest one
        for (var x = 0; x < sites.length; x++) {
            var curPlace = sites[x].place;
            var mapTo = false;
            for(var i=0; i < mapToTypes.length; i++){
                var type = mapToTypes[i];
                if(type == curPlace.pinType){
                    mapTo = true;
                }
            }
            //we continue if the current place's type isn't in the mapToTypes array
            if(!mapTo){                
                continue;
            }
            
            var distance = pnt.distanceFrom(sites[x].getPoint());							
            if(x == 0){
                closest = distance;
                d = x;
            }
    
            if(distance < closest){
                closest = distance
                d = x;
            }
        }	       
        //set closest site as the current marker                        
        curMarker = sites[d];   
        curMarker.show();
        
        toSite = toSt;
		directions.clear();
		if(custMarker != null){                
			if(toSite){
				directions.load(custMarker.getPoint().toUrlValue() + " to " + curMarker.getPoint().toUrlValue());                    
			}
			else{
				directions.load(curMarker.getPoint().toUrlValue() + " to " + custMarker.getPoint().toUrlValue());  
			}                		
		}
		else{
			alert("Please type in your address or zip code above first!");
		}        
    } catch (e) {
		alert(e.name + " " + e.message);
    }
}    

//this function builds a div named "location" and a div named "locationsLinks" with all the places in the xml file
function displayPlaces(){
    try{
        sortedPlaces.sort();
        //start the locations table
        var locationHTML = "<table width=\"100%\" border=\"0\" align=\"center\" cellspacing=\"5\" cellpadding=\"0\">";    
        var linksHTML = "";
        var lastState = "";
        var counter = 0;

        for (i=0; i<sortedPlaces.length; i++){
            var place = sortedPlaces[i];
            var newState = place.state != lastState;         

            if(newState){            
                counter++;
                var image = "<img src=\"/images/states/" + place.state.toUpperCase() + ".jpg\" border=\"0\" align=\"top\"/>";
                //its a new state so we put in a state image in the first cell and then start a second cell a put a table in that cell
                locationHTML += "<tr><td colspan=\"2\"><hr width=\"100%\"></td></tr>" +
                    "<tr><td align=\"left\" valign=\"top\"><a id=\"" + place.state.toLowerCase() + "\" name=\"" + place.state.toLowerCase() + "\"></a><font size=\"4\" color=\"#666666\">" + image + "</font></td>" +
                    "<td><table>";

                //build the shortcut header
                if(i > 0 && (counter - 1) % 4 != 0){
                    linksHTML += " :: ";
                }
                linksHTML += "<a title=\"" + place.state.toUpperCase() + "\" Store Locations href=\"#" + place.state.toLowerCase() + "\" onClick=\"javascript:toggleLayer('location',true);\">" + place.state.toUpperCase() + "</a>";
                if(counter % 4 == 0){
                    linksHTML += "<br>";
                }
            }

            var phone = "";
            var web = "";
            if(place.phone){
                phone = place.phone + "</font><br/>";
            }
            if(place.web){
                web = "<a href=\"http://" + place.web + "\" target=\"_blank\">" + place.web + "</a><br/>";
            }

            //create a new row for each place, start cell put the point info in it and then another cell a put the map icon to link to the map
            locationHTML += "<tr><td valign=\"top\" width=\"450\"><font size=\"3\" color=\"#993333\" face=\"Century Gothic, Helvetica, Arial, FontName\"><strong>" + place.name + "</strong>" +
                "</font><font size=\"2\" face=\"Century Gothic, Helvetica, Arial, FontName\"><br/>" + place.address + "<br/>" + place.city + ", " + place.state + " " + place.zip + "<br/>" + phone + web +
                "<br/></td><td valign=\"top\" width=\"75\"><a href=\"javascript:centerMap('" + place.lat + "','" + place.lon + "')\"><img src=\"/images/map_icon.gif\" alt=\"Map Icon\" border=\"0\" style=\"cursor:hand\"/></a></td></tr>";

            if(newState){           
                lastState = place.state;
            }

            if(sortedPlaces.length == i + 1 || sortedPlaces[i + 1].state != place.state){
                locationHTML += "</table></td></tr>";
            }

        }    

        locationHTML += "<tr><td colspan=\"2\"><hr width=\"100%\"></tr></table>";    

        var locationDiv = document.getElementById('location');
        locationDiv.innerHTML = locationHTML; 
        var locationsLinksDiv = document.getElementById('locationlinks');
        locationsLinksDiv.innerHTML = linksHTML;
        
    }catch(error){
        alert("An error occurred in displayPlaces...." + error.name + " " + error.message);
    }
}

///prevent page scroll
function wheelevent(e) {
    if (!e){
        e = window.event;
    }
    if (e.preventDefault){
        e.preventDefault();
    }
    e.returnValue = false;    
} 

function centerMap(lat, lon){      
    document.getElementById('map').scrollIntoView(true);
    map.setCenter(new GLatLng(lat,lon), 11);    
}

function setCurrentMarker(id){
    curMarker.show();
    curMarker = sites[id];        
}
    
function clickclear(thisfield, defaulttext) {
    if (thisfield.value == defaulttext) {
        thisfield.value = "";
    }
}

function clickrecall(thisfield, defaulttext) {
    if (thisfield.value == "") {
        thisfield.value = defaulttext;
    }
}

function toggleLayer(in_layer, show) {
    if(show){
        $("#" + in_layer).fadeIn(1750);         
        if(in_layer == "location"){
            document.getElementById("showHide").checked=true;                
        }        
    }else{        
        $("#" + in_layer).fadeOut(1750);       
    }

}

// === functions that perform the context menu options ===
function zoomIn() {
    // perform the requested operation
    map.zoomIn();
    // hide the context menu now that it has been used
    contextmenu.style.visibility="hidden";
}      
function zoomOut() {
    // perform the requested operation
    map.zoomOut();
    // hide the context menu now that it has been used
    contextmenu.style.visibility="hidden";
}      
function zoomInHere() {
    // perform the requested operation
    var point = map.fromContainerPixelToLatLng(clickedPixel)
    map.zoomIn(point,true);
    // hide the context menu now that it has been used
    contextmenu.style.visibility="hidden";
}      
function zoomOutHere() {
    // perform the requested operation
    var point = map.fromContainerPixelToLatLng(clickedPixel)
    map.setCenter(point,map.getZoom()-1); // There is no map.zoomOut() equivalent
    // hide the context menu now that it has been used
    contextmenu.style.visibility="hidden";
}      
function centreMapHere() {
    // perform the requested operation
    var point = map.fromContainerPixelToLatLng(clickedPixel)
    map.setCenter(point);
    // hide the context menu now that it has been used
    contextmenu.style.visibility="hidden";
}

//<----------------START STRING TOKENIZER----------------------------------------------->
/*******************************************************************/
/***                                                             ***/
/***   Tokenizer.js - JavaScript String Tokenizer Function       ***/
/***                                                             ***/
/***   Version   : 0.2                                           ***/
/***   Date      : 01.05.2005                                    ***/
/***   Copyright : 2005 Adrian Zentner                           ***/
/***   Website   : http://www.adrian.zentner.name/               ***/
/***                                                             ***/
/***   This library is free software. It can be freely used as   ***/
/***   long as this this copyright notice is not removed.        ***/
/***                                                             ***/
/*******************************************************************/
function tokenize()
{
    var input             = "";
    var separator         = " ";
    var trim              = "";
    var ignoreEmptyTokens = true;

    try {
        String(this.toLowerCase());
    }
    catch(e) {
        window.alert("Tokenizer Usage: string myTokens[] = myString.tokenize(string separator, string trim, boolean ignoreEmptyTokens);");
        return;
    }

    if(typeof(this) != "undefined")
    {
        input = String(this);
    }

    if(typeof(tokenize.arguments[0]) != "undefined")
    {
        separator = String(tokenize.arguments[0]);
    }

    if(typeof(tokenize.arguments[1]) != "undefined")
    {
        trim = String(tokenize.arguments[1]);
    }

    if(typeof(tokenize.arguments[2]) != "undefined")
    {
        if(!tokenize.arguments[2])
            ignoreEmptyTokens = false;
    }

    var array = input.split(separator);

    if(trim)
        for(var i=0; i<array.length; i++)
    {
        while(array[i].slice(0, trim.length) == trim)
            array[i] = array[i].slice(trim.length);
        while(array[i].slice(array[i].length-trim.length) == trim)
            array[i] = array[i].slice(0, array[i].length-trim.length);
    }

    var token = new Array();
    if(ignoreEmptyTokens)
    {
        for(var i=0; i<array.length; i++)
            if(array[i] != "")
                token.push(array[i]);
    }
    else
    {
        token = array;
    }

    return token;
}
//<----------------END STRING TOKENIZER----------------------------------------------->
