36 #include "omega_recipe.h"
38 #include "omega_background.h"
39 #include "omega_bpm.h"
40 #include "omega_flats.h"
41 #include <cpl_errorstate.h>
76 static int omega_mflat_create(cpl_plugin *) ;
77 static int omega_mflat_exec(cpl_plugin *) ;
78 static int omega_mflat_destroy(cpl_plugin *) ;
79 static int omega_mflat(cpl_frameset *,cpl_parameterlist *);
85 static void omega_mflat_init(
void);
86 static void omega_mflat_tidy(
void);
116 const cpl_frame *cframe;
117 const cpl_frame *hframe;
118 const cpl_frame *mbframe;
119 const cpl_frame *mdomefr;
120 const cpl_frame *nskyfr;
121 const cpl_frame *bpframe;
123 cpl_frameset *flatlist;
124 cpl_propertylist *eh;
126 omega_fits *firstflat;
131 cpl_image *mtwilight;
140 #define RECIPE "omega_mflat"
158 cpl_recipe * recipe = cpl_calloc(1,
sizeof(*recipe)) ;
159 cpl_plugin * plugin = &recipe->interface ;
161 cpl_plugin_init(plugin,
163 OMEGA_BINARY_VERSION,
164 CPL_PLUGIN_TYPE_RECIPE,
166 "OMEGA - Create Master Twilight and Master Flat for each chip",
167 "This recipe is used to derive a valid twilight flat frame (Calfile 543, 546) \n"
168 "for one particular chip and filter. The recipe always takes as input \n"
169 "a list of raw twilight flat frames, a master bias and an optional master \n"
170 "dome flat to be used in creating a final Master Flat Field. In addition, a hot \n"
171 "pixel map (and a cold pixel map can be provided, which will be used to create a \n"
172 "bad pixels map. Optionally, an overscan correction mode \n"
173 "can be set. The default is to apply no overscan correction.\n\n"
174 "The raw twilight flats are trimmed and overscan corrected. The data are then \n"
175 "normalized, averaged, and the result is normalized again. Image statistics \n"
176 "are computed for the resulting frames.",
182 omega_mflat_destroy) ;
184 cpl_pluginlist_append(list, plugin) ;
192 static int omega_mflat_create(cpl_plugin * plugin)
199 if (cpl_error_get_code() != CPL_ERROR_NONE) {
200 cpl_msg_error(cpl_func,
"%s():%d: An error is already set: %s",
201 cpl_func, __LINE__, cpl_error_get_where());
202 return (
int)cpl_error_get_code();
205 if (plugin == NULL) {
206 cpl_msg_error(cpl_func,
"Null plugin");
207 cpl_ensure_code(0, (
int)CPL_ERROR_NULL_INPUT);
211 if (cpl_plugin_get_type(plugin) != CPL_PLUGIN_TYPE_RECIPE) {
212 cpl_msg_error(cpl_func,
"Plugin is not a recipe");
213 cpl_ensure_code(0, (
int)CPL_ERROR_TYPE_MISMATCH);
217 recipe = (cpl_recipe *)plugin;
220 recipe->parameters = cpl_parameterlist_new() ;
221 if (recipe->parameters == NULL) {
222 cpl_msg_error(cpl_func,
"Parameter list allocation failed");
223 cpl_ensure_code(0, (
int)CPL_ERROR_ILLEGAL_OUTPUT);
230 p = cpl_parameter_new_value(
"omega.omega_mflat.ExtensionNumber",
232 "FITS extension number to load (1 to 32). (-1 = all)",
236 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"ext") ;
237 cpl_parameterlist_append(recipe->parameters, p) ;
240 p = cpl_parameter_new_range(
"omega.omega_mflat.OverscanMethod",
242 "Overscan Correction Method",
246 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"oc-meth") ;
247 cpl_parameterlist_append(recipe->parameters, p) ;
249 p = cpl_parameter_new_value(
"omega.omega_mflat.PAF",
251 "Boolean value to create PAF files. 1(Yes), 0(No)",
255 cpl_parameter_set_alias(p,CPL_PARAMETER_MODE_CLI,
"paf") ;
256 cpl_parameterlist_append(recipe->parameters, p) ;
258 p = cpl_parameter_new_value(
"omega.omega_mflat.SigmaClip",
260 "Sigma Clipping Threshold",
264 cpl_parameter_set_alias(p,CPL_PARAMETER_MODE_CLI,
"sig-clip") ;
265 cpl_parameterlist_append(recipe->parameters, p) ;
270 path = cpl_sprintf(
"%s", OMEGA_BIN_PATH);
271 p = cpl_parameter_new_value(
"omega.omega_mflat.BinPath",
273 "Path to any external executable program.",
277 cpl_parameter_set_alias(p,CPL_PARAMETER_MODE_CLI,
"bin-path");
278 cpl_parameterlist_append(recipe->parameters, p);
281 p = cpl_parameter_new_value(
"omega.omega_mflat.GaussianFiltSize",
283 "Standard deviation of Gaussian Fourier filter size",
287 cpl_parameter_set_alias(p,CPL_PARAMETER_MODE_CLI,
"gau_filt_sz") ;
288 cpl_parameterlist_append(recipe->parameters, p) ;
290 p = cpl_parameter_new_value(
"omega.omega_mflat.MirrorXpix",
292 "Width of X region for mirroring edges (FFT continuity)",
296 cpl_parameter_set_alias(p,CPL_PARAMETER_MODE_CLI,
"mr_xpix") ;
297 cpl_parameterlist_append(recipe->parameters, p) ;
299 p = cpl_parameter_new_value(
"omega.omega_mflat.MirrorYpix",
301 "Width of Y region for mirroring edges (FFT continuity)",
305 cpl_parameter_set_alias(p,CPL_PARAMETER_MODE_CLI,
"mr_ypix") ;
306 cpl_parameterlist_append(recipe->parameters, p) ;
309 p = cpl_parameter_new_range(
"omega.omega_mflat.LowThre",
311 "Low flagging threshold for cold pixels map",
315 cpl_parameter_set_alias(p,CPL_PARAMETER_MODE_CLI,
"low") ;
316 cpl_parameterlist_append(recipe->parameters, p) ;
318 p = cpl_parameter_new_range(
"omega.omega_mflat.HighThre",
320 "High flagging threshold for cold pixels map",
324 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"high") ;
325 cpl_parameterlist_append(recipe->parameters, p) ;
333 static int omega_mflat_exec(cpl_plugin * plugin)
339 if (cpl_error_get_code() != CPL_ERROR_NONE) {
340 cpl_msg_error(cpl_func,
"%s():%d: An error is already set: %s",
341 cpl_func, __LINE__, cpl_error_get_where());
342 return (
int)cpl_error_get_code();
345 if (plugin == NULL) {
346 cpl_msg_error(cpl_func,
"Null plugin");
347 cpl_ensure_code(0, (
int)CPL_ERROR_NULL_INPUT);
351 if (cpl_plugin_get_type(plugin) != CPL_PLUGIN_TYPE_RECIPE) {
352 cpl_msg_error(cpl_func,
"Plugin is not a recipe");
353 cpl_ensure_code(0, (
int)CPL_ERROR_TYPE_MISMATCH);
357 recipe = (cpl_recipe *)plugin;
360 if (recipe->parameters == NULL) {
361 cpl_msg_error(cpl_func,
"Recipe invoked with NULL parameter list");
362 cpl_ensure_code(0, (
int)CPL_ERROR_NULL_INPUT);
364 if (recipe->frames == NULL) {
365 cpl_msg_error(cpl_func,
"Recipe invoked with NULL frame set");
366 cpl_ensure_code(0, (
int)CPL_ERROR_NULL_INPUT);
370 recipe_status = omega_mflat(recipe->frames, recipe->parameters);
373 if (cpl_dfs_update_product_header(recipe->frames)) {
374 if (!recipe_status) recipe_status = (int)cpl_error_get_code();
377 return recipe_status;
383 static int omega_mflat_destroy(cpl_plugin * plugin)
387 if (plugin == NULL) {
388 cpl_msg_error(cpl_func,
"Null plugin");
389 cpl_ensure_code(0, (
int)CPL_ERROR_NULL_INPUT);
393 if (cpl_plugin_get_type(plugin) != CPL_PLUGIN_TYPE_RECIPE) {
394 cpl_msg_error(cpl_func,
"Plugin is not a recipe");
395 cpl_ensure_code(0, (
int)CPL_ERROR_TYPE_MISMATCH);
399 recipe = (cpl_recipe *)plugin;
401 cpl_parameterlist_delete(recipe->parameters) ;
409 static int omega_mflat(cpl_frameset *
set, cpl_parameterlist *pars)
419 const char *_id =
"omega_mflat";
421 char *outtwilight = NULL;
422 char *outmflat = NULL;
423 const cpl_frame *firstframe;
424 const cpl_frame *refframe;
425 cpl_frame *prframe_twil = NULL;
426 cpl_frame *prframe_mflat = NULL;
427 cpl_frame *prframe_bpm = NULL;
429 cpl_propertylist *qclist;
430 cpl_propertylist *alist;
431 cpl_stats *diffstats = NULL;
432 cpl_errorstate prestate = cpl_errorstate_get();
438 cpl_msg_error (_id,
"Parameters list not found");
442 if (cpl_frameset_is_empty(
set) == 1) {
443 cpl_msg_error (_id,
"Frameset not found");
448 par = cpl_parameterlist_find(pars,
"omega.omega_mflat.ExtensionNumber") ;
449 omega_mflat_config.extnum = cpl_parameter_get_int(par) ;
451 par = cpl_parameterlist_find(pars,
"omega.omega_mflat.OverscanMethod") ;
452 omega_mflat_config.oc = cpl_parameter_get_int(par) ;
454 par = cpl_parameterlist_find(pars,
"omega.omega_mflat.SigmaClip") ;
455 omega_mflat_config.sigma = cpl_parameter_get_double(par) ;
457 par = cpl_parameterlist_find(pars,
"omega.omega_mflat.PAF") ;
458 omega_mflat_config.paf = cpl_parameter_get_bool(par) ;
461 if (oc_dfs_set_groups(
set)) {
462 cpl_msg_error(_id,
"Cannot identify RAW and CALIB frames") ;
472 cpl_msg_error(_id,
"Cannot labelise the input frameset");
477 MTWIL_RAW)) == NULL) {
478 cpl_msg_error(_id,
"Cannot find twilight flats in input frameset");
482 nflats = cpl_frameset_count_tags (ps.flatlist, MTWIL_RAW);
484 cpl_msg_error (_id,
"Need at least 2 (%s) frames to run "
485 "this recipe", MTWIL_RAW);
490 cpl_msg_info (_id,
"There are %d %s frames in frame set",nflats, MTWIL_RAW);
494 ps.mbframe = cpl_frameset_find_const(
set, OMEGA_CALIB_BIAS);
495 if (ps.mbframe == NULL) {
496 cpl_msg_error(cpl_func,
"Cannot find OMEGA_CALIB_BIAS input in frame set");
500 cpl_msg_info(_id,
"Using %s %s",OMEGA_CALIB_BIAS, cpl_frame_get_filename(ps.mbframe));
503 ps.cframe = cpl_frameset_find_const(
set, OMEGA_CALIB_CPM);
504 if(ps.cframe == NULL){
505 cpl_msg_error(cpl_func,
"Cannot find %s input in frame set",OMEGA_CALIB_CPM);
509 cpl_msg_info(_id,
"Using %s %s",OMEGA_CALIB_CPM, cpl_frame_get_filename(ps.cframe));
512 ps.hframe = cpl_frameset_find_const(
set, OMEGA_CALIB_HPM);
513 if(ps.hframe == NULL){
514 cpl_msg_error(cpl_func,
"Cannot find %s input in frame set",OMEGA_CALIB_HPM);
518 cpl_msg_info(_id,
"Using %s %s",OMEGA_CALIB_HPM, cpl_frame_get_filename(ps.hframe));
521 ps.mdomefr = cpl_frameset_find_const(
set, OMEGA_CALIB_DOME);
522 if(ps.mdomefr != NULL) {
523 cpl_msg_info(_id,
"Using %s %s", OMEGA_CALIB_DOME, cpl_frame_get_filename(ps.mdomefr));
527 ps.nskyfr = cpl_frameset_find_const(
set, OMEGA_CALIB_NSKY);
528 if(ps.nskyfr != NULL) {
529 cpl_msg_info(_id,
"Using %s %s", OMEGA_CALIB_NSKY, cpl_frame_get_filename(ps.nskyfr));
533 refframe = cpl_frameset_find_const(
set, REFMFLAT);
534 if (refframe != NULL)
535 cpl_msg_info(cpl_func,
"Using %s for comparison",cpl_frame_get_filename(refframe));
539 firstframe = cpl_frameset_get_first(ps.flatlist);
543 if(omega_mflat_config.extnum == 0){
544 cpl_msg_error(cpl_func,
"Unsupported extension request, %d",omega_mflat_config.extnum);
549 for (j = jst; j <= jfn; j++) {
551 isfirst = (j == jst);
552 cpl_msg_info(_id,
"Beginning work on extension %d",j);
554 omega_mflat_config.bpm = 0;
555 omega_mflat_config.Mean = 0.0;
556 omega_mflat_config.Median = 0.0;
557 omega_mflat_config.Stdev = 0.0;
558 omega_mflat_config.RawMin = 0.0;
559 omega_mflat_config.RawMax = 0.0;
560 omega_mflat_config.RawMean = 0.0;
561 omega_mflat_config.RawMedian = 0.0;
562 omega_mflat_config.RawStdev = 0.0;
565 if(ps.mbframe != NULL){
567 if(oscan1 != omega_mflat_config.oc) {
568 cpl_msg_warning (_id,
"Overscan correction mode for Master Bias (oc = %d) differs from "
569 "the one used here (oc = %d)", oscan1, omega_mflat_config.oc);
581 cpl_msg_warning(_id,
"Image detector is not live");
583 freefits(ps.firstflat);
587 else if(status == -1){
588 cpl_msg_error(_id,
"Cannot combine images");
590 freespace(outtwilight);
598 qclist = cpl_propertylist_new();
602 if(refframe != NULL){
604 cpl_msg_warning(cpl_func,
"Cannot compare with reference frame");
607 cpl_propertylist_append_double(qclist,
"ESO QC DIFF REFMFLAT MEAN",
608 cpl_stats_get_mean(diffstats));
609 cpl_propertylist_set_comment(qclist,
"ESO QC DIFF REFMFLAT MEAN",
610 "Mean of difference with reference");
611 cpl_propertylist_append_double(qclist,
"ESO QC DIFF REFMFLAT MEDIAN",
612 cpl_stats_get_median(diffstats));
613 cpl_propertylist_set_comment(qclist,
"ESO QC DIFF REFMFLAT MEDIAN",
614 "Median of difference with reference");
615 cpl_propertylist_append_double(qclist,
"ESO QC DIFF REFMFLAT STDEV",
616 cpl_stats_get_stdev(diffstats));
617 cpl_propertylist_set_comment(qclist,
"ESO QC DIFF REFMFLAT STDEV",
618 "Stdev of difference with reference");
620 freestats(diffstats);
626 ps.stats = cpl_stats_new_from_image(ps.mflat, CPL_STATS_ALL);
627 if(ps.stats != NULL) {
628 omega_mflat_config.Mean = cpl_stats_get_mean(ps.stats);
629 omega_mflat_config.Median = cpl_stats_get_median(ps.stats);
630 omega_mflat_config.Stdev = cpl_stats_get_stdev(ps.stats);
635 cpl_propertylist_append_double(qclist,
"ESO QC MASTER FLAT MEAN",
636 omega_mflat_config.Mean) ;
637 cpl_propertylist_set_comment(qclist,
"ESO QC MASTER FLAT MEAN",
638 "Mean value of master flat");
639 cpl_propertylist_append_double(qclist,
"ESO QC MASTER FLAT MEDIAN",
640 omega_mflat_config.Median) ;
641 cpl_propertylist_set_comment(qclist,
"ESO QC MASTER FLAT MEDIAN",
642 "Median value of master flat");
643 cpl_propertylist_append_double(qclist,
"ESO QC MASTER FLAT STDEV",
644 omega_mflat_config.Stdev) ;
645 cpl_propertylist_set_comment(qclist,
"ESO QC MASTER FLAT STDEV",
646 "Standard deviation value of master flat");
650 outmflat = cpl_sprintf(
"%s_%s.fits", INSTRUME,MFLAT_PROCATG);
655 alist = cpl_propertylist_new();
656 cpl_propertylist_append_string(alist,
"EXTNAME",
657 cpl_propertylist_get_string(ps.eh,
"EXTNAME"));
658 cpl_propertylist_set_comment(alist,
"EXTNAME",
"Extension name");
660 cpl_propertylist_copy_property_regexp(alist, ps.eh, WCS_KEYS, 0);
663 cpl_propertylist_update_int(alist,
"ESO DRS OVERSCAN METHOD", omega_mflat_config.oc);
664 cpl_propertylist_set_comment(alist,
"ESO DRS OVERSCAN METHOD",
"overscan correction method");
666 if(
omega_save_image(ps.mflat,
set,pars,alist,qclist,CPL_BPP_IEEE_FLOAT,outmflat,
667 RECIPE,prframe_mflat,NULL,isfirst) == -1){
668 cpl_msg_error(_id,
"Cannot save product %s", MFLAT_PROCATG);
672 freespace(outtwilight);
685 ps.stats = cpl_stats_new_from_image(ps.mtwilight, CPL_STATS_ALL);
686 if(ps.stats != NULL) {
687 omega_mflat_config.Mean = cpl_stats_get_mean(ps.stats);
688 omega_mflat_config.Median = cpl_stats_get_median(ps.stats);
689 omega_mflat_config.Stdev = cpl_stats_get_stdev(ps.stats);
694 qclist = cpl_propertylist_new();
695 cpl_propertylist_append_double(qclist,
"ESO QC MASTER TWILIGHT MEAN",
696 omega_mflat_config.Mean) ;
697 cpl_propertylist_set_comment(qclist,
"ESO QC MASTER TWILIGHT MEAN",
698 "Mean value of master twilight flat");
699 cpl_propertylist_append_double(qclist,
"ESO QC MASTER TWILIGHT MEDIAN",
700 omega_mflat_config.Median) ;
701 cpl_propertylist_set_comment(qclist,
"ESO QC MASTER TWILIGHT MEDIAN",
702 "Median value of master twilight flat");
703 cpl_propertylist_append_double(qclist,
"ESO QC MASTER TWILIGHT STDEV",
704 omega_mflat_config.Stdev) ;
705 cpl_propertylist_set_comment(qclist,
"ESO QC MASTER TWILIGHT STDEV",
706 "Standard deviation value of master twilight flat");
708 cpl_propertylist_append_double(qclist,
"ESO QC RAW TWILIGHT MIN",
709 omega_mflat_config.RawMin);
710 cpl_propertylist_append_double(qclist,
"ESO QC RAW TWILIGHT MAX",
711 omega_mflat_config.RawMax);
712 cpl_propertylist_append_double(qclist,
"ESO QC RAW TWILIGHT MEAN",
713 omega_mflat_config.RawMean);
714 cpl_propertylist_append_double(qclist,
"ESO QC RAW TWILIGHT MEDIAN",
715 omega_mflat_config.RawMedian);
716 cpl_propertylist_append_double(qclist,
"ESO QC RAW TWILIGHT STDEV",
717 omega_mflat_config.RawStdev);
719 cpl_propertylist_set_comment(qclist,
"ESO QC RAW TWILIGHT MIN",
720 "median value of the raw flat flat having the lowest flux");
721 cpl_propertylist_set_comment(qclist,
"ESO QC RAW TWILIGHT MAX",
722 "median value of the raw flat flat having the highest flux");
723 cpl_propertylist_set_comment(qclist,
"ESO QC RAW TWILIGHT MEAN",
724 "mean value of all input raw flat flats (ADU)");
725 cpl_propertylist_set_comment(qclist,
"ESO QC RAW TWILIGHT MEDIAN",
726 "median value of all input raw flat flats (ADU)");
727 cpl_propertylist_set_comment(qclist,
"ESO QC RAW TWILIGHT STDEV",
728 "standard deviation of all input raw flat flats (ADU)");
732 outtwilight = cpl_sprintf(
"%s_%s.fits", INSTRUME,MTWIL_PROCATG);
736 if(
omega_save_image(ps.mtwilight,
set,pars,alist,qclist,CPL_BPP_IEEE_FLOAT,outtwilight,
737 RECIPE,prframe_twil,NULL,isfirst) == -1){
738 cpl_msg_error(_id,
"Cannot save product %s", MTWIL_PROCATG);
741 freespace(outtwilight);
749 freeimage(ps.mtwilight);
754 qclist = cpl_propertylist_new();
755 cpl_propertylist_append_int(qclist,
"ESO QC NUMBER BAD PIXELS",omega_mflat_config.bpm);
756 cpl_propertylist_set_comment(qclist,
"ESO QC NUMBER BAD PIXELS",
757 "Number of bad pixels");
760 outbpm = cpl_sprintf(
"%s_%s.fits", INSTRUME,BPM_PROCATG);
764 if(
omega_save_image(ps.bpixels,
set,pars,alist,qclist,CPL_BPP_16_SIGNED,outbpm,
765 RECIPE,prframe_bpm,NULL,isfirst) == -1){
766 cpl_msg_error(_id,
"Cannot save product %s", BPM_PROCATG);
770 freespace(outtwilight);
778 freeimage(ps.bpixels);
779 freefits(ps.firstflat);
787 freespace(outtwilight);
791 if(!cpl_errorstate_is_equal(prestate)){
792 cpl_errorstate_dump(prestate,CPL_FALSE,NULL);
813 int i,nflats,live, naxis1, naxis2;
817 double threshold = 0.0;
819 const char *_id =
"omega_mflat_combine";
822 const cpl_frame *flatfr;
824 cpl_vector *median_vector = NULL;
825 cpl_image *trim_raw,*dev,*good_float,*good_int,*median_all,*new_image;
826 cpl_image *sum_data,*sum_good;
831 cpl_imagelist *ilist;
834 nflats = cpl_frameset_get_size(ps.flatlist);
835 flatfr = cpl_frameset_get_first_const(ps.flatlist);
844 if(ps.mbframe != NULL){
845 mbias = cpl_image_load(cpl_frame_get_filename(ps.mbframe), CPL_TYPE_FLOAT,0,xn);
847 cpl_msg_warning(_id,
"Cannot load image %s", OMEGA_CALIB_BIAS);
852 bpm_map =
makebpm(ps.hframe, ps.cframe, xn);
855 omega_mflat_config.bpm = cpl_mask_count(bpm_map);
858 scales = cpl_vector_new(nflats);
859 data_scales = cpl_vector_get_data(scales);
861 median_vector = cpl_vector_new (nflats);
862 cpl_vector_fill(median_vector,0.0);
864 ilist = cpl_imagelist_new();
865 cpl_msg_info (_id,
"Doing trim and overscan correction on images");
868 for (i=0; i< nflats; i++)
872 if(trim_raw == NULL){
874 freevector(median_vector);
882 cpl_image_subtract(trim_raw, mbias);
884 cpl_image_subtract_scalar(trim_raw, bias);
886 if (bpm_map == NULL) {
887 ps.stats = cpl_stats_new_from_image(trim_raw, CPL_STATS_ALL);
888 median = cpl_stats_get_median(ps.stats);
891 cpl_image_reject_from_mask(trim_raw, bpm_map);
892 ps.stats = cpl_stats_new_from_image(trim_raw, CPL_STATS_ALL);
893 median = cpl_stats_get_median(ps.stats);
896 cpl_vector_set(median_vector, i, median);
898 data_scales[i] = (double)1.0/median;
900 cpl_image_divide_scalar(trim_raw, median);
902 cpl_imagelist_set(ilist, trim_raw, i);
905 flatfr = cpl_frameset_get_next_const(ps.flatlist);
913 omega_mflat_config.RawMin = cpl_vector_get_min(median_vector);
914 omega_mflat_config.RawMax = cpl_vector_get_max(median_vector);
915 omega_mflat_config.RawMean = cpl_vector_get_mean(median_vector);
916 omega_mflat_config.RawMedian = cpl_vector_get_median(median_vector);
917 omega_mflat_config.RawStdev = cpl_vector_get_stdev(median_vector);
919 freevector(median_vector);
925 cpl_msg_error(_id,
"Error in image list <%s>",cpl_error_get_message());
947 cpl_msg_info(_id,
"Using default value for gain");
952 cpl_msg_info(_id,
"Gain value from images is %g", gain);
955 cpl_msg_info (_id,
"Computing the median of all images...");
956 median_all = cpl_imagelist_collapse_median_create(ilist);
958 if (median_all == NULL) {
959 cpl_msg_error (_id,
"Cannot take median of imset <%s>",cpl_error_get_message());
966 naxis1 = cpl_image_get_size_x(median_all);
967 naxis2 = cpl_image_get_size_y(median_all);
969 sum_data = cpl_image_new(naxis1,naxis2,CPL_TYPE_FLOAT);
970 sum_good = cpl_image_new(naxis1,naxis2,CPL_TYPE_FLOAT);
973 for (i=0; i< nflats; i++)
975 trim_raw = cpl_imagelist_get(ilist, i);
976 new_image = cpl_image_duplicate(trim_raw);
982 cpl_image_threshold(trim_raw, 0, FLT_MAX, 0, 2e20);
984 dev = cpl_image_subtract_create(median_all, trim_raw);
986 code = cpl_image_power(trim_raw, 0.5);
987 if(code != CPL_ERROR_NONE) {
988 cpl_msg_error(_id,
"Error in SQRT operation <%s>",cpl_error_get_message());
991 freeimage(median_all);
994 freeimage(new_image);
1000 cpl_image_divide(dev, trim_raw);
1002 threshold = omega_mflat_config.sigma * (sqrt(gain * data_scales[i]));
1004 good = cpl_mask_threshold_image_create(dev, -threshold, threshold);
1007 good_int = cpl_image_new_from_mask(good) ;
1010 good_float = cpl_image_cast(good_int, CPL_TYPE_FLOAT);
1011 freeimage(good_int);
1013 cpl_image_multiply(new_image, good_float);
1014 cpl_image_add(sum_data, new_image);
1016 cpl_image_add(sum_good, good_float);
1018 freeimage(new_image);
1019 freeimage(good_float);
1023 freeimage(median_all);
1027 ps.mtwilight = cpl_image_divide_create(sum_data, sum_good);
1028 if (ps.mtwilight == NULL) {
1029 cpl_msg_error(_id,
"Error in division %s <%s>",MTWIL_PROCATG, cpl_error_get_message());
1031 freeimage(sum_data);
1032 freeimage(sum_good);
1037 freeimage(sum_data);
1038 freeimage(sum_good);
1043 if(ps.mdomefr != NULL){
1045 mdome = cpl_image_load(cpl_frame_get_filename(ps.mdomefr), CPL_TYPE_FLOAT,0,xn);
1047 cpl_msg_warning(_id,
"Cannot load image %s", OMEGA_CALIB_DOME);
1048 ps.mflat = cpl_image_duplicate(ps.mtwilight);
1052 if(ps.mflat == NULL){
1053 cpl_msg_warning(_id,
"Cannot calculate Master Flat Field");
1054 ps.mflat = cpl_image_duplicate(ps.mtwilight);
1060 cpl_msg_warning(_id,
"There is no Master Dome Flat in frame set");
1061 ps.mflat = cpl_image_duplicate(ps.mtwilight);
1065 if (ps.nskyfr != NULL) {
1066 nsky = cpl_image_load(cpl_frame_get_filename(ps.nskyfr), CPL_TYPE_FLOAT,0,xn);
1068 cpl_msg_warning(_id,
"Cannot load image %s", OMEGA_CALIB_NSKY);
1071 cpl_image_multiply (ps.mflat, nsky);
1080 ps.bpixels = cpl_image_new_from_mask(bpm_map);
1082 omega_mflat_config.bpm = cpl_mask_count(bpm_map);
1089 static void omega_mflat_init(
void) {
1093 ps.firstflat = NULL;
1100 ps.mtwilight = NULL;
1106 static void omega_mflat_tidy(
void) {
1107 freefits(ps.firstflat);
1108 freeframeset(ps.flatlist);
1109 freeimage(ps.bpixels);
1110 freeimage(ps.mflat);
1111 freeimage(ps.mtwilight);
1112 freespace(ps.labels);
1113 freestats(ps.stats);