2013-10-14 13 views
9

Desidero disegnare un poligono attorno a una polilinea. La polilinea nel mio caso è una direzione di Google Maps e ho bisogno di mostrare un poligono intorno alla tela di Google Maps.Come disegnare un poligono attorno a una polilinea in JavaScript?

Primo:

Per compensare io uso il Clipper libreria JavaScript. Ho la seguente polilinea (percorso): eseguo un poligono offset sotto usando Clipper:

Ho un funzionamento JS Bin example.

Il codice è:

<html> 
    <head> 
    <title>Javascript Clipper Library/Offset polyline</title> 
    <script src="clipper.js"></script> 
    <script> 
    function draw() { 
     var polygons = [[{"X":72,"Y":59.45},{"X":136,"Y":66},{"X":170,"Y":99},{"X":171,"Y":114},{"X":183,"Y":125},{"X":218,"Y":144},{"X":218,"Y":165},{"X":226,"Y":193},{"X":254,"Y":195},{"X":283,"Y":195},{"X":292,"Y":202},{"X":325,"Y":213},{"X":341,"Y":234},{"X":397,"Y":245},{"X":417,"Y":248}]]; 
     var scale = 100; 
     reverse_copy(polygons); 
     polygons = scaleup(polygons, scale); 
     var cpr = new ClipperLib.Clipper(); 
     var delta = 25; 
     var joinType = ClipperLib.JoinType.jtRound; 
     var miterLimit = 2; 
     var AutoFix = true; 
     var svg, offsetted_polygon, 
     cont = document.getElementById('svgcontainer'); 
     offsetted_polygon = cpr.OffsetPolygons(polygons, delta * scale, joinType, miterLimit, AutoFix); 
     //console.log(JSON.stringify(offsetted_polygon)); 

     // Draw red offset polygon 
     svg = '<svg style="margin-top:10px;margin-right:10px;margin-bottom:10px;background-color:#dddddd" width="540" height="340">'; 
     svg += '<path stroke="red" fill="red" stroke-width="2" stroke-opacity="0.6" fill-opacity="0.2" d="' + polys2path(offsetted_polygon, scale) + '"/>'; 

     //Draw blue polyline 
     svg += '<path stroke="blue" stroke-width="3" d="' + polys2path(polygons, scale) + '"/>'; 
     svg += '</svg>'; 

     cont.innerHTML += svg; 
    } 

    // helper function to scale up polygon coordinates 
    function scaleup(poly, scale) { 
     var i, j; 

     if (!scale) 
     scale = 1; 

     for(i = 0; i < poly.length; i++) { 
     for(j = 0; j < poly[i].length; j++) { 
      poly[i][j].X *= scale; 
      poly[i][j].Y *= scale; 
     } 
     } 

     return poly; 
    } 

    // converts polygons to SVG path string 
    function polys2path (poly, scale) { 
     var path = "", i, j; 

     if (!scale) 
     scale = 1; 

     for(i = 0; i < poly.length; i++) { 
     for(j = 0; j < poly[i].length; j++) { 
      if (!j) 
      path += "M"; 
      else 
      path += "L"; 
      path += (poly[i][j].X/scale) + ", " + (poly[i][j].Y/scale); 
     } 
     path += "Z"; 
     } 

     return path; 
    } 

    function reverse_copy(poly) { 
     // Make reverse copy of polygons = convert polyline to a 'flat' polygon ... 
     var k, klen = poly.length, len, j; 

     for (k = 0; k < klen; k++) { 
     len = poly[k].length; 
     poly[k].length = len * 2 - 2; 

     for (j = 1; j <= len - 2; j++) { 
      poly[k][len - 1 + j] = { 
      X: poly[k][len - 1 - j].X, 
      Y: poly[k][len - 1 - j].Y 
      } 
     } 
     } 
    } 
    </script> 
    </head> 
    <body onload="draw()"> 
    <h2>Javascript Clipper Library/Offset polyline</h2> 
    This page shows an example of offsetting polyline and drawing it using SVG. 
    <div id="svgcontainer"></div> 
    </body> 
</html> 

E tutto questo è buono, ma ora devo sostituire le variabili poligono con punti da Google Maps le direzioni, in modo da fare questo cambiamento:

