irplib_cat.c

00001 /* $Id: irplib_cat.c,v 1.10 2009/12/01 12:34:25 cgarcia Exp $
00002  *
00003  * This file is part of the irplib package
00004  * Copyright (C) 2002,2003 European Southern Observatory
00005  *
00006  * This program is free software; you can redistribute it and/or modify
00007  * it under the terms of the GNU General Public License as published by
00008  * the Free Software Foundation; either version 2 of the License, or
00009  * (at your option) any later version.
00010  *
00011  * This program is distributed in the hope that it will be useful,
00012  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00013  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014  * GNU General Public License for more details.
00015  *
00016  * You should have received a copy of the GNU General Public License
00017  * along with this program; if not, write to the Free Software
00018  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02111-1307  USA
00019  */
00020 
00021 /*
00022  * $Author: cgarcia $
00023  * $Date: 2009/12/01 12:34:25 $
00024  * $Revision: 1.10 $
00025  * $Name: naco-4_3_3 $
00026  */
00027 
00028 #ifdef HAVE_CONFIG_H
00029 #include <config.h>
00030 #endif
00031 
00032 /*-----------------------------------------------------------------------------
00033                                    Includes
00034  -----------------------------------------------------------------------------*/
00035 
00036 #include <libgen.h>
00037 #include <math.h>
00038 #include <cpl.h>
00039 
00040 #include "irplib_cat.h"
00041 #include "irplib_wcs.h"
00042 
00043 #define FILENAME_SZBUF 1024
00044 
00045 /*----------------------------------------------------------------------------*/
00049 /*----------------------------------------------------------------------------*/
00050 
00053 /*---------------------------------------------------------------------------*/
00072 /*---------------------------------------------------------------------------*/
00073 
00074 int irplib_2mass_get_catpars
00075 (const cpl_frame *  master_index,
00076  char            ** catpath,
00077  char            ** catname)
00078 {
00079     cpl_propertylist * p;
00080     const char       * unk = "unknown";
00081     char             * fname;
00082     int                status = CPL_ERROR_NONE;
00083 
00084     /* Initialise a few things */
00085     *catpath = NULL;
00086     *catname = NULL;
00087 
00088     /* First get the full path to the index file and make sure it exists */
00089     fname = cpl_strdup(cpl_frame_get_filename(master_index));
00090     if (access((const char *)fname,R_OK) != 0)
00091     {
00092          cpl_msg_error(__func__,"Can't access index file %s",fname);
00093          cpl_free(fname);
00094          return CPL_ERROR_FILE_IO;
00095     }
00096     *catpath = cpl_strdup(dirname(fname));
00097 
00098     /* Try to load the propertylist. If it is not possible signal a fatal
00099        error since this probably means the whole file is messed up */
00100     if ((p = cpl_propertylist_load(cpl_frame_get_filename(master_index),0)) == NULL)
00101     {
00102         cpl_msg_error(__func__,"Can't load index file header %s",fname);
00103         cpl_free(*catpath);
00104         cpl_free(fname);
00105         return CPL_ERROR_FILE_IO;
00106     }
00107 
00108     /* If there is a catalogue name in the header then send it back. If there
00109        isn't then give a default name and send a warning */
00110     if (cpl_propertylist_has(p,"CATNAME"))
00111     {
00112         *catname = cpl_strdup(cpl_propertylist_get_string(p,"CATNAME"));
00113         status = CPL_ERROR_NONE;
00114     } else {
00115         *catname = cpl_strdup(unk);
00116         cpl_msg_warning(__func__,"Property CATNAME not in index file header %s",
00117                         fname);
00118     }
00119 
00120     /* Free and return */
00121     cpl_free(fname);
00122     cpl_propertylist_delete(p);
00123     return(status);
00124 }
00125 
00126 
00127 
00128 /*---------------------------------------------------------------------------*/
00151 /*---------------------------------------------------------------------------*/
00152 
00153 cpl_error_code irplib_cat_get_image_limits
00154 (const cpl_wcs    * wcs,
00155  float              ext_search,
00156  double           * ra1,
00157  double           * ra2,
00158  double           * dec1,
00159  double           * dec2)
00160 {
00161     double            ra;
00162     double            dec;
00163     double            x;
00164     double            y;
00165     double            dra;
00166     double            ddec;
00167     double            min_4q;
00168     double            max_1q;
00169     int               first_quad;
00170     int               fourth_quad;
00171     const int       * naxes;
00172     long              i;
00173     long              j;
00174     const cpl_array * a;
00175 
00176     /* Initialise these in case of failure later*/
00177     *ra1 = 0.0;
00178     *ra2 = 0.0;
00179     *dec1 = 0.0;
00180     *dec2 = 0.0;
00181 
00182     /* Grab the WCS info from the property list */
00183     if (wcs == NULL)
00184         return CPL_ERROR_DATA_NOT_FOUND;
00185 
00186     /* Get the size of the data array */
00187 
00188     a = cpl_wcs_get_image_dims(wcs);
00189     if(a == NULL)
00190         return CPL_ERROR_ILLEGAL_INPUT;
00191     naxes = cpl_array_get_data_int_const(a);
00192 
00193     /* Find the RA and Dec limits of the image */
00194 
00195     *ra1 = 370.0;
00196     *ra2 = -370.0;
00197     *dec1 = 95.0;
00198     *dec2 = -95.0;
00199     first_quad = 0;
00200     fourth_quad = 0;
00201     min_4q = 370.0;
00202     max_1q = 0.0;
00203     for (j = 1; j < naxes[1]; j += 10) {
00204         y = (double)j;
00205         for (i = 1; i < naxes[0]; i += 10) {
00206             x = (double)i;
00207             irplib_wcs_xytoradec(wcs,x,y,&ra,&dec);
00208             if (ra >= 0.0 && ra <= 90.0) {
00209                 first_quad = 1;
00210                 if(ra > max_1q)
00211                     max_1q = ra;
00212             } else if (ra >= 270.0 && ra <= 360.0) {
00213                 fourth_quad = 1;
00214                 if(ra - 360.0 < min_4q)
00215                     min_4q = ra - 360.0;
00216             }
00217             if(ra < *ra1)
00218                 *ra1 = ra;
00219             if(ra > *ra2)
00220                 *ra2 = ra;
00221             if(dec < *dec1)
00222                 *dec1 = dec;
00223             if(dec > *dec2)
00224                 *dec2 = dec;
00225         }
00226     }
00227 
00228     /* Now have a look to see if you had RA values in both the first and
00229        fourth quadrants.  If you have, then make the minimum RA a negative
00230        value.  This will be the signal to the caller that you have the
00231        wraparound... */
00232 
00233     if (first_quad && fourth_quad) {
00234         *ra1 = min_4q;
00235         *ra2 = max_1q;
00236     }
00237 
00238     /* Pad out search a bit */
00239     if (ext_search)
00240     {
00241         dra = 0.5*ext_search*(*ra2 - *ra1);
00242         *ra1 -= dra;
00243         *ra2 += dra;
00244         ddec = 0.5*ext_search*(*dec2 - *dec1);
00245         *dec1 -= ddec;
00246         *dec2 += ddec;
00247     }
00248 
00249     /* Exit */
00250     return CPL_ERROR_NONE;
00251 }
00252 
00253 /*---------------------------------------------------------------------------*/
00277 /*---------------------------------------------------------------------------*/
00278 
00279 cpl_table *  irplib_2mass_extract
00280 (char *path,
00281  float ramin,
00282  float ramax,
00283  float decmin,
00284  float decmax)
00285 {
00286     cpl_table *t,*s;
00287     cpl_table *out;
00288     int i,nrows,start,finish,first_index,last_index,irow,init,j;
00289     int first_index_ra,last_index_ra,wrap,iwrap;
00290     float dectest,ratest,ramin_wrap,ramax_wrap;
00291     char fullname[FILENAME_SZBUF];
00292     cpl_array *a;
00293     const char *deccol[] = {"Dec"};
00294     cpl_propertylist *p;
00295 
00296     /* Create an output table */
00297 
00298     out = cpl_table_new(0);
00299     init = 1;
00300 
00301     /* Create a cpl array */
00302 
00303     /* deccol will NOT be modified */
00304     a = cpl_array_wrap_string((char **)deccol,1);
00305 
00306     /* Is there a wrap around problem? */
00307 
00308     wrap = (ramin < 0.0 && ramax > 0.0) ? 2 : 1;
00309 
00310     /* Loop for each query. If there is a wrap around problem then we need 2
00311        queries. If not, then we only need 1 */
00312 
00313     for (iwrap = 0; iwrap < wrap; iwrap++) {
00314         if (wrap == 2) {
00315             if (iwrap == 0) {
00316                 ramin_wrap = ramin + 360.0;
00317                 ramax_wrap = 360.0;
00318             } else {
00319                 ramin_wrap = 0.000001;
00320                 ramax_wrap = ramax;
00321             }
00322         } else {
00323             ramin_wrap = ramin;
00324             ramax_wrap = ramax;
00325         }
00326 
00327         /* Find out where in the index to look */
00328 
00329         first_index_ra = (int)ramin_wrap;
00330         last_index_ra = (int)ramax_wrap;
00331         if(last_index_ra > 359)
00332             last_index_ra = 359;
00333 
00334         /* Look at the min and max RA and decide which files need to be
00335            opened. */
00336 
00337         for (i = first_index_ra; i <= last_index_ra; i++)
00338         {
00339 
00340             /* Ok, we've found one that needs opening. Read the file with
00341                the relevant CPL call */
00342 
00343             (void)snprintf(fullname,FILENAME_SZBUF,"%s/npsc%03d.fits",path,i);
00344 
00345             /* Read the propertylist so that you know how many rows there
00346                are in the table */
00347 
00348             p = cpl_propertylist_load(fullname,1);
00349             if (p == NULL)
00350             {
00351                 cpl_error_set_message_macro(__func__,CPL_ERROR_DATA_NOT_FOUND,
00352                         __FILE__, __LINE__, "2mass file %s missing",fullname);
00353                 cpl_table_delete(out);
00354                 cpl_array_unwrap(a);
00355                 return(NULL);
00356             }
00357             nrows = cpl_propertylist_get_int(p, "NAXIS2");
00358             cpl_propertylist_delete(p);
00359 
00360             /* Load various rows until you find the Dec range that you
00361              have specified. First the minimum Dec */
00362 
00363             start = 0;
00364             finish = nrows;
00365             first_index = nrows/2;
00366             while (finish - start >= 2)
00367             {
00368                 t = cpl_table_load_window(fullname, 1, 0, a, first_index, 1);
00369                 dectest = cpl_table_get_float(t, "Dec", 0, NULL);
00370                 cpl_table_delete(t);
00371                 if (dectest < decmin)
00372                 {
00373                     start = first_index;
00374                     first_index = (first_index + finish)/2;
00375                 }
00376                 else
00377                 {
00378                     finish = first_index;
00379                     first_index = (first_index + start)/2;
00380                 }
00381             }
00382 
00383             /* Load various rows until you find the Dec range that you
00384              have specified. Now the maximum Dec */
00385 
00386             start = first_index;
00387             finish = nrows;
00388             last_index = start + (finish - start)/2;
00389             while (finish - start >= 2)
00390             {
00391                 t = cpl_table_load_window(fullname, 1, 0, a, last_index, 1);
00392                 dectest = cpl_table_get_float(t, "Dec", 0, NULL);
00393                 cpl_table_delete(t);
00394                 if (dectest < decmax)
00395                 {
00396                     start = last_index;
00397                     last_index = (last_index + finish)/2;
00398                 }
00399                 else
00400                 {
00401                     finish = last_index;
00402                     last_index = (last_index + start)/2;
00403                 }
00404             }
00405             if (last_index < first_index)
00406                 last_index = first_index;
00407 
00408             /* Ok now now load all the rows in the relevant dec limits */
00409 
00410             nrows = last_index - first_index + 1;
00411             if ((t = cpl_table_load_window(fullname, 1, 0, NULL, first_index,
00412                                            nrows)) == NULL)
00413             {
00414                 cpl_error_set_message_macro(__func__,CPL_ERROR_DATA_NOT_FOUND,
00415                         __FILE__, __LINE__, "Error in subset of 2mass file %s ",
00416                         fullname);
00417                 cpl_table_delete(out);
00418                 cpl_array_unwrap(a);
00419                 return (NULL);
00420             }
00421             cpl_table_unselect_all(t);
00422 
00423             /* Right, we now know what range of rows to search. Go through
00424              these and pick the ones that are in the correct range of RA.
00425              If a row qualifies, then 'select' it. */
00426 
00427             for (j = 0; j < nrows; j++)
00428             {
00429                 ratest = cpl_table_get_float(t, "RA", j, NULL);
00430                 if (cpl_error_get_code() != CPL_ERROR_NONE)
00431                 {
00432                     cpl_error_set_message_macro(__func__,CPL_ERROR_DATA_NOT_FOUND,
00433                             __FILE__, __LINE__, "No RA column in 2mass file %s",
00434                             fullname);
00435                     cpl_table_delete(t);
00436                     cpl_array_unwrap(a);
00437                     cpl_table_delete(out);
00438                     return (NULL);
00439                 }
00440                 if (ratest >= ramin_wrap && ratest <= ramax_wrap)
00441                     cpl_table_select_row(t, j);
00442             }
00443 
00444             /* Extract the rows that have been selected now and append them
00445              onto the output table */
00446 
00447             s = cpl_table_extract_selected(t);
00448             if (init == 1)
00449             {
00450                 cpl_table_copy_structure(out, t);
00451                 init = 0;
00452             }
00453             irow = cpl_table_get_nrow(out) + 1;
00454             cpl_table_insert(out, s, irow);
00455 
00456             /* Tidy up */
00457 
00458             cpl_table_delete(t);
00459             cpl_table_delete(s);
00460         }
00461     }
00462 
00463     /* Ok, now just return the table and get out of here */
00464 
00465     cpl_array_unwrap(a);
00466     return(out);
00467 }

Generated on Tue Mar 12 15:19:52 2013 for NACO Pipeline Reference Manual by  doxygen 1.4.7