Exemple #1
0
    def renderArea(self, width, height, srs, xmin, ymin, xmax, ymax, zoom):
        """
        """
        if self.mapnik is None:
            self.mapnik = mapnik.Map(0, 0)

            if exists(self.mapfile):
                mapnik.load_map(self.mapnik, str(self.mapfile))

            else:
                handle, filename = mkstemp()
                os.write(handle, urlopen(self.mapfile).read())
                os.close(handle)

                mapnik.load_map(self.mapnik, filename)
                os.unlink(filename)

        self.mapnik.width = width
        self.mapnik.height = height
        self.mapnik.zoom_to_box(mapnik.Envelope(xmin, ymin, xmax, ymax))

        img = mapnik.Image(width, height)
        mapnik.render(self.mapnik, img)

        img = Image.fromstring('RGBA', (width, height), img.tostring())

        return img
Exemple #2
0
    def rendertiles(self, bounds, data, item, label, lat, layer, lon,
                    num_items, projec):
        z = 1
        imgx = 128 * z
        imgy = 128 * z

        mapfile = "/map_data/styles/bs_" + layer + ".xml"

        m = mapnik.Map(imgx, imgy)
        mapnik.load_map(m, mapfile)
        # ensure the target map projection is mercator
        m.srs = projec.params()

        if hasattr(mapnik, 'Box2d'):
            bbox = mapnik.Box2d(*bounds)
        else:
            bbox = mapnik.Envelope(*bounds)

        transform = mapnik.ProjTransform(longlat, projec)
        merc_bbox = transform.forward(bbox)

        m.zoom_to_box(merc_bbox)

        # render the map to an image
        im = mapnik.Image(imgx, imgy)
        mapnik.render(m, im)
        img = im.tostring('png256')
        data[(item, layer)] = img
    def render_tile(self, tile_uri, x, y, z):

        # Calculate pixel positions of bottom-left & top-right
        p0 = (x * 256, (y + 1) * 256)
        p1 = ((x + 1) * 256, y * 256)

        # Convert to LatLong (EPSG:4326)
        l0 = self.tileproj.fromPixelToLL(p0, z)
        l1 = self.tileproj.fromPixelToLL(p1, z)

        # Convert to map projection (e.g. mercator co-ords EPSG:900913)
        c0 = self.prj.forward(mapnik.Coord(l0[0], l0[1]))
        c1 = self.prj.forward(mapnik.Coord(l1[0], l1[1]))

        # Bounding box for the tile
        if hasattr(mapnik,
                   'mapnik_version') and mapnik.mapnik_version() >= 800:
            bbox = mapnik.Box2d(c0.x, c0.y, c1.x, c1.y)
        else:
            bbox = mapnik.Envelope(c0.x, c0.y, c1.x, c1.y)
        render_size = 256
        self.m.resize(render_size, render_size)
        self.m.zoom_to_box(bbox)
        if (self.m.buffer_size < 128):
            self.m.buffer_size = 128

        # Render image with default Agg renderer
        im = mapnik.Image(render_size, render_size)
        mapnik.render(self.m, im)
        im.save(tile_uri, 'png256')
Exemple #4
0
 def render_location(self):
     # spherical mercator (most common target map projection of osm data imported with osm2pgsql)
     merc = mapnik.Projection('+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0 +k=1.0 +units=m +nadgrids=@null +no_defs +over')
     longlat = mapnik.Projection('+proj=longlat +ellps=WGS84 +datum=WGS84 +no_defs')
     mapfile = "renderer/map_data/styles/bs_complete.xml"
     bounds = (self.lon-self.size, self.lat-self.size, self.lon+self.size,self.lat+self.size)
     z = 1
     imgx = 224 * z
     imgy = 224 * z
     m = mapnik.Map(imgx,imgy)
     mapnik.load_map(m,mapfile)
     m.srs = merc.params()
     if hasattr(mapnik,'Box2d'):
         bbox = mapnik.Box2d(*bounds)
     else:
         bbox = mapnik.Envelope(*bounds)
     transform = mapnik.ProjTransform(longlat,merc)
     merc_bbox = transform.forward(bbox)
     m.zoom_to_box(merc_bbox)
     #render the map to an image
     im = mapnik.Image(imgx,imgy)
     mapnik.render(m, im)
     img = im.tostring('png256')
     img = cv2.imdecode(np.fromstring(img, dtype=np.uint8), 1)
     img =np.asarray(img)
     window_name = "Location"
     cv2.imshow(window_name, img)
     cv2.waitKey(0)
