hawki_step_detect_obj.c

00001 /* $Id: hawki_step_detect_obj.c,v 1.22 2010/09/28 14:13:11 cgarcia Exp $
00002  *
00003  * This file is part of the HAWKI Pipeline
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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00019  */
00020 
00021 /*
00022  * $Author: cgarcia $
00023  * $Date: 2010/09/28 14:13:11 $
00024  * $Revision: 1.22 $
00025  * $Name: hawki-1_8_0 $
00026  */
00027 
00028 #ifdef HAVE_CONFIG_H
00029 #include <config.h>
00030 #endif
00031 
00032 /*-----------------------------------------------------------------------------
00033                                 Includes
00034  -----------------------------------------------------------------------------*/
00035 
00036 #include <math.h>
00037 #include <cpl.h>
00038 #include <string.h>
00039 
00040 #include "irplib_utils.h"
00041 #include "irplib_calib.h"
00042 
00043 #include "hawki_utils.h"
00044 #include "hawki_obj_det.h"
00045 #include "hawki_mask.h"
00046 #include "hawki_image_stats.h"
00047 #include "hawki_calib.h"
00048 #include "hawki_load.h"
00049 #include "hawki_save.h"
00050 #include "hawki_pfits.h"
00051 #include "hawki_dfs.h"
00052 
00053 /*-----------------------------------------------------------------------------
00054                             Functions prototypes
00055  -----------------------------------------------------------------------------*/
00056 
00057 static int hawki_step_detect_obj_create(cpl_plugin *) ;
00058 static int hawki_step_detect_obj_exec(cpl_plugin *) ;
00059 static int hawki_step_detect_obj_destroy(cpl_plugin *) ;
00060 static int hawki_step_detect_obj(cpl_parameterlist *, cpl_frameset *) ;
00061 
00062 static void hawki_step_detect_obj_init_output(void);
00063 static void hawki_step_detect_obj_get_pscale
00064 (cpl_frameset * combframes);
00065 static int hawki_step_detect_obj_retrieve_input_param
00066 (cpl_parameterlist  *  parlist);
00067 static cpl_apertures  ** hawki_step_detect_obj_mask_and_apertures
00068 (cpl_frameset    *  combframes,
00069  cpl_image       ** mask_image,
00070  cpl_image       ** comb_image);
00071 static int hawki_step_detect_obj_aper_params
00072 (cpl_image      **  combined_images, 
00073  cpl_apertures  **  apertures,
00074  cpl_table      **  obj_charac);
00075 static int hawki_step_detect_obj_save
00076 (cpl_image           **  mask_images,
00077  cpl_table           **  obj_charac,
00078  cpl_propertylist    **  obj_stats,
00079  cpl_parameterlist   *   parlist,
00080  cpl_frameset        *   framelist);
00081 
00082 /*-----------------------------------------------------------------------------
00083                             Static variables
00084  -----------------------------------------------------------------------------*/
00085 
00086 static struct 
00087 {
00088     /* Inputs */
00089     double sigma_det;
00090     int    growing_radius;
00091 } hawki_step_detect_obj_config;
00092 
00093 static struct 
00094 {
00095     /* Outputs */
00096     double          pixscale;
00097     double          iq[HAWKI_NB_DETECTORS] ;
00098     int             nbobjs[HAWKI_NB_DETECTORS] ;
00099     double          fwhm_pix[HAWKI_NB_DETECTORS] ;
00100     double          fwhm_arcsec[HAWKI_NB_DETECTORS] ;
00101     double          fwhm_mode[HAWKI_NB_DETECTORS] ;
00102     double          pos_x[HAWKI_NB_DETECTORS] ;
00103     double          pos_y[HAWKI_NB_DETECTORS] ;
00104 } hawki_step_detect_obj_output;
00105 
00106 static char hawki_step_detect_obj_description[] =
00107 "hawki_step_detect_obj -- hawki detect objects recipe.\n"
00108 "This recipe detects objects from the combined image creating a mask\n"
00109 "and a list of object properties\n"
00110 "The files listed in the Set Of Frames (sof-file) must be tagged:\n"
00111 "combined.fits "HAWKI_CALPRO_COMBINED"\n";
00112 
00113 /*-----------------------------------------------------------------------------
00114                                 Functions code
00115  -----------------------------------------------------------------------------*/
00116 
00117 /*----------------------------------------------------------------------------*/
00125 /*----------------------------------------------------------------------------*/
00126 int cpl_plugin_get_info(cpl_pluginlist * list)
00127 {
00128     cpl_recipe  *   recipe = cpl_calloc(1, sizeof(*recipe)) ;
00129     cpl_plugin  *   plugin = &recipe->interface ;
00130 
00131     cpl_plugin_init(plugin,
00132                     CPL_PLUGIN_API,
00133                     HAWKI_BINARY_VERSION,
00134                     CPL_PLUGIN_TYPE_RECIPE,
00135                     "hawki_step_detect_obj",
00136                     "Object detection recipe",
00137                     hawki_step_detect_obj_description,
00138                     "Cesar Enrique Garcia Dabo",
00139                     PACKAGE_BUGREPORT,  
00140                     hawki_get_license(),
00141                     hawki_step_detect_obj_create,
00142                     hawki_step_detect_obj_exec,
00143                     hawki_step_detect_obj_destroy) ;
00144 
00145     cpl_pluginlist_append(list, plugin) ;
00146     
00147     return 0;
00148 }
00149 
00150 /*----------------------------------------------------------------------------*/
00159 /*----------------------------------------------------------------------------*/
00160 static int hawki_step_detect_obj_create(cpl_plugin * plugin)
00161 {
00162     cpl_recipe      * recipe ;
00163     cpl_parameter   * p ;
00164 
00165     /* Get the recipe out of the plugin */
00166     if (cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE)
00167         recipe = (cpl_recipe *)plugin ;
00168     else return -1 ;
00169 
00170     /* Create the parameters list in the cpl_recipe object */
00171     recipe->parameters = cpl_parameterlist_new() ;
00172 
00173     /* Fill the parameters list */
00174     /* --sigma_det */
00175     p = cpl_parameter_new_value("hawki.hawki_step_detect_obj.sigma_det", 
00176                                 CPL_TYPE_DOUBLE, "detection level",
00177                                 "hawki.hawki_step_detect_obj", 6.);
00178     cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "sigma_det");
00179     cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
00180     cpl_parameterlist_append(recipe->parameters, p);
00181 
00182     /* --growing_radius */
00183     p = cpl_parameter_new_value("hawki.hawki_step_detect_obj.growing_radius", 
00184                                 CPL_TYPE_INT,
00185                                 "radius of convolution kernel to apply to objects",
00186                                 "hawki.hawki_step_detect_obj", 5);
00187     cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "growing_radius");
00188     cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
00189     cpl_parameterlist_append(recipe->parameters, p);
00190 
00191     /* Return */
00192     return 0;
00193 }
00194 
00195 /*----------------------------------------------------------------------------*/
00201 /*----------------------------------------------------------------------------*/
00202 static int hawki_step_detect_obj_exec(cpl_plugin * plugin)
00203 {
00204     cpl_recipe  *   recipe ;
00205 
00206     /* Get the recipe out of the plugin */
00207     if (cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE)
00208         recipe = (cpl_recipe *)plugin ;
00209     else return -1 ;
00210 
00211     /* Issue a banner */
00212     hawki_print_banner();
00213 
00214     return hawki_step_detect_obj(recipe->parameters, recipe->frames) ;
00215 }
00216 
00217 /*----------------------------------------------------------------------------*/
00223 /*----------------------------------------------------------------------------*/
00224 static int hawki_step_detect_obj_destroy(cpl_plugin * plugin)
00225 {
00226     cpl_recipe  *   recipe ;
00227 
00228     /* Get the recipe out of the plugin */
00229     if (cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE)
00230         recipe = (cpl_recipe *)plugin ;
00231     else return -1 ;
00232 
00233     cpl_parameterlist_delete(recipe->parameters) ;
00234     return 0 ;
00235 }
00236 
00237 /*----------------------------------------------------------------------------*/
00244 /*----------------------------------------------------------------------------*/
00245 static int hawki_step_detect_obj(
00246         cpl_parameterlist   *   parlist, 
00247         cpl_frameset        *   framelist)
00248 {
00249     cpl_frameset     *   combframes;
00250     cpl_image        **  mask_image;
00251     cpl_image        **  comb_image;
00252     cpl_apertures    **  apertures;
00253     cpl_table        **  obj_charac;
00254     cpl_propertylist **  obj_stats;
00255     int                  idet;
00256     
00257     /* Initialise */
00258     hawki_step_detect_obj_init_output();
00259 
00260     /* Retrieve input parameters */
00261     if(hawki_step_detect_obj_retrieve_input_param(parlist))
00262     {
00263         cpl_msg_error(__func__, "Wrong parameters");
00264         return -1;
00265     }
00266 
00267     /* Identify the RAW and CALIB frames in the input frameset */
00268     if (hawki_dfs_set_groups(framelist)) {
00269         cpl_msg_error(__func__, "Cannot identify RAW and CALIB frames") ;
00270         return -1 ;
00271     }
00272 
00273     /* Retrieve raw frames */
00274     combframes = hawki_extract_frameset(framelist, HAWKI_CALPRO_COMBINED) ;
00275     if (combframes == NULL) 
00276     {
00277         cpl_msg_error(__func__, "Cannot find combined images in the input (%s)",
00278                 HAWKI_CALPRO_COMBINED);
00279         return -1 ;
00280     }
00281     if (cpl_frameset_get_size(combframes) != 1)
00282     {
00283         cpl_msg_error(__func__, "Only one combined image must be provided");
00284         return -1 ;
00285     }
00286 
00287     /* Get info from the headers */
00288     hawki_step_detect_obj_get_pscale(combframes);
00289     
00290     /* Get the mask with the points above the background 
00291      * and the associated apertures*/
00292     cpl_msg_info(__func__, "Getting the object masks") ;
00293     mask_image = cpl_malloc(HAWKI_NB_DETECTORS * sizeof(cpl_image *));
00294     comb_image = cpl_malloc(HAWKI_NB_DETECTORS * sizeof(cpl_image *));
00295     apertures =  hawki_step_detect_obj_mask_and_apertures
00296         (combframes, mask_image, comb_image);
00297     if(apertures == NULL)
00298     {
00299         cpl_msg_error(__func__,"Could not detect objects in image");
00300         cpl_frameset_delete(combframes);
00301         cpl_free(mask_image);
00302         cpl_free(comb_image);
00303         return -1;
00304     }
00305     
00306     /* Get object characterizations and statistics */
00307     cpl_msg_info(__func__, "Getting object parameters") ;
00308     obj_charac = cpl_malloc(HAWKI_NB_DETECTORS * sizeof(cpl_table *)) ;
00309     obj_stats  = cpl_malloc(HAWKI_NB_DETECTORS * sizeof(cpl_propertylist *));
00310     for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++)
00311     {
00312         obj_charac[idet] = cpl_table_new
00313             (cpl_apertures_get_size(apertures[idet]));
00314         obj_stats[idet] = cpl_propertylist_new();
00315     }
00316     hawki_step_detect_obj_aper_params(comb_image, apertures, obj_charac);
00317  
00318     /* Statistics of the detected objects in the QC */
00319     hawki_obj_prop_stats(obj_charac, obj_stats);
00320 
00321     /* Save the products */
00322     cpl_msg_info(__func__, "Save the products") ;
00323     if (hawki_step_detect_obj_save(mask_image, obj_charac, obj_stats,
00324                                    parlist, framelist) == -1)
00325     {
00326         cpl_msg_warning(__func__, "Some data could not be saved. "
00327                         "Check permisions or disk space") ;
00328         for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++) 
00329         {
00330             cpl_table_delete(obj_charac[idet]);
00331             cpl_propertylist_delete(obj_stats[idet]);
00332             cpl_apertures_delete(apertures[idet]);
00333         }
00334         cpl_free(apertures);
00335         cpl_free(obj_charac);
00336         cpl_free(obj_stats);
00337         cpl_frameset_delete(combframes);
00338         for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++) 
00339         {
00340             cpl_image_delete(mask_image[idet]);
00341             cpl_image_delete(comb_image[idet]);
00342         }
00343         cpl_free(mask_image);
00344         cpl_free(comb_image);
00345         return -1 ;
00346     }
00347     
00348     /* Return */
00349     for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++) 
00350     {
00351         cpl_table_delete(obj_charac[idet]);
00352         cpl_propertylist_delete(obj_stats[idet]);
00353         cpl_apertures_delete(apertures[idet]);
00354         cpl_image_delete(mask_image[idet]);
00355         cpl_image_delete(comb_image[idet]);
00356     }
00357     cpl_free(apertures);
00358     cpl_free(obj_charac);
00359     cpl_free(obj_stats);
00360     cpl_frameset_delete(combframes);
00361     cpl_free(mask_image);
00362     cpl_free(comb_image);
00363 
00364     /* Return */
00365     if (cpl_error_get_code())
00366     {
00367         cpl_msg_error(__func__,
00368                       "HAWK-I pipeline could not recover from previous errors");
00369         return -1 ;
00370     }
00371     else return 0 ;
00372 }
00373 
00374 int hawki_step_detect_obj_retrieve_input_param
00375 (cpl_parameterlist  *  parlist)
00376 {
00377     cpl_parameter   *   par ;
00378 
00379     par = NULL ;
00380     par = cpl_parameterlist_find
00381         (parlist, "hawki.hawki_step_detect_obj.sigma_det");
00382     hawki_step_detect_obj_config.sigma_det = cpl_parameter_get_double(par);
00383     par = cpl_parameterlist_find
00384         (parlist, "hawki.hawki_step_detect_obj.growing_radius");
00385     hawki_step_detect_obj_config.growing_radius = cpl_parameter_get_int(par);
00386     if(hawki_step_detect_obj_config.growing_radius > 100)
00387     {
00388         cpl_msg_error(__func__,"The maximum radius allowed is 100");
00389         return -1;
00390     }
00391     if(hawki_step_detect_obj_config.sigma_det <= 0 )
00392     {
00393         cpl_msg_error(__func__,"Detection sigma has to be greater than 0");
00394         return -1;
00395     }
00396 
00397     return 0;
00398 }
00399 
00400 
00401 
00402 /*----------------------------------------------------------------------------*/
00412 /*----------------------------------------------------------------------------*/
00413 static cpl_apertures  ** hawki_step_detect_obj_mask_and_apertures
00414 (cpl_frameset    *  combframes,
00415  cpl_image       ** mask_image,
00416  cpl_image       ** comb_image)
00417 {
00418     cpl_apertures   **  apertures;
00419     int                 idet;
00420 
00421     /* Create output object */
00422     apertures = cpl_malloc(HAWKI_NB_DETECTORS * sizeof(cpl_apertures *));
00423   
00424     /* Loop on the detectors */
00425     cpl_msg_indent_more();
00426     for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++)
00427     {
00428         cpl_image  * chip_image;
00429         cpl_image  * chip_image_sort;
00430         cpl_mask   * object_mask;
00431         cpl_mask   * kernel_op;
00432         cpl_matrix * kernel;
00433         cpl_image  * labels;
00434         int          nobj;
00435         double       bkg_level;
00436         double       bkg_noise;
00437         double       threshold;
00438         int          kernel_size;
00439         int          ix;
00440         int          iy;
00441 
00442         cpl_msg_info(__func__, "Detecting objects on chip number %d", idet+1) ;
00443         cpl_msg_indent_more();
00444         
00445         /* Load the input data */
00446         cpl_msg_info(__func__, "Load the input data") ;
00447         chip_image = hawki_load_image(combframes, 0, idet+1, CPL_TYPE_FLOAT);
00448         if (chip_image == NULL) 
00449         {
00450             cpl_msg_error(__func__, "Cannot load chip %d", idet+1) ;
00451             cpl_msg_indent_less() ;
00452             cpl_free(apertures);
00453             return NULL ;
00454         }
00455         
00456         /* Subtract the median of the frame first */
00457         chip_image_sort = cpl_image_duplicate(chip_image);
00458         bkg_level = cpl_image_get_median(chip_image);
00459         bkg_noise = hawki_image_float_get_sigma_from_quartile(chip_image_sort); 
00460         cpl_image_delete(chip_image_sort);
00461         threshold = bkg_level + hawki_step_detect_obj_config.sigma_det * bkg_noise;        
00462         cpl_msg_info(__func__, "Background:       %f",bkg_level);
00463         cpl_msg_info(__func__, "Background noise: %f",bkg_noise);
00464         
00465         /* Create the mask */
00466         cpl_msg_info(__func__, "Mask creation with threshold: %f",threshold);
00467         object_mask = cpl_mask_threshold_image_create
00468             (chip_image, threshold, DBL_MAX);
00469 
00470         /* Apply a morphological opening to remove single pixel detections */
00471         cpl_msg_info(__func__, "Removing single pixel detections");
00472         kernel_op = cpl_mask_new(3, 3); 
00473         cpl_mask_not(kernel_op);
00474         if (cpl_mask_filter(object_mask, object_mask, kernel_op, 
00475                             CPL_FILTER_OPENING, 
00476                             CPL_BORDER_ZERO) != CPL_ERROR_NONE)
00477         {
00478             cpl_mask_delete(object_mask);
00479             cpl_mask_delete(kernel_op);
00480             return NULL;
00481         }
00482         cpl_mask_delete(kernel_op);
00483         
00484         /* Apply dilation to the mask */
00485         if(hawki_step_detect_obj_config.growing_radius>0)
00486         {
00487             cpl_msg_info(__func__, "Growing the mask with radius %d",
00488                     hawki_step_detect_obj_config.growing_radius);
00489             kernel_size = hawki_step_detect_obj_config.growing_radius*2+1;
00490             kernel = cpl_matrix_new(kernel_size, kernel_size);
00491             for(ix=0;ix<kernel_size;++ix)
00492                 for(iy=0;iy<kernel_size;++iy)
00493                 {
00494                     double xpos = ix+0.5-kernel_size/2.;
00495                     double ypos = iy+0.5-kernel_size/2.;
00496                     double kernel_func = 1-sqrt(xpos*xpos+ypos*ypos)/
00497                     hawki_step_detect_obj_config.growing_radius;
00498                     if(kernel_func<0)
00499                         kernel_func = 0;
00500                     cpl_matrix_set(kernel, ix, iy, kernel_func);
00501                 }
00502             if (hawki_mask_convolve(object_mask, kernel) != CPL_ERROR_NONE) {
00503                 cpl_mask_delete(object_mask) ;
00504                 cpl_matrix_delete(kernel) ;
00505                 return NULL;
00506             }
00507             cpl_matrix_delete(kernel);
00508         }
00509     
00510         /* Put the mask and the chip image in the imagelist */
00511         mask_image[idet] =  cpl_image_new_from_mask(object_mask);
00512         comb_image[idet] =  chip_image;
00513         
00514         /* Labelise the different detected apertures */
00515         cpl_msg_info(__func__, "Labelise mask") ;
00516         labels = cpl_image_labelise_mask_create(object_mask, &nobj);
00517         if (labels == NULL) 
00518         {
00519             int jdet;
00520             cpl_free(apertures);
00521             cpl_mask_delete(object_mask);
00522             for (jdet=0 ; jdet<idet + 1 ; jdet++)
00523             {
00524                 cpl_image_delete(mask_image[jdet]);
00525                 cpl_image_delete(comb_image[jdet]);
00526             }
00527         }
00528         cpl_msg_info(__func__, "Number of objects detected: %d", nobj) ;
00529 
00530         /* Create the detected apertures list */
00531         cpl_msg_info(__func__, "Create apertures") ;
00532         apertures[idet] = cpl_apertures_new_from_image(chip_image, labels);
00533         if (apertures[idet] == NULL)
00534         {
00535             int jdet;
00536             cpl_free(apertures);
00537             cpl_mask_delete(object_mask);
00538             for (jdet=0 ; jdet<idet + 1 ; jdet++)
00539             {
00540                 cpl_image_delete(mask_image[jdet]);
00541                 cpl_image_delete(comb_image[jdet]);
00542             }
00543             return NULL;
00544         }
00545         
00546         /* Free */
00547         cpl_mask_delete(object_mask);
00548         cpl_image_delete(labels);
00549         cpl_msg_indent_less();
00550     }
00551 
00552     /* Free and return */
00553     cpl_msg_indent_less();
00554     return apertures;
00555 }
00556 
00557 /*----------------------------------------------------------------------------*/
00564 /*----------------------------------------------------------------------------*/
00565 static int hawki_step_detect_obj_aper_params
00566 (cpl_image      **  combined_images, 
00567  cpl_apertures  **  apertures,
00568  cpl_table      **  obj_charac)
00569 {
00570     int                 nb_objs ;
00571     double              angle ;
00572     double          *   fwhms_x ;
00573     double          *   fwhms_y ;
00574     cpl_bivector    *   iqe ;
00575     int                 nb_good ;
00576     cpl_vector      *   fwhms_good ;
00577     double          *   fwhms_good_data ;
00578     double              f_min, f_max, fr, fx, fy ;
00579     int                 chip;
00580     int                 iobj;
00581     int                 j;
00582     
00583     /* Initialise */
00584     double              seeing_min_arcsec = 0.1 ;
00585     double              seeing_max_arcsec = 5.0 ;
00586     double              seeing_fwhm_var   = 0.2 ;
00587 
00588     /* Check entries */
00589     if (combined_images  == NULL) return -1 ;
00590     if (obj_charac       == NULL) return -1 ;
00591 
00592     /* Loop on the HAWK-I detectors */
00593     cpl_msg_indent_more();
00594     for (chip=0 ; chip<HAWKI_NB_DETECTORS ; chip++) 
00595     {
00596 
00597         /* Number of detected objects */
00598         nb_objs = cpl_apertures_get_size(apertures[chip]);
00599         cpl_msg_info(__func__, "%d objects detected on chip %d",nb_objs,chip+1);
00600         hawki_step_detect_obj_output.nbobjs[chip] = nb_objs ;
00601         fwhms_x = cpl_malloc(nb_objs * sizeof(double)) ;
00602         fwhms_y = cpl_malloc(nb_objs * sizeof(double)) ;
00603         
00604         /* Initialize the output table */
00605         cpl_table_set_size(obj_charac[chip], nb_objs);
00606         cpl_table_new_column
00607             (obj_charac[chip], HAWKI_COL_OBJ_POSX, CPL_TYPE_DOUBLE) ;
00608         cpl_table_new_column
00609             (obj_charac[chip], HAWKI_COL_OBJ_POSY, CPL_TYPE_DOUBLE) ;
00610         cpl_table_new_column
00611             (obj_charac[chip], HAWKI_COL_OBJ_ANGLE, CPL_TYPE_DOUBLE) ;
00612         cpl_table_new_column
00613             (obj_charac[chip], HAWKI_COL_OBJ_FWHM_MAJAX, CPL_TYPE_DOUBLE) ;
00614         cpl_table_new_column
00615             (obj_charac[chip], HAWKI_COL_OBJ_FWHM_MINAX, CPL_TYPE_DOUBLE) ;
00616         cpl_table_new_column
00617             (obj_charac[chip], HAWKI_COL_OBJ_ELLIP, CPL_TYPE_DOUBLE);
00618         cpl_table_new_column
00619             (obj_charac[chip], HAWKI_COL_OBJ_FLUX, CPL_TYPE_DOUBLE);
00620         for (iobj=0 ; iobj<nb_objs ; iobj++)
00621         {
00622             /* Fill with the already known information */
00623             cpl_table_set_double(obj_charac[chip], HAWKI_COL_OBJ_POSX, iobj, 
00624                                  cpl_apertures_get_centroid_x(apertures[chip],
00625                                                               iobj+1));
00626             cpl_table_set_double(obj_charac[chip], HAWKI_COL_OBJ_POSY, iobj, 
00627                                  cpl_apertures_get_centroid_y(apertures[chip],
00628                                                               iobj+1));
00629             cpl_table_set_double(obj_charac[chip], HAWKI_COL_OBJ_FLUX, iobj, 
00630                                  cpl_apertures_get_flux(apertures[chip],
00631                                                         iobj+1));
00632             /* Compute the FWHM informations */
00633             iqe = cpl_image_iqe(combined_images[chip], 
00634                 (int)cpl_apertures_get_centroid_x(apertures[chip], iobj+1)- 10,
00635                 (int)cpl_apertures_get_centroid_y(apertures[chip], iobj+1)- 10,
00636                 (int)cpl_apertures_get_centroid_x(apertures[chip], iobj+1)+ 10,
00637                 (int)cpl_apertures_get_centroid_y(apertures[chip], iobj+1)+ 10);
00638             if (iqe == NULL)
00639             {
00640                 cpl_error_reset() ;
00641                 cpl_msg_debug(__func__, "Cannot get FWHM for obj at pos %g %g",
00642                               cpl_apertures_get_centroid_x(apertures[chip],
00643                                                            iobj+1),
00644                               cpl_apertures_get_centroid_y(apertures[chip],
00645                                                            iobj+1)) ;
00646                 fwhms_x[iobj] = -1.0 ;
00647                 fwhms_y[iobj] = -1.0 ;
00648                 angle = 0.0 ;
00649             }
00650             else 
00651             {
00652                 fwhms_x[iobj] = cpl_vector_get(cpl_bivector_get_x(iqe), 2) ;
00653                 fwhms_y[iobj] = cpl_vector_get(cpl_bivector_get_x(iqe), 3) ;
00654                 angle = cpl_vector_get(cpl_bivector_get_x(iqe), 4) ;
00655                 cpl_bivector_delete(iqe) ;
00656                 cpl_msg_debug(__func__,
00657                               "FWHM for obj at pos %g %g: %g x %g (%g)",
00658                               cpl_apertures_get_centroid_x(apertures[chip],
00659                                                            iobj+1),
00660                               cpl_apertures_get_centroid_y(apertures[chip],
00661                                                            iobj+1),
00662                               fwhms_x[iobj], fwhms_y[iobj], angle) ;
00663             }
00664             cpl_table_set_double
00665                 (obj_charac[chip], HAWKI_COL_OBJ_ANGLE, iobj, angle) ;
00666             cpl_table_set_double
00667                 (obj_charac[chip], HAWKI_COL_OBJ_FWHM_MAJAX, iobj,
00668                  fwhms_x[iobj]);
00669             cpl_table_set_double
00670                 (obj_charac[chip], HAWKI_COL_OBJ_FWHM_MINAX, iobj,
00671                  fwhms_y[iobj]);
00672             cpl_table_set_double
00673                 (obj_charac[chip], HAWKI_COL_OBJ_ELLIP, iobj,
00674                  1 - fwhms_y[iobj] / fwhms_x[iobj]);
00675         }
00676 
00677         /* Get the number of good values */
00678         nb_good = 0 ;
00679         for (iobj=0 ; iobj<nb_objs ; iobj++) 
00680         {
00681             if ((fwhms_x[iobj] > 0.0) && (fwhms_y[iobj] > 0.0)) nb_good++ ;
00682         }
00683         if (nb_good == 0) 
00684         {
00685             cpl_msg_warning
00686                 (__func__, "No objects to compute mean FWHM on chip %d",chip+1);
00687             cpl_free(fwhms_x) ;
00688             cpl_free(fwhms_y) ;
00689             continue;
00690         }
00691     
00692         /* Get the good values */
00693         fwhms_good = cpl_vector_new(nb_good) ;
00694         fwhms_good_data = cpl_vector_get_data(fwhms_good) ;
00695         j=0 ;
00696         for (iobj=0 ; iobj<nb_objs ; iobj++) 
00697         {
00698             if ((fwhms_x[iobj] > 0.0) && (fwhms_y[iobj] > 0.0)) 
00699             {
00700                 fwhms_good_data[j] = (fwhms_x[iobj]+fwhms_y[iobj])/2.0 ;
00701                 j++ ;
00702             }
00703         }
00704    
00705         /* Compute the fwhm */
00706         if (nb_good < 3) 
00707         {
00708             /* Too few values to compute the median */
00709             hawki_step_detect_obj_output.fwhm_pix[chip] = fwhms_good_data[0] ;
00710             cpl_msg_warning
00711                 (__func__, "Fewer than 3 objects, using the first object FWHM");
00712         } 
00713         else 
00714         {
00715             /* Compute the median */
00716             hawki_step_detect_obj_output.fwhm_pix[chip] =
00717                 cpl_vector_get_median_const(fwhms_good);
00718         }
00719         hawki_step_detect_obj_output.fwhm_arcsec[chip] = 
00720             hawki_step_detect_obj_output.fwhm_pix[chip] *
00721                 hawki_step_detect_obj_output.pixscale ;
00722 
00723         /* Compute the mode of the FWHMs */
00724         if (nb_good > 5)
00725         {
00726             hawki_step_detect_obj_output.fwhm_mode[chip] =
00727                 hawki_vector_get_mode(fwhms_good);
00728             hawki_step_detect_obj_output.fwhm_mode[chip] *= 
00729                 hawki_step_detect_obj_output.pixscale;
00730         }
00731         cpl_vector_delete(fwhms_good);
00732     
00733         /* IQ is the median of the (fwhm_x+fwhm_y/2) of the good stars */
00734         /* Compute f_min and f_max */
00735         f_min = seeing_min_arcsec / hawki_step_detect_obj_output.pixscale;
00736         f_max = seeing_max_arcsec / hawki_step_detect_obj_output.pixscale; 
00737 
00738         /* Get the number of good values */
00739         nb_good = 0 ;
00740         for (iobj=0 ; iobj<nb_objs ; iobj++) 
00741         {
00742             fx = fwhms_x[iobj] ;
00743             fy = fwhms_y[iobj] ;
00744             fr = 2.0 * fabs(fx-fy) / (fx+fy) ;
00745             if ((fx > f_min) && (fx < f_max) && (fy > f_min) && (fy < f_max) &&
00746                     (fr < seeing_fwhm_var)) nb_good++ ;
00747         }
00748         if (nb_good == 0) 
00749         {
00750             cpl_msg_warning(__func__, "No objects to compute IQ on chip %d",
00751                             chip+1);
00752             cpl_free(fwhms_x) ;
00753             cpl_free(fwhms_y) ;
00754             continue;
00755         }
00756 
00757         /* Get the good values */
00758         fwhms_good = cpl_vector_new(nb_good) ;
00759         fwhms_good_data = cpl_vector_get_data(fwhms_good) ;
00760         j=0 ;
00761         for (iobj=0 ; iobj<nb_objs ; iobj++) 
00762         {
00763             fx = fwhms_x[iobj] ;
00764             fy = fwhms_y[iobj] ;
00765             fr = 2.0 * fabs(fx-fy) / (fx+fy) ;
00766             if ((fx > f_min) && (fx < f_max) && (fy > f_min) && (fy < f_max) &&
00767                     (fr < seeing_fwhm_var)) 
00768             {
00769                 fwhms_good_data[j] = (fx + fy)/2.0 ;
00770                 j++ ;
00771             }
00772         }
00773         cpl_free(fwhms_x) ;
00774         cpl_free(fwhms_y) ;
00775     
00776         /* Compute the fwhm */
00777         if (nb_good < 3) 
00778         {
00779             /* Too few values to compute the median */
00780             hawki_step_detect_obj_output.iq[chip] = fwhms_good_data[0] ;
00781         }
00782         else 
00783         {
00784             /* Compute the median */
00785             hawki_step_detect_obj_output.iq[chip] = 
00786                 cpl_vector_get_median_const(fwhms_good) ;
00787         }
00788         cpl_vector_delete(fwhms_good);
00789         hawki_step_detect_obj_output.iq[chip] *= 
00790             hawki_step_detect_obj_output.pixscale;
00791     }
00792     cpl_msg_indent_less();
00793     
00794     return 0;
00795 }
00796         
00797         
00798 /*----------------------------------------------------------------------------*/
00807 /*----------------------------------------------------------------------------*/
00808 static int hawki_step_detect_obj_save
00809 (cpl_image           **  mask_images,
00810  cpl_table           **  obj_charac,
00811  cpl_propertylist    **  obj_stats,
00812  cpl_parameterlist   *   parlist,
00813  cpl_frameset        *   framelist)
00814 {
00815     const cpl_frame     *   ref_frame ;
00816     cpl_propertylist    **  qclists;
00817     int                     ext_nb ;
00818     const char          *   recipe_name = "hawki_step_detect_obj" ;
00819     int                     i;
00820     cpl_errorstate          error_prevstate = cpl_errorstate_get();
00821     
00822 
00823 
00824     /* Load the WCS keys */
00825     ref_frame = irplib_frameset_get_first_from_group
00826         (framelist, CPL_FRAME_GROUP_RAW);
00827 
00828     /* Create the QC lists */
00829     qclists = cpl_malloc(HAWKI_NB_DETECTORS * sizeof(cpl_propertylist*)) ;
00830     for (i=0 ; i<HAWKI_NB_DETECTORS ; i++)
00831     {
00832         cpl_propertylist    *   inputlist;
00833         cpl_propertylist    *   offsetlist;
00834         cpl_propertylist    *   wcslist;
00835 
00836         /* Get the extension number */
00837         ext_nb=hawki_get_ext_from_detector(cpl_frame_get_filename(ref_frame), i+1);
00838         qclists[i] = cpl_propertylist_new() ;
00839 
00840         /* Fill the QC */
00841         cpl_propertylist_append_int
00842             (qclists[i], "ESO QC NBOBJS", 
00843              hawki_step_detect_obj_output.nbobjs[i]);
00844         cpl_propertylist_append_double
00845             (qclists[i], "ESO QC IQ", hawki_step_detect_obj_output.iq[i]);
00846         cpl_propertylist_append_double
00847             (qclists[i], "ESO QC FWHM PIX",
00848              hawki_step_detect_obj_output.fwhm_pix[i]);
00849         cpl_propertylist_append_double
00850             (qclists[i], "ESO QC FWHM ARCSEC",
00851              hawki_step_detect_obj_output.fwhm_arcsec[i]);
00852         cpl_propertylist_append_double
00853             (qclists[i], "ESO QC FWHM MODE",
00854              hawki_step_detect_obj_output.fwhm_mode[i]);
00855 
00856         /* Propagate some keywords from input raw frame extensions */
00857         inputlist = cpl_propertylist_load_regexp(
00858                 cpl_frame_get_filename(ref_frame), ext_nb,
00859                 HAWKI_HEADER_EXT_FORWARD, 0);
00860         offsetlist = cpl_propertylist_load_regexp(
00861                 cpl_frame_get_filename(ref_frame), ext_nb,
00862                 HAWKI_HEADER_COMB_OFFSETS, 0);
00863         wcslist = cpl_propertylist_load_regexp(
00864                 cpl_frame_get_filename(ref_frame), ext_nb,
00865                 HAWKI_HEADER_WCS, 0);
00866         cpl_propertylist_append(qclists[i], inputlist);
00867         cpl_propertylist_append(qclists[i], offsetlist);
00868         cpl_propertylist_append(qclists[i], wcslist);
00869         cpl_propertylist_delete(inputlist);
00870         cpl_propertylist_delete(offsetlist);
00871         cpl_propertylist_delete(wcslist);
00872         
00873         /* Add the object statistics keywords */
00874         cpl_propertylist_append(qclists[i], obj_stats[i]);
00875     }
00876 
00877 
00878     /* Write the object mask */
00879     hawki_images_save(framelist,
00880                       parlist,
00881                       framelist, 
00882                       (const cpl_image**)mask_images, 
00883                       recipe_name,
00884                       HAWKI_CALPRO_OBJ_MASK, 
00885                       HAWKI_PROTYPE_OBJ_MASK,
00886                       NULL,
00887                       (const cpl_propertylist**)qclists,
00888                       "hawki_step_detect_obj_mask.fits") ;
00889 
00890     /* Write the FITS table with the objects statistics */
00891     hawki_tables_save(framelist,
00892                       parlist,
00893                       framelist,    
00894                       (const cpl_table **)obj_charac,
00895                       recipe_name,
00896                       HAWKI_CALPRO_OBJ_PARAM,
00897                       HAWKI_PROTYPE_OBJ_PARAM,
00898                       NULL,
00899                       (const cpl_propertylist**)qclists,
00900                       "hawki_step_detect_obj_stars.fits") ;
00901 
00902 
00903     /* Free and return */
00904     for (i=0 ; i<HAWKI_NB_DETECTORS ; i++) {
00905         cpl_propertylist_delete(qclists[i]) ;
00906     }
00907     cpl_free(qclists) ;
00908     if(!cpl_errorstate_is_equal(error_prevstate))
00909     {
00910         cpl_errorstate_set(CPL_ERROR_NONE);
00911         return -1;
00912     }
00913     return  0;
00914 }
00915 
00916 static void hawki_step_detect_obj_init_output(void)
00917 {
00918     int    idet;
00919     
00920     for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++) 
00921     {
00922         hawki_step_detect_obj_output.iq[idet] = -1.0 ;
00923         hawki_step_detect_obj_output.nbobjs[idet] = -1 ;
00924         hawki_step_detect_obj_output.fwhm_pix[idet] = -1.0 ;
00925         hawki_step_detect_obj_output.fwhm_arcsec[idet] = -1.0 ;
00926         hawki_step_detect_obj_output.fwhm_mode[idet] = -1.0 ;
00927         hawki_step_detect_obj_output.pos_x[idet] = -1.0 ;
00928         hawki_step_detect_obj_output.pos_y[idet] = -1.0 ;
00929     }
00930     hawki_step_detect_obj_output.pixscale = -1.0;
00931 }
00932 
00933 static void hawki_step_detect_obj_get_pscale
00934 (cpl_frameset * combframes)
00935 {
00936     cpl_propertylist  * plist;
00937     cpl_frame         * firstframe;
00938     cpl_errorstate      error_prevstate = cpl_errorstate_get();
00939     
00940     /* Get the header infos */
00941     firstframe = cpl_frameset_get_frame(combframes, 0) ;
00942     plist=cpl_propertylist_load(cpl_frame_get_filename(firstframe), 0) ;
00943     hawki_step_detect_obj_output.pixscale = hawki_pfits_get_pixscale(plist);
00944     cpl_propertylist_delete(plist) ;
00945     if(!cpl_errorstate_is_equal(error_prevstate))
00946     {
00947         cpl_msg_error(__func__, "Missing PIXSCALE keyword in FITS header") ;
00948         cpl_errorstate_set(CPL_ERROR_NONE);
00949         return;
00950     }
00951 }
00952 

Generated on Thu Feb 17 17:13:08 2011 for HAWKI Pipeline Reference Manual by  doxygen 1.4.7