在Google地图中预加载可编辑的绘图管理器多边形

时间:2013-03-19 16:14:09

标签: jquery google-maps google-maps-api-3 google-maps-markers

我正在编写一个应用程序,允许用户使用Google Maps API绘制地理多边形“区域”并将其保存在数据库中。每个用户只能有一个区域,所以我通过切换到手并在overlaycomplete上隐藏绘图工具来限制它。在overlaycomplete之后,我能够点击保存并且它保存在我的数据库中就好了 - 所以这一点有效。此外,我能够从数据库中检索多边形,并在地图上将其显示为可编辑的多边形。我遇到的问题是:

  1. 当尝试拖动插入多边形的点时,它们会“卡住”鼠标并且永远不会释放。我的猜测是某种鼠标问题?

  2. 尽管已存在多边形,但我仍然能够绘制另一个多边形。如果从db?

  3. 加载多边形,我是否应该在开头隐藏绘图工具?
  4. 如何将事件附加到从数据库中提取的多边形,以便捕获其顶点坐标?

  5. 您可以在此处查看我当前的代码:http://jsfiddle.net/FUUxz/或更低:

    JS:

                var map; // Global declaration of the map
                var iw = new google.maps.InfoWindow(); // Global declaration of the infowindow
                var lat_longs = new Array();
                var markers = new Array();
                var drawingManager;
                function initialize() {
    
                     var myLatlng = new google.maps.LatLng(40.9403762, -74.1318096);
                    var myOptions = {
                        zoom: 13,
                        center: myLatlng,
                        mapTypeId: google.maps.MapTypeId.ROADMAP}
                    map = new google.maps.Map(document.getElementById("map_canvas"), myOptions);
                    drawingManager = new google.maps.drawing.DrawingManager({
                    drawingMode: google.maps.drawing.OverlayType.POLYGON,
                    drawingControl: true,
                    drawingControlOptions: {
                        position: google.maps.ControlPosition.TOP_CENTER,
                        drawingModes: [google.maps.drawing.OverlayType.POLYGON]
                    },
                            polygonOptions: {editable:true,fillColor:'#ff0000',strokeColor:'#ff0000',strokeWeight:2}
                });
                drawingManager.setMap(map);
    
                google.maps.event.addListener(drawingManager, "overlaycomplete", function(event) {
                    var newShape = event.overlay;
                    newShape.type = event.type;
                    if (event.type==google.maps.drawing.OverlayType.POLYGON) {
                            overlayClickListener(event.overlay);$('#polygon').val(event.overlay.getPath().getArray());drawingManager.setOptions({drawingMode:null,drawingControl:false});
                        }
    
                });
                    var polygon_plan_0 = [
                        new google.maps.LatLng(40.9534555976547, -74.0871620178223)
                        ,
                        new google.maps.LatLng(40.9410084152192, -74.0948867797852)
                        ,
                        new google.maps.LatLng(40.9411380854622, -74.1165161132812)
                        ,
                        new google.maps.LatLng(40.9490474888751, -74.1221809387207)
                        ,
                        new google.maps.LatLng(40.955140973234, -74.124584197998)
                        ,
                        new google.maps.LatLng(40.9604561066844, -74.1153144836426)
                        ,
                        new google.maps.LatLng(40.9534555976547, -74.0871620178223)
                        ];
                        lat_longs.push(new google.maps.LatLng(40.9534555976547, -74.0871620178223));
    
                        lat_longs.push(new google.maps.LatLng(40.9410084152192, -74.0948867797852));
    
                        lat_longs.push(new google.maps.LatLng(40.9411380854622, -74.1165161132812));
    
                        lat_longs.push(new google.maps.LatLng(40.9490474888751, -74.1221809387207));
    
                        lat_longs.push(new google.maps.LatLng(40.955140973234, -74.124584197998));
    
                        lat_longs.push(new google.maps.LatLng(40.9604561066844, -74.1153144836426));
    
                        lat_longs.push(new google.maps.LatLng(40.9534555976547, -74.0871620178223));
    
                var polygon_0 = new google.maps.Polygon({
                    path: polygon_plan_0,
    
                    strokeColor: "#ff0000",
                    strokeOpacity: 0.8,
                    strokeWeight: 2,
                    fillColor: "#ff0000",
                    fillOpacity: 0.3,
                    editable: true
                });
    
                polygon_0.setMap(map);
    
    
                google.maps.event.addListener(polygon_0, "mouseup", function(event) {
                    overlayClickListener(event.overlay);$('#polygon').val(event.overlay.getPath().getArray());drawingManager.setOptions({drawingMode:null,drawingControl:false});
                });
    
    
                }
    
    
            function createMarker(markerOptions) {
                var marker = new google.maps.Marker(markerOptions);
                markers.push(marker);
                lat_longs.push(marker.getPosition());
                return marker;
            }
    
    initialize();
    
    function overlayClickListener(overlay) {
        google.maps.event.addListener(overlay, "mouseup", function(event){
            $('#polygon').val(overlay.getPath().getArray());
        });
    }
    

    HTML:

    <div id="map_canvas" style="width:100%; height:450px;"></div>
    <form action="http://garbagedayreminder.com/test/save" method="post" accept-charset="utf-8" id="map_form">
    <input type="text" name="polygon" value="" id="polygon"  />
    <input type="submit" name="save" value="Save!" id="save"  />
    </form>
    

