38 #include "irplib_mkmaster.h"
70 irplib_imagelist_get_clean_mean_levels(
const cpl_imagelist* iml,
73 const double tolerance)
76 const cpl_image* img=NULL;
79 cpl_vector* levels=NULL;
85 cpl_error_ensure(iml != NULL, CPL_ERROR_NULL_INPUT,
return(levels),
86 "Null input image list");
87 cpl_error_ensure(kappa >= 0, CPL_ERROR_ILLEGAL_INPUT,
return(levels),
90 size=cpl_imagelist_get_size(iml);
91 levels=cpl_vector_new(size);
92 pval=cpl_vector_get_data(levels);
95 img=cpl_imagelist_get_const(iml,i);
96 irplib_ksigma_clip(img,1,1,
97 cpl_image_get_size_x(img),
98 cpl_image_get_size_y(img),
99 nclip,kappa,tolerance,&mean,&stdev);
100 cpl_msg_info(cpl_func,
"Ima %d mean level: %g",i+1,mean);
117 static cpl_error_code
118 irplib_imagelist_subtract_values(cpl_imagelist** iml, cpl_vector* values)
126 size=cpl_imagelist_get_size(*iml);
127 pval=cpl_vector_get_data(values);
129 for(i=0;i<size;i++) {
130 img=cpl_imagelist_get(*iml,i);
131 cpl_image_subtract_scalar(img,pval[i]);
132 cpl_imagelist_set(*iml,img,i);
135 return cpl_error_get_code();
153 irplib_vector_ksigma(cpl_vector *values,
154 const double klow,
const double khigh,
int kiter)
156 cpl_vector *accepted;
159 double *data = cpl_vector_get_data(values);
160 int n = cpl_vector_get_size(values);
170 mean = cpl_vector_get_median(values);
172 for (i = 0; i < n; i++) {
173 sigma += (mean - data[i]) * (mean - data[i]);
175 sigma = sqrt(sigma / (n - 1));
179 for (i = 0; i < ngood; i++) {
180 if (data[i]-mean < khigh*sigma && mean-data[i] < klow*sigma) {
181 data[count] = data[i];
195 accepted = cpl_vector_wrap(count, data);
196 mean = cpl_vector_get_mean(accepted);
198 sigma = cpl_vector_get_stdev(accepted);
200 cpl_vector_unwrap(accepted);
202 if (count == ngood) {
232 irplib_imagelist_ksigma_stack(
const cpl_imagelist *imlist,
233 double klow,
double khigh,
int kiter)
235 int ni, nx, ny, npix;
236 cpl_image *out_ima=NULL;
237 cpl_imagelist *loc_iml=NULL;
238 double *pout_ima=NULL;
239 cpl_image *image=NULL;
240 const double **data=NULL;
242 cpl_vector *time_line=NULL;
244 double *ptime_line=NULL;
246 double mean_of_medians=0;
248 cpl_error_ensure(imlist != NULL, CPL_ERROR_NULL_INPUT,
return(out_ima),
249 "Null input image list");
251 ni = cpl_imagelist_get_size(imlist);
252 loc_iml = cpl_imagelist_duplicate(imlist);
253 image = cpl_imagelist_get(loc_iml, 0);
254 nx = cpl_image_get_size_x(image);
255 ny = cpl_image_get_size_y(image);
258 out_ima = cpl_image_new(nx, ny, CPL_TYPE_DOUBLE);
259 pout_ima = cpl_image_get_data_double(out_ima);
261 time_line = cpl_vector_new(ni);
263 ptime_line = cpl_vector_get_data(time_line);
265 data = cpl_calloc(
sizeof(
double *), ni);
266 med = cpl_calloc(
sizeof(
double), ni);
268 for (i = 0; i < ni; i++) {
269 image = cpl_imagelist_get(loc_iml, i);
270 med[i]=cpl_image_get_median(image);
271 cpl_image_subtract_scalar(image,med[i]);
272 data[i] = cpl_image_get_data_double(image);
273 mean_of_medians+=med[i];
277 for (i = 0; i < npix; i++) {
278 for (j = 0; j < ni; j++) {
279 ptime_line[j] = data[j][i];
281 pout_ima[i] = irplib_vector_ksigma(time_line, klow, khigh, kiter);
284 cpl_image_add_scalar(out_ima,mean_of_medians);
289 cpl_vector_delete(time_line);
290 cpl_imagelist_delete(loc_iml);
313 irplib_mkmaster_mean(cpl_imagelist* images,
const double kappa,
const int nclip,
const double tolerance,
const double klow,
const double khigh,
const int niter)
316 cpl_image* master=NULL;
317 cpl_vector* levels=NULL;
319 cpl_imagelist* iml=NULL;
321 cpl_msg_info(cpl_func,
"method mean");
322 iml=cpl_imagelist_duplicate(images);
323 levels=irplib_imagelist_get_clean_mean_levels(iml,kappa,nclip,tolerance);
324 mean=cpl_vector_get_mean(levels);
325 cpl_msg_info(cpl_func,
"Master mean level: %g",mean);
327 irplib_imagelist_subtract_values(&iml,levels);
329 master = irplib_imagelist_ksigma_stack(iml,klow,khigh,niter);
330 cpl_image_add_scalar(master,mean);
332 cpl_vector_delete(levels);
333 cpl_imagelist_delete(iml);
355 cpl_image* master=NULL;
356 cpl_vector* levels=NULL;
358 cpl_imagelist* iml=NULL;
360 cpl_msg_info(cpl_func,
"method median");
361 iml=cpl_imagelist_duplicate(images);
362 levels=irplib_imagelist_get_clean_mean_levels(iml,kappa,nclip,tolerance);
364 mean=cpl_vector_get_mean(levels);
365 cpl_msg_info(cpl_func,
"Master mean level: %g",mean);
366 irplib_imagelist_subtract_values(&iml,levels);
368 master = cpl_imagelist_collapse_median_create(iml);
370 cpl_image_add_scalar(master,mean);
372 cpl_vector_delete(levels);
373 cpl_imagelist_delete(iml);
380 static cpl_error_code
381 irplib_mkmaster_dark_qc(
const cpl_imagelist* raw_images,
382 cpl_imagelist* preproc_images,
383 const cpl_parameterlist* parameters,
384 const int pr_num_x,
const int pr_num_y,
385 const int pr_box_sx,
const int pr_box_sy,
const char* recipe_id,
388 cpl_ensure_code(qclog !=NULL, CPL_ERROR_NULL_INPUT);
389 cpl_ensure_code(recipe_id !=NULL, CPL_ERROR_NULL_INPUT);
390 cpl_ensure_code(parameters !=NULL, CPL_ERROR_NULL_INPUT);
393 cpl_image* current_dark = 0;
394 if (pr_num_x != 0 && pr_num_y != 0 && pr_box_sx != 0 && pr_box_sy != 0) {
395 for (i = 0; i < cpl_imagelist_get_size(raw_images); i++) {
396 current_dark = cpl_image_duplicate(
397 cpl_imagelist_get_const(preproc_images, i));
398 cpl_msg_info(cpl_func,
"Calculating QC parameters on raw dark frame %d",
405 cpl_image_delete(current_dark);
408 return cpl_error_get_code();
423 irplib_head_get_exptime(
const cpl_propertylist * plist) {
426 result=cpl_propertylist_get_double(plist,
"EXPTIME");
427 cpl_ensure_code(result >= 0, CPL_ERROR_ILLEGAL_OUTPUT);
441 static cpl_error_code
442 irplib_head_set_exptime(cpl_propertylist *plist,
double exptime)
444 cpl_propertylist_update_double(plist,
"EXPTIME", exptime);
445 cpl_propertylist_set_comment(plist,
"EXPTIME",
"Total integration time");
447 return cpl_error_get_code();
450 static cpl_imagelist*
451 irplib_mkmaster_dark_fill_imagelist(
const cpl_imagelist* raw_images,
452 cpl_propertylist** raw_headers,
const cpl_image* master_bias,
453 double* mean_exptime) {
457 cpl_imagelist* preproc_images = NULL;
459 cpl_image* current_dark = NULL;
460 double min_exptime = 0;
461 double max_exptime = 0;
463 preproc_images = cpl_imagelist_new();
464 for (i = 0; i < cpl_imagelist_get_size(raw_images); i++) {
465 double exposure_time = 0.0;
466 const cpl_propertylist *current_header;
468 current_dark = cpl_image_duplicate(cpl_imagelist_get_const(raw_images, i));
469 current_header = raw_headers[i];
472 if (master_bias != NULL) {
473 cpl_msg_info(cpl_func,
"Subtracting master bias");
474 cpl_image_subtract(current_dark, master_bias);
476 cpl_msg_info(cpl_func,
"Skipping bias subtraction");
479 exposure_time = irplib_head_get_exptime(current_header);
482 if (i == 0 || exposure_time < min_exptime) {
483 min_exptime = exposure_time;
485 if (i == 0 || exposure_time > max_exptime) {
486 max_exptime = exposure_time;
497 cpl_imagelist_set(preproc_images, current_dark, i);
506 cpl_msg_info(cpl_func,
507 "Exposure times range from %e s to %e s (%e %% variation)", min_exptime,
508 max_exptime, 100 * (max_exptime - min_exptime) / min_exptime);
510 if ((max_exptime - min_exptime) / min_exptime > .001) {
511 cpl_msg_warning(cpl_func,
"Exposure times differ by %e %%",
512 100 * (max_exptime - min_exptime) / min_exptime);
516 *mean_exptime=0.5 * (max_exptime + min_exptime);
517 return preproc_images;
522 irplib_mdark_process_chip(
const cpl_imagelist *raw_images,
523 cpl_propertylist **raw_headers,
const cpl_image *master_bias,
524 cpl_propertylist *mdark_header,
const cpl_parameterlist *parameters,
525 const char* recipe_id, cpl_table* qclog,
const int do_qc,
526 const char* STACK_METHOD,
const double STACK_KLOW,
const double STACK_KHIGH,
527 const int STACK_NITER,
528 const int pr_num_x,
const int pr_num_y,
529 const int pr_box_sx,
const int pr_box_sy) {
530 cpl_image *master_dark = NULL;
531 cpl_image *current_dark = NULL;
532 cpl_imagelist *preproc_images = NULL;
533 double mean_exptime = 0;
537 preproc_images = irplib_mkmaster_dark_fill_imagelist(raw_images, raw_headers,
538 master_bias, &mean_exptime);
541 irplib_mkmaster_dark_qc(raw_images, preproc_images, parameters, pr_num_x,
542 pr_num_y, pr_box_sx, pr_box_sy, recipe_id, qclog);
546 if (strcmp(STACK_METHOD,
"MEDIAN") == 0) {
547 cpl_msg_info(cpl_func,
"Calculating stack median");
548 master_dark = cpl_imagelist_collapse_median_create(preproc_images);
550 cpl_msg_info(cpl_func,
"Calculating stack mean");
551 master_dark = irplib_imagelist_ksigma_stack(preproc_images, STACK_KLOW,
552 STACK_KHIGH, STACK_NITER);
555 irplib_head_set_exptime(mdark_header, mean_exptime );
557 cpl_image_delete(current_dark);
558 cpl_imagelist_delete(preproc_images);
559 if (cpl_error_get_code() != CPL_ERROR_NONE) {
560 cpl_image_delete(master_dark);