Search code examples
google-mapsmathgoogle-maps-api-3latitude-longitudegmsgroundoverlay

How do I get the latitude and longitude of a rectangle if I know the center and top left GPS positions?


Background:

I'm trying to use a Google maps ground overlay but we are missing GPS positions.

We have a map to overlay that was drawn over a Google Maps screenshot. From this screenshot we recorded the Top Left and Center Center position.

We require the bottom right position to accurately overlay these images. See below:

Top Left positions and center positions GPS known

The intial thinking is finding the difference between the two points and adding that onto the center point.

Attempted logic:

In JavaScript:

var topLeft      = [-32.8830055, 151.686214];
var centerCenter = [-32.9293803, 151.756686];

var difference1 = centerCenter[0] - ( (topLeft[0] - centerCenter[0] ) ) ;
var difference2 = centerCenter[1] - ( (topLeft[1] - centerCenter[1] ) ) ;

// being bottom right this should be "bigger" than above values
// outputs [-32.97575509999999, 151.827158];
var bottomRight  = [difference1 , difference2];

Problem:

However it appears this is where the curve of the earth throws that simple maths out the door. I'm guessing that what is happening below is why.

The image overlay is flat while the GPS system is curved.

So given I have a rectangle overlay and I know the top left point and the center point can I work out the latitude and longitude of the bottom right point I.e X in the above diagram. Note I do not know the real world distances of this rectangle.

Note: I also know that I will have to change these to NW / SE to use ground overlays.


Solution

  • Approach(using the geometry-library):

    1. calculate the heading from northwest to center

      google.maps.geometry.spherical.computeHeading(northwest, center);
      
    2. calculate the distance from northwest to center

      google.maps.geometry.spherical.computeDistanceBetween(northwest, center);
      
    3. calculate southeast by using

      google.maps.geometry.spherical.computeOffset(center,
                                                   calculatedDistance,
                                                   calculatedHeading);
      

    function initialize() {
    
      var nw = new google.maps.LatLng(62.400471, -150.287132),
        center = new google.maps.LatLng(62.341145, -150.14637),
        map = new google.maps.Map(document.getElementById('map_canvas'), {
          zoom: 9,
          center: center
        }),
        heading, distance, se;
    
      heading = google.maps.geometry.spherical.computeHeading(nw, center);
      distance = google.maps.geometry.spherical.computeDistanceBetween(nw, center);
      se = google.maps.geometry.spherical.computeOffset(center, distance, heading);
    
      new google.maps.Marker({
        map: map,
        position: center
      });
      new google.maps.Marker({
        map: map,
        position: nw
      });
      new google.maps.Marker({
        map: map,
        position: se
      });
    
      new google.maps.GroundOverlay(
        'https://developers.google.com/maps/documentation/' +
        'javascript/examples/full/images/talkeetna.png', {
          north: nw.lat(),
          south: se.lat(),
          west: nw.lng(),
          east: se.lng()
        }, {
          map: map
        });
    
    
    }
    
    google.maps.event.addDomListener(window, 'load', initialize);
    html,
    body,
    #map_canvas {
      height: 100%;
      margin: 0;
      padding: 0;
    }
    <div id="map_canvas"></div>
    <script src="https://maps.googleapis.com/maps/api/js?v=3&libraries=geometry"></script>