var gmap_displayLimit = 0;
var gmap_resultList = new Array();
var gmap_resultZoom = 12;
var gmap = null;
var gmap_geocoder = null;
var gmap_locations = new Array();
var gmap_filmid = 0;
var gmap_markerOptions = null;
var gmap_cityMarkerOptions = null;
var gmap_cityMarker = null;
var gmap_markerNormImg = "/_img/cinema-finder/marker_blue.png";
var gmap_markerActImg = "/_img/cinema-finder/marker_pink.png";

function gmap_init(filmid) {
	if (GBrowserIsCompatible()) {	    
		
		document.getElementById("gmap_box").style.display="block";

        if(filmid > 0) {
            gmap_filmid = filmid;
        }

	    gmap = new GMap2(document.getElementById("gmap_box"));
		gmap_geocoder = new GClientGeocoder();

		gmap.setCenter(new GLatLng(54.5,-3), 5, G_NORMAL_MAP);
		gmap.addControl(new GSmallMapControl());
//	   	gmap.enableScrollWheelZoom();
	   	gmap.enableContinuousZoom(); // caution

	   	function wheelevent(e)
		{
			if (!e) {
				e = window.event;
			}
			if (e.preventDefault) {
				e.preventDefault();
			}
			e.returnValue = false;
		}
		GEvent.addDomListener(gmap.getContainer(), "DOMMouseScroll", wheelevent);
		gmap.getContainer().onmousewheel = wheelevent; 


		var markerIcon = new GIcon(G_DEFAULT_ICON);
		markerIcon.image = "/_img/cinema-finder/marker_blue.png";
		markerIcon.iconSize = new GSize(14,34);
		markerIcon.shadowSize = new GSize(40,34);	
		gmap_markerOptions = {icon: markerIcon };
		
		var cityMarkerIcon = new GIcon(markerIcon);
		cityMarkerIcon.image = "/_img/cinema-finder/marker_here.png";
		cityMarkerIcon.iconSize = new GSize(24,24);
		cityMarkerIcon.shadow = "/_img/cinema-finder/marker_here_shadow.png";
		cityMarkerIcon.shadowSize = new GSize(32,24)
		cityMarkerIcon.iconAnchor = new GPoint(12,12);
		gmap_cityMarkerOptions = {icon: cityMarkerIcon};
		
		for(var i=0; i<gmap_locations.length; i++) {
			gmap_createMarker(i);
		}
		
		document.getElementById("gmap_form").onsubmit=function() { gmap_search(this.pcfi_city.value); return false; };
	}
}

function gmap_createMarker(i) {
	var location=gmap_locations[i];
	var marker = new GMarker(new GLatLng(location[2], location[3]), gmap_markerOptions);
	var html = "<div class=\"gmap_bubble\"><a href=\"/fanatic/film_times/s"+location[4]+"/\"><strong>"+location[0]+"</strong></a><br />"+location[6]+"<br/>"+location[5]+", "+location[1]+"</div>";
    if(gmap_filmid > 0) {
        html = "<div class=\"gmap_bubble\"><a href=\"/fanatic/film_info/s"+location[4]+"/m"+gmap_filmid+"/\"><strong>"+location[0]+"</strong></a><br />"+location[6]+"<br/>"+location[5]+", "+location[1]+"</div>";
    }

	GEvent.addListener(marker, "click", function() { marker.openInfoWindowHtml(html); });
	gmap.addOverlay(marker);

	gmap_locations[i][20] = marker; // saving reference to the actual marker-object
}

function gmap_sortByDistance(a, b) {
    var x = a[7]; // idx(5)=distance
    var y = b[7];
    return ((x < y) ? -1 : ((x > y) ? 1 : 0));
}

function gmap_search(q) {
	var rangeInMeters=5000; // search in this area

	gmap_geocoder.getLatLng(q + ", UK",
		function(point) {
			if(!point) {
				alert("The postcode or town could not be found!"); // TODO
			}
			else {
				var result="";
				var pointsInRange=new Array();
				var zoom = 14;
				var marginPercentOfDelta=15;
				var bounds = new GLatLngBounds();
				
				if(gmap_cityMarker!=null)
					gmap.removeOverlay(gmap_cityMarker);
				
				gmap_cityMarker = new GMarker(point, gmap_cityMarkerOptions);
								
				GEvent.addListener(gmap_cityMarker, "mouseover", function() {
						gmap.panTo(point);
				});
		

				gmap.addOverlay(gmap_cityMarker);
				
				gmap_resultList=gmap_locations;
				
				for(var i=0; i<gmap_resultList.length; i++) {
					var cinema=new GLatLng(gmap_resultList[i][2],gmap_resultList[i][3]);
					gmap_resultList[i][7]=point.distanceFrom(cinema);
				}
				
				// sort the array by distance
				gmap_resultList.sort(gmap_sortByDistance);

				for(var i=0; i<gmap_resultList.length; i++) {
					var cinema=new GLatLng(gmap_resultList[i][2],gmap_resultList[i][3]);
					
					if(gmap_resultList[i][7] < rangeInMeters) {
						pointsInRange.push(cinema);
					}
				}
				
				if(pointsInRange.length>1) {
					for(var i=0; i<pointsInRange.length; i++) {
						bounds.extend(pointsInRange[i]);
					}
					gmap_resultZoom = gmap.getBoundsZoomLevel(bounds);
					gmap.setCenter(bounds.getCenter(), gmap_resultZoom);
				}
				else if(pointsInRange.length==1) {
					gmap_resultZoom=14;
					gmap.setCenter(pointsInRange[0], gmap_resultZoom);
				}
				else {
					//test: Capel
					bounds.extend(point);
					
					var cinemaPoint=new GLatLng(gmap_resultList[0][2], gmap_resultList[0][3]);
					bounds.extend(cinemaPoint);
					
					var px=point.x, py=point.y;
					var lx=cinemaPoint.x, ly=cinemaPoint.y;
					var ox=Math.abs(px-lx), oy=Math.abs(py-ly);	
					
					var bx=0,by=0;

					var marginFactor=1+( 1 / 100 * marginPercentOfDelta );
					
					if(px>=lx)
						bx=px+ox*marginFactor;
					else
						bx=px-ox*marginFactor;
					
					if(py>=lx)
						by=py+oy*marginFactor;
					else
						by=py-oy*marginFactor;
					
					/*alert("px: " + px + "    py: " + py + "\n" +
						  "lx: " + lx + "    ly: " + ly + "\n" +
						  "ox: " + ox + "    oy: " + oy + "\n" +
						  "bx: " + bx + "    by: " + by);*/
					
					
					
					bounds.extend(new GLatLng(py-oy*marginFactor,px+ox*marginFactor)); 
					bounds.extend(new GLatLng(by,bx)); 
					
					gmap.setCenter(bounds.getCenter(), gmap.getBoundsZoomLevel(bounds));
					
				}

				gmap_displayLimit=10;
				gmap_displayResults(gmap_displayLimit);
			}
		});
	return false;
}