def render_legend(mapfile, tile_uri):
    m = mapnik.Map(1024, 2048)
    # Load style XML
    mapnik.load_map(m, mapfile, True)
    # Obtain <Map> projection
    prj = mapnik.Projection(m.srs)
    # Projects between tile pixel co-ordinates and LatLong (EPSG:4326)
    tileproj = GoogleProjection(20)

    # Convert to map projection (e.g. mercator co-ords EPSG:900913)
    c0 = prj.forward(mapnik.Coord(14.4503,50.0673))
    c1 = prj.forward(mapnik.Coord(14.457,50.0678))

    # Bounding box for the tile
    if hasattr(mapnik,'mapnik_version') and mapnik.mapnik_version() >= 800:
        bbox = mapnik.Box2d(c0.x,c0.y, c1.x,c1.y)
    else:
        bbox = mapnik.Envelope(c0.x,c0.y, c1.x,c1.y)
    render_size_x = 1024
    render_size_y = 1500
    m.resize(render_size_x, render_size_y)
    m.zoom_to_box(bbox)
    m.buffer_size = 128

    # Render image with default Agg renderer
    im = mapnik.Image(render_size_x, render_size_y)
    mapnik.render(m, im)
    im.save(tile_uri, 'png256')

    surface = cairo.SVGSurface('legend.svg', render_size_x, render_size_y)
    mapnik.render(m, surface)
    surface.finish()
Exemple #6
0
 def render_dynamic(self, painter):
     if self.mapnik_map:
         w = painter.device().width()
         h = painter.device().height()
         # using canvas dims leads to shift in QGIS < 1.3...
         #w = self.canvas.width()
         #h = self.canvas.height()
         try:
             self.mapnik_map.resize(w, h)
         except:
             self.mapnik_map.width = w
             self.mapnik_map.height = h
         if self.qCanvas:
             can = self.qCanvas
         else:
             can = self.canvas
         try:
             e = can.extent()
         except:
             can = self.canvas
             e = can.extent()
         bbox = mapnik.Envelope(e.xMinimum(), e.yMinimum(), e.xMaximum(),
                                e.yMaximum())
         self.mapnik_map.zoom_to_box(bbox)
         im = mapnik.Image(w, h)
         mapnik.render(self.mapnik_map, im)
         if os.name == 'nt':
             qim = QImage()
             qim.loadFromData(QByteArray(im.tostring('png')))
             painter.drawImage(0, 0, qim)
         else:
             qim = QImage(im.tostring(), w, h, QImage.Format_ARGB32)
             painter.drawImage(0, 0, qim.rgbSwapped())
         can.refresh()
    def render_tile(self, tile_uri, x, y, z):

        # Calculate pixel positions of bottom-left & top-right
        p0 = (x * 256, (y + 1) * 256)
        p1 = ((x + 1) * 256, y * 256)

        # Convert to LatLong (EPSG:4326)
        l0 = self.tileproj.fromPixelToLL(p0, z)
        l1 = self.tileproj.fromPixelToLL(p1, z)

        # Convert to map projection (e.g. mercator co-ords EPSG:900913)
        c0 = self.prj.forward(mapnik.Coord(l0[0], l0[1]))
        c1 = self.prj.forward(mapnik.Coord(l1[0], l1[1]))

        # Bounding box for the tile
        if hasattr(mapnik,
                   'mapnik_version') and mapnik.mapnik_version() >= 800:
            bbox = mapnik.Box2d(c0.x, c0.y, c1.x, c1.y)
        else:
            bbox = mapnik.Envelope(c0.x, c0.y, c1.x, c1.y)
        render_size = 256
        self.m.resize(render_size, render_size)
        self.m.zoom_to_box(bbox)
        self.m.buffer_size = 128

        # Render image with default Agg renderer
        im = mapnik.Image(render_size, render_size)
        mapnik.render(self.m, im)
        im.save(tile_uri, 'png256')
        grid_uri = tile_uri.replace('.png', '.grid.json')

        # new mapnik.Grid api, works like mapnik.Image
        # with the exception that you can only render one
        # layer to it with the mapnik.render_layer function

        # create grid as same size as map/image
        grid = mapnik.Grid(render_size, render_size)
        # render a layer to that grid array
        mapnik.render_layer(self.m, grid, layer=0, fields=['POP2005', 'NAME'])
        # then encode the grid array as utf, resample to 1/4 the size, and dump features
        grid_utf = grid.encode('utf', resolution=4, add_features=True)

        # below is the old grid api - will be removed soon, don't use
        #grid_utf = mapnik.render_grid(self.m,0,key='__id__',resolution=4,fields=['POP2005','NAME'])
        # client code uses jsonp, so fake by wrapping in grid() callback
        open(grid_uri, 'wb').write('grid(' + json.dumps(grid_utf) + ')')
    def render_tile(self, tile_uri, x, y, z):
        # Calculate pixel positions of bottom-left & top-right
        p0 = (x * TILES_SIZE, (y + 1) * TILES_SIZE)
        p1 = ((x + 1) * TILES_SIZE, y * TILES_SIZE)

        # Convert to LatLong (EPSG:4326)
        l0 = self.tileproj.fromPixelToLL(p0, z)
        l1 = self.tileproj.fromPixelToLL(p1, z)

        # Convert to map projection (e.g. mercator co-ords EPSG:900913)
        c0 = self.prj.forward(mapnik.Coord(l0[0], l0[1]))
        c1 = self.prj.forward(mapnik.Coord(l1[0], l1[1]))

        # Bounding box for the tile
        if hasattr(mapnik,
                   'mapnik_version') and mapnik.mapnik_version() >= 800:
            bbox = mapnik.Box2d(c0.x, c0.y, c1.x, c1.y)
        else:
            bbox = mapnik.Envelope(c0.x, c0.y, c1.x, c1.y)
        render_size = TILES_SIZE
        self.m.resize(render_size, render_size)
        self.m.zoom_to_box(bbox)
        self.m.buffer_size = 128

        if FORMAT == 'grid':
            grid = mapnik.Grid(render_size, render_size)
            #            mapnik.render_layer(self.m, grid, layer=64, fields=['name'])
            for n, l in enumerate(self.m.layers):
                if l.name != 'admin-012345678':
                    if 'name' in l.datasource.fields():
                        mapnik.render_layer(self.m,
                                            grid,
                                            layer=n,
                                            fields=['name'])
            utfgrid = grid.encode('utf', resolution=4)
            f = open(tile_uri + '.' + FILE_EXTENSION, 'w')
            f.write(json.dumps(utfgrid))
            f.close()
        else:
            # Render image with default Agg renderer
            im = mapnik.Image(render_size, render_size)
            mapnik.render(self.m, im)
            im.save(tile_uri + '.' + FILE_EXTENSION, FORMAT)
