locked
javascript accessing variables within functions RRS feed

  • Question

  • User-418973555 posted

    trying to use var location01lat as global withing its functions, but having alert(location01lat.a); undefined

        function CalculateDistance() {
    
                var geocoder = new google.maps.Geocoder();
                var location01lat = {};
                location01lat.a;
                //var location01lat;
                var location01lng;
                var location02lat;
                var location02lng;
                var location011;
                var location022;
                const center = { lat: 40.774102, lng: -73.971734 };
                const options = { zoom: 15, scaleControl: true, center: center };
                map = new google.maps.Map(
                    document.getElementById('dvMap'), options);
    
    
                geocoder.geocode({ 'address': document.getElementById('<%= txtlocation01.ClientID %>').value + ", my" }, function (results, status) {
    
                    if (status == google.maps.GeocoderStatus.OK) {
                        //document.getElementById('dvDistance').innerHTML = "location1: " + results[0].geometry.location.lat() + ", " + results[0].geometry.location.lng();
                        //location01lat = results[0].geometry.location.lat();
                        let a = results[0].geometry.location.lat();
                        location01lng = results[0].geometry.location.lng();
                        location011 = { lat: location01lat, lng: location01lng };                 
                      
                    } else {
                        alert("Something got wrong " + status);
                    }
    
                });
    
                geocoder.geocode({ 'address': document.getElementById('<%= txtlocation02.ClientID %>').value + ", my" }, function (results2, status) {
                    
                    if (status == google.maps.GeocoderStatus.OK) {
                        //document.getElementById('dvDistance').innerHTML += " ; location2: " + results2[0].geometry.location.lat() + ", " + results2[0].geometry.location.lng();
                        location02lat = results2[0].geometry.location.lat();
                        location02lng = results2[0].geometry.location.lng();
                        location022 = { lat: location02lat, lng: location02lng };
                        
                        //alert("location : " + results[0].geometry.location.lat() + " " +results[0].geometry.location.lng()); 
                    } else {
                        alert("Something got wrong " + status);
                    }
    
                });
    
    
                alert(location01lat.a);
                //const location011 = { lat: location01lat, lng: location01lng };
                //const location022 = { lat: location02lat, lng: location02lng };
    
    
                var mk1 = new google.maps.Marker({ , map: map });
                var mk2 = new google.maps.Marker({ , map: map });
    
                function haversine_distance(mk1, mk2) {
                    //var R = 3958.8; // Radius of the Earth in miles
                    var R = 6371; // Radius of the Earth in kms
                    var rlat1 = mk1.position.lat() * (Math.PI / 180); // Convert degrees to radians
                    var rlat2 = mk2.position.lat() * (Math.PI / 180); // Convert degrees to radians
                    var difflat = rlat2 - rlat1; // Radian difference (latitudes)
                    var difflon = (mk2.position.lng() - mk1.position.lng()) * (Math.PI / 180); // Radian difference (longitudes)
    
                    var d = 2 * R * Math.asin(Math.sqrt(Math.sin(difflat / 2) * Math.sin(difflat / 2) + Math.cos(rlat1) * Math.cos(rlat2) * Math.sin(difflon / 2) * Math.sin(difflon / 2)));
                    return d;
                }
    
                var distance = haversine_distance(mk1, mk2);
                document.getElementById('dvDistance2').innerHTML = "Distance between markers: " + distance.toFixed(2) + " km";
    
                //return false;
    
            }
            

    Saturday, January 18, 2020 1:36 AM

Answers

  • User-474980206 posted

    As stated you are trying to use async values before they are set. Please read about async processing. 

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Sunday, January 19, 2020 8:37 PM

