﻿var gridSquare;
var localSearch;
var map;
var icon;
var drawCircle;
var circleRadiusDDLName;
var minRes;
var maxRes;

function getQueryStringBits(name)
{   qs = window.location.search.substring(1);
    bits = qs.split("&");
    for (i=0; i < bits.length; i++)
    {   bit = bits[i].split("=");
        if (bit[0] == name)
            return bit[1];
    }
}
// Get Search Type and Value, and set up Map Types.
function load(searchType, searchValue, canvasName, gridRefAtClickBoxName, gridRefAtMouseBoxName, showOverviewMapControl, showSmallMapTypeControl,
              showLRCBoundaryControl, displayText, displayInsertGridRefBtn, gridRefTypeDDLName, gridRefTypeSpanName, drawCentralGridSquare, getBoundaryInfo,
              drawCircleAndPoint, circleRadDDLName, minResolution, maxResolution) {
    if (GBrowserIsCompatible())
    {   if (document.getElementById(gridRefAtClickBoxName))
        {   if (searchType == null && searchValue == null && document.getElementById(gridRefAtClickBoxName).value != "")
            {   searchType = "GridReference";
                searchValue = (document.getElementById(gridRefAtClickBoxName)).value.toUpperCase();
            }
        }
        drawCircle = drawCircleAndPoint;
        circleRadiusDDLName = circleRadDDLName;
        if (minResolution != null)
            minRes = minResolution;
        else
            minRes = 0;

        if (maxResolution != null)
            maxRes = maxResolution;
        else
            maxRes = 10;
        if(!canvasName) canvasName = "map_canvas";
        //Create Map object
        map = new GMap2(document.getElementById(canvasName), { draggableCursor: 'pointer' });
        //Remove any existing overlays
        map.clearOverlays();
        //Add Controls
        try
        {   map.addControl(new GLargeMapControl3D());
        }
        catch(ex)
        {   map.addControl(new GLargeMapControl());
        }
        if (showOverviewMapControl) map.addControl(new GOverviewMapControl());
        if(showSmallMapTypeControl)
            map.addControl(new GMapTypeControl(), new GControlPosition(G_ANCHOR_BOTTOM_RIGHT));
        else
            map.addControl(new GMapTypeControl());
        DrawMap(searchType, searchValue, gridRefAtClickBoxName, gridRefAtMouseBoxName, displayText, displayInsertGridRefBtn,
                gridRefTypeDDLName, gridRefTypeSpanName, drawCentralGridSquare, getBoundaryInfo);
    }
}