Exemple #9
0
def complexRun(image, stylesheet, extent, size):
    mapfile = stylesheet
    map_uri = image

    imgx = size[0]
    imgy = size[1]

    m = mapnik.Map(imgx, imgy)
    mapnik.load_map(m, mapfile)

    if hasattr(mapnik, 'mapnik_version') and mapnik.mapnik_version() >= 800:
        bbox = mapnik.Box2d(extent[0], extent[2], extent[1], extent[3])
    else:
        bbox = mapnik.Envelope(extent[0], extent[2], extent[1], extent[3])
    m.zoom_to_box(bbox)
    im = mapnik.Image(imgx, imgy)
    mapnik.render(m, im)
    view = im.view(0, 0, imgx, imgy)  # x,y,width,height
    view.save(map_uri, 'png')
Exemple #10
0
    def render_tile(self, tile_uri, x, y, z):
        # Calculate pixel positions of bottom-left & top-right
        #        start=time.time()
        #        p0 = (x * TILESIZE, (y + 1) * TILESIZE)
        #        p1 = ((x + 1) * TILESIZE, y * TILESIZE)
        #
        #        # Convert to LatLong (EPSG:4326)
        #        l0 = self.tileproj.fromPixelToLL(p0, z);
        #        l1 = self.tileproj.fromPixelToLL(p1, z);
        #
        #        # Convert to map projection (e.g. mercator co-ords EPSG:900913)
        #        c0 = self.prj.forward(mapnik2.Coord(l0[0],l0[1]))
        #        c1 = self.prj.forward(mapnik2.Coord(l1[0],l1[1]))

        l0y, l0x = num2deg(x, y + 1, z)
        l1y, l1x = num2deg(x + 1, y, z)

        # Convert to map projection (e.g. mercator co-ords EPSG:900913)
        c0 = self.prj.forward(mapnik2.Coord(l0x, l0y))
        c1 = self.prj.forward(mapnik2.Coord(l1x, l1y))

        # Bounding box for the tile
        if hasattr(mapnik2,
                   'mapnik_version') and mapnik2.mapnik_version() >= 800:
            bbox = mapnik2.Box2d(c0.x, c0.y, c1.x, c1.y)
        else:
            bbox = mapnik2.Envelope(c0.x, c0.y, c1.x, c1.y)
        render_size = TILESIZE
        self.m.resize(render_size, render_size)
        self.m.zoom_to_box(bbox)
        self.m.buffer_size = 128

        # Render image with default Agg renderer
        im = mapnik2.Image(render_size, render_size)
        #        print("%f"%(time.time()-start))
        #        start=time.time()
        mapnik2.render(self.m, im)
        #        print("%f"%(time.time()-start))
        #        start=time.time()
        im.save(tile_uri, 'png256')
