MOONS Pipeline Reference Manual 0.13.2
moo_compute_linearity.c
1/*
2 * This file is part of the MOONS Pipeline
3 * Copyright (C) 2002-2016 European Southern Observatory
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19
20#ifdef HAVE_CONFIG_H
21#include <config.h>
22#endif
23
24/*-----------------------------------------------------------------------------
25 Includes
26 -----------------------------------------------------------------------------*/
27
28#include "moo_utils.h"
29#include "moo_pfits.h"
30#include "moo_detector.h"
31#include "moo_badpix.h"
32#include "moo_fibres_table.h"
33#include "moo_fits.h"
34#include "moo_pfits.h"
35#include "moo_cube.h"
36#include "moo_compute_linearity.h"
37#include <cpl.h>
38#include <hdrl.h>
39#include <math.h>
40#include <string.h>
41
42/*----------------------------------------------------------------------------*/
47/*----------------------------------------------------------------------------*/
50static void
51_moo_compute_trace_mask(cpl_mask *mask,
52 moo_loc *loc1,
54 int num)
55{
56 cpl_array *sel = NULL;
57 int nx = cpl_mask_get_size_x(mask);
58 int ny = cpl_mask_get_size_y(mask);
59
60 if (loc1 == NULL) {
61 for (int x = 1; x <= nx; x++) {
62 for (int y = 1; y <= ny; y++) {
63 cpl_mask_set(mask, x, y, CPL_BINARY_1);
64 }
65 }
66 }
67 else {
68 int spectro_name = moo_fibres_table_get_spectro(num);
69 moo_loc_single *locs1 = moo_loc_get_single(loc1, type, num);
70 cpl_table *ft1 = moo_loc_get_fibre_table(loc1);
71 moo_try_check(cpl_table_select_all(ft1), " ");
72 moo_try_check(cpl_table_and_selected_int(ft1, MOO_FIBRES_TABLE_SPECTRO,
73 CPL_EQUAL_TO, spectro_name),
74 " ");
75 moo_try_check(cpl_table_and_selected_int(ft1, MOO_FIBRES_TABLE_HEALTH,
76 CPL_EQUAL_TO, 1),
77 " ");
78 sel = cpl_table_where_selected(ft1);
79 cpl_size nsel = cpl_array_get_size(sel);
80 cpl_image *centroid_img = moo_loc_single_get_f_centroids(locs1);
81 cpl_image *wlo_img = moo_loc_single_get_f_wlo(locs1);
82 cpl_image *wup_img = moo_loc_single_get_f_wup(locs1);
83
84 for (int i = 0; i < nsel; i++) {
85 int rej;
86 cpl_size idx = cpl_array_get_cplsize(sel, i, NULL);
87 int indexext =
88 cpl_table_get_int(ft1, MOO_FIBRES_TABLE_INDEXEXT, idx, &rej);
89 for (int x = 1; x <= nx; x++) {
90 int rej2;
91 double centroid =
92 cpl_image_get(centroid_img, x, indexext, &rej2);
93 double wlo = cpl_image_get(wlo_img, x, indexext, &rej2);
94 double wup = cpl_image_get(wup_img, x, indexext, &rej2);
95 int yl = (int)floor(centroid - wlo);
96 if (yl < 1) {
97 yl = 1;
98 }
99 int yu = (int)ceil(centroid + wup);
100 if (yu >= ny) {
101 yu = ny;
102 }
103 for (int y = yl; y <= yu; y++) {
104 cpl_mask_set(mask, x, y, CPL_BINARY_1);
105 }
106 }
107 }
108 }
109moo_try_cleanup:
110 cpl_array_delete(sel);
111}
112/*-----------------------------------------------------------------------------
113 Function codes
114 -----------------------------------------------------------------------------*/
115cpl_imagelist *
116_moo_compute_linearity_single(moo_detlist *detlist,
117 moo_loc *loc,
119 int num,
120 cpl_image *saturate,
121 moo_cube *cube)
122{
123 cpl_imagelist *result = NULL;
124 cpl_imagelist *list = NULL;
125 cpl_mask *mask = NULL;
126 cpl_vector *exptime = NULL;
127 cpl_vector *fluxes = NULL;
128
129 cpl_errorstate prestate = cpl_errorstate_get();
130
131 cpl_ensure(detlist != NULL, CPL_ERROR_NULL_INPUT, NULL);
132 cpl_ensure(cube != NULL, CPL_ERROR_NULL_INPUT, NULL);
133
134 int badpix_level = MOO_BADPIX_GOOD;
135 int degree = MOO_COMPUTE_LINEARITY_DEGREE;
136
137 moo_detlist_load_single(detlist, type, num, badpix_level);
138 int size = moo_detlist_get_size(detlist);
139 list = moo_detlist_get_single_data(detlist, type, num);
140
141 if (list != NULL && cpl_imagelist_get_size(list) > 0) {
142 cpl_msg_info(__func__, "Compute coefficients map for %s",
143 moo_detector_get_extname(type, num));
144
145 int nx = cpl_image_get_size_x(cpl_imagelist_get(list, 0));
146 int ny = cpl_image_get_size_y(cpl_imagelist_get(list, 0));
147
148 result = cpl_imagelist_new();
149 mask = cpl_mask_new(nx, ny);
150
151 moo_try_check(_moo_compute_trace_mask(mask, loc, type, num), " ");
152 exptime = cpl_vector_new(size);
153 fluxes = cpl_vector_new(size);
154
155 for (int i = 0; i < size; i++) {
156 moo_det *det = moo_detlist_get(detlist, i);
157 double t = moo_pfits_get_exptime(det->primary_header);
158 if (type > 0) {
159 cpl_propertylist *extheader =
160 moo_det_get_single_header(det, type, num);
161 double dit = moo_pfits_get_dit(extheader);
162 double ndit = moo_pfits_get_ndit(extheader);
163 t = dit * ndit;
164 }
165 cpl_vector_set(exptime, i, t);
166 }
167
168#if CPL_COEFF_FIT
169 cpl_imagelist *coefs = NULL;
170 cpl_mask_not(mask);
171 for (int j = 1; j <= ny; j++) {
172 for (int i = 1; i <= nx; i++) {
173 int rej;
174 int v = cpl_image_get(saturate, i, j, &rej);
175 int kdx = v + 1;
176 if (kdx < size) {
177 if (kdx < 3) {
178 kdx = 0;
179 }
180 for (int k = kdx; k < size; k++) {
181 cpl_image *im = cpl_imagelist_get(list, k);
182 cpl_image_reject(im, i, j);
183 }
184 }
185 }
186 }
187
188 for (int i = 0; i < size; i++) {
189 cpl_image *im = cpl_imagelist_get(list, i);
190 cpl_mask *m = cpl_image_get_bpm(im);
191 cpl_mask_or(m, mask);
192 }
193
194 cpl_image *chi2 = NULL;
195 coefs = cpl_fit_imagelist_polynomial(exptime, list, 0, degree,
196 CPL_FALSE, CPL_TYPE_DOUBLE, chi2);
197
198#if MOO_DEBUG_COMPUTE_LINEARITY
199 char *chiname =
200 cpl_sprintf("CHI2_%s_%d.fits", moo_detector_get_extname(type, num),
201 degree);
202 cpl_image_save(chi2, chiname, CPL_TYPE_DOUBLE, NULL, CPL_IO_CREATE);
203 cpl_free(chiname);
204#endif
205 cpl_image_delete(chi2);
206
207 for (int i = 0; i <= degree; i++) {
208 cpl_image *coef = cpl_imagelist_get(coefs, i);
209 cpl_imagelist_set(result, cpl_image_duplicate(coef), i);
210 }
211 cpl_imagelist_delete(coefs);
212#else
213 int ntime = hdrl_imagelist_get_size(list);
214 cpl_image *c0_img = cpl_image_new(nx, ny, CPL_TYPE_DOUBLE);
215 cpl_image *c1_img = cpl_image_new(nx, ny, CPL_TYPE_DOUBLE);
216 cpl_image *c2_img = cpl_image_new(nx, ny, CPL_TYPE_DOUBLE);
217 cpl_imagelist_set(result, c0_img, 0);
218 cpl_imagelist_set(result, c1_img, 1);
219 cpl_imagelist_set(result, c2_img, 2);
220 for (int y = 1; y <= ny; y++) {
221 for (int x = 1; x <= nx; x++) {
222 for (int t = 0; t < ntime; t++) {
223 hdrl_image *himg = hdrl_imagelist_get(list, t);
224 int rej;
225 hdrl_value val = hdrl_image_get_pixel(himg, x, y, &rej);
226 cpl_vector_set(fluxes, t, val.data);
227 }
228 int illuminated = cpl_mask_get(mask, x, y);
229 double c0 = NAN;
230 double c1 = NAN;
231 double c2 = NAN;
232
233 if (illuminated == 1) {
234 const cpl_size coef0 = 0;
235 const cpl_size coef1 = 1;
236 cpl_size coef2 = 2;
237 cpl_polynomial *poly_linfit = cpl_polynomial_new(1);
238 cpl_matrix *samppos1d =
239 cpl_matrix_wrap(1, ntime, cpl_vector_get_data(exptime));
240 cpl_vector *fitvals = fluxes;
241 const cpl_size maxdeg1d = degree;
242 cpl_polynomial_fit(poly_linfit, samppos1d, NULL, fitvals,
243 NULL, CPL_FALSE, NULL, &maxdeg1d);
244 c0 = cpl_polynomial_get_coeff(poly_linfit, &coef0);
245 c1 = cpl_polynomial_get_coeff(poly_linfit, &coef1);
246 c2 = cpl_polynomial_get_coeff(poly_linfit, &coef2);
247
248 cpl_matrix_unwrap(samppos1d);
249 cpl_polynomial_delete(poly_linfit);
250 }
251 cpl_image_set(c0_img, x, y, c0);
252 cpl_image_set(c1_img, x, y, c1);
253 cpl_image_set(c2_img, x, y, c2);
254 }
255 }
256#endif
257 }
258 moo_detlist_free_single(detlist, type, num);
259moo_try_cleanup:
260 cpl_mask_delete(mask);
261 cpl_imagelist_delete(list);
262 cpl_vector_delete(exptime);
263 cpl_vector_delete(fluxes);
264 if (!cpl_errorstate_is_equal(prestate)) {
265 cpl_imagelist_delete(result);
266 result = NULL;
267 }
268 return result;
269}
270/******************************************************************************/
271moo_cube *
272moo_compute_linearity(moo_detlist *detlist,
273 moo_loc *loc,
274 moo_saturate_map *saturate_map,
275 const char *cube_name)
276{
277 cpl_errorstate prestate = cpl_errorstate_get();
278 moo_cube *result = NULL;
279
280 cpl_ensure(detlist != NULL, CPL_ERROR_NULL_INPUT, NULL);
281 cpl_ensure(cube_name != NULL, CPL_ERROR_NULL_INPUT, NULL);
282 cpl_ensure(saturate_map != NULL, CPL_ERROR_NULL_INPUT, NULL);
283
284 moo_fits_create(cube_name);
285
286 moo_try_check(result = moo_cube_new(), " ");
287 result->primary_header = cpl_propertylist_new();
288 moo_try_check(result->filename = cpl_strdup(cube_name), " ");
289
290 for (int num = 1; num <= 2; num++) {
291 for (int type = 0; type < 3; type++) {
292 cpl_imagelist *data = NULL;
293 data = _moo_compute_linearity_single(
294 detlist, loc, type, num,
295 saturate_map->data[type + (num - 1) * 3], result);
296 moo_cube_add_data(result, data, type, num);
297 }
298 }
299moo_try_cleanup:
300 if (!cpl_errorstate_is_equal(prestate)) {
301 moo_cube_delete(result);
302 result = NULL;
303 }
304 return result;
305}
306/******************************************************************************/
307cpl_image *
308_moo_compute_bpm_linear_single(cpl_imagelist *coeffs,
309 moo_loc *loc,
311 int num,
312 double kappa,
313 cpl_image *index,
314 cpl_image *flux,
315 double min_snr)
316{
317 cpl_image *result = NULL;
318 cpl_mask *cold_mask = NULL;
319 cpl_mask *hot_mask = NULL;
320 cpl_mask *trace_mask = NULL;
321
322 cpl_errorstate prestate = cpl_errorstate_get();
323 cpl_ensure(coeffs != NULL, CPL_ERROR_NULL_INPUT, NULL);
324 cpl_ensure(index != NULL, CPL_ERROR_NULL_INPUT, NULL);
325 int nx = cpl_image_get_size_x(index);
326 int ny = cpl_image_get_size_y(index);
327
328 result = cpl_image_new(nx, ny, CPL_TYPE_INT);
329
330 cold_mask = cpl_mask_new(nx, ny);
331 hot_mask = cpl_mask_new(nx, ny);
332
333 for (int j = 1; j <= ny; j++) {
334 for (int i = 1; i <= nx; i++) {
335 int rej;
336 double vi = cpl_image_get(flux, i, j, &rej);
337 if (isnan(vi)) {
338 cpl_image_reject(flux, i, j);
339 }
340 }
341 }
342
343 if (type == MOO_TYPE_RI) {
344 double medflux = cpl_image_get_median(flux);
345 for (int j = 1; j <= ny; j++) {
346 for (int i = 1; i <= nx; i++) {
347 int rej;
348 int vi = cpl_image_get(index, i, j, &rej);
349 if (vi == -1) {
350 double vf = cpl_image_get(flux, i, j, &rej);
351 if (vf >= medflux) {
352 cpl_mask_set(hot_mask, i, j, CPL_BINARY_1);
353 }
354 else {
355 cpl_mask_set(cold_mask, i, j, CPL_BINARY_1);
356 }
357 }
358 }
359 }
360 }
361 else {
362 for (int j = 1; j <= ny; j++) {
363 for (int i = 1; i <= nx; i++) {
364 int rej;
365 int vi = cpl_image_get(index, i, j, &rej);
366 if (vi == -1) {
367 double vf = cpl_image_get(flux, i, j, &rej);
368 if (fabs(vf) <= DBL_EPSILON) {
369 cpl_mask_set(hot_mask, i, j, CPL_BINARY_1);
370 cpl_image_set(result, i, j, MOO_BADPIX_HOT);
371 }
372 else {
373 cpl_mask_set(cold_mask, i, j, CPL_BINARY_1);
374 cpl_image_set(result, i, j, MOO_BADPIX_COLD);
375 }
376 }
377 }
378 }
379 }
380
381 trace_mask = cpl_mask_new(nx, ny);
382 moo_try_check(_moo_compute_trace_mask(trace_mask, loc, type, num), " ");
383 cpl_mask_not(trace_mask);
384
385 cpl_msg_info(__func__,
386 "Compute bad pixels map for %s using kappa %f and min snr %f",
387 moo_detector_get_extname(type, num), kappa, min_snr);
388
389 int size = cpl_imagelist_get_size(coeffs);
390
391 cpl_msg_indent_more();
392 for (int k = 1; k < size; k++) {
393 cpl_image *im = cpl_imagelist_get(coeffs, k);
394 cpl_mask *mask = cpl_image_get_bpm(im);
395 cpl_mask_or(mask, trace_mask);
396 cpl_mask_or(mask, hot_mask);
397 cpl_mask_or(mask, cold_mask);
398
399 double s;
400
401 double median = cpl_image_get_mad(im, &s);
402 s *= CPL_MATH_STD_MAD;
403 cpl_msg_info(__func__, "coef%d find median %f sigma %f", k, median, s);
404 for (int j = 1; j <= ny; j++) {
405 for (int i = 1; i <= nx; i++) {
406 int rej;
407 double c = cpl_image_get(im, i, j, &rej);
408 if (rej == 0 && (fabs(c - median) > kappa * s)) {
409 cpl_image_set(result, i, j, MOO_BADPIX_NON_LINEAR);
410 }
411 }
412 }
413 }
414 cpl_msg_indent_less();
415/*
416 hdrl_image* im1 = hdrl_imagelist_get(list,0);
417 for(int j=1;j<=ny;j++){
418 for(int i=1;i<=nx;i++){
419 hdrl_value v = hdrl_image_get_pixel(im1,i,j,NULL);
420 if (isnan(v.data)){
421 cpl_mask_set(mask,i,j,CPL_BINARY_1);
422 }
423 }
424 }
425
426 for(int i=0;i<size;i++){
427 hdrl_image* im = hdrl_imagelist_get(list,i);
428 cpl_mask_or(hdrl_image_get_mask(im),mask);
429 cpl_mask_or(hdrl_image_get_mask(im),snr_mask);
430 }
431 hdrl_parameter *par = hdrl_bpm_fit_parameter_create_rel_coef(
432 2,kappa,kappa);
433 moo_hdrl_bpm_fit_compute(par, list, exptime, &result);
434 hdrl_parameter_delete(par);
435
436 for(int j=1;j<=ny;j++){
437 for(int i=1;i<=nx;i++){
438 cpl_binary v= cpl_mask_get(mask,i,j);
439 int rej;
440 int val = cpl_image_get(result,i,j,&rej);
441 if (val < 2 || v == CPL_BINARY_1){
442 cpl_image_set(result,i,j,0);
443 }
444 else{
445 cpl_image_set(result,i,j,MOO_BADPIX_NON_LINEAR);
446 }
447 }
448 }
449 cpl_mask_delete(mask);
450 }
451 */
452moo_try_cleanup:
453 cpl_mask_delete(cold_mask);
454 cpl_mask_delete(hot_mask);
455 cpl_mask_delete(trace_mask);
456
457 if (!cpl_errorstate_is_equal(prestate)) {
458 cpl_image_delete(result);
459 result = NULL;
460 }
461 return result;
462}
463
464moo_bpm *
465moo_compute_bpm_linearity(moo_cube *cube,
466 moo_loc *loc,
467 moo_saturate_map *saturate_map,
468 moo_linear_params *params,
469 const char *bpm_name)
470{
471 cpl_errorstate prestate = cpl_errorstate_get();
472 moo_bpm *result = NULL;
473
474 cpl_ensure(cube != NULL, CPL_ERROR_NULL_INPUT, NULL);
475 cpl_ensure(saturate_map != NULL, CPL_ERROR_NULL_INPUT, NULL);
476 cpl_ensure(params != NULL, CPL_ERROR_NULL_INPUT, NULL);
477 cpl_ensure(bpm_name != NULL, CPL_ERROR_NULL_INPUT, NULL);
478 moo_fits_create(bpm_name);
479
480 moo_try_check(result = moo_bpm_new(), " ");
481 result->primary_header = cpl_propertylist_new();
482 moo_try_check(result->filename = cpl_strdup(bpm_name), " ");
483
484 double *ktab = params->kappa;
485 double *snrtab = params->min_snr;
486 for (int num = 1; num <= 2; num++) {
487 for (int type = 0; type < 3; type++) {
488 int idx = type + (num - 1) * 3;
489 double kappa = ktab[idx];
490 double min_snr = snrtab[idx];
491 cpl_image *index = saturate_map->data[idx];
492 cpl_image *flux = saturate_map->flux[idx];
493 cpl_imagelist *cdata = cube->data[idx];
494 cpl_image *resdata = NULL;
495 if (cdata != NULL) {
496 resdata =
497 _moo_compute_bpm_linear_single(cdata, loc, type, num, kappa,
498 index, flux, min_snr);
499 }
500 moo_bpm_add_data(result, resdata, type, num);
501 }
502 }
503moo_try_cleanup:
504 if (!cpl_errorstate_is_equal(prestate)) {
505 moo_bpm_delete(result);
506 result = NULL;
507 }
508 return result;
509}
510/******************************************************************************/
511
512cpl_image *
513_moo_compute_saturate_pixels_single(moo_detlist *detlist,
514 moo_loc *loc,
516 int num,
517 double threshold,
518 cpl_image **flux_img,
519 cpl_image **err_img,
520 cpl_image **exptime_img)
521{
522 cpl_image *result = NULL;
523 cpl_mask *mask = NULL;
524 hdrl_imagelist *list = NULL;
525 cpl_image *sub = NULL;
526 cpl_vector *exptime = NULL;
527
528 cpl_errorstate prestate = cpl_errorstate_get();
529
530 cpl_ensure(detlist != NULL, CPL_ERROR_NULL_INPUT, NULL);
531 cpl_ensure(flux_img != NULL, CPL_ERROR_NULL_INPUT, NULL);
532 cpl_ensure(err_img != NULL, CPL_ERROR_NULL_INPUT, NULL);
533 cpl_ensure(exptime_img != NULL, CPL_ERROR_NULL_INPUT, NULL);
534
535 int badpix_level = MOO_BADPIX_GOOD;
536 int size = moo_detlist_get_size(detlist);
537
538 moo_try_check(moo_detlist_load_single(detlist, type, num, badpix_level),
539 " ");
540 moo_try_check(list = moo_detlist_get_image(detlist, type, num), " ");
541
542 if (list != NULL && hdrl_imagelist_get_size(list) > 0) {
543 cpl_msg_info(__func__,
544 "Compute saturate pixels map for %s using threshold %f",
545 moo_detector_get_extname(type, num), threshold);
546
547 int nx = hdrl_imagelist_get_size_x(list);
548 int ny = hdrl_imagelist_get_size_y(list);
549
550 result = cpl_image_new(nx, ny, CPL_TYPE_INT);
551 *exptime_img = cpl_image_new(nx, ny, CPL_TYPE_DOUBLE);
552 *flux_img = cpl_image_new(nx, ny, CPL_TYPE_DOUBLE);
553 *err_img = cpl_image_new(nx, ny, CPL_TYPE_DOUBLE);
554 mask = cpl_mask_new(nx, ny);
555 _moo_compute_trace_mask(mask, loc, type, num);
556 cpl_mask_not(mask);
557 for (int j = 1; j <= ny; j++) {
558 for (int i = 1; i <= nx; i++) {
559 cpl_binary b = cpl_mask_get(mask, i, j);
560 if (b == CPL_BINARY_0) {
561 // cpl_image_set(result,i,j,0);
562 cpl_image_set(result, i, j, size - 1);
563 }
564 else {
565 cpl_image_set(result, i, j, NAN);
566 cpl_image_reject(result, i, j);
567 }
568 }
569 }
570
571 for (int k = size - 1; k >= 0; k--) {
572 cpl_image *im1 = hdrl_image_get_image(hdrl_imagelist_get(list, k));
573 int nb_saturate = 0;
574
575 for (int j = 1; j <= ny; j++) {
576 for (int i = 1; i <= nx; i++) {
577 int rej;
578 double v = cpl_image_get(im1, i, j, &rej);
579 cpl_binary m = cpl_mask_get(mask, i, j);
580 if (m == CPL_BINARY_0) {
581 if (v <= threshold) {
582 cpl_mask_set(mask, i, j, CPL_BINARY_1);
583 cpl_image_set(result, i, j, k);
584 }
585 else {
586 nb_saturate++;
587 }
588 }
589 }
590 }
591 if (nb_saturate == 0) {
592 break;
593 }
594 else {
595 cpl_msg_info(__func__, "Find at %d : %d saturate pixels", k,
596 nb_saturate);
597 }
598 }
599
600 exptime = cpl_vector_new(size);
601
602 for (int i = 0; i < size; i++) {
603 moo_det *det = moo_detlist_get(detlist, i);
604 double t = moo_pfits_get_exptime(det->primary_header);
605 if (type > 0) {
606 cpl_propertylist *extheader =
607 moo_det_get_single_header(det, type, num);
608 double dit = moo_pfits_get_dit(extheader);
609 double ndit = moo_pfits_get_ndit(extheader);
610 t = dit * ndit;
611 }
612 cpl_vector_set(exptime, i, t);
613 }
614
615 for (int j = 1; j <= ny; j++) {
616 for (int i = 1; i <= nx; i++) {
617 int rej;
618
619 int v = cpl_image_get(result, i, j, &rej);
620
621 if (rej == 0) {
622 if (v == size - 1) {
623 cpl_image *im1 = hdrl_image_get_image(
624 hdrl_imagelist_get(list, size - 1));
625 cpl_image *im2 = hdrl_image_get_image(
626 hdrl_imagelist_get(list, size - 2));
627 cpl_image *im3 = hdrl_image_get_image(
628 hdrl_imagelist_get(list, size - 3));
629 double v1 = cpl_image_get(im1, i, j, &rej);
630 double v2 = cpl_image_get(im2, i, j, &rej);
631 double v3 = cpl_image_get(im3, i, j, &rej);
632 double t1 = cpl_vector_get(exptime, size - 1);
633 double t2 = cpl_vector_get(exptime, size - 2);
634 double t3 = cpl_vector_get(exptime, size - 3);
635 double f1 = (v1 - v2) / (t1 - t2);
636 double f2 = (v2 - v3) / (t2 - t3);
637
638 if (f1 < f2 * 0.5) {
639 v = size - 2;
640 cpl_image_set(result, i, j, v);
641 }
642 }
643 else if (v == -1) {
644 v = size - 1;
645 }
646 cpl_image *im1 =
647 hdrl_image_get_image(hdrl_imagelist_get(list, v));
648 cpl_image *err1 =
649 hdrl_image_get_error(hdrl_imagelist_get(list, v));
650 double f = cpl_image_get(im1, i, j, &rej);
651 double fe = cpl_image_get(err1, i, j, &rej);
652 double e = cpl_vector_get(exptime, v);
653 cpl_image_set(*flux_img, i, j, f);
654 cpl_image_set(*err_img, i, j, fe);
655 cpl_image_set(*exptime_img, i, j, e);
656 }
657 else {
658 cpl_image_set(*flux_img, i, j, NAN);
659 cpl_image_set(*err_img, i, j, NAN);
660 cpl_image_set(*exptime_img, i, j, NAN);
661 }
662 }
663 }
664 }
665 moo_try_check(moo_detlist_free_single(detlist, type, num), " ");
666
667moo_try_cleanup:
668 hdrl_imagelist_unwrap(list);
669 cpl_mask_delete(mask);
670 cpl_vector_delete(exptime);
671 if (!cpl_errorstate_is_equal(prestate)) {
672 cpl_image_delete(sub);
673 cpl_image_delete(*flux_img);
674 cpl_image_delete(*err_img);
675 cpl_image_delete(*exptime_img);
676 cpl_image_delete(result);
677 *flux_img = NULL;
678 *err_img = NULL;
679 *exptime_img = NULL;
680 result = NULL;
681 }
682 return result;
683}
684
685moo_saturate_map *
686moo_compute_saturate_pixels(moo_detlist *detlist,
687 moo_loc *loc,
688 moo_linear_params *params)
689{
690 moo_saturate_map *result = NULL;
691 cpl_image *data = NULL;
692
693 cpl_errorstate prestate = cpl_errorstate_get();
694
695 cpl_ensure(detlist != NULL, CPL_ERROR_NULL_INPUT, NULL);
696 cpl_ensure(params != NULL, CPL_ERROR_NULL_INPUT, NULL);
697
698 double threshold = params->saturate_threshold;
699
700 result = moo_saturate_map_new();
701 result->primary_header = cpl_propertylist_new();
702
703 for (int num = 1; num <= 2; num++) {
704 for (int type = 0; type < 3; type++) {
705 cpl_image *flux = NULL;
706 cpl_image *err = NULL;
707 cpl_image *exptime = NULL;
708 moo_try_check(data = _moo_compute_saturate_pixels_single(
709 detlist, loc, type, num, threshold, &flux, &err,
710 &exptime),
711 " ");
712 cpl_propertylist *header = cpl_propertylist_new();
713 moo_saturate_map_set_data(result, type, num, data, flux, err,
714 exptime, header);
715 }
716 }
717
718moo_try_cleanup:
719 if (!cpl_errorstate_is_equal(prestate)) {
721 result = NULL;
722 }
723 return result;
724}
#define MOO_BADPIX_COLD
Definition: moo_badpix.h:54
#define MOO_BADPIX_NON_LINEAR
Definition: moo_badpix.h:60
#define MOO_BADPIX_HOT
Definition: moo_badpix.h:51
#define MOO_BADPIX_GOOD
Definition: moo_badpix.h:36
void moo_bpm_delete(moo_bpm *self)
Delete a moo_bpm.
Definition: moo_bpm.c:213
cpl_error_code moo_bpm_add_data(moo_bpm *self, cpl_image *img, moo_detector_type type, int ntas)
Add CPL_IMAGE extension to BPM filename and update moo_bpm structure.
Definition: moo_bpm.c:113
moo_bpm * moo_bpm_new(void)
Create a new moo_bpm.
Definition: moo_bpm.c:66
moo_cube * moo_cube_new(void)
Create a new moo_cube.
Definition: moo_cube.c:66
cpl_error_code moo_cube_add_data(moo_cube *self, cpl_imagelist *list, moo_detector_type type, int ntas)
Add CPL_IMAGELIST extension to CUBE filename and update moo_cube structure.
Definition: moo_cube.c:147
void moo_cube_delete(moo_cube *self)
Delete a moo_cube.
Definition: moo_cube.c:343
const char * moo_detector_get_extname(moo_detector_type type, int ntas)
Get the extension name of a detector.
Definition: moo_detector.c:137
enum _moo_detector_type_ moo_detector_type
The type code type.
Definition: moo_detector.h:64
@ MOO_TYPE_RI
Definition: moo_detector.h:46
hdrl_imagelist * moo_detlist_get_image(const moo_detlist *self, moo_detector_type type, int num)
Get the all the images of the type part in the detlist.
Definition: moo_detlist.c:225
cpl_size moo_detlist_get_size(const moo_detlist *self)
Get the number of DET in the detlist.
Definition: moo_detlist.c:173
cpl_error_code moo_detlist_free_single(const moo_detlist *self, moo_detector_type type, int num)
Free the type part for all DET in the detlist.
Definition: moo_detlist.c:143
cpl_imagelist * moo_detlist_get_single_data(const moo_detlist *self, moo_detector_type type, int num)
Get the type data part for all DET in the detlist.
Definition: moo_detlist.c:279
cpl_error_code moo_detlist_load_single(const moo_detlist *self, moo_detector_type type, int num, int level)
Load the type part for all DET in the detlist.
Definition: moo_detlist.c:107
moo_det * moo_detlist_get(moo_detlist *self, int i)
Get the DET at the position i in the list.
Definition: moo_detlist.c:196
cpl_error_code moo_fits_create(const char *filename)
Create a new fits file with empty propertylist.
Definition: moo_fits.c:533
cpl_image * moo_loc_single_get_f_wup(moo_loc_single *self)
Get image of width low.
cpl_image * moo_loc_single_get_f_centroids(moo_loc_single *self)
Get image of fit centroids.
cpl_image * moo_loc_single_get_f_wlo(moo_loc_single *self)
Get image of width low.
moo_loc_single * moo_loc_get_single(moo_loc *self, moo_detector_type type, int ntas)
Get the type part in LOC and return it.
Definition: moo_loc.c:155
cpl_table * moo_loc_get_fibre_table(moo_loc *self)
Get the FIBRE TABLE in LOC.
Definition: moo_loc.c:306
moo_saturate_map * moo_saturate_map_new(void)
Create a new moo_saturate_map.
void moo_saturate_map_delete(moo_saturate_map *self)
Delete a moo_map_saturate.
cpl_error_code moo_saturate_map_set_data(moo_saturate_map *self, moo_detector_type type, int ntas, cpl_image *data, cpl_image *flux, cpl_image *err, cpl_image *exptime, cpl_propertylist *header)
set saturate map data for relevant extension
int moo_pfits_get_ndit(const cpl_propertylist *plist)
find out the ESO DET NDIT value
Definition: moo_pfits.c:382
double moo_pfits_get_dit(const cpl_propertylist *plist)
find out the DIT value
Definition: moo_pfits.c:362
double moo_pfits_get_exptime(const cpl_propertylist *plist)
find out the EXPTIME value
Definition: moo_pfits.c:1039