Пример #1
0
    def _get_boundaries(self, src):

        self.output("Getting boundaries", normal=True, arrow=True)
        output = {'ul': {'x': [0, 0], 'y': [0, 0]},  # ul: upper left
                  'ur': {'x': [0, 0], 'y': [0, 0]},  # ur: upper right
                  'll': {'x': [0, 0], 'y': [0, 0]},  # ll: lower left
                  'lr': {'x': [0, 0], 'y': [0, 0]}}  # lr: lower right

        output['ul']['x'][0] = src['affine'][2]
        output['ul']['y'][0] = src['affine'][5]
        output['ur']['x'][0] = output['ul']['x'][0] + self.pixel * src['shape'][1]
        output['ur']['y'][0] = output['ul']['y'][0]
        output['ll']['x'][0] = output['ul']['x'][0]
        output['ll']['y'][0] = output['ul']['y'][0] - self.pixel * src['shape'][0]
        output['lr']['x'][0] = output['ul']['x'][0] + self.pixel * src['shape'][1]
        output['lr']['y'][0] = output['ul']['y'][0] - self.pixel * src['shape'][0]

        output['ul']['x'][1], output['ul']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['ul']['x'][0]],
                                                               [output['ul']['y'][0]])

        output['ur']['x'][1], output['ur']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['ur']['x'][0]],
                                                               [output['ur']['y'][0]])

        output['ll']['x'][1], output['ll']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['ll']['x'][0]],
                                                               [output['ll']['y'][0]])

        output['lr']['x'][1], output['lr']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['lr']['x'][0]],
                                                               [output['lr']['y'][0]])

        return output
Пример #2
0
def point(scene, coord):

    scene_params = utils.landsat_parse_scene_id(scene)
    meta_data = utils.landsat_get_mtl(scene)
    landsat_address = f's3://landsat-pds/{scene_params["key"]}'

    band_address = f'{landsat_address}_B4.TIF'
    with rio.open(band_address) as band:
        lon_srs, lat_srs = warp.transform('EPSG:4326', band.crs, [coord[0]],
                                          [coord[1]])
        b4 = list(band.sample([(lon_srs[0], lat_srs[0])]))[0]
        b4 = float(utils.landsat_to_toa(b4, 4, meta_data)[0])

    band_address = f'{landsat_address}_B5.TIF'
    with rio.open(band_address) as band:
        lon_srs, lat_srs = warp.transform('EPSG:4326', band.crs, [coord[0]],
                                          [coord[1]])
        b5 = list(band.sample([(lon_srs[0], lat_srs[0])]))[0]
        b5 = float(utils.landsat_to_toa(b5, 5, meta_data)[0])

    if b4 * b5 > 0:
        ratio = (b5 - b4) / (b5 + b4)
    else:
        ratio = 0

    out = {
        'ndvi': ratio,
        'date': scene_params['date'],
        'cloud': float(utils.landsat_mtl_extract(meta_data, 'CLOUD_COVER'))
    }

    return out
Пример #3
0
    def _get_boundaries(self, src):

        self.output("Getting boundaries", normal=True, arrow=True)
        output = {'ul': {'x': [0, 0], 'y': [0, 0]},  # ul: upper left
                  'ur': {'x': [0, 0], 'y': [0, 0]},  # ur: upper right
                  'll': {'x': [0, 0], 'y': [0, 0]},  # ll: lower left
                  'lr': {'x': [0, 0], 'y': [0, 0]}}  # lr: lower right

        output['ul']['x'][0] = src['affine'][2]
        output['ul']['y'][0] = src['affine'][5]
        output['ur']['x'][0] = output['ul']['x'][0] + self.pixel * src['shape'][1]
        output['ur']['y'][0] = output['ul']['y'][0]
        output['ll']['x'][0] = output['ul']['x'][0]
        output['ll']['y'][0] = output['ul']['y'][0] - self.pixel * src['shape'][0]
        output['lr']['x'][0] = output['ul']['x'][0] + self.pixel * src['shape'][1]
        output['lr']['y'][0] = output['ul']['y'][0] - self.pixel * src['shape'][0]

        output['ul']['x'][1], output['ul']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['ul']['x'][0]],
                                                               [output['ul']['y'][0]])

        output['ur']['x'][1], output['ur']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['ur']['x'][0]],
                                                               [output['ur']['y'][0]])

        output['ll']['x'][1], output['ll']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['ll']['x'][0]],
                                                               [output['ll']['y'][0]])

        output['lr']['x'][1], output['lr']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['lr']['x'][0]],
                                                               [output['lr']['y'][0]])

        return output
Пример #4
0
    def _get_boundaries(self, src, shape):

        self.output("Getting boundaries", normal=True, arrow=True)
        output = {
            'ul': {
                'x': [0, 0],
                'y': [0, 0]
            },  # ul: upper left
            'ur': {
                'x': [0, 0],
                'y': [0, 0]
            },  # ur: upper right
            'll': {
                'x': [0, 0],
                'y': [0, 0]
            },  # ll: lower left
            'lr': {
                'x': [0, 0],
                'y': [0, 0]
            }
        }  # lr: lower right

        output['ul']['x'][0] = src['affine'][2]
        output['ul']['y'][0] = src['affine'][5]
        output['ur']['x'][
            0] = output['ul']['x'][0] + self.pixel * src['shape'][1]
        output['ur']['y'][0] = output['ul']['y'][0]
        output['ll']['x'][0] = output['ul']['x'][0]
        output['ll']['y'][
            0] = output['ul']['y'][0] - self.pixel * src['shape'][0]
        output['lr']['x'][
            0] = output['ul']['x'][0] + self.pixel * src['shape'][1]
        output['lr']['y'][
            0] = output['ul']['y'][0] - self.pixel * src['shape'][0]

        output['ul']['x'][1], output['ul']['y'][1] = transform(
            src['crs'], self.projection, [output['ul']['x'][0]],
            [output['ul']['y'][0]])

        output['ur']['x'][1], output['ur']['y'][1] = transform(
            src['crs'], self.projection, [output['ur']['x'][0]],
            [output['ur']['y'][0]])

        output['ll']['x'][1], output['ll']['y'][1] = transform(
            src['crs'], self.projection, [output['ll']['x'][0]],
            [output['ll']['y'][0]])

        output['lr']['x'][1], output['lr']['y'][1] = transform(
            src['crs'], self.projection, [output['lr']['x'][0]],
            [output['lr']['y'][0]])

        dst_corner_ys = [output[k]['y'][1][0] for k in output.keys()]
        dst_corner_xs = [output[k]['x'][1][0] for k in output.keys()]
        y_pixel = abs(max(dst_corner_ys) - min(dst_corner_ys)) / shape[0]
        x_pixel = abs(max(dst_corner_xs) - min(dst_corner_xs)) / shape[1]

        return (min(dst_corner_xs), x_pixel, 0.0, max(dst_corner_ys), 0.0,
                -y_pixel)
