00001 00002 00003 00004 00005 00006 00007 00008 00009 00010 00011 00012 00013 00014 00015 00016 00017 00018 00019 00020 00021 00022 00023 00024 00025 00026 00027 00028 00029 00030 00030 00030 00030 00031 00032 00033 00034 00035 00036 00037 00038 00039 00040 00041 00042 00043 00044 00045 00046 00047 00048 00049 00050 00051 00052 00053 00054 00055 00056 00057 00058 00059 00060 00061 00062 00063 00064 00065 00066 00067 00068 00069 00070 00071 00072 00073 00074 00075 00076 00077 00078 00079 00080 00081 00082 00083 00084 00085 00086 00087 00088 00089 00090 00091 00092 00093 00094
00095
00096 #include "gdal_priv.h"
00097
00098
00099
00100
00101
00102
00103
00104
00105 #ifdef __GNUC__
00106
00107 extern "C"
00108 void __pure_virtual()
00109
00110 {
00111 }
00112
00113 #endif
00114
00115
00116
00117
00118
00129 GDALDataType GDALDataTypeUnion( GDALDataType eType1, GDALDataType eType2 )
00130
00131 {
00132 int bFloating, bComplex, nBits, bSigned;
00133
00134 bComplex = GDALDataTypeIsComplex(eType1) | GDALDataTypeIsComplex(eType2);
00135
00136 switch( eType1 )
00137 {
00138 case GDT_Byte:
00139 nBits = 8;
00140 bSigned = FALSE;
00141 bFloating = FALSE;
00142 break;
00143
00144 case GDT_Int16:
00145 case GDT_CInt16:
00146 nBits = 16;
00147 bSigned = TRUE;
00148 bFloating = FALSE;
00149 break;
00150
00151 case GDT_UInt16:
00152 nBits = 16;
00153 bSigned = FALSE;
00154 bFloating = FALSE;
00155 break;
00156
00157 case GDT_Int32:
00158 case GDT_CInt32:
00159 nBits = 32;
00160 bSigned = TRUE;
00161 bFloating = FALSE;
00162 break;
00163
00164 case GDT_UInt32:
00165 nBits = 32;
00166 bSigned = FALSE;
00167 bFloating = FALSE;
00168 break;
00169
00170 case GDT_Float32:
00171 case GDT_CFloat32:
00172 nBits = 32;
00173 bSigned = TRUE;
00174 bFloating = TRUE;
00175 break;
00176
00177 case GDT_Float64:
00178 case GDT_CFloat64:
00179 nBits = 64;
00180 bSigned = TRUE;
00181 bFloating = TRUE;
00182 break;
00183
00184 default:
00185 CPLAssert( FALSE );
00186 return GDT_Unknown;
00187 }
00188
00189 switch( eType2 )
00190 {
00191 case GDT_Byte:
00192 break;
00193
00194 case GDT_Int16:
00195 nBits = MAX(nBits,16);
00196 bSigned = TRUE;
00197 break;
00198
00199 case GDT_UInt16:
00200 nBits = MAX(nBits,16);
00201 break;
00202
00203 case GDT_Int32:
00204 case GDT_CInt32:
00205 nBits = MAX(nBits,32);
00206 bSigned = TRUE;
00207 break;
00208
00209 case GDT_UInt32:
00210 nBits = MAX(nBits,32);
00211 break;
00212
00213 case GDT_Float32:
00214 case GDT_CFloat32:
00215 nBits = MAX(nBits,32);
00216 bSigned = TRUE;
00217 bFloating = TRUE;
00218 break;
00219
00220 case GDT_Float64:
00221 case GDT_CFloat64:
00222 nBits = MAX(nBits,64);
00223 bSigned = TRUE;
00224 bFloating = TRUE;
00225 break;
00226
00227 default:
00228 CPLAssert( FALSE );
00229 return GDT_Unknown;
00230 }
00231
00232 if( nBits == 8 )
00233 return GDT_Byte;
00234 else if( nBits == 16 && bComplex )
00235 return GDT_CInt16;
00236 else if( nBits == 16 && bSigned )
00237 return GDT_Int16;
00238 else if( nBits == 16 && !bSigned )
00239 return GDT_UInt16;
00240 else if( nBits == 32 && bFloating && bComplex )
00241 return GDT_CFloat32;
00242 else if( nBits == 32 && bFloating )
00243 return GDT_Float32;
00244 else if( nBits == 32 && bComplex )
00245 return GDT_CInt32;
00246 else if( nBits == 32 && bSigned )
00247 return GDT_Int32;
00248 else if( nBits == 32 && !bSigned )
00249 return GDT_UInt32;
00250 else if( nBits == 64 && bComplex )
00251 return GDT_CFloat64;
00252 else
00253 return GDT_Float64;
00254 }
00255
00256
00257
00258
00259
00260 int GDALGetDataTypeSize( GDALDataType eDataType )
00261
00262 {
00263 switch( eDataType )
00264 {
00265 case GDT_Byte:
00266 return 8;
00267
00268 case GDT_UInt16:
00269 case GDT_Int16:
00270 return 16;
00271
00272 case GDT_UInt32:
00273 case GDT_Int32:
00274 case GDT_Float32:
00275 case GDT_CInt16:
00276 return 32;
00277
00278 case GDT_Float64:
00279 case GDT_CInt32:
00280 case GDT_CFloat32:
00281 return 64;
00282
00283 case GDT_CFloat64:
00284 return 128;
00285
00286 default:
00287 CPLAssert( FALSE );
00288 return 0;
00289 }
00290 }
00291
00292
00293
00294
00295
00296 int GDALDataTypeIsComplex( GDALDataType eDataType )
00297
00298 {
00299 switch( eDataType )
00300 {
00301 case GDT_CInt16:
00302 case GDT_CInt32:
00303 case GDT_CFloat32:
00304 case GDT_CFloat64:
00305 return TRUE;
00306
00307 default:
00308 return FALSE;
00309 }
00310 }
00311
00312
00313
00314
00315
00316 const char *GDALGetDataTypeName( GDALDataType eDataType )
00317
00318 {
00319 switch( eDataType )
00320 {
00321 case GDT_Byte:
00322 return "Byte";
00323
00324 case GDT_UInt16:
00325 return "UInt16";
00326
00327 case GDT_Int16:
00328 return "Int16";
00329
00330 case GDT_UInt32:
00331 return "UInt32";
00332
00333 case GDT_Int32:
00334 return "Int32";
00335
00336 case GDT_Float32:
00337 return "Float32";
00338
00339 case GDT_Float64:
00340 return "Float64";
00341
00342 case GDT_CInt16:
00343 return "CInt16";
00344
00345 case GDT_CInt32:
00346 return "CInt32";
00347
00348 case GDT_CFloat32:
00349 return "CFloat32";
00350
00351 case GDT_CFloat64:
00352 return "CFloat64";
00353
00354 default:
00355 return NULL;
00356 }
00357 }
00358
00359
00360
00361
00362
00363 const char *GDALGetPaletteInterpretationName( GDALPaletteInterp eInterp )
00364
00365 {
00366 switch( eInterp )
00367 {
00368 case GPI_Gray:
00369 return "Gray";
00370
00371 case GPI_RGB:
00372 return "RGB";
00373
00374 case GPI_CMYK:
00375 return "CMYK";
00376
00377 case GPI_HLS:
00378 return "HLS";
00379
00380 default:
00381 return "Unknown";
00382 }
00383 }
00384
00385
00386
00387
00388
00389 const char *GDALGetColorInterpretationName( GDALColorInterp eInterp )
00390
00391 {
00392 switch( eInterp )
00393 {
00394 case GCI_Undefined:
00395 return "Undefined";
00396
00397 case GCI_GrayIndex:
00398 return "Gray";
00399
00400 case GCI_PaletteIndex:
00401 return "Palette";
00402
00403 case GCI_RedBand:
00404 return "Red";
00405
00406 case GCI_GreenBand:
00407 return "Green";
00408
00409 case GCI_BlueBand:
00410 return "Blue";
00411
00412 case GCI_AlphaBand:
00413 return "Alpha";
00414
00415 case GCI_HueBand:
00416 return "Hue";
00417
00418 case GCI_SaturationBand:
00419 return "Saturation";
00420
00421 case GCI_LightnessBand:
00422 return "Lightness";
00423
00424 case GCI_CyanBand:
00425 return "Cyan";
00426
00427 case GCI_MagentaBand:
00428 return "Magenta";
00429
00430 case GCI_YellowBand:
00431 return "Yellow";
00432
00433 case GCI_BlackBand:
00434 return "Black";
00435
00436 default:
00437 return "Unknown";
00438 }
00439 }
00440
00441
00442
00443
00444
00463 void GDALComputeRasterMinMax( GDALRasterBandH hBand, int bApproxOK,
00464 double adfMinMax[2] )
00465
00466 {
00467 double dfMin=0.0, dfMax=0.0;
00468 GDALRasterBand *poBand;
00469
00470
00471
00472
00473 if( bApproxOK )
00474 {
00475 int bSuccessMin, bSuccessMax;
00476
00477 dfMin = GDALGetRasterMinimum( hBand, &bSuccessMin );
00478 dfMax = GDALGetRasterMaximum( hBand, &bSuccessMax );
00479
00480 if( bSuccessMin && bSuccessMax )
00481 {
00482 adfMinMax[0] = dfMin;
00483 adfMinMax[1] = dfMax;
00484 return;
00485 }
00486 }
00487
00488
00489
00490
00491 if( bApproxOK )
00492 poBand = (GDALRasterBand *) GDALGetRasterSampleOverview( hBand, 2500 );
00493 else
00494 poBand = (GDALRasterBand *) hBand;
00495
00496
00497
00498
00499
00500 int nBlockXSize, nBlockYSize;
00501 int nBlocksPerRow, nBlocksPerColumn;
00502 int nSampleRate;
00503 int bGotNoDataValue, bFirstValue = TRUE;
00504 double dfNoDataValue;
00505
00506 dfNoDataValue = poBand->GetNoDataValue( &bGotNoDataValue );
00507
00508 poBand->GetBlockSize( &nBlockXSize, &nBlockYSize );
00509 nBlocksPerRow = (poBand->GetXSize() + nBlockXSize - 1) / nBlockXSize;
00510 nBlocksPerColumn = (poBand->GetYSize() + nBlockYSize - 1) / nBlockYSize;
00511
00512 if( bApproxOK )
00513 nSampleRate =
00514 (int) MAX(1,sqrt((double) nBlocksPerRow * nBlocksPerColumn));
00515 else
00516 nSampleRate = 1;
00517
00518 for( int iSampleBlock = 0;
00519 iSampleBlock < nBlocksPerRow * nBlocksPerColumn;
00520 iSampleBlock += nSampleRate )
00521 {
00522 double dfValue = 0.0;
00523 int iXBlock, iYBlock, nXCheck, nYCheck;
00524 GDALRasterBlock *poBlock;
00525
00526 iYBlock = iSampleBlock / nBlocksPerRow;
00527 iXBlock = iSampleBlock - nBlocksPerRow * iYBlock;
00528
00529 poBlock = poBand->GetBlockRef( iXBlock, iYBlock );
00530 if( poBlock == NULL )
00531 continue;
00532
00533 if( (iXBlock+1) * nBlockXSize > poBand->GetXSize() )
00534 nXCheck = poBand->GetXSize() - iXBlock * nBlockXSize;
00535 else
00536 nXCheck = nBlockXSize;
00537
00538 if( (iYBlock+1) * nBlockYSize > poBand->GetYSize() )
00539 nYCheck = poBand->GetYSize() - iYBlock * nBlockYSize;
00540 else
00541 nYCheck = nBlockYSize;
00542
00543
00544 for( int iY = 0; iY < nYCheck; iY++ )
00545 {
00546 for( int iX = 0; iX < nXCheck; iX++ )
00547 {
00548 int iOffset = iX + iY * nBlockXSize;
00549
00550 switch( poBlock->GetDataType() )
00551 {
00552 case GDT_Byte:
00553 dfValue = ((GByte *) poBlock->GetDataRef())[iOffset];
00554 break;
00555 case GDT_UInt16:
00556 dfValue = ((GUInt16 *) poBlock->GetDataRef())[iOffset];
00557 break;
00558 case GDT_Int16:
00559 dfValue = ((GInt16 *) poBlock->GetDataRef())[iOffset];
00560 break;
00561 case GDT_UInt32:
00562 dfValue = ((GUInt32 *) poBlock->GetDataRef())[iOffset];
00563 break;
00564 case GDT_Int32:
00565 dfValue = ((GInt32 *) poBlock->GetDataRef())[iOffset];
00566 break;
00567 case GDT_Float32:
00568 dfValue = ((float *) poBlock->GetDataRef())[iOffset];
00569 break;
00570 case GDT_Float64:
00571 dfValue = ((double *) poBlock->GetDataRef())[iOffset];
00572 break;
00573 case GDT_CInt16:
00574 dfValue = ((GInt16 *) poBlock->GetDataRef())[iOffset*2];
00575 break;
00576 case GDT_CInt32:
00577 dfValue = ((GInt32 *) poBlock->GetDataRef())[iOffset*2];
00578 break;
00579 case GDT_CFloat32:
00580 dfValue = ((float *) poBlock->GetDataRef())[iOffset*2];
00581 break;
00582 case GDT_CFloat64:
00583 dfValue = ((double *) poBlock->GetDataRef())[iOffset*2];
00584 break;
00585 default:
00586 CPLAssert( FALSE );
00587 }
00588
00589 if( bGotNoDataValue && dfValue == dfNoDataValue )
00590 continue;
00591
00592 if( bFirstValue )
00593 {
00594 dfMin = dfMax = dfValue;
00595 bFirstValue = FALSE;
00596 }
00597 else
00598 {
00599 dfMin = MIN(dfMin,dfValue);
00600 dfMax = MAX(dfMax,dfValue);
00601 }
00602 }
00603 }
00604 }
00605
00606 adfMinMax[0] = dfMin;
00607 adfMinMax[1] = dfMax;
00608 }
00609
00610
00611
00612
00613
00678 int GDALDummyProgress( double, const char *, void * )
00679
00680 {
00681 return TRUE;
00682 }
00683
00684
00685
00686
00687 typedef struct {
00688 GDALProgressFunc pfnProgress;
00689 void *pData;
00690 double dfMin;
00691 double dfMax;
00692 } GDALScaledProgressInfo;
00693
00694 int GDALScaledProgress( double dfComplete, const char *pszMessage,
00695 void *pData )
00696
00697 {
00698 GDALScaledProgressInfo *psInfo = (GDALScaledProgressInfo *) pData;
00699
00700 return psInfo->pfnProgress( dfComplete * (psInfo->dfMax - psInfo->dfMin)
00701 + psInfo->dfMin,
00702 pszMessage, psInfo->pData );
00703 }
00704
00705
00706
00707
00708
00709 void *GDALCreateScaledProgress( double dfMin, double dfMax,
00710 GDALProgressFunc pfnProgress,
00711 void * pData )
00712
00713 {
00714 GDALScaledProgressInfo *psInfo;
00715
00716 psInfo = (GDALScaledProgressInfo *)
00717 CPLCalloc(sizeof(GDALScaledProgressInfo),1);
00718
00719 if( ABS(dfMin-dfMax) < 0.0000001 )
00720 dfMax = dfMin + 0.01;
00721
00722 psInfo->pData = pData;
00723 psInfo->pfnProgress = pfnProgress;
00724 psInfo->dfMin = dfMin;
00725 psInfo->dfMax = dfMax;
00726
00727 return (void *) psInfo;
00728 }
00729
00730
00731
00732
00733
00734 void GDALDestroyScaledProgress( void * pData )
00735
00736 {
00737 CPLFree( pData );
00738 }
00739
00740
00741
00742
00743
00744 int GDALTermProgress( double dfComplete, const char *pszMessage, void * )
00745
00746 {
00747 static double dfLastComplete = -1.0;
00748
00749 if( dfLastComplete > dfComplete )
00750 {
00751 if( dfLastComplete > 1.0 )
00752 dfLastComplete = -1.0;
00753 else
00754 dfLastComplete = dfComplete;
00755 }
00756
00757 if( floor(dfLastComplete*10) != floor(dfComplete*10) )
00758 {
00759 int nPercent = (int) floor(dfComplete*100);
00760
00761 if( nPercent == 0 && pszMessage != NULL )
00762 fprintf( stdout, "%s:", pszMessage );
00763
00764 if( nPercent == 100 )
00765 fprintf( stdout, "%d - done.\n", (int) floor(dfComplete*100) );
00766 else
00767 {
00768 fprintf( stdout, "%d.", (int) floor(dfComplete*100) );
00769 fflush( stdout );
00770 }
00771 }
00772 else if( floor(dfLastComplete*30) != floor(dfComplete*30) )
00773 {
00774 fprintf( stdout, "." );
00775 fflush( stdout );
00776 }
00777
00778 dfLastComplete = dfComplete;
00779
00780 return TRUE;
00781 }
00782
00783
00784
00785
00786
00802 GDALRasterBandH GDALGetRasterSampleOverview( GDALRasterBandH hBand,
00803 int nDesiredSamples )
00804
00805 {
00806 int nBestSamples;
00807 GDALRasterBandH hBestBand = hBand;
00808
00809 nBestSamples = GDALGetRasterBandXSize(hBand)
00810 * GDALGetRasterBandYSize(hBand);
00811
00812 for( int iOverview = 0;
00813 iOverview < GDALGetOverviewCount( hBand );
00814 iOverview++ )
00815 {
00816 GDALRasterBandH hOBand = GDALGetOverview( hBand, iOverview );
00817 int nOSamples;
00818
00819 nOSamples = GDALGetRasterBandXSize(hOBand)
00820 * GDALGetRasterBandYSize(hOBand);
00821
00822 if( nOSamples < nBestSamples && nOSamples > nDesiredSamples )
00823 {
00824 nBestSamples = nOSamples;
00825 hBestBand = hOBand;
00826 }
00827 }
00828
00829 return hBestBand;
00830 }
00831
00832
00833
00834
00835
00836 int GDALGetRandomRasterSample( GDALRasterBandH hBand, int nSamples,
00837 float *pafSampleBuf )
00838
00839 {
00840 GDALRasterBand *poBand;
00841
00842 poBand = (GDALRasterBand *) GDALGetRasterSampleOverview( hBand, nSamples );
00843
00844
00845
00846
00847
00848 int nBlockXSize, nBlockYSize;
00849 int nBlocksPerRow, nBlocksPerColumn;
00850 int nSampleRate;
00851 int bGotNoDataValue;
00852 double dfNoDataValue;
00853 int nActualSamples = 0;
00854 int nBlockSampleRate;
00855
00856 dfNoDataValue = poBand->GetNoDataValue( &bGotNoDataValue );
00857
00858 poBand->GetBlockSize( &nBlockXSize, &nBlockYSize );
00859 nBlocksPerRow = (poBand->GetXSize() + nBlockXSize - 1) / nBlockXSize;
00860 nBlocksPerColumn = (poBand->GetYSize() + nBlockYSize - 1) / nBlockYSize;
00861
00862 nSampleRate =
00863 (int) MAX(1,sqrt((double) nBlocksPerRow * nBlocksPerColumn)-2.0);
00864
00865 if( nSampleRate == nBlocksPerRow && nSampleRate > 1 )
00866 nSampleRate--;
00867
00868 nBlockSampleRate = MAX(1,(nBlockXSize * nBlockYSize) /
00869 (nSamples / (nBlocksPerRow*nBlocksPerColumn / nSampleRate)));
00870
00871 for( int iSampleBlock = 0;
00872 iSampleBlock < nBlocksPerRow * nBlocksPerColumn;
00873 iSampleBlock += nSampleRate )
00874 {
00875 double dfValue = 0.0;
00876 int iXBlock, iYBlock, nYCheck, iOffset;
00877 GDALRasterBlock *poBlock;
00878
00879 iYBlock = iSampleBlock / nBlocksPerRow;
00880 iXBlock = iSampleBlock - nBlocksPerRow * iYBlock;
00881
00882 poBlock = poBand->GetBlockRef( iXBlock, iYBlock );
00883 if( poBlock == NULL )
00884 continue;
00885
00886 if( (iYBlock+1) * nBlockYSize > poBand->GetYSize() )
00887 nYCheck = poBand->GetYSize() - iYBlock * nBlockYSize;
00888 else
00889 nYCheck = nBlockYSize;
00890
00891
00892 for( iOffset = nBlockXSize*nBlockYSize-1;
00893 iOffset >= 0 && nActualSamples < nSamples;
00894 iOffset -= nBlockSampleRate )
00895 {
00896 switch( poBlock->GetDataType() )
00897 {
00898 case GDT_Byte:
00899 dfValue = ((GByte *) poBlock->GetDataRef())[iOffset];
00900 break;
00901 case GDT_UInt16:
00902 dfValue = ((GUInt16 *) poBlock->GetDataRef())[iOffset];
00903 break;
00904 case GDT_Int16:
00905 dfValue = ((GInt16 *) poBlock->GetDataRef())[iOffset];
00906 break;
00907 case GDT_UInt32:
00908 dfValue = ((GUInt32 *) poBlock->GetDataRef())[iOffset];
00909 break;
00910 case GDT_Int32:
00911 dfValue = ((GInt32 *) poBlock->GetDataRef())[iOffset];
00912 break;
00913 case GDT_Float32:
00914 dfValue = ((float *) poBlock->GetDataRef())[iOffset];
00915 break;
00916 case GDT_Float64:
00917 dfValue = ((double *) poBlock->GetDataRef())[iOffset];
00918 break;
00919 case GDT_CInt16:
00920 dfValue = ((GInt16 *) poBlock->GetDataRef())[iOffset*2];
00921 break;
00922 case GDT_CInt32:
00923 dfValue = ((GInt32 *) poBlock->GetDataRef())[iOffset*2];
00924 break;
00925 case GDT_CFloat32:
00926 dfValue = ((float *) poBlock->GetDataRef())[iOffset*2];
00927 break;
00928 case GDT_CFloat64:
00929 dfValue = ((double *) poBlock->GetDataRef())[iOffset*2];
00930 break;
00931 default:
00932 CPLAssert( FALSE );
00933 }
00934
00935 if( bGotNoDataValue && dfValue == dfNoDataValue )
00936 continue;
00937
00938 pafSampleBuf[nActualSamples++] = dfValue;
00939 }
00940 }
00941
00942 return nActualSamples;
00943 }
00944
00945
00946
00947
00948
00949 void GDALInitGCPs( int nCount, GDAL_GCP * psGCP )
00950
00951 {
00952 for( int iGCP = 0; iGCP < nCount; iGCP++ )
00953 {
00954 memset( psGCP, 0, sizeof(GDAL_GCP) );
00955 psGCP->pszId = CPLStrdup("");
00956 psGCP->pszInfo = CPLStrdup("");
00957 psGCP++;
00958 }
00959 }
00960
00961
00962
00963
00964
00965 void GDALDeinitGCPs( int nCount, GDAL_GCP * psGCP )
00966
00967 {
00968 for( int iGCP = 0; iGCP < nCount; iGCP++ )
00969 {
00970 CPLFree( psGCP->pszId );
00971 CPLFree( psGCP->pszInfo );
00972 psGCP++;
00973 }
00974 }
00975
00976
00977
00978
00979
00980 GDAL_GCP *GDALDuplicateGCPs( int nCount, const GDAL_GCP *pasGCPList )
00981
00982 {
00983 GDAL_GCP *pasReturn;
00984
00985 pasReturn = (GDAL_GCP *) CPLMalloc(sizeof(GDAL_GCP) * nCount);
00986 GDALInitGCPs( nCount, pasReturn );
00987
00988 for( int iGCP = 0; iGCP < nCount; iGCP++ )
00989 {
00990 CPLFree( pasReturn[iGCP].pszId );
00991 pasReturn[iGCP].pszId = CPLStrdup( pasGCPList[iGCP].pszId );
00992
00993 CPLFree( pasReturn[iGCP].pszInfo );
00994 pasReturn[iGCP].pszInfo = CPLStrdup( pasGCPList[iGCP].pszInfo );
00995
00996 pasReturn[iGCP].dfGCPPixel = pasGCPList[iGCP].dfGCPPixel;
00997 pasReturn[iGCP].dfGCPLine = pasGCPList[iGCP].dfGCPLine;
00998 pasReturn[iGCP].dfGCPX = pasGCPList[iGCP].dfGCPX;
00999 pasReturn[iGCP].dfGCPY = pasGCPList[iGCP].dfGCPY;
01000 pasReturn[iGCP].dfGCPZ = pasGCPList[iGCP].dfGCPZ;
01001 }
01002
01003 return pasReturn;
01004 }
01005