22 #include "imageclasses/ImgReaderGdal.h" 23 #include "imageclasses/ImgWriterGdal.h" 24 #include "base/Optionpk.h" 73 int main(
int argc,
char *argv[])
79 Optionpk<string> otype_opt(
"ot",
"otype",
"Data type for output image ({Byte/Int16/UInt16/UInt32/Int32/Float32/Float64/CInt16/CInt32/CFloat32/CFloat64}). Empty string: inherit type from input image",
"");
80 Optionpk<string> oformat_opt(
"of",
"oformat",
"Output image format (see also gdal_translate)",
"GTiff");
81 Optionpk<string> option_opt(
"co",
"co",
"Creation option for output file. Multiple options can be specified.");
82 Optionpk<int> msknodata_opt(
"msknodata",
"msknodata",
"Mask value(s) where image has nodata. Use one value for each mask, or multiple values for a single mask.", 1);
83 Optionpk<short> mskband_opt(
"mskband",
"mskband",
"Mask band to read (0 indexed). Provide band for each mask.", 0);
84 Optionpk<char> operator_opt(
"p",
"operator",
"Operator: < = > !. Use operator for each msknodata option",
'=');
85 Optionpk<int> nodata_opt(
"nodata",
"nodata",
"nodata value to put in image if not valid", 0);
86 Optionpk<string> colorTable_opt(
"ct",
"ct",
"color table (file with 5 columns: id R G B ALFA (0: transparent, 255: solid)");
90 oformat_opt.setHide(1);
91 option_opt.setHide(1);
92 colorTable_opt.setHide(1);
93 mskband_opt.setHide(1);
97 doProcess=input_opt.retrieveOption(argc,argv);
98 mask_opt.retrieveOption(argc,argv);
99 msknodata_opt.retrieveOption(argc,argv);
100 mskband_opt.retrieveOption(argc,argv);
101 output_opt.retrieveOption(argc,argv);
102 nodata_opt.retrieveOption(argc,argv);
103 operator_opt.retrieveOption(argc,argv);
104 otype_opt.retrieveOption(argc,argv);
105 oformat_opt.retrieveOption(argc,argv);
106 option_opt.retrieveOption(argc,argv);
107 colorTable_opt.retrieveOption(argc,argv);
108 verbose_opt.retrieveOption(argc,argv);
110 catch(
string predefinedString){
111 std::cout << predefinedString << std::endl;
116 cout <<
"Usage: pksetmask -i input -m mask [-m mask]* [-msknodata value -nodata value]* -o output" << endl;
118 std::cout <<
"short option -h shows basic options only, use long option --help to show all options" << std::endl;
123 cout <<
"number of mask images: " << mask_opt.size() << endl;
126 while(mskband_opt.size()<mask_opt.size())
127 mskband_opt.push_back(mskband_opt[0]);
129 vector<ImgReaderGdal> maskReader(mask_opt.size());
130 for(
int imask=0;imask<mask_opt.size();++imask){
132 cout <<
"opening mask image file " << mask_opt[imask] << endl;
133 maskReader[imask].open(mask_opt[imask]);
135 assert(input_opt.size());
137 cout <<
"opening input image file " << input_opt[0] << endl;
139 inputReader.
open(input_opt[0]);
141 if(oformat_opt.size())
142 imageType=oformat_opt[0];
143 GDALDataType theType=GDT_Unknown;
145 std::cout <<
"Image type: " << imageType << std::endl;
146 std::cout <<
"possible output data types: ";
148 for(
int iType = 0; iType < GDT_TypeCount; ++iType){
150 cout <<
" " << GDALGetDataTypeName((GDALDataType)iType);
151 if( GDALGetDataTypeName((GDALDataType)iType) != NULL
152 && EQUAL(GDALGetDataTypeName((GDALDataType)iType),
153 otype_opt[0].c_str()))
154 theType=(GDALDataType) iType;
156 if(theType==GDT_Unknown)
159 assert(output_opt.size());
161 std::cout << std::endl <<
"Output data type: " << GDALGetDataTypeName(theType) << std::endl;
162 std::cout <<
"opening output image for writing: " << output_opt[0] << std::endl;
166 if(option_opt.findSubstring(
"INTERLEAVE=")==option_opt.end()){
167 string theInterleave=
"INTERLEAVE=";
169 option_opt.push_back(theInterleave);
171 outputWriter.
open(output_opt[0],inputReader.
nrOfCol(),inputReader.
nrOfRow(),inputReader.
nrOfBand(),theType,imageType,option_opt);
172 for(
int iband=0;iband<inputReader.
nrOfBand();++iband)
177 catch(
string errorstring){
178 cout << errorstring << endl;
184 if(colorTable_opt.size()){
185 if(colorTable_opt[0]!=
"none")
191 for(
int imask=0;imask<mask_opt.size();++imask)
192 assert(maskReader[imask].isGeoRef());
194 assert(nodata_opt.size()==msknodata_opt.size());
195 assert(operator_opt.size()==msknodata_opt.size()||operator_opt.size()==1);
197 cout <<
" mask files selected: " << mask_opt.size() << endl;
198 for(
int iv=0;iv<msknodata_opt.size();++iv){
199 char op=(operator_opt.size()==msknodata_opt.size())?operator_opt[iv]:operator_opt[0];
200 cout << op <<
" " << msknodata_opt[iv] <<
"->" << nodata_opt[iv] << endl;
206 assert(lineOutput.size()==lineInput.size());
210 for(
int imask=0;imask<mask_opt.size();++imask){
212 cout <<
"mask " << imask <<
" has " << maskReader[imask].nrOfCol() <<
" columns and " << maskReader[imask].nrOfRow() <<
" rows" << endl;
213 lineMask[imask].resize(maskReader[imask].nrOfCol());
217 const char* pszMessage;
218 void* pProgressArg=NULL;
219 GDALProgressFunc pfnProgress=GDALTermProgress;
222 pfnProgress(progress,pszMessage,pProgressArg);
224 vector<double> oldRowMask(mask_opt.size());
225 for(
int imask=0;imask<mask_opt.size();++imask)
226 oldRowMask[imask]=-1;
227 for(irow=0;irow<inputReader.
nrOfRow();++irow){
229 for(
int iband=0;iband<inputReader.
nrOfBand();++iband){
231 inputReader.
readData(lineInput[iband],irow,iband);
233 catch(
string errorstring){
234 cerr << errorstring << endl;
239 double colMask,rowMask;
240 for(icol=0;icol<inputReader.
nrOfCol();++icol){
241 if(mask_opt.size()>1){
242 for(
int imask=0;imask<mask_opt.size();++imask){
244 maskReader[imask].geo2image(x,y,colMask,rowMask);
245 colMask=
static_cast<int>(colMask);
246 rowMask=
static_cast<int>(rowMask);
248 if(rowMask>=0&&rowMask<maskReader[imask].nrOfRow()&&colMask>=0&&colMask<maskReader[imask].nrOfCol()){
249 if(static_cast<int>(rowMask)!=
static_cast<int>(oldRowMask[imask])){
250 assert(rowMask>=0&&rowMask<maskReader[imask].nrOfRow());
253 maskReader[imask].readData(lineMask[imask],static_cast<int>(rowMask),mskband_opt[imask]);
255 catch(
string errorstring){
256 cerr << errorstring << endl;
259 oldRowMask[imask]=rowMask;
265 if(mask_opt.size()==msknodata_opt.size())
266 ivalue=msknodata_opt[imask];
268 ivalue=msknodata_opt[0];
269 char op=(operator_opt.size()==mask_opt.size())?operator_opt[imask]:operator_opt[0];
273 if(lineMask[imask][colMask]==ivalue)
277 if(lineMask[imask][colMask]<ivalue)
281 if(lineMask[imask][colMask]>ivalue)
285 if(lineMask[imask][colMask]!=ivalue)
291 cout <<
"image masked at (col=" << icol <<
",row=" << irow <<
") with mask " << mask_opt[imask] <<
" and value " << ivalue << endl;
292 for(
int iband=0;iband<inputReader.
nrOfBand();++iband){
293 if(mask_opt.size()==nodata_opt.size())
294 lineInput[iband][icol]=nodata_opt[imask];
296 lineInput[iband][icol]=nodata_opt[0];
305 maskReader[0].geo2image(x,y,colMask,rowMask);
306 colMask=
static_cast<int>(colMask);
307 rowMask=
static_cast<int>(rowMask);
309 if(rowMask>=0&&rowMask<maskReader[0].nrOfRow()&&colMask>=0&&colMask<maskReader[0].nrOfCol()){
310 if(static_cast<int>(rowMask)!=
static_cast<int>(oldRowMask[0])){
311 assert(rowMask>=0&&rowMask<maskReader[0].nrOfRow());
314 maskReader[0].readData(lineMask[0],static_cast<int>(rowMask),mskband_opt[0]);
316 catch(
string errorstring){
317 cerr << errorstring << endl;
320 oldRowMask[0]=rowMask;
322 for(
int ivalue=0;ivalue<msknodata_opt.size();++ivalue){
323 assert(msknodata_opt.size()==nodata_opt.size());
324 char op=(operator_opt.size()==msknodata_opt.size())?operator_opt[ivalue]:operator_opt[0];
328 if(lineMask[0][colMask]==msknodata_opt[ivalue])
332 if(lineMask[0][colMask]<msknodata_opt[ivalue])
336 if(lineMask[0][colMask]>msknodata_opt[ivalue])
340 if(lineMask[0][colMask]!=msknodata_opt[ivalue])
345 for(
int iband=0;iband<inputReader.
nrOfBand();++iband)
346 lineInput[iband][icol]=nodata_opt[ivalue];
353 for(
int iband=0;iband<lineOutput.size();++iband)
354 lineOutput[iband][icol]=lineInput[iband][icol];
357 for(
int iband=0;iband<outputWriter.
nrOfBand();++iband){
359 outputWriter.
writeData(lineOutput[iband],irow,iband);
361 catch(
string errorstring){
362 cerr << errorstring << endl;
367 progress=
static_cast<float>(irow+1.0)/outputWriter.
nrOfRow();
368 pfnProgress(progress,pszMessage,pProgressArg);
371 for(
int imask=0;imask<mask_opt.size();++imask)
372 maskReader[imask].close();
373 outputWriter.
close();
void close(void)
Set the memory (in MB) to cache a number of rows in memory.
int nrOfCol(void) const
Get the number of columns of this dataset.
void setColorTable(const std::string &filename, int band=0)
Set the color table using an (ASCII) file with 5 columns (value R G B alpha)
void readData(T &value, int col, int row, int band=0)
Read a single pixel cell value at a specific column and row for a specific band (all indices start co...
int nrOfRow(void) const
Get the number of rows of this dataset.
bool image2geo(double i, double j, double &x, double &y) const
Convert image coordinates (column and row) to georeferenced coordinates (x and y) ...
GDALColorTable * getColorTable(int band=0) const
Get the GDAL color table for this dataset as an instance of the GDALColorTable class.
bool isGeoRef() const
Is this dataset georeferenced (pixel size in y must be negative) ?
bool writeData(T &value, int col, int row, int band=0)
Write a single pixel cell value at a specific column and row for a specific band (all indices start c...
void copyGeoTransform(const ImgRasterGdal &imgSrc)
Copy geotransform information from another georeferenced image.
void open(const std::string &filename, const ImgReaderGdal &imgSrc, const std::vector< std::string > &options=std::vector< std::string >())
Open an image for writing, copying image attributes from a source image. Image is directly written to...
std::string getProjection(void) const
Get the projection string (deprecated, use getProjectionRef instead)
GDALDataType getDataType(int band=0) const
Get the GDAL datatype for this dataset.
CPLErr setProjection(const std::string &projection)
Set the projection for this dataset in well known text (wkt) format.
void close(void)
Close the image.
CPLErr GDALSetNoDataValue(double noDataValue, int band=0)
Set the GDAL (internal) no data value for this data set. Only a single no data value per band is supp...
void open(const std::string &filename, const GDALAccess &readMode=GA_ReadOnly)
Open an image.
int nrOfBand(void) const
Get the number of bands of this dataset.
std::string getInterleave() const
Get the band coding (interleave)