Exemple #11
0
    def generate_map_tile(self, m, filename, z, x, y):
        # Code taken from OSM generate_tiles.py
        proj = GoogleProjection()
        mprj = mapnik.Projection(m.srs)

        p0 = (x * 256, (y + 1) * 256)
        p1 = ((x + 1) * 256, y * 256)
        l0 = proj.fromPixelToLL(p0, z);
        l1 = proj.fromPixelToLL(p1, z);
        c0 = mprj.forward(mapnik.Coord(l0[0], l0[1]))
        c1 = mprj.forward(mapnik.Coord(l1[0], l1[1]))

        if hasattr(mapnik,'mapnik_version') and mapnik.mapnik_version() >= 800:
            bbox = mapnik.Box2d(c0.x, c0.y, c1.x, c1.y)
        else:
            bbox = mapnik.Envelope(c0.x, c0.y, c1.x, c1.y)

        m.resize(256, 256)
        m.zoom_to_box(bbox)

        im = mapnik.Image(256, 256)
        mapnik.render(m, im)
        im.save(str(filename), "png256")
Exemple #12
0
def rendertiles( bounds, item, label, lat, layers, lon, projec, writer):
    z = 1
    imgx = 128 * z
    imgy = 128 * z
    
    for layer in layers:
        index = layers.index(layer)
        mapfile = "/map_data/styles/bs_" + layer + ".xml"
     
        m = mapnik.Map(imgx,imgy)
        mapnik.load_map(m,mapfile)
        # ensure the target map projection is mercator
        m.srs = projec.params()
        
        if hasattr(mapnik,'Box2d'):
            bbox = mapnik.Box2d(*bounds)
        else:
            bbox = mapnik.Envelope(*bounds)

        transform = mapnik.ProjTransform(longlat,projec)
        merc_bbox = transform.forward(bbox)
        
        m.zoom_to_box(merc_bbox)
        
        # render the map to an image
        im = mapnik.Image(imgx,imgy)
        mapnik.render(m, im)
        
        img = im.tostring('png256')
        
        if index == 0:
            data=[img]
            #data = np.expand_dims(data, 0) 
        else:            
            data.append(img)    
                    
    save_data(data, layers, item, label, lat, lon, writer)
Exemple #13
0
m = mapnik2.Map(pic_output_width, pic_output_height)

# Load osm-xml-stylesheet for rendering the views
# DB has to have the same name as cmd user
mapnik2.load_map(m, path_to_osm_xml)

# Define projection
prj = mapnik2.Projection(
    "+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0 +k=1.0 +units=m +nadgrids=@null +no_defs +over"
)

# Map bounds. Bound values come from SQL-query
if hasattr(mapnik2, 'Box2d'):
    bbox = mapnik2.Box2d(xmin, ymin, xmax, ymax)
else:
    bbox = mapnik2.Envelope(xmin, ymin, xmax, ymax)

# Project bounds to map projection
e = mapnik2.forward_(bbox, prj)

# Zoom map to bounding box
m.zoom_to_box(e)

###
### START Layer 1
###

# style object to hold rules
s = mapnik2.Style()
s2 = mapnik2.Style()
Exemple #14
0
# This library is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
# Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public
# License along with this library; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
#

import mapnik2

mapfile = 'tutorial2.xml'
map_output = '~/geodata/raster/world/hello_world_using_xml_config.png'
map_output = 'hello_world_using_xml_config.png'

