2009-10-30 2 views
3

Я пытаюсь работать с API карт google и испытываю некоторые проблемы. Я создал функцию getPoint, которая принимает адрес. Он использует google api, чтобы превратить этот адрес в объект GPoint, используя функцию GClientGeocoder.getLatLng (адрес, обратный вызов). GetLatLng() передает адрес и функцию обратного вызова, как вы можете видеть ниже. Я хочу, чтобы функция getPoint(), которую я написал, возвращала переменную «точка», переданную функции обратного вызова из вызова getLatLng(). Я изо всех сил пытаюсь понять, как это сделать или даже если это можно сделать?Проблема с возвращаемым значением функции Javascript

function getPoint(address) { 
    var geocoder = new GClientGeocoder(); 

    return geocoder.getLatLng(
    address, 
    function(point){ 
     return point; 
    } 
); 
} 

Заранее благодарим за помощь!

ответ

6

GClientGeocoder.getLatLng является асинхронной операцией, так что вы не можете иметь return заявления в getPoint на самом деле делать то, что вы ожидаете.

Вы должны перестроить свой код, чтобы принять функцию обратного вызова, который вы называете, когда асинхронная операция завершает:

function getPoint(address, callback) { 
    var geocoder = new GClientGeocoder(); 

    geocoder.getLatLng(
     address, 
     function(point){ 
      /* asynch operation complete. 
      * Call the callback with the results */ 
      callback(point) 
     } 
    ); 
} 

или даже лучше (хотя и налетом более эзотерического):

function getPoint(address, callback) { 
    var geocoder = new GClientGeocoder(); 

    geocoder.getLatLng(
     address, 
     callback // GClientGeocoder will call the callback for you 
    ); 
} 

Редактировать вопрос:

O K, что это совершенно другой вопрос, но в двух словах, функция обратного вызова JavaScript вы передаете будет иметь доступ к экземпляру карты до тех пор, как вы определяете функцию в том же объеме, как это определено экземпляр карты:

var map = new GMap2(/*...*/); 
var addresses = []; // list of address strings 
for(var i=0; i < addresses.length; i++) { 
    getPoint(addresses[i], function(point) { // pass the callback function 
     map.addOverlay(/*...*/); // map variable is in scope 
    }) 
} 

Этот стиль функции называется замыканием.

+0

Спасибо большое за ответ. Это приводит меня к другой проблеме, я думаю ... У меня есть функция, называемая Initialize(), которая называется onLoad() тела, которая создает объект GMap2. Затем я делаю сообщение ajax для получения списка адресов, а затем прохожу через эти адреса и один за другим создаю объект GPoint, чтобы я мог добавить GMarker в GMap2 для каждого адреса. Разве функция обратного вызова, которую вы говорите, не должна указывать на необходимость доступа к этому объекту GMap? Если да, то как мне получить этот объект GMap2 в области функции обратного вызова? – Ryan

+0

Nevermind, карта в сфере не похожа, я думал, что это не так. Спасибо! – Ryan

+2

Ах, я просто набрал весь ответ на ваш комментарий. –

0

Вы не можете этого сделать. getLatLng() - это асинхронная функция: он отправит HTTP-запрос и вызовет обратный вызов после получения ответа. Между тем, выполнение вашего локального скрипта будет продолжаться, и getLatLng() вернется до вызова вашего обратного вызова.

2

Нет, это невозможно. Вместо этого вы должны настроить метод, который знает, что делать с ответом, как только он появится в какой-то момент в будущем - это характер обратного вызова.

Таким образом, в настоящее время, ваша конструкция выглядит следующим образом:

var myPoint = getPoint(theAddress); 
doSomethingWithPoint(myPoint); 
doSomethingElseWithPoint(myPoint); 

Но теперь она должна выглядеть

function getPoint(address, callback) { 
    var geocoder = new GClientGeocoder(); 
    geocoder.getLatLng(address, callback); 
} 
getPoint(theAddress, function(myPoint) { 
    doSomethingWithPoint(myPoint); 
    doSomethingElseWithPoint(myPoint); 
}); 
+0

+1; но для вашей анонимной функции обратного вызова требуется параметр «myPoint». – RMorrisey

+0

D'oh! Благодарю. 15 символов. 15 символов. 15 символов. –

Смежные вопросы