//Draw differently depending on search type
function DrawMap(searchType, searchValue, gridRefAtClickBoxName, gridRefAtMouseBoxName, displayText, displayInsertGridRefBtn,
                 gridRefTypeDDLName, gridRefTypeSpanName, drawCentralGridSquare, getBoundaryInfo)
{   var bounds;
    if (searchType == "Postcode" && searchValue != "")
    {   searchValue = unescape(searchValue).replace(" ", "");
        usePointFromPostcode(searchValue, drawCentralGridSquare, gridRefAtClickBoxName, getBoundaryInfo);
    }
    else if (searchType == "Place" && searchValue != "")
    {   var geocoder = new GClientGeocoder();
        searchValue = unescape(searchValue) + ",UK";
        geocoder.getLatLng(searchValue, function(latlon)
        {
            if (!latlon)
                alert("Place '" + searchValue + "' not found");
            else
            {   if (drawCentralGridSquare)
                {   var wgs84 = new GT_WGS84(); //Create Lat/Long Object
                    var coordinate = String(latlon).replace(/[\)\(]/g, "").split(", ");
                    wgs84.setDegrees(coordinate[0], coordinate[1]);
                    var osgb = wgs84.getOSGB(); //Convert Lat/Long to Easting/Northing
                    var gridref = osgb.getGridRef(3); //Get a grid reference with 5 digits
                    if (gridref.indexOf("SV00") == -1 && gridref.indexOf("undefined") == -1)
                    {   if(document.getElementById(gridRefAtClickBoxName))
                            document.getElementById(gridRefAtClickBoxName).value = gridref;
                        var gridSquare = plotOSGridSquare(gridref, "#5E0");
                        map.addOverlay(gridSquare);
                        var bnds = gridSquare.getBounds();
                        popupInfo(bnds.getCenter(), gridref, null, null);
                        map.setCenter(latlon, calculateZoom(gridref.length - 2));
                        map.setMapType(G_HYBRID_MAP);
                        if (getBoundaryInfo) getLocationInfo(gridref, document.getElementById(circleRadiusDDLName).value);
                    }
                }
                else
                {   map.setCenter(latlon, 15);
                    map.setMapType(G_HYBRID_MAP);
                }
            }
        });
    }
    else if (searchType == "GridReference" && searchValue != "")
    {   //***Draw Grid Square***
        var grLength = searchValue.length - 2;
        //Create Grid Square
        gridSquare = plotOSGridSquare(searchValue.toUpperCase(), "#0000FF");
        //Centre Map on middle of Grid Square
        bounds = gridSquare.getBounds();
        map.setCenter(bounds.getCenter(), calculateZoom(grLength));
        map.setMapType(G_HYBRID_MAP);
        //Add Grid Square to map
        map.addOverlay(gridSquare);
        if (getBoundaryInfo) getLocationInfo(searchValue, document.getElementById(circleRadiusDDLName).value);
        //Open initial Info Window
        popupInfo(bounds.getCenter(), searchValue, displayText, null);
    }
    else if (searchType == "Office")
    {   //Create Grid Square
        gridSquare = plotOSGridSquare("SH54326981", "#0000FF");
        //Centre Map on middle of Grid Square
        bounds = gridSquare.getBounds();
        map.setCenter(bounds.getCenter(), calculateZoom(grLength));
        map.setMapType(G_HYBRID_MAP);
        var cofnodIcon = new GIcon(G_DEFAULT_ICON);
        /*var cofnodIcon = new GIcon();
        cofnodIcon.image = "images/CofnodLogo.gif";
        cofnodIcon.iconSize = new GSize(16, 16);
        cofnodIcon.iconAnchor = new GPoint(10, 34);*/
        var markerOptions = { icon:cofnodIcon };
        var marker = new GMarker(bounds.getCenter(), markerOptions);
        var htmlStr = "<img src='images/CofnodLogo.gif' alt='Cofnod Logo' \/><br \/><b>Cofnod<\/b><br \/>Intec, Ffordd y Parc, Parc Menai<br \/>Bangor, Gwynedd, LL57 4FG<br \/><br \/><b>Grid Reference:<\/b> SH54326981";
        GEvent.addListener(marker, "click", function() {marker.openInfoWindowHtml(htmlStr);});
        map.addOverlay(marker);
        map.openInfoWindowHtml(bounds.getCenter(), htmlStr);
        map.setZoom(15);
    }
    else
    {   map.setCenter(new GLatLng(53.0658,-3.7710), 8);
        map.setMapType(G_HYBRID_MAP);
    }

    var xmlPresent = false;
    //If XML content present
    if(document.getElementById("ctl00_BodyPlaceHolder_MapXMLHF")) {
        if (unescape(document.getElementById("ctl00_BodyPlaceHolder_MapXMLHF").value).indexOf("<markers>") != -1) {
            xmlPresent = true;
            var xmlDoc = GXml.parse(document.getElementById("ctl00_BodyPlaceHolder_MapXMLHF").value);
            var markers = xmlDoc.documentElement.getElementsByTagName("marker");
            var recordIcon = new GIcon(G_DEFAULT_ICON);
            var mkrOptions = { icon: recordIcon };
            for (var i = 0; i < markers.length; i++) {   //Get information for each record
                var gridRefXML = markers[i].getAttribute("osgb");
                var htmlString = markers[i].getAttribute("html");
                gridSquare = plotOSGridSquare(gridRefXML.toUpperCase(), "#FF0000");
                bounds = gridSquare.getBounds();
                //var pic = new GIcon();
                //pic.image = "http://www.cofnod.org.uk/images/KML1kSquare.png";
                var mkr = new GMarker(bounds.getCenter(), mkrOptions);
                mkr.bindInfoWindowHtml(htmlString);
                map.addOverlay(mkr);
                map.addOverlay(gridSquare);
            }
        }
    }
    //Only add click event if it's not the Office Location Search
    if (searchType != "Office")
    {   if(gridRefAtMouseBoxName)
        {   GEvent.addListener(map, "mousemove", function(latlng)
                                        {   var mmCoordinate
                                            if (latlng)
                                                mmCoordinate = String(latlng).replace(/[\)\(]/g,"").split(", ");
                                            else
                                                return;
                                            var wgs84 = new GT_WGS84(); //Create Lat/Long Object
                                            wgs84.setDegrees(mmCoordinate[0], mmCoordinate[1]);
                                            var osgb = wgs84.getOSGB(); //Convert Lat/Long to Easting/Northing
                                            var gridref = osgb.getGridRef(5); //Get a grid reference with 8 digits
                                            if (gridref.indexOf("SV00") == -1 && gridref.indexOf("undefined") == -1)
                                                document.getElementById(gridRefAtMouseBoxName).value = gridref;
                                            else
                                                document.getElementById(gridRefAtMouseBoxName).value = "";
                                        });
        }
        if(gridRefAtClickBoxName || displayInsertGridRefBtn)
        {GEvent.addListener(map, "click", function(overlay, latlng, overlaylatlng) {
            var coordinate
            if (latlng != null)
                coordinate = String(latlng).replace(/[\)\(]/g, "").split(", ");
            else
                coordinate = String(overlaylatlng).replace(/[\)\(]/g, "").split(", ");

            var wgs84 = new GT_WGS84(); //Create Lat/Long Object
            wgs84.setDegrees(coordinate[0], coordinate[1]);

            var osgb = wgs84.getOSGB(); //Convert Lat/Long to Easting/Northing
            var gridref
            if (drawCircle) {
                gridref = osgb.getGridRef(4);
            }
            else {
                if (map.getZoom() < 15 && minRes <= 4)
                    gridref = osgb.getGridRef(2); //Get a grid reference with 4 digits
                else if (map.getZoom() < 18 && minRes <= 6 && maxRes >= 6)
                    gridref = osgb.getGridRef(3); //Get a grid reference with 6 digits
                else if (map.getZoom() < 19 && minRes <= 8 && maxRes >= 8)
                    gridref = osgb.getGridRef(4); //Get a grid reference with 8 digits
                else if (map.getZoom() < 21 && maxRes == 10)
                    gridref = osgb.getGridRef(5); //Get a grid reference with 10 digits
                else //if zoomed in too far for max res, just get 4-figure
                    gridref = osgb.getGridRef(2); //Get a grid reference with 4 digits
            }
            //FOR TESTING
            /*var tempos = new GT_OSGB();
            tempos.setGridCoordinates(258600, 372400);
            alert(tempos.getWGS84().latitude + ", " + tempos.getWGS84().longitude);*/
            //Draw Grid Square and display info window
            if (overlay == null) {
                try {
                    if (gridSquare != null) map.removeOverlay(gridSquare);
                }
                catch (ex)
                { }
                if (gridref.indexOf("SV00") == -1 && gridref.indexOf("undefined") == -1) {
                    if (!displayInsertGridRefBtn && document.getElementById(gridRefAtClickBoxName)) document.getElementById(gridRefAtClickBoxName).value = gridref;
                    gridSquare = plotOSGridSquare(gridref, "#5E0");
                    if (xmlPresent == false) map.clearOverlays();
                    map.addOverlay(gridSquare);
                    var bnds = gridSquare.getBounds();

                    var buttonHTML = null;
                    if (displayInsertGridRefBtn) buttonHTML = "<br /><br /><button onclick=\"insertGridReference('" +
                        gridRefAtClickBoxName + "','" + gridref + "','" + gridRefTypeDDLName + "','" + gridRefTypeSpanName +
                        "'); return false;\"><span><em>Insert Grid Reference</em></span></button>";

                    popupInfo(bnds.getCenter(), gridref, null, buttonHTML);

                    if (getBoundaryInfo) getLocationInfo(gridref, document.getElementById(circleRadiusDDLName).value);
                }
                else {
                    if (!displayInsertGridRefBtn) document.getElementById(gridRefAtClickBoxName).value = "";
                }
            }
        });
        }
    }
}

