GDAL을 사용하여 Python에서 WGS 1984 Web Mercator (EPSG : 3857) 재 투영


17

GDAL을 사용하여 파이썬으로 래스터를 다시 투영하고 있습니다. 나중에 OpenStreetMap 및 Google지도와 함께 Openlayers에서 사용하려면 지리적 WGS 84 좌표에서 WGS 1984 Web Mercator (Auxiliary Sphere)로 여러 가지 강성을 투영해야합니다. 여기 에서 Python 2.7.5 및 GDAL 1.10.1을 사용하고 여기 에서 조언을 사용하여 좌표를 변환하고 있습니다 (내 코드는 다음과 같습니다). 즉, 나는 수입 osgeo.osr 및 사용 ImportFromEPSG (코드)(에,에서) CoordinateTransformation을 .

내가 먼저 시도 EPSG (32629) 코드가 올바른 것 같다, 그래서 UTM 구역 (29)이며,이 투영 된 래스터 (더 많거나 적은 미세) 도착 : utm 그럼 난 사용 EPSG (3857)를 내가 읽은 때문에 질문에 발견을 올바른 최근 유효한 코드 입니다. 그러나 래스터는 공간 참조없이 생성됩니다. WGS 84 데이터 프레임에서 멀리 떨어져 있지만 데이터 프레임을 Web Mercator로 전환해도 괜찮습니다. 3857

함께 EPSG (900,913) 의 출력은 참조 된되지만 북쪽 3 개 래스터 셀에 대해 시프트 : 900913

ArcGIS (WGS_1984_Web_Mercator_Auxiliary_Sphere로 내보내기)를 사용하여 래스터를 재 투영하면 결과가 거의 좋습니다. Arcgis

그리고 이전 코드 102113 (41001,54004)을 사용 하면 결과가 완벽합니다. 54004

모든 코드를 사용한 테스트 요약 :

3857: far away up (missing georeference)
3785: far away up (like 3857)
3587: far away right
900913: slightly jumped up
102100: python error
102113: perfect
41001: perfect
54004: perfect
ArcGIS (web merc. aux.): good

그래서 내 질문은 :

  • 올바른 EPSG 코드가 왜 잘못된 결과를 줍니까?
  • 왜 이전 코드가 제대로 작동합니까, 더 이상 사용되지 않습니까?
  • 어쩌면 내 GDAL 버전이 좋지 않거나 파이썬 코드에 오류가 있습니까?

코드:

    yres = round(lons[1]-lons[0], 4)  # pixel size, degrees
    xres = round(lats[1]-lats[0], 4)
    ysize = len(lats)-1  # number of pixels
    xsize = len(lons)-1
    ulx = round(lons[0], 4)
    uly = round(lats[-1], 4)  # last
    driver = gdal.GetDriverByName(fileformat)
    ds = driver.Create(filename, xsize, ysize, 2, gdal.GDT_Float32)  # 2 bands
    #--- Geographic ---
    srs = osr.SpatialReference()
    srs.ImportFromEPSG(4326)  # Geographic lat/lon WGS 84
    ds.SetProjection(srs.ExportToWkt())
    gt = [ulx, xres, 0, uly, 0, -yres]  # the affine transformation coeffs (ulx, pixel, angle(skew), uly, angle, -pixel)
    ds.SetGeoTransform(gt)  # coords of top left corner of top left pixel (w-file - center of the pixel!)
    outband = ds.GetRasterBand(1)
    outband.WriteArray(data)
    outband2 = ds.GetRasterBand(2)
    outband2.WriteArray(data3)
    #--- REPROJECTION ---
    utm29 = osr.SpatialReference()
#    utm29.ImportFromEPSG(32629)  # utm 29
    utm29.ImportFromEPSG(900913)  # web mercator 3857
    wgs84 = osr.SpatialReference()
    wgs84.ImportFromEPSG(4326)
    tx = osr.CoordinateTransformation(wgs84,utm29)
    # Get the Geotransform vector
    # Work out the boundaries of the new dataset in the target projection
    (ulx29, uly29, ulz29) = tx.TransformPoint(ulx, uly)  # corner coords in utm meters
    (lrx29, lry29, lrz29) = tx.TransformPoint(ulx + xres*xsize, uly - yres*ysize )
    filenameutm = filename[0:-4] + '_web.tif'
    dest = driver.Create(filenameutm, xsize, ysize, 2, gdal.GDT_Float32)
    xres29 = round((lrx29 - ulx29)/xsize, 2) # pixel size, utm meters
    yres29 = abs(round((lry29 - uly29)/ysize, 2))
    new_gt = [ulx29, xres29, 0, uly29, 0, -yres29]
    dest.SetGeoTransform(new_gt)
    dest.SetProjection(utm29.ExportToWkt())
    gdal.ReprojectImage(ds, dest, wgs84.ExportToWkt(), utm29.ExportToWkt(), gdal.GRA_Bilinear)
    dest.GetRasterBand(1).SetNoDataValue(0.0)
    dest.GetRasterBand(2).SetNoDataValue(0.0)
    dest = None  # Flush the dataset to the disk
    ds = None  # only after the reprojected!
    print 'Image Created'

EPSG : 3042에서 Google Mercator One으로 래스터를 다시 투영하고 있는데 원칙적으로 3857이라고 생각했지만 시도 할 때 gdal_translate -a_srs EPSG : 3857 input.tif output.tif에서 출력은 멀리 떨어져 있습니다 (GDAL 1.11.2). 다행히도 ArcGIS 10.2 및 WGS_1984_Web_Mercator_Auxiliary_Sphere (WKID : 3857 Authority : EPSG)를 사용하여 래프 이미지가 올바른 위치에있을 때 출력이 멀리 떨어집니다 (GDAL 1.11.2). 따라서 EPSG : 3857이 최신 버전의 GDAL에서 제대로 처리되지 않았다고 생각합니다.
Web-GIS 기업가

3
재 투영 후 래스터는 더 이상 사각형 일 필요가 없습니다. 따라서 코너 좌표를 다시 투영하면 잘못된 해결책이 될 수 있습니다. 커맨드 라인에서 gdalwarp를 사용해 보셨습니까? BTW는 gisinternals에서 최신 GDAL 버전을 얻을 수 있습니다.
AndreJ

답변:


5

로 파일을 다시 투영합니다 gdalwarp.

EPSG : 3757로 변환하려는 EPSG : 3763 파일에 대해서도 동일한 작업을 수행했습니다. QGIS와 Geoserver를 사용하여 결과를 비교 한 결과 생성 된 이미지가 양호했습니다. 이미지에 작은 회전이 적용되므로 테두리에 검은 선이 생길 수 있습니다 (그러나이 선은 나중에 투명하게 만들 수 있습니다).

여러 tif이미지 가 있으므로 기존 파일을 변경하지 않고 다음과 같은 스크립트를 사용 하여 생성 된 파일을 3857이라는 폴더에 넣을 수 있습니다.

#!/bin/bash
mkdir 3857
for file in $(ls *.tif); do
    gdalwarp -s_srs EPSG:3763 -t_srs EPSG:3857 $file 3857/$file;
    listgeo -tfw 3857/$file;
done

.twf파일 을 생성하려면을 추가했습니다 listgeo.

이 스크립트는 Linux 용이지만 Windows와 비슷한 것을 작성할 수 있습니다.


당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.