pricing longitude latitude google error javascript google-maps coordinates google-static-maps

javascript - longitude - Convierte long/lat a pixel x/y en una imagen dada



google maps static pricing (10)

Entonces, ¿desea tomar coordenadas de latitud / longitud y averiguar las coordenadas de píxeles en su imagen de esa ubicación?

La clase principal de GMap2 proporciona transformación desde / hacia un píxel en el mapa mostrado y una coordenada lat / long:

Gmap2.fromLatLngToContainerPixel(latlng)

Por ejemplo:

var gmap2 = new GMap2(document.getElementById("map_canvas")); var geocoder = new GClientGeocoder(); geocoder.getLatLng( "1600 Pennsylvania Avenue NW Washington, D.C. 20500", function( latlng ) { var pixel_coords = gmap2.fromLatLngToContainerPixel(latlng); window.alert( "The White House is at pixel coordinates (" + pixel_coodrs.x + ", " + pixel_coords.y + ") on the " + "map image shown on this page." ); } );

Entonces, suponiendo que la imagen de su mapa es una captura de pantalla de la pantalla de Google Map, esto le dará la coordenada de píxel correcta en esa imagen de una coordenada lat / long.

Las cosas son más complicadas si tomas imágenes de mosaico y las unes tú mismo, ya que el área del conjunto de mosaicos completo quedará fuera del área del mapa que se muestra.

En este caso, tendrá que usar los valores superior e izquierdo del mosaico de la imagen superior izquierda como un desplazamiento de las coordenadas que le da deLatLngToContainerPixel (latlng: GLatLng), restando la coordenada izquierda de la coordenada x y la parte superior del y coordinar Entonces, si la imagen superior izquierda está en (-50, -122) (izquierda, arriba), y deLatLngToContainerPixel () indica que lat / long está en la coordenada de píxel (150, 320), entonces en la imagen cosida desde fichas, la posición verdadera de la coordenada está en (150 - (-50), 320 - (-122)) que es (200, 442).

También es posible que una función de traducción de coordenadas GMap2 similar:

GMap2.fromLatLngToDivPixel(latlng:GLatLng)

le dará la traducción correcta de lat / largo a píxel para el caso de los mosaicos cosidos; no he probado esto, ni está 100% claro de los documentos de API.

Consulte aquí para obtener más información: http://code.google.com/apis/maps/documentation/reference.html#GMap2.Methods.Coordinate-Transformations

Tengo un mapa de la ciudad de Moscú. Modificamos una imagen de Google Maps con algunos elementos artísticos, pero la relación entre las coordenadas GPS y los píxeles sigue siendo la misma.

Problema: ¿Cómo convierto las coordenadas GPS de varios puntos de datos que tenemos en coordenadas de píxeles en la imagen?

Idealmente, puedo hacer esto en Javascript, pero PHP estaría bien.

Sé que en escalas pequeñas (por ejemplo, en escalas de ciudades) es simplemente suficiente (es necesario saber qué coordenadas geográficas tiene una de las esquinas de las imágenes, luego aprender el "precio" de un píxel en coordenadas geográficas en una imagen en los ejes OX y OY por separado).

Pero en las escalas grandes (escala de país) el "precio" de un píxel no será constante, y variará lo suficientemente fuerte y no se podrá aplicar el método descrito anteriormente.

¿Cómo resolver un problema en escalas de país?

Actualizar:

No uso API Google Maps, solo tengo: coordenadas geográficas del objeto (son de Google Maps), todavía tengo en mi sitio una imagen simple *. GIF, en el que debo dibujar un punto correspondientes coordenadas geográficas.


La clave de todo esto es comprender las proyecciones de los mapas . Como han señalado otros, la causa de la distorsión es el hecho de que la Tierra esférica (o más exactamente elipsoidal) se proyecta sobre un plano.

Para lograr su objetivo, primero debe saber dos cosas sobre sus datos:

  1. La proyección en la que se encuentran sus mapas. Si se derivan exclusivamente de Google Maps , es probable que utilicen una proyección esférica de Mercator .
  2. El sistema de coordenadas geográficas que usa las coordenadas de latitud / longitud. Esto puede variar, porque hay diferentes formas de ubicar lat / longs en el globo. El GCS más común, utilizado en la mayoría de las aplicaciones de mapeo web y para GPS, es WGS84 .

Supongo que tus datos están en estos sistemas de coordenadas.