# Instantiate a map object with given width, height and spatial reference system
#m = mapnik.Map(600,300,"+proj=latlong +datum=WGS84")
m = mapnik2.Map(600, 300)

mapnik2.load_map(m, mapfile)
bbox = mapnik2.Envelope(mapnik2.Coord(-180.0, -90.0),
                        mapnik2.Coord(180.0, 90.0))
m.zoom_to_box(bbox)

# Write the data to a png image called world.png in the base directory of your user
mapnik2.render_to_file(m, map_output)

# Exit the python interpreter
exit()
Exemple #15
0
def render_map(mapfile):
    #A4
    #filename = 'export_A4'
    #render_size_x = 842
    #render_size_y = 595
    #A3
    #filename = 'export_A3'
    #render_size_x = 1191
    #render_size_y = 842
    #A2
    #filename = 'export_A2'
    #render_size_x = 1684
    #render_size_y = 1191
    #A1
    #filename = 'export_A1'
    #render_size_x = 2384
    #render_size_y = 1684
    #A0
    filename = 'export_A0'
    render_size_x = 3370
    render_size_y = 2384
    #A-1
    #filename = 'export_A-1'
    #render_size_x = 4768
    #render_size_y = 3370
    #A-2
    #filename = 'export_A-2'
    #render_size_x = 6740
    #render_size_y = 4768

    m = mapnik.Map(render_size_x, render_size_y)
    # Load style XML
    mapnik.load_map(m, mapfile, True)
    # Obtain <Map> projection
    prj = mapnik.Projection(m.srs)
    # Projects between tile pixel co-ordinates and LatLong (EPSG:4326)
    tileproj = GoogleProjection(20)

    # Convert to map projection (e.g. mercator co-ords EPSG:900913)
    c0 = prj.forward(mapnik.Coord(14.33, 50.05))
    c1 = prj.forward(mapnik.Coord(14.53, 50.14))

    #filename = filename + '_BIG'
    #c0 = prj.forward(mapnik.Coord(14.25,49.95))
    #c1 = prj.forward(mapnik.Coord(14.68,50.16))

    # Bounding box for the tile
    if hasattr(mapnik, 'mapnik_version') and mapnik.mapnik_version() >= 800:
        bbox = mapnik.Box2d(c0.x, c0.y, c1.x, c1.y)
    else:
        bbox = mapnik.Envelope(c0.x, c0.y, c1.x, c1.y)
    m.resize(render_size_x, render_size_y)
    m.zoom_to_box(bbox)
    m.buffer_size = 128

    # Render image with default Agg renderer
    #im = mapnik.Image(render_size_x, render_size_y)
    #mapnik.render(m, im)
    #im.save('export.png', 'png256')

    #surface = cairo.PDFSurface(filename + '.pdf', render_size_x, render_size_y)
    #mapnik.render(m, surface)

    surface = cairo.PSSurface(filename + '.ps', render_size_x, render_size_y)

    surface.dsc_comment("%%Title: Cyklisticka mapa prahy")
    surface.dsc_comment("%%Copyright: CC-BY-SA")
    mapnik.render(m, surface)

    #surface = cairo.SVGSurface(filename + '.svg', render_size_x, render_size_y)
    #mapnik.render(m, surface)
    surface.finish()
    #---------------------------------------------------

    z = 10
    imgx = 120 * z
    imgy = 80 * z

    m = mapnik.Map(imgx,imgy)
    mapnik.load_map(m,mapfile)
    
    # ensure the target map projection is mercator
    m.srs = merc.params()

    if hasattr(mapnik,'Box2d'):
        bbox = mapnik.Box2d(*bounds)
    else:
        bbox = mapnik.Envelope(*bounds)

    # Our bounds above are in long/lat, but our map
    # is in spherical mercator, so we need to transform
    # the bounding box to mercator to properly position
    # the Map when we call `zoom_to_box()`
    transform = mapnik.ProjTransform(longlat,merc)
    merc_bbox = transform.forward(bbox)
    
    # Mapnik internally will fix the aspect ratio of the bounding box
    # to match the aspect ratio of the target image width and height
    # This behavior is controlled by setting the `m.aspect_fix_mode`
    # and defaults to GROW_BBOX, but you can also change it to alter
    # the target image size by setting aspect_fix_mode to GROW_CANVAS
    #m.aspect_fix_mode = mapnik.GROW_CANVAS
    # Note: aspect_fix_mode is only available in Mapnik >= 0.6.0