Пример #5
0
def get_tile_tif(tile, imagery, folder, kwargs):
    """
    Read a GeoTIFF with a window corresponding to a TMS tile

    The TMS tile bounds are converted to the GeoTIFF source CRS. That bounding
    box is converted to a pixel window which is read from the GeoTIFF. For
    remote files which are internally tiled, this will take advantage of HTTP
    GET Range Requests to avoid downloading the entire file. See more info at:
    http://www.cogeo.org/in-depth.html
    """
    bound = bounds(*[int(t) for t in tile.split('-')])
    imagery_offset = kwargs.get('imagery_offset') or [0, 0]
    with rasterio.open(imagery) as src:
        x_res, y_res = src.transform[0], src.transform[4]

        # offset our imagery in the "destination pixel" space
        offset_bound = dict()
        deg_per_pix_x = (bound.west - bound.east) / 256
        deg_per_pix_y = (bound.north - bound.south) / 256

        offset_bound['west'] = bound.west + imagery_offset[0] * deg_per_pix_x
        offset_bound['east'] = bound.east + imagery_offset[0] * deg_per_pix_x
        offset_bound['north'] = bound.north + imagery_offset[1] * deg_per_pix_y
        offset_bound['south'] = bound.south + imagery_offset[1] * deg_per_pix_y

        # project tile boundaries from lat/lng to source CRS
        x, y = transform(WGS84_CRS, src.crs, [offset_bound['west']],
                         [offset_bound['north']])
        tile_ul_proj = x[0], y[0]

        x, y = transform(WGS84_CRS, src.crs, [offset_bound['east']],
                         [offset_bound['south']])
        tile_lr_proj = x[0], y[0]

        # get origin point from the TIF
        tif_ul_proj = (src.bounds.left, src.bounds.top)

        # use the above information to calculate the pixel indices of the window
        top = int((tile_ul_proj[1] - tif_ul_proj[1]) / y_res)
        left = int((tile_ul_proj[0] - tif_ul_proj[0]) / x_res)
        bottom = int((tile_lr_proj[1] - tif_ul_proj[1]) / y_res)
        right = int((tile_lr_proj[0] - tif_ul_proj[0]) / x_res)

        window = ((top, bottom), (left, right))

        # read the first three bands (assumed RGB) of the TIF into an array
        data = np.empty(shape=(3, 256, 256)).astype(src.profile['dtype'])
        for k in (1, 2, 3):
            src.read(k, window=window, out=data[k - 1], boundless=True)

        # save
        tile_img = op.join(folder, '{}{}'.format(tile, '.jpg'))
        img = Image.fromarray(np.moveaxis(data, 0, -1), mode='RGB')
        img.save(tile_img)

    return tile_img
Пример #6
0
def test_transform():
    """2D and 3D."""
    WGS84_crs = CRS.from_epsg(4326)
    WGS84_points = ([12.492269], [41.890169], [48.])
    ECEF_crs = CRS.from_epsg(4978)
    ECEF_points = ([4642610.], [1028584.], [4236562.])
    ECEF_result = transform(WGS84_crs, ECEF_crs, *WGS84_points)
    assert np.allclose(np.array(ECEF_result), np.array(ECEF_points))

    UTM33_crs = CRS.from_epsg(32633)
    UTM33_points = ([291952], [4640623])
    UTM33_result = transform(WGS84_crs, UTM33_crs, *WGS84_points[:2])
    assert np.allclose(np.array(UTM33_result), np.array(UTM33_points))
Пример #7
0
def test_transform():
    """2D and 3D"""
    WGS84_crs = {'init': 'EPSG:4326'}
    WGS84_points = ([12.492269], [41.890169], [48.])
    ECEF_crs = {'init': 'EPSG:4978'}
    ECEF_points = ([4642610.], [1028584.], [4236562.])
    ECEF_result = transform(WGS84_crs, ECEF_crs, *WGS84_points)
    assert numpy.allclose(numpy.array(ECEF_result), numpy.array(ECEF_points))

    UTM33_crs = {'init': 'EPSG:32633'}
    UTM33_points = ([291952], [4640623])
    UTM33_result = transform(WGS84_crs, UTM33_crs, *WGS84_points[:2])
    assert numpy.allclose(numpy.array(UTM33_result), numpy.array(UTM33_points))
Пример #8
0
def test_transform():
    """2D and 3D."""
    WGS84_crs = {"init": "epsg:4326"}
    WGS84_points = ([12.492269], [41.890169], [48.])
    ECEF_crs = {"init": "epsg:4978"}
    ECEF_points = ([4642610.], [1028584.], [4236562.])
    ECEF_result = transform(WGS84_crs, ECEF_crs, *WGS84_points)
    assert np.allclose(np.array(ECEF_result), np.array(ECEF_points))

    UTM33_crs = {"init": "epsg:32633"}
    UTM33_points = ([291952], [4640623])
    UTM33_result = transform(WGS84_crs, UTM33_crs, *WGS84_points[:2])
    assert np.allclose(np.array(UTM33_result), np.array(UTM33_points))
Пример #9
0
def test_transform():
    """2D and 3D."""
    WGS84_crs = {'init': 'EPSG:4326'}
    WGS84_points = ([12.492269], [41.890169], [48.])
    ECEF_crs = {'init': 'EPSG:4978'}
    ECEF_points = ([4642610.], [1028584.], [4236562.])
    ECEF_result = transform(WGS84_crs, ECEF_crs, *WGS84_points)
    assert np.allclose(np.array(ECEF_result), np.array(ECEF_points))

    UTM33_crs = {'init': 'EPSG:32633'}
    UTM33_points = ([291952], [4640623])
    UTM33_result = transform(WGS84_crs, UTM33_crs, *WGS84_points[:2])
    assert np.allclose(np.array(UTM33_result), np.array(UTM33_points))
Пример #10
0
    def point(
        self,
        coordinates: Tuple[float, float],
        coord_crs: CRS = WGS84_CRS,
        **kwargs: Any,
    ) -> List:
        """
        Read point value from a COG.

        Attributes
        ----------
            coordinates : tuple
                (X, Y) coordinates.
            coord_crs : rasterio.crs.CRS, optional
                (X, Y) coordinate system. Default is WGS84/EPSG:4326.
            kwargs : Any, optional
                Additional options to forward to src_dst.sample()

        Returns
        -------
            list : List

        """
        lon, lat = transform(coord_crs, self.src_dst.crs, [coordinates[0]],
                             [coordinates[1]])
        return list(self.src_dst.sample([(lon[0], lat[0])],
                                        **kwargs))[0].tolist()