La proyección esférica de Mercator define un par de coordenadas en metros, para la superficie de la tierra. Esto significa que, para cada coordenada lat / long, hay una coordenada de metro / metro correspondiente. Esto le permite hacer la conversión usando el siguiente procedimiento:

  1. Encuentra el latitud / longitud WGS84 de las esquinas de la imagen.
  2. Convierta los lat / long de WGS a la proyección esférica de Mercator. Hay herramientas de conversión, mi favorito es usar la herramienta cs2cs que es parte del proyecto PROJ4 .
  3. Puede realizar de forma segura una transformación lineal simple para convertir puntos en la imagen y puntos en la tierra en la proyección esférica de Mercator, y viceversa.

Para pasar de un punto WGS84 a un píxel en la imagen, el procedimiento ahora es:

  1. Proyecto lat / lon a Mercator esférico. Esto se puede hacer usando la biblioteca proj4js.
  2. Transformar las coordenadas esféricas de Mercator en coordenadas de píxel de imagen utilizando la relación lineal descubierta anteriormente.

Puede usar la biblioteca proj4js así:

// include the library <script src="lib/proj4js-combined.js"></script> //adjust the path for your server //or else use the compressed version // creating source and destination Proj4js objects // once initialized, these may be re-used as often as needed var source = new Proj4js.Proj(''EPSG:4326''); //source coordinates will be in Longitude/Latitude, WGS84 var dest = new Proj4js.Proj(''EPSG:3785''); //destination coordinates in meters, global spherical mercators projection, see http://spatialreference.org/ref/epsg/3785/ // transforming point coordinates var p = new Proj4js.Point(-76.0,45.0); //any object will do as long as it has ''x'' and ''y'' properties Proj4js.transform(source, dest, p); //do the transformation. x and y are modified in place //p.x and p.y are now EPSG:3785 in meters


La traducción que está abordando tiene que ver con Proyección de mapas , que es cómo la superficie esférica de nuestro mundo se traduce en una representación bidimensional. Hay múltiples formas (proyecciones) para renderizar el mundo en una superficie 2D.

