172
183
CPLErr TSXRasterBand::IReadBlock( int nBlockXOff, int nBlockYOff,
177
/* Check if the last strip is partial so we can avoid over-requesting */
178
if ( (nBlockYOff + 1) * nBlockYSize > nRasterYSize ) {
179
nRequestYSize = nRasterYSize - nBlockYOff * nBlockYSize;
180
memset( pImage, 0, (GDALGetDataTypeSize( eDataType ) / 8) *
181
nBlockXSize * nBlockYSize);
184
nRequestYSize = nBlockYSize;
187
/* Read Complex Data */
188
if ( eDataType == GDT_CInt16 ) {
189
return poBand->RasterIO( GF_Read, nBlockXOff * nBlockXSize,
190
nBlockYOff * nBlockYSize, nBlockXSize, nRequestYSize,
191
pImage, nBlockXSize, nRequestYSize, GDT_CInt16, 1, NULL, 4,
192
nBlockXSize * 4, 0 );
194
else { /* Detected Product */
195
return poBand->RasterIO( GF_Read, nBlockXOff * nBlockXSize,
196
nBlockYOff * nBlockYSize, nBlockXSize, nRequestYSize,
197
pImage, nBlockXSize, nRequestYSize, GDT_UInt16, 1, NULL, 2,
198
nBlockXSize * 2, 0 );
188
/* Check if the last strip is partial so we can avoid over-requesting */
189
if ( (nBlockYOff + 1) * nBlockYSize > nRasterYSize ) {
190
nRequestYSize = nRasterYSize - nBlockYOff * nBlockYSize;
191
memset( pImage, 0, (GDALGetDataTypeSize( eDataType ) / 8) *
192
nBlockXSize * nBlockYSize);
195
nRequestYSize = nBlockYSize;
198
/* Read Complex Data */
199
if ( eDataType == GDT_CInt16 ) {
200
return poBand->RasterIO( GF_Read, nBlockXOff * nBlockXSize,
201
nBlockYOff * nBlockYSize, nBlockXSize, nRequestYSize,
202
pImage, nBlockXSize, nRequestYSize, GDT_CInt16, 1, NULL, 4,
203
nBlockXSize * 4, 0 );
205
else { /* Detected Product */
206
return poBand->RasterIO( GF_Read, nBlockXOff * nBlockXSize,
207
nBlockYOff * nBlockYSize, nBlockXSize, nRequestYSize,
208
pImage, nBlockXSize, nRequestYSize, GDT_UInt16, 1, NULL, 2,
209
nBlockXSize * 2, 0 );
202
213
/************************************************************************/
203
214
/* ==================================================================== */
205
216
/* ==================================================================== */
206
217
/************************************************************************/
222
241
TSXDataset::~TSXDataset() {
244
CPLFree( pszProjection );
246
CPLFree( pszGCPProjection );
249
GDALDeinitGCPs( nGCPCount, pasGCPList );
250
CPLFree( pasGCPList );
226
254
/************************************************************************/
228
256
/************************************************************************/
230
int TSXDataset::Identify( GDALOpenInfo *poOpenInfo ) {
231
if (poOpenInfo->fp == NULL || poOpenInfo->nHeaderBytes < 260)
234
/* Check if the filename contains TSX1_SAR */
235
if (!EQUALN(CPLGetBasename( poOpenInfo->pszFilename ), "TSX1_SAR", 8))
238
/* finally look for the <level1Product tag */
239
if (!EQUALN((char *)poOpenInfo->pabyHeader, "<level1Product", 14))
258
int TSXDataset::Identify( GDALOpenInfo *poOpenInfo )
260
if (poOpenInfo->fp == NULL || poOpenInfo->nHeaderBytes < 260)
262
if( poOpenInfo->bIsDirectory )
264
CPLString osFilename =
265
CPLFormCIFilename( poOpenInfo->pszFilename, CPLGetFilename( poOpenInfo->pszFilename ), "xml" );
267
/* Check if the filename contains TSX1_SAR (TerraSAR-X) or TDX1_SAR (TanDEM-X) */
268
if (!(EQUALN(CPLGetBasename( osFilename ), "TSX1_SAR", 8) ||
269
EQUALN(CPLGetBasename( osFilename ), "TDX1_SAR", 8)))
273
if( VSIStatL( osFilename, &sStat ) == 0 )
280
/* Check if the filename contains TSX1_SAR (TerraSAR-X) or TDX1_SAR (TanDEM-X) */
281
if (!(EQUALN(CPLGetBasename( poOpenInfo->pszFilename ), "TSX1_SAR", 8) ||
282
EQUALN(CPLGetBasename( poOpenInfo->pszFilename ), "TDX1_SAR", 8)))
285
/* finally look for the <level1Product tag */
286
if (!EQUALN((char *)poOpenInfo->pabyHeader, "<level1Product", 14))
292
/************************************************************************/
293
/* getGCPsFromGEOREF_XML() */
294
/*Reads georeferencing information from the TerraSAR-X GEOREF.XML file */
295
/*and writes the information to the dataset's gcp list and projection */
297
/*Returns true on success. */
298
/************************************************************************/
299
bool TSXDataset::getGCPsFromGEOREF_XML(char *pszGeorefFilename)
302
CPLXMLNode *psGeorefData;
303
psGeorefData = CPLParseXMLFile( pszGeorefFilename );
304
if (psGeorefData==NULL)
307
//get the ellipsoid and semi-major, semi-minor axes
308
CPLXMLNode *psSphere;
309
const char *pszEllipsoidName;
310
double minor_axis, major_axis, inv_flattening;
311
OGRSpatialReference osr;
312
psSphere = CPLGetXMLNode( psGeorefData, "=geoReference.referenceFrames.sphere" );
315
pszEllipsoidName = CPLGetXMLValue( psSphere, "ellipsoidID", "" );
316
minor_axis = atof(CPLGetXMLValue( psSphere, "semiMinorAxis", "0.0" ));
317
major_axis = atof(CPLGetXMLValue( psSphere, "semiMajorAxis", "0.0" ));
318
//save datum parameters to the spatial reference
319
if ( EQUAL(pszEllipsoidName, "") || minor_axis==0.0 || major_axis==0.0 )
321
CPLError(CE_Warning,CPLE_AppDefined,"Warning- incomplete"
322
" ellipsoid information. Using wgs-84 parameters.\n");
323
osr.SetWellKnownGeogCS( "WGS84" );
325
else if ( EQUAL( pszEllipsoidName, "WGS84" ) ) {
326
osr.SetWellKnownGeogCS( "WGS84" );
329
inv_flattening = major_axis/(major_axis - minor_axis);
330
osr.SetGeogCS( "","",pszEllipsoidName, major_axis, inv_flattening);
336
CPLXMLNode *psGeolocationGrid = CPLGetXMLNode( psGeorefData, "=geoReference.geolocationGrid" );
337
if (psGeolocationGrid==NULL)
339
CPLDestroyXMLNode( psGeorefData );
342
nGCPCount = atoi(CPLGetXMLValue( psGeolocationGrid, "numberOfGridPoints.total", "0" ));
343
//count the gcps if the given count value is invalid
346
for( psNode = psGeolocationGrid->psChild; psNode != NULL; psNode = psNode->psNext )
347
if( EQUAL(psNode->pszValue,"gridPoint") )
350
//if there are no gcps, fail
353
CPLDestroyXMLNode( psGeorefData );
357
//put some reasonable limits of the number of gcps
358
if (nGCPCount>MAX_GCPS )
360
//allocate memory for the gcps
361
pasGCPList = (GDAL_GCP *)CPLCalloc(sizeof(GDAL_GCP),nGCPCount);
362
//loop through all gcps and set info
363
int gcps_allocated = nGCPCount; //save the number allocated to ensure it does not run off the end of the array
364
nGCPCount=0; //reset to zero and count
365
//do a check on the grid point to make sure it has lat,long row, and column
366
//it seems that only SSC products contain row, col - how to map lat long otherwise??
367
//for now fail if row and col are not present - just check the first and assume the rest are the same
368
for( psNode = psGeolocationGrid->psChild; psNode != NULL; psNode = psNode->psNext )
370
if( !EQUAL(psNode->pszValue,"gridPoint") )
373
if ( !strcmp(CPLGetXMLValue(psNode,"col","error"), "error") ||
374
!strcmp(CPLGetXMLValue(psNode,"row","error"), "error") ||
375
!strcmp(CPLGetXMLValue(psNode,"lon","error"), "error") ||
376
!strcmp(CPLGetXMLValue(psNode,"lat","error"), "error"))
378
CPLDestroyXMLNode( psGeorefData );
382
for( psNode = psGeolocationGrid->psChild; psNode != NULL; psNode = psNode->psNext )
384
//break out if the end of the array has been reached
385
if (nGCPCount >= gcps_allocated)
387
CPLError(CE_Warning, CPLE_AppDefined, "GDAL TSX driver: Truncating the number of GCPs.");
392
GDAL_GCP *psGCP = pasGCPList + nGCPCount;
394
if( !EQUAL(psNode->pszValue,"gridPoint") )
399
sprintf( szID, "%d", nGCPCount );
400
psGCP->pszId = CPLStrdup( szID );
401
psGCP->pszInfo = CPLStrdup("");
403
atof(CPLGetXMLValue(psNode,"col","0"));
405
atof(CPLGetXMLValue(psNode,"row","0"));
407
atof(CPLGetXMLValue(psNode,"lon",""));
409
atof(CPLGetXMLValue(psNode,"lat",""));
410
//looks like height is in meters - should it be converted so xyz are all on the same scale??
412
//atof(CPLGetXMLValue(psNode,"height",""));
415
CPLFree(pszGCPProjection);
416
osr.exportToWkt( &(pszGCPProjection) );
418
CPLDestroyXMLNode( psGeorefData );
245
423
/************************************************************************/
250
428
/* -------------------------------------------------------------------- */
251
429
/* Is this a TerraSAR-X product file? */
252
430
/* -------------------------------------------------------------------- */
253
if (!TSXDataset::Identify( poOpenInfo )) {
254
return NULL; /* nope */
431
if (!TSXDataset::Identify( poOpenInfo ))
433
return NULL; /* nope */
257
436
/* -------------------------------------------------------------------- */
258
437
/* Confirm the requested access is supported. */
259
438
/* -------------------------------------------------------------------- */
260
439
if( poOpenInfo->eAccess == GA_Update )
262
CPLError( CE_Failure, CPLE_NotSupported,
441
CPLError( CE_Failure, CPLE_NotSupported,
263
442
"The TSX driver does not support update access to existing"
264
443
" datasets.\n" );
269
CPLXMLNode *psData, *psComponents, *psProductInfo;
270
psData = CPLParseXMLFile( poOpenInfo->pszFilename );
272
/* find the product components */
273
psComponents = CPLGetXMLNode( psData, "=level1Product.productComponents" );
274
if (psComponents == NULL) {
275
CPLError( CE_Failure, CPLE_OpenFailed,
276
"Unable to find <productComponents> tag in file.\n" );
280
/* find the product info tag */
281
psProductInfo = CPLGetXMLNode( psData, "=level1Product.productInfo" );
282
if (psComponents == NULL) {
283
CPLError( CE_Failure, CPLE_OpenFailed,
284
"Unable to find <productInfo> tag in file.\n" );
447
CPLString osFilename;
449
if( poOpenInfo->bIsDirectory )
452
CPLFormCIFilename( poOpenInfo->pszFilename, CPLGetFilename( poOpenInfo->pszFilename ), "xml" );
455
osFilename = poOpenInfo->pszFilename;
458
CPLXMLNode *psData, *psComponents, *psProductInfo;
459
psData = CPLParseXMLFile( osFilename );
463
/* find the product components */
464
psComponents = CPLGetXMLNode( psData, "=level1Product.productComponents" );
465
if (psComponents == NULL) {
466
CPLError( CE_Failure, CPLE_OpenFailed,
467
"Unable to find <productComponents> tag in file.\n" );
468
CPLDestroyXMLNode(psData);
472
/* find the product info tag */
473
psProductInfo = CPLGetXMLNode( psData, "=level1Product.productInfo" );
474
if (psProductInfo == NULL) {
475
CPLError( CE_Failure, CPLE_OpenFailed,
476
"Unable to find <productInfo> tag in file.\n" );
477
CPLDestroyXMLNode(psData);
288
481
/* -------------------------------------------------------------------- */
289
482
/* Create the dataset. */
290
483
/* -------------------------------------------------------------------- */
292
485
TSXDataset *poDS = new TSXDataset();
293
poDS->fp = poOpenInfo->fp;
294
poOpenInfo->fp = NULL;
296
487
/* -------------------------------------------------------------------- */
297
488
/* Read in product info. */
300
491
poDS->SetMetadataItem( "SCENE_CENTRE_TIME", CPLGetXMLValue( psProductInfo,
301
492
"sceneInfo.sceneCenterCoord.azimuthTimeUTC", "unknown" ) );
302
poDS->SetMetadataItem( "OPERATIONAL_MODE", CPLGetXMLValue( psProductInfo,
303
"generationInfo.groundOperationsType", "unknown" ) );
304
poDS->SetMetadataItem( "ORBIT_CYCLE", CPLGetXMLValue( psProductInfo,
305
"missionInfo.orbitCycle", "unknown" ) );
306
poDS->SetMetadataItem( "ABSOLUTE_ORBIT", CPLGetXMLValue( psProductInfo,
307
"missionInfo.absOrbit", "unknown" ) );
308
poDS->SetMetadataItem( "ORBIT_DIRECTION", CPLGetXMLValue( psProductInfo,
309
"missionInfo.orbitDirection", "unknown" ) );
310
poDS->SetMetadataItem( "IMAGING_MODE", CPLGetXMLValue( psProductInfo,
311
"acquisitionInfo.imagingMode", "unknown" ) );
312
poDS->SetMetadataItem( "PRODUCT_VARIANT", CPLGetXMLValue( psProductInfo,
313
"productVariantInfo.productVariant", "unknown" ) );
314
char *pszDataType = strdup( CPLGetXMLValue( psProductInfo,
315
"imageDataInfo.imageDataType", "unknown" ) );
316
poDS->SetMetadataItem( "IMAGE_TYPE", pszDataType );
318
/* Get raster information */
319
int nRows = atoi( CPLGetXMLValue( psProductInfo,
320
"imageDataInfo.imageRaster.numberOfRows", "" ) );
321
int nCols = atoi( CPLGetXMLValue( psProductInfo,
322
"imageDataInfo.imageRaster.numberOfColumns", "" ) );
324
poDS->nRasterXSize = nCols;
325
poDS->nRasterYSize = nRows;
327
poDS->SetMetadataItem( "ROW_SPACING", CPLGetXMLValue( psProductInfo,
328
"imageDataInfo.imageRaster.rowSpacing", "unknown" ) );
329
poDS->SetMetadataItem( "COL_SPACING", CPLGetXMLValue( psProductInfo,
330
"imageDataInfo.imageRaster.columnSpacing", "unknown" ) );
493
poDS->SetMetadataItem( "OPERATIONAL_MODE", CPLGetXMLValue( psProductInfo,
494
"generationInfo.groundOperationsType", "unknown" ) );
495
poDS->SetMetadataItem( "ORBIT_CYCLE", CPLGetXMLValue( psProductInfo,
496
"missionInfo.orbitCycle", "unknown" ) );
497
poDS->SetMetadataItem( "ABSOLUTE_ORBIT", CPLGetXMLValue( psProductInfo,
498
"missionInfo.absOrbit", "unknown" ) );
499
poDS->SetMetadataItem( "ORBIT_DIRECTION", CPLGetXMLValue( psProductInfo,
500
"missionInfo.orbitDirection", "unknown" ) );
501
poDS->SetMetadataItem( "IMAGING_MODE", CPLGetXMLValue( psProductInfo,
502
"acquisitionInfo.imagingMode", "unknown" ) );
503
poDS->SetMetadataItem( "PRODUCT_VARIANT", CPLGetXMLValue( psProductInfo,
504
"productVariantInfo.productVariant", "unknown" ) );
505
char *pszDataType = CPLStrdup( CPLGetXMLValue( psProductInfo,
506
"imageDataInfo.imageDataType", "unknown" ) );
507
poDS->SetMetadataItem( "IMAGE_TYPE", pszDataType );
509
/* Get raster information */
510
int nRows = atoi( CPLGetXMLValue( psProductInfo,
511
"imageDataInfo.imageRaster.numberOfRows", "" ) );
512
int nCols = atoi( CPLGetXMLValue( psProductInfo,
513
"imageDataInfo.imageRaster.numberOfColumns", "" ) );
515
poDS->nRasterXSize = nCols;
516
poDS->nRasterYSize = nRows;
518
poDS->SetMetadataItem( "ROW_SPACING", CPLGetXMLValue( psProductInfo,
519
"imageDataInfo.imageRaster.rowSpacing", "unknown" ) );
520
poDS->SetMetadataItem( "COL_SPACING", CPLGetXMLValue( psProductInfo,
521
"imageDataInfo.imageRaster.columnSpacing", "unknown" ) );
331
522
poDS->SetMetadataItem( "COL_SPACING_UNITS", CPLGetXMLValue( psProductInfo,
332
523
"imageDataInfo.imageRaster.columnSpacing.units", "unknown" ) );
334
/* Get equivalent number of looks */
335
poDS->SetMetadataItem( "AZIMUTH_LOOKS", CPLGetXMLValue( psProductInfo,
336
"imageDataInfo.imageRaster.azimuthLooks", "unknown" ) );
337
poDS->SetMetadataItem( "RANGE_LOOKS", CPLGetXMLValue( psProductInfo,
338
"imageDataInfo.imageRaster.rangeLooks", "unknown" ) );
525
/* Get equivalent number of looks */
526
poDS->SetMetadataItem( "AZIMUTH_LOOKS", CPLGetXMLValue( psProductInfo,
527
"imageDataInfo.imageRaster.azimuthLooks", "unknown" ) );
528
poDS->SetMetadataItem( "RANGE_LOOKS", CPLGetXMLValue( psProductInfo,
529
"imageDataInfo.imageRaster.rangeLooks", "unknown" ) );
340
531
const char *pszProductVariant;
341
pszProductVariant = CPLGetXMLValue( psProductInfo,
532
pszProductVariant = CPLGetXMLValue( psProductInfo,
342
533
"productVariantInfo.productVariant", "unknown" );
344
535
poDS->SetMetadataItem( "PRODUCT_VARIANT", pszProductVariant );
356
547
poDS->nProduct = eUnknown;
358
/* Start reading in the product components */
360
char *pszGeorefFile = NULL;
361
CPLXMLNode *psComponent;
362
for (psComponent = psComponents->psChild; psComponent != NULL;
363
psComponent = psComponent->psNext)
366
pszPath = CPLFormFilename(
367
CPLGetDirname( poOpenInfo->pszFilename ),
368
GetFilePath(psComponent, &pszType),
370
const char *pszPolLayer = CPLGetXMLValue(psComponent, "polLayer", " ");
372
if ( !EQUALN(pszType," ",1) ) {
373
if (EQUALN(pszType, "MAPPING_GRID", 12) ) {
374
/* the mapping grid... save as a metadata item this path */
375
poDS->SetMetadataItem( "MAPPING_GRID", pszPath );
377
else if (EQUALN(pszType, "GEOREF", 6)) {
378
/* save the path to the georef data for later use */
379
pszGeorefFile = strdup( pszPath );
383
else if( !EQUALN(pszPolLayer, " ", 1) &&
384
EQUALN(psComponent->pszValue, "imageData", 9) ) {
385
/* determine the polarization of this band */
387
if ( EQUALN(pszPolLayer, "HH", 2) ) {
390
else if ( EQUALN(pszPolLayer, "HV" , 2) ) {
393
else if ( EQUALN(pszPolLayer, "VH", 2) ) {
400
GDALDataType eDataType = EQUALN(pszDataType, "COMPLEX", 7) ?
401
GDT_CInt16 : GDT_UInt16;
403
/* try opening the file that represents that band */
404
TSXRasterBand *poBand;
405
GDALDataset *poBandData;
407
poBandData = (GDALDataset *) GDALOpen( pszPath, GA_ReadOnly );
408
if ( poBandData != NULL ) {
409
poBand = new TSXRasterBand( poDS, eDataType, ePol,
411
poDS->SetBand( poDS->GetRasterCount() + 1, poBand );
416
CPLFree(pszDataType);
549
/* Start reading in the product components */
551
char *pszGeorefFile = NULL;
552
CPLXMLNode *psComponent;
553
CPLErr geoTransformErr=CE_Failure;
554
for (psComponent = psComponents->psChild; psComponent != NULL;
555
psComponent = psComponent->psNext)
557
const char *pszType = NULL;
558
pszPath = CPLFormFilename(
559
CPLGetDirname( osFilename ),
560
GetFilePath(psComponent, &pszType),
562
const char *pszPolLayer = CPLGetXMLValue(psComponent, "polLayer", " ");
564
if ( !EQUALN(pszType," ",1) ) {
565
if (EQUALN(pszType, "MAPPING_GRID", 12) ) {
566
/* the mapping grid... save as a metadata item this path */
567
poDS->SetMetadataItem( "MAPPING_GRID", pszPath );
569
else if (EQUALN(pszType, "GEOREF", 6)) {
570
/* save the path to the georef data for later use */
571
pszGeorefFile = CPLStrdup( pszPath );
574
else if( !EQUALN(pszPolLayer, " ", 1) &&
575
EQUALN(psComponent->pszValue, "imageData", 9) ) {
576
/* determine the polarization of this band */
578
if ( EQUALN(pszPolLayer, "HH", 2) ) {
581
else if ( EQUALN(pszPolLayer, "HV" , 2) ) {
584
else if ( EQUALN(pszPolLayer, "VH", 2) ) {
591
GDALDataType eDataType = EQUALN(pszDataType, "COMPLEX", 7) ?
592
GDT_CInt16 : GDT_UInt16;
594
/* try opening the file that represents that band */
595
TSXRasterBand *poBand;
596
GDALDataset *poBandData;
598
poBandData = (GDALDataset *) GDALOpen( pszPath, GA_ReadOnly );
599
if ( poBandData != NULL ) {
600
poBand = new TSXRasterBand( poDS, eDataType, ePol,
602
poDS->SetBand( poDS->GetRasterCount() + 1, poBand );
604
//copy georeferencing info from the band
605
//need error checking??
606
//it will just save the info from the last band
607
CPLFree( poDS->pszProjection );
608
poDS->pszProjection = CPLStrdup(poBandData->GetProjectionRef());
609
geoTransformErr = poBandData->GetGeoTransform(poDS->adfGeoTransform);
614
//now check if there is a geotransform
615
if ( strcmp(poDS->pszProjection, "") && geoTransformErr==CE_None)
617
poDS->bHaveGeoTransform = TRUE;
621
poDS->bHaveGeoTransform = FALSE;
622
CPLFree( poDS->pszProjection );
623
poDS->pszProjection = CPLStrdup("");
624
poDS->adfGeoTransform[0] = 0.0;
625
poDS->adfGeoTransform[1] = 1.0;
626
poDS->adfGeoTransform[2] = 0.0;
627
poDS->adfGeoTransform[3] = 0.0;
628
poDS->adfGeoTransform[4] = 0.0;
629
poDS->adfGeoTransform[5] = 1.0;
632
CPLFree(pszDataType);
419
635
/* -------------------------------------------------------------------- */
420
636
/* Check and set matrix representation. */
421
637
/* -------------------------------------------------------------------- */
423
if (poDS->GetRasterCount() == 4) {
424
poDS->SetMetadataItem( "MATRIX_REPRESENTATION", "SCATTERING" );
639
if (poDS->GetRasterCount() == 4) {
640
poDS->SetMetadataItem( "MATRIX_REPRESENTATION", "SCATTERING" );
427
643
/* -------------------------------------------------------------------- */
428
644
/* Read the four corners and centre GCPs in */
429
645
/* -------------------------------------------------------------------- */
431
CPLXMLNode *psSceneInfo = CPLGetXMLNode( psData,
647
CPLXMLNode *psSceneInfo = CPLGetXMLNode( psData,
432
648
"=level1Product.productInfo.sceneInfo" );
433
/* for SSC products */
434
if (poDS->nProduct == eSSC && psSceneInfo != NULL) {
437
double dfAvgHeight = atof(CPLGetXMLValue(psSceneInfo,
438
"sceneAverageHeight", "0.0"));
441
poDS->nGCPCount = 5; /* 5 GCPs provided */
442
poDS->pasGCPList = (GDAL_GCP *)CPLCalloc(sizeof(GDAL_GCP),
445
/* iterate over GCPs */
446
for (psNode = psSceneInfo->psChild; psNode != NULL;
447
psNode = psNode->psNext )
449
GDAL_GCP *psGCP = poDS->pasGCPList + nGCP;
451
if (!EQUAL(psNode->pszValue, "sceneCenterCoord") &&
452
!EQUAL(psNode->pszValue, "sceneCornerCoord"))
455
CPLSPrintf( szID, "%d", nGCP );
457
psGCP->dfGCPPixel = atof(CPLGetXMLValue(psNode, "refColumn",
459
psGCP->dfGCPLine = atof(CPLGetXMLValue(psNode, "refRow", "0.0"));
460
psGCP->dfGCPX = atof(CPLGetXMLValue(psNode, "lon", "0.0"));
461
psGCP->dfGCPY = atof(CPLGetXMLValue(psNode, "lat", "0.0"));
462
psGCP->dfGCPZ = dfAvgHeight;
463
psGCP->pszId = CPLStrdup( szID );
464
psGCP->pszInfo = CPLStrdup("");
469
else if (psSceneInfo != NULL) {
649
if (psSceneInfo != NULL)
470
651
/* extract the GCPs from the provided file */
652
bool success = false;
653
if (pszGeorefFile != NULL)
654
success = poDS->getGCPsFromGEOREF_XML(pszGeorefFile);
656
//if the gcp's cannot be extracted from the georef file, try to get the corner coordinates
657
//for now just SSC because the others don't have refColumn and refRow
658
if (!success && poDS->nProduct == eSSC)
662
double dfAvgHeight = atof(CPLGetXMLValue(psSceneInfo,
663
"sceneAverageHeight", "0.0"));
665
//count and allocate gcps - there should be five - 4 corners and a centre
667
for (psNode = psSceneInfo->psChild; psNode != NULL; psNode = psNode->psNext )
669
if (!EQUAL(psNode->pszValue, "sceneCenterCoord") &&
670
!EQUAL(psNode->pszValue, "sceneCornerCoord"))
675
if (poDS->nGCPCount > 0)
677
poDS->pasGCPList = (GDAL_GCP *)CPLCalloc(sizeof(GDAL_GCP), poDS->nGCPCount);
679
/* iterate over GCPs */
680
for (psNode = psSceneInfo->psChild; psNode != NULL; psNode = psNode->psNext )
682
GDAL_GCP *psGCP = poDS->pasGCPList + nGCP;
684
if (!EQUAL(psNode->pszValue, "sceneCenterCoord") &&
685
!EQUAL(psNode->pszValue, "sceneCornerCoord"))
688
psGCP->dfGCPPixel = atof(CPLGetXMLValue(psNode, "refColumn",
690
psGCP->dfGCPLine = atof(CPLGetXMLValue(psNode, "refRow", "0.0"));
691
psGCP->dfGCPX = atof(CPLGetXMLValue(psNode, "lon", "0.0"));
692
psGCP->dfGCPY = atof(CPLGetXMLValue(psNode, "lat", "0.0"));
693
psGCP->dfGCPZ = dfAvgHeight;
694
psGCP->pszId = CPLStrdup( CPLSPrintf( "%d", nGCP ) );
695
psGCP->pszInfo = CPLStrdup("");
700
//set the projection string - the fields are lat/long - seems to be WGS84 datum
701
OGRSpatialReference osr;
702
osr.SetWellKnownGeogCS( "WGS84" );
703
CPLFree(poDS->pszGCPProjection);
704
osr.exportToWkt( &(poDS->pszGCPProjection) );
708
//gcps override geotransform - does it make sense to have both??
709
if (poDS->nGCPCount>0)
711
poDS->bHaveGeoTransform = FALSE;
712
CPLFree( poDS->pszProjection );
713
poDS->pszProjection = CPLStrdup("");
714
poDS->adfGeoTransform[0] = 0.0;
715
poDS->adfGeoTransform[1] = 1.0;
716
poDS->adfGeoTransform[2] = 0.0;
717
poDS->adfGeoTransform[3] = 0.0;
718
poDS->adfGeoTransform[4] = 0.0;
719
poDS->adfGeoTransform[5] = 1.0;
475
CPLError(CE_Warning, CPLE_AppDefined,
476
"Unable to find sceneInfo tag in XML document. "
724
CPLError(CE_Warning, CPLE_AppDefined,
725
"Unable to find sceneInfo tag in XML document. "
477
726
"Proceeding with caution.");
729
CPLFree(pszGeorefFile);
480
731
/* -------------------------------------------------------------------- */
481
732
/* Initialize any PAM information. */
482
733
/* -------------------------------------------------------------------- */