function popupInfo(point, gridref, infoHTML, buttonHTML) {
    var popupHTML = "";
    
    if (infoHTML) {
        popupHTML = infoHTML;
    }
    else {
        if (document.getElementById("ctl00_BodyPlaceHolder_LanguageHF").value == "1")
            if (drawCircle) {
                popupHTML = "<b>Cyfeirnod Grid:<\/b> " + gridref + "<br />"
                      + "<b>Radiws Chwiliad:</b> " + document.getElementById(circleRadiusDDLName).value + "m";
                buttonHTML = "<div id='orderSearchDiv' style='display:none; text-align:center; margin-top:5px;'>" +
                            "<span style='font-size:11px'>Defnyddiwch y manylion hyn i</span>" +
                            "<br /><button onclick=\"location.href='Enquiries.aspx?Page=2&amp;GridRef=" +
                            gridref + "&amp;Radius=" + document.getElementById(circleRadiusDDLName).value +
                            "'; return false;\"><span><em>Archebu Chwilio</em></span></button></div>";
            }
            else {
                popupHTML = "<b>Cyfeirnod Grid:<\/b> " + gridref;
            }
        else {
            if (drawCircle) {
                popupHTML = "<b>Grid Reference:<\/b> " + gridref + "<br />"
                      + "<b>Search Radius:</b> " + document.getElementById(circleRadiusDDLName).value + "m";
                buttonHTML = "<div id='orderSearchDiv' style='display:none; text-align:center; margin-top:5px;'>" +
                            "<span style='font-size:11px'>Use these details to</span>" +
                            "<br /><button onclick=\"location.href='Enquiries.aspx?Page=2&amp;GridRef=" +
                            gridref + "&amp;Radius=" + document.getElementById(circleRadiusDDLName).value +
                            "'; return false;\"><span><em>Order a Search</em></span></button></div>";
            }
            else {
                popupHTML = "<b>Grid Reference:<\/b> " + gridref;
            }
        }
    }
    var btnHTML = ""
    //if (buttonHTML) btnHTML = buttonHTML;
    if (infoHTML)
        map.openInfoWindowHtml(point, popupHTML + btnHTML, { width: 140, autoScroll: true });
    else
        map.openInfoWindowHtml(point, popupHTML + btnHTML, { maxWidth: 90, maxHeight:80, autoScroll: true });
}