Пример #11
0
def get_bounding_box_from_draw(raster, dc):
    """
    returns bounding box in a image
    :param raster: displayed raster (rasterio image)
    :param dc: drawcontrol ipyleaflet
    """
    try:
        # Get last draw from the map
        coordinates = np.array(dc.last_draw['geometry']['coordinates'][0])

        # lon, lat to Sentinel-2 coordinate reference system
        lon_min_max = [np.amin(coordinates[:, 0]), np.amax(coordinates[:, 0])]
        lat_min_max = [np.amin(coordinates[:, 1]), np.amax(coordinates[:, 1])]
        lons, lats = np.meshgrid(lon_min_max, lat_min_max)
        xs, ys = transform({'init': 'EPSG:4326'}, raster.crs, lons.flatten(),
                           lats.flatten())

        # Get the region of interest in the image
        rows, cols = [], []
        for x, y in zip(xs, ys):
            row, col = ~raster.affine * (x, y)
            rows.append(row)
            cols.append(col)
        row_min, row_max = np.amin(rows), np.amax(rows)
        col_min, col_max = np.amin(cols), np.amax(cols)
        startx, starty = map(lambda v: int(np.floor(v)), [col_min, row_min])
        endx, endy = map(lambda v: int(np.ceil(v)), [col_max, row_max])
        print("Bounding box computed")
    except:
        print("Draw a polygon in the displayed map")
        startx, starty, endx, endy = None, None, None, None
    return startx, starty, endx, endy
Пример #12
0
def point_handler(
    url: str,
    lon: float,
    lat: float,
    indexes: Union[str, Tuple[int]] = None,
) -> Tuple[str, str, str]:
    """Handle /point requests."""
    if isinstance(indexes, str):
        indexes = tuple(int(s) for s in re.findall(r"\d+", indexes))

    if isinstance(lon, str):
        lon = float(lon)

    if isinstance(lat, str):
        lat = float(lat)

    with rasterio.Env(aws_session):
        with rasterio.open(url) as src_dst:
            lon_srs, lat_srs = warp.transform("epsg:4326", src_dst.crs, [lon],
                                              [lat])

            if not ((src_dst.bounds[0] < lon_srs[0] < src_dst.bounds[2]) and
                    (src_dst.bounds[1] < lat_srs[0] < src_dst.bounds[3])):
                raise TilerError("Point is outside the raster bounds")

            indexes = indexes if indexes is not None else src_dst.indexes
            values = list(
                src_dst.sample([(lon_srs[0], lat_srs[0])],
                               indexes=indexes))[0].tolist()

    meta = {"coordinates": [lon, lat], "values": values}
    return ("OK", "application/json", json.dumps(meta))
Пример #13
0
    def load_dem(self, dem_file):
        # install using `conda install -c conda-forge rastrio`
        wgs84 = CRS.from_epsg(4326)

        with rs.open(dem_file) as ds:
            top, left, bottom, right = self.bounds
            top, bottom = int(ds.height * top), int(ds.height * bottom)
            left, right = int(ds.width * left), int(ds.width * right)

            xx, yy = np.meshgrid(np.arange(left, right),
                                 np.arange(top, bottom))
            alt = ds.read(1)[top:bottom, left:right]
            lon, lat = ds.xy(yy, xx)
            lon, lat, alt = transform(
                ds.crs, wgs84,
                *map(lambda x: np.array(x).flatten(), (lon, lat, alt)))

        # from https://proj.org/operations/conversions/topocentric.html
        # should work since proj version 8, gives errors here though
        #
        # lc = CRS.from_proj4(('cct -d 3 +proj=pipeline +step +proj=cart +ellps=WGS84 '
        #                     + '+step +proj=topocentric +ellps=WGS84 +lat_0=%f +lon_0=%f +h_0=%f') % self.coord0)

        # now going first to wgs84 and then using pygeodesy, which is very slow but luckily need to do only once
        lc = LocalCartesian(*self.coord0)
        dem = np.zeros((len(lon), 3), dtype=np.float32)
        for i, (lat_, lon_, alt_) in enumerate(zip(lat, lon, alt)):
            xyz = lc.forward(lat_, lon_, alt_)
            dem[i, :] = xyz.xyz

        # transform to correct coordinate frame (now x east, y north, z up => x east, y south, z down)
        dem = tools.q_times_mx(self.w2c.quat.conj(), dem)
        dem = dem.reshape((bottom - top, right - left, 3))
        return dem
Пример #14
0
    def createGeoJSONtoExport(self):
        if self.gj_loaded != "":
            return
        nodes_gj = []  # supported format to create geojson (epsg:4326)
        for point in self.roi_coords:
            xy = self.raster.xy(
                self.roi_coords[self.roi_coords.index(point)].y() - 0.5,
                self.roi_coords[self.roi_coords.index(point)].x() - 0.5)
            nodes_gj.append(xy[0])
            nodes_gj.append(xy[1])
        nodes_gj.append(nodes_gj[0])
        nodes_gj.append(nodes_gj[1])

        ys, xs = warp.transform(self.raster.crs, {'init': 'epsg:4326'},
                                nodes_gj[::2], nodes_gj[1::2])
        nodes_proj = []
        for i in range(0, len(ys)):
            nodes_proj.append([ys[i], xs[i]])
        geojson = """{"type": "FeatureCollection", "features": [{"type": "Feature", "properties": {}, "geometry":
                        {"type": "Polygon", "coordinates": [""" + str(
            nodes_proj) + """]}}]}"""

        if self.createGeoJSONDir():
            with open(
                    Control.dirname + "/Output_data/GeoJSON/" +
                    str(self.roi_id) + ".geojson", "w") as gj:
                gj.write(geojson)
                gj.close()