Exemple #17
0
def metadata_image(bboxes, mapfile):
    """Create a metadata image"""

    from json import dumps as tojson
    import mapnik2 as mapnik

    features = []

    for bbox in bboxes:
        minx, miny, maxx, maxy = bbox

        # create the bounding box as a json string
        width, height = (maxx - minx, maxy - miny)
        min_dim = 0.0125                        # minimum dimension for display as a rectangle (in degrees)
        if width < min_dim or height < min_dim:   # it should be a point
            feature = { "type": "Feature",
                        "geometry": {
                            "type": "Point",
                            "coordinates": [minx, miny]
                            },
                        "properties": {
                            "type": "point"
                            }
                        }
            width, height = (9, 9)
        else:
            feature = { "type": "Feature",
                        "geometry": {
                            "type": "Polygon",
                            "coordinates": [[[minx, miny], [maxx, miny], [maxx, maxy], [minx, maxy], [minx, miny]]]
                            },
                        "properties": {
                            "type": "bbox"
                            }
                        }
        features.append(feature)

    json = tojson({
            "type": "FeatureCollection",
            "features": features
            })

    # instantiate the map
    m = mapnik.Map(250, 250)
    mapnik.load_map_from_string(m, mapfile)

    # set the datasource for the last layer to show the bounding box
    datasource = mapnik.Ogr(file=json, layer='OGRGeoJSON')
    m.layers[-1].datasource = datasource

    # create an image of the area of interest with a border
    border = 80.0                       # percentage border
    dx = width * (border / 100)
    minx2 = minx - dx; maxx2 = maxx + dx
    dy = height * (border / 100)
    miny2 = miny - dy; maxy2 = maxy + dy

    # don't create a border larger than the globe's extent
    if minx2 < -180.0 or maxx2 > 180.0 or miny2 < -90.0 or maxy2 > 90.0:
        minx2 = minx; maxx2 = maxx; miny2 = miny; maxy2 = maxy
    
    bbox = mapnik.Envelope(mapnik.Coord(minx2, miny2), mapnik.Coord(maxx2, maxy2))
    m.zoom_to_box(bbox)
    image = mapnik.Image(m.width, m.height)
    mapnik.render(m, image)

    return image
Exemple #18
0
    def render_metatile(self, metatile):
        z = metatile.z
        x = metatile.x
        y = metatile.y

        # TODO: move all this somewhere else
        # Calculate pixel positions of bottom-left & top-right
        p0 = (x * self.tile_size, (y + self.metatile_size) * self.tile_size)
        p1 = ((x + self.metatile_size) * self.tile_size, y * self.tile_size)

        # Convert to LatLong (EPSG:4326)
        l0 = self.tileproj.fromPixelToLL(p0, z)
        l1 = self.tileproj.fromPixelToLL(p1, z)

        # Convert to map projection (e.g. mercator co-ords EPSG:900913)
        c0 = self.prj.forward(mapnik.Coord(l0[0], l0[1]))
        c1 = self.prj.forward(mapnik.Coord(l1[0], l1[1]))

        # Bounding box for the tile
        if hasattr(mapnik,
                   'mapnik_version') and mapnik.mapnik_version() >= 800:
            bbox = mapnik.Box2d(c0.x, c0.y, c1.x, c1.y)
        else:
            bbox = mapnik.Envelope(c0.x, c0.y, c1.x, c1.y)

        self.m.resize(self.image_size, self.image_size)
        self.m.zoom_to_box(bbox)
        if self.m.buffer_size < 128:
            self.m.buffer_size = 128

        # we must decide wether to render the subtiles/children of this tile
        render_children = {child: False for child in metatile.children()}

        if not self.opts.dry_run:
            # Render image with default Agg renderer
            start = time.perf_counter()
            im = mapnik.Image(self.image_size, self.image_size)

            try:
                mapnik.render(self.m, im)
            except RuntimeError as e:
                exception("%r: %s", metatile, e)
            else:
                mid = time.perf_counter()

                # save the image, splitting it in the right amount of tiles
                for tile in metatile.tiles:
                    i, j = tile.meta_index

                    # TODO: Tile.meta_pixel_coords
                    img = im.view(i * self.tile_size, j * self.tile_size,
                                  self.tile_size, self.tile_size)
                    tile.data = img.tostring('png256')
                    # TODO: move to Tile
                    is_empty = map_utils.is_empty(tile.data)

                    if not is_empty or self.opts.empty == 'write':
                        self.backend.store(tile)

                        # at least something to render. note that if we're
                        # rendering only one tile (either metatile_size == 1
                        # or z == 0), i, j can only be == 0. this matches
                        # the situation further down
                        render_children[metatile.child(tile)] = True
                    else:
                        if self.opts.empty == 'skip':
                            # empty tile, skip
                            debug("%r: empty" % tile)
                            continue
                        # TODO: else?

                    self.backend.commit()

                end = time.perf_counter()
                info("%r: %f, %f" % (metatile, mid - start, end - mid))

        else:
            # simulate some work
            time.sleep(randint(0, 30) / 10)
            for child in metatile.children():
                if random() <= 0.75 or 2**metatile.z < self.opts.metatile_size:
                    render_children[child] = True

        return render_children
