/*
Object: MapLoader
Purpose: Given a 'div' element, loads a Google Map into it.
Notes:
-This is a singleton object. You must not create more than one at a time.
-Requires that the Google Map API be loaded.
-Uses Map action to get longitude/latitude.
-Requires the XmlHttpRequest object.
*/

/*
Constructor
*/
MapLoader = function(divName, divWidth, divHeight, streetNumber, streetName, district, postalCode, mapActionURL)
{
	//The div which will contain the map
	//We delay setting this value until loadMap() is called, because the page may not yet be fully loaded
	this.div = null;
	
	//Name of the div
	this.divName = divName;
	
	//Need size of div, because if div is hidden when trying to load map, the map doesn't look right.
	//So, we explicitly tell Google what size the map should be
	this.divWidth = divWidth;
	this.divHeight = divHeight;

	//Parameters to be passed to Map action
	this.streetNumber = streetNumber;
	this.streetName = streetName;
	this.district = district;
	this.postalCode = postalCode;
	
	//The URL for the map action
	this.mapActionURL = mapActionURL;

	//We don't reload the map twice
	this.isMapLoaded = false;
		
	//parameters for loading the map from DB lat and long fields
	this.coordinates = false;
	this.latCo = "";
	this.lngCo = "";
	
	MapLoader.instance = this;
}

//The instance of this MapLoader class
MapLoader.instance = null;

//Callback function for XMLHttpRequest object.
//This little hack is necessary because, apparently, if you try to assign a prototype method to a function pointer,
//when it is used, "this" is lost and the method won't work.
MapLoader.reqCallback = function()
{
	MapLoader.instance.displayMap();
}

//Should ALWAYS access div through this function
MapLoader.prototype.getDiv = function()
{
	if ( !this.div )
	{
		this.div = document.getElementById(this.divName);
	}
	
	return this.div;
}

//Start loading the map
MapLoader.prototype.loadMap = function()
{
	var div = this.getDiv();
	if ( !this.isMapLoaded )
	{
		div.innerHTML="<div style=\"color:red\">Please wait...</div>";
		var req = new XMLHttpRequest();
		window.req = req;
		req.onreadystatechange=MapLoader.reqCallback;
		req.open('GET', this.mapActionURL + '?street_number=' + encodeURIComponent(this.streetNumber) 
		   + '&street_name=' + encodeURIComponent(this.streetName) 
			+ '&district=' + encodeURIComponent(this.district) 
			+ '&postal_code=' + encodeURIComponent(this.postalCode), true);
		req.send(null);
		this.isMapLoaded = true;
	}
}
//load map from DB coordinates
MapLoader.prototype.loadMapLatLng = function(lat, lng)
{
	if ( !this.isMapLoaded )
	{
		this.coordinates = true;
		this.latCo = lat;
		this.lngCo = lng;
		
		MapLoader.instance.displayMap();
		this.isMapLoaded = true;
	}
}


MapLoader.prototype.displayMap = function()
{
	var div = this.getDiv();
	
	//if we are loading from DB
	if (this.coordinates)
	{
		var point = new GPoint(this.lngCo, this.latCo);	    
		var map = new GMap(div, null, this.divWidth, this.divHeight);
		map.addControl(new GSmallMapControl());
		map.addControl(new GMapTypeControl());
		map.centerAndZoom(point, 4);
		
		var marker = new GMarker(point);
		var html = "<p style=\"width:180px;\"><b>" + this.streetNumber +" "+ this.streetName +", "+ this.district + "</b></p>";
		  GEvent.addListener(marker, "click", function() {
		    marker.openInfoWindowHtml(html);
		  });
		
		map.addOverlay(marker);
	}else{
	//load from address lookup
	
	var req = window.req;
	
	if (req.readyState == 4 && req.status == 200)
	{
		div.innerHTML="";
		var strs = req.responseText.split("\t");
		var addr = strs[0];
		var lng = strs[1];
		var lat = strs[2];

		if (lng == '0' && lat == '0')
		{
			div.innerHTML="Could not get map for <b>" + addr + "</b>";
		}
		else
		{
		    var point = new GPoint(lng, lat);	    
		    var map = new GMap(div, null, this.divWidth, this.divHeight);
		    map.addControl(new GSmallMapControl());
		    map.addControl(new GMapTypeControl());
		    map.centerAndZoom(point, 4);
		
		 	var marker = new GMarker(point);
		  	var html = "<b>" + addr + "</b>";
		  	GEvent.addListener(marker, "click", function() {
		    	marker.openInfoWindowHtml(html);
		   	});
		
			map.addOverlay(marker); 
		}
	}
	}
}

