Пример #1
0
    def get_export(self, crs='EPSG:4326', scale=10):
        '''Export NDVI year compositions as .tif to your local folder.
        This method calls geemap.ee_export_image.
        
        Args:
            crs (string): Coordinate Reference System of the output tifs. Use EPSG style e.g. "EPSG:4326"; "EPSG:32629"
            scale (int): Value for pixel size of your output tifs, default is 10 because default sat is Sentinel 2 NDVI,
                with bands 8 and 4 (10 m pix/resolution). In case you choose Landsat yous should change scale to 30. 
                You can also considerer use this parameter like resample in case you get a size limitation error
                when try to download a big area. 
        Returns:
          object(tif): 4 bands ndvi_year.tif per year in your ndvi collection, downloaded at your current working directory 
          '''

        self.imagelist = []
        self.get_year_composite()

        count = (len(self.imagelist))
        print(count)

        for n in range(count):
            year = self.start_year + n
            image = self.imagelist[n]
            name = 'ndvi_' + str(year) + '.tif'
            filename = os.path.join(os.getcwd(), name)
            print('Exporting {}'.format(filename), '\n')
            geemap.ee_export_image(image,
                                   filename=filename,
                                   scale=scale,
                                   crs=crs,
                                   region=self.roi,
                                   file_per_band=False)

        print('All the images in the ndvi collection have been exported')
Пример #2
0
    def get_export_single(self,
                          image,
                          name='mycomposition.tif',
                          crs='EPSG:4326',
                          scale=10):
        '''Export single composition as .tif to your local folder. So long as we can do really nice
        multiseasonal composites, e.g. median seasonal NDVI for whole Africa between 2001 and 2020. 
        I thought that would be interesting to have the chance to export this composites.
        This method calls geemap.ee_export_image.
        
        Args:
            crs (string): Coordinate Reference System of the output tifs. Use EPSG style e.g. "EPSG:4326"; "EPSG:32629"
            scale (int): Value for pixel size of your output tifs, default is 10 because default sat is Sentinel 2 NDVI,
                with bands 8 and 4 (10 m pix/resolution). In case you choose Landsat yous should change scale to 30. 
                You can also considerer use this parameter like resample in case you get a size limitation error
                when try to download a big area. 
        Returns:
          object(tif): 4 bands mycompositon.tif, with max, median or perc_90 for the period you chosen, 
          downloaded at your current working directory 
          '''

        filename = os.path.join(os.getcwd(), name)
        geemap.ee_export_image(image,
                               filename=filename,
                               scale=scale,
                               crs=crs,
                               region=self.roi,
                               file_per_band=False)

        print('Image have been exported')
Пример #3
0
def export(layer, name):
    out_dir = output_directory
    name = name.replace('/', '_')
    name = name + '.tif'
    filename = os.path.join(out_dir, name)
    if clipper == None:
        geemap.ee_export_image(layer,
                               filename=filename,
                               crs=epsg_code,
                               scale=output_scale)
    else:
        geemap.ee_export_image(layer,
                               filename=filename,
                               region=clipper,
                               crs=epsg_code,
                               scale=output_scale)
