/**
 * Googlemaps wrapper class
 */
var GoogleMap = Class.create(
{
	/**
	 * Map object constructor
	 */
	initialize: function(sID, aOptions) 
	{
		this.sID 				= sID;
		this.sURI 				= '';
		this.bPopupVisible		= false;
		this.aDefaultOptions 	= 
		{
			height				: 350,
			width				: 290,
			zoom				: 10,
			setCenterLatitude	: 51.894,
			setCenterLongitude	: 5.470,
			controls			: [],
			controlPadding		: 50
		};
		this.aOptions 			= $H(this.aDefaultOptions).merge(aOptions);

		//Setup the map
		this.setup();
	},
	
	/**
	 * Setup the initial map parameters
	 */
	setup: function()
	{
		//Root element
		this.oRoot 				= $(this.sID);
		if (!this.oRoot) 
		{
			return;
		}
		
		//Set map layout
		this.oRoot.setStyle
		({
		      height			: this.aOptions.get('height') + 'px',
		      width				: this.aOptions.get('width') + 'px'
	    });
		
		this.addMap();
		this.addControls();
		
		//Create a GLatLngBounds object
		this.oBounds			= new GLatLngBounds();
		
		//Create geocode object
		this.oGeocoder 			= new GClientGeocoder();
		this.oGeocoder.setBaseCountryCode('.nl');
		
		//Marker array
		this.aMarker			= new Array();

		Event.observe(window, 'unload', GUnload);
	},
	
	/**
	 * Create the map
	 */
	addMap: function()
	{
		if (!GBrowserIsCompatible()) 
		{
			return;
		}

		this.oMap = new GMap2(this.oRoot);
		this.oMap.setCenter(new GLatLng(this.aOptions.get('setCenterLatitude'), this.aOptions.get('setCenterLongitude')), this.aOptions.get('zoom'));
		this.oMap.enableScrollWheelZoom();
	},
	
	/**
	 * Add the controls to the map
	 */
	addControls: function()
	{
		this.aOptions.get('controls').each(function(oControl, iIndex)
		{
			this.oMap.addControl(oControl);
		}.bind(this));
	},

	/**
	 * Geocode an address
	 */
	geocode: function(sAddress, oCallback)
	{
		this.oGeocoder.getLatLng(sAddress, oCallback);
	},
	
	/**
	 * Show a location on the map
	 */
	showLocation: function(fLatitude, fLongitude)
	{
		this.aOptions.set('setCenterLatitude', fLatitude);
		this.aOptions.set('setCenterLongitude', fLongitude);
		this.oMap.setCenter(new GLatLng(this.aOptions.get('setCenterLatitude'), this.aOptions.get('setCenterLongitude')), this.aOptions.get('zoom'));
	},
	
	/**
	 * Set the zoom leven of the map
	 */
	setZoomLevel: function(iZoomLevel)
	{
		this.aOptions.set('zoom', iZoomLevel);
		this.oMap.setZoom(iZoomLevel);
	},
	
	/**
	 * Add multiple markers to the map
	 * @param aMarker Array with GMarker objects
	 */
	addMarkers: function(aMarker)
	{
		aMarker.each
		(
			function(oMarker)
			{
				this.addMarker(oMarker);
			}, this
		)
	},
	
	/**
	 * Add a marker to the map
	 * @param oMarker GMarker object
	 */
	addMarker: function(oMarker)
	{
		this.aMarker.push(oMarker);
		this.oBounds.extend(oMarker.getLatLng());
		this.oMap.addOverlay(oMarker);
	},
	
	/**
	 * Get a marker from a GPoint
	 */
	getMarker: function(oPoint, oOptions)
	{
		var oMarker = new GMarker(oPoint, oOptions);
		return oMarker;		
	},
	
	/**
	 * Delete a marker object from the map
	 */
	deleteMarker: function(oMarker)
	{
		this.oMap.removeOverlay(oMarker);
	},
	
	/**
	 * Center the map view on all the markers
	 */
	centerOnMarkers: function()
	{
		this.oMap.setCenter(this.oBounds.getCenter());
	},
	
	/**
	 * Zoom the map view on all the markers
	 */	
	zoomOnMarkers: function(iZoomOutExtra)
	{
		var iZoomLevel	= this.oMap.getBoundsZoomLevel( this.oBounds );
		if(typeof iZoomOutExtra != 'undefined')
		{
			iZoomLevel = iZoomLevel - iZoomOutExtra;
		}
		this.setZoomLevel(iZoomLevel);
	},
	
	/**
	 * Get custom made icon
	 */
	getGoogleIcon: function(sPalSet, sIcon)
	{
	     var oBaseIcon 				= new GIcon();
	     oBaseIcon.iconSize			= new GSize(17,17);
	     oBaseIcon.iconAnchor		= new GPoint(11,22);
	     oBaseIcon.infoWindowAnchor	= new GPoint(11,0);
	     return new GIcon(oBaseIcon, '/images/gmaps_pointer.png', null, null);
	},
	
	/**
	 * This function will refresh the map state
	 * Usefull when showing a map in a div that was hidden and then shown 
	 */
	refresh: function()
	{
		this.oMap.checkResize();
	},
	
	/**
	 * This function toggles the html window state
	 */
	togglePopup: function(oMarker, sInfo)
	{
		if(this.bPopupVisible)
		{
			oMarker.openInfoWindowHtml(sInfo);
		}
		else
		{
			oMarker.closeInfoWindow();
		}
	}
});
