35 #include "muse_scipost_make_cube_z.h"
49 static const char *muse_scipost_make_cube_help =
50 "This recipe takes a pixel table and resamples it to either a FITS cube or a Euro3D table and optionally to a stacked spectrum. This is a part of the muse_scipost recipe.";
52 static const char *muse_scipost_make_cube_help_esorex =
53 "\n\nInput frames for raw frame tag \"PIXTABLE_OBJECT\":\n"
54 "\n Frame tag Type Req #Fr Description"
55 "\n -------------------- ---- --- --- ------------"
56 "\n PIXTABLE_OBJECT raw Y Input pixel table"
57 "\n FILTER_LIST calib . 1 File to be used to create field-of-view images."
58 "\n OUTPUT_WCS calib . 1 WCS to override output cube location / dimensions"
59 "\n\nProduct frames for raw frame tag \"PIXTABLE_OBJECT\":\n"
60 "\n Frame tag Level Description"
61 "\n -------------------- -------- ------------"
62 "\n DATACUBE_FINAL final Output datacube"
63 "\n IMAGE_FOV final Field-of-view images corresponding to the \"filter\" parameter."
64 "\n OBJECT_RESAMPLED final Stacked image (if --stacked=true)";
75 static cpl_recipeconfig *
76 muse_scipost_make_cube_new_recipeconfig(
void)
78 cpl_recipeconfig *recipeconfig = cpl_recipeconfig_new();
81 tag =
"PIXTABLE_OBJECT";
82 cpl_recipeconfig_set_tag(recipeconfig, tag, 1, -1);
83 cpl_recipeconfig_set_input(recipeconfig, tag,
"FILTER_LIST", -1, 1);
84 cpl_recipeconfig_set_input(recipeconfig, tag,
"OUTPUT_WCS", -1, 1);
85 cpl_recipeconfig_set_output(recipeconfig, tag,
"DATACUBE_FINAL");
86 cpl_recipeconfig_set_output(recipeconfig, tag,
"IMAGE_FOV");
87 cpl_recipeconfig_set_output(recipeconfig, tag,
"OBJECT_RESAMPLED");
103 static cpl_error_code
104 muse_scipost_make_cube_prepare_header(
const char *aFrametag, cpl_propertylist *aHeader)
106 cpl_ensure_code(aFrametag, CPL_ERROR_NULL_INPUT);
107 cpl_ensure_code(aHeader, CPL_ERROR_NULL_INPUT);
108 if (!strcmp(aFrametag,
"DATACUBE_FINAL")) {
109 }
else if (!strcmp(aFrametag,
"IMAGE_FOV")) {
110 }
else if (!strcmp(aFrametag,
"OBJECT_RESAMPLED")) {
112 cpl_msg_warning(__func__,
"Frame tag %s is not defined", aFrametag);
113 return CPL_ERROR_ILLEGAL_INPUT;
115 return CPL_ERROR_NONE;
128 static cpl_frame_level
129 muse_scipost_make_cube_get_frame_level(
const char *aFrametag)
132 return CPL_FRAME_LEVEL_NONE;
134 if (!strcmp(aFrametag,
"DATACUBE_FINAL")) {
135 return CPL_FRAME_LEVEL_FINAL;
137 if (!strcmp(aFrametag,
"IMAGE_FOV")) {
138 return CPL_FRAME_LEVEL_FINAL;
140 if (!strcmp(aFrametag,
"OBJECT_RESAMPLED")) {
141 return CPL_FRAME_LEVEL_FINAL;
143 return CPL_FRAME_LEVEL_NONE;
157 muse_scipost_make_cube_get_frame_mode(
const char *aFrametag)
162 if (!strcmp(aFrametag,
"DATACUBE_FINAL")) {
165 if (!strcmp(aFrametag,
"IMAGE_FOV")) {
168 if (!strcmp(aFrametag,
"OBJECT_RESAMPLED")) {
186 muse_scipost_make_cube_create(cpl_plugin *aPlugin)
190 if (cpl_plugin_get_type(aPlugin) == CPL_PLUGIN_TYPE_RECIPE) {
191 recipe = (cpl_recipe *)aPlugin;
199 muse_scipost_make_cube_new_recipeconfig(),
200 muse_scipost_make_cube_prepare_header,
201 muse_scipost_make_cube_get_frame_level,
202 muse_scipost_make_cube_get_frame_mode);
207 cpl_msg_set_time_on();
211 recipe->parameters = cpl_parameterlist_new();
216 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.lambdamin",
218 "Cut off the data below this wavelength after loading the pixel table(s).",
219 "muse.muse_scipost_make_cube",
221 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"lambdamin");
222 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"lambdamin");
224 cpl_parameterlist_append(recipe->parameters, p);
227 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.lambdamax",
229 "Cut off the data above this wavelength after loading the pixel table(s).",
230 "muse.muse_scipost_make_cube",
232 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"lambdamax");
233 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"lambdamax");
235 cpl_parameterlist_append(recipe->parameters, p);
238 p = cpl_parameter_new_enum(
"muse.muse_scipost_make_cube.resample",
240 "The resampling technique to use for the final output cube.",
241 "muse.muse_scipost_make_cube",
242 (
const char *)
"drizzle",
244 (
const char *)
"nearest",
245 (
const char *)
"linear",
246 (
const char *)
"quadratic",
247 (
const char *)
"renka",
248 (
const char *)
"drizzle",
249 (
const char *)
"lanczos");
250 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"resample");
251 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"resample");
253 cpl_parameterlist_append(recipe->parameters, p);
256 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.dx",
258 "Horizontal step size for resampling (in arcsec or pixel). The following defaults are taken when this value is set to 0.0: 0.2'' for WFM, 0.075'' for NFM, 1.0 if data is in pixel units.",
259 "muse.muse_scipost_make_cube",
261 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"dx");
262 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"dx");
264 cpl_parameterlist_append(recipe->parameters, p);
267 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.dy",
269 "Vertical step size for resampling (in arcsec or pixel). The following defaults are taken when this value is set to 0.0: 0.2'' for WFM, 0.075'' for NFM, 1.0 if data is in pixel units.",
270 "muse.muse_scipost_make_cube",
272 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"dy");
273 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"dy");
275 cpl_parameterlist_append(recipe->parameters, p);
278 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.dlambda",
280 "Wavelength step size (in Angstrom). Natural instrument sampling is used, if this is 0.0",
281 "muse.muse_scipost_make_cube",
283 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"dlambda");
284 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"dlambda");
286 cpl_parameterlist_append(recipe->parameters, p);
289 p = cpl_parameter_new_enum(
"muse.muse_scipost_make_cube.crtype",
291 "Type of statistics used for detection of cosmic rays during final resampling. \"iraf\" uses the variance information, \"mean\" uses standard (mean/stdev) statistics, \"median\" uses median and the median median of the absolute median deviation.",
292 "muse.muse_scipost_make_cube",
293 (
const char *)
"median",
295 (
const char *)
"iraf",
296 (
const char *)
"mean",
297 (
const char *)
"median");
298 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"crtype");
299 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"crtype");
301 cpl_parameterlist_append(recipe->parameters, p);
304 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.crsigma",
306 "Sigma rejection factor to use for cosmic ray rejection during final resampling. A zero or negative value switches cosmic ray rejection off.",
307 "muse.muse_scipost_make_cube",
309 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"crsigma");
310 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"crsigma");
312 cpl_parameterlist_append(recipe->parameters, p);
315 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.rc",
317 "Critical radius for the \"renka\" resampling method.",
318 "muse.muse_scipost_make_cube",
320 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"rc");
321 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"rc");
323 cpl_parameterlist_append(recipe->parameters, p);
326 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.pixfrac",
328 "Pixel down-scaling factor for the \"drizzle\" resampling method.",
329 "muse.muse_scipost_make_cube",
331 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"pixfrac");
332 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"pixfrac");
334 cpl_parameterlist_append(recipe->parameters, p);
337 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.ld",
339 "Number of adjacent pixels to take into account during resampling in all three directions (loop distance); this affects all resampling methods except \"nearest\".",
340 "muse.muse_scipost_make_cube",
342 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"ld");
343 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"ld");
345 cpl_parameterlist_append(recipe->parameters, p);
348 p = cpl_parameter_new_enum(
"muse.muse_scipost_make_cube.format",
350 "Type of output file format, \"Cube\" is a standard FITS cube with NAXIS=3 and multiple extensions (for data and variance). The extended \"x\" formats include the reconstructed image(s) in FITS image extensions within the same file.",
351 "muse.muse_scipost_make_cube",
352 (
const char *)
"Cube",
354 (
const char *)
"Cube",
355 (
const char *)
"Euro3D",
356 (
const char *)
"xCube",
357 (
const char *)
"xEuro3D");
358 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"format");
359 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"format");
361 cpl_parameterlist_append(recipe->parameters, p);
364 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.stacked",
366 "If true, write an additional output file in form of a 2D stacked image (x direction is pseudo-spatial, y direction is wavelength).",
367 "muse.muse_scipost_make_cube",
369 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"stacked");
370 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"stacked");
372 cpl_parameterlist_append(recipe->parameters, p);
375 p = cpl_parameter_new_value(
"muse.muse_scipost_make_cube.filter",
377 "The filter name(s) to be used for the output field-of-view image. Each name has to correspond to an EXTNAME in an extension of the FILTER_LIST file. If an unsupported filter name is given, creation of the respective image is omitted. If multiple filter names are given, they have to be comma separated.",
378 "muse.muse_scipost_make_cube",
379 (
const char *)
"white");
380 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CFG,
"filter");
381 cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI,
"filter");
383 cpl_parameterlist_append(recipe->parameters, p);
403 cpl_ensure_code(aParams, CPL_ERROR_NULL_INPUT);
404 cpl_ensure_code(aParameters, CPL_ERROR_NULL_INPUT);
407 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.lambdamin");
408 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
409 aParams->
lambdamin = cpl_parameter_get_double(p);
411 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.lambdamax");
412 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
413 aParams->
lambdamax = cpl_parameter_get_double(p);
415 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.resample");
416 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
417 aParams->
resample_s = cpl_parameter_get_string(p);
419 (!strcasecmp(aParams->
resample_s,
"nearest")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_RESAMPLE_NEAREST :
420 (!strcasecmp(aParams->
resample_s,
"linear")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_RESAMPLE_LINEAR :
421 (!strcasecmp(aParams->
resample_s,
"quadratic")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_RESAMPLE_QUADRATIC :
422 (!strcasecmp(aParams->
resample_s,
"renka")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_RESAMPLE_RENKA :
423 (!strcasecmp(aParams->
resample_s,
"drizzle")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_RESAMPLE_DRIZZLE :
424 (!strcasecmp(aParams->
resample_s,
"lanczos")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_RESAMPLE_LANCZOS :
425 MUSE_SCIPOST_MAKE_CUBE_PARAM_RESAMPLE_INVALID_VALUE;
426 cpl_ensure_code(aParams->
resample != MUSE_SCIPOST_MAKE_CUBE_PARAM_RESAMPLE_INVALID_VALUE,
427 CPL_ERROR_ILLEGAL_INPUT);
429 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.dx");
430 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
431 aParams->
dx = cpl_parameter_get_double(p);
433 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.dy");
434 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
435 aParams->
dy = cpl_parameter_get_double(p);
437 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.dlambda");
438 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
439 aParams->
dlambda = cpl_parameter_get_double(p);
441 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.crtype");
442 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
443 aParams->
crtype_s = cpl_parameter_get_string(p);
445 (!strcasecmp(aParams->
crtype_s,
"iraf")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_CRTYPE_IRAF :
446 (!strcasecmp(aParams->
crtype_s,
"mean")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_CRTYPE_MEAN :
447 (!strcasecmp(aParams->
crtype_s,
"median")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_CRTYPE_MEDIAN :
448 MUSE_SCIPOST_MAKE_CUBE_PARAM_CRTYPE_INVALID_VALUE;
449 cpl_ensure_code(aParams->
crtype != MUSE_SCIPOST_MAKE_CUBE_PARAM_CRTYPE_INVALID_VALUE,
450 CPL_ERROR_ILLEGAL_INPUT);
452 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.crsigma");
453 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
454 aParams->
crsigma = cpl_parameter_get_double(p);
456 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.rc");
457 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
458 aParams->
rc = cpl_parameter_get_double(p);
460 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.pixfrac");
461 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
462 aParams->
pixfrac = cpl_parameter_get_double(p);
464 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.ld");
465 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
466 aParams->
ld = cpl_parameter_get_int(p);
468 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.format");
469 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
470 aParams->
format_s = cpl_parameter_get_string(p);
472 (!strcasecmp(aParams->
format_s,
"Cube")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_FORMAT_CUBE :
473 (!strcasecmp(aParams->
format_s,
"Euro3D")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_FORMAT_EURO3D :
474 (!strcasecmp(aParams->
format_s,
"xCube")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_FORMAT_XCUBE :
475 (!strcasecmp(aParams->
format_s,
"xEuro3D")) ? MUSE_SCIPOST_MAKE_CUBE_PARAM_FORMAT_XEURO3D :
476 MUSE_SCIPOST_MAKE_CUBE_PARAM_FORMAT_INVALID_VALUE;
477 cpl_ensure_code(aParams->
format != MUSE_SCIPOST_MAKE_CUBE_PARAM_FORMAT_INVALID_VALUE,
478 CPL_ERROR_ILLEGAL_INPUT);
480 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.stacked");
481 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
482 aParams->
stacked = cpl_parameter_get_bool(p);
484 p = cpl_parameterlist_find(aParameters,
"muse.muse_scipost_make_cube.filter");
485 cpl_ensure_code(p, CPL_ERROR_DATA_NOT_FOUND);
486 aParams->
filter = cpl_parameter_get_string(p);
500 muse_scipost_make_cube_exec(cpl_plugin *aPlugin)
502 if (cpl_plugin_get_type(aPlugin) != CPL_PLUGIN_TYPE_RECIPE) {
505 cpl_recipe *recipe = (cpl_recipe *)aPlugin;
506 cpl_msg_set_threadid_on();
508 cpl_frameset *usedframes = cpl_frameset_new(),
509 *outframes = cpl_frameset_new();
511 muse_scipost_make_cube_params_fill(¶ms, recipe->parameters);
513 cpl_errorstate prestate = cpl_errorstate_get();
517 int rc = muse_scipost_make_cube_compute(proc, ¶ms);
518 cpl_frameset_join(usedframes, proc->
usedframes);
519 cpl_frameset_join(outframes, proc->
outframes);
522 if (!cpl_errorstate_is_equal(prestate)) {
526 cpl_msg_set_level(CPL_MSG_INFO);
537 cpl_frameset_join(recipe->frames, usedframes);
538 cpl_frameset_join(recipe->frames, outframes);
539 cpl_frameset_delete(usedframes);
540 cpl_frameset_delete(outframes);
553 muse_scipost_make_cube_destroy(cpl_plugin *aPlugin)
557 if (cpl_plugin_get_type(aPlugin) == CPL_PLUGIN_TYPE_RECIPE) {
558 recipe = (cpl_recipe *)aPlugin;
564 cpl_parameterlist_delete(recipe->parameters);
581 cpl_plugin_get_info(cpl_pluginlist *aList)
583 cpl_recipe *recipe = cpl_calloc(1,
sizeof *recipe);
584 cpl_plugin *plugin = &recipe->interface;
588 helptext = cpl_sprintf(
"%s%s", muse_scipost_make_cube_help,
589 muse_scipost_make_cube_help_esorex);
591 helptext = cpl_sprintf(
"%s", muse_scipost_make_cube_help);
595 cpl_plugin_init(plugin, CPL_PLUGIN_API, MUSE_BINARY_VERSION,
596 CPL_PLUGIN_TYPE_RECIPE,
597 "muse_scipost_make_cube",
598 "Make a MUSE cube from a MUSE pixel table.",
603 muse_scipost_make_cube_create,
604 muse_scipost_make_cube_exec,
605 muse_scipost_make_cube_destroy);
606 cpl_pluginlist_append(aList, plugin);
void muse_processing_delete(muse_processing *aProcessing)
Free the muse_processing structure.
double pixfrac
Pixel down-scaling factor for the "drizzle" resampling method.
const char * filter
The filter name(s) to be used for the output field-of-view image. Each name has to correspond to an E...
muse_cplframework_type muse_cplframework(void)
Return the CPL framework the recipe is run under.
const char * resample_s
The resampling technique to use for the final output cube. (as string)
double crsigma
Sigma rejection factor to use for cosmic ray rejection during final resampling. A zero or negative va...
int ld
Number of adjacent pixels to take into account during resampling in all three directions (loop distan...
cpl_frameset * usedframes
muse_processing * muse_processing_new(const char *aName, cpl_recipe *aRecipe)
Create a new processing structure.
const char * muse_get_license(void)
Get the pipeline copyright and license.
int format
Type of output file format, "Cube" is a standard FITS cube with NAXIS=3 and multiple extensions (for ...
double lambdamax
Cut off the data above this wavelength after loading the pixel table(s).
int stacked
If true, write an additional output file in form of a 2D stacked image (x direction is pseudo-spatial...
int resample
The resampling technique to use for the final output cube.
void muse_cplerrorstate_dump_some(unsigned aCurrent, unsigned aFirst, unsigned aLast)
Dump some CPL errors.
void muse_processinginfo_delete(cpl_recipe *)
Clear all information from the processing info and from the recipe config.
double dx
Horizontal step size for resampling (in arcsec or pixel). The following defaults are taken when this ...
double rc
Critical radius for the "renka" resampling method.
cpl_error_code muse_cplframeset_erase_duplicate(cpl_frameset *aFrames)
Erase all duplicate frames from a frameset.
cpl_error_code muse_cplframeset_erase_all(cpl_frameset *aFrames)
Erase all frames in a frameset.
Structure to hold the parameters of the muse_scipost_make_cube recipe.
const char * crtype_s
Type of statistics used for detection of cosmic rays during final resampling. "iraf" uses the varianc...
double lambdamin
Cut off the data below this wavelength after loading the pixel table(s).
double dy
Vertical step size for resampling (in arcsec or pixel). The following defaults are taken when this va...
int crtype
Type of statistics used for detection of cosmic rays during final resampling. "iraf" uses the varianc...
void muse_processinginfo_register(cpl_recipe *, cpl_recipeconfig *, muse_processing_prepare_header_func *, muse_processing_get_frame_level_func *, muse_processing_get_frame_mode_func *)
Register extended functionalities for MUSE recipes.
double dlambda
Wavelength step size (in Angstrom). Natural instrument sampling is used, if this is 0...
const char * format_s
Type of output file format, "Cube" is a standard FITS cube with NAXIS=3 and multiple extensions (for ...