Пример #15
0
def read_raster(filename, out_crs="EPSG:3857", use_z=False):
    """Read a raster to a ``pyvista.StructuredGrid``.

    This will handle coordinate transformations.
    """
    # Read in the data
    data = xr.open_rasterio(filename)
    values = np.asarray(data)
    nans = values == data.nodatavals
    if np.any(nans):
        # values = np.ma.masked_where(nans, values)
        values[nans] = np.nan
    # Make a mesh
    xx, yy = np.meshgrid(data["x"], data["y"])
    if use_z and values.shape[0] == 1:
        # will make z-comp the values in the file
        zz = values.reshape(xx.shape)
    else:
        # or this will make it flat
        zz = np.zeros_like(xx)
    mesh = pv.StructuredGrid(xx, yy, zz)
    pts = mesh.points
    lon, lat = transform(data.crs, out_crs, pts[:, 0], pts[:, 1])
    mesh.points[:, 0] = lon
    mesh.points[:, 1] = lat
    mesh["data"] = values.reshape(mesh.n_points, -1, order="F")
    return mesh
Пример #16
0
 def _get_point(self, src_path: str, coordinates: Tuple[float, float]) -> dict:
     with rasterio.open(src_path) as src_dst:
         lon_srs, lat_srs = transform(
             "EPSG:4326", src_dst.crs, [coordinates[0]], [coordinates[1]]
         )
         return list(
             src_dst.sample([(lon_srs[0], lat_srs[0])], indexes=src_dst.indexes)
         )[0].tolist()
Пример #17
0
 def worker(address):
     """Worker."""
     with rasterio.open(address) as band:
         lon_srs, lat_srs = warp.transform("EPSG:4326", band.crs,
                                           [coordinates[0]],
                                           [coordinates[1]])
         point = list(band.sample([(lon_srs[0], lat_srs[0])]))[0]
     return point[0]
Пример #18
0
def point_value(url, coordinates, indexes=None):
    """
    Handle /point requests.

    Note: All the querystring parameters are translated to function keywords
    and passed as string value by lambda_proxy

    Attributes
    ----------
    url : str, required
        Dataset url to read from.
    coordinates : str, required
        Comma separated longitude,latitude values.
    indexes : str, optional, (defaults: None)
        Comma separated band index number (e.g "1,2,3").

    Returns
    -------
    status : str
        Status of the request (e.g. OK, NOK).
    MIME type : str
        response body MIME type (e.g. image/jpeg).
    body : bytes
        String encoded json point value

    """
    if indexes is not None and isinstance(indexes, str):
        indexes = tuple(int(s) for s in re.findall(r"\d+", indexes))

    coordinates = list(map(float, coordinates.split(",")))
    with rasterio.open(url) as src_dst:
        indexes = indexes if indexes is not None else src_dst.indexes
        lon_srs, lat_srs = warp.transform("EPSG:4326", src_dst.crs,
                                          [coordinates[0]], [coordinates[1]])
        results = list(
            src_dst.sample([(lon_srs[0], lat_srs[0])], indexes=indexes))[0]

        def _get_name(idx):
            name = src_dst.descriptions[idx - 1]
            if not name:
                name = f"band{idx}"
            return name

        band_descriptions = [(ix, _get_name(ix)) for ix in indexes]

    return (
        "OK",
        "application/json",
        json.dumps({
            "address": url,
            "coordinates": coordinates,
            "band_descriptions": band_descriptions,
            "values":
            {b[0]: r
             for b, r in zip(band_descriptions, results.tolist())}
        }),
    )
Пример #19
0
def point(
    src_dst: Union[DatasetReader, DatasetWriter, WarpedVRT],
    coordinates: Tuple[float, float],
    indexes: Optional[Union[Sequence[int], int]] = None,
    coord_crs: CRS = constants.WGS84_CRS,
    unscale: bool = False,
) -> List:
    """
    Read point value

    Attributes
    ----------
        src_dst : rasterio.io.DatasetReader
            rasterio.io.DatasetReader object
        coordinates : tuple
            (X, Y) coordinates.
        indexes : list of ints or a single int, optional
            Band indexes
        coord_crs : rasterio.crs.CRS, optional
            (X, Y) coordinate system. Default is WGS84/EPSG:4326.
        unscale, bool, optional
            If True, apply scale and offset to the data.
            Default is set to False.
        kwargs : Any, optional
            Additional options to forward to src_dst.sample()

    Returns
    -------
        point : list
            List of pixel values per bands indexes.

    """
    if isinstance(indexes, int):
        indexes = (indexes, )

    lon, lat = transform(coord_crs, src_dst.crs, [coordinates[0]],
                         [coordinates[1]])
    if not ((src_dst.bounds[0] < lon[0] < src_dst.bounds[2]) and
            (src_dst.bounds[1] < lat[0] < src_dst.bounds[3])):
        raise Exception("Point is outside dataset bounds")

    indexes = indexes if indexes is not None else src_dst.indexes

    point_values = list(src_dst.sample([(lon[0], lat[0])], indexes=indexes))[0]

    if unscale:
        point_values = point_values.astype("float32", casting="unsafe")
        numpy.multiply(point_values,
                       src_dst.scales[0],
                       out=point_values,
                       casting="unsafe")
        numpy.add(point_values,
                  src_dst.offsets[0],
                  out=point_values,
                  casting="unsafe")

    return point_values.tolist()
Пример #20
0
def convertPointCrs(lon,
                    lat,
                    orgCrs=CRS.from_epsg(4326),
                    destCrs=CRS.from_epsg(4326)):
    """Do the crs convertion of a point"""
    lonConv, latConv = transform(orgCrs, destCrs, [lon], [lat])
    lonConv = lonConv[0]
    latConv = latConv[0]
    return lonConv, latConv
Пример #21
0
def geojson_reproject(feature, srid_in, srid_out):
    """Reproject GeoJSON Polygon feature coords
       Inspired by: https://gist.github.com/dnomadb/5cbc116aacc352c7126e779c29ab7abe
    """

    if feature["geometry"]["type"] == "Polygon":
        xys = (zip(*ring) for ring in feature["geometry"]["coordinates"])
        xys = (list(zip(*transform(CRS.from_epsg(srid_in), CRS.from_epsg(srid_out), *xy))) for xy in xys)

        yield {"coordinates": list(xys), "type": "Polygon"}
def get_elevation(lat_lon, image):
    results = []

    lat = lat_lon[0]
    lon = lat_lon[1]
    new_coo = transform(WGS84, epsg_27700, xs=[lon], ys=[lat])
    vals = image.sample(((new_coo[0][0], new_coo[1][0]), ))
    for val in vals:
        results.append({"lat": lat, "lon": lon, "elevation": val[0]})
    return results