All replies

  • User-474980206 posted

    There is no code that sets  location01lat.a to a value, so of course it’s undefined.

    Saturday, January 18, 2020 1:40 AM
  • User-719153870 posted

    Hi larnvok09,

    First of all, as @bruce mentioned, location01lat.a has never been set a value.

    However, i can see there's let a = results[0].geometry.location.lat(); in your 

    geocoder.geocode({ 'address': document.getElementById('<%= txtlocation01.ClientID %>').value + ", my" }, function (results, status) {
    ...
    let a = results[0].geometry.location.lat();
    ...  });

    If you want to assiagn a for location01lat.a and as global within the CalculateDistance() function then you should have something like:

    geocoder.geocode({ 'address': document.getElementById('<%= txtlocation01.ClientID %>').value + ", my" }, function (results, status) {
    ...
     let a = results[0].geometry.location.lat();
    location01lat.a=a; ...  });

    Best Regard,

    Yang Shen

    Saturday, January 18, 2020 5:52 AM
  • User-418973555 posted

    still undefined for alert('location01lat.a);

                geocoder.geocode({ 'address': document.getElementById('<%= txtlocation01.ClientID %>').value + ", my" }, function (results, status) {
    
                    if (status == google.maps.GeocoderStatus.OK) {
                        //document.getElementById('dvDistance').innerHTML = "location1: " + results[0].geometry.location.lat() + ", " + results[0].geometry.location.lng();
                        //location01lat = results[0].geometry.location.lat();
                        let a = results[0].geometry.location.lat();
                        let b = results[0].geometry.location.lng();
                        //location01lng = results[0].geometry.location.lng();
                        //location011 = { lat: location01lat, lng: location01lng };                 
                        location01lat.a = a;
                        location01lng.b = b;
                    } else {
                        alert("Something got wrong " + status);
                    }
    
                });
    
                geocoder.geocode({ 'address': document.getElementById('<%= txtlocation02.ClientID %>').value + ", my" }, function (results2, status) {
    
                    if (status == google.maps.GeocoderStatus.OK) {
                        //document.getElementById('dvDistance').innerHTML += " ; location2: " + results2[0].geometry.location.lat() + ", " + results2[0].geometry.location.lng();
                        let c = results2[0].geometry.location.lat();
                        let d = results2[0].geometry.location.lng();
    
                        //location02lat = results2[0].geometry.location.lat();
                        //location02lng = results2[0].geometry.location.lng();
    
                        location02lat.c = c;
                        location02lng.d = d;
    
                        //location022 = { lat: location02lat, lng: location02lng };
    
                        //alert("location : " + results[0].geometry.location.lat() + " " +results[0].geometry.location.lng()); 
                    } else {
                        alert("Something got wrong " + status);
                    }
    
                });
    
    
                alert(location01lat.a);

    Saturday, January 18, 2020 11:56 AM
  • User475983607 posted

    larnvok09

    still undefined for alert('location01lat.a);

    Correct, location01lat.a is defined within geocoder.geocode not the scope where the alert() is located.

    Saturday, January 18, 2020 1:53 PM
  • User-418973555 posted

    aint alert(location01lat.a) outside the scope has carried the value while defined inside location01lat.a = a; 

     geocoder.geocode({ 'address': document.getElementById('<%= txtlocation01.ClientID %>').value + ", my" }, function (results, status) {
    
                    if (status == google.maps.GeocoderStatus.OK) {
                        //document.getElementById('dvDistance').innerHTML = "location1: " + results[0].geometry.location.lat() + ", " + results[0].geometry.location.lng();
                        //location01lat = results[0].geometry.location.lat();
                        let a = results[0].geometry.location.lat();
                        let b = results[0].geometry.location.lng();
                        //location01lng = results[0].geometry.location.lng();
                        //location011 = { lat: location01lat, lng: location01lng };                 
                        location01lat.a = a;
                        location01lng.b = b;
                    } else {
                        alert("Something got wrong " + status);
                    }
    
                });
    
                geocoder.geocode({ 'address': document.getElementById('<%= txtlocation02.ClientID %>').value + ", my" }, function (results2, status) {
    
                    if (status == google.maps.GeocoderStatus.OK) {
                        //document.getElementById('dvDistance').innerHTML += " ; location2: " + results2[0].geometry.location.lat() + ", " + results2[0].geometry.location.lng();
                        let c = results2[0].geometry.location.lat();
                        let d = results2[0].geometry.location.lng();
    
                        //location02lat = results2[0].geometry.location.lat();
                        //location02lng = results2[0].geometry.location.lng();
    
                        location02lat.c = c;
                        location02lng.d = d;
    
                        //location022 = { lat: location02lat, lng: location02lng };
    
                        //alert("location : " + results[0].geometry.location.lat() + " " +results[0].geometry.location.lng()); 
                    } else {
                        alert("Something got wrong " + status);
                    }
    
                });
    
    
                alert(location01lat.a);
                const location011 = { lat: location01lat.a, lng: location01lng.b };
                const location022 = { lat: location02lat.c, lng: location02lng.d };
    
    
                var mk1 = new google.maps.Marker({ , map: map });
                var mk2 = new google.maps.Marker({ , map: map });

    Saturday, January 18, 2020 2:08 PM
  • User475983607 posted

    My fault for making an assumption.  It's always helpful to see all the code.   

    The problem with this design is JavaScript events are asynchronous.  There's no set order.   You can't just drop a variable in global scope and expect the value to be available when your code read the variable.  You use handler or a promise to know when the variable has been set.

    Saturday, January 18, 2020 2:24 PM
  • User-719153870 posted

    Hi larnvok09,

    I created a demo and reproduced the problem:

    <html xmlns="http://www.w3.org/1999/xhtml">
    <head runat="server">
        <title></title>
        <script src="https://maps.googleapis.com/maps/api/js?key=myapikey&callback=initMap"></script>
        <script>
            var geocoder;
            var map;
            function initialize() {
                geocoder = new google.maps.Geocoder();
                var latlng = new google.maps.LatLng(-34.397, 150.644);
                var mapOptions = {
                    zoom: 8,
                    center: latlng
                }
                map = new google.maps.Map(document.getElementById('map'), mapOptions);
            }
    
            function CalculateDistance() {
    
                var geocoder = new google.maps.Geocoder();
                var location01lat = {};
                location01lat.a;
                var location01lng;
                const center = { lat: 40.774102, lng: -73.971734 };
                const options = { zoom: 15, scaleControl: true, center: center };
                map = new google.maps.Map(
                    document.getElementById('map'), options);
    
                geocoder.geocode({ 'address':'Sydney, NSW' }, function (results, status) {
    
                    if (status == google.maps.GeocoderStatus.OK) {
                        let a = results[0].geometry.location.lat();
                        let b = results[0].geometry.location.lng();                 
                        location01lat.a = a;
                        location01lng.b = b;
                    } else {
                        alert("Something got wrong " + status+location01lat.a);
                    }
    
                });
                alert(location01lat.a);
            }
        </script>
    </head>
    <body onload="initialize()">
        <form id="form1" runat="server">
            <div>
                <div id="map" style="width: 320px; height: 480px;"></div>
                <input type="button" onclick="CalculateDistance()" id="cal" value="Calculate"/>
            </div>
        </form>
    </body>
    </html>

    I was debugging the code using Chrome devtools and found the highlighted part was never fired, the if statement never got touched.

    Meanwhile, an error message was thrown in the console:

    This means that you have not enabled the Geocoding Service for my project, you can follow this thread to enable it. (However, it looks like it's charged? I'm not sure.)

    Please check if you met the same situation as i mentioned above and try enable the service if it is.

    Best Regard,

    Yang Shen

    Sunday, January 19, 2020 3:20 AM
  • User-418973555 posted

    got it worked by setting those variables into hiddenfields, but one thing is that the form did a postback once and show "Distance between markers NaN km"

    , then only show the successful result the second time button clicked,

            var map;
            function initMap() {
                // The map, centered on Central Park
    
                 const center = { lat: 40.774102, lng: -73.971734 };
                    const options = { zoom: 15, scaleControl: true, center: center };
                    map = new google.maps.Map(
                        document.getElementById('dvMap'), options);
    
           }
    
    
            function CalculateDistance() {
    
                var geocoder = new google.maps.Geocoder();
                var location01lat = {};
                location01lat.a;
                //var location01lat;
                var location01lng = {};
                location01lng.b;
            
                var location02lat = {};
                location02lat.c;
    
                var location02lng = {};
                location02lng.d;
               
                geocoder.geocode({ 'address': document.getElementById('<%= txtlocation01.ClientID %>').value + ", my" }, function (results, status) {
    
                    if (status == google.maps.GeocoderStatus.OK) {
                      
                        document.getElementById('<%= hf01.ClientID %>').value = results[0].geometry.location.lat();
                        document.getElementById('<%= hf02.ClientID %>').value = results[0].geometry.location.lng();
                       
                    } else {
                        alert("Something got wrong " + status);
                    }
    
                });
    
                geocoder.geocode({ 'address': document.getElementById('<%= txtlocation02.ClientID %>').value + ", my" }, function (results2, status) {
    
                    if (status == google.maps.GeocoderStatus.OK) {
                       
                        document.getElementById('<%= hf03.ClientID %>').value = results2[0].geometry.location.lat();
                        document.getElementById('<%= hf04.ClientID %>').value = results2[0].geometry.location.lng();
    
                    } else {
                        alert("Something got wrong " + status);
                    }
    
                });
                      
                const location011 = { lat: parseFloat(document.getElementById('<%= hf01.ClientID %>').value), lng:  parseFloat(document.getElementById('<%= hf02.ClientID %>').value) };
                const location022 = { lat:  parseFloat(document.getElementById('<%= hf03.ClientID %>').value), lng: parseFloat(document.getElementById('<%= hf04.ClientID %>').value) };
    
                var mk1 = new google.maps.Marker({ , map: map });
                var mk2 = new google.maps.Marker({ , map: map });
    
                function haversine_distance(mk1, mk2) {
                    //var R = 3958.8; // Radius of the Earth in miles
                    var R = 6371; // Radius of the Earth in kms
                    var rlat1 = mk1.position.lat() * (Math.PI / 180); // Convert degrees to radians
                    var rlat2 = mk2.position.lat() * (Math.PI / 180); // Convert degrees to radians
                    var difflat = rlat2 - rlat1; // Radian difference (latitudes)
                    var difflon = (mk2.position.lng() - mk1.position.lng()) * (Math.PI / 180); // Radian difference (longitudes)
    
                    var d = 2 * R * Math.asin(Math.sqrt(Math.sin(difflat / 2) * Math.sin(difflat / 2) + Math.cos(rlat1) * Math.cos(rlat2) * Math.sin(difflon / 2) * Math.sin(difflon / 2)));
                    return d;
                }
    
                var distance = haversine_distance(mk1, mk2);
                document.getElementById('dvDistance2').innerHTML = "Distance between markers: " + parseFloat(distance.toFixed(2)) + " km";
    
                return false;
    
            }


    aspx
    <input id="btncalculate" type="button" value="calculate" onclick="CalculateDistance(); return false;" />

    Sunday, January 19, 2020 5:22 PM
  • User-474980206 posted

    As stated you are trying to use async values before they are set. Please read about async processing. 

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Sunday, January 19, 2020 8:37 PM
  • User-418973555 posted

    got it,

       function FindLatLong1(address1, address2, callback) {
                var geocoder = new google.maps.Geocoder();
    
                geocoder.geocode({ 'address': address1 }, function (results, status1) {
                    if (status1 == google.maps.GeocoderStatus.OK) {
                        document.getElementById('<%= hf01.ClientID %>').value = results[0].geometry.location.lat();
                        document.getElementById('<%= hf02.ClientID %>').value = results[0].geometry.location.lng();
    
                        callback({
                            status1: "OK", Latitude: document.getElementById('<%= hf01.ClientID %>').value = results[0].geometry.location.lat(), Longitude: document.getElementById('<%= hf02.ClientID %>').value = results[0].geometry.location.lng()
                            
                            
    
    
                        });
                    }
                });
    
                geocoder.geocode({ 'address': address2 }, function (results1, status2) {
                    if (status2 == google.maps.GeocoderStatus.OK) {
                        document.getElementById('<%= hf03.ClientID %>').value = results1[0].geometry.location.lat();
                        document.getElementById('<%= hf04.ClientID %>').value = results1[0].geometry.location.lng();
    
                        callback({
    
                            status2: "OK", Latitude: document.getElementById('<%= hf03.ClientID %>').value = results1[0].geometry.location.lat(), Longitude: document.getElementById('<%= hf04.ClientID %>').value = results1[0].geometry.location.lng(),
    
    
                        });
                    }
    
                });
    
            }
    
    
            function CalculateDistance() {
    
                const center = { lat: 40.774102, lng: -73.971734 };
                const options = { zoom: 15, scaleControl: true, center: center };
                map = new google.maps.Map(
                        document.getElementById('dvMap'), options);
    
                var geocoder = new google.maps.Geocoder();
                var location01lat = {};
                location01lat.a;
                //var location01lat;
                var location01lng = {};
                location01lng.b;
            
                var location02lat = {};
                location02lat.c;
    
                var location02lng = {};
                location02lng.d;
    
               FindLatLong1(document.getElementById('<%= txtlocation01.ClientID %>').value + ", my", document.getElementById('<%= txtlocation02.ClientID %>').value + ", my" , function (data) {
    
                  const location011 = { lat: parseFloat(document.getElementById('<%= hf01.ClientID %>').value), lng: parseFloat(document.getElementById('<%= hf02.ClientID %>').value) };
                const location022 = { lat: parseFloat(document.getElementById('<%= hf03.ClientID %>').value), lng: parseFloat(document.getElementById('<%= hf04.ClientID %>').value) };
    
                var mk1 = new google.maps.Marker({ , map: map });
                var mk2 = new google.maps.Marker({ , map: map });
    
                function haversine_distance(mk1, mk2) {
                    //var R = 3958.8; // Radius of the Earth in miles
                    var R = 6371; // Radius of the Earth in kms
                    var rlat1 = mk1.position.lat() * (Math.PI / 180); // Convert degrees to radians
                    var rlat2 = mk2.position.lat() * (Math.PI / 180); // Convert degrees to radians
                    var difflat = rlat2 - rlat1; // Radian difference (latitudes)
                    var difflon = (mk2.position.lng() - mk1.position.lng()) * (Math.PI / 180); // Radian difference (longitudes)
    
                    var d = 2 * R * Math.asin(Math.sqrt(Math.sin(difflat / 2) * Math.sin(difflat / 2) + Math.cos(rlat1) * Math.cos(rlat2) * Math.sin(difflon / 2) * Math.sin(difflon / 2)));
                    return d;
                }
    
                var distance = haversine_distance(mk1, mk2);
                document.getElementById('dvDistance2').innerHTML = "Distance between markers: " + parseFloat(distance.toFixed(2)) + " km";
    
            
                });
    
            }

    Monday, January 20, 2020 12:11 AM