Si sus mapas están usando solo una proyección específica ( Mercator es popular), debería poder encontrar las ecuaciones, algunos ejemplos de código y / o alguna biblioteca (por ejemplo, una solución de Mercator - Conversión de Lat / Longs en coordenadas X / Y Si eso no funciona, estoy seguro de que puede encontrar otros ejemplos: https://.com/search?q=mercator . Si sus imágenes no son mapas utilizando una proyección de Mercator, usted '' Necesitaré determinar qué proyección utiliza para encontrar las ecuaciones de traducción correctas.

Si intenta soportar múltiples proyecciones de mapas (desea admitir muchos mapas diferentes que usan proyecciones diferentes), entonces definitivamente quiere usar una biblioteca como PROJ.4 , pero nuevamente no estoy seguro de lo que encontrará para Javascript o PHP.


Luchado con esto: tener ambos mapas de la calle abierta y Google Street Map y quería proyectar una imagen gráfica externa

var map = new OpenLayers.Map({ div:"map-id", allOverlays: true }); var osm = new OpenLayers.Layer.OSM("OpenStreeMao"); var gmap = new OpenLayers.Layer.Google("Google Streets", {visibility: false}); map.addLayers([osm,gmap]); var vectorLayer = new OpenLayers.Layer.Vector("IconLayer"); var lonlatObject = new OpenLayers.LonLat(24.938622,60.170421).transform( new OpenLayers.Projection("EPSG:4326"), map.getProjectionObject() ); console.log(lonlatObject); var point = new OpenLayers.Geometry.Point(lonlatObject.lon, lonlatObject.lat); console.log(point); var point2 = new OpenLayers.Geometry.Point(lonlatObject.x, lonlatObject.y); console.log(point2); var feature = new OpenLayers.Feature.Vector(point, null, { externalGraphic: "http://cdn1.iconfinder.com/data/icons/SUPERVISTA/networking/png/72/antenna.png", graphicWidth: 72, graphicHeight: 72, fillOpacity: 1 }); vectorLayer.addFeatures(feature); map.addLayer(vectorLayer); map.setCenter( new OpenLayers.LonLat(24.938622,60.170421).transform( new OpenLayers.Projection("EPSG:4326"), map.getProjectionObject() ), 12); map.addControl(new OpenLayers.Control.LayerSwitcher());

http://jsfiddle.net/alexcpn/N9dLN/8/


Necesita fórmulas para convertir la latitud y la longitud en coordenadas rectangulares. Hay un gran número para elegir y cada uno distorsionará el mapa de una manera diferente. Wolfram MathWorld tiene una buena colección:

http://mathworld.wolfram.com/MapProjection.html

Siga los enlaces "Ver también".




Tendrá que implementar la proyección API de Google Maps en su idioma. Tengo el código fuente de C # para esto:

public class GoogleMapsAPIProjection { private readonly double PixelTileSize = 256d; private readonly double DegreesToRadiansRatio = 180d / Math.PI; private readonly double RadiansToDegreesRatio = Math.PI / 180d; private readonly PointF PixelGlobeCenter; private readonly double XPixelsToDegreesRatio; private readonly double YPixelsToRadiansRatio; public GoogleMapsAPIProjection(double zoomLevel) { var pixelGlobeSize = this.PixelTileSize * Math.Pow(2d, zoomLevel); this.XPixelsToDegreesRatio = pixelGlobeSize / 360d; this.YPixelsToRadiansRatio = pixelGlobeSize / (2d * Math.PI); var halfPixelGlobeSize = Convert.ToSingle(pixelGlobeSize / 2d); this.PixelGlobeCenter = new PointF( halfPixelGlobeSize, halfPixelGlobeSize); } public PointF FromCoordinatesToPixel(PointF coordinates) { var x = Math.Round(this.PixelGlobeCenter.X + (coordinates.X * this.XPixelsToDegreesRatio)); var f = Math.Min( Math.Max( Math.Sin(coordinates.Y * RadiansToDegreesRatio), -0.9999d), 0.9999d); var y = Math.Round(this.PixelGlobeCenter.Y + .5d * Math.Log((1d + f) / (1d - f)) * -this.YPixelsToRadiansRatio); return new PointF(Convert.ToSingle(x), Convert.ToSingle(y)); } public PointF FromPixelToCoordinates(PointF pixel) { var longitude = (pixel.X - this.PixelGlobeCenter.X) / this.XPixelsToDegreesRatio; var latitude = (2 * Math.Atan(Math.Exp( (pixel.Y - this.PixelGlobeCenter.Y) / -this.YPixelsToRadiansRatio)) - Math.PI / 2) * DegreesToRadiansRatio; return new PointF( Convert.ToSingle(latitude), Convert.ToSingle(longitude)); } }

Fuente:

http://code.google.com/p/geographical-dot-net/source/browse/trunk/GeographicalDotNet/GeographicalDotNet/Projection/GoogleMapsAPIProjection.cs


Una de las cosas importantes a tener en cuenta es el nivel de "zoom" de su proyección (para Google Maps en particular).

Como lo explica Google:

En el nivel de zoom 1, el mapa consta de 4 mosaicos de 256x256 píxeles, lo que da como resultado un espacio de píxeles de 512x512. En el nivel de zoom 19, se puede hacer referencia a cada píxel xey del mapa utilizando un valor entre 0 y 256 * 2 ^ 19

(Consulte https://developers.google.com/maps/documentation/javascript/maptypes?hl=en#MapCoordinates )

Para tener en cuenta el valor de "zoom", recomiendo las funciones simples y efectivas deltaLonPerDeltaX y deltaLatPerDeltaY a continuación. Si bien los píxeles-x y las longitudes son estrictamente proporcionales, este no es el caso para los píxeles yy las latitudes, para los cuales la fórmula requiere la latitud inicial.

// Adapted from : http://blog.cppse.nl/x-y-to-lat-lon-for-google-maps window.geo = { glOffset: Math.pow(2,28), //268435456, glRadius: Math.pow(2,28) / Math.PI, a: Math.pow(2,28), b: 85445659.4471, c: 0.017453292519943, d: 0.0000006705522537, e: Math.E, //2.7182818284590452353602875, p: Math.PI / 180, lonToX: function(lon) { return Math.round(this.glOffset + this.glRadius * lon * this.p); }, XtoLon: function(x) { return -180 + this.d * x; }, latToY: function(lat) { return Math.round(this.glOffset - this.glRadius * Math.log((1 + Math.sin(lat * this.p)) / (1 - Math.sin(lat * this.p))) / 2); }, YtoLat: function(y) { return Math.asin(Math.pow(this.e,(2*this.a/this.b - 2*y/this.b)) / (Math.pow(this.e, (2*this.a/this.b - 2*y/this.b))+1) - 1/(Math.pow(this.e, (2*this.a/this.b - 2*y/this.b))+1) ) / this.c; }, deltaLonPerDeltaX: function(deltaX, zoom) { // 2^(7+zoom) pixels <---> 180 degrees return deltaX * 180 / Math.pow(2, 7+zoom); }, deltaLatPerDeltaY: function(deltaY, zoom, startLat) { // more complex because of the curvature, we calculte it by difference var startY = this.latToY(startLat), endY = startY + deltaY * Math.pow(2, 28-7-zoom), endLat = this.YtoLat(endY); return ( endLat - startLat ); // = deltaLat } }


mi enfoque funciona sin una biblioteca y con mapas recortados. Significa que funciona solo con partes de una imagen de Mercator. Tal vez ayuda a alguien: https://.com/a/10401734/730823