События маркера Google Maps

#javascript #google-maps

#javascript #google-карты

Вопрос:

У меня есть следующий код для Google Maps. Цель этого кода — отобразить карту с маркером посередине. Маркер можно перетаскивать, и когда он удаляется, мне нужно, чтобы он указывал текущую широту / длину, в которой был удален маркер. Событие не всегда срабатывает. В Chrome, если я просто позволяю коду выполняться, он не работает. Но, если я замедлю это, отладив и остановив код, который прикрепляет событие, а затем продолжу, это сработает. Похоже, что где-то есть условие гонки, но я понятия не имею, где. Может кто-нибудь, пожалуйста, взглянуть и посмотреть, не придумали ли вы что-нибудь.

 function initialize() {
        var myOptions = {
            zoom: 10,
            mapTypeId: google.maps.MapTypeId.ROADMAP
        };
        var canvas = document.getElementById("MapCanvas");
        var map = new google.maps.Map(canvas, myOptions);

        // Try W3C Geolocation (Preferred)
        if (navigator.geolocation) {
            browserSupportFlag = true;
            navigator.geolocation.getCurrentPosition(function (position) {
                initialLocation = new google.maps.LatLng(position.coords.latitude, position.coords.longitude);
                map.setCenter(initialLocation);
                marker = new google.maps.Marker({
                    position: initialLocation,
                    draggable: true,
                    map: map,
                    title: "You are here"
                });  
            }, function () {
                handleNoGeolocation(browserSupportFlag);
            });
            // Try Google Gears Geolocation
        } else if (google.gears) {
            browserSupportFlag = true;
            var geo = google.gears.factory.create('beta.geolocation');
            geo.getCurrentPosition(function (position) {
                initialLocation = new google.maps.LatLng(position.latitude, position.longitude);
                map.setCenter(initialLocation);
                marker = new google.maps.Marker({
                    position: initialLocation,
                    draggable: true,
                    map: map,
                    title: "You are here"
                });  
            }, function () {
                handleNoGeoLocation(browserSupportFlag);
            });
            // Browser doesn't support Geolocation
        } else {
            browserSupportFlag = false;
            handleNoGeolocation(browserSupportFlag);
        }



        google.maps.event.addListener(marker, 'dragend', function () {
            $("#txtLat").val(marker.position.Ia);
            $("#txtLong").val(marker.position.Ja);
        });




    }   
  

Ответ №1:

Я не тестировал это, но похоже, что marker инициализируется в рамках одной из getCurrentPosition функций. Я предполагаю, что обе эти функции являются асинхронными, поэтому они принимают функцию обратного вызова. Однако вы пытаетесь подключить функцию прослушивателя к marker синхронно — так что в обычных условиях вы, вероятно, пытаетесь подключить прослушиватель к marker до marker инициализации. (Кроме того, я не вижу var инструкции для marker , поэтому, если вы не упустили это, marker находится в глобальном пространстве имен — вероятно, не то, что вы хотите).

Способ исправить это — подключить прослушиватель к функции обратного вызова после marker инициализации. Поскольку обратный вызов выглядит одинаково для W3C Geolocation API и Gears API, возможно, вам захочется поместить все это в одну функцию:

 function initialize() {
    var myOptions = {
        zoom: 10,
        mapTypeId: google.maps.MapTypeId.ROADMAP
    };
    var map = new google.maps.Map(canvas, myOptions);
    var marker;

    // set up callback
    function initMap(initialLocation) {
        map.setCenter(initialLocation);
        // init marker
        marker = new google.maps.Marker({
            position: initialLocation,
            draggable: true,
            map: map,
            title: "You are here"
        });
        // now attach the event
        google.maps.event.addListener(marker, 'dragend', function () {
            // you know you'd be better off with 
            // marker.getPosition().lat(), right?
            $("#txtLat").val(marker.position.Ia);
            $("#txtLong").val(marker.position.Ja);
        });
    }

    // Try W3C Geolocation (Preferred)
    if (navigator.geolocation) {
        navigator.geolocation.getCurrentPosition(function (position) {
            // call the callback
            initMap(new google.maps.LatLng(
                position.coords.latitude, position.coords.longitude
            ));
        }, function () {
            // I just assumed you weren't using 
            // browserSupportFlag anywhere else
            handleNoGeolocation(true); 
        });
    // Try Google Gears Geolocation
    } else if (google.gears) {
        var geo = google.gears.factory.create('beta.geolocation');
        geo.getCurrentPosition(function (position) {
            initMap(new google.maps.LatLng(
                position.latitude, position.longitude
            ));
        }, function () {
            handleNoGeoLocation(true);
        });
    // Browser doesn't support Geolocation
    } else {
        handleNoGeolocation(false);
    }

}