Пример #23
0
def geojson_to_mercator(feature):
    """Convert GeoJSON Polygon feature coords to Mercator (i.e EPSG:3857).
       Inspired by: https://gist.github.com/dnomadb/5cbc116aacc352c7126e779c29ab7abe
    """

    # FIXME: We assume that GeoJSON input coordinates can't be anything else than EPSG:4326
    if feature["geometry"]["type"] == "Polygon":
        xys = (zip(*ring) for ring in feature["geometry"]["coordinates"])
        xys = (list(zip(*transform(CRS.from_epsg(4326), CRS.from_epsg(3857), *xy))) for xy in xys)

        yield {"coordinates": list(xys), "type": "Polygon"}
Пример #24
0
def transform_bounds(boundsArr, crs):
    if not crs:
        raise ValueError('Input raster must have a CRS')

    if 'init' in crs and crs['init'] == 'epsg:4326':
        boundsArr[:, 0] = _wrap_x_coord(boundsArr[:, 0])
    else:
        boundsArr = np.dstack(
            warp.transform(crs, {'init': 'epsg:4326'}, boundsArr[:, 0],
                           boundsArr[:, 1]))[0]

    return boundsArr
Пример #25
0
def dest_affine(affine, src_crs, shape):
    from rasterio.warp import transform
    corners = [(0, 0), (0, shape[0]), (shape[1], shape[0]), (shape[1], 0)]
    corners = [affine * p for p in corners]
    crn = transform(src_crs, dst_crs, [p[0] for p in corners],
                    [p[1] for p in corners])

    y_pixel = abs(max(crn[1]) - min(crn[1])) / shape[0]
    x_pixel = abs(max(crn[0]) - min(crn[0])) / shape[1]
    dst_transform = (x_pixel, 0.0, min(crn[0]), 0.0, -y_pixel, max(crn[1]))

    return dst_transform
Пример #26
0
def get_tiles(zoom, input, dst_crs="EPSG:3857"):
    print("getting tiles for", input)
    input = input.replace("s3://", "/vsicurl/http://s3.amazonaws.com/")
    with rasterio.drivers():
        with rasterio.open(input) as src:
            # Compute the geographic bounding box of the dataset.
            (west, east), (south, north) = transform(
                src.crs, "EPSG:4326", src.bounds[::2], src.bounds[1::2])

            # Initialize an iterator over output tiles.
            return mercantile.tiles(
                west, south, east, north, range(zoom, zoom + 1))
Пример #27
0
def geojson_to_mercator(feature, epsg=4326):
    """Convert GeoJSON Polygon feature coords to Mercator (i.e EPSG:3857).
       Inspired by: https://gist.github.com/dnomadb/5cbc116aacc352c7126e779c29ab7abe
    """

    if feature["geometry"]["type"] == "Polygon":
        xys = (zip(*ring) for ring in feature["geometry"]["coordinates"])
        xys = (list(
            zip(*transform(CRS.from_epsg(int(epsg)), CRS.from_epsg(3857), *
                           xy))) for xy in xys)

        yield {"coordinates": list(xys), "type": "Polygon"}
Пример #28
0
def convert_cols_rows(fn, cols, rows,
                      dst_crs=rasterio.crs.CRS.from_epsg(4326)):
    with rasterio.open(fn) as ds:
        xs, ys = rasterio.transform.xy(ds.transform, rows, cols)
        xs, ys = np.array(xs), np.array(ys)
        lons, lats = warp.transform(ds.crs, dst_crs, xs.flatten(),
                                    ys.flatten())
        lons, lats = (
            np.array(lons).reshape(xs.shape),
            np.array(lats).reshape(ys.shape),
        )
        return xs, ys, lons, lats
Пример #29
0
def read_SWISS_SM(
        basepath='/mnt/CEPH_PROJECTS/ADO/SWI/reference_data/swiss_model/',
        format='tif'):
    # multidataset method
    # get file paths
    sm_files = list()
    date_list = list()

    if format == 'tif':
        for path in Path(basepath).rglob('*.tif'):
            sm_files.append(path)
            date_list.append(dt.datetime.strptime(path.name[4:12], '%Y%m%d'))
    elif format == 'asc':
        for path in Path(basepath).rglob('*.asc'):
            sm_files.append(path)
            date_list.append(dt.datetime.strptime(path.name[4:12], '%Y%m%d'))

    # initiate sm stack
    tmp = xr.open_rasterio(basepath + 'fcp_20190101.tif')
    #del tmp['band']
    # coordinate transformation
    tmp.attrs['crs'] = 'EPSG:21781'
    ny, nx = len(tmp['y']), len(tmp['x'])
    x, y = np.meshgrid(tmp['x'], tmp['y'])
    lon, lat = transform(tmp.crs, {'init': 'EPSG:4326'}, x.flatten(),
                         y.flatten())
    lon = np.asarray(lon).reshape((ny, nx))
    lat = np.asarray(lat).reshape((ny, nx))
    tmp.coords['lon'] = (('y', 'x'), lon)
    tmp.coords['lat'] = (('y', 'x'), lat)

    stack = xr.DataArray(np.full((365, len(lat[:, 0]), len(lon[0, :])),
                                 -9999.0),
                         coords=[('time', date_list), ('lat', lat[:, 0]),
                                 ('lon', lon[0, :])],
                         name='SM_2019')
    tmp.close()
    tmp = None

    # read all sm files
    sm_data_list = list()
    for (path, date) in zip(sm_files, date_list):

        if format == 'tif':
            tmp = xr.open_rasterio(path)
            stack.loc[dict(time=date)] = tmp.values.squeeze()
            tmp.close()
        elif format == 'asc':
            tmp = pd.read_csv(path, sep=" ", header=None, skiprows=6)
            stack.loc[dict(time=date)] = tmp.values

    return stack
Пример #30
0
def get_point_data(lat, lng, path):
    with rasterio.open(path) as src_dst:
        # Concert to source CRS.
        x, y = warp.transform("epsg:4326", src_dst.crs, [lng], [lat])
        # Check bounds.
        x_inside = min(src_dst.bounds.left, src_dst.bounds.right) < x[0] < \
                   max(src_dst.bounds.left, src_dst.bounds.right)
        y_inside = min(src_dst.bounds.bottom, src_dst.bounds.top) < y[0] < \
                   max(src_dst.bounds.bottom, src_dst.bounds.top)
        if not (x_inside and y_inside):
            raise InvalidArgumentsError('requested lat lon outside bounds')
        # Sample value.
        return list(src_dst.sample([(x[0], y[0])]))[0].tolist()[0]
Пример #31
0
    def lnglat(self, x: float, y: float, truncate=False) -> Coords:
        """Transform point(x,y) to longitude and latitude."""
        inside = point_in_bbox(Coords(x, y), self.xy_bbox)
        if not inside:
            warnings.warn("Point is outside TMS bounds.", UserWarning)

        xs, ys = transform(self.crs, WGS84_CRS, [x], [y])
        lng, lat = xs[0], ys[0]

        if truncate:
            lng, lat = truncate_lnglat(lng, lat)

        return Coords(lng, lat)