directionsService.route(request, function(response, status) { 
    if (status == google.maps.DirectionsStatus.OK) { 
    directionsDisplay.setDirections(response); 

    function draw() { 
     var polygons = response.routes[0].overview_path; 

     //REST OF CODE 
    } 
    } 
} 

ho a JS Bin example con questo codice per compensare il poligono attorno alla polilinea.

Ma c'è qualche problema, che non riesco a regonize e non riesco a ottenere un poligono attorno direzioni.

C'è un modo per risolvere questo problema?

+0

perché - meno per questa domanda, che cosa è sbagliato? –

+0

Non sono stato io a svalutare, ma posso immaginare che fosse perché la tua domanda era troppo ampia. COSÌ. non è qui per eseguire il debug dei programmi.Hai bisogno di mostrare quali passi hai preso per risolvere il problema te stesso. Ad esempio, il primo passo sarebbe quello di riordinare il codice e sbarazzarsi degli errori javascript che vengono visualizzati nella console. Quindi puoi farlo visualizzare il percorso (senza il poligono)? Quindi prova ad aggiungere il codice poligono. –

+0

sì, provo a risolvere il mio problema con var polygon = response.routes [0] .overview_path; –

risposta

7

Questa è la soluzione di lavoro. È possibile trovare il JSTS files at coderwall.com.

var overviewPath = response.routes[0].overview_path, 
overviewPathGeo = []; 
for (var i = 0; i < overviewPath.length; i++) { 
    overviewPathGeo.push(
     [overviewPath[i].lng(), overviewPath[i].lat()] 
    ); 
} 

var distance = value/10000, // Roughly 10km 
geoInput = { 
type: "LineString", 
    coordinates: overviewPathGeo 
}; 
var geoReader = new jsts.io.GeoJSONReader(), 
    geoWriter = new jsts.io.GeoJSONWriter(); 
var geometry = geoReader.read(geoInput).buffer(distance); 
var polygon = geoWriter.write(geometry); 

var oLanLng = []; 
var oCoordinates; 
oCoordinates = polygon.coordinates[0]; 
for (i = 0; i < oCoordinates.length; i++) { 
    var oItem; 
    oItem = oCoordinates[i]; 
    oLanLng.push(new google.maps.LatLng(oItem[1], oItem[0])); 
} 

var polygone = new google.maps.Polygon({ 
    paths: oLanLng, 
    map:map 
}); 
9

La mia soluzione di lavoro: working example (in base al largo della risposta di Manolis Xountasis) e pezzi da queste domande correlati:

  1. How to calculate intersection area in Google Maps API with JSTS Library?
  2. Google Maps Polygons self intersecting detection
  • includono la JSTS library
  • aggiungere le routine di tradurre i percorsi google.maps.Polyline a JSTS oggetti:
function googleMaps2JTS(boundaries) { 
    var coordinates = []; 
    var length = 0; 
    if (boundaries && boundaries.getLength) length = boundaries.getLength(); 
    else if (boundaries && boundaries.length) length = boundaries.length; 
    for (var i = 0; i < length; i++) { 
     if (boundaries.getLength) coordinates.push(new jsts.geom.Coordinate(
     boundaries.getAt(i).lat(), boundaries.getAt(i).lng())); 
     else if (boundaries.length) coordinates.push(new jsts.geom.Coordinate(
     boundaries[i].lat(), boundaries[i].lng())); 
    } 
    return coordinates; 
}; 
  • e di nuovo a array google.maps.LatLng
var jsts2googleMaps = function (geometry) { 
    var coordArray = geometry.getCoordinates(); 
    GMcoords = []; 
    for (var i = 0; i < coordArray.length; i++) { 
    GMcoords.push(new google.maps.LatLng(coordArray[i].x, coordArray[i].y)); 
    } 
    return GMcoords; 
} 
directionsService.route(request, function (response, status) { 
    if (status == google.maps.DirectionsStatus.OK) { 
     directionsDisplay.setDirections(response); 
     var overviewPath = response.routes[0].overview_path, 
      overviewPathGeo = []; 
     for (var i = 0; i < overviewPath.length; i++) { 
      overviewPathGeo.push(
      [overviewPath[i].lng(), overviewPath[i].lat()]); 
     } 

     var distance = 10/111.12, // Roughly 10km 
      geoInput = { 
       type: "LineString", 
       coordinates: overviewPathGeo 
      }; 
     var geoInput = googleMaps2JTS(overviewPath); 
     var geometryFactory = new jsts.geom.GeometryFactory(); 
     var shell = geometryFactory.createLineString(geoInput); 
     var polygon = shell.buffer(distance); 

     var oLanLng = []; 
     var oCoordinates; 
     oCoordinates = polygon.shell.points[0]; 
     for (i = 0; i < oCoordinates.length; i++) { 
      var oItem; 
      oItem = oCoordinates[i]; 
      oLanLng.push(new google.maps.LatLng(oItem[1], oItem[0])); 
     } 
     if (routePolygon && routePolygon.setMap) routePolygon.setMap(null); 
     routePolygon = new google.maps.Polygon({ 
      paths: jsts2googleMaps(polygon), 
      map: map 
     }); 
    } 
}); 
+2

Qual è l'unità di distanza che 'shell.buffer (distanza)' si aspetta? Come viene calcolato? @geocodezip – jbgarr

+0

Sarebbe davvero bello capire come stai calcolando la distanza qui? Perché stai facendo 10/111.12? –

+0

Questo è approssimativamente 10 km (https://www.google.com/#q=km%20per%20degree%20longitude%20km) per il commento nel codice ('var distance = 10/111.12, // Roughly 10km') – geocodezip

Problemi correlati