1 个答案:

答案 0 :(得分:8)

我知道这有点老了,但我一直在研究类似的情况。从数据库加载多边形,允许它们可编辑,并允许将其他多边形添加到地图中。可能有更好的方法来做到这一点,但这是有用的,希望能让其他人走上正轨。

      var areas = ( <?php echo json_encode($areas);?> );
  var coords = ( <?php echo json_encode($coords);?> );

  var drawingManager;
  var selectedShape;
  var colors = ['#1E90FF', '#FF1493', '#32CD32', '#FF8C00', '#4B0082'];
  var selectedColor;
  var colorButtons = {};

  // Saving vars
  var selectedShape;
  var contentString;
  var polygons = [];
  var newPolys = [];

  function clearSelection() {
    if (selectedShape) {
      selectedShape.setEditable(false);
      selectedShape = null;
    }
  }

  function setSelection(shape) {
    clearSelection();
    selectedShape = shape;
    shape.setEditable(true);
    selectColor(shape.get('fillColor') || shape.get('strokeColor'));
  }

  function deleteSelectedShape(e) {
    if (selectedShape) {
      selectedShape.setMap(null);
      for (i=0; i < polygons.length; i++) {   // Clear out the polygons entry
        if (selectedShape.getPath == polygons[i].getPath) {
            polygons.splice(i, 1);
        }
      }
    }
  }

  function selectColor(color) {
    selectedColor = color;
    for (var i = 0; i < colors.length; ++i) {
      var currColor = colors[i];
      colorButtons[currColor].style.border = currColor == color ? '2px solid #789' : '2px solid #fff';
    }

    // Retrieves the current options from the drawing manager and replaces the
    // stroke or fill color as appropriate.
    var polylineOptions = drawingManager.get('polylineOptions');
    polylineOptions.strokeColor = color;
    drawingManager.set('polylineOptions', polylineOptions);

    var rectangleOptions = drawingManager.get('rectangleOptions');
    rectangleOptions.fillColor = color;
    drawingManager.set('rectangleOptions', rectangleOptions);

    var circleOptions = drawingManager.get('circleOptions');
    circleOptions.fillColor = color;
    drawingManager.set('circleOptions', circleOptions);

    var polygonOptions = drawingManager.get('polygonOptions');
    polygonOptions.fillColor = color;
    drawingManager.set('polygonOptions', polygonOptions);
  }

  function setSelectedShapeColor(color) {
    if (selectedShape) {
      if (selectedShape.type == google.maps.drawing.OverlayType.POLYLINE) {
        selectedShape.set('strokeColor', color);
      } else {
        selectedShape.set('fillColor', color);
      }
    }
  }

  function makeColorButton(color) {
    var button = document.createElement('span');
    button.className = 'color-button';
    button.style.backgroundColor = color;
    google.maps.event.addDomListener(button, 'click', function() {
      selectColor(color);
      setSelectedShapeColor(color);
    });

    return button;
  }

   function buildColorPalette() {
     var colorPalette = document.getElementById('color-palette');
     for (var i = 0; i < colors.length; ++i) {
       var currColor = colors[i];
       var colorButton = makeColorButton(currColor);
       colorPalette.appendChild(colorButton);
       colorButtons[currColor] = colorButton;
     }
     selectColor(colors[0]);
   }

  function initialize() {
      var map = new google.maps.Map(document.getElementById('map'), {
      zoom: 7,
      center: new google.maps.LatLng(40.2444, -111.6608),           // Utah default coords
      mapTypeId: google.maps.MapTypeId.Terrain,
      disableDefaultUI: true,
      zoomControl: true
    });

    var polyOptions = {
      strokeWeight: 0,
      fillOpacity: 0.45,
      editable: true
    };


    // Creates a drawing manager attached to the map that allows the user to draw
    // markers, lines, and shapes.
    drawingManager = new google.maps.drawing.DrawingManager({
      drawingMode: google.maps.drawing.OverlayType.POLYGON,
      drawingControlOptions: {
        drawingModes: [google.maps.drawing.OverlayType.POLYGON]},
      markerOptions: {
        draggable: true
      },
      polylineOptions: {
        editable: true
      },
      rectangleOptions: polyOptions,
      circleOptions: polyOptions,
      polygonOptions: polyOptions,
      map: map
    });

    google.maps.event.addListener(drawingManager, 'overlaycomplete', function(e) {
        if (e.type != google.maps.drawing.OverlayType.MARKER) {
        // Switch back to non-drawing mode after drawing a shape.
        drawingManager.setDrawingMode(null);
        // Add an event listener that selects the newly-drawn shape when the user
        // mouses down on it.
        var newShape = e.overlay;
        newShape.type = e.type;
        polygons.push(newShape);

        setSelection(newShape);


        google.maps.event.addListener(newShape, 'click', function() {
          setSelection(newShape);
        });

        google.maps.event.addListener(newShape, 'mouseup', function() {
          for (i=0; i < polygons.length; i++) {   // Clear out the old polygons entry
            if (newShape.getPath == polygons[i].getPath) {
                polygons.splice(i, 1);
            }
          }
          polygons.push(newShape);
        });
      }
    });


    // Clear the current selection when the drawing mode is changed, or when the
    // map is clicked.
    google.maps.event.addListener(drawingManager, 'drawingmode_changed', clearSelection);
    google.maps.event.addListener(map, 'click', clearSelection);
    google.maps.event.addDomListener(document.getElementById('delete-button'), 'click', deleteSelectedShape);

    buildColorPalette();


   /* Load Shapes that were previously saved */
    for (var inc = 0, ii = areas.length; inc < ii; inc++) {
      var newCoords = [];
      for (var c = 0, cc = coords.length; c < cc; c++) {
          if (coords[c].polygon == areas[inc].polygon) {
            var point = coords[c];
            newCoords.push(new google.maps.LatLng(point.lat, point.lng));
          }
      }

      newPolys[inc] = new google.maps.Polygon({
        path: newCoords,
        strokeWeight: 0,
        fillColor: areas[inc].fillColor,
        fillOpacity: areas[inc].fillOpacity
      });
      newPolys[inc].setMap(map);
      polygons.push(newPolys[inc]);
      addNewPolys(newPolys[inc]);
    }


    function addNewPolys(newPoly) {
        google.maps.event.addListener(newPoly, 'click', function() {
            setSelection(newPoly);
        });
    }

  }

  google.maps.event.addDomListener(window, 'load', initialize);