Пример #4
0
    def exportpoint(self, szid, eepoint, verbose=False):
        """
        """
        eeimagecollectionofstacks = self._getexportimage(eepoint,
                                                         verbose=verbose)

        #
        #    exportimage is unbounded. we'll clip it to the region specified when instantiating the GEEExport,
        #    hoping this will give results consistent with the image tif obtained via exportpointtofile/exportpointtodrive
        #    (by clipping, its footprint and geometry seem to be updated to our region)
        #
        #         print ("- exportpoint image - footprint", exportimage.get('system:footprint').getInfo())   # None
        #         print ("- exportpoint image - geometry",  exportimage.geometry().getInfo())                # unbound ( [[[-180, -90], [180, -90]...)
        #         print ("- exportpoint image - 'region'",  exportimage.get('region').getInfo())             # our eeregion
        #         exportimage = exportimage.clip(exportimage.get('region'))
        #         print ("- clipped image - footprint", exportimage.get('system:footprint').getInfo())       # our eeregion
        #         print ("- clipped image - geometry",  exportimage.geometry().getInfo())                    # our eeregion
        #         print ("- clipped image - 'region'",  exportimage.get('region').getInfo())                 # our eeregion

        eeimagecollectionofstacks = eeimagecollectionofstacks.map(
            lambda eeimage: eeimage.clip(eeimage.get('region')))

        #
        #    test/debug purposes
        #
        if True:
            imageslist = eeimagecollectionofstacks.toList(
                eeimagecollectionofstacks.size())
            for iIdx in range(eeimagecollectionofstacks.size().getInfo()):
                exportimage = ee.Image(imageslist.get(iIdx))
                geemap.ee_export_image(
                    exportimage,
                    filename=
                    f"C:/Users/HAESEND/tmp/{str(szid) + '_' + str(type(self._geeproduct).__name__) + '_' + geeutils.szISO8601Date(self._eedatefrom) + '_' + geeutils.szISO8601Date(self._eedatetill) + '_' + exportimage.get('band').getInfo() }.tif",
                    scale=exportimage.projection().nominalScale(
                    ),  # this scale only will determine the pixel size of the ***exported*** image
                    region=exportimage.geometry(),
                    file_per_band=False)

        return eeimagecollectionofstacks
        if len(ee.Image(ilist.get(i)).bandNames().getInfo()) <= 0:
            print(
                "ERROR; No bands found in image index %d... will skip export."
                % (i))
        else:
            filename = "{}/{}/{}/{}.tif".format(OUTPATH, sitename, a_tile, i)
            temp_dir = "{}/{}/{}/".format(OUTPATH, sitename, a_tile)
            if not os.path.exists(temp_dir):
                os.mkdir(temp_dir)
            if os.path.exists(filename):
                print("Image {} already exists. Skipping...".format(i))
                next
            else:
                tic = time.time()
                print("Exporting Image %d" % (i))
                geemap.ee_export_image(ee.Image(ilist.get(i)).select('NDRE'),
                                       filename=filename,
                                       scale=20,
                                       region=poly,
                                       file_per_band=False)
                toc = time.time()
                hours, rem = divmod(toc - tic, 3600)
                mins, secs = divmod(rem, 60)
                print("Time elapsed: {:0>2}:{:0>2}:{:05.2f}".format(
                    int(hours), int(mins), secs))
toc1 = time.time()
hrs1, rem1 = divmod(toc1 - tic1, 3600)
mins1, secs1 = divmod(rem1, 60)
print("Total time elapsed: {:0>2}:{:0>2}:{:05.2f}".format(
    int(hrs1), int(mins1), secs1))