function usePointFromPostcode(enteredPostcode, drawCentralGridSquare, gridRefAtClickBoxName, getBoundaryInfo)
{   localSearch = new GlocalSearch()
    localSearch.setSearchCompleteCallback(null, function() {
        if (localSearch.results[0]) {
            var gridref;
            var resultLat = localSearch.results[0].lat;
            var resultLng = localSearch.results[0].lng;
            if (drawCentralGridSquare) {
                var wgs84 = new GT_WGS84(); //Create Lat/Long Object
                wgs84.setDegrees(resultLat, resultLng);
                var osgb = wgs84.getOSGB(); //Convert Lat/Long to Easting/Northing
                gridref = osgb.getGridRef(3); //Get a grid reference with 5 digits
                if (gridref.indexOf("SV00") == -1 && gridref.indexOf("undefined") == -1) {
                    if(document.getElementById(gridRefAtClickBoxName)) document.getElementById(gridRefAtClickBoxName).value = gridref;
                    var gridSquare = plotOSGridSquare(gridref, "#5E0");
                    map.addOverlay(gridSquare);
                    var bnds = gridSquare.getBounds();
                    popupInfo(bnds.getCenter(), gridref, null, null);
                    if (getBoundaryInfo) getLocationInfo(gridref, document.getElementById(circleRadiusDDLName).value);
                }
            }
            var point = new GLatLng(resultLat, resultLng);
            if (drawCentralGridSquare)
                if (drawCircle)
                    map.setCenter(point, calculateZoom());
                else
                    map.setCenter(point, 16);
            else
                map.setCenter(point, 17);
            map.setMapType(G_HYBRID_MAP);
        }
        else {
            alert("Postcode '" + enteredPostcode + "' not found");
        }
    });  
    
    localSearch.execute(enteredPostcode + ", UK");
}

// Draw a circle around centre point
function plotCircle(centre, radius)
{   var poly = [];
    var numPoints = 80;                     //Number of points in polyline
    var lat = centre.lat();
    var lng = centre.lng();
    var d2r = Math.PI / 180;                // degrees to radians
    var r2d = 180 / Math.PI;                // radians to degrees
    var Clat = (radius / 6378100) * r2d;    //  using 6378100m as earth's radius
    var Clng = Clat / Math.cos(lat * d2r);

    //Add each point in the circle
    for (var i = 0; i < numPoints; i++)
    {   var theta = Math.PI * (i / (numPoints / 2));
        Cx = lng + (Clng * Math.cos(theta));
        Cy = lat + (Clat * Math.sin(theta));
        poly.push(new GLatLng(Cy, Cx));
    }
    
    //Add the first point to complete the circle
    poly.push(poly[0]);

    //Create a line with the points from poly, red, 3 pixels wide, 80% opaque
    var line = new GPolyline(poly, '#FF0000', 3, 0.8);

    return line;
}

function insertGridReference(insertIntoBoxName, selectedGridReference, grTypeDDLName, grTypeSpanName)
{   document.getElementById(insertIntoBoxName).value = selectedGridReference;
    var grTypeDDL = document.getElementById(grTypeDDLName);
    var grTypeSpan = document.getElementById(grTypeSpanName);
    if(grTypeDDL)
    {   var grType = grTypeDDL[grTypeDDL.selectedIndex].value;
        if (grType == "")
            grTypeDDL.value = "2";
        grTypeSpan.innerHTML = grTypeDDL[grTypeDDL.selectedIndex].text;
    }
    $find("MapPopupMPE").hide();
}