Exemple #19
0
    #---------------------------------------------------
    #  Change this to the bounding box you want
    #
    #ll = (-5.2, 41.4, 10.16, 46.2)
    #ll = (1.393547058105469, 43.56610697474913, 1.429810523986817, 43.58131079720606) #reynerie
    #ll = (1.406988241528325, 43.56730920511517, 1.461919882153325, 43.60237411394007) #ponts
    #ll = (1.359014509180042, 43.59232959871322, 1.404848096826527, 43.62626162214223) #tournefeuille (rocades)
    ll = args.bbox
    #---------------------------------------------------

    z = args.zoom
    imgx = 500 * z
    imgy = 1000 * z

    m = mapnik2.Map(imgx, imgy)
    mapnik2.load_map(m, args.mapfile)
    prj = mapnik2.Projection(
        "+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0 +k=1.0 +units=m +nadgrids=@null +no_defs +over"
    )
    c0 = prj.forward(mapnik2.Coord(ll[0], ll[1]))
    c1 = prj.forward(mapnik2.Coord(ll[2], ll[3]))
    if hasattr(mapnik2, 'mapnik_version') and mapnik2.mapnik_version() >= 800:
        bbox = mapnik2.Box2d(c0.x, c0.y, c1.x, c1.y)
    else:
        bbox = mapnik2.Envelope(c0.x, c0.y, c1.x, c1.y)
    m.zoom_to_box(bbox)
    im = mapnik2.Image(imgx, imgy)
    mapnik2.render(m, im)
    view = im.view(0, 0, imgx, imgy)  # x,y,width,height
    view.save(map_uri, 'png')
    def render_metatile(
            self, metatile: map_utils.MetaTile) -> Dict[map_utils.Tile, bool]:
        # get LatLong (EPSG:4326)
        l0 = metatile.coords[0]
        l1 = metatile.coords[1]

        # this is the only time where we convert manually into WebMerc
        # Convert to map projection (e.g. mercator co-ords EPSG:900913)
        c0 = self.prj.forward(mapnik.Coord(l0[0], l0[1]))
        c1 = self.prj.forward(mapnik.Coord(l1[0], l1[1]))

        # Bounding box for the tile
        if hasattr(mapnik,
                   'mapnik_version') and mapnik.mapnik_version() >= 800:
            bbox = mapnik.Box2d(c0.x, c0.y, c1.x, c1.y)
        else:
            bbox = mapnik.Envelope(c0.x, c0.y, c1.x, c1.y)

        image_size = self.opts.tile_size * min(self.metatile_size, 2**
                                               metatile.z)
        self.m.resize(image_size, image_size)
        self.m.zoom_to_box(bbox)
        if self.m.buffer_size < 128:
            self.m.buffer_size = 128

        bail_out = True

        start = time.perf_counter()
        if not self.opts.dry_run:
            im = mapnik.Image(image_size, image_size)
            # Render image with default Agg renderer
            debug('[%s] rende...', self.name)
            # TODO: handle exception, send back into queue
            mapnik.render(self.m, im)
            debug('[%s] ...ring!', self.name)
            mid = time.perf_counter()

            # TODO: all this is on a single tile, not a metatile

            # converting to png256 is the fastest I have found so far:
            # python3.6 -m timeit -s 'import mapnik; im = mapnik.Image.fromstring(open("Attic/tmp/369.png", "br").read())' 'data = im.tostring("png256")'
            # 100 loops, best of 3: 7.72 msec per loop
            # tostring() looks nice, but I can't rebuild a mapnik.Image from it :(
            # python3.6 -m timeit -s 'import mapnik; im = mapnik.Image.fromstring(open("Attic/tmp/369.png", "br").read())' 'data = im.tostring()'
            # 100000 loops, best of 3: 13.8 usec per loop
            # python3.6 -m timeit -s 'import mapnik, bz2; im = mapnik.Image.fromstring(open("Attic/tmp/369.png", "br").read())' 'c = bz2.BZ2Compressor(); c.compress(im.tostring()); data = c.flush()'
            # 10 loops, best of 3: 20.3 msec per loop
            # python3.6 -m timeit -s 'import mapnik, gzip; im = mapnik.Image.fromstring(open("Attic/tmp/369.png", "br").read())' 'data = gzip.compress(im.tostring())'
            # 10 loops, best of 3: 27.7 msec per loop
            # python3.6 -s -m timeit -s 'import mapnik, lzma; im = mapnik.Image.fromstring(open("Attic/tmp/369.png", "br").read())' "c = lzma.LZMACompressor(); c.compress(im.tostring()); data = c.flush()"
            # 10 loops, best of 3: 92 msec per loop

            # TODO:
            # but bz2 compresses the best, 52714 png vs 49876 bzip vs 70828 gzip vs 53032 lzma

            if not self.opts.store_thread:
                # metatile will go in a non-marshaling queue, no need tostring() it
                metatile.im = im
            else:
                metatile.im = im.tostring('png256')

            end = time.perf_counter()
        else:
            debug('[%s] thumbtumbling', self.name)
            time.sleep(randint(0, 30) / 10)
            mid = time.perf_counter()
            end = time.perf_counter()

        metatile.render_time = mid - start
        metatile.serializing_time = end - mid
        bail_out = False

        debug("[%s] putting %r", self.name, metatile)
        self.output.put(metatile)
        debug("[%s] put! (%d)", self.name, self.output.qsize())

        if not self.opts.store_thread and self.output.qsize() > 0:
            # NOTE: mypy complains here that Item "Process" of "Union[Process, StormBringer]" has no attribute "single_step"
            # the solutions are ugly, so I'm leaving it as that
            self.store_thread.single_step()

        return bail_out
