[GIS] Adding band to GDAL VRT dataset and converting to TIFF using GDAL

cgdalgeotiff-tiffqtvrt

I'm trying to add a band to a TIFF dataset by converting it to a VRT format and using the AddBand() function, then convert it back to a TIFF to access the band and write the data. Here is an example of my code:

const char *formatVRT = "VRT";
const char *formatTIFF = "GTiff";
char *filenameTIFF;
char *filenameVRT;
GDALDriver pDriverTIFF, pDriverVRT;
GDALDataset pTiffDS, pVrtDS;

GDALALLRegister();

pDriverTIFF = GetGDALDriverManager()->GetDriverByName(formatTIFF);
pDriverVRT = GetGDALDriverManager()->GetDriverByName(formatVRT);

pTiffDS = pDriverTIFF->Create(filenameTIFF, cols, rows, bands, GDT_Float32, NULL);
pVrtDS = pDriverVRt->CreateCopy(filenameVRT, pTiffDS, FALSE, NULL, NULL, NULL);

pVrtDS->AddBand(GDT_Float32, NULL);
pTiffDS = pDriverTIFF->CreateCopy(filenameTIFF, pVrtDS, FALSE, NULL, NULL, NULL);

I get the following errors:

ERROR 1: Deleting (filenameTIFF) failed:

Permission denied

ERROR 1: TIFFFillStrip:Read error at scanline 25; got 0 bytes, expected 24840

Best Answer

There were two problems. One noticed by @kyle, that the VRTDataset depends on the original, the other that the datasets needed to be closed in a specific order. Since all the datasets in this example are created in a program I was not able to use GDALOpenShared() as the documentation suggests, so instead the proper datasets need to be closed and removed at the proper time, then recreated. Here is the updated code:

const char *formatVRT = "VRT";
const char *formatTIFF = "GTiff";
char *filenameTIFF= "orignaltiff.tif";
char *filenameTempTIFF= "temptiff.tif";
char *filenameVRT = "intermediatevrt.vrt";

GDALDriver pDriverTIFF, pDriverVRT;
GDALDataset pTiffDS, pVrtDS, pTempDS;

GDALALLRegister();

pDriverTIFF = GetGDALDriverManager()->GetDriverByName(formatTIFF);
pDriverVRT = GetGDALDriverManager()->GetDriverByName(formatVRT);

pTiffDS = pDriverTIFF->Create(filenameTIFF, cols, rows, bands, GDT_Float32, NULL);
pVrtDS = pDriverVRt->CreateCopy(filenameVRT, pTiffDS, FALSE, NULL, NULL, NULL);

pVrtDS->AddBand(GDT_Float32, NULL);
pTempDS = pDriverTIFF->CreateCopy(filenameTempTIFF, pVrtDS, FALSE, NULL, NULL, NULL);

if (pTiffDS != NULL)
{
    GDALClose(pTiffDS);
    QFile::remove(filenameTiff); //this would need to be a QString not a *char
}

pTiffDS = pDriverTIFF->CreateCopy(filenameTIFF, pTempDS, FALSE, NULL, NULL, NULL);