Пример #32
0
def add_lat_lon(da_in):
    ny, nx = len(da_in['y']), len(da_in['x'])
    x, y = np.meshgrid(da_in['x'], da_in['y'])

    # Rasterio works with 1D arrays
    lon, lat = transform(da_in.crs, {'init': 'EPSG:4326'}, x.flatten(),
                         y.flatten())
    lon = np.asarray(lon).reshape((ny, nx))
    lat = np.asarray(lat).reshape((ny, nx))
    da_in.coords['lon'] = (('y', 'x'), lon)
    da_in.coords['lat'] = (('y', 'x'), lat)

    return da_in
Пример #33
0
    def _get_boundaries(self, src, shape):

        self.output("Getting boundaries", normal=True, arrow=True)
        output = {'ul': {'x': [0, 0], 'y': [0, 0]},  # ul: upper left
                  'ur': {'x': [0, 0], 'y': [0, 0]},  # ur: upper right
                  'll': {'x': [0, 0], 'y': [0, 0]},  # ll: lower left
                  'lr': {'x': [0, 0], 'y': [0, 0]}}  # lr: lower right

        output['ul']['x'][0] = src['affine'][2]
        output['ul']['y'][0] = src['affine'][5]
        output['ur']['x'][0] = output['ul']['x'][0] + self.pixel * src['shape'][1]
        output['ur']['y'][0] = output['ul']['y'][0]
        output['ll']['x'][0] = output['ul']['x'][0]
        output['ll']['y'][0] = output['ul']['y'][0] - self.pixel * src['shape'][0]
        output['lr']['x'][0] = output['ul']['x'][0] + self.pixel * src['shape'][1]
        output['lr']['y'][0] = output['ul']['y'][0] - self.pixel * src['shape'][0]

        output['ul']['x'][1], output['ul']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['ul']['x'][0]],
                                                               [output['ul']['y'][0]])

        output['ur']['x'][1], output['ur']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['ur']['x'][0]],
                                                               [output['ur']['y'][0]])

        output['ll']['x'][1], output['ll']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['ll']['x'][0]],
                                                               [output['ll']['y'][0]])

        output['lr']['x'][1], output['lr']['y'][1] = transform(src['crs'], self.projection,
                                                               [output['lr']['x'][0]],
                                                               [output['lr']['y'][0]])

        dst_corner_ys = [output[k]['y'][1][0] for k in output.keys()]
        dst_corner_xs = [output[k]['x'][1][0] for k in output.keys()]
        y_pixel = abs(max(dst_corner_ys) - min(dst_corner_ys)) / shape[0]
        x_pixel = abs(max(dst_corner_xs) - min(dst_corner_xs)) / shape[1]

        return (min(dst_corner_xs), x_pixel, 0.0, max(dst_corner_ys), 0.0, -y_pixel)
Пример #34
0
def dest_affine(affine, src_crs, shape):
    from rasterio.warp import transform
    corners = [(0, 0), (0, shape[0]), (shape[1], shape[0]), (shape[1], 0)]
    corners = [affine * p for p in corners]
    crn = transform(src_crs, dst_crs, [p[0] for p in corners],
                                      [p[1] for p in corners])

    y_pixel = abs(max(crn[1]) - min(crn[1])) / shape[0]
    x_pixel = abs(max(crn[0]) - min(crn[0])) / shape[1]
    dst_transform = (x_pixel, 0.0, min(crn[0]),
                     0.0, -y_pixel, max(crn[1]))

    return dst_transform
Пример #35
0
def get_elevation(lat_lon, IMAGE_PATH):
    WGS84 = CRS.from_epsg(4326)
    epsg_27700 = CRS.from_epsg(27700)
    image = rasterio.open(IMAGE_PATH)
    results = []

    lat = lat_lon[0]
    lon = lat_lon[1]
    new_coo = transform(WGS84, epsg_27700, xs=[lon], ys=[lat])
    vals = image.sample(((new_coo[0][0], new_coo[1][0]), ))
    for val in vals:
        results.append({"lat": lat, "lon": lon, "elevation": val[0]})
    return results
Пример #36
0
def get_latlon(da):
    """Calculates lat, lon for grid"""
    ny, nx = len(da['y']), len(da['x'])
    x, y = np.meshgrid(da['x'], da['y'])

    lon, lat = transform(da.crs, {'init': 'EPSG:4326'}, x.flatten(),
                         y.flatten())
    lon = np.asarray(lon).reshape((ny, nx))
    lat = np.asarray(lat).reshape((ny, nx))

    da.coords['lon'] = (('y', 'x'), lon)
    da.coords['lat'] = (('y', 'x'), lat)

    return
Пример #37
0
    def _get_boundaries(self, src):

        self.output("Getting boundaries", normal=True, arrow=True)
        output = {
            "ul": {"x": [0, 0], "y": [0, 0]},  # ul: upper left
            "ur": {"x": [0, 0], "y": [0, 0]},  # ur: upper right
            "ll": {"x": [0, 0], "y": [0, 0]},  # ll: lower left
            "lr": {"x": [0, 0], "y": [0, 0]},
        }  # lr: lower right

        output["ul"]["x"][0] = src["affine"][2]
        output["ul"]["y"][0] = src["affine"][5]
        output["ur"]["x"][0] = output["ul"]["x"][0] + self.pixel * src["shape"][1]
        output["ur"]["y"][0] = output["ul"]["y"][0]
        output["ll"]["x"][0] = output["ul"]["x"][0]
        output["ll"]["y"][0] = output["ul"]["y"][0] - self.pixel * src["shape"][0]
        output["lr"]["x"][0] = output["ul"]["x"][0] + self.pixel * src["shape"][1]
        output["lr"]["y"][0] = output["ul"]["y"][0] - self.pixel * src["shape"][0]

        output["ul"]["x"][1], output["ul"]["y"][1] = transform(
            src["crs"], self.projection, [output["ul"]["x"][0]], [output["ul"]["y"][0]]
        )

        output["ur"]["x"][1], output["ur"]["y"][1] = transform(
            src["crs"], self.projection, [output["ur"]["x"][0]], [output["ur"]["y"][0]]
        )

        output["ll"]["x"][1], output["ll"]["y"][1] = transform(
            src["crs"], self.projection, [output["ll"]["x"][0]], [output["ll"]["y"][0]]
        )

        output["lr"]["x"][1], output["lr"]["y"][1] = transform(
            src["crs"], self.projection, [output["lr"]["x"][0]], [output["lr"]["y"][0]]
        )

        return output
