5

I'm building a polygon in Google Maps through markers that can be dragged to reshape it. So, when there are 3 markers, the polygon is drawn, and further markers are appended in the shape, expanding it. That's fine when the user just want to follow a simple clockwise/counterclockwise pattern, but when he wants to expand the polygon through one of its edges, instead it will append the marker, twisting itself.

Normal appending marker

Here in this example, if we add markers 1, 2 and 3, it will be drawn a simple triangle. But if marker 4 is added, the polygon just twists itself.

Instead, I want when 4 is added, it's inserted between markers 1 and 2, like this image:

Wanted appending marker

Basically, in the polygon's vertex array, instead of:

[
    //marker 1 position,
    //marker 2 position,
    //marker 3 position,
    //current marker 4 position
]

I want to have:

[
    //marker 1 position,
    //desired marker 4 position
    //marker 2 position,
    //marker 3 position
]

So the polygon will expand instead of twist itself.

Is there a way to achieve this? Or I just will have to tell the user to build his polygon clock/counterclockwise?

TylerH
  • 20,799
  • 66
  • 75
  • 101
Roberto Maldonado
  • 1,585
  • 14
  • 27
  • 1
    Is there any reason why you didn't use the drawing-library? – Dr.Molle Jun 04 '14 at 21:50
  • [similar question: How to sort points in a Google maps polygon so that lines do not cross?](http://stackoverflow.com/questions/2374708/how-to-sort-points-in-a-google-maps-polygon-so-that-lines-do-not-cross) – geocodezip Jun 05 '14 at 14:08
  • possible duplicate of [Sort latitude and longitude coordinates into clockwise ordered quadrilateral](http://stackoverflow.com/questions/2855189/sort-latitude-and-longitude-coordinates-into-clockwise-ordered-quadrilateral) – geocodezip Jun 05 '14 at 14:10
  • @Dr.Molle well, didn't know that library until you mentioned it. – Roberto Maldonado Jun 05 '14 at 18:01

2 Answers2

6

General solution (find a center point, sort the points in order of heading from that point, using geometry library computeHeading method).

given an array gmarkers containing google.maps.Marker objects representing the vertices of the polygon:

function sortPoints2Polygon() {
      if (polyline) polyline.setMap(null);
      points = [];
      var bounds = new google.maps.LatLngBounds(); 
      for (var i=0; i < gmarkers.length; i++) {
        points.push(gmarkers[i].getPosition());
    bounds.extend(gmarkers[i].getPosition());
      }
      var center = bounds.getCenter();
      var bearing = [];
      for (var i=0; i < points.length; i++) {
        points[i].bearing = google.maps.geometry.spherical.computeHeading(center,points[i]);
      }
      points.sort(bearingsort);
      polyline = new google.maps.Polygon({
        map: map,
        paths:points, 
        fillColor:"#FF0000",
        strokeWidth:2, 
        fillOpacity:0.5, 
        strokeColor:"#0000FF",
        strokeOpacity:0.5
      });
}

function bearingsort(a,b) {
  return (a.bearing - b.bearing);
}

working example (starts with 3 random points)

geocodezip
  • 158,664
  • 13
  • 220
  • 245
0

Finally solved it via finding the nearest edge and inserting it after the first vertex and before the second one of this edge. I used the algorithm from here to use it in javascript:

Shortest distance between a point and a line segment

Community
  • 1
  • 1
Roberto Maldonado
  • 1,585
  • 14
  • 27