使用 PyQGIS 将矢量和栅格图层导出到 GeoPackage (gpkg)

问题描述 投票:0回答:1

如何将列表中的图层(形状文件和 GTiff)导出到一个 gpkg 文件中?
它分别适用于矢量和栅格图层,但输出中仅保存一种类型的图层。
我已经意识到在编写栅格图层时哪些地理包不会更新,所以我决定创建临时地理包,然后更新 self.output
您可以在我的代码中看到下面的内容:

def save_as_gpkg(self, layers: List[QgsVectorLayer]):
        for layer in layers:
            layer_name = layer.name()
            context = QgsProject.instance().transformContext()
            if layer.type() == QgsMapLayer.VectorLayer:
                options = QgsVectorFileWriter.SaveVectorOptions()
                options.layerName = layer_name
                options.fileEncoding = layer.dataProvider().encoding()
                options.driverName = "GPKG"
                if os.path.exists(self.output):
                    options.actionOnExistingFile = QgsVectorFileWriter.CreateOrOverwriteLayer
                else:
                    options.actionOnExistingFile = QgsVectorFileWriter.CreateOrOverwriteFile
                options.EditionCapability = 0
                res = QgsVectorFileWriter.writeAsVectorFormatV3(layer, 
                                                                self.output, 
                                                                context, 
                                                                options)
            elif layer.type() == QgsMapLayer.RasterLayer:
                if layer.isValid():
                    overwrite = [f"RASTER_TABLE={layer_name}", 
                                  "OVERWRITE=YES", 
                                  "APPEND_SUBDATASET=YES"]
                    if os.path.exists(self.output):
                        temp_gpkg = tempfile.NamedTemporaryFile(suffix='.gpkg', delete=False)
                        writer = QgsRasterFileWriter(temp_gpkg.name)
                        writer.setCreateOptions(overwrite)
                        pipe = QgsRasterPipe()
                        pipe.set(layer.dataProvider().clone())
                        res = writer.writeRaster(pipe, layer.width(), layer.height(),layer.extent(),
                                                 layer.crs(), context)
                        temp_gpkg.close()
                        raster_ds = gdal.Open(temp_gpkg.name)
                        raster_driver = gdal.GetDriverByName('GPKG')
                        new_raster_ds = raster_driver.Create(self.output, raster_ds.RasterXSize,
                                                                          raster_ds.RasterYSize,
                                                                          raster_ds.RasterCount,
                                                                         gdal.GDT_Float32)
                        geotransform = raster_ds.GetGeoTransform()
                        new_raster_ds.SetGeoTransform(geotransform)
                        for i in range(1, raster_ds.RasterCount + 1):
                            band = raster_ds.GetRasterBand(i)
                            data = band.ReadAsArray()
                            new_raster_ds.GetRasterBand(i).WriteArray(data)
                        new_raster_ds.FlushCache()

                    else:
                        writer = QgsRasterFileWriter(self.output)
                        writer.setCreateOptions(overwrite)
                        pipe = QgsRasterPipe()
                        pipe.set(layer.dataProvider().clone())
                        res = writer.writeRaster(pipe, layer.width(), layer.height(), layer.extent(), layer.crs(), context)

有趣的是,这个字符串的工作原理是正确的:

QgsProject.instance().write(f"geopackage:{self.output}")
raster gdal qgis pyqgis geopackage
1个回答
0
投票
gdal.Translate(self.output, raster_dataset, format='GPKG',
                                       creationOptions=['APPEND_SUBDATASET=YES'])

它有效。

© www.soinside.com 2019 - 2024. All rights reserved.