﻿/// <reference path="jquery-1.4.1-vsdoc.js" />

var GoogleMap = function () {
	this.initialize.apply(this, arguments);
};

GoogleMap.prototype = {
    initialize: function (arg) {
        this.mapContainer = arg.container;
        this.newyorkLocation = new google.maps.LatLng(40.69847032728747, -73.9514422416687);
        this.renderControls = arg.renderControls !== undefined ? arg.renderControls : true;
        this.mapZoom = arg.mapZoom !== undefined ? arg.mapZoom : 15;
        this.xPan = arg.xPan !== undefined ? arg.xPan : 0;
        this.markerLatLng = arg.markerLatLng;
        this.myLatLng = arg.myLatLng !== undefined ? arg.myLatLng : this.newyorkLocation;
        this.findMe = arg.findMe !== undefined ? arg.findMe : true;
        this.showMe = arg.showMe !== undefined ? arg.showMe : true;
        this.myMarker = {};
        this.myAccuracy = 0;
        this.myAccuracyRadius = {};
        this.myFormattedLocation = "";
        this.goToUser = arg.goToUser !== undefined ? arg.goToUser : true;
        this.browserSupportFlag = new Boolean();
        this.iconMarkerStar = new google.maps.MarkerImage('i/star.png', new google.maps.Size(32, 32), new google.maps.Point(0, 0), new google.maps.Point(16, 16));
        this.iconMarkernew = new google.maps.MarkerImage('i/blue-black-32.png', new google.maps.Size(32, 32), new google.maps.Point(0, 0), new google.maps.Point(16, 32));
        this.iconMarkerFavnew = new google.maps.MarkerImage('i/blue-black-fav-32.png', new google.maps.Size(32, 32), new google.maps.Point(0, 0), new google.maps.Point(16, 32));
        this.iconMarkernewMyLocation = new google.maps.MarkerImage('i/me.png', new google.maps.Size(16, 16), new google.maps.Point(0, 0), new google.maps.Point(8, 8));
        this.marker = {};
        this.circle = {};
        //this.clickHold;
        this.clickHoldActive = false;
        this.geocoder = new google.maps.Geocoder();
        this.baloon = null;

        this.mapOptions = {
            zoom: this.mapZoom,
            center: this.myLatLng,
            draggable: true,
            mapTypeControl: this.renderControls,
            mapTypeControlOptions: {
                style: google.maps.MapTypeControlStyle.DROPDOWN_MENU, //ZOOM_PAN,
                position: google.maps.ControlPosition.RIGHT_BOTTOM
            },
            navigationControl: this.renderControls,
            scaleControl: this.renderControls,
            disableDefaultUI: this.renderControls == false,
            navigationControlOptions: {
                style: google.maps.NavigationControlStyle.SMALL, //ZOOM_PAN,
                position: google.maps.ControlPosition.LEFT_CENTER
            },
            mapTypeId: google.maps.MapTypeId.ROADMAP
        };

        this.mapObject = new google.maps.Map(this.mapContainer, this.mapOptions);

        if (this.findMe)
            this.detectUserLocation();

        var local = this;

        google.maps.event.addListener(this.mapObject, 'mousedown', function (event) {
            //local.clickHold = new Date();
            //local.clickHoldActive = true;
            //local.clickHold = setTimeout(function () { local.placeMark(event.latLng.lat(), event.latLng.lng()); }, 500);
            local.clickHoldActive = true;
        });

        google.maps.event.addListener(this.mapObject, 'mouseup', function (event) {
            if (local.clickHoldActive && local.renderControls) {
                local.clickHoldActive = false;
                local.placeMark(event.latLng.lat(), event.latLng.lng());
            }
            //clearTimeout(local.clickHold);
        });

        google.maps.event.addListener(this.mapObject, "dragstart", function () {
            local.clickHoldActive = false;
            //clearTimeout(local.clickHold);
        });
    },
    detectUserLocation: function () {
        var me = this;
        // Try W3C Geolocation method (Preferred)
        if (navigator.geolocation) {
            navigator.geolocation.getCurrentPosition(function (position) {
                me.myLatLng = new google.maps.LatLng(position.coords.latitude, position.coords.longitude);
                me.myAccuracy = position.coords.accuracy;
                me.handeleGeolocation();
            }, function () {
                me.handleNoGeolocation();
            });
        }
        else if (google.gears) {
            // Try Google Gears Geolocation
            var geo = google.gears.factory.create('beta.geolocation');
            geo.getCurrentPosition(function (position) {
                me.myLatLng = new google.maps.LatLng(position.latitude, position.longitude)
                me.myAccuracy = position.accuracy;
                me.handeleGeolocation();
            }, function () {
                me.handleNoGeolocation();
            });
        }
        else {
            me.handleNoGeolocation();
        }
    },

    handeleGeolocation: function () {
        var local = this;

        if (this.showMe) {
            this.myMarker = new google.maps.Marker({
                position: this.myLatLng,
                map: this.mapObject,
                draggable: false,
                title: "My location",
                icon: this.iconMarkernewMyLocation
            });

            if (this.myAccuracy > 0 && this.myAccuracy < 1000) {
                this.myAccuracyRadius = new google.maps.Circle({
                    map: this.mapObject,
                    fillColor: '#55C8F7', //'#BFE1F3',
                    fillOpacity: 0.2,
                    strokeWeight: 0,
                    radius: this.myAccuracy,
                    zIndex: 0
                });
                this.myAccuracyRadius.bindTo('center', this.myMarker, 'position');
            }
        }

        if (this.goToUser)
            this.goToPosition(this.myLatLng);

        this.geocoder.geocode({ 'location': this.myLatLng }, function (results, status) {
            if (status == google.maps.GeocoderStatus.OK) {
                local.myFormattedLocation = results[results.length - 2].formatted_address;
            }
        });
    },

    handleNoGeolocation: function () {
        this.myLatLng = this.newyorkLocation;

        if (this.showMe) {
            this.myMarker = new google.maps.Marker({
                    position: this.myLatLng,
                    map: this.mapObject,
                    draggable: false,
                    title: "My location",
                    icon: this.iconMarkernewMyLocation
                });
        }

        if (this.goToUser)
            this.goToPosition(this.myLatLng);
    },

    clearStyles: function () {
        $(this.mapContainer).removeAttr("style");
    },

    //    removeMarkers: function () {
    //        for (var i = 0; i < this.merkers.length; i++) {
    //            this.markers[i].setMap(null);
    //        }

    //        this.markers = new Array();
    //    },

    placeMark: function (lat, lng, posChangeProxy) {
        var local = this;

        this.markerLatLng = new google.maps.LatLng(lat, lng);

        if (!$.isEmptyObject(this.marker)) {

            this.marker.setMap(null);
            this.marker = null;
            //this.mapObject.setCenter(this.markerLatLng);
        }

        this.marker = new google.maps.Marker({
            position: this.markerLatLng,
            map: this.mapObject,
            draggable: true,
            title: "",
            icon: this.iconMarkernew
        });

        //this.mapObject.setCenter(this.markerLatLng);

        //this.setTaskRadius($("div.l-place li.place-entity-radius.active").attr("taskradius"));
        //this.setMarkerRadius(marker, radius);

        google.maps.event.addListener(local.marker, 'position_changed', $.proxy(function () {
            this.geocoder.geocode({ 'location': local.marker.getPosition() }, function (results, status) {
                if (status == google.maps.GeocoderStatus.OK && posChangeProxy !== undefined) {
                    posChangeProxy(results[0].formatted_address);
                    //$("div.l-place div.place-entity-address").text(results[0].formatted_address);
                }
            });
        }, this));

        google.maps.event.addListener(local.marker, "dragstart", function () {
            local.clickHoldActive = false;
        });

        if (this.baloon != null) {
            this.baloon.open(this.mapObject, this.marker);
            google.maps.event.addListener(local.marker, 'click', function () {
                if (local.baloon.map != null)
                    local.baloon.setMap(null);

                local.baloon.open(local.mapObject, local.marker);
            });
        }
    },

    goToMarker: function () {
        this.goToPosition(this.marker.getPosition());
    },

    goToPosition: function (position) {
        this.mapObject.setCenter(position);
        this.panBy(this.xPan);
    },

    setMarkerRadius: function (radius) {
        radius = parseInt(radius);
        if (!$.isEmptyObject(this.marker)) {
            if ($.isEmptyObject(this.circle)) {
                this.circle = new google.maps.Circle({
                    map: this.mapObject,
                    fillColor: '#55C8F7', //'#BFE1F3',
                    fillOpacity: 0.10,
                    strokeColor: '#55C8F7',
                    strokeWeight: 2,
                    strokeOpacity: 0.8,
                    radius: radius,
                    zIndex: 1
                });
                this.circle.bindTo('center', this.marker, 'position');
            }
            else {
                //var value = this.getRadius();
                this.circle.setRadius(radius);
            }
        }
    },

    setMarkerBaloon: function (content) {
        var local = this;

        if (local.baloon != null && local.baloon.map != null) {
            local.baloon.setMap(null);
            local.baloon = null;
        }

        local.baloon = new google.maps.InfoWindow({
            content: content
        });
    },

    panBy: function (xPan) {
        if (xPan === undefined)
            xPan = 0;

        this.mapObject.panBy(xPan, 0);
    }
}
