/*************************************************************************** * Copyright (C) 2005 by Nicolas PASCAL * * nicolas.pascal@icare.univ-lille1.fr * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 2 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ #include "ceresfiledata.h" const string CERESFileData::latitude_sds_name="Colatitude of CERES FOV at surface"; const string CERESFileData::longitude_sds_name="Longitude of CERES FOV at surface"; const float CERESFileData::colocation_tolerance=0.2; CERESFileData::CERESFileData(const string &name /*= ""*/, const string &mode/*= "r"*/) : FileData(name,mode),SatelliteFileData(name,mode),HDFFileData(name,mode) { init(); } void CERESFileData::init() { // extract the acquisition date from the file name string short_filename = get_tail(get_name()); lat_data=NULL; lon_data=NULL; time_data=NULL; parse_filename(short_filename); // the temporal coverage depends of the file's type : to be completed with new products time_coverage=-1.; if (product=="CRS" || product=="SSF") time_coverage=3600.; // 1 file per hour else if (product=="ES-8") time_coverage=86400.; // 1 file per day else cerr<<"In "<<__FILE__<<" at "<<__LINE__<<" : unknow CERES product "<get_sds(latitude_sds_name.c_str()).get_dimension(0)-1; lat_lon_index_max[1]=0; if (!is_hdf_file_already_loaded) free_hdf_file(); } void CERESFileData::parse_filename( const string & short_filename ) { check_filename(short_filename); // throw a parse_CERES_filename_error if the filename doesn't matches the pattern try { string ceres_filename(short_filename); int first_underscore_pos = ceres_filename.find_first_of("_",0); int second_underscore_pos = ceres_filename.find_first_of("_",first_underscore_pos+1); product=ceres_filename.substr(first_underscore_pos+1,second_underscore_pos-first_underscore_pos-1); int first_minus_pos = ceres_filename.find_first_of("-",second_underscore_pos+1); platform = ceres_filename.substr(second_underscore_pos+1,first_minus_pos-second_underscore_pos-1); int second_minus_pos = ceres_filename.find_first_of("-",first_minus_pos+1); int third_underscore_pos = ceres_filename.find_first_of("_",second_minus_pos+1); instrument=ceres_filename.substr(first_minus_pos+1,third_underscore_pos-first_minus_pos-1); int first_dot_pos = ceres_filename.find_first_of(".",third_underscore_pos+1); version =ceres_filename.substr(third_underscore_pos+1,first_dot_pos-third_underscore_pos-1); // date info is contained between first and third dot position string s_date = ceres_filename.substr(first_dot_pos+1,ceres_filename.size()-first_dot_pos-1); s_date+= "0000"; // add default min and seconds // init the date date->set_date_str(s_date,"%Y%m%e%H%M%S"); } catch (invalid_filename e) { cerr<360 convention for longitude } const float CERESFileData::get_ceres_lat( const float & lat ) { return 90.-lat; // ceres uses the colatitude } /*const bool CERESFileData::contain_data( const float & lat, const float & lon, const double & time ) const { return contain_time(time) && contain_location(lat,lon) ; }*/ const bool CERESFileData::contain_location( const float & lat, const float & lon, float tolerance) { assert(is_geolocation_data_loaded()); if (tolerance<0.) // use default value tolerance=CERESFileData::colocation_tolerance; int index; return get_index(lat,lon,-1.,index,tolerance); } const bool CERESFileData::is_geolocation_data_loaded() const { return (lat_data!=NULL && lon_data!=NULL && time_data!=NULL); } void CERESFileData::free_geolocation_data() { if (!is_geolocation_data_loaded()) { delete[] lat_data; lat_data=NULL; delete[] lon_data; lon_data=NULL; delete[] time_data; time_data=NULL; } } void CERESFileData::load_geolocation_data() { if (!is_geolocation_data_loaded()) { // hdf_file is needed, but the method assume to conserve the caller's state bool hdf_file_already_loaded = is_hdf_file_loaded(); if (!hdf_file_already_loaded) load_hdf_file(); // read lat, lon, time data if (lat_data==NULL) lat_data=static_cast(read_data((void*)lat_data,latitude_sds_name.c_str())); if (lon_data==NULL) lon_data=static_cast(read_data((void*)lon_data,longitude_sds_name.c_str())); if (time_data==NULL) time_data=static_cast(read_data((void*)time_data,get_time_sds_name().c_str())); if (!hdf_file_already_loaded) free_hdf_file(); } } const bool CERESFileData::get_index(const float &lat, const float& lon, int &nearest_pix_idx, const float coloc_tolerance) { return get_index(lat, lon, -1.0, nearest_pix_idx, coloc_tolerance); } const float CERESFileData::get_nearest_point_distance( const float & lat, const float & lon, const float coloc_tolerance ) { bool data_already_loaded=is_geolocation_data_loaded(); if (!data_already_loaded) load_geolocation_data(); int nearest_point_idx; double nearest_point_distance=-1.; if (get_index(lat,lon,nearest_point_idx,coloc_tolerance)) // a point in the coincidence frame has been found nearest_point_distance=sqrt(pow(lat_data[nearest_point_idx]-lat,2) + pow(lon_data[nearest_point_idx]-lon,2)); if (!data_already_loaded) free_geolocation_data(); return nearest_point_distance; } const bool CERESFileData::contain_location(const float &lat,const float &lon, const double &tolerance){ int nearest_idx=-1; return get_index(lat,lon,nearest_idx,colocation_tolerance); } const bool CERESFileData::contain_data( const float & lat, const float & lon, const double & time, const double &colocation_tolerance ) { return contain_location(lat,lon,colocation_tolerance)&&contain_time(time); }