function IsNumeric(sText)
{   var ValidChars = "0123456789.";
    var IsNumber = true;
    var Char;
 
    for (i = 0; i < sText.length && IsNumber == true; i++) 
    {   Char = sText.charAt(i); 
        if (ValidChars.indexOf(Char) == -1) 
        {   IsNumber = false;
        }
    }
    return IsNumber;
}
function validateGridReference(gridRef)
{   if (gridRef.length == 0)
    {   return true;
    }
    else if (gridRef.length < 4 || gridRef.length % 2 != 0)
    {   if (document.getElementById("ctl00_BodyPlaceHolder_LanguageHF").value == "1")
        {   alert("Mae'r hyd y Cyfeiriad Grid yn Annilys");
            return false;
        }
        else
        {   alert("Invalid Grid Reference Length");
            return false;
        }
    }
    else if (!IsGridLetter(gridRef.substring(0,2)))
    {   if (document.getElementById("ctl00_BodyPlaceHolder_LanguageHF").value == "1")
        {   alert("Llythyrau Grid Annilys");
            return false;
        }
        else
        {   alert("Invalid Grid Letters");
            return false;
        }
    }
    else if (!IsNumeric(gridRef.substring(2)))
    {   if (document.getElementById("ctl00_BodyPlaceHolder_LanguageHF").value == "1")
        {   alert("Rhifau Grid Annilys");
            return false;
        }
        else
        {   alert("Invalid Grid Numbers");
            return false;
        }
    }
    else
    {   return true;
    }
}
function IsGridLetter(sText)
{   var ValidChars = "ABCDEFGHJKLMNOPQRSTUVWXYZabcdefghjklmnopqrstuvwxyz";
    var IsText = true;
    var Char;
 
    for (i = 0; i < sText.length && IsGridLetter == true; i++) 
    {   Char = sText.charAt(i); 
        if (ValidChars.indexOf(Char) == -1) 
        {   IsText = false;
        }
    }
    return IsGridLetter;
}
function plotOSGridSquare(gridRef, colour)
{   //Create new OSGB object
    var grBL = new GT_OSGB();
    //Convert Grid Reference to Easting/Northing
    grBL.parseGridRef(gridRef);
    //Convert Easting/Northing to Lat/Long
    var llBL = grBL.getWGS84();
    //Get Length
    var grLength = gridRef.length - 2;
    var isTetrad = false;
    if(grLength == 3) isTetrad = true;
    
    //Top Left Point
    var grTL = new GT_OSGB();
    grTL.parseGridRef(grBL.getGridSquarePoint(isTetrad, grLength / 2, "topleft"));
    var llTL = grTL.getWGS84();
    
    //Bottom Right Point
    var grBR = new GT_OSGB();
    grBR.parseGridRef(grBL.getGridSquarePoint(isTetrad, grLength / 2, "bottomright"));
    var llBR = grBR.getWGS84();
    
    //Top Right Point
    var grTR = new GT_OSGB();
    grTR.parseGridRef(grBL.getGridSquarePoint(isTetrad, grLength / 2, "topright"));
    var llTR = grTR.getWGS84();
    
    var points = new Array();
    points[0] = new GLatLng(llTR.latitude, llTR.longitude);
    points[1] = new GLatLng(llBR.latitude, llBR.longitude);
    points[2] = new GLatLng(llBL.latitude, llBL.longitude);
    points[3] = new GLatLng(llTL.latitude, llTL.longitude);
    points[4] = new GLatLng(llTR.latitude, llTR.longitude);
    
    var osGridSquare = new GPolyline(points, colour,  4, 0.6);
    var returnPolygon;
    if (drawCircle)
    {   var bnds = osGridSquare.getBounds();
        returnPolygon = plotCircle(bnds.getCenter(), document.getElementById(circleRadiusDDLName).value);
    }
    else
        returnPolygon = osGridSquare;
    
    return returnPolygon;
}

function right(str, count)
{   return str.substring(str.length - count);
}
function calculateZoom(grLength)
{
    if (drawCircle) {
        switch (parseInt(document.getElementById(circleRadiusDDLName).value)) {
            case 250:
                return 16;
                break;
            case 500:
                return 15;
                break;
            case 1000: case 1500:
                return 14;
                break;
            case 2000: case 2500: case 3000:
                return 13;
                break;
            case 4000: case 5000:
                return 12;
                break;
        }
    }
    else
    {   switch(grLength)
        {   case 0:
                return 7;
                break;
            case 2:
                return 11;
                break;
            case 3:
                return 13;
                break;
            case 4:
                return 14;
                break;
            case 6:
                return 17;
                break;
            case 8:
                return 18;
                break;
            case 10:
                return 19;
                break;
        }
    }
}