Пример #6
0
    def exportpointtofile(self, szid, eepoint, szdstpath, verbose=False):
        """
        :param szdstpath: destination filename or director name.
        
        in case szdstpath is an existing directory, a default filename will be generated,
        otherwise, in case the parent directory of szdstpath  is an existing directory, szdstpath will be considered as a base filename,
        otherwise an exception is raised
        """
        #
        #    filenames filenames filenames... I hate filenames...
        #
        szdstpath = os.path.normpath(szdstpath)
        if os.path.isdir(szdstpath):
            szbasefilename = os.path.join(
                szdstpath,
                (str(szid) + '_' + str(type(self._geeproduct).__name__) + '_' +
                 geeutils.szISO8601Date(self._eedatefrom) + '_' +
                 geeutils.szISO8601Date(self._eedatetill)))
        elif os.path.isdir(os.path.dirname(szdstpath)):
            szbasefilename = szdstpath
        else:
            raise ValueError(f"invalid szdstpath ({szdstpath})")
        if szbasefilename.lower().endswith(".tif"):
            szbasefilename = szbasefilename[:-4]
        if verbose:
            print(
                f"{str(type(self).__name__)}.exportpointtofile: base filename: {szbasefilename}"
            )

        eeimagecollectionofstacks = self._getexportimage(eepoint,
                                                         verbose=verbose)
        imageslist = eeimagecollectionofstacks.toList(
            eeimagecollectionofstacks.size())
        for iIdx in range(eeimagecollectionofstacks.size().getInfo()):
            exportimage = ee.Image(imageslist.get(iIdx))
            exportband = exportimage.get('band').getInfo()
            eeregion = ee.Geometry(exportimage.get('region'))
            #
            #    and Yet Again: Terminal Touching pixels will be exported. Shinking the original roi with 1% of its pixel size... and pray.
            #    TODO: implement in exportpointtodrive too
            #
            exportregion = eeregion.buffer(-0.01,
                                           proj=exportimage.projection())
            if verbose:
                eeregionpixelcount = exportimage.select(0).unmask(
                    sameFootprint=False).reduceRegion(ee.Reducer.count(),
                                                      eeregion)
                exportregionpixelcount = exportimage.select(0).unmask(
                    sameFootprint=False).reduceRegion(ee.Reducer.count(),
                                                      exportregion)
                print(
                    f"{str(type(self).__name__)}.exportpointtofile (earliest image band {exportband} in stack):"
                )
                print(
                    f"- actual region: {geeutils.szprojectioninfo(eeregion)}")
                print(f"- area: {eeregion.area(maxError=0.001).getInfo()}")
                print(
                    f"- covering {eeregionpixelcount.getInfo()} pixels in src image"
                )
                print(
                    f"- export region: {geeutils.szprojectioninfo(exportregion)}"
                )
                print(f"- area: {exportregion.area(maxError=0.001).getInfo()}")
                print(
                    f"- covering {exportregionpixelcount.getInfo()} pixels in src image"
                )
            #
            #    exportpointtofile is mainly for debug; works only for few bands ( < 100 ), small files, fast processes
            #
            szfilename = szbasefilename + "_" + exportband + ".tif"
            geemap.ee_export_image(
                exportimage,
                filename=szfilename,
                scale=exportimage.projection().nominalScale(
                ),  # this scale only will determine the pixel size of the ***exported*** image
                region=exportregion,
                file_per_band=False
            )  # the ***exported*** region which is just a teeny-tiny bit smaller than it should be.
            #
            #    some nursing due to quirks in ee.Image.getDownloadURL (current versions: ee 0.1.248, gee 0.8.12)
            #
            try:
                import osgeo.gdal
                src_ds = osgeo.gdal.Open(szfilename)
                dst_ds = src_ds.GetDriver().CreateCopy(szfilename + ".tmp.tif",
                                                       src_ds)
                #
                #    restore band descriptions which are mysteriously lost in the ee.Image.getDownloadURL (current versions: ee 0.1.248, gee 0.8.12)
                #
                lstbandnames = exportimage.bandNames().getInfo()
                for iband in range(src_ds.RasterCount):
                    dst_ds.GetRasterBand(iband + 1).SetDescription(
                        lstbandnames[iband])
                #
                #    qgis chokes on '-inf' which is default for masked values in Float32 and Float64 images (current versions: ee 0.1.248, gee 0.8.12)
                #
                datatype = dst_ds.GetRasterBand(1).DataType
                if (datatype == osgeo.gdalconst.GDT_Float32) or (
                        datatype == osgeo.gdalconst.GDT_Float64):
                    rasterArray = dst_ds.GetRasterBand(iband + 1).ReadAsArray()
                    rasterArray[rasterArray == -math.inf] = math.nan
                    dst_ds.GetRasterBand(iband + 1).WriteArray(rasterArray)
                    dst_ds.GetRasterBand(iband + 1).SetNoDataValue(math.nan)

                dst_ds = None
                src_ds = None
                os.remove(szfilename)
                os.rename(szfilename + ".tmp.tif", szfilename)

            except Exception as e:
                #
                #    happens all the time e.g. some file is open in qgis
                #
                print(
                    f"{str(type(self).__name__)}.exportpointtofile: updating band names FAILED with exception: {str(e)}"
                )
                pass

            #
            #    debug. export the shape file of the eeregion (and exportregion) too.
            #
            if verbose:  # yes. verbose. yes. if I verbose, I am debugging, ain't I?
                geemap.ee_to_shp(
                    ee.FeatureCollection(
                        [ee.Feature(eeregion),
                         ee.Feature(exportregion)]), szfilename[0:-4] + ".shp")
        #
        #
        #
        return eeimagecollectionofstacks
        'D:\samples',
        ee.Image(s2_all_.get(i)).get('PRODUCT_ID').getInfo())

    if not os.path.exists(saveFolder_):
        os.mkdir(saveFolder_)
    else:
        continue
    #if path.exists(filename):
    #    continue

    s2_mosaic = ee.Image(s2_all_.get(i)).clip(aoi)

    filename = os.path.join(saveFolder_, '10GSD.tif')
    geemap.ee_export_image(s2_mosaic.select(s2_bands_10),
                           filename=filename,
                           scale=10,
                           region=aoi,
                           crs=ee.Projection(epsg),
                           file_per_band=False)
    os.remove(filename[:-4] + ".zip")

    filename = os.path.join(saveFolder_, '20GSD.tif')
    geemap.ee_export_image(s2_mosaic.select(s2_bands_20),
                           filename=filename,
                           scale=20,
                           region=aoi,
                           crs=ee.Projection(epsg),
                           file_per_band=False)
    os.remove(filename[:-4] + ".zip")

    # url = s2_mosaic.getDownloadURL({
    # 'name':citySeason,# +'B'+str(i),