def feature_to_mercator(feature):
    '''Normalize feature and converts coords to 3857.

    Args:
      feature: geojson feature to convert to mercator geometry.
    '''
    # Ref: https://gist.github.com/dnomadb/5cbc116aacc352c7126e779c29ab7abe

    src_crs = CRS.from_epsg(4326)
    dst_crs = CRS.from_epsg(3857)

    geometry = feature['geometry']
    if geometry['type'] == 'Polygon':
        xys = (zip(*part) for part in geometry['coordinates'])
        xys = (list(zip(*transform(src_crs, dst_crs, *xy))) for xy in xys)

        yield {'coordinates': list(xys), 'type': 'Polygon'}

    elif geometry['type'] == 'MultiPolygon':
        for component in geometry['coordinates']:
            xys = (zip(*part) for part in component)
            xys = (list(zip(*transform(src_crs, dst_crs, *xy))) for xy in xys)

            yield {'coordinates': list(xys), 'type': 'Polygon'}
Пример #39
0
def get_zoom(input, dst_crs="EPSG:3857"):
    input = input.replace("s3://", "/vsicurl/http://s3.amazonaws.com/")
    with rasterio.drivers():
        with rasterio.open(input) as src:
            # Compute the geographic bounding box of the dataset.
            (west, east), (south, north) = transform(
                src.crs, "EPSG:4326", src.bounds[::2], src.bounds[1::2])

            affine, _, _ = calculate_default_transform(src.crs, dst_crs,
                src.width, src.height, *src.bounds, resolution=None)

            # grab the lowest resolution dimension
            resolution = max(abs(affine[0]), abs(affine[4]))

            return int(round(math.log((2 * math.pi * 6378137) /
                                      (resolution * CHUNK_SIZE)) / math.log(2)))
Пример #40
0
def get_corners(src_crs, affine, shape, dst_crs):
    corners = [affine * p for p in corners_from_shape(shape)]
    return transform(src_crs, dst_crs,
            [p[0] for p in corners],
            [p[1] for p in corners])
Пример #41
0
def mbtiles(ctx, files, output_opt, title, description, layer_type,
            img_format, zoom_levels, image_dump, num_workers):
    """Export a dataset to MBTiles (version 1.1) in a SQLite file.

    The input dataset may have any coordinate reference system. It must
    have at least three bands, which will be become the red, blue, and
    green bands of the output image tiles.

    If no zoom levels are specified, the defaults are the zoom levels
    nearest to the one at which one tile may contain the entire source
    dataset.

    If a title or description for the output file are not provided,
    they will be taken from the input dataset's filename.

    This command is suited for small to medium (~1 GB) sized sources.

    Python package: rio-mbtiles (https://github.com/mapbox/rio-mbtiles).
    """

    verbosity = (ctx.obj and ctx.obj.get('verbosity')) or 1
    logger = logging.getLogger('rio')

    output, files = resolve_inout(files=files, output=output_opt)
    inputfile = files[0]

    with rasterio.drivers(CPL_DEBUG=verbosity > 2):

        # Read metadata from the source dataset.
        with rasterio.open(inputfile) as src:

            # Name and description.
            title = title or os.path.basename(src.name)
            description = description or src.name

            # Compute the geographic bounding box of the dataset.
            (west, east), (south, north) = transform(
                src.crs, 'EPSG:4326', src.bounds[::2], src.bounds[1::2])

        # Resolve the minimum and maximum zoom levels for export.
        if zoom_levels:
            minzoom, maxzoom = map(int, zoom_levels.split('..'))
        else:
            zw = int(round(math.log(360.0/(east-west), 2.0)))
            zh = int(round(math.log(170.1022/(north-south), 2.0)))
            minzoom = min(zw, zh)
            maxzoom = max(zw, zh)
        logger.debug("Zoom range: %d..%d", minzoom, maxzoom)

        # Parameters for creation of tile images.
        base_kwds = {
            'driver': img_format.upper(),
            'dtype': 'uint8',
            'nodata': 0,
            'height': 256,
            'width': 256,
            'count': 3,
            'crs': 'EPSG:3857'}

        img_ext = 'jpg' if img_format.lower() == 'jpeg' else 'png'

        # Initialize the sqlite db.
        if os.path.exists(output):
            os.unlink(output)
        conn = sqlite3.connect(output)
        cur = conn.cursor()
        cur.execute(
            "CREATE TABLE tiles "
            "(zoom_level integer, tile_column integer, "
            "tile_row integer, tile_data blob);")
        cur.execute(
            "CREATE TABLE metadata (name text, value text);")

        # Insert mbtiles metadata into db.
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("name", title))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("type", layer_type))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("version", "1.1"))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("description", description))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("format", img_ext))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("bounds", "%f,%f,%f,%f" % (west, south, east, north)))

        conn.commit()

        # Create a pool of workers to process tile tasks.
        pool = Pool(num_workers, init_worker, (inputfile, base_kwds), 100)

        # Constrain bounds.
        EPS = 1.0e-10
        west = max(-180+EPS, west)
        south = max(-85.051129, south)
        east = min(180-EPS, east)
        north = min(85.051129, north)

        # Initialize iterator over output tiles.
        tiles = mercantile.tiles(
            west, south, east, north, range(minzoom, maxzoom+1))

        for tile, contents in pool.imap_unordered(process_tile, tiles):

            # MBTiles has a different origin than Mercantile/tilebelt.
            tiley = int(math.pow(2, tile.z)) - tile.y - 1

            # Optional image dump.
            if image_dump:
                img_name = '%d-%d-%d.%s' % (
                    tile.x, tiley, tile.z, img_ext)
                img_path = os.path.join(image_dump, img_name)
                with open(img_path, 'wb') as img:
                    img.write(contents)

            # Insert tile into db.
            cur.execute(
                "INSERT INTO tiles "
                "(zoom_level, tile_column, tile_row, tile_data) "
                "VALUES (?, ?, ?, ?);",
                (tile.z, tile.x, tiley, buffer(contents)))

            conn.commit()

        conn.close()
Пример #42
0
def transform_coordinates(source_srs, target_srs, x, y):
    return tuple(i[0] for i in transform(source_srs, target_srs, x, y))
Пример #43
0
def get_corners(affine, src_crs, shape, dst_crs):
    corners = [(0,0), (0, shape[0]), (shape[1], shape[0]), (shape[1], 0)]
    corners = [affine * p for p in corners]
    return transform(src_crs, dst_crs, [p[0] for p in corners], [p[1] for p in corners])
