33#include "eris_utils.h"
34#include "eris_ifu_dfs.h"
35#include "eris_ifu_utils.h"
36#include "eris_ifu_error.h"
37#include "eris_ifu_resample.h"
38#include "eris_ifu_efficiency_response.h"
39#include "eris_ifu_jitter_interface.h"
51#define RECIPE_NAME "eris_ifu_combine_hdrl"
52#define ERIS_IFU_COMBINE_DOCATG "OBJECT_CUBE"
53#define ERIS_IFU_COMBINE_PROCATG "COMBINED_CUBE"
55#define MAX_NAME_SIZE 512
56#define CONTEXT "eris.eris_ifu_combine_hdrl"
57static const char eris_ifu_combine_description[] =
"\
58Align and combine SPIFFIER data cubes \n\
60-----------------------------------------------------------------------------\n\
62 DO CATG Explanation Required #Frames\n\
63 ------- ----------- -------- -------\n\
64 OBJECT_CUBE Science cubes Y >=2 \n\
65 EXTCOEFF_TABLE Table with atmospheric extinction (optional, req. to fluxcal [0,1]\n\
66 RESPONSE Table with instrument response (optional, req. to fluxcal) [0,1]\n\
69 PRO CATG Explanation\n\
70 ------- -----------\n\
71 "ERIS_IFU_COMBINE_PROCATG
" Combined scince cube using hdrl library functions. \n\
73Information on relevant parameters may be found with\n\
74 esorex --params "RECIPE_NAME
"\n\
75 esorex --help "RECIPE_NAME
"\n\
76---------------------------------------------------------------------------\n\
78cpl_recipe_define(eris_ifu_combine_hdrl, ERIS_BINARY_VERSION,
"Y. Cao",
79 PACKAGE_BUGREPORT,
"2023",
80 "Combine science cubes using hdrl",
81 eris_ifu_combine_description);
94static cpl_error_code eris_ifu_combine_hdrl_fill_parameterlist(cpl_parameterlist *pl)
99 cpl_ensure_code(pl, CPL_ERROR_NULL_INPUT);
104 p = cpl_parameter_new_value(CONTEXT
".offset_mode",
105 CPL_TYPE_BOOL,
"Offset conventions. If TRUE applies "
106 "reference offset correction. If FALSE: "
107 "take user offsets. The reference offset "
108 "is computed as (min_off+max_off)/2",
110 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"offset_mode") ;
111 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
112 cpl_parameterlist_append(pl, p) ;
114 p = cpl_parameter_new_value(CONTEXT
".name_i",
116 "Input filename. This must be provided and allow the user to set X "
117 "and Y cumulative offsets in a two column format",
118 CONTEXT,
"offset.list");
119 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"name_i") ;
120 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
121 cpl_parameterlist_append(pl, p) ;
123 p = cpl_parameter_new_enum(CONTEXT
".offset_unit", CPL_TYPE_STRING,
124 "Offset unit", CONTEXT,
"PIXEL",4,
125 "PIXEL",
"ARCSEC",
"DEGREE",
"PIXDEG");
126 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"offset_unit");
127 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
128 cpl_parameterlist_append(pl, p);
133 char *context = NULL;
134 context = cpl_sprintf(
"eris.%s", RECIPE_NAME);
136 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"method");
137 p = cpl_parameter_new_enum(pName, CPL_TYPE_STRING,
138 "Resampling method", context,
"DRIZZLE",6,
139 "NEAREST",
"LINEAR",
"QUADRATIC",
"RENKA",
140 "DRIZZLE",
"LANCZOS");
141 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"method");
142 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
143 cpl_parameterlist_append(pl, p);
146 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"method.loop-distance");
147 p = cpl_parameter_new_value(pName, CPL_TYPE_INT,
148 "Loop distance used by all (but NEAREST) "
149 "methods to control the number of surrounding "
150 "voxels that are taken into account. "
151 "A small value allow faster re-sampling but may not give good quality",
152 context, LOOP_DISTANCE);
153 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"method.loop-distance");
154 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
155 cpl_parameterlist_append(pl, p);
158 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"method.use-errorweights");
159 p = cpl_parameter_new_value(pName,
161 "Use additional weights of 1/err^2", context,
163 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
164 "method.use-errorweights");
165 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
166 cpl_parameterlist_append(pl, p);
169 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"method.renka.critical-radius");
170 p = cpl_parameter_new_value(pName,
171 CPL_TYPE_DOUBLE,
"Critical radius of the Renka "
173 context, RENKA_CRITICAL_RADIUS);
174 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
175 "method.renka.critical-radius");
176 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
177 cpl_parameterlist_append(pl, p);
180 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"method.lanczos.kernel-size");
181 p = cpl_parameter_new_value(pName,
182 CPL_TYPE_INT,
"Kernel size of the Lanczos "
184 context, LANCZOS_KERNEL_SIZE);
185 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
186 "method.lanczos.kernel-size");
187 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
188 cpl_parameterlist_append(pl, p);
191 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"method.drizzle.downscale-x");
192 p = cpl_parameter_new_value(pName,
193 CPL_TYPE_DOUBLE,
"Drizzle down-scaling factor "
195 context, DRIZZLE_DOWN_SCALING_FACTOR_X);
196 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
197 "method.drizzle.downscale-x");
198 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
199 cpl_parameterlist_append(pl, p);
202 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"method.drizzle.downscale-y");
203 p = cpl_parameter_new_value(pName,
204 CPL_TYPE_DOUBLE,
"Drizzle down-scaling factor "
206 context, DRIZZLE_DOWN_SCALING_FACTOR_Y);
207 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
208 "method.drizzle.downscale-y");
209 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
210 cpl_parameterlist_append(pl, p);
213 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"method.drizzle.downscale-z");
214 p = cpl_parameter_new_value(pName,
215 CPL_TYPE_DOUBLE,
"Drizzle down-scaling factor "
216 "in wavelength direction",
217 context, DRIZZLE_DOWN_SCALING_FACTOR_Z);
218 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
219 "method.drizzle.downscale-z");
220 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
221 cpl_parameterlist_append(pl, p);
326 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"subtract-background");
327 p = cpl_parameter_new_value(pName, CPL_TYPE_BOOL,
328 "Subtract median of the images chanel-by-chanel", context,
330 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"subtract-background");
331 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
332 cpl_parameterlist_append(pl, p);
335 int jitterMode= M_SCIENCE;
340 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"flux-calibrate");
341 p = cpl_parameter_new_value(pName, CPL_TYPE_BOOL,
342 "If True flux calibrate the extracted spectrum and data cube (you need to also --extract-source=TRUE)",
344 if (jitterMode == M_SCIENCE) {
345 cpl_parameter_set_default_bool(p, CPL_FALSE);
347 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"flux-calibrate");
348 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
349 cpl_parameterlist_append(pl, p);
355 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"fieldmargin");
356 p = cpl_parameter_new_value(pName, CPL_TYPE_DOUBLE,
357 "Add this margin/border (in percent) to the "
358 "resampled image/cube", context, FIELDMARGIN);
359 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"fieldmargin");
360 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
361 cpl_parameterlist_append(pl, p);
364 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"edge-trim");
365 p = cpl_parameter_new_value(pName, CPL_TYPE_INT,
366 "Number or pixels to trim for each plane of the input frames. "
367 "It should be smaller than half image size", context, EDGETRIM);
368 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"edge-trim");
369 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
370 cpl_parameterlist_append(pl, p);
372 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"max-cubes-centres-dist");
373 p = cpl_parameter_new_range(pName, CPL_TYPE_INT,
374 "Maximum distance between cube centers to build a mosaic. Mosaic creation "
375 "requires a lot of RAM. Users may trim this value to fit RAM resources",
376 context, 240, 20, 10000);
377 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"max-cubes-centres-dist");
378 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
379 cpl_parameterlist_append(pl, p);
383 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"bpc_iter");
384 p = cpl_parameter_new_value(pName, CPL_TYPE_INT,
385 "No. of iterations for bad pixel correction",
387 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"bpc_iter");
388 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
389 cpl_parameterlist_append(pl, p);
394 snprintf(pName,
sizeof(pName),
"%s.%s", context,
"chop-nan");
395 p = cpl_parameter_new_value(pName, CPL_TYPE_BOOL,
396 "If true chop cube planes with more than 50% NAN pixels",
398 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"chop-nan");
399 cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV);
400 cpl_parameterlist_append(pl, p);
407 return cpl_error_get_code();
419static int eris_ifu_combine_hdrl(
420 cpl_frameset * frameset,
421 const cpl_parameterlist * parlist)
423 const cpl_parameter * par ;
425 struct stdParamStruct stdParams = stdParamStructInit;
427 const char* name_i = NULL;
428 int offset_mode = CPL_TRUE;
429 const char* offunit = NULL;
430 FILE* file_list = NULL;
438 float * offsetx = NULL;
439 float * offsety = NULL;
440 float * crpix1_usr = NULL;
441 float * crpix2_usr = NULL;
442 float * crval1_usr = NULL;
443 float * crval2_usr = NULL;
451 cpl_ensure_code(frameset, CPL_ERROR_NULL_INPUT);
452 cpl_ensure_code(parlist, CPL_ERROR_NULL_INPUT);
453 cpl_error_ensure(cpl_frameset_get_size(frameset) >= 0, CPL_ERROR_ILLEGAL_INPUT,
454 0,
"Missing or empty SOF file");
459 if (parlist == NULL || frameset == NULL) {
460 cpl_msg_error(__func__,
"Null Inputs") ;
461 cpl_error_set(__func__, CPL_ERROR_NULL_INPUT) ;
462 return (
int) cpl_error_get_code() ;
466 const char* required_tags[1] = {
467 ERIS_IFU_COMBINE_DOCATG
470 cpl_ensure_code(CPL_ERROR_NONE ==
471 eris_dfs_check_input_tags(frameset, required_tags, ntags, 1),
472 CPL_ERROR_ILLEGAL_INPUT);
473 const int ntags_opt = 1;
474 const char* optional_tags[2] = {
475 ERIS_IFU_CALIB_EXTCOEFF_TABLE,
476 ERIS_IFU_PRO_JITTER_RESPONSE
478 eris_dfs_check_input_tags(frameset, optional_tags, ntags_opt, 0);
485 par = cpl_parameterlist_find_const(parlist,
486 CONTEXT
".offset_mode");
487 offset_mode = cpl_parameter_get_bool(par);
489 par = cpl_parameterlist_find_const(parlist,
491 name_i = cpl_parameter_get_string(par);
493 par = cpl_parameterlist_find_const(parlist,
494 CONTEXT
".offset_unit");
495 offunit = cpl_parameter_get_string(par);
500 cpl_msg_error(__func__,
"Cannot identify RAW and CALIB frames") ;
501 return (
int) cpl_error_set(__func__, CPL_ERROR_ILLEGAL_INPUT) ;
505 cpl_ensure_code(CPL_ERROR_NONE ==
506 eris_dfs_check_input_tags(frameset, required_tags, ntags, 1),
507 CPL_ERROR_ILLEGAL_INPUT);
510 cpl_frameset* cube_set;
513 cpl_msg_info(__func__,
"Use user offsets to combine.") ;
515 if ( NULL == (file_list = fopen (name_i,
"r" )) ){
516 cpl_msg_error(__func__,
"cannot open %s\n", name_i) ;
517 return (
int) cpl_error_set(__func__, CPL_ERROR_ILLEGAL_INPUT) ;
521 if (strcmp(offunit,
"PIXDEG") == 0){
522 while (fscanf( file_list,
"%lf %lf %lf %lf",&crpix1,&crpix2, &alpha, &delta ) != EOF ) {
527 while ( fscanf( file_list,
"%f %f",&tmpoffx, &tmpoffy) != EOF ){
533 if (cnt != cpl_frameset_get_size(cube_set)) {
534 cpl_msg_error(__func__,
"Input offlist is not consistent with frameset or offunit") ;
535 if (strcmp(offunit,
"PIXDEG") == 0){
536 cpl_msg_error(__func__,
"If offunit is PIXDEG input ASCII file must have four columns");
538 cpl_msg_error(__func__,
"If offunit is not PIXDEG input ASCII file must have two columns");
540 return (
int) cpl_error_set(__func__, CPL_ERROR_INCOMPATIBLE_INPUT) ;
544 cpl_msg_info(__func__,
"Use wcs in each input cube to combine.") ;
550 cpl_msg_info(__func__,
"Reading offset list.") ;
553 offsetx = (
float*) cpl_calloc(nframes,
sizeof(
float));
554 offsety = (
float*) cpl_calloc(nframes,
sizeof(
float));
556 crpix1_usr = (
float*) cpl_calloc(nframes,
sizeof(
float));
557 crpix2_usr = (
float*) cpl_calloc(nframes,
sizeof(
float));
558 crval1_usr = (
float*) cpl_calloc(nframes,
sizeof(
float));
559 crval2_usr = (
float*) cpl_calloc(nframes,
sizeof(
float));
560 if (offsetx == NULL || offsety == NULL){
561 cpl_msg_error(__func__,
"Could not allocate memory!") ;
564 return (
int) cpl_error_set(__func__, CPL_ERROR_UNSPECIFIED);
568 file_list = fopen (name_i,
"r" );
572 if (strcmp(offunit,
"PIXDEG") == 0){
573 while (fscanf( file_list,
"%lf %lf %lf %lf",&crpix1,&crpix2, &alpha, &delta ) != EOF ) {
575 crpix1_usr[cnt] = crpix1;
576 crpix2_usr[cnt] = crpix2;
577 crval1_usr[cnt] = alpha;
578 crval2_usr[cnt] = delta;
584 while (fscanf( file_list,
"%f %f",&tmpoffx,&tmpoffy ) != EOF ) {
586 offsetx[cnt] = tmpoffx;
587 offsety[cnt] = tmpoffy;
598 double as2deg = 1.0/3600.0;
603 cpl_size ncubes = cpl_frameset_get_size(cube_set);
604 cpl_frame* cube_frm = NULL;
605 cpl_propertylist* plist = NULL;
606 cpl_propertylist* hdata = NULL;
607 const char* fname = NULL;
610 cpl_vector* factor_vec = cpl_vector_new(ncubes);
611 double* pfactor = cpl_vector_get_data(factor_vec);
612 for(
int i = 0; i < ncubes; i++) {
614 cube_frm = cpl_frameset_get_position(cube_set, i);
615 cpl_frame_set_group(cube_frm, CPL_FRAME_GROUP_RAW);
616 fname = cpl_frame_get_filename(cube_frm);
617 hdata = cpl_propertylist_load(fname, 0);
618 dit = cpl_propertylist_get_double(hdata, FHDR_E_DIT);
619 cpl_msg_info(cpl_func,
"time[%d]=%g",i,dit);
624 pfactor[i] = dit_ref / dit ;
626 cpl_propertylist_delete(hdata);
628 if(cpl_error_get_code() != CPL_ERROR_NONE) {
629 cpl_msg_error(cpl_func,
"errors to get exposure time from data. Check your data. Exit.");
630 cpl_vector_delete(factor_vec);
631 cpl_frameset_delete(cube_set);
632 return (
int) cpl_error_get_code();
634 const char* fname_spec_cube =
"cube";
635 if (offunit != NULL && offsetx !=NULL && offsety !=NULL){
636 if (strcmp(offunit,
"PIXEL") == 0){
638 cpl_msg_info(cpl_func,
"User-defined offset unit in PIXEL");
639 }
else if (strcmp(offunit,
"DEGREE") == 0){
641 cpl_msg_info(cpl_func,
"User-defined offset unit is DEGREE");
642 }
else if (strcmp(offunit,
"ARCSEC") == 0){
644 cpl_msg_info(cpl_func,
"User-defined offset unit is ARCSEC");
647 }
else if (strcmp(offunit,
"PIXDEG") == 0){
649 cpl_msg_info(cpl_func,
"User-defined offset unit is PIXDEG");
651 cpl_msg_error(cpl_func,
"User-defined offset unit or offset list is not correct.");
657 char* new_name = NULL;
658 cpl_imagelist* data = NULL;
659 cpl_imagelist* errs = NULL;
660 cpl_imagelist* qual = NULL;
662 cpl_propertylist* herrs = NULL;
663 cpl_propertylist* hqual = NULL;
664 for(
int i = 0; i < ncubes; i++) {
665 cube_frm = cpl_frameset_get_position(cube_set, i);
666 fname = cpl_frame_get_filename(cube_frm);
667 hdata = cpl_propertylist_load(fname, 1);
670 crpix1 = cpl_propertylist_get_double(hdata,
"CRPIX1");
671 crpix2 = cpl_propertylist_get_double(hdata,
"CRPIX2");
672 cpl_propertylist_set_double(hdata,
"CRPIX1", crpix1 + offsetx[i]);
673 cpl_propertylist_set_double(hdata,
"CRPIX2", crpix2 + offsety[i]);
674 }
else if (offcode == 1) {
675 crval1 = cpl_propertylist_get_double(hdata,
"CRVAL1");
676 crval2 = cpl_propertylist_get_double(hdata,
"CRVAL2");
677 cpl_propertylist_set_double(hdata,
"CRVAL1", crval1 + offsetx[i]);
678 cpl_propertylist_set_double(hdata,
"CRVAL2", crval2 + offsety[i]);
680 }
else if (offcode == 2) {
681 crval1 = cpl_propertylist_get_double(hdata,
"CRVAL1");
682 crval2 = cpl_propertylist_get_double(hdata,
"CRVAL2");
683 cpl_propertylist_set_double(hdata,
"CRVAL1", crval1 + offsetx[i] * scalex);
684 cpl_propertylist_set_double(hdata,
"CRVAL2", crval2 + offsety[i] * scaley);
686 }
else if (offcode == 3) {
688 cpl_propertylist_set_double(hdata,
"CRPIX1", crpix1_usr[i]);
689 cpl_propertylist_set_double(hdata,
"CRPIX2", crpix2_usr[i]);
691 cpl_propertylist_set_double(hdata,
"CRVAL1", crval1_usr[i]);
692 cpl_propertylist_set_double(hdata,
"CRVAL2", crval2_usr[i]);
696 plist = cpl_propertylist_load(fname, 0);
697 herrs = cpl_propertylist_load(fname, 2);
698 hqual = cpl_propertylist_load(fname, 3);
699 data = cpl_imagelist_load(fname, CPL_TYPE_DOUBLE, 1);
700 errs = cpl_imagelist_load(fname, CPL_TYPE_DOUBLE, 2);
701 qual = cpl_imagelist_load(fname, CPL_TYPE_INT, 3);
703 cpl_msg_info(cpl_func,
"correct[%d] by=%g",i,pfactor[i]);
704 cpl_imagelist_multiply_scalar(data,pfactor[i]);
705 cpl_imagelist_multiply_scalar(errs,sqrt(pfactor[i]));
706 new_name = cpl_sprintf(
"cube_%2.2d.fits",i);
707 cpl_frame_set_filename(cube_frm, new_name);
708 cpl_propertylist_save(plist, new_name, CPL_IO_CREATE);
709 cpl_imagelist_save(data, new_name, CPL_TYPE_DOUBLE, hdata, CPL_IO_EXTEND);
710 cpl_imagelist_save(errs, new_name, CPL_TYPE_DOUBLE, herrs, CPL_IO_EXTEND);
711 cpl_imagelist_save(qual, new_name, CPL_TYPE_INT, hqual, CPL_IO_EXTEND);
712 cpl_propertylist_delete(plist);
713 cpl_propertylist_delete(hdata);
714 cpl_propertylist_delete(herrs);
715 cpl_propertylist_delete(hqual);
716 cpl_imagelist_delete(data);
717 cpl_imagelist_delete(errs);
718 cpl_imagelist_delete(qual);
726 ERIS_IFU_COMBINE_DOCATG, fname_spec_cube,
728 RECIPE_NAME, RECIPE_NAME) != CPL_ERROR_NONE){
729 cpl_msg_error(__func__,
"Cannot resampling the cubes for combination.");
735 char* new_name = NULL;
736 cpl_imagelist* data = NULL;
737 cpl_imagelist* errs = NULL;
738 cpl_imagelist* qual = NULL;
740 cpl_propertylist* herrs = NULL;
741 cpl_propertylist* hqual = NULL;
743 for(
int i = 0; i < ncubes; i++) {
744 cube_frm = cpl_frameset_get_position(cube_set, i);
745 fname = cpl_frame_get_filename(cube_frm);
746 hdata = cpl_propertylist_load(fname, 1);
750 plist = cpl_propertylist_load(fname, 0);
751 herrs = cpl_propertylist_load(fname, 2);
752 hqual = cpl_propertylist_load(fname, 3);
753 data = cpl_imagelist_load(fname, CPL_TYPE_DOUBLE, 1);
754 errs = cpl_imagelist_load(fname, CPL_TYPE_DOUBLE, 2);
755 qual = cpl_imagelist_load(fname, CPL_TYPE_INT, 3);
757 cpl_msg_info(cpl_func,
"correct[%d] by=%g",i,pfactor[i]);
758 cpl_imagelist_multiply_scalar(data,pfactor[i]);
759 cpl_imagelist_multiply_scalar(errs,sqrt(pfactor[i]));
760 new_name = cpl_sprintf(
"cube_%2.2d.fits",i);
761 cpl_frame_set_filename(cube_frm, new_name);
762 cpl_propertylist_save(plist, new_name, CPL_IO_CREATE);
763 cpl_imagelist_save(data, new_name, CPL_TYPE_DOUBLE, hdata, CPL_IO_EXTEND);
764 cpl_imagelist_save(errs, new_name, CPL_TYPE_DOUBLE, herrs, CPL_IO_EXTEND);
765 cpl_imagelist_save(qual, new_name, CPL_TYPE_INT, hqual, CPL_IO_EXTEND);
766 cpl_propertylist_delete(plist);
767 cpl_propertylist_delete(hdata);
768 cpl_propertylist_delete(herrs);
769 cpl_propertylist_delete(hqual);
770 cpl_imagelist_delete(data);
771 cpl_imagelist_delete(errs);
772 cpl_imagelist_delete(qual);
780 ERIS_IFU_COMBINE_DOCATG, fname_spec_cube,
782 RECIPE_NAME, RECIPE_NAME) != CPL_ERROR_NONE){
783 cpl_msg_error(__func__,
"Cannot resampling the cubes for combination.");
787 cpl_vector_delete(factor_vec);
794 if (crpix1_usr != NULL)
795 cpl_free(crpix1_usr);
796 if (crpix2_usr != NULL)
797 cpl_free(crpix2_usr);
799 if (crval1_usr != NULL)
800 cpl_free(crval1_usr);
801 if (crval2_usr != NULL)
802 cpl_free(crval2_usr);
806 cubeType obj_type = OBJECT_CUBE;
807 cubeType resampled_obj_type = OBJECT_CUBE_COADD;
809 cpl_frame* frame = NULL;
810 if( NULL != (frame = cpl_frameset_find(frameset, ERIS_IFU_PRO_JITTER_RESPONSE ))) {
811 cpl_frameset_insert(cube_set, cpl_frame_duplicate(frame));
817 if( NULL != (frame = cpl_frameset_find(frameset, ERIS_IFU_CALIB_EXTCOEFF_TABLE ))) {
818 cpl_frameset_insert(cube_set, cpl_frame_duplicate(frame));
823 if (cpl_frameset_count_tags(cube_set, ERIS_IFU_PRO_JITTER_DAR_CUBE)
826 resampled_obj_type = DAR_CUBE_COADD;
827 proCatg = ERIS_IFU_PRO_JITTER_DAR_CUBE;
828 }
else if (cpl_frameset_count_tags(cube_set, ERIS_IFU_PRO_JITTER_TWK_CUBE)
830 obj_type = TWEAKED_CUBE;
831 resampled_obj_type = TWEAKED_CUBE_COADD;
832 proCatg = ERIS_IFU_PRO_JITTER_TWK_CUBE;
834 obj_type = OBJECT_CUBE;
835 resampled_obj_type = OBJECT_CUBE_COADD;
836 proCatg = ERIS_IFU_PRO_JITTER_OBJ_CUBE;
840 char *combDoCatg = NULL;
841 char *filenameSpec = NULL;
846 char* param_name = cpl_sprintf(
"%s.flux-calibrate", CONTEXT);
847 cpl_boolean flux_calibrate = cpl_parameter_get_bool(
848 cpl_parameterlist_find_const(parlist, param_name));
849 cpl_free(param_name);
851 param_name = cpl_sprintf(
"%s.extract-source", CONTEXT);
852 cpl_boolean extract_source = cpl_parameter_get_bool(
853 cpl_parameterlist_find_const(parlist, param_name));
854 cpl_free(param_name);
858 if (extract_source && eris_can_extract(cube_set)) {
859 cpl_msg_info(cpl_func,
"extracting");
861 proCatg, stdParams, RECIPE_NAME, CONTEXT);
864 if(flux_calibrate && eris_can_flux_calibrate(cube_set)) {
867 cpl_msg_info(cpl_func,
"Flux calibrate extracted spectrum");
868 eris_flux_calibrate_spectra(RECIPE_NAME, RECIPE_NAME, parlist,
872 char* cube_pro_catg = NULL;
873 if(obj_type == DAR_CUBE) {
874 cube_pro_catg = cpl_sprintf(
"%s",ERIS_IFU_PRO_JITTER_OBJ_DAR_CUBE_COADD);
875 }
else if(obj_type == TWEAKED_CUBE) {
876 cube_pro_catg = cpl_sprintf(
"%s",ERIS_IFU_PRO_JITTER_TWK_CUBE_COADD);
878 cube_pro_catg = cpl_sprintf(
"%s",ERIS_IFU_PRO_JITTER_OBJ_CUBE_COADD);
881 cpl_msg_info(cpl_func,
"proCatg: %s",cube_pro_catg);
883 cpl_msg_info(cpl_func,
"Flux calibrate combined data cube");
888 eris_flux_calibrate_cube2(cube_pro_catg, RECIPE_NAME, RECIPE_NAME, parlist,
891 cpl_free(cube_pro_catg);
894 cpl_frameset_erase(cube_set,ERIS_IFU_COMBINE_DOCATG);
895 cpl_frameset_join(frameset,cube_set);
897 char* cmd = cpl_sprintf(
"rm cube*.fits");
898 int status = system(cmd);
901 cpl_frameset_delete(cube_set);
905 return (
int) cpl_error_get_code();
cpl_error_code eris_dfs_set_groups(cpl_frameset *self)
Set the group as RAW or CALIB in a frameset.
cpl_frameset * eris_ifu_extract_frameset(const cpl_frameset *in, const char *tag)
Extract frames with a specific tag from a frameset.
cpl_error_code eris_parlist_config_add_all_recipes(cpl_parameterlist *pl, const char *recname)
Add common configuration parameters for all recipes.
cpl_error_code eris_ifu_jitter_fill_extract_parameterlist(char *context, jitterModes jitterMode, cpl_parameterlist *pl)
Fill parameter list with source extraction parameters.
cpl_error_code eris_ifu_jitter_extract(cpl_frameset *frameset, const cpl_parameterlist *parlist, cubeType obj_type, const char *pcatg, struct stdParamStruct stdParams, const char *pipefile_prefix, const char *context)
Main spectral extraction function.
cpl_error_code eris_ifu_jitter_get_procatg_and_filename(cubeType type, char **proCatg, char **filenamePrefix)
Get the value of the PRO.CATG and the filename as function of the type of cube.
cpl_error_code eris_ifu_combine_pbp(cpl_frameset *frameset, const cpl_parameterlist *parlist, const char *input_cube_pro_catg, const char *filenameSpec, float *offsetx, float *offsety, const char *offunit, const char *recipe_name, const char *pipefile_prefix)
Resample and combine cubes plane-by-plane (2D spatial resampling per wavelength)
void eris_ifu_free_string(char **item)
Free memory and set pointer to null.