var map = stdClass.extend({
	//constructor
	constructor: function(el, settings) {
		this.base();
		// initialize settings
		Object.extend(this.s, {
			moduleName: 'mapModule',
			jsonURL: '/map/json.php',
			json: {
				ver: '0.1',
				meta: {},
				data: {
				},
				requests: []
			},
			zoom: 3,
			centerLatitude: 33.000000,
			centerLongitude: -108.000000,
			showPlayers: false,
			showAffiliates: true,
			showAmbassadors: true,
			showSponsors: true,
			imageHost: 'http://www.XtheGame.com',
			userImageDir: '/images/users/',
			defaultImage: '/images/Xpic-64.jpg',
			actionSelector: '.mapaction'
			/* put extensions to settings here */
		});
		Object.extend(this.s, settings);
		
		// initialize nodes
		Object.extend(this.n, {
			el: el,
			map: null
			/* put extensions to nodes here */
		});
		
		// initialize collections
		Object.extend(this.c, {
			requests: [],
			markers: [],  // just storing int flag instead of the object
			actionEls: []
			/* put extensions to collections here */
		});
		
		this._startGoogleMap();
		this._findActionElements();
	},
	
	/* EVENT CAPTURE FUNCTIONS */
	onMoveEnd: function() {
		this.refresh();
	},
	actionOnClick: function(){
		for(var x = 0; x < this.c.actionEls.length; x++){
			if(Element.hasClassName(this.c.actionEls[x], 'showPlayers')){
				if(this.c.actionEls[x].checked){
					this.s.showPlayers = true;
				} else {
					this.s.showPlayers = false;
				}
			}
			if(Element.hasClassName(this.c.actionEls[x], 'showAffiliates')){
				if( this.c.actionEls[x].checked ){
					this.s.showAffiliates = true;
				} else {
					this.s.showAffiliates = false;
				}
			}
			if(Element.hasClassName(this.c.actionEls[x], 'showAmbassadors')){
				if( this.c.actionEls[x].checked ){
					this.s.showAmbassadors = true;
				} else {
					this.s.showAmbassadors = false;
				}
			}
			if(Element.hasClassName(this.c.actionEls[x], 'showSponsors')){
				if( this.c.actionEls[x].checked ){
					this.s.showSponsors = true;
				} else {
					this.s.showSponsors = false;
				}
			}
		}
		//clear the map and refresh
		this.n.map.clearOverlays();
		this.c.markers = [];
		this.refresh();
	},
	markerOnClick: function(marker, html) {
		marker.openInfoWindowHtml(html);
	},
	
	/* GENERIC FUNCTIONS */
	refresh: function() {
		var bounds = this.n.map.getBounds();
		var sw = bounds.getSouthWest();
		var ne = bounds.getNorthEast();
		var minCoords = Array();
		minCoords['lat'] = sw.lat();
		minCoords['lon'] = sw.lng();
		var maxCoords = Array();
		maxCoords['lat'] = ne.lat();
		maxCoords['lon'] = ne.lng();
		this.addRequest("getMarkers", {
			minCoords: minCoords,
			maxCoords: maxCoords,
			showPlayers: this.s.showPlayers,
			showAffiliates: this.s.showAffiliates,
			showAmbassadors: this.s.showAmbassadors,
			showSponsors: this.s.showSponsors
		});
		this.JsonOut();
	},
	createMarker: function(latlng, html, userType) {
		var visible = false;
		if( ( userType != '' ) && ( typeof(userType) == 'string' ) ){
			var icon = new GIcon();
			if( userType == 'Sponsor' || userType == 'Investor' ){
				icon.image = '/images/mapicon_purple-18.png';
  			icon.iconSize = new GSize(18, 30);
  			icon.iconAnchor = new GPoint(10, 30);
  			icon.infoWindowAnchor = new GPoint(10, 1);
			} else if( userType == 'Ambassador' ){
				icon.image = '/images/mapicon_green-15.png';
  			icon.iconSize = new GSize(15, 25);
  			icon.iconAnchor = new GPoint(8, 25);
  			icon.infoWindowAnchor = new GPoint(8, 1);
			} else if( userType == 'Affiliate' ){
				icon.image = '/images/mapicon_yellow-12.png';
  			icon.iconSize = new GSize(12, 20);
  			icon.iconAnchor = new GPoint(6, 20);
  			icon.infoWindowAnchor = new GPoint(6, 1);
			} else if( userType == 'Player' ){
				icon.image = '/images/mapicon_red-9.png';
  			icon.iconSize = new GSize(9, 15);
  			icon.iconAnchor = new GPoint(4, 15);
  			icon.infoWindowAnchor = new GPoint(4, 1);
  		} else { alert("userType: " + userType); }
			
			var marker = new GMarker(latlng, icon);
			GEvent.addListener(marker, 'click', this.markerOnClick.bind(this, marker, html));
			return marker;
		} 
		else {
			return null;
			/*
			alert("whoa!");
			alert("userType: " + userType);
			var marker = new GMarker(latlng);
			GEvent.addListener(marker, 'click', this.markerOnClick.bind(this, marker, html));
			return marker;
			*/
		}
	},
	createInfoWindow: function(userData, coords) {
		var html = "";
		var smallPic = ( userData.user_image_small != null ) ? this.s.userImageDir + userData.user_image_small : this.s.defaultImage;

		var distance = coords.distanceFrom( new GLatLng( parseFloat(this.s.centerLatitude), parseFloat(this.s.centerLongitude) )  );
		// convert to miles and round to one decimal place:
		var myDistance = Math.round( ( distance / 1609 ) * 10 ) / 10 ;

		html += '<div><b>' + userData.user_type_name + '</b></div> <br />'
					+ '<div><table style="border:0; width:200px; height:80px"><tr><td><a href="http://www.XtheGame.com/profile.php?user='
					+ userData.user_ID + '" target="_blank">'
					+ '<img src="'
					+ this.s.imageHost + smallPic
					+ '" align="middle" border="0" /></a> </td><td> '
					+ '<a href="http://XtheGame.com/profiles/?user='
					+ userData.user_ID + '">'
					+ userData.name_first + " " + userData.name_last
					+ '</a> <br /> ';
		return html;
	},

	updateMarkers: function(markers) {
		for( idx in markers ){
			var marker = markers[idx];

			if(typeof(this.c.markers[marker.user_ID]) != 'number' && typeof(marker.user_type_name) == 'string' ){
				this.c.markers[marker.user_ID] = 1;
				var coords = new GLatLng( parseFloat(marker.user_latitude), parseFloat(marker.user_longitude) );
				this.c.markers[marker.user_ID] = this.createMarker( coords, this.createInfoWindow( marker, coords ), marker.user_type_name);
				this.n.map.addOverlay(this.c.markers[marker.user_ID]);
			}
		}
		return;
	},
	
	/* JSON FUNCTIONS */
	addRequest: function(requestName, dataObject) {
		this.c.requests.push({
			id: this.c.requests.length,
			type: requestName,
			data: dataObject
		});
	},
	JsonOut: function(hideThrobber) {
		this.s.json.requests = this.c.requests;
		var data = '__json=' + this.s.moduleName + '&data=' + toJSONString(this.s.json);
		this.c.requests = [];
		var myAjax = new Ajax.Request(this.s.jsonURL,
		{
			method: 'post',
			parameters: data,
			onSuccess: this.JsonIn.bind(this)
		});
	},
	JsonIn: function(t) {
		var result = t.responseText.parseJSON();
		(result.responses.length).times(function(i) {
			switch(result.responses[i].type){
			case 'showMarkers':
				this.updateMarkers(result.responses[i].data.markers);
/*
				this.updateMarkers();
*/
				/* code to show markers on the map */
				break;
			default:
				break;
			}
		}.bind(this));
	},
	
	
	/* CONSTRUCTOR FUNCTIONS */
	_startGoogleMap: function() {
		if(GBrowserIsCompatible()){
			
			var startPoint = new GLatLng( parseFloat(this.s.centerLatitude), parseFloat(this.s.centerLongitude) );
			this.n.map = new GMap2(this.n.el);
			this.n.map.addControl(new GSmallMapControl());
			this.n.map.addControl(new GMapTypeControl());
			this.n.map.setCenter(startPoint, this.s.zoom);
			
			GEvent.addListener(this.n.map,'moveend', this.onMoveEnd.bind(this));
			
			this.refresh();
			
			Element.removeClassName(document.body, 'loading');
			Element.addClassName(document.body, 'standby');
		}
	},
	_findActionElements: function() {
		var eles = document.getElementsBySelector(this.s.actionSelector);
		for(var x=0; x < eles.length; x++){
			this.eObserve(eles[x], 'click', this.actionOnClick.bind(this));
			this.c.actionEls.push( eles[x] );
		}
	}
});
EventSelectors.register({
	'.mapclass' : function(el){
		/* use a class instead of an ID so that if we want to we can have more than one on a page */
		new map (el);
	}
});