function gmap_displayResults(limit) {
	if(gmap_resultList.length < limit) limit = gmap_resultList.length;
	var result="";

	for(var i=0; i<limit; i++) {
		if(gmap_filmid > 0) {
            result+="<div class=\"gmap-result\"><div class=\"gmap-result-text\"><a href=\"#\" title=\"Show ODEON "+gmap_resultList[i][0]+" on the map\" onmouseover=\"gmap_moveTo("+gmap_resultList[i][2]+","+gmap_resultList[i][3]+"); gmap_actMarker(gmap_locations["+i+"],true);\" onmouseout=\"gmap_actMarker(gmap_locations["+i+"],false);\" onclick=\"gmap_moveTo("+gmap_resultList[i][2]+","+gmap_resultList[i][3]+"); gmap.setZoom(15); return false;\">"+gmap_resultList[i][0]+"</a> - "+Math.round(gmap_resultList[i][7]/16.09344)/100+" miles<br />"+gmap_resultList[i][6]+", "+gmap_resultList[i][5]+", "+gmap_resultList[i][1]+"</div><div class=\"gmap-result-link\"><a href=\"/fanatic/film_info/s"+gmap_resultList[i][4]+"/m"+gmap_filmid+"/\" title=\"See this film at ODEON "+gmap_resultList[i][0]+"\" class=\"goBtn\">GO</a></div></div>\n";
        } else {
            result+="<div class=\"gmap-result\"><div class=\"gmap-result-text\"><a href=\"#\" title=\"Show ODEON "+gmap_resultList[i][0]+" on the map\" onmouseover=\"gmap_moveTo("+gmap_resultList[i][2]+","+gmap_resultList[i][3]+"); gmap_actMarker(gmap_locations["+i+"],true);\" onmouseout=\"gmap_actMarker(gmap_locations["+i+"],false);\" onclick=\"gmap_moveTo("+gmap_resultList[i][2]+","+gmap_resultList[i][3]+"); gmap.setZoom(15); return false; \">"+gmap_resultList[i][0]+"</a> - "+Math.round(gmap_resultList[i][7]/16.09344)/100+" miles<br />"+gmap_resultList[i][6]+", "+gmap_resultList[i][5]+", "+gmap_resultList[i][1]+"</div><div class=\"gmap-result-link\"><a href=\"/fanatic/film_times/s"+gmap_resultList[i][4]+"/\" title=\"See all film times at ODEON "+gmap_resultList[i][0]+"\" class=\"goBtn\">GO</a></div></div>\n";
        }
	}

	document.getElementById("gmap_results").innerHTML=result;

	if(limit < gmap_resultList.length) {
		document.getElementById("gmap_results").innerHTML+="<div class=\"boxin\">  <div class=\"namebox\">  <a name=\"resultFoot\" href=\"#resultFoot\" onclick=\"gmap_displayResults(gmap_displayLimit+10);\">show more</a>  </div>  <div class=\"clear\"></div><p class=\"bodytext\"><br>Please note that this service is provided by Google!</p></div></div> <div id=\"three\">   </div> 	</div>";
	}

	gmap_displayLimit=limit;
}

function gmap_actMarker(loc, state) {
	var marker = loc[20];
	var img="";
	
	if(state==true)
		img=gmap_markerActImg;
	else
		img=gmap_markerNormImg;
	
	marker.setImage(img);
}

function gmap_moveTo(lat,lon) {
		var pos = new GLatLng(lat,lon);
		
		if(gmap.getZoom()==gmap_resultZoom) {
			gmap.panTo(pos);
		}
		else {
			gmap.setCenter(pos, gmap_resultZoom);
		}
		return false;
}

function addLoadEvent(func) {
	var oldonload = window.onload;
	if(typeof window.onload != 'function') {
		window.onload = func;	
	}
	else {
		window.onload = function() {
			if(oldonload) {
				oldonload();
			}
			func();
		}
	}
}

function addUnloadEvent(func) {
	var oldonunload = window.onunload;
	if(typeof window.onunload != 'function') {
		window.onunload = func;
	}
	else {
		window.onunload = function() {
			if(oldonunload) {
				oldonunload();
			}
			func();
		}
	}
}