Пример #44
0
import matplotlib.pyplot as plt
import numpy as np
from rasterio.warp import transform

import xarray as xr

# Read the data
url = 'https://github.com/mapbox/rasterio/raw/master/tests/data/RGB.byte.tif'
da = xr.open_rasterio(url)

# Compute the lon/lat coordinates with rasterio.warp.transform
ny, nx = len(da['y']), len(da['x'])
x, y = np.meshgrid(da['x'], da['y'])

# Rasterio works with 1D arrays
lon, lat = transform(da.crs, {'init': 'EPSG:4326'},
                     x.flatten(), y.flatten())
lon = np.asarray(lon).reshape((ny, nx))
lat = np.asarray(lat).reshape((ny, nx))
da.coords['lon'] = (('y', 'x'), lon)
da.coords['lat'] = (('y', 'x'), lat)

# Compute a greyscale out of the rgb image
greyscale = da.mean(dim='band')

# Plot on a map
ax = plt.subplot(projection=ccrs.PlateCarree())
greyscale.plot(ax=ax, x='lon', y='lat', transform=ccrs.PlateCarree(),
               cmap='Greys_r', add_colorbar=False)
ax.coastlines('10m', color='r')
plt.show()
Пример #45
0
def mbtiles(ctx, files, output, overwrite, title, description,
            layer_type, img_format, tile_size, zoom_levels, image_dump,
            num_workers, src_nodata, dst_nodata, resampling, rgba):
    """Export a dataset to MBTiles (version 1.1) in a SQLite file.

    The input dataset may have any coordinate reference system. It must
    have at least three bands, which will be become the red, blue, and
    green bands of the output image tiles.

    An optional fourth alpha band may be copied to the output tiles by
    using the --rgba option in combination with the PNG format. This
    option requires that the input dataset has at least 4 bands.

    If no zoom levels are specified, the defaults are the zoom levels
    nearest to the one at which one tile may contain the entire source
    dataset.

    If a title or description for the output file are not provided,
    they will be taken from the input dataset's filename.

    This command is suited for small to medium (~1 GB) sized sources.

    Python package: rio-mbtiles (https://github.com/mapbox/rio-mbtiles).
    """
    output, files = resolve_inout(files=files, output=output,
                                  overwrite=overwrite)
    inputfile = files[0]

    log = logging.getLogger(__name__)

    with ctx.obj['env']:

        # Read metadata from the source dataset.
        with rasterio.open(inputfile) as src:

            validate_nodata(dst_nodata, src_nodata, src.profile.get('nodata'))
            base_kwds = {'dst_nodata': dst_nodata, 'src_nodata': src_nodata}

            if src_nodata is not None:
                base_kwds.update(nodata=src_nodata)

            if dst_nodata is not None:
                base_kwds.update(nodata=dst_nodata)

            # Name and description.
            title = title or os.path.basename(src.name)
            description = description or src.name

            # Compute the geographic bounding box of the dataset.
            (west, east), (south, north) = transform(
                src.crs, 'EPSG:4326', src.bounds[::2], src.bounds[1::2])

        # Resolve the minimum and maximum zoom levels for export.
        if zoom_levels:
            minzoom, maxzoom = map(int, zoom_levels.split('..'))
        else:
            zw = int(round(math.log(360.0 / (east - west), 2.0)))
            zh = int(round(math.log(170.1022 / (north - south), 2.0)))
            minzoom = min(zw, zh)
            maxzoom = max(zw, zh)

        log.debug("Zoom range: %d..%d", minzoom, maxzoom)

        if rgba:
            if img_format == 'JPEG':
                raise click.BadParameter("RGBA output is not possible with JPEG format.")
            else:
                count = 4
        else:
            count = 3

        # Parameters for creation of tile images.
        base_kwds.update({
            'driver': img_format.upper(),
            'dtype': 'uint8',
            'nodata': 0,
            'height': tile_size,
            'width': tile_size,
            'count': count,
            'crs': TILES_CRS})

        img_ext = 'jpg' if img_format.lower() == 'jpeg' else 'png'

        # Initialize the sqlite db.
        if os.path.exists(output):
            os.unlink(output)

        # workaround for bug here: https://bugs.python.org/issue27126
        sqlite3.connect(':memory:').close()

        conn = sqlite3.connect(output)
        cur = conn.cursor()
        cur.execute(
            "CREATE TABLE tiles "
            "(zoom_level integer, tile_column integer, "
            "tile_row integer, tile_data blob);")
        cur.execute(
            "CREATE TABLE metadata (name text, value text);")

        # Insert mbtiles metadata into db.
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("name", title))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("type", layer_type))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("version", "1.1"))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("description", description))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("format", img_ext))
        cur.execute(
            "INSERT INTO metadata (name, value) VALUES (?, ?);",
            ("bounds", "%f,%f,%f,%f" % (west, south, east, north)))

        conn.commit()

        # Create a pool of workers to process tile tasks.
        pool = Pool(num_workers, init_worker,
                    (inputfile, base_kwds, resampling), 100)

        # Constrain bounds.
        EPS = 1.0e-10
        west = max(-180 + EPS, west)
        south = max(-85.051129, south)
        east = min(180 - EPS, east)
        north = min(85.051129, north)

        # Initialize iterator over output tiles.
        tiles = mercantile.tiles(
            west, south, east, north, range(minzoom, maxzoom + 1))

        for tile, contents in pool.imap_unordered(process_tile, tiles):

            if contents is None:
                log.info("Tile %r is empty and will be skipped", tile)
                continue

            # MBTiles have a different origin than Mercantile/tilebelt.
            tiley = int(math.pow(2, tile.z)) - tile.y - 1

            # Optional image dump.
            if image_dump:
                img_name = '%d-%d-%d.%s' % (
                    tile.x, tiley, tile.z, img_ext)
                img_path = os.path.join(image_dump, img_name)
                with open(img_path, 'wb') as img:
                    img.write(contents)

            # Insert tile into db.
            cur.execute(
                "INSERT INTO tiles "
                "(zoom_level, tile_column, tile_row, tile_data) "
                "VALUES (?, ?, ?, ?);",
                (tile.z, tile.x, tiley, sqlite3.Binary(contents)))

            conn.commit()

        conn.close()
Пример #46
0
def test_transform_src_crs_none():
    with pytest.raises(CRSError):
        transform(None, WGS84_crs, [], [])
Пример #47
0
def test_transform_dst_crs_none():
    with pytest.raises(CRSError):
        transform(WGS84_crs, None, [], [])