00001 #include "hdfeosfrmt.h" 00002 #include <qmessagebox.h> 00003 #include "TraceLog.h" 00004 00005 HdfEosFrmt::~HdfEosFrmt( ) { 00006 SWclose( mSWfid ); 00007 for ( int i=0; i < (int)mGFList.size(); i++ ) { 00008 GeoField &gf = mGFList[i]; 00009 switch ( gf.type ) { 00010 case DFNT_FLOAT32: 00011 delete [] (float*)gf.geomap; 00012 break; 00013 00014 case DFNT_FLOAT64: 00015 delete [] (double*)gf.geomap; 00016 break; 00017 } 00018 } 00019 } 00020 00021 bool HdfEosFrmt::open( std::string fname ) { 00022 char *list; 00023 std::vector<std::string> swlist; 00024 std::vector<std::string> fldlist; 00025 int32 nret, nswath, bufsz, swid; 00026 int i; 00027 00028 mFName = fname; 00029 if ( mFName == "" ) return false; 00030 00031 mSWfid = SWopen( (char*)mFName.c_str(), DFACC_READ ); 00032 if ( mSWfid == -1 ) return false; 00033 00034 // GET NUMBER OF SWATHS AND LIST STRING SIZE 00035 nswath = SWinqswath( (char*)mFName.c_str(), NULL, &bufsz ); 00036 if ( nswath < 1 || bufsz < 1 ) return false; 00037 00038 list = new char[bufsz+2]; 00039 list[bufsz+1] = (char)0; 00040 SWinqswath( (char*)mFName.c_str(), list, &bufsz ); 00041 swlist = splitList( list, ',' ); 00042 delete [] list; 00043 00044 for ( i=0; i < nswath; i++ ) { 00045 int nfield; 00046 int32 *rank, *type, *dims; 00047 00048 swid = SWattach( mSWfid, (char*)swlist[i].c_str() ); 00049 if ( swid == -1 ) continue; // UNABLE TO ATTACH 00050 00051 parseGeoFlds( swid, swlist[i] ); 00052 00053 nret = SWnentries( swid, HDFE_NENTDFLD, &bufsz ); 00054 if ( nret <= 0 ) continue; // NO DATA FIELDS 00055 00056 rank = new int32[nret]; 00057 type = new int32[nret]; 00058 list = new char[bufsz]; 00059 nfield = SWinqdatafields( swid, list, rank, type ); 00060 00061 fldlist = splitList( list, ',' ); 00062 delete [] list; 00063 00064 for ( int ifld=0; ifld < (int)fldlist.size(); ifld++ ) { 00065 int32 ndims; 00066 double min = 0.0; 00067 double max = 0.0; 00068 DataType btype; 00069 DataField df; 00070 df.swathname = swlist[i]; 00071 df.fieldname = fldlist[ifld]; 00072 df.type = type[ifld]; 00073 00074 // if( df.type == NOT_DEFINED ) 00075 // continue; 00076 00077 dims = new int32[ rank[ifld] ]; 00078 list = new char[300]; 00079 memset( list, 0, 300 ); 00080 nret = SWfieldinfo( swid, (char*)fldlist[ifld].c_str(), 00081 &ndims, dims, &df.type, list ); 00082 00083 if ( ndims != 2 || dims[0] < 50 || dims[1] < 50 ) { 00084 delete [] dims; 00085 delete [] list; 00086 continue; 00087 } 00088 00089 df.dimnames = splitList( list, ',' ); 00090 delete [] list; 00091 00092 for ( int idim=0; idim < ndims; idim++ ) 00093 df.dims.push_back( dims[ndims-idim-1] ); 00094 delete [] dims; 00095 00096 switch ( df.type ) { 00097 case DFNT_INT8: 00098 min = -127; 00099 max = 128; 00100 btype = INT8; 00101 break; 00102 00103 case DFNT_UINT8: 00104 min = 0; 00105 max = 255; 00106 btype = UINT8; 00107 break; 00108 00109 case DFNT_INT16: 00110 { 00111 short lwr=32767, upr=-32767; 00112 00113 // original 00114 //min = lwr; 00115 //max = upr; 00116 //findrange( swid, df.fieldname, lwr, upr, df.dims ); 00117 00118 // dls did this to fix problem reading INT16 HDF data 00119 findrange( swid, df.fieldname, lwr, upr, df.dims ); 00120 min = lwr; 00121 max = upr; 00122 00123 btype = INT16; 00124 00125 } 00126 break; 00127 00128 case DFNT_UINT16: 00129 { 00130 unsigned short lwr=65535, upr = 0; 00131 00132 findrange( swid, df.fieldname, lwr, upr, df.dims ); 00133 min = lwr; 00134 max = upr; 00135 00136 btype = UINT16; 00137 } 00138 break; 00139 00140 default: 00141 btype = NOT_DEFINED; 00142 } 00143 00144 00145 BandInf b; 00146 b.name = (char*)(df.swathname+"-"+df.fieldname).c_str(); 00147 b.ndims = ndims; 00148 b.width = df.dims[0]; 00149 b.height = df.dims[1]; 00150 b.max = max; 00151 b.min = min; 00152 b.type = btype; 00153 00154 if ( ! (b.type == NOT_DEFINED) ) { 00155 mBandSet.push_back( b ); 00156 mDFList.push_back( df ); 00157 } 00158 00159 00160 } // END DATA FIELD 00161 00162 delete [] rank; 00163 delete [] type; 00164 00165 SWdetach( swid ); 00166 } // END SWATH 00167 00168 if ( mDFList.size() == 0 ) 00169 return false; 00170 00171 // FILL IN IMAGE INFO 00172 if (mImageInf.mAquiDateTime.size() == 0) { 00173 mImageInf.mAquiDateTime = getAquiDateTime( fname ); 00174 } 00175 if (mImageInf.mCloudPct == 0) { 00176 mImageInf.mCloudPct = atof( getCloudPct( fname ).c_str() ); 00177 } 00178 if (mImageInf.mImageAzim == 0) { 00179 mImageInf.mImageAzim = atof( getImageAzim( fname ).c_str() ); 00180 } 00181 if (mImageInf.mOrigID.size() == 0) { 00182 mImageInf.mOrigID = getOrigID( fname ); 00183 } 00184 if (mImageInf.mInstrument_zenith == 0) { 00185 mImageInf.mInstrument_zenith = atof( getInstZenith( fname ).c_str() ); 00186 } 00187 if (mImageInf.mSunAzim == 0) { 00188 mImageInf.mSunAzim = atof( getSunAzim( fname ).c_str() ); 00189 } 00190 if (mImageInf.mSunElev == 0) { 00191 mImageInf.mSunElev = atof( getSunElev( fname ).c_str() ); 00192 } 00193 if (mImageInf.mProjection.size() == 0) { 00194 mImageInf.mProjection = getProjection( fname ); 00195 } 00196 00197 mImageInf.mLocURL = fname ; 00198 00199 // 2007-06-14 dls - Removed image ID references and functions 00200 /* 00201 if (mImageInf.mImageID.size() <= 0) { 00202 mImageInf.mImageID = getImageID( fname ); 00203 } 00204 */ 00205 if (mImageInf.mInstID.size() <= 0) { 00206 mImageInf.mInstID = getInstID( fname ); 00207 } 00208 if (mImageInf.mInstrument_azimuth <= 0) { 00209 mImageInf.mInstrument_azimuth = atof(getInstAz( fname ).c_str() ) ; 00210 } 00211 00212 00213 00214 // LOAD THE GEOFIELDS ASSOCIATED WITH EACH BAND INTO THE DATAFIELD 00215 for ( int iband=0; iband < (int)mBandSet.size(); iband++ ) { 00216 getGeoFields( iband ); 00217 } 00218 00219 getBandMetaData(); 00220 getULCorners(); 00221 00222 if ((int)mBandSet.size()) { 00223 double x = mBandSet[0].width / 2; 00224 double y = mBandSet[0].height / 2; 00225 getLL( 0, x, y ); 00226 mImageInf.mCenterLat = y; 00227 mImageInf.mCenterLon = x; 00228 } 00229 00230 return true; 00231 } 00232 00233 void HdfEosFrmt::getGeoFields( int iband ) { 00234 int32 swid; 00235 int32 iLat = -1; 00236 int32 iLon = -1; 00237 int32 latoff[2]; 00238 int32 lonoff[2]; 00239 int32 latinc[2]; 00240 int32 loninc[2]; 00241 int32 ret; 00242 DataField &df = mDFList[iband]; 00243 00244 /* 00245 if( df.dimnames.size() <= 1 ) 00246 return; 00247 */ 00248 00249 swid = SWattach( mSWfid, (char*)df.swathname.c_str() ); 00250 if ( swid == -1 ) return; 00251 00252 for ( int ind=0; ind < (int)mGFList.size(); ind++ ) { 00253 if ( mGFList[ind].swathname != df.swathname ) 00254 continue; 00255 00256 if ( mGFList[ind].gfldname == "Latitude" ) 00257 iLat = ind; 00258 00259 if ( mGFList[ind].gfldname == "Longitude" ) 00260 iLon = ind; 00261 } 00262 00263 if ( iLat == -1 || iLon == -1 ) { 00264 SWdetach( swid ); 00265 return; 00266 } 00267 00268 // GET HORIZONTAL MAPPINGS 00269 ret = SWmapinfo( swid, 00270 (char*)mGFList[iLon].dimnames[0].c_str(), 00271 (char*)df.dimnames[0].c_str(), 00272 &lonoff[0], &loninc[0] ); 00273 00274 // GET VERTICAL MAPPINGS 00275 ret = SWmapinfo( swid, 00276 (char*)mGFList[iLon].dimnames[1].c_str(), 00277 (char*)df.dimnames[1].c_str(), 00278 &lonoff[1], &loninc[1] ); 00279 00280 // GET HORIZONTAL MAPPINGS 00281 ret = SWmapinfo( swid, 00282 (char*)mGFList[iLat].dimnames[0].c_str(), 00283 (char*)df.dimnames[0].c_str(), 00284 &latoff[0], &latinc[0] ); 00285 00286 // GET VERTICAL MAPPINGS 00287 ret = SWmapinfo( swid, 00288 (char*)mGFList[iLat].dimnames[1].c_str(), 00289 (char*)df.dimnames[1].c_str(), 00290 &latoff[1], &latinc[1] ); 00291 00292 df.geofldlat = &mGFList[iLat]; 00293 df.geofldlon = &mGFList[iLon]; 00294 00295 if ( latoff[0] < 0 || latoff[0] > df.dims[0] ) 00296 latoff[0] = 0; 00297 if ( latoff[1] < 0 || latoff[1] > df.dims[1] ) 00298 latoff[1] = 0; 00299 if ( lonoff[0] < 0 || lonoff[0] > df.dims[0] ) 00300 lonoff[0] = 0; 00301 if ( lonoff[1] < 0 || lonoff[1] > df.dims[1] ) 00302 lonoff[1] = 0; 00303 00304 df.latoff.push_back( latoff[0] ); 00305 df.latoff.push_back( latoff[1] ); 00306 df.lonoff.push_back( lonoff[0] ); 00307 df.lonoff.push_back( lonoff[1] ); 00308 00309 df.latinc.push_back( latinc[0] ); 00310 df.latinc.push_back( latinc[1] ); 00311 df.loninc.push_back( loninc[0] ); 00312 df.loninc.push_back( loninc[1] ); 00313 00314 SWdetach( swid ); 00315 } 00316 00317 void HdfEosFrmt::getLL( int iband, double &i, double &j, bool toWGS84 ) { 00318 double lat; 00319 double lon; 00320 DataField &df = mDFList[iband]; 00321 00322 if ( iband < 0 || iband > (int)mBandSet.size() || 00323 i < 0 || i > mBandSet[iband].width || 00324 j < 0 || j > mBandSet[iband].height ) { 00325 i = 0; 00326 j = 0; 00327 return; 00328 } 00329 00330 switch ( df.geofldlon->type ) { 00331 case DFNT_FLOAT32: 00332 bilinterp( (float*)df.geofldlon->geomap, 00333 df.geofldlon->dims, 00334 df.lonoff, 00335 df.loninc, 00336 (int)i, 00337 (int)j, 00338 lon ); 00339 break; 00340 00341 case DFNT_FLOAT64: 00342 bilinterp( (double*)df.geofldlon->geomap, 00343 df.geofldlon->dims, 00344 df.lonoff, 00345 df.loninc, 00346 (int)i, 00347 (int)j, 00348 lon ); 00349 break; 00350 00351 default: 00352 // CLEAN UP HERE 00353 break; 00354 } 00355 00356 switch ( df.geofldlat->type ) { 00357 case DFNT_FLOAT32: 00358 bilinterp( (float*)df.geofldlat->geomap, 00359 df.geofldlat->dims, 00360 df.latoff, 00361 df.latinc, 00362 (int)i, 00363 (int)j, 00364 lat ); 00365 break; 00366 00367 case DFNT_FLOAT64: 00368 bilinterp( (double*)df.geofldlat->geomap, 00369 df.geofldlat->dims, 00370 df.latoff, 00371 df.latinc, 00372 (int)i, 00373 (int)j, 00374 lat ); 00375 break; 00376 } 00377 00378 00379 /* CONVERT GEODEDIC TO GEOCENTRIC LAT */ 00380 // double wgs84_C = 1.0067395; 00381 if ( toWGS84 ) { 00382 double wgs84_C = 1.00673797751; 00383 lat = (180.0/M_PI) * atan( ( tan(lat*(M_PI/180.0) ) * wgs84_C ) ); 00384 } 00385 if (lon < 0.0) { 00386 lon += 360.0 ; 00387 } 00388 i = lon; 00389 j = lat; 00390 } 00391 00392 void HdfEosFrmt::getXY( int iband, double &i, double &j ) { 00393 DataField &df = mDFList[iband]; 00394 GeoField &gflat = *df.geofldlat; 00395 GeoField &gflon = *df.geofldlon; 00396 int x, y; 00397 int mapw, maph; 00398 bool latfound, lonfound; 00399 double lon, lat; 00400 int imgw, imgh; 00401 00402 double wgs84_C = 1.00673797751; 00403 std::vector<int*> cross_set; 00404 00405 if ( iband < 0 || iband > (int)mBandSet.size() ) { 00406 return; 00407 } 00408 00409 if ( mBandSet[iband].proj != "" ) { 00410 llToXY( iband, i, j ); 00411 return; 00412 } 00413 00414 imgw = mBandSet[iband].width; 00415 imgh = mBandSet[iband].height; 00416 lon = i; 00417 lat = j; 00418 i = -999999.0; 00419 j = -999999.0; 00420 00421 // CONVERT TO GEOCENTRIC COORDINATES AS THE LAT/LON GRID IS IN 00422 lat = atan( tan(lat / (180.0/M_PI)) / wgs84_C ) / (M_PI/180.0); 00423 00424 // GET THE GEOGRAPHICAL COORDINATE MAPS FOR LAT/LON OF THIS BAND 00425 mapw = gflon.dims[1]; 00426 maph = gflon.dims[0]; 00427 00428 // SEARCHING THE LONGITUDE TABLE HERE FOR INTERSECTION OF THE INPUT 00429 // LONGITUDE. ONLY TRYING TO FIND ONE TO VERIFY IT'S ON THE GRID. 00430 lonfound = false; 00431 latfound = false; 00432 for ( y=0; y < maph && !lonfound; y++ ) { 00433 for ( x=0; x < mapw && !lonfound; x++ ) { 00434 // SEARCH HORIZONTAL LINE 00435 if ( x < mapw-1 ) { 00436 if ( gflon.type == DFNT_FLOAT32 ) { 00437 float *data = (float*)gflon.geomap; 00438 if ( between( data[y*mapw + x], data[y*mapw + x+1], lon ) ) { 00439 lonfound = true; 00440 continue; 00441 } 00442 } else if ( gflon.type == DFNT_FLOAT64 ) { 00443 double *data = (double*)gflon.geomap; 00444 if ( between( data[y*mapw + x], data[y*mapw + x+1], lon ) ) { 00445 lonfound = true; 00446 continue; 00447 } 00448 } 00449 } 00450 00451 // SEARCH VERTICAL LINE 00452 if ( y < maph-1 ) { 00453 if ( gflon.type == DFNT_FLOAT32 ) { 00454 float *data = (float*)gflon.geomap; 00455 if ( between( data[y*mapw + x], data[(y+1)*mapw + x], lon ) ) { 00456 lonfound = true; 00457 continue; 00458 } 00459 } else if ( gflon.type == DFNT_FLOAT64 ) { 00460 double *data = (double*)gflon.geomap; 00461 if ( between( data[y*mapw + x], data[(y+1)*mapw + x], lon ) ) { 00462 lonfound = true; 00463 continue; 00464 } 00465 } 00466 } 00467 } 00468 } 00469 00470 mapw = gflat.dims[1]; 00471 maph = gflat.dims[0]; 00472 for ( y=0; y < maph && !latfound; y++ ) { 00473 for ( x=0; x < mapw && !latfound; x++ ) { 00474 // SEARCH HORIZONTAL LINE 00475 if ( x < mapw-1 ) { 00476 if ( gflon.type == DFNT_FLOAT32 ) { 00477 float *data = (float*)gflat.geomap; 00478 if ( between( data[y*mapw + x], data[y*mapw + x+1], lat ) ) { 00479 latfound = true; 00480 continue; 00481 } 00482 } else if ( gflon.type == DFNT_FLOAT64 ) { 00483 double *data = (double*)gflat.geomap; 00484 if ( between( data[y*mapw + x], data[y*mapw + x+1], lat ) ) { 00485 latfound = true; 00486 continue; 00487 } 00488 } 00489 } 00490 00491 // SEARCH VERTICAL LINE 00492 if ( y < maph-1 ) { 00493 if ( gflon.type == DFNT_FLOAT32 ) { 00494 float *data = (float*)gflat.geomap; 00495 if ( between( data[y*mapw + x], data[(y+1)*mapw + x], lat ) ) { 00496 latfound = true; 00497 continue; 00498 } 00499 } else if ( gflon.type == DFNT_FLOAT64 ) { 00500 double *data = (double*)gflat.geomap; 00501 if ( between( data[y*mapw + x], data[(y+1)*mapw + x], lat ) ) { 00502 latfound = true; 00503 continue; 00504 } 00505 } 00506 } 00507 00508 } 00509 } 00510 00511 if ( !lonfound || !latfound ) { 00512 return; 00513 } 00514 00515 // SEARCH THE LAT GRID STORING ALL INTERSECTIONS. IF ONE NOT FOUND THEN 00516 // INPUT COORDS NOT ON IMAGE. 00517 // 00518 // COULD THIS JUST DO 24 ITERATIONS, 12 IN X AND 12 IN Y, CHECKING FOR 00519 // AN INTERSECTION ON THE LINE FOR THE LENGTH OF THE GRID??? 00520 // 00521 bool found = false; 00522 mapw = gflat.dims[1]; 00523 maph = gflat.dims[0]; 00524 00525 //int track, p1, p2; 00526 //int *set; 00527 00528 for ( y=0; y < maph; y++ ) { 00529 for ( x=0; x < mapw; x++ ) { 00530 int track, p1, p2; 00531 int *set; 00532 /* 00533 // SEARCH HORIZONTAL LINE 00534 if( x < mapw-1 ) 00535 { 00536 if( gflat.type == DFNT_FLOAT32 ) 00537 { 00538 float *data = (float*)gflat.geomap; 00539 if( between( data[y*mapw + x], data[y*mapw + x+1], lat ) ) 00540 { 00541 found = true; 00542 track = df.latoff[1] + (y * df.latinc[1]); 00543 p1 = df.latoff[0] + (x * df.latinc[0]); 00544 p2 = df.latoff[0] + ((x+1) * df.latinc[0]); 00545 getIntersect( track, p1, p2, iband, lat, false, true ); 00546 set = new int[2]; 00547 set[0] = p1; 00548 set[1] = track; 00549 cross_set.push_back( set ); 00550 } 00551 } else if( gflat.type == DFNT_FLOAT64 ) { 00552 double *data = (double*)gflat.geomap; 00553 if( between( data[y*mapw + x], data[y*mapw + x+1], lat ) ) 00554 { 00555 found = true; 00556 track = df.latoff[1] + (y * df.latinc[1]); 00557 p1 = df.latoff[0] + (x * df.latinc[0]); 00558 p2 = df.latoff[0] + ((x+1) * df.latinc[0]); 00559 getIntersect( track, p1, p2, iband, lat, false, true ); 00560 set = new int[2]; 00561 set[0] = p1; 00562 set[1] = track; 00563 cross_set.push_back( set ); 00564 } 00565 00566 } 00567 } 00568 */ 00569 // SEARCH VERTICAL LINE 00570 if ( y < maph-1 ) { 00571 if ( gflat.type == DFNT_FLOAT32 ) { 00572 float *data = (float*)gflat.geomap; 00573 if ( between( data[y*mapw + x], data[(y+1)*mapw + x], lat ) ) { 00574 found = true; 00575 track = df.latoff[0] + (x * df.latinc[0]); 00576 p1 = df.latoff[1] + (y * df.latinc[1]); 00577 p2 = df.latoff[1] + ((y+1) * df.latinc[1]); 00578 getIntersect( track, p1, p2, iband, lat, false, false ); 00579 set = new int[2]; 00580 set[0] = track; 00581 set[1] = p1; 00582 cross_set.push_back( set ); 00583 } 00584 } else if ( gflat.type == DFNT_FLOAT64 ) { 00585 double *data = (double*)gflat.geomap; 00586 if ( between( data[y*mapw + x], data[(y+1)*mapw + x], lat ) ) { 00587 found = true; 00588 track = df.latoff[0] + (x * df.latinc[0]); 00589 p1 = df.latoff[1] + (y * df.latinc[1]); 00590 p2 = df.latoff[1] + ((y+1) * df.latinc[1]); 00591 getIntersect( track, p1, p2, iband, lat, false, false ); 00592 set = new int[2]; 00593 set[0] = track; 00594 set[1] = p1; 00595 cross_set.push_back( set ); 00596 } 00597 } 00598 } 00599 } 00600 } 00601 00602 if ( (int)cross_set.size() == 0 ) { 00603 return; 00604 } 00605 00606 // FIND BEST INTERSECT POINT 00607 double testlon, testlat; 00608 double prevlon; 00609 x = cross_set[0][0]; 00610 y = cross_set[0][1]; 00611 prevlon = x; 00612 testlat = y; 00613 getLL( iband, prevlon, testlat ); 00614 00615 for ( int ipnt=1; ipnt < (int)cross_set.size(); ipnt++ ) { 00616 testlon = cross_set[ipnt][0]; 00617 testlat = cross_set[ipnt][1]; 00618 getLL( iband, testlon, testlat ); 00619 if ( fabs( testlon - lon ) < fabs( prevlon - lon ) ) { 00620 prevlon = testlon; 00621 x = cross_set[ipnt][0]; 00622 y = cross_set[ipnt][1]; 00623 } 00624 } 00625 00626 trackLineTo( x, y, iband, lat, lon ); 00627 00628 for ( int ivec=0; ivec < (int)cross_set.size(); ivec++ ) 00629 delete cross_set[ivec]; 00630 00631 i = x; 00632 j = y; 00633 } 00634 00635 void HdfEosFrmt::getIntersect( int &track, 00636 int &p1, 00637 int p2, 00638 int iband, 00639 double searchVal, 00640 bool, 00641 bool horizontal ) { 00642 int l, m, r; 00643 double lon, lat; 00644 double val; 00645 bool ascending = true; 00646 00647 if ( p2 < p1 ) { 00648 int tmp = p1; 00649 p1 = p2; 00650 p2 = tmp; 00651 } 00652 00653 l = p1; 00654 r = p2; 00655 m = (r - l) / 2; 00656 00657 // CHECK FOR TRACK VALUE DIRECTION 00658 if ( horizontal ) { 00659 double lon1, lat1, lon2, lat2; 00660 lon1 = l; 00661 lat1 = lat2 = track; 00662 lon2 = r; 00663 getLL( iband, lon1, lat1, false ); 00664 getLL( iband, lon2, lat2, false ); 00665 ascending = ( lat1 < lat2 ); 00666 } else { 00667 double lon1, lat1, lon2, lat2; 00668 lat1 = l; 00669 lon1 = lon2 = track; 00670 lat2 = r; 00671 getLL( iband, lon1, lat1, false ); 00672 getLL( iband, lon2, lat2, false ); 00673 ascending = ( lat1 < lat2 ); 00674 } 00675 00676 while ( m > 0 ) { 00677 if ( horizontal ) { 00678 lon = l + m; 00679 lat = track; 00680 } else { 00681 lon = track; 00682 lat = l + m; 00683 } 00684 00685 getLL( iband, lon, lat, false ); 00686 00687 val = lat; 00688 if ( ( ascending && val < searchVal ) || 00689 ( !ascending && val > searchVal ) ) 00690 l += m; 00691 else 00692 r -= m; 00693 00694 m = (r - l) / 2; 00695 } 00696 00697 p1 = l; 00698 if ( l != r ) { 00699 double lon1, lat1, lon2, lat2; 00700 double val2; 00701 if ( horizontal ) { 00702 lon1 = l; 00703 lat1 = track; 00704 lon2 = r; 00705 lat2 = track; 00706 } else { 00707 lon1 = track; 00708 lat1 = l; 00709 lon2 = track; 00710 lat2 = r; 00711 } 00712 00713 getLL( iband, lon1, lat1, false ); 00714 getLL( iband, lon2, lat2, false ); 00715 00716 val = lat1; 00717 val2 = lat2; 00718 if ( fabs( val - searchVal ) > fabs( val2 - searchVal ) ) 00719 p1 = r; 00720 } 00721 00722 return; 00723 } 00724 00725 void HdfEosFrmt::trackLineTo( int &x, 00726 int &y, 00727 int iband, 00728 double trackVal, 00729 double searchVal ) { 00730 int a = 0, b = 0; 00731 int x1 = 0, y1 = 0, x2 = 0, y2 = 0; 00732 bool found = false; 00733 int cnt = 0; 00734 00735 double bestlat1 = 0, bestlat2 = 0; 00736 double testlon[3][3] = { 00737 { -999.0, -999.0, -999.0}, 00738 { -999.0, -999.0, -999.0}, 00739 { -999.0, -999.0, -999.0} 00740 }; 00741 00742 double testlat[3][3] = { 00743 { -999.0, -999.0, -999.0}, 00744 { -999.0, -999.0, -999.0}, 00745 { -999.0, -999.0, -999.0} 00746 }; 00747 00748 while ( !found ) { 00749 for ( a = 0; a < 3; a++ ) { 00750 for ( b = 0; b < 3; b++ ) { 00751 testlat[a][b] = y + a-1; 00752 testlon[a][b] = x + b-1; 00753 getLL( iband, testlon[a][b], testlat[a][b], false ); 00754 } 00755 } 00756 00757 double londiff = fabs( testlon[1][1] - searchVal ); 00758 00759 found = true; 00760 for ( a = 0; found && a < 3; a++ ) { 00761 for ( b = 0; b < 3; b++ ) { 00762 if ( a == 1 && b == 1 ) 00763 continue; 00764 00765 if ( fabs( testlon[a][b] - searchVal ) < londiff ) { 00766 found = false; 00767 continue; 00768 } 00769 } 00770 } 00771 00772 bestlat1 = bestlat2 = 999.0; 00773 for ( a=0; a < 3; a++ ) { 00774 for ( b=0; b < 3; b++ ) { 00775 if ( a == 1 && b == 1 ) 00776 continue; 00777 00778 double latdiff = fabs( testlat[a][b] - trackVal ); 00779 if ( latdiff < bestlat1 ) { 00780 bestlat2 = bestlat1; 00781 x2 = x1; 00782 y2 = y1; 00783 x1 = b; 00784 y1 = a; 00785 bestlat1 = latdiff; 00786 } else if ( latdiff < bestlat2 ) { 00787 x2 = b; 00788 y2 = a; 00789 bestlat2 = latdiff; 00790 } 00791 } 00792 } 00793 00794 00795 00796 if ( fabs( searchVal - testlon[y1][x1] ) > 00797 fabs( searchVal - testlon[y2][x2] ) ) { 00798 x1 = x2; 00799 y1 = y2; 00800 } 00801 00802 /* 00803 if( fabs( searchVal - testlon[1][1] ) < 00804 fabs( searchVal - testlon[y1][x1] ) ) 00805 { 00806 found = true; 00807 } else { 00808 x += x1-1; 00809 y += y1-1; 00810 } 00811 */ 00812 00813 x += x1-1; 00814 y += y1-1; 00815 00816 cnt++; 00817 } 00818 } 00819 00820 void * HdfEosFrmt::getBand( int iband, 00821 int x, 00822 int y, 00823 int w, 00824 int h, 00825 int w2, 00826 int h2, 00827 ScaleType st ) const { 00828 unsigned char* data = NULL; 00829 00830 if ( w <= 0 ) 00831 w = mBandSet[iband].width; 00832 if ( h <= 0 ) 00833 h = mBandSet[iband].height; 00834 00835 if ( w2 == 0 ) return data; // DIVIDE BY ZERO 00836 00837 int32 skip = w / w2; 00838 if ( skip == 0 ) 00839 skip = 1; 00840 00841 w = (w / skip) * skip; 00842 h = (h / skip) * skip; 00843 00844 int nw = w / skip; 00845 int nh = h / skip; 00846 00847 int32 start[] = { y, x}; 00848 int32 scales[] = { skip, skip}; 00849 int32 edge[] = { nh, nw}; 00850 int32 swid; 00851 int dSize; 00852 00853 dSize = ImageFormat::dtypeSize( mBandSet[iband].type ); 00854 data = new unsigned char[(nw * nh) * dSize]; 00855 00856 std::string swname = mDFList[iband].swathname; 00857 std::string fldname = mDFList[iband].fieldname; 00858 00859 swid = SWattach( mSWfid, (char*)swname.c_str() ); 00860 if ( swid == -1 ) { 00861 delete [] data; 00862 return NULL; 00863 } 00864 00865 SWreadfield( swid, (char*)fldname.c_str(), start, scales, edge, data ); 00866 SWdetach( swid ); 00867 00868 if ( nw != w2 || nh != h2 ) 00869 scaleData( (char**)&data, nw, nh, w2, h2, mBandSet[iband].type, st ); 00870 return data; 00871 } 00872 00873 void HdfEosFrmt::parseGeoFlds( int32 swid, std::string swname ) { 00874 int32 nret, ngeofld, bufsz; 00875 int32 *rank, *type; 00876 char *list; 00877 std::vector<std::string> gflist; 00878 00879 ngeofld = SWnentries( swid, HDFE_NENTGFLD, &bufsz ); 00880 00881 list = new char[bufsz]; 00882 rank = new int32[bufsz]; 00883 type = new int32[bufsz]; 00884 nret = SWinqgeofields( swid, list, rank, type ); 00885 if ( nret < 1 ) 00886 return; 00887 00888 gflist = splitList( list, ',' ); 00889 delete [] list; 00890 00891 for ( int igfld=0; igfld < (int)gflist.size(); igfld++ ) { 00892 int32 *dims; 00893 int32 ndims; 00894 int datasz = 0; 00895 GeoField gf; 00896 00897 gf.swathname = swname; 00898 gf.gfldname = gflist[igfld]; 00899 00900 dims = new int32[ rank[igfld] ]; 00901 list = new char[1024]; 00902 memset( list, 0, 1024 ); 00903 nret = SWfieldinfo( swid, (char*)gflist[igfld].c_str(), 00904 &ndims, dims, &gf.type, list ); 00905 00906 if ( nret == -1 ) { 00907 delete [] list; 00908 delete [] dims; 00909 continue; 00910 } 00911 00912 gf.dimnames = splitList( list, ',' ); 00913 delete [] list; 00914 00915 for ( int idim=0; idim < ndims; idim++ ) 00916 gf.dims.push_back( dims[idim] ); 00917 delete [] dims; 00918 00919 00920 switch ( gf.type ) { 00921 case DFNT_FLOAT32: 00922 datasz = 4; 00923 break; 00924 00925 case DFNT_FLOAT64: 00926 datasz = 8; 00927 break; 00928 } 00929 00930 if ( datasz == 0 ) 00931 continue; 00932 00933 gf.geomap = new unsigned char[ gf.dims[0] * gf.dims[1] * datasz ]; 00934 00935 int32 start[] = { 0, 0}; 00936 int32 scale[] = { 1, 1}; 00937 int32 edge[] = { gf.dims[0], gf.dims[1]}; 00938 00939 SWreadfield( swid, (char*)gflist[igfld].c_str(), start, scale, edge, gf.geomap ); 00940 mGFList.push_back( gf ); 00941 } 00942 00943 delete [] rank; 00944 delete [] type; 00945 } 00946 00947 template<class DType> 00948 void HdfEosFrmt::findrange( int32 swid, 00949 std::string field, 00950 DType &lwr, 00951 DType &upr, 00952 std::vector<int32> dims ) { 00953 int32 ret; 00954 00955 if ( (int)dims.size() < 1 ) 00956 return; 00957 00958 int32 start[2] = { 0, 0}; 00959 int32 scales[2] = { 1, 1}; 00960 int32 edge[2] = { dims[1], dims[0]}; 00961 00962 int32 bufsz = dims[1] * dims[0]; 00963 00964 DType* buf = new DType[ bufsz ]; 00965 if ( buf == NULL ) { 00966 char err[256]; 00967 sprintf( err, "buf is NULL %d", (int)bufsz ); 00968 QMessageBox::information( NULL, "", err ); 00969 return; 00970 } 00971 ret = SWreadfield( swid, (char*)field.c_str(), start, scales, edge, (unsigned char*)buf ); 00972 maxmin( buf, bufsz, lwr, upr ); 00973 delete [] buf; 00974 00975 } 00976 00977 00978 std::string HdfEosFrmt::getAquiDateTime( const std::string &filename ) const { 00979 std::string strtod; 00980 std::string strcal; 00981 const ODLTree *tree; 00982 00983 std::string data = getHdfGblAttr( filename, "coremetadata.0" ); 00984 if ( data == "" ) 00985 return ""; 00986 00987 ODLParser p( data ); 00988 tree = p.getObject( "TIMEOFDAY" ); 00989 if ( tree ) { 00990 ODLElement *elem = tree->getElem( 1 ); 00991 if ( elem ) 00992 strtod = elem->getValue(); 00993 } 00994 00995 tree = p.getObject( "CALENDARDATE" ); 00996 if ( tree ) { 00997 ODLElement *elem = tree->getElem( 1 ); 00998 if ( elem ) 00999 strcal = elem->getValue(); 01000 } 01001 01002 // check for invalid characters in TIMEOFDAY field 01003 bool valid = true ; 01004 char tmpstr[2] = " " ; 01005 unsigned int i ; 01006 for (i = 0 ; i < strtod.length() ; i++) { 01007 tmpstr[0] = strtod[i] ; 01008 if (!(tmpstr[0] == '\"' || 01009 tmpstr[0] == '.' || 01010 tmpstr[0] == 'Z' || 01011 (tmpstr[0] >= '0' && tmpstr[0] <= '9') ) ) { 01012 valid = false ; 01013 } 01014 } 01015 // If there are no invalid chars in the TIMEOFDAY field 01016 // reformat the string 01017 if (valid) { 01018 std::string h,m,s; 01019 if ( strtod.length() > 0 && strtod[0] == '\"' ) 01020 strtod = strtod.substr( 1, strtod.length()-2 ); 01021 h = strtod.substr( 0, 2 ); 01022 m = strtod.substr( 2, 2 ); 01023 s = strtod.substr( 4, 2 ); 01024 01025 strtod = h + ":" + m + ":" + s + "-00:00"; 01026 } 01027 01028 01029 // check for invalid characters in CALENDARDATE field 01030 for (i = 0 ; i < strcal.length() ; i++) { 01031 tmpstr[0] = strcal[i] ; 01032 if (!(tmpstr[0] == '\"' || 01033 tmpstr[0] == '.' || 01034 (tmpstr[0] >= '0' && tmpstr[0] <= '9') ) ) { 01035 valid = false ; 01036 } 01037 } 01038 // If there are no invalid chars in the CALENDARDATE field 01039 // reformat the string 01040 if (valid) { 01041 if ( strcal.length() > 0 && strcal[0] == '\"' ) { 01042 strcal = strcal.substr( 1, strcal.length()-2 ); 01043 } 01044 01045 strcal = strcal.substr( 0, 4 ) + "-" + 01046 strcal.substr( 4, 2 ) + "-" + 01047 strcal.substr( 6, 2 ) ; 01048 01049 } 01050 01051 if (valid) { 01052 // return ISO 1806 compliant 01053 return( strcal + "T" + strtod ); 01054 } 01055 else { 01056 // return exactly what was stored in the metadata 01057 return( strcal + " " + strtod ); 01058 } 01059 } 01060 01061 std::string HdfEosFrmt::getOrigID( const std::string &fname ) const { 01062 std::string val; 01063 const ODLTree *tree; 01064 01065 std::string data = getHdfGblAttr( fname, "productmetadata.0" ); 01066 if ( data == "" ) 01067 return ""; 01068 01069 ODLParser p( data ); 01070 tree = p.getObject( "IDOFASTERGDSDATAGRANULE" ); 01071 if ( tree ) { 01072 ODLElement *elem = tree->getElem( 1 ); 01073 if ( elem ) 01074 val = elem->getValue(); 01075 } 01076 01077 if ( val.length() > 0 && val[0] == '\"' ) 01078 val = val.substr( 1, val.length()-2 ); 01079 01080 return val; 01081 } 01082 01083 std::string HdfEosFrmt::getInstZenith( const std::string &fname ) const { 01084 std::string val; 01085 const ODLTree *tree; 01086 01087 std::string data = getHdfGblAttr( fname, "productmetadata.0" ); 01088 if ( data == "" ) 01089 return ""; 01090 01091 ODLParser p( data ); 01092 tree = p.getObject( "POINTINGANGLE" ); 01093 if ( tree ) { 01094 ODLElement *elem = tree->getElem( 2 ); 01095 if ( elem ) 01096 val = elem->getValue(); 01097 } 01098 01099 return val; 01100 } 01101 01102 std::string HdfEosFrmt::getCloudPct( const std::string &fname ) const { 01103 std::string val; 01104 const ODLTree *tree; 01105 01106 std::string data = getHdfGblAttr( fname, "productmetadata.0" ); 01107 if ( data == "" ) 01108 return ""; 01109 01110 ODLParser p( data ); 01111 tree = p.getObject( "SCENECLOUDCOVERAGE" ); 01112 if ( tree ) { 01113 ODLElement *elem = tree->getElem( 1 ); 01114 if ( elem ) 01115 val = elem->getValue(); 01116 } 01117 01118 return val; 01119 } 01120 01121 std::string HdfEosFrmt::getSunAzim( const std::string &fname ) const { 01122 std::string val; 01123 int i1; 01124 const ODLTree *tree; 01125 01126 std::string data = getHdfGblAttr( fname, "productmetadata.0" ); 01127 if ( data == "" ) 01128 return ""; 01129 01130 ODLParser p( data ); 01131 tree = p.getObject( "SOLARDIRECTION" ); 01132 if ( tree ) { 01133 ODLElement *elem = tree->getElem( 1 ); 01134 if ( elem ) 01135 val = elem->getValue(); 01136 } 01137 01138 i1 = val.find( '(' )+1; 01139 val = val.substr( i1, val.find( ',' )-i1 ); 01140 return val; 01141 } 01142 01143 std::string HdfEosFrmt::getSunElev( const std::string &fname ) const { 01144 std::string val; 01145 int i1; 01146 const ODLTree *tree; 01147 01148 std::string data = getHdfGblAttr( fname, "productmetadata.0" ); 01149 if ( data == "" ) 01150 return ""; 01151 01152 ODLParser p( data ); 01153 tree = p.getObject( "SOLARDIRECTION" ); 01154 if ( tree ) { 01155 ODLElement *elem = tree->getElem( 1 ); 01156 if ( elem ) 01157 val = elem->getValue(); 01158 } 01159 01160 i1 = val.find( ',' )+1; 01161 val = val.substr( i1, val.find( ')' )-i1 ); 01162 return val; 01163 } 01164 01165 std::string HdfEosFrmt::getImageAzim( const std::string &fname ) const { 01166 std::string val; 01167 const ODLTree *tree; 01168 01169 std::string data = getHdfGblAttr( fname, "productmetadata.0" ); 01170 if ( data == "" ) 01171 return ""; 01172 01173 ODLParser p( data ); 01174 tree = p.getObject( "MAPORIENTATIONANGLE" ); 01175 if ( tree ) { 01176 ODLElement *elem = tree->getElem( 1 ); 01177 if ( elem ) 01178 val = elem->getValue(); 01179 } 01180 01181 return val; 01182 } 01183 01184 std::string HdfEosFrmt::getProjection( const std::string &fname ) const { 01185 std::string val; 01186 const ODLTree *tree; 01187 01188 std::string data = getHdfGblAttr( fname, "coremetadata.0" ); 01189 if ( data == "" ) 01190 return ""; 01191 01192 ODLParser p( data ); 01193 tree = p.getObject( "MAPPROJECTIONNAME" ); 01194 if ( tree ) { 01195 ODLElement *elem = tree->getElem( 1 ); 01196 if ( elem ) 01197 val = elem->getValue(); 01198 } 01199 01200 if ( val.length() > 0 && val[0] == '\"' ) 01201 val = val.substr( 1, val.length()-2 ); 01202 01203 return val; 01204 } 01205 01206 01207 01208 // 2007-06-14 dls - Removed image ID references and functions 01209 /* 01210 std::string HdfEosFrmt::getImageID( const std::string &fname ) const { 01211 std::string val; 01212 const ODLTree *tree; 01213 01214 std::string data = getHdfGblAttr( fname, "productmetadata.0" ); 01215 if ( data == "" ) 01216 return ""; 01217 01218 ODLParser p( data ); 01219 tree = p.getObject( "ASTERSCENEID" ); 01220 if ( tree ) { 01221 ODLElement *elem = tree->getElem( 1 ); 01222 if ( elem ) { 01223 val = elem->getValue(); 01224 if ( val.length() > 0 && val[0] == '(' ) { 01225 val = val.substr( 1, val.length()-2 ); 01226 unsigned int i = 0 ; 01227 QString build = "Path=" ; 01228 while (i < val.length() && val[i++] != ',') { 01229 if (val[i] >= '0' && val[i] <= '9') { 01230 build += val[i] ; 01231 } 01232 } 01233 build += " Row=" ; 01234 while (i < val.length() && val[++i] != ',') { 01235 if (val[i] >= '0' && val[i] <= '9') { 01236 build += val[i] ; 01237 } 01238 } 01239 build += " View=" ; 01240 while (i < val.length() && val[++i] != ',') { 01241 if (val[i] >= '0' && val[i] <= '9') { 01242 build += val[i] ; 01243 } 01244 } 01245 val = build.ascii() ; 01246 01247 } 01248 } 01249 } 01250 01251 return val; 01252 } 01253 */ 01254 01255 std::string HdfEosFrmt::getInstID( const std::string &fname ) const { 01256 std::string val; 01257 const ODLTree *tree; 01258 01259 std::string data = getHdfGblAttr( fname, "coremetadata.0" ); 01260 if ( data == "" ) 01261 return ""; 01262 01263 ODLParser p( data ); 01264 tree = p.getObject( "INSTRUMENTSHORTNAME" ); 01265 if ( tree ) { 01266 ODLElement *elem = tree->getElem( 0 ); 01267 if ( elem ) 01268 val = elem->getValue(); 01269 } 01270 01271 if ( val.length() > 0 && val[0] == '\"' ) 01272 val = val.substr( 1, val.length()-2 ); 01273 01274 return val; 01275 } 01276 01277 std::string HdfEosFrmt::getInstAz( const std::string &fname ) const { 01278 std::string val; 01279 const ODLTree *tree; 01280 01281 std::string data = getHdfGblAttr( fname, "coremetadata.0" ); 01282 if ( data == "" ) 01283 return ""; 01284 01285 ODLParser p( data ); 01286 tree = p.getObject( "SCENEORIENTATIONANGLE" ); 01287 if ( tree ) { 01288 ODLElement *elem = tree->getElem( 1 ); 01289 if ( elem ) 01290 val = elem->getValue(); 01291 } 01292 return val; 01293 } 01294 01295 01296 01297 01298 01299 std::string HdfEosFrmt::getHdfGblAttr( 01300 const std::string &fname, 01301 const std::string &attrname ) const { 01302 int32 sd_id; 01303 //int32 sds_id; 01304 int32 status; 01305 int32 dtype; // DATA TYPE 01306 int32 count; // NUMBER OF ENTRIES 01307 int32 iattr; // ATTRIBUTE INDEX 01308 int32 ndset; // # OF DATASETS 01309 int32 nattr; // # OF ATTRIBUTES 01310 char attrnamebuf[MAX_NC_NAME]; // ATTRIBUTE NAME 01311 int8 *attrbuf; // ATTRIBUTE TEXT BUFFER 01312 01313 // Open the HDF file 01314 sd_id = SDstart( fname.c_str(), DFACC_READ ); 01315 if ( !sd_id ) return ""; 01316 01317 status = SDfileinfo( sd_id, &ndset, &nattr ); 01318 iattr = SDfindattr( sd_id, attrname.c_str() ); 01319 if ( iattr < 0 ) return ""; 01320 01321 status = SDattrinfo( sd_id, iattr, attrnamebuf, &dtype, &count ); 01322 attrbuf = new int8[ count * DFKNTsize( dtype ) ]; 01323 01324 status = SDreadattr( sd_id, iattr, attrbuf ); 01325 01326 // Dispose of the file identifier to close the file. 01327 status = SDend( sd_id ); 01328 01329 std::string ret = attrbuf; 01330 delete [] attrbuf; 01331 return ret; 01332 } 01333 01334 // PRETTY ASTER SPECIFIC HERE 01335 void HdfEosFrmt::getBandMetaData( ) const { 01336 std::string IMGD = "ImageData"; 01337 std::string bid; 01338 std::string swath; 01339 std::string swathFull; 01340 int pos; 01341 std::string val; 01342 const ODLTree *tree; 01343 std::string data; 01344 double rot = 0.0; 01345 double ulx = 0.0, uly = 0.0; 01346 01347 std::string prod_v; 01348 std::string prod_s; 01349 std::string prod_t; 01350 std::string prod_0; 01351 01352 ODLParser *pv; 01353 ODLParser *ps; 01354 ODLParser *pt; 01355 ODLParser *p0; 01356 01357 prod_v = getHdfGblAttr( mFName, std::string( "productmetadata.v" ) ); 01358 prod_s = getHdfGblAttr( mFName, std::string( "productmetadata.s" ) ); 01359 prod_t = getHdfGblAttr( mFName, std::string( "productmetadata.t" ) ); 01360 prod_0 = getHdfGblAttr( mFName, std::string( "productmetadata.0" ) ); 01361 01362 pv = new ODLParser( prod_v ); 01363 ps = new ODLParser( prod_s ); 01364 pt = new ODLParser( prod_t ); 01365 p0 = new ODLParser( prod_0 ); 01366 01367 if ( p0 ) { 01368 tree = p0->getObject( std::string( "MAPORIENTATIONANGLE" ) ); 01369 if ( tree ) { 01370 ODLElement *elem = tree->getElem( 1 ); 01371 if ( elem ) 01372 rot = atof( elem->getValue().c_str() ); 01373 } else { 01374 tree = p0->getObject( std::string( "SCENEORIENTATIONANGLE" ) ); 01375 if ( tree ) { 01376 ODLElement *elem = tree->getElem( 1 ); 01377 if ( elem ) 01378 rot = 0-atof( elem->getValue().c_str() ); 01379 } 01380 } 01381 01382 tree = p0->getObject( std::string( "SCENEFOURCORNERS" ) ); 01383 if ( tree ) { 01384 const std::vector<ODLTree> &children = tree->getChildSet(); 01385 for ( int ichld=0; ichld < (int)children.size(); ichld++ ) { 01386 if ( children[ichld].getName() == "UPPERLEFT" ) { 01387 ODLElement *elem = children[ichld].getElem( 1 ); 01388 if ( elem ) { 01389 int l, r; 01390 std::string val = elem->getValue(); 01391 l = val.find( "(" ) + 1; 01392 r = val.find( ")" ); 01393 val = val.substr( l, r-l ); 01394 l = 0; 01395 r = val.find( "," ); 01396 uly = atof( val.substr( l, r-l ).c_str() ); 01397 val = val.substr( r+1, val.length()-r ); 01398 ulx = atof( val.c_str() ); 01399 } 01400 } 01401 } 01402 /* 01403 ODLElement *elem = tree->getElem( 1 ); 01404 if( elem ) 01405 rot = atof( elem->getValue().c_str() ); 01406 */ 01407 } 01408 } 01409 01410 for ( int iband=0; iband < (int)mBandSet.size(); iband++ ) { 01411 BandInf &binf = (BandInf&)mBandSet[iband]; 01412 const ODLTree *mptree, *uztree; 01413 01414 binf.ulx = ulx; 01415 binf.uly = uly; 01416 01417 pos = binf.name.find_last_of( IMGD ) + 1; 01418 if ( pos <= 0 ) continue; 01419 bid = binf.name.substr( pos ); 01420 if ( bid.length() < 1 ) continue; 01421 01422 if ( (int)binf.name.find( "VNIR" ) != -1 ) { 01423 mptree = pv->getObject( std::string( "MPMETHOD" ) + bid ); 01424 uztree = pv->getObject( std::string( "UTMZONECODE" ) + bid ); 01425 binf.res = 15; 01426 } else if ( (int)binf.name.find( "SWIR" ) != -1 ) { 01427 mptree = ps->getObject( std::string( "MPMETHOD" ) + bid ); 01428 uztree = ps->getObject( std::string( "UTMZONECODE" ) + bid ); 01429 binf.res = 30; 01430 } else if ( (int)binf.name.find( "TIR" ) != -1 ) { 01431 mptree = pt->getObject( std::string( "MPMETHOD" ) + bid ); 01432 uztree = pt->getObject( std::string( "UTMZONECODE" ) + bid ); 01433 binf.res = 90; 01434 } else { 01435 continue; 01436 } 01437 01438 if ( mptree ) { 01439 ODLElement *elem = mptree->getElem( 1 ); 01440 if ( elem ) { 01441 std::string val = elem->getValue(); 01442 if ( (int)val.find( "UTM" ) >= 0 ) 01443 binf.proj = "utm"; 01444 else if ( (int)val.find( "EQRECT" ) >= 0 ) 01445 binf.proj = ""; 01446 else if ( (int)val.find( "LAMCC" ) >= 0 ) 01447 binf.proj = ""; 01448 else if ( (int)val.find( "SOM" ) >= 0 ) 01449 binf.proj = ""; 01450 else if ( (int)val.find( "PS" ) >= 0 ) 01451 binf.proj = ""; 01452 else 01453 binf.proj = ""; 01454 } 01455 } 01456 01457 if ( uztree && binf.proj != "" ) { 01458 ODLElement *elem = uztree->getElem( 1 ); 01459 if ( elem ) 01460 binf.UTMZ = atoi( elem->getValue().c_str() ); 01461 } 01462 01463 binf.rot = rot; 01464 binf.parms.push_back( "ellps=WGS84" ); 01465 } 01466 01467 delete pv; 01468 delete ps; 01469 delete pt; 01470 delete p0; 01471 } 01472 01473 template<class DType> 01474 void HdfEosFrmt::bilinterp( DType *map, 01475 std::vector<int32> dims, 01476 std::vector<int32> offset, 01477 std::vector<int32> inc, 01478 int x, 01479 int y, 01480 double &res ) { 01481 if ( dims[0] < 1 || dims[1] < 1 ) 01482 return; 01483 01484 int minX = offset[0]; 01485 int minY = offset[1]; 01486 01487 int32 xinc = inc[1]; 01488 int32 yinc = inc[0]; 01489 int32 xdim = dims[1]; 01490 int32 ydim = dims[0]; 01491 01492 int maxX = xdim*xinc + minX; 01493 int maxY = ydim*yinc + minY; 01494 01495 if ( x < minX || x > maxX || 01496 y < minY || y > maxY ) 01497 return; 01498 01499 int gridX = (int)(((float)(x-minX) / (float)(maxX-minX)) * xdim); 01500 int gridY = (int)(((float)(y-minY) / (float)(maxY-minY)) * ydim); 01501 01502 int mapY = gridY * xdim; 01503 int mapYp1 = (gridY+1) * xdim; 01504 01505 DType dnA = map[mapY + gridX]; 01506 DType dnB = map[mapY + gridX+1]; 01507 DType dnC = map[mapYp1 + gridX]; 01508 DType dnD = map[mapYp1 + gridX+1]; 01509 01510 double deltaX = (x - (gridX * xinc + offset[0])) / (double)xinc; 01511 double deltaX2 = 1.0-deltaX; 01512 double deltaY = (y - (gridY * yinc + offset[1])) / (double)yinc; 01513 01514 res = (deltaX*dnB + deltaX2*dnA) * (1-deltaY) + 01515 (deltaX*dnD + deltaX2*dnC) * deltaY; 01516 } 01517 01518 01519 01520
Home |
Search |
Disclaimers & Privacy |
Contact Us GLIMSView Maintainer: dsoltesz@usgs.gov |