Tuesday, May 29, 2012

[Programming] Javascript: Calling 3 Functions Synchronously

Personally, I have no idea why I'm putting programming on this blog. This wouldn't seem like the place to post programming questions and help; however, I feel like when I talk aloud to myself or type down extensive notes and comments, it helps me think and figure out problems I couldn't solve by simply staring at them.

The problem I'm currently having with one of my projects involves 3 functions that are running asynchronously (all at once) while I want them to run synchronously (one after the other).



The first two functions read in a user-input set from a text box upon form submission, pass them through Google Maps API's "geocoder" function, and returns the latitude and longitude of that location.

function setOrigin(){
    //Search input for "Origin"
    var search = $('#input_origin').val();
    
    //Create the Google Geocoder object    
    var geocoder = new google.maps.Geocoder();
    var location;
            
    geocoder.geocode({
        //Search for the address in Google Maps database
        address: search,
    }, 
    function(results, status){
        //If the location can be found, set result
        if (status == google.maps.GeocoderStatus.OK){
            result = results[0].geometry.location;
        }
        //Else, report error
        else{
            result = "Unable to find address";
        }
        
        origin = result;
        console.log('Step 1: Set Origin');
        console.log('Origin: '+origin);
    });
}

The same code is repeated for the most part in the function "setDestination" with the input value being taken from "#input_dest".

The third function simply gets the latitude and longitude coordinates returned from the "setOrigin" and "setDestination" and passes them to Google Maps API's "directionsService" function.

function getDirections(){    
    console.log('Step 3: Run Direction Service');
    var request = {
        origin: origin,
        destination: destination,
        travelMode: google.maps.TravelMode.DRIVING,
    };
    directionsService.route(request, function(result, status){
        if(status == google.maps.DirectionsStatus.OK){
            directionsDisplay.setDirections(result);
        }
        else{
            console.log(status);
        }
    });
}

The problem is that retrieving the input, sending it to Google, and getting the results back from the first and second functions take longer than the last function. Simply calling the functions in order doesn't work since "getDirections" is called before the variables "origin" and "destination" are set in the previous two functions.

$('#submit_trip').live('click', function(e)
{
    setOrigin();
    setDestination();
    getDirections();
});

I have tried putting the functions in one another as callback functions, as suggested here, but the results remain the same.

function setOrigin(callback){
    //Code here
    callback();
}
function setDestination(callback){
    //Code here
    callback();
}
function getDirections(){
    //Code here
}

setOrigin(
    setDestination(){
        getDirections();
    }
);

I am currently using "setTimeout" to force a delay on the last function on running until the others have completed. This is solely to get the code working but would probably not be recommended for actual use in the code. This is because based on the users' connection speeds, the hard-coded delay timer might not be enough and may result in the same problems as before if this occurs.

$('#submit_trip').live('click', function(e){
    setOrigin();
    setDestination();
    setTimeout('getDirections()', 1000);
});

A friend suggested the obvious "if" conditional to check if the variables have been set (which for some reason, I didn't think of that while writing the code at all) but that would only check on initialization. I would probably couple that with a "while" loop for continuous checking but as of right now, I have yet to write/test that code to see if it's viable.

I intend updating this and posting the results here for future reference in case anyone stumbles upon this page and happens to face the same problem or if anyone has any suggestions.

Update [05/30/12 @ 12:24am]
I tried the while loop theory and it was a horrible idea. It simply triggers an infinite loop. Still using the timeout as of right now.




1 comment:

  1. its been 3 years since your post and i have th same exact problem.
    i also use setTimeOut but its wrong.
    if you did solved it i would be happy to know how.

    cheers

    ReplyDelete