Exemple #21
0
    def render(self, item, zoom, size, dest):
        """ Compile a Cascadenik MML file, returning a cascadenik.output.Map object.
    
        Parameters:
        
          src:
            Path to .mml file, or raw .mml file content.
          
          dirs:
            Object with directory names in 'cache', 'output', and 'source' attributes.
            dirs.source is expected to be fully-qualified, e.g. "http://example.com"
            or "file:///home/example".
        
        Keyword Parameters:
        
          verbose:
            If True, debugging information will be printed to stderr.
        
          srs:
            Target spatiral reference system for the compiled stylesheet.
            If provided, overrides default map srs in the .mml file.
        
          datasources_cfg:
            If a file or URL, uses the config to override datasources or parameters
            (i.e. postgis_dbname) defined in the map's canonical <DataSourcesConfig>
            entities.  This is most useful in development, whereby one redefines
            individual datasources, connection parameters, and/or local paths.
        """
        mmap = mapnik.Map(*size)
        mmap.srs = '+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0 +k=1.0 +units=m +nadgrids=@null'

        resolution = 20037508.34 / 128 / (pow(2, zoom))
        extent = [
            -resolution / 2 * size[0], -resolution / 2 * size[1],
            resolution / 2 * size[0], resolution / 2 * size[1]
        ]

        classes = set(item.get('class', '').split())

        layers = []

        for layer in self.layers:

            # check if this layers classes are in class list
            if not need_layer(layer.classes, item, classes):
                continue

            datasource = create_datasource()

            if layer.classes <= classes:
                datasource.addFeatures(item, extent)

            for bg_el in item.findall('background'):
                bg_classes = set(bg_el.get('class', '').split())
                if layer.classes <= bg_classes:
                    datasource.addFeatures(bg_el, extent)

            layer.datasource = datasource
            layers.append(layer)

        output.Map(self.map_el.attrib.get('srs', None), layers, self.fontsets,
                   **self.map_attrs).to_mapnik(mmap, self.dirs)
        bbox = mapnik.Envelope(*extent)
        mmap.zoom_to_box(bbox)
        mmap.background = mapnik.Color(0, 0, 0, 0)
        im = mapnik.Image(*size)
        mapnik.render(mmap, im)
        im.save(dest, 'png256')
        return im.tostring()