I have noticed that, from Google Maps page, you can get an "embed" link to put inside an iframe and load the map in a browser. (no news here)
The image size can be adjusted to be very large, so I am interested in getting som big images as single .PNGs.
More specifically, I would like to define a rectangular area from a bounding box (upper-right and lower-left coordinates), and get the corresponding image, with an appropriate zoom factor.
But my question is: How can I use Python to get the "pixel content" of this map as an image object?
(My rationale is: if the browser can get and render such image content, then Python should be capable of doing it, too).
EDIT: this is the content of the HTML file that shows my sample map:
<iframe
width="2000"
height="1500"
frameborder="0"
scrolling="yes"
marginheight="0"
marginwidth="0"
src="http://maps.google.com.br/maps?hl=pt-BR&ll=-30.027489,-51.229248&spn=1.783415,2.745209&z=10&output=embed"/>
EDIT: I did as suggested by Ned Batchelder, and read the content of an urllib.urlopen()
call using the src
address taken from the iframe above. The result was a lot of javascript code, which I think has to do with the Google Maps JavaScript API. So, the question lingers: how could I do some useful stuff from all this stuff in Python in order to get the map image?
EDIT: this link appears to contain some pretty relevant info on how Google Maps tiles their maps: http://www.codeproject.com/KB/scrapbook/googlemap.aspx
also: http://econym.org.uk/gmap/howitworks.htm
You can access the full google map by clicking the "View Larger Map" icon in the upper right corner of the map embedded on the page you shared. Here is the url. In the google map, if you go to the top of the legend and click the three vertical dots, the menu will display the option "Download KML".
I thank for all the answers. I ended up solving the problem another way, using Google Maps Static API and some formulas to convert from Coordinate space to Pixel space, so that I can get precise images that "stitch" nicely together.
For anyone interested, here is the code. If it helps someone, please comment!
=============================
import Image, urllib, StringIO
from math import log, exp, tan, atan, pi, ceil
EARTH_RADIUS = 6378137
EQUATOR_CIRCUMFERENCE = 2 * pi * EARTH_RADIUS
INITIAL_RESOLUTION = EQUATOR_CIRCUMFERENCE / 256.0
ORIGIN_SHIFT = EQUATOR_CIRCUMFERENCE / 2.0
def latlontopixels(lat, lon, zoom):
mx = (lon * ORIGIN_SHIFT) / 180.0
my = log(tan((90 + lat) * pi/360.0))/(pi/180.0)
my = (my * ORIGIN_SHIFT) /180.0
res = INITIAL_RESOLUTION / (2**zoom)
px = (mx + ORIGIN_SHIFT) / res
py = (my + ORIGIN_SHIFT) / res
return px, py
def pixelstolatlon(px, py, zoom):
res = INITIAL_RESOLUTION / (2**zoom)
mx = px * res - ORIGIN_SHIFT
my = py * res - ORIGIN_SHIFT
lat = (my / ORIGIN_SHIFT) * 180.0
lat = 180 / pi * (2*atan(exp(lat*pi/180.0)) - pi/2.0)
lon = (mx / ORIGIN_SHIFT) * 180.0
return lat, lon
############################################
# a neighbourhood in Lajeado, Brazil:
upperleft = '-29.44,-52.0'
lowerright = '-29.45,-51.98'
zoom = 18 # be careful not to get too many images!
############################################
ullat, ullon = map(float, upperleft.split(','))
lrlat, lrlon = map(float, lowerright.split(','))
# Set some important parameters
scale = 1
maxsize = 640
# convert all these coordinates to pixels
ulx, uly = latlontopixels(ullat, ullon, zoom)
lrx, lry = latlontopixels(lrlat, lrlon, zoom)
# calculate total pixel dimensions of final image
dx, dy = lrx - ulx, uly - lry
# calculate rows and columns
cols, rows = int(ceil(dx/maxsize)), int(ceil(dy/maxsize))
# calculate pixel dimensions of each small image
bottom = 120
largura = int(ceil(dx/cols))
altura = int(ceil(dy/rows))
alturaplus = altura + bottom
final = Image.new("RGB", (int(dx), int(dy)))
for x in range(cols):
for y in range(rows):
dxn = largura * (0.5 + x)
dyn = altura * (0.5 + y)
latn, lonn = pixelstolatlon(ulx + dxn, uly - dyn - bottom/2, zoom)
position = ','.join((str(latn), str(lonn)))
print x, y, position
urlparams = urllib.urlencode({'center': position,
'zoom': str(zoom),
'size': '%dx%d' % (largura, alturaplus),
'maptype': 'satellite',
'sensor': 'false',
'scale': scale})
url = 'http://maps.google.com/maps/api/staticmap?' + urlparams
f=urllib.urlopen(url)
im=Image.open(StringIO.StringIO(f.read()))
final.paste(im, (int(x*largura), int(y*altura)))
final.show()
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With