SINFONI Pipeline Reference Manual  2.5.2
sinfo_new_bezier.c
1 /*
2  * This file is part of the ESO SINFONI Pipeline
3  * Copyright (C) 2004,2005 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, 51 Franklin St, Fifth Floor, Boston, MA 02111-1307 USA
18  */
19 /*****************************************************************************
20  * M.P.E. - SPIFFI project
21  *
22  *
23  *
24  * who when what
25 
26  * -------- -------- ----------------------------------------------
27  * rabuter 2004-11-04 Fixed error on Find Cosmic when no valid neighboors
28  where found in the subcube
29  * rabuter 10/07/03 created
30  */
31 
32 /************************************************************************
33  * NAME
34  * sinfo_new_bezier.c -
35  * procedures to correct for bad pixels using bezier splines
36  *
37  * SYNOPSIS
38  *
39  * DESCRIPTION
40  *
41  * FILES
42  *
43  * ENVIRONMENT
44  *
45  * RETURN VALUES
46  *
47  * CAUTIONS
48  *
49  * EXAMPLES
50  *
51  * SEE ALSO
52  *
53  * BUGS
54  *
55  *------------------------------------------------------------------------
56  */
57 
58 #ifdef HAVE_CONFIG_H
59 # include <config.h>
60 #endif
61 #define POSIX_SOURCE 1
62 #include "sinfo_vltPort.h"
63 
64 /*
65  * System Headers
66  */
67 
68 /*
69  * Local Headers
70  */
71 
72 #include "sinfo_new_bezier.h"
73 #include "sinfo_msg.h"
81 /*----------------------------------------------------------------------------
82  * Function codes
83  *--------------------------------------------------------------------------*/
84 
93 int
94 sinfo_im_xy(cpl_image* im, int X, int Y)
95 {
96  int res = 0;
97 
98  res = X + Y * cpl_image_get_size_x(im);
99  return res;
100 }
109 int
110 sinfo_im_xyz(cpl_image* im, int X, int Y, int Z)
111 {
112  int res = 0;
113  res = X + Y * cpl_image_get_size_x(im)
114  + Z * cpl_image_get_size_x(im) * cpl_image_get_size_y(im);
115  return res;
116 }
117 
126 int
127 sinfo_cu_xy(cpl_imagelist* cu, int X, int Y)
128 {
129  int res = 0;
130 
131  res = X + Y * cpl_image_get_size_x(cpl_imagelist_get(cu, 0));
132  return res;
133 }
144 int
145 sinfo_cu_xyz(cpl_imagelist* cu, int X, int Y, int Z)
146 {
147  int res = 0;
148  res = X + Y * cpl_image_get_size_x(cpl_imagelist_get(cu, 0))
149  + Z * cpl_image_get_size_x(cpl_imagelist_get(cu, 0))
150  * cpl_image_get_size_y(
151  cpl_imagelist_get(cu, 0));
152  return res;
153 }
154 
169 cpl_image *
170 sinfo_new_c_bezier_interpolate_image(cpl_image *im, cpl_image *mask,
171  new_Lookup *look, short rx, short ry,
172  short rz, int max_rad, float ** slit_edges)
173 {
174 
175  int i, j, count;
176  cpl_imagelist * sc_im, *drs_sc_mask;
177  cpl_image *auxImage;
178  cpl_image *tempMask;
179  short szx, szy, szz;
180  short rx_loop, ry_loop, rz_loop;
181  /*float ant,new,dif;*/
182 
183  int ilx = 0;
184  int ily = 0;
185  int mlx = 0;
186  int mly = 0;
187 
188  float* pidata = NULL;
189  float* pmdata = NULL;
190  float* ptdata = NULL;
191  float* padata = NULL;
192 
193  cpl_image* sc_img = NULL;
194  cpl_image* drs_img = NULL;
195 
196  mlx = cpl_image_get_size_x(mask);
197  mly = cpl_image_get_size_y(mask);
198  ilx = cpl_image_get_size_x(im);
199  ily = cpl_image_get_size_y(im);
200 
201  pmdata = cpl_image_get_data_float(mask);
202  pidata = cpl_image_get_data_float(im);
203 
204  if (mlx != ilx || mly != ily) {
205  sinfo_msg_error(" data & mask images not compatible in size\n");
206  return NULL ;
207  }
208 
209  /* allocate memory for sub cubes*/
210  szx = (rx * 2) + 1;
211  szy = (ry * 2) + 1;
212  szz = (rz * 2) + 1;
213 
214  if (NULL == (sc_im = cpl_imagelist_new())) {
215  sinfo_msg_error(" could not allocate memory for data subcube\n");
216  return NULL ;
217  }
218 
219  for (i = 0; i < szz; i++) {
220  sc_img = cpl_image_new(szx, szy, CPL_TYPE_FLOAT);
221  cpl_imagelist_set(sc_im, sc_img, i);
222  }
223 
224  if (NULL == (drs_sc_mask = cpl_imagelist_new())) {
225  sinfo_msg_error(" could not allocate memory for mask subcube\n");
226  return NULL ;
227  }
228  for (i = 0; i < szz; i++) {
229  drs_img = cpl_image_new(szx, szy, CPL_TYPE_FLOAT);
230  cpl_imagelist_set(drs_sc_mask, drs_img, i);
231  }
232 
233  if (NULL == (tempMask = cpl_image_new(mlx, mly, CPL_TYPE_FLOAT))) {
234  sinfo_msg_error("could not allocate memory for temporary "
235  "dead pixel mask\n");
236  return NULL ;
237  }
238  ptdata = cpl_image_get_data_float(tempMask);
239 
240  count = 0;
241  for (i = 0; i < mlx; i++) {
242  for (j = 0; j < mly; j++) {
243  if (pmdata[sinfo_im_xy(im, i, j)] == cubePT_BADPIXEL) {
244  rx_loop = 1;
245  ry_loop = 1;
246  rz_loop = 1;
247  pidata[sinfo_im_xy(im, i, j)] =
248  sinfo_new_c_bezier_correct_pixel(i, j, im, mask,
249  sc_im, drs_sc_mask, look,
250  rx_loop, ry_loop, rz_loop);
251  /* if not enough neighbors found, increase size of sub
252  cube until max radius is reached */
253  while (pidata[sinfo_im_xy(im, i, j)] == cubeNONEIGHBOR
254  && rx_loop < rx && ry_loop < ry && rz_loop < rz) {
255  rx_loop++;
256  ry_loop++;
257  rz_loop++;
258  /* sinfo_msg_warning("Increasing radius to %d, in %d %d",
259  rx_loop, i, j) ; */
260 
261  pidata[sinfo_im_xy(im, i, j)] =
262  sinfo_new_c_bezier_correct_pixel(i, j, im,
263  mask, sc_im, drs_sc_mask,
264  look, rx_loop, ry_loop,
265  rz_loop);
266  }
267  /* If still not enough neighbors, make result NaN = ZERO
268  in spred convention */
269  if (pidata[sinfo_im_xy(im, i, j)] == cubeNONEIGHBOR) {
270  pidata[sinfo_im_xy(im, i, j)] = ZERO;
271  }
272  count++;
273  }
274  if (pidata[sinfo_im_xy(im, i, j)] == ZERO) {
275  ptdata[sinfo_im_xy(tempMask, i, j)] = 0;
276  }
277  else {
278  ptdata[sinfo_im_xy(tempMask, i, j)] = 1;
279  }
280  }
281  }
282 
283  sinfo_msg("Replacing NaN\n");
284  auxImage = sinfo_interpol_source_image(im, tempMask, max_rad, slit_edges);
285  padata = cpl_image_get_data_float(auxImage);
286  for (i = 0; i < mlx; i++) {
287  for (j = 0; j < mly; j++) {
288 
289  if (isnan(pidata[sinfo_im_xy(im,i,j)])) /*<= -2e10ZERO )*/
290  {
291  /* sinfo_msg_warning("Replacing NaN -> %d %d %f\n",
292  i,j, padata[sinfo_im_xy(im,i,j)] ); */
293  pidata[sinfo_im_xy(im, i, j)] = padata[sinfo_im_xy(im, i, j)];
294  }
295  }
296  }
297  cpl_image_delete(auxImage);
298  cpl_imagelist_delete(sc_im);
299  cpl_imagelist_delete(drs_sc_mask);
300 
301  sinfo_msg("bad pixels count: %d\n", count);
302 
303  return im;
304 }
305 
306 cpl_image *
307 sinfo_new_c_bezier_find_bad(cpl_image *im, cpl_image *mask,
308 /* Lookup *look,*/
309 short rx,
310  short ry, short rz, short lowerI, short highI,
311  short lowerJ, short highJ, float factor)
312 {
313 
314  int i, j, count;
315  cpl_imagelist * sc_im, *drs_sc_mask;
316  short szx, szy, szz;
317  float /*ant,*/newValue, old/*,dif,porcentage,distance*/;
318  double med, stdev;
319  /*cpl_image *out;*/
320  short rx_loop, ry_loop, rz_loop;
321 
322  int ilx = 0;
323  int ily = 0;
324  int mlx = 0;
325  int mly = 0;
326 
327  float* pidata = NULL;
328  //float* pmdata=NULL;
329 
330  cpl_image* sc_img = NULL;
331  cpl_image* drs_img = NULL;
332 
333  mlx = cpl_image_get_size_x(mask);
334  mly = cpl_image_get_size_y(mask);
335  ilx = cpl_image_get_size_x(im);
336  ily = cpl_image_get_size_y(im);
337 
338  //pmdata=cpl_image_get_data_float(mask);
339  pidata = cpl_image_get_data_float(im);
340 
341  if (mlx != ilx || mly != ily) {
342  sinfo_msg_error(" data & mask images not compatible in size\n");
343  return NULL ;
344  }
345 
346  /* allocate memory for sub cubes*/
347  szx = (rx * 2) + 1;
348  szy = (ry * 2) + 1;
349  szz = (rz * 2) + 1;
350 
351  if (NULL == (sc_im = cpl_imagelist_new())) {
352  sinfo_msg_error(" could not allocate memory for data subcube\n");
353  return NULL ;
354  }
355  for (i = 0; i < szz; i++) {
356  sc_img = cpl_image_new(szx, szy, CPL_TYPE_FLOAT);
357  cpl_imagelist_set(sc_im, sc_img, i);
358  }
359 
360  if (NULL == (drs_sc_mask = cpl_imagelist_new())) {
361  sinfo_msg_error(" could not allocate memory for mask subcube\n");
362  return NULL ;
363  }
364  for (i = 0; i < szz; i++) {
365  drs_img = cpl_image_new(szx, szy, CPL_TYPE_FLOAT);
366  cpl_imagelist_set(drs_sc_mask, drs_img, i);
367  }
368 
369  count = 0;
370  for (i = 0; i < mlx; i++) {
371  for (j = 0; j < mly; j++) {
372  if (i >= lowerI && i < highI && j >= lowerJ && j < highJ) {
373 
374  rx_loop = 1;
375  ry_loop = 1;
376  rz_loop = 1;
377  newValue = sinfo_new_c_bezier_correct_pixel_2D(i, j, im, mask,
378  sc_im, drs_sc_mask,
379  /* look,*/
380  rx_loop, ry_loop, rz_loop, &med, &stdev,
381  factor);
382  /* if NaN returned, increase size of sub cube
383  until max radius is reached */
384  while (newValue == ZERO && rx_loop < rx && ry_loop < ry
385  && rz_loop < rz) {
386  rx_loop++;
387  ry_loop++;
388  rz_loop++;
389  /*sinfo_msg_warning("Increasing radius to %d,
390  in %d %d", rx_loop, i, j) ; */
391  newValue = sinfo_new_c_bezier_correct_pixel_2D(i, j, im,
392  mask, sc_im, drs_sc_mask,
393  /*, look*/
394  rx_loop, ry_loop, rz_loop, &med, &stdev,
395  factor);
396  }
397  if (isnan(newValue)) /*<= -3.e10 ZERO )*/
398  continue;
399 
400  old = pidata[sinfo_im_xy(im, i, j)];
401  if (newValue != old) {
402  pidata[sinfo_im_xy(im, i, j)] = newValue;
403  /*sinfo_msg_warning("[%d,%d]=%f -> %f, med= %f,
404  stdev=%f\n",i,j, old, newValue, med, stdev );*/
405  count++;
406  }
407  }
408  }
409  }
410 
411  sinfo_msg("bad pixels count: %d\n", count);
412 
413  cpl_imagelist_delete(sc_im);
414  cpl_imagelist_delete(drs_sc_mask);
415  return im;
416 }
417 
418 float
419 sinfo_new_c_bezier_correct_pixel(int ipos, int jpos, cpl_image * im,
420  cpl_image * mask, cpl_imagelist * sc_im,
421  cpl_imagelist * drs_sc_mask, new_Lookup * look,
422  short rx, short ry, short rz)
423 {
424  short ic, jc, kc, ii, jj, kk/*, sjj, skk*/, is, js, ks;
425  short i, j, k, indexJ, indexI, lx, ly, lz, szx, szy, szz;
426  /*float indexIf,indexJf,sp;*/
427  cpl_image * X, *Y, *Z, *hX;
428  cpl_imagelist * id, *jd;
429 
430  int idlx = 0;
431  int idly = 0;
432  int idnp = 0;
433 
434  int drslx = 0;
435  int drsly = 0;
436  int drsnp = 0;
437 
438  float* pXdata = NULL;
439  float* pYdata = NULL;
440  float* pZdata = NULL;
441  float* phXdata = NULL;
442  float* pidata = NULL;
443  float* pmdata = NULL;
444  float* piddata = NULL;
445  float* pjddata = NULL;
446  float* pscdata = NULL;
447  float* pdrsdata = NULL;
448 
449  cpl_image* id_img = NULL;
450  cpl_image* jd_img = NULL;
451  cpl_image* sc_img = NULL;
452  cpl_image* drs_img = NULL;
453 
454  X = look->X;
455  Y = look->Y;
456  Z = look->Z;
457  hX = look->hX;
458  id = look->id;
459  jd = look->jd;
460 
461  /*
462  phXdata=cpl_image_get_data_float(hX);
463  if ( phXdata[sinfo_im_xy( hX, ipos, jpos)] > 1 )
464  {
465  sinfo_msg_error(" double hit in position [%d,%d]=%f, "
466  "can not correct\n",
467  ipos,jpos,phXdata[sinfo_im_xy(hX,ipos,jpos)]) ;
468  return ( -2e10 );
469  }*/
470 
471  pidata = cpl_image_get_data_float(im);
472  pmdata = cpl_image_get_data_float(mask);
473 
474  phXdata = cpl_image_get_data_float(hX);
475  if (phXdata[sinfo_im_xy(hX, ipos, jpos)] < 1) {
476  /*sinfo_msg_error("no lookup in position [%d,%d]=%f, can not correct",
477  ipos,jpos,phXdata[sinfo_im_xy(hX,ipos,jpos)]) ;*/
478  return ( ZERO);
479  }
480  pXdata = cpl_image_get_data_float(X);
481  pYdata = cpl_image_get_data_float(Y);
482  pZdata = cpl_image_get_data_float(Z);
483 
484  ic = pXdata[sinfo_im_xy(X, ipos, jpos)];
485  jc = pYdata[sinfo_im_xy(Y, ipos, jpos)];
486  kc = pZdata[sinfo_im_xy(Z, ipos, jpos)];
487  /*if ( !(ipos % 16 ) )*/
488 #ifdef DEBUG
489  sinfo_msg_debug("Correcting bad pixel : ipos=%d,jpos=%d, "
490  "in Cube -> ic=%d, jc=%d, kc=%d\n",
491  ipos,jpos, ic, jc, kc );
492 #endif
493  /*limit to start not before the beginning of the cube*/
494  ii = ic - rx;
495  if (ii < 0)
496  ii = 0;
497  jj = jc - ry;
498  if (jj < 0)
499  jj = 0;
500  kk = kc - rz;
501  if (kk < 0)
502  kk = 0;
503 
504 #ifdef DEBUG
505  sinfo_msg_debug("Start Point in Cube -> ii=%d,jj=%d,kk=%d\n", ii, jj, kk );
506 #endif
507 
508  /*limit to end not outside of the cube */
509  szx = (rx * 2) + 1;
510  szy = (ry * 2) + 1;
511  szz = (rz * 2) + 1;
512 
513  idlx = cpl_image_get_size_x(cpl_imagelist_get(id, 0));
514  idly = cpl_image_get_size_y(cpl_imagelist_get(id, 0));
515  idnp = cpl_imagelist_get_size(id);
516 
517  lx = idlx;
518  ly = idly;
519  lz = idnp;
520 
521  if ((ic + rx) >= idlx)
522  szx = szx - ((ic + rx) - (lx - 1));
523 
524  if ((jc + ry) >= idly)
525  szy = szy - ((jc + ry) - (ly - 1));
526 
527  if ((kc + rz) >= idnp)
528  szz = szz - ((kc + rz) - (lz - 1));
529 
530  drslx = cpl_image_get_size_x(cpl_imagelist_get(drs_sc_mask, 0));
531  drsly = cpl_image_get_size_y(cpl_imagelist_get(drs_sc_mask, 0));
532  drsnp = cpl_imagelist_get_size(drs_sc_mask);
533 #ifdef DEBUG
534 
535  sinfo_msg_error("Size of subcube: szx=%d,szy=%d,szz=%d\n", szx, szy, szz );
536  /*fill whole mask with not available*/
537  sinfo_msg_error("Fill Mask subcube of size: %d,%d,%d, with NOINFO\n",
538  drslx, drsly, drsnp);
539 #endif
540  for (i = 0; i < drslx; i++) {
541  for (j = 0; j < drsly; j++) {
542  for (k = 0; k < drsnp; k++) {
543  drs_img = cpl_imagelist_get(drs_sc_mask, k);
544  pdrsdata = cpl_image_get_data_float(drs_img);
545  pdrsdata[sinfo_cu_xy(drs_sc_mask, i, j)] = cubePT_NOINFO;
546  }
547  }
548  }
549 
550  for (i = ii, is = 0; i < ii + szx; i++, is++) {
551  for (j = jj, js = 0; j < jj + szy; j++, js++) {
552  for (k = kk, ks = 0; k < kk + szz; k++, ks++) {
553 #ifdef DEBUG
554  sinfo_msg_debug("i=%d j=%d k=%d is=%d ij=%d ik=%d",
555  i,j,k,is,js,ks);
556 #endif
557  id_img = cpl_imagelist_get(id, k);
558  jd_img = cpl_imagelist_get(jd, k);
559  piddata = cpl_image_get_data_float(id_img);
560  pjddata = cpl_image_get_data_float(jd_img);
561 
562  drs_img = cpl_imagelist_get(drs_sc_mask, ks);
563  pdrsdata = cpl_image_get_data_float(drs_img);
564  sc_img = cpl_imagelist_get(sc_im, ks);
565  pscdata = cpl_image_get_data_float(sc_img);
566 
567  indexI = sinfo_new_nint(piddata[sinfo_cu_xy(id, i, j)]);
568  indexJ = sinfo_new_nint(pjddata[sinfo_cu_xy(jd, i, j)]);
569  if (indexJ <= -1 || indexJ >= 2048 || indexI == -1) {
570  pdrsdata[sinfo_cu_xy(drs_sc_mask, is, js)] = cubePT_NOINFO;
571  continue;
572  }
573  pscdata[sinfo_cu_xy(sc_im, is, js)] = pidata[sinfo_im_xy(im,
574  indexI, indexJ)];
575  pdrsdata[sinfo_cu_xy(drs_sc_mask, is, js)] = pmdata[sinfo_im_xy(
576  mask, indexI, indexJ)];
577  /*
578  #ifdef DEBUG
579  sinfo_msg_debug("Cube i=%d, j=%d, k=%d ;"
580  " Sub is=%d, js=%d, ks=%d ;"
581  " Plane I=%d,J=%d ; mask %f ; im %f",
582  i, j, k, is, js, ks, indexI, indexJ,
583  pmdata[sinfo_im_xy(mask,indexI,indexJ)],
584  pidata[sinfo_im_xy(im,indexI,indexJ)]);
585  #endif
586  */
587  }
588  }
589  }
590 
591  /*signal to correct this pixel*/
592  drs_img = cpl_imagelist_get(drs_sc_mask, rz);
593  pdrsdata = cpl_image_get_data_float(drs_img);
594  pdrsdata[sinfo_cu_xy(drs_sc_mask, rx, ry)] = cubePT_FIND;
595  return (sinfo_new_c_bezier_interpol(sc_im, drs_sc_mask));
596 }
597 
598 float
599 sinfo_new_c_bezier_correct_pixel_2D(int ipos, int jpos, cpl_image * im,
600  cpl_image * mask, cpl_imagelist * sc_im,
601  cpl_imagelist * drs_sc_mask,
602  /* Lookup * look,*/
603  short rx,
604  short ry, short rz, double *med,
605  double *stdev, float factor)
606 {
607  short ic, jc, kc, ii, jj, kk/*, sjj, skk*/, is, js, ks;
608  short i, j, k, indexJ, indexI, lx, ly, lz, szx, szy, szz;
609  double sum;
610  int counter;
611  float sumarr[100];
612 
613  int ilx = 0;
614  int ily = 0;
615 
616  int drslx = 0;
617  int drsly = 0;
618  int drsnp = 0;
619 
620  float* pidata = 0;
621  float* pmdata = 0;
622  float* pscdata = 0;
623  float* pdrsdata = 0;
624 
625  cpl_image* drs_img = NULL;
626  cpl_image* sc_img = NULL;
627 
628  jc = 0;
629  ic = ipos;
630  kc = jpos;
631  sinfo_msg_debug("Correcting bad pixel : ipos=%d,jpos=%d, "
632  "in Cube -> ic=%d, jc=%d, kc=%d", ipos, jpos, ic, jc, kc);
633  /*limit to start not before the beginning of the cube*/
634  ii = ic - rx;
635  if (ii < 0)
636  ii = 0;
637  jj = jc - ry;
638  if (jj < 0)
639  jj = 0;
640  kk = kc - rz;
641  if (kk < 0)
642  kk = 0;
643 
644  sinfo_msg_debug("Start Point in Cube -> ii=%d,jj=%d,kk=%d", ii, jj, kk);
645 
646  ilx = cpl_image_get_size_x(im);
647  ily = cpl_image_get_size_y(im);
648 
649  /*limit to end not outside of the cube */
650  szx = (rx * 2) + 1;
651  szy = (ry * 2) + 1;
652  szz = (rz * 2) + 1;
653  lx = ilx;
654  ly = ily;
655  lz = ily;
656  if ((ic + rx) >= ilx)
657  szx = szx - ((ic + rx) - (lx - 1));
658 
659  if ((jc + ry) >= ily)
660  szy = szy - ((jc + ry) - (ly - 1));
661 
662  if ((kc + rz) >= ily)
663  szz = szz - ((kc + rz) - (lz - 1));
664 
665 #ifdef DEBUG
666  drslx=cpl_image_get_size_x(cpl_imagelist_get(drs_sc_mask,0));
667  drsly=cpl_image_get_size_y(cpl_imagelist_get(drs_sc_mask,0));
668  drsnp=cpl_imagelist_get_size(drs_sc_mask);
669  sinfo_msg_debug("Size of subcube : szx=%d,szy=%d,szz=%d", szx, szy, szz );
670  /*fill whole mask with not available*/
671  sinfo_msg_debug("Fill Mask subcube of size:%d,%d,%d, with NOINFO",
672  drslx, drsly, drsnp);
673 #endif
674  for (i = 0; i < drslx; i++) {
675  for (j = 0; j < drsly; j++) {
676  for (k = 0; k < drsnp; k++) {
677  drs_img = cpl_imagelist_get(drs_sc_mask, k);
678  pdrsdata = cpl_image_get_data_float(drs_img);
679  pdrsdata[sinfo_cu_xy(drs_sc_mask, i, j)] = cubePT_NOINFO;
680  }
681  }
682  }
683  counter = 0;
684  sum = 0;
685  memset(sumarr, 0x00, sizeof(sumarr));
686  pidata = cpl_image_get_data(im);
687  pmdata = cpl_image_get_data(mask);
688 
689  for (i = ii, is = 0; i < ii + szx; i++, is++) {
690  for (j = jj, js = 0; j < jj + szy; j++, js++) {
691  for (k = kk, ks = 0; k < kk + szz; k++, ks++) {
692 #ifdef DEBUG
693  sinfo_msg_debug("i=%d j=%d k=%d is=%d ij=%d ik=%d",
694  i,j,k,is,js,ks);
695 #endif
696  indexI = i;
697  indexJ = k;
698  if (isnan(pidata[sinfo_im_xy(mask,indexI,indexJ)]))
699  pmdata[sinfo_im_xy(mask, indexI, indexJ)] = 0;
700 
701  if (pmdata[sinfo_im_xy(mask, indexI, indexJ)] == 1
702  && (indexI != ipos || indexJ != jpos)) {
703  /*sumarr[counter] = pidata[sinfo_im_xy(im,indexI,indexJ)];*/
704  sum = sum + pidata[sinfo_im_xy(im, indexI, indexJ)];
705  counter++;
706  }
707  sc_img = cpl_imagelist_get(sc_im, ks);
708  pscdata[sinfo_cu_xy(sc_im, is, js)] = pidata[sinfo_im_xy(im,
709  indexI, indexJ)];
710  drs_img = cpl_imagelist_get(drs_sc_mask, ks);
711  pdrsdata = cpl_image_get_data_float(drs_img);
712  pdrsdata[sinfo_cu_xy(drs_sc_mask, is, js)] = pmdata[sinfo_im_xy(
713  mask, indexI, indexJ)];
714 #ifdef DEBUG
715  sinfo_msg_debug("Cube i=%d, j=%d, k=%d ; "
716  "Sub is=%d, js=%d, ks=%d ; "
717  " Plane I=%d,J=%d ; mask %f ; im %f",
718  i, j, k, is, js, ks, indexI, indexJ,
719  pmdata[sinfo_im_xy(mask,indexI,indexJ)],
720  pidata[sinfo_im_xy(im,indexI,indexJ)]);
721 #endif
722 
723  }
724  }
725  }
726 
727  /*signal to correct this pixel*/
728  drs_img = cpl_imagelist_get(drs_sc_mask, rz);
729  pdrsdata = cpl_image_get_data_float(drs_img);
730  pdrsdata[sinfo_cu_xy(drs_sc_mask, rx, ry)] = cubePT_FIND;
731  if (counter)
733  *med = sum / counter;
734  else
735  return (pidata[sinfo_im_xy(im, ipos, jpos)]);
736 
737  /*sinfo_msg_debug("%f %f %d\n",
738  sum ,pidata[sinfo_im_xy(im,ipos,jpos)], counter);*/
739 
740  sum = 0;
741  counter = 0;
742  for (i = ii, is = 0; i < ii + szx; i++, is++) {
743  for (j = jj, js = 0; j < jj + szy; j++, js++) {
744  for (k = kk, ks = 0; k < kk + szz; k++, ks++) {
745  drs_img = cpl_imagelist_get(drs_sc_mask, ks);
746  pdrsdata = cpl_image_get_data_float(drs_img);
747  indexI = i;
748  indexJ = k;
749  if (pdrsdata[sinfo_cu_xy(drs_sc_mask, is, js)] == 1
750  && (indexI != ipos || indexJ != jpos)) {
751  sc_img = cpl_imagelist_get(sc_im, ks);
752  pscdata = cpl_image_get_data_float(sc_img);
753 
754  sum =
755  sum
756  + ((pscdata[sinfo_cu_xy(
757  drs_sc_mask,
758  is, js)]
759  - *med)
760  * (pscdata[sinfo_cu_xy(
761  drs_sc_mask,
762  is,
763  js)]
764  - *med));
765  counter++;
766  }
767  }
768  }
769  }
770  /*
771  double aux;
772  aux = sum;
773  */
774  sum = sum / (counter - 1);
775  *stdev = sqrt(sum);
776 
777  if ((fabs(pidata[sinfo_im_xy(im, ipos, jpos)] - *med) > factor * *stdev)
778  || isnan(pidata[sinfo_im_xy(im,ipos,jpos)])) {
779  /*sinfo_msg_debug("[%d,%d]: distance to mean = %f,"
780  " thres =%f sum=%f, stdev=%f, counter=%d, aux= %f",
781  ipos,jpos, fabs( pidata[sinfo_im_xy(im,ipos,jpos)] - *med),
782  factor * *stdev, sum,*stdev, counter,aux );
783  pmdata[sinfo_im_xy(mask,ipos,jpos)] = 0;*/
784  return (sinfo_new_c_bezier_interpol(sc_im, drs_sc_mask));
785  }
786  return (pidata[sinfo_im_xy(im, ipos, jpos)]);
787 }
788 
789 float
790 sinfo_new_c_bezier_interpol(cpl_imagelist * im, cpl_imagelist * action)
791 {
792  short pos;
793  unsigned short i, j, k;
794  new_XYZW indata[1000];
795  new_XYZW res;
796  new_XYZW selected;
797  float step, cumstep, distance, selected_distance;
798  new_Dim *point = NULL;
799  double munk;
800  int ilx = 0;
801  int ily = 0;
802  int inp = 0;
803  float* padata = NULL;
804  float* pidata = NULL;
805  cpl_image* i_img = NULL;
806  cpl_image* a_img = NULL;
807 
808  selected.w = 0;
809  memset(indata, 0x00, 1000 * sizeof(new_XYZW));
810  ilx = cpl_image_get_size_x(cpl_imagelist_get(im, 0));
811  ily = cpl_image_get_size_y(cpl_imagelist_get(im, 0));
812  inp = cpl_imagelist_get_size(im);
813 
814  pos = 0;
815  for (i = 0; i < ilx; i++) {
816  for (j = 0; j < ily; j++) {
817 #ifdef DEBUG
818  int pix=0;
819  pix=i+j*ilx;
820 #endif
821  for (k = 0; k < inp; k++) {
822  a_img = cpl_imagelist_get(action, k);
823  padata = cpl_image_get_data_float(a_img);
824  i_img = cpl_imagelist_get(action, k);
825  pidata = cpl_image_get_data_float(i_img);
826  if (padata[sinfo_cu_xy(action, i, j)] == cubePT_USE) {
827 #ifdef DEBUG
828  sinfo_msg_debug("Used im[%d,%d,%d]=%lf\n",
829  i,j,k,pidata[pix]);
830 #endif
831  indata[pos].x = i;
832  indata[pos].y = j;
833  indata[pos].z = k;
834  indata[pos].w = pidata[sinfo_cu_xy(im, i, j)];
835  pos++;
836  }
837  else {
838  if (padata[sinfo_cu_xy(action, i, j)] == cubePT_FIND) {
839  (*point).x = i;
840  (*point).y = j;
841  (*point).z = k;
842 #ifdef DEBUG
843  sinfo_msg_debug("Find for im[%d,%d,%d]=%lf reason:%f",
844  i,j,k,pidata[pix],
845  padata[sinfo_cu_xy(action,i,j)]);
846 #endif
847  }
848  else {
849 #ifdef DEBUG
850  sinfo_msg_debug("Ignored im[%d,%d,%d]=%lf reason:%f",
851  i,j,k,pidata[sinfo_im_xy(im,i,j)],
852  padata[pix]);
853 #endif
854  }
855  }
856  }
857  }
858  }
859 
860 
861  if (pos < 2) {
862 #ifdef DEBUG
863  sinfo_msg_debug("subcube contains no valid pixels "
864  "to use in iterpolation");
865 #endif
866  /*i_img=cpl_imagelist_get((*point).z);
867  pidata=cpl_image_get_data_float(i_img);
868  return( pidata[sinfo_im_xy(im,(*point).x,(*point).y)] );*/
869  return (cubeNONEIGHBOR);
870 
871  }
872 
873  step = 0.01;
874  cumstep = 0.0;
875  selected_distance = 1000;
876  munk = pow(1.0 - cumstep, (double) pos - 1);
877  for (i = 0; (i < 100) && (munk != 0.0); i++) {
878  memset(&res, 0x00, sizeof(new_XYZW));
879  sinfo_new_bezier(indata, pos - 1, cumstep, munk, &res);
880  distance = sqrt(
881  pow(((*point).x - res.x), 2)
882  + pow(((*point).y - res.y), 2)
883  + pow(((*point).z - res.z), 2));
884  /*sinfo_msg_debug("%lf %lf %lf %lf %lf\n",
885  res.x,res.y,res.z,res.w,distance);*/
886  if (distance < selected_distance) {
887  selected_distance = distance;
888  selected.x = res.x;
889  selected.y = res.y;
890  selected.z = res.z;
891  selected.w = res.w;
892  }
893  cumstep = cumstep + step;
894  munk = pow(1.0 - cumstep, (double) pos - 1);
895 
896  }
897 
898 #ifdef DEBUG
899  sinfo_msg_debug("Selected %lf %lf %lf %lf, distance=%lf",
900  selected.x,selected.y,selected.z,
901  selected.w,selected_distance);
902 #endif
903  i_img = cpl_imagelist_get(im, (*point).z);
904  pidata = cpl_image_get_data_float(i_img);
905  pidata[sinfo_cu_xy(im, (*point).x, (*point).y)] = selected.w;
906 
907  return selected.w;
908 }
909 
910 int
911 sinfo_new_bezier(new_XYZW *p, int n, double mu, double munk, new_XYZW *res)
912 {
913  int k, kn, nn, nkn;
914  double blend, muk;
915 
916  muk = 1;
917  for (k = 0; k <= n; k++) {
918  nn = n;
919  kn = k;
920  nkn = n - k;
921  blend = muk * munk;
922  muk *= mu;
923  munk /= (1.0 - mu);
924  while (nn >= 1) {
925  blend *= (double) nn;
926  nn--;
927  if (kn > 1) {
928  blend /= (double) kn;
929  kn--;
930  }
931  if (nkn > 1) {
932  blend /= (double) nkn;
933  nkn--;
934  }
935  }
936  res->x += p[k].x * blend;
937  res->y += p[k].y * blend;
938  res->z += p[k].z * blend;
939  res->w += p[k].w * blend;
940  }
941  return (0);
942 }
943 
944 int
945 sinfo_new_c_create_XYZ(new_Lookup *l)
946 {
947  cpl_image *imX, *imY, *imZ, *imcX;
948  short i, j, k, indexI, indexJ, x, y, z;
949  int size;
950  int idlx = 0;
951  int idly = 0;
952  int idnp = 0;
953  float* piddata = NULL;
954  float* pjddata = NULL;
955  float* pXdata = NULL;
956  float* pYdata = NULL;
957  float* pZdata = NULL;
958  float* phXdata = NULL;
959 
960  cpl_image* i_img = NULL;
961  cpl_image* j_img = NULL;
962 
963  idlx = cpl_image_get_size_x(cpl_imagelist_get(l->id, 0));
964  idly = cpl_image_get_size_y(cpl_imagelist_get(l->id, 0));
965  idnp = cpl_imagelist_get_size(l->id);
966 
967  size = idlx * idly;
968  /* allocate memory */
969  if (NULL == (imX = cpl_image_new(size, size, CPL_TYPE_FLOAT))) {
970  sinfo_msg_error(" could not allocate memory for X !\n");
971  return -1;
972  }
973  if (NULL == (imY = cpl_image_new(size, size, CPL_TYPE_FLOAT))) {
974  sinfo_msg_error(" could not allocate memory for Y !\n");
975  return -1;
976  }
977  if (NULL == (imZ = cpl_image_new(size, size, CPL_TYPE_FLOAT))) {
978  sinfo_msg_error(" could not allocate memory for Z !\n");
979  return -1;
980  }
981  if (NULL == (imcX = cpl_image_new(size, size, CPL_TYPE_FLOAT))) {
982  sinfo_msg_error(" could not allocate memory for cX !\n");
983  return -1;
984  }
985 
986  l->X = imX;
987  l->Y = imY;
988  l->Z = imZ;
989  l->hX = imcX;
990 
991  /*Round id*/
992  for (i = 0; i < idlx; i++) {
993  for (j = 0; j < idly; j++) {
994  for (k = 0; k < idnp; k++) {
995  i_img = cpl_imagelist_get(l->id, k);
996  piddata = cpl_image_get_data_float(i_img);
997  piddata[sinfo_cu_xy(l->id, i, j)] = (float) sinfo_new_nint(
998  piddata[sinfo_cu_xy(l->id, i, j)]);
999  }
1000  }
1001  }
1002 
1003  /*Round jd*/
1004  for (i = 0; i < idlx; i++) {
1005  for (j = 0; j < idly; j++) {
1006  for (k = 0; k < idnp; k++) {
1007  j_img = cpl_imagelist_get(l->jd, k);
1008  pjddata = cpl_image_get_data_float(j_img);
1009  pjddata[sinfo_cu_xy(l->jd, i, j)] = (float) sinfo_new_nint(
1010  pjddata[sinfo_cu_xy(l->jd, i, j)]);
1011  }
1012  }
1013  }
1014 
1015  /*Fill with -1 X Y Z*/
1016  for (i = 0; i < cpl_image_get_size_x(l->X); i++) {
1017  for (j = 0; j < cpl_image_get_size_y(l->X); j++) {
1018  pXdata = cpl_image_get_data_float(l->X);
1019  pYdata = cpl_image_get_data_float(l->Y);
1020  pZdata = cpl_image_get_data_float(l->Z);
1021 
1022  pXdata[sinfo_im_xy(l->X, i, j)] = ZERO;
1023  pYdata[sinfo_im_xy(l->Y, i, j)] = ZERO;
1024  pZdata[sinfo_im_xy(l->Z, i, j)] = ZERO;
1025  }
1026  }
1027 #define FORW
1028 #ifdef BACK
1029  for( x = idlx - 1;x>=0;x--)
1030  {
1031  for( y = idly - 1;y>=0;y--)
1032  {
1033  for( z = idnp - 1;z>=0;z--)
1034 #endif
1035 #ifdef FORW
1036  for (x = 0; x < idlx; x++) {
1037  for (y = 0; y < idly; y++) {
1038  for (z = 0; z < idnp; z++)
1039 #endif
1040  {
1041  i_img = cpl_imagelist_get(l->id, z);
1042  piddata = cpl_image_get_data_float(i_img);
1043  j_img = cpl_imagelist_get(l->jd, z);
1044  pjddata = cpl_image_get_data_float(j_img);
1045  indexI = piddata[sinfo_cu_xy(l->id, x, y)];
1046  indexJ = pjddata[sinfo_cu_xy(l->jd, x, y)];
1047  if (indexI > 0.0 && indexI < size && indexJ > 0.0
1048  && indexJ < size) {
1049  /*sinfo_msg_debug("%d %d %d = %f, %f\n",
1050  x,y,z,(float)ICube(x,y,z),(float)JCube(x,y,z));*/
1051  pXdata = cpl_image_get_data_float(l->X);
1052  pYdata = cpl_image_get_data_float(l->Y);
1053  pZdata = cpl_image_get_data_float(l->Z);
1054  phXdata = cpl_image_get_data_float(l->hX);
1055 
1056  pXdata[sinfo_im_xy(l->X, indexI, indexJ)] = x;
1057  phXdata[sinfo_im_xy(l->hX, indexI, indexJ)] =
1058  phXdata[sinfo_im_xy(l->hX, indexI, indexJ)]
1059  + 1;
1060 
1061  pYdata[sinfo_im_xy(l->Y, indexI, indexJ)] = y;
1062  /*phXdata[sinfo_im_xy(l->hX,indexI,indexJ)] =
1063  phXdata[sinfo_im_xy(l->hX,indexI,indexJ)] + 1;*/
1064 
1065  pZdata[sinfo_im_xy(l->Z, indexI, indexJ)] = z;
1066  /*phXdata[sinfo_im_xy(l->hX,indexI,indexJ)] =
1067  phXdata[sinfo_im_xy(l->hX,indexI,indexJ)] + 1;*/
1068  }
1069  }
1070  }
1071  }
1072 
1073  sinfo_msg("Filled X Y Z , cX cY cZ 2D frames\n");
1074  return (0);
1075 }
1076 
1082 new_Lookup *
1083 sinfo_new_lookup(void)
1084 {
1085  new_Lookup *l;
1086  l = (new_Lookup*) cpl_calloc(1, sizeof(new_Lookup));
1087  return (l);
1088 }
1095 void
1096 sinfo_new_destroy_lookup(new_Lookup *l)
1097 {
1098  if (l)
1099  cpl_free(l);
1100 }
1108 int
1109 sinfo_new_change_mask(cpl_image * mask, cpl_image * im)
1110 {
1111  int i;
1112  //int mlx=0;
1113  //int mly=0;
1114  int ilx = 0;
1115  int ily = 0;
1116  float* pidata = NULL;
1117  float* pmdata = NULL;
1118 
1119  if (mask == NULL || im == NULL )
1120  return -1;
1121  ilx = cpl_image_get_size_x(im);
1122  ily = cpl_image_get_size_y(im);
1123  pidata = cpl_image_get_data_float(im);
1124 
1125  //mlx=cpl_image_get_size_x(mask);
1126  //mly=cpl_image_get_size_y(mask);
1127  pmdata = cpl_image_get_data_float(mask);
1128 
1129  for (i = 0; i < (int) ilx * ily; i++) {
1130  if (isnan(pidata[i])) {
1131  pmdata[i] = 0.;
1132  }
1133  }
1134  return 0;
1135 }
1136 
1153 cpl_image *
1154 sinfo_new_c_bezier_find_cosmic(cpl_image *im, cpl_image *mask, new_Lookup *look,
1155  short rx, short ry, short rz, short lowerI,
1156  short highI, short lowerJ, short highJ,
1157  float factor)
1158 {
1159 
1160  int i, j, count;
1161  cpl_imagelist * sc_im, *drs_sc_mask;
1162  short szx, szy, szz;
1163  float /*ant,*/newValue, old/*,dif,porcentage,distance*/;
1164  double med, stdev;
1165  /*cpl_image *out;*/
1166  short rx_loop, ry_loop, rz_loop;
1167 
1168  cpl_image* o_img = NULL;
1169  //float* pmdata=NULL;
1170  float* pidata = NULL;
1171 
1172  int ilx = 0;
1173  int ily = 0;
1174 
1175  int mlx = 0;
1176  int mly = 0;
1177 
1178  mlx = cpl_image_get_size_x(mask);
1179  mly = cpl_image_get_size_y(mask);
1180  //pmdata=cpl_image_get_data_float(mask);
1181 
1182  ilx = cpl_image_get_size_x(im);
1183  ily = cpl_image_get_size_y(im);
1184  pidata = cpl_image_get_data_float(im);
1185 
1186  if (mlx != ilx || mly != ily) {
1187  sinfo_msg_error(" data & mask images not compatible in size\n");
1188  return NULL ;
1189  }
1190 
1191  /* allocate memory for sub cubes*/
1192  szx = (rx * 2) + 1;
1193  szy = (ry * 2) + 1;
1194  szz = (rz * 2) + 1;
1195 
1196  if (NULL == (sc_im = cpl_imagelist_new())) {
1197  sinfo_msg_error(" could not allocate memory for data subcube\n");
1198  return NULL ;
1199  }
1200  for (i = 0; i < szz; i++) {
1201  o_img = cpl_image_new(szx, szy, CPL_TYPE_FLOAT);
1202  cpl_imagelist_set(sc_im, o_img, i);
1203  }
1204 
1205  if (NULL == (drs_sc_mask = cpl_imagelist_new())) {
1206  sinfo_msg_error(" could not allocate memory for mask subcube\n");
1207  return NULL ;
1208  }
1209 
1210  for (i = 0; i < szz; i++) {
1211  o_img = cpl_image_new(szx, szy, CPL_TYPE_FLOAT);
1212  cpl_imagelist_set(drs_sc_mask, o_img, i);
1213  }
1214 
1215  count = 0;
1216  for (i = 0; i < mlx; i++) {
1217  for (j = 0; j < mly; j++) {
1218  if (i >= lowerI && i < highI && j >= lowerJ && j < highJ) {
1219 
1220  rx_loop = 1;
1221  ry_loop = 1;
1222  rz_loop = 1;
1223  newValue = sinfo_new_c_bezier_correct_cosmic(i, j, im, mask,
1224  sc_im, drs_sc_mask, look, rx_loop, ry_loop,
1225  rz_loop, &med, &stdev, factor);
1226  /* if no valid neighboors are found, increase size of
1227  sub cube until max radius is reached */
1228  while (newValue == cubeNONEIGHBOR && rx_loop < rx
1229  && ry_loop < ry && rz_loop < rz) {
1230  rx_loop++;
1231  ry_loop++;
1232  rz_loop++;
1233  /*sinfo_msg_debug("Increasing radius to %d, in %d %d",
1234  rx_loop, i, j) ; */
1235  newValue = sinfo_new_c_bezier_correct_cosmic(i, j, im, mask,
1236  sc_im, drs_sc_mask, look, rx_loop, ry_loop,
1237  rz_loop, &med, &stdev, factor);
1238  }
1239  /*give up on increasing the size*/
1240  if (isnan(newValue) || newValue == cubeNONEIGHBOR)
1241  /*<= -3.e10 ZERO )*/
1242  continue;
1243 
1244  old = pidata[sinfo_im_xy(im, i, j)];
1245  if (newValue != old) {
1246  pidata[sinfo_im_xy(im, i, j)] = newValue;
1247  /*sinfo_msg_debug("[%d,%d]=%f -> %f, med= %f, stdev=%f",
1248  i,j, old, newValue, med, stdev ); */
1249  count++;
1250  }
1251  }
1252  }
1253  }
1254 
1255  sinfo_msg_debug("bad pixels count: %d", count);
1256 
1257  cpl_imagelist_delete(sc_im);
1258  cpl_imagelist_delete(drs_sc_mask);
1259  return im;
1260 }
1261 
1279 float
1280 sinfo_new_c_bezier_correct_cosmic(int ipos, int jpos, cpl_image * im,
1281  cpl_image * mask, cpl_imagelist * sc_im,
1282  cpl_imagelist * drs_sc_mask,
1283  new_Lookup * look, short rx, short ry,
1284  short rz, double *med, double *stdev,
1285  float factor)
1286 {
1287  short ic, jc, kc, ii, jj, kk/*, sjj, skk*/, is, js, ks;
1288  short i, j, k, indexJ, indexI, lx, ly, lz, szx, szy, szz;
1289  /*float indexIf,indexJf,sp;*/
1290  cpl_image * X, *Y, *Z, *hX;
1291  cpl_imagelist * id, *jd;
1292  short counter;
1293  double sum;
1294  float* phXdata = NULL;
1295  float* pXdata = NULL;
1296  float* pYdata = NULL;
1297  float* pZdata = NULL;
1298 
1299  float* pimdata = NULL;
1300  float* pscdata = NULL;
1301  float* pdrsdata = NULL;
1302  float* piddata = NULL;
1303  float* pjddata = NULL;
1304  float* pmaskdata = NULL;
1305 
1306  int idlx = 0;
1307  int idly = 0;
1308  int idnp = 0;
1309 
1310  int drslx = 0;
1311  int drsly = 0;
1312  int drsnp = 0;
1313 
1314  X = look->X;
1315  Y = look->Y;
1316  Z = look->Z;
1317  hX = look->hX;
1318  id = look->id;
1319  jd = look->jd;
1320 
1321  phXdata = cpl_image_get_data_float(hX);
1322  /*if ( phXdata[sinfo_im_xy( hX, ipos, jpos)] > 1 )
1323  {
1324  sinfo_msg_error("double hit in position [%d,%d]=%f, can not correct",
1325  ipos,jpos,phXdata[sinfo_im_xy(hX,ipos,jpos)]) ;
1326  return ( -2e10 );
1327  }*/
1328  if (phXdata[sinfo_im_xy(hX, ipos, jpos)] < 1) {
1329  /*sinfo_msg_error("no lookup in position [%d,%d]=%f, can not correct",
1330  ipos,jpos,phXdata[sinfo_im_xy(hX,ipos,jpos)]) ;*/
1331  return ( ZERO);
1332  }
1333 
1334  pXdata = cpl_image_get_data_float(X);
1335  pYdata = cpl_image_get_data_float(Y);
1336  pZdata = cpl_image_get_data_float(Z);
1337 
1338  ic = pXdata[sinfo_im_xy(X, ipos, jpos)];
1339  jc = pYdata[sinfo_im_xy(Y, ipos, jpos)];
1340  kc = pZdata[sinfo_im_xy(Z, ipos, jpos)];
1341  /*if ( !(ipos % 16 ) )*/
1342 #ifdef DEBUG
1343  sinfo_msg_debug("Correcting bad pixel : ipos=%d,jpos=%d, "
1344  "in Cube -> ic=%d, jc=%d, kc=%d", ipos,jpos, ic, jc, kc );
1345 #endif
1346  /*limit to start not before the beginning of the cube*/
1347  ii = ic - rx;
1348  if (ii < 0)
1349  ii = 0;
1350  jj = jc - ry;
1351  if (jj < 0)
1352  jj = 0;
1353  kk = kc - rz;
1354  if (kk < 0)
1355  kk = 0;
1356 
1357 #ifdef DEBUG
1358  sinfo_msg_debug("Start Point in Cube -> ii=%d,jj=%d,kk=%d", ii, jj, kk );
1359 #endif
1360 
1361  /*limit to end not outside of the cube */
1362  szx = (rx * 2) + 1;
1363  szy = (ry * 2) + 1;
1364  szz = (rz * 2) + 1;
1365 
1366  idlx = cpl_image_get_size_x(cpl_imagelist_get(id, 0));
1367  idly = cpl_image_get_size_y(cpl_imagelist_get(id, 0));
1368  idnp = cpl_imagelist_get_size(id);
1369 
1370  lx = idlx;
1371  ly = idly;
1372  lz = idnp;
1373  if ((ic + rx) >= idlx)
1374  szx = szx - ((ic + rx) - (lx - 1));
1375 
1376  if ((jc + ry) >= idly)
1377  szy = szy - ((jc + ry) - (ly - 1));
1378 
1379  if ((kc + rz) >= idnp)
1380  szz = szz - ((kc + rz) - (lz - 1));
1381 
1382 #ifdef DEBUG
1383  sinfo_msg_error("Size of subcube : szx=%d,szy=%d,szz=%d\n", szx, szy, szz );
1384  /*fill whole mask with not available*/
1385  drsnp=cpl_imagelist_get_size(drs_sc_mask);
1386  drslx=cpl_image_get_size_x(cpl_imagelist_get(drs_sc_mask,0));
1387  drsly=cpl_image_get_size_y(cpl_imagelist_get(drs_sc_mask,0));
1388 
1389  sinfo_msg_error("Fill Mask subcube of size: %d,%d,%d, with NOINFO",
1390  drslx, drsly, drsnp);
1391 #endif
1392  for (i = 0; i < drslx; i++) {
1393  for (j = 0; j < drsly; j++) {
1394  for (k = 0; k < drsnp; k++) {
1395  pdrsdata = cpl_image_get_data_float(
1396  cpl_imagelist_get(drs_sc_mask, k));
1397  pdrsdata[sinfo_cu_xy(drs_sc_mask, i, j)] = cubePT_NOINFO;
1398  }
1399  }
1400  }
1401  pimdata = cpl_image_get_data_float(im);
1402  pmaskdata = cpl_image_get_data_float(mask);
1403  for (i = ii, is = 0; i < ii + szx; i++, is++) {
1404  for (j = jj, js = 0; j < jj + szy; j++, js++) {
1405  for (k = kk, ks = 0; k < kk + szz; k++, ks++) {
1406 #ifdef DEBUG
1407  sinfo_msg_debug("i=%d j=%d k=%d is=%d ij=%d ik=%d",
1408  i,j,k,is,js,ks);
1409 #endif
1410  piddata = cpl_image_get_data_float(cpl_imagelist_get(id, k));
1411  pjddata = cpl_image_get_data_float(cpl_imagelist_get(id, k));
1412  pdrsdata = cpl_image_get_data_float(
1413  cpl_imagelist_get(drs_sc_mask, ks));
1414  pscdata = cpl_image_get_data_float(
1415  cpl_imagelist_get(sc_im, ks));
1416 
1417  indexI = sinfo_new_nint(piddata[sinfo_cu_xy(id, i, j)]);
1418  indexJ = sinfo_new_nint(pjddata[sinfo_cu_xy(jd, i, j)]);
1419  if (indexJ <= -1 || indexJ >= 2048 || indexI == -1) {
1420  pdrsdata[sinfo_cu_xy(drs_sc_mask, is, js)] = cubePT_NOINFO;
1421  continue;
1422  }
1423  pscdata[sinfo_cu_xy(sc_im, is, js)] = pimdata[sinfo_im_xy(im,
1424  indexI, indexJ)];
1425  pdrsdata[sinfo_cu_xy(drs_sc_mask, is, js)] =
1426  pmaskdata[sinfo_im_xy(mask, indexI, indexJ)];
1427 #ifdef DEBUG
1428  sinfo_msg_debug("Cube i=%d, j=%d, k=%d ; "
1429  " Sub is=%d, js=%d, ks=%d ; "
1430  " Plane I=%d,J=%d ; mask %f ; im %f\n",
1431  i, j, k, is, js, ks, indexI, indexJ,
1432  pmaskdata[sinfo_im_xy(mask,indexI,indexJ)],
1433  pimdata[sinfo_im_xy(im,indexI,indexJ)]);
1434 #endif
1435 
1436  }
1437  }
1438  }
1439 
1440  /* ignoring the elements in the slitlet of the tested pixel */
1441 
1442  for (i = 0; i < szx; i++) {
1443  for (k = 0; k < szz; k++) {
1444  pdrsdata = cpl_image_get_data_float(
1445  cpl_imagelist_get(drs_sc_mask, k));
1446  pdrsdata[sinfo_cu_xy(drs_sc_mask, i, ry)] = cubePT_NOINFO;
1447  }
1448  }
1449  /* now calculate mean and stdev in subcube */
1450 
1451  counter = 0;
1452  sum = 0;
1453  for (i = 0; i < szx; i++) {
1454  for (j = 0; j < szy; j++) {
1455  for (k = 0; k < szz; k++) {
1456  pdrsdata = cpl_image_get_data_float(
1457  cpl_imagelist_get(drs_sc_mask, k));
1458  pscdata = cpl_image_get_data_float(cpl_imagelist_get(sc_im, k));
1459  if (pscdata[sinfo_cu_xy(sc_im, i, j)] != ZERO
1460  && pdrsdata[sinfo_cu_xy(drs_sc_mask, i, j)]
1461  != cubePT_NOINFO) {
1462  sum = sum + pscdata[sinfo_cu_xy(sc_im, i, j)];
1463  counter++;
1464  }
1465  }
1466  }
1467  }
1468 
1469  *med = sum / counter;
1470 
1471  counter = 0;
1472  sum = 0;
1473  for (i = 0; i < szx; i++) {
1474  for (j = 0; j < szy; j++) {
1475  for (k = 0; k < szz; k++) {
1476  pscdata = cpl_image_get_data_float(cpl_imagelist_get(sc_im, k));
1477  pdrsdata = cpl_image_get_data_float(
1478  cpl_imagelist_get(drs_sc_mask, k));
1479  if (pscdata[sinfo_cu_xy(sc_im, i, j)] != ZERO
1480  && pdrsdata[sinfo_cu_xy(drs_sc_mask, i, j)]
1481  != cubePT_NOINFO) {
1482  sum = sum + (pscdata[sinfo_cu_xy(
1483  sc_im, i, j)]
1484  - *med)
1485  * (pscdata[sinfo_cu_xy(
1486  sc_im,
1487  i,
1488  j)]
1489  - *med);
1490  counter++;
1491  }
1492  }
1493  }
1494  }
1495 
1496  *stdev = sqrt(sum / (counter - 1));
1497 
1498  if ((fabs(pimdata[sinfo_im_xy(im, ipos, jpos)] - *med) > factor * *stdev)
1499  || isnan(pimdata[sinfo_im_xy(im,ipos,jpos)])) {
1500  pdrsdata = cpl_image_get_data_float(cpl_imagelist_get(drs_sc_mask, rz));
1501  pdrsdata[sinfo_cu_xy(drs_sc_mask, rx, ry)] = cubePT_FIND;
1502  return (sinfo_new_c_bezier_interpol(sc_im, drs_sc_mask));
1503  }
1504  else
1505  return (pimdata[sinfo_im_xy(im, ipos, jpos)]);
1506 
1507 }
1508