Пример #8
0
def GetBurnedArea(year, feature):
    """
    Function to get the burnt area and landuse from GEE. The input is the year you are interested in, and a feature of the AOI. 
    The output is a dictionary of the burnt area per lancover type and a .tif with the raster data of the burnt area.  
    """

    #import libraries
    import os
    import requests
    import rasterio
    from rasterio.plot import show
    from rasterio.features import shapes
    import pandas as pd
    import geopandas as gpd
    import matplotlib
    from matplotlib import pyplot as plt
    import gdal
    import ee
    import geemap

    #create folders if they are not present
    if not os.path.exists('data'): os.makedirs('data')
    if not os.path.exists('output'): os.makedirs('output')

    #filter GEE data based on year and select landcover.
    startdate = str(year) + '-01-01'
    enddate = str(year) + '-12-31'
    dataset = ee.ImageCollection('ESA/CCI/FireCCI/5_1').filterDate(
        str(startdate), str(enddate))
    burnedArea = dataset.select('LandCover')
    maxBA = burnedArea.max()

    #get feature geometry
    AOI = feature
    roi = AOI.geometry()

    #clip feature to GEE raster and save as a .tif
    image = maxBA.clip(AOI).unmask()
    filenameWGS = 'data/BA_' + str(year) + '.tif'
    geemap.ee_export_image(image,
                           filename=str(filenameWGS),
                           scale=250,
                           region=roi,
                           file_per_band=False)

    #reproject to tif to use it in calculations
    warp = gdal.Open(str(filenameWGS))
    filenameWM = str('data/BA_' + str(year) + 'WM.tif')
    b19 = gdal.Warp(filenameWM,
                    warp,
                    srcNodata=0,
                    dstNodata=0,
                    srcSRS='EPSG:4326',
                    dstSRS='EPSG:3395')
    del b19

    #Read raster into an array
    b19 = rasterio.open(filenameWM)
    array2 = b19.read(1)

    #calculate burnt area per landcover type and return a dictionary
    flat_list = [item for sublist in array2 for item in sublist]
    BurnedArea = dict((x, flat_list.count(x)) for x in set(flat_list))
    del BurnedArea[0]
    meta = b19.meta
    area = meta['transform'][0]**2 / 10000
    BurnedArea.update((x, y * area) for x, y in BurnedArea.items())

    dicti = {}
    Cropland = [10, 20, 30]
    Forest = [50, 60, 70, 80, 90, 100, 110, 170]
    Shrubland = [120, 180, 40]
    Grassland = [130, 150, 140]

    area = 0.0
    for k in Cropland:
        try:
            area += BurnedArea[k]
        except KeyError:
            continue
    dicti["Cropland"] = area

    area = 0.0
    for k in Forest:
        try:
            area += BurnedArea[k]
        except KeyError:
            continue
    dicti["Forest"] = area

    area = 0.0
    for k in Shrubland:
        try:
            area += BurnedArea[k]
        except KeyError:
            continue
    dicti["Shrubland"] = area

    area = 0.0
    for k in Grassland:
        try:
            area += BurnedArea[k]
        except KeyError:
            continue
    dicti["Grassland"] = area

    return (dicti)
Пример #9
0
            s2_masked = exportCloudFreeSen2(aoi, start_date, end_date)
            s2_masked = s2_masked.select(s2_bands)

            if m < 10:
                filename = os.path.join(
                    saveFolder_, feature['properties']['title'] + '_' +
                    str(year) + '_0' + str(m) + '.tif')
            else:
                filename = os.path.join(
                    saveFolder_, feature['properties']['title'] + '_' +
                    str(year) + '_' + str(m) + '.tif')

            geemap.ee_export_image(s2_masked,
                                   filename=filename,
                                   scale=10,
                                   region=aoi,
                                   crs=ee.Projection(epsg),
                                   file_per_band=False)

            os.remove(filename[:-4] + ".zip")

        start_date = ee.Date.fromYMD(year, 12, 1)
        end_date = ee.Date.fromYMD(year + 1, 1, 1)

        #s2 = ee.ImageCollection('COPERNICUS/S2') \
        #        .filterDate(start_date, end_date).select(s2_bands) \
        #        .filterBounds(aoi).median().clip(aoi)

        s2_masked = exportCloudFreeSen2(aoi, start_date, end_date)
        s2_masked = s2_masked.select(s2_bands)