web-dev-qa-db-fra.com

Obtenir la latitude et la longitude à partir d'un fichier GeoTIFF

En utilisant GDAL en Python, comment obtenir la latitude et la longitude d'un fichier GeoTIFF?

Les GeoTIFF ne semblent pas stocker d'informations de coordonnées. Au lieu de cela, ils stockent les coordonnées d'origine XY. Cependant, les coordonnées XY ne fournissent pas la latitude et la longitude du coin supérieur gauche et du coin inférieur gauche.

Il semble que j'aurai besoin de faire quelques calculs pour résoudre ce problème, mais je ne sais pas par où commencer.

Quelle procédure faut-il pour effectuer cette opération?

Je sais que la méthode GetGeoTransform() est importante pour cela, cependant, je ne sais pas quoi en faire à partir de là.

41
Phanto

Pour obtenir les coordonnées des coins de votre géotiff, procédez comme suit:

from osgeo import gdal
ds = gdal.Open('path/to/file')
width = ds.RasterXSize
height = ds.RasterYSize
gt = ds.GetGeoTransform()
minx = gt[0]
miny = gt[3] + width*gt[4] + height*gt[5] 
maxx = gt[0] + width*gt[1] + height*gt[2]
maxy = gt[3] 

Cependant, ceux-ci peuvent ne pas être au format latitude/longitude. Comme l'a noté Justin, votre géotiff sera stocké avec une sorte de système de coordonnées. Si vous ne savez pas de quel système de coordonnées il s'agit, vous pouvez le découvrir en exécutant gdalinfo:

gdalinfo ~/somedir/somefile.tif 

Quelles sorties:

Driver: GTiff/GeoTIFF
Size is 512, 512
Coordinate System is:
PROJCS["NAD27 / UTM zone 11N",
    GEOGCS["NAD27",
        DATUM["North_American_Datum_1927",
            SPHEROID["Clarke 1866",6378206.4,294.978698213901]],
        PRIMEM["Greenwich",0],
        UNIT["degree",0.0174532925199433]],
    PROJECTION["Transverse_Mercator"],
    PARAMETER["latitude_of_Origin",0],
    PARAMETER["central_meridian",-117],
    PARAMETER["scale_factor",0.9996],
    PARAMETER["false_easting",500000],
    PARAMETER["false_northing",0],
    UNIT["metre",1]]
Origin = (440720.000000,3751320.000000)
Pixel Size = (60.000000,-60.000000)
Corner Coordinates:
Upper Left  (  440720.000, 3751320.000) (117d38'28.21"W, 33d54'8.47"N)
Lower Left  (  440720.000, 3720600.000) (117d38'20.79"W, 33d37'31.04"N)
Upper Right (  471440.000, 3751320.000) (117d18'32.07"W, 33d54'13.08"N)
Lower Right (  471440.000, 3720600.000) (117d18'28.50"W, 33d37'35.61"N)
Center      (  456080.000, 3735960.000) (117d28'27.39"W, 33d45'52.46"N)
Band 1 Block=512x16 Type=Byte, ColorInterp=Gray

Cette sortie peut être tout ce dont vous avez besoin. Si vous voulez le faire par programmation dans python cependant, c'est ainsi que vous obtenez les mêmes informations.

Si le système de coordonnées est un PROJCS comme dans l'exemple ci-dessus, vous avez affaire à un système de coordonnées projeté. Un système de coordiante projeté est un représentation de la surface de la terre sphéroïdale, mais aplatie et déformée sur un plan . Si vous voulez la latitude et la longitude, vous devez convertir les coordonnées dans le système de coordonnées géographiques souhaité.

Malheureusement, toutes les paires latitude/longitude ne sont pas créées égales, étant basées sur différents modèles sphéroïdaux de la terre. Dans cet exemple, je convertis en WGS84 , le système de coordonnées géographiques privilégié dans les GPS et utilisé par tous les sites de cartographie Web populaires. Le système de coordonnées est défini par une chaîne bien définie. Un catalogue d'entre eux est disponible sur référence spatiale , voir par exemple WGS84 .

from osgeo import osr, gdal

# get the existing coordinate system
ds = gdal.Open('path/to/file')
old_cs= osr.SpatialReference()
old_cs.ImportFromWkt(ds.GetProjectionRef())

# create the new coordinate system
wgs84_wkt = """
GEOGCS["WGS 84",
    DATUM["WGS_1984",
        SPHEROID["WGS 84",6378137,298.257223563,
            AUTHORITY["EPSG","7030"]],
        AUTHORITY["EPSG","6326"]],
    PRIMEM["Greenwich",0,
        AUTHORITY["EPSG","8901"]],
    UNIT["degree",0.01745329251994328,
        AUTHORITY["EPSG","9122"]],
    AUTHORITY["EPSG","4326"]]"""
new_cs = osr.SpatialReference()
new_cs .ImportFromWkt(wgs84_wkt)

# create a transform object to convert between coordinate systems
transform = osr.CoordinateTransformation(old_cs,new_cs) 

#get the point to transform, pixel (0,0) in this case
width = ds.RasterXSize
height = ds.RasterYSize
gt = ds.GetGeoTransform()
minx = gt[0]
miny = gt[3] + width*gt[4] + height*gt[5] 

#get the coordinates in lat long
latlong = transform.TransformPoint(minx,miny) 

J'espère que cela fera ce que vous voulez.

80
fmark

Je ne sais pas si c'est une réponse complète, mais ce site dit:

Les dimensions de la carte x/y sont appelées est et nord. Pour les jeux de données dans un système de coordonnées géographiques, ceux-ci contiendraient la longitude et la latitude. Pour les systèmes de coordonnées projetés, ils seraient normalement l'abscisse et l'ordonnée dans le système de coordonnées projeté. Pour les images non référencées, l'abscisse et l'ordonnée seraient simplement les décalages pixel/ligne de chaque pixel (comme l'indique une géotransformation unitaire).

ils peuvent donc être en fait la longitude et la latitude.

16
Justin Peel