36#include "catalogue/casu_utils.h"
37#include "catalogue/casu_fits.h"
38#include "casu_stats.h"
47#define DATAMIN -1000.0
48#define DATAMAX 65535.0
62static void twodfilt(
float *data,
unsigned char *bpm,
int nx,
int ny,
63 int medfilt,
int linfilt,
int niter,
int axis,
64 int twod,
int takeout_sky,
int inorm,
int wantback,
65 float signeg,
float sigpos,
float **backmap);
66static void bfilt_1d(
float *data,
unsigned char *bpm,
int nx,
int ny,
67 int filt,
int stat,
int axis);
68static void bfilt_2d(
float *data,
unsigned char *bpmcopy,
int nx,
int ny,
70static void docols_2(
float *data,
unsigned char *bpm,
float *dbuf,
71 unsigned char *bbuf,
int nx,
int ny,
int filter,
73static void dorows_2(
float *data,
unsigned char *bpm,
float *dbuf,
74 unsigned char *bbuf,
int nx,
int ny,
int filter,
76static void dostat(
float *data,
unsigned char *bpm,
unsigned char *goodval,
77 int npts,
int nfilt,
int whichstat);
78static void wraparound(
float *data,
unsigned char *bpm,
int npts,
int nfilt,
79 int whichstat,
float **ybuf,
unsigned char **ybbuf,
81static void medavg(
float *array,
unsigned char *bpm,
int *ipoint,
int npix,
82 int whichstat,
int newl, nextlast *nl,
float *outval,
83 unsigned char *outbp);
84static void quickie(
float *array,
unsigned char *iarray,
int *iarray2,
86static void sortm(
float *a1,
unsigned char *a2,
int *a3,
int n);
87static void plugholes(
float *data,
unsigned char *bpm,
int nx);
154 int linfilt,
int niter,
int axis,
int twod,
155 int takeout_sky,
int norm,
int wantback,
156 float signeg,
float sigpos, casu_fits **backmap,
160 float *data,*backdata,*bdata;
163 const char *fctid =
"casu_nebuliser";
168 if (*status != CASU_OK)
174 nx = cpl_image_get_size_x(im);
175 ny = cpl_image_get_size_y(im);
176 data = cpl_image_get_data_float(im);
182 bpm = cpl_calloc(npts,
sizeof(
unsigned char));
183 if (inconf != NULL) {
185 if (cpl_image_get_size_x(im) != nx || cpl_image_get_size_y(im) != ny) {
186 cpl_msg_error(fctid,
"Image and conf map dimensions don't match");
190 cdata = cpl_image_get_data(im);
191 for (i = 0; i < npts; i++)
192 bpm[i] = (cdata[i] == 0);
197 twodfilt(data,bpm,nx,ny,medfilt,linfilt,niter,axis,twod,takeout_sky,norm,
198 wantback,signeg,sigpos,&backdata);
204 "ESO DRS NEBULISED",1);
207 "Nebuliser has been used on this image");
215 bdata = cpl_image_get_data_float(im);
216 memmove(bdata,backdata,npts*
sizeof(
float));
274static void twodfilt(
float *data,
unsigned char *bpm,
int nx,
int ny,
275 int medfilt,
int linfilt,
int niter,
int axis,
276 int twod,
int takeout_sky,
int inorm,
int wantback,
277 float signeg,
float sigpos,
float **backmap) {
278 int i,iter,nter,nmask;
280 float *buffer,*orig,*orig_sm,*work,medsky,sigsky,rescale,lthr,hthr;
282 unsigned char *bpmcopy;
288 buffer = cpl_malloc(3*nn*
sizeof(*buffer));
292 memmove((
char *)orig,(
char *)data,nn*
sizeof(*data));
293 memmove((
char *)orig_sm,(
char *)data,nn*
sizeof(*data));
294 memmove((
char *)work,(
char *)data,nn*
sizeof(*data));
299 bpmcopy = cpl_calloc(nn,
sizeof(*bpmcopy));
300 for (i = 0; i < nn; i++)
301 bpmcopy[i] = (bpm[i] ? 1 : 0);
305 if (niter > 1 && medfilt > 10) {
306 bfilt_1d(orig_sm,bpmcopy,nx,ny,5,MEDIANCALC,axis);
307 bfilt_1d(orig_sm,bpmcopy,nx,ny,3,MEANCALC,axis);
312 for (iter = 1; iter <= niter; iter++) {
314 memmove((
char *)data,(
char *)orig,nn*
sizeof(*data));
320 bfilt_1d(data,bpmcopy,nx,ny,medfilt,MEDIANCALC,axis);
322 bfilt_2d(data,bpmcopy,nx,ny,medfilt,MEDIANCALC);
329 for (i = 0; i < nn; i++)
330 work[i] = orig_sm[i] - data[i];
335 casu_qmedsig(work,bpmcopy,nn,3.0,3,DATAMIN,DATAMAX,&medsky,&sigsky);
338 while (sigsky < 2.5 && nter < 16) {
340 for (i = 0; i < nn; i++)
342 casu_qmedsig(work,bpmcopy,nn,3.0,3,DATAMIN,DATAMAX,&medsky,
346 rescale = (float)pow(2.0,(
double)nter);
347 for (i = 0; i < nn; i++)
352 lthr = -signeg*sigsky;
353 hthr = sigpos*sigsky;
358 for (i = 0; i < nn; i++) {
361 diff = work[i] - medsky;
362 if (diff > hthr || diff < lthr) {
374 bfilt_1d(data,bpm,nx,ny,linfilt,MEANCALC,axis);
376 bfilt_2d(data,bpm,nx,ny,linfilt,MEANCALC);
381 casu_qmedsig(orig,bpmcopy,nn,3.0,3,DATAMIN,DATAMAX,&medsky,&sigsky);
388 *backmap = cpl_malloc(nn*
sizeof(**backmap));
389 for (i = 0; i < nn; i++)
390 (*backmap)[i] = data[i];
398 for (i = 0; i < nn; i++)
399 data[i] = orig[i] - data[i] + medsky;
401 for (i = 0; i < nn; i++)
402 data[i] = orig[i]/max(1.0,data[i]);
441static void bfilt_1d(
float *data,
unsigned char *bpm,
int nx,
int ny,
442 int filt,
int stat,
int axis) {
451 dbuf = cpl_malloc(nbuf*
sizeof(*dbuf));
452 bbuf = cpl_malloc(nbuf*
sizeof(*bbuf));
458 dorows_2(data,bpm,dbuf,bbuf,nx,ny,filt,stat);
459 docols_2(data,bpm,dbuf,bbuf,nx,ny,filt,stat);
461 docols_2(data,bpm,dbuf,bbuf,nx,ny,filt,stat);
462 dorows_2(data,bpm,dbuf,bbuf,nx,ny,filt,stat);
498static void bfilt_2d(
float *data,
unsigned char *bpmcopy,
int nx,
int ny,
499 int filt,
int stat) {
500 float *dbuf,*outmap,value,*om;
501 unsigned char *outbpm,*ob;
502 int nbuf,j,i,nf2,nalloc,jj,ii,ind,ind1,j1old,j2old,i1old,i2old;
510 nalloc = (2*filt+1)*(2*filt+1);
511 dbuf = cpl_malloc(nalloc*
sizeof(*dbuf));
512 outmap = cpl_malloc(nx*ny*
sizeof(*outmap));
513 outbpm = cpl_malloc(nx*ny*
sizeof(*outbpm));
517 for (j = 0; j < ny; j++) {
518 for (i = 0; i < nx; i++) {
520 for (jj = j - nf2; jj <= j + nf2; jj++) {
521 if (jj < 0 || jj >= ny)
524 for (ii = i - nf2; ii <= i + nf2; ii++) {
525 if (ii < 0 || ii >= nx)
530 dbuf[nbuf++] = data[ind];
542 for (jj = j - filt; jj <= j + filt; jj++) {
543 if (jj < 0 || jj >= ny || (jj >= j1old && jj <= j2old))
546 for (ii = i - filt; ii <= i + filt; ii++) {
547 if (ii < 0 || ii >= nx || (ii >= i1old && ii <= i2old))
552 dbuf[nbuf++] = data[ind];
562 if (stat == MEDIANCALC)
563 value =
casu_med(dbuf,NULL,(
long)nbuf);
569 outmap[ind] = -1000.0;
578 for (j = 0; j < ny; j++) {
582 for (i = 0; i < nx; i++)
583 data[j*nx+i] = om[i];
627static void docols_2(
float *data,
unsigned char *bpm,
float *dbuf,
628 unsigned char *bbuf,
int nx,
int ny,
int filter,
632 unsigned char *goodval,*b;
638 goodval = cpl_malloc(ny*
sizeof(*goodval));
639 t = cpl_malloc(ny*
sizeof(*t));
640 b = cpl_malloc(ny*
sizeof(*b));
641 for (k = 0; k < nx; k++) {
642 memset((
char *)goodval,0,ny);
644 for (j = 0; j < ny; j++) {
646 if (bpm[indx] == 0) {
647 dbuf[nn] = data[indx];
651 dostat(dbuf,bbuf,goodval,nn,filter,stat);
653 for (j = 0; j < ny; j++) {
655 if (bpm[indx] == 0) {
665 for (j = 0; j < ny; j++) {
708static void dorows_2(
float *data,
unsigned char *bpm,
float *dbuf,
709 unsigned char *bbuf,
int nx,
int ny,
int filter,
713 unsigned char *goodval,*b;
719 goodval = cpl_malloc(nx*
sizeof(*goodval));
720 t = cpl_malloc(nx*
sizeof(*t));
721 b = cpl_malloc(nx*
sizeof(*b));
722 for (k = 0; k < ny; k++) {
723 memset((
char *)goodval,0,nx);
725 for (j = 0; j < nx; j++) {
729 dbuf[nn] = data[indx];
732 dostat(dbuf,bbuf,goodval,nn,filter,stat);
734 for (j = 0; j < nx; j++) {
736 if (bpm[indx] == 0) {
745 for (j = 0; j < nx; j++) {
785static void dostat(
float *data,
unsigned char *bpm,
unsigned char *goodval,
786 int npts,
int nfilt,
int whichstat) {
787 int nbuf,jl,jh,j,*ipoint,ifree,i;
788 unsigned char *ybbuf,*barray,bval;
790 float *ybuf,*darray,val;
794 if (npts < nfilt || npts < 10)
799 if ((nfilt/2)*2 == nfilt)
804 wraparound(data,bpm,npts,nfilt,whichstat,&ybuf,&ybbuf,&nbuf);
808 darray = cpl_malloc(nfilt*
sizeof(*darray));
809 barray = cpl_malloc(nfilt*
sizeof(*barray));
810 ipoint = cpl_malloc(nfilt*
sizeof(*ipoint));
811 memmove((
char *)darray,(
char *)ybuf,nfilt*
sizeof(*ybuf));
812 memmove((
char *)barray,(
char *)ybbuf,nfilt*
sizeof(*ybbuf));
813 for (j = 0; j < nfilt; j++)
816 medavg(darray,barray,ipoint,nfilt,whichstat,-1,&nl,&val,&bval);
821 jh = nfilt + npts - 2;
822 for (j = jl; j <= jh; j++) {
823 for (i = 0; i < nfilt; i++) {
824 if (ipoint[i] == 0) {
826 ipoint[i] = nfilt - 1;
827 nl.lastval = darray[ifree];
830 if (barray[ifree] == 0) {
834 darray[ifree] = ybuf[j];
835 barray[ifree] = ybbuf[j];
836 nl.nextval = darray[ifree];
839 if (barray[ifree] == 0) {
846 medavg(darray,barray,ipoint,nfilt,whichstat,ifree,&nl,&val,&bval);
849 goodval[j-jl+1] = bval;
893static void wraparound(
float *data,
unsigned char *bpm,
int npts,
int nfilt,
894 int whichstat,
float **ybuf,
unsigned char **ybbuf,
897 float *darray,xmns,xmnf;
898 int i1,ilow,i,*ipoint;
899 unsigned char *barray,bxmns,bxmnf;
905 ilow = max(3,nfilt/4);
906 ilow = (ilow/2)*2 + 1;
910 darray = cpl_malloc(nfilt*
sizeof(*darray));
911 barray = cpl_malloc(nfilt*
sizeof(*barray));
912 ipoint = cpl_calloc(nfilt,
sizeof(*ipoint));
914 *ybuf = cpl_malloc(*nbuf*
sizeof(
float));
915 *ybbuf = cpl_malloc(*nbuf*
sizeof(
unsigned char));
919 memmove((
char *)darray,(
char *)data,ilow*
sizeof(*data));
920 memmove((
char *)barray,(
char *)bpm,ilow*
sizeof(*bpm));
921 medavg(darray,barray,ipoint,ilow,whichstat,-1,&nl,&xmns,&bxmns);
922 memmove((
char *)darray,(
char *)(data+npts-ilow),ilow*
sizeof(*data));
923 memmove((
char *)barray,(
char *)(bpm+npts-ilow),ilow*
sizeof(*bpm));
924 medavg(darray,barray,ipoint,ilow,whichstat,-1,&nl,&xmnf,&bxmnf);
925 for (i = 0; i < i1; i++) {
927 (*ybuf)[i] = 2.0*xmns - data[i1+ilow-i-1];
928 (*ybbuf)[i] = bpm[i1+ilow-i-1];
930 (*ybuf)[i] = data[i1+ilow-i-1];
934 (*ybuf)[npts+i1+i] = 2.0*xmnf - data[npts-i-ilow-1];
935 (*ybbuf)[npts+i1+i] = bpm[npts-i-ilow-1];
937 (*ybuf)[npts+i1+i] = data[npts-i-ilow-1];
938 (*ybbuf)[npts+i1+i] = 1;
944 memmove((
char *)(*ybuf+i1),data,npts*
sizeof(*data));
945 memmove((
char *)(*ybbuf+i1),bpm,npts*
sizeof(*bpm));
988static void medavg(
float *array,
unsigned char *bpm,
int *ipoint,
int npix,
989 int whichstat,
int newl, nextlast *nl,
float *outval,
990 unsigned char *outbp) {
999 if (whichstat == MEDIANCALC) {
1001 sortm(array,bpm,ipoint,npix);
1003 quickie(array,bpm,ipoint,newl,npix);
1007 buf = cpl_malloc(npix*
sizeof(*buf));
1012 for (i = 0; i < npix; i++) {
1018 }
else if (whichstat == MEANCALC) {
1023 for (i = 0; i < npix; i++) {
1025 nl->sum += array[i];
1032 nl->sum += (nl->nextw*nl->nextval - nl->lastw*nl->lastval);
1033 nl->sumw += (nl->nextw - nl->lastw);
1034 nl->naver += (nl->nextc - nl->lastc);
1044 if (whichstat == MEDIANCALC)
1050 if (whichstat == MEDIANCALC) {
1053 }
else if (whichstat == MEANCALC)
1054 *outval = (nl->sum)/(nl->sumw);
1087static void quickie(
float *array,
unsigned char *iarray,
int *iarray2,
1088 int lll,
int narray) {
1098 for (i = 0; i < narray; i++) {
1099 if (i != lll && test <= array[i]) {
1111 for (i = 0; i < npt; i++) {
1112 array[lll-i] = array[lll-i-1];
1113 iarray[lll-i] = iarray[lll-i-1];
1114 iarray2[lll-i] = iarray2[lll-i-1];
1123 for (i = 0; i < npt; i++) {
1124 array[lll+i] = array[lll+i+1];
1125 iarray[lll+i] = iarray[lll+i+1];
1126 iarray2[lll+i] = iarray2[lll+i+1];
1159static void sortm(
float *a1,
unsigned char *a2,
int *a3,
int n) {
1160 int iii,ii,i,ifin,j,b3;
1167 iii = min(n,(3*iii)/4 - 1);
1172 for (ii = 0; ii < ifin; ii++) {
1175 if (a1[i] > a1[j]) {
1185 if (i < 0 || a1[i] <= b1)
1218static void plugholes(
float *data,
unsigned char *bpm,
int nx) {
1219 int i,ifirst,ilast,i1,i2,j;
1220 float nc,d1,d2,t1,t2,slope;
1225 while (i < nx && bpm[i] != 0)
1237 while (i >= 0 && bpm[i] != 0)
1245 while (i <= ilast) {
1254 nc = (float)(i2 - i1 + 1);
1257 for (j = i1+1; j <= i2-1; j++) {
1258 t1 = 1.0 - (float)(j - i1)/nc;
1260 data[j] = t1*d1 + t2*d2;
1267 slope = data[ifirst+1] - data[ifirst];
1268 for (j = 0; j < ifirst; j++)
1269 data[j] = slope*(
float)(j - ifirst) + data[ifirst];
1274 if (ilast < nx - 1) {
1275 slope = data[ilast] - data[ilast-1];
1276 for (j = ilast; j < nx; j++)
1277 data[j] = slope*(
float)(j - ilast) + data[ilast];
cpl_image * casu_fits_get_image(casu_fits *p)
casu_fits * casu_fits_duplicate(casu_fits *in)
cpl_propertylist * casu_fits_get_ehu(casu_fits *p)
int casu_nebuliser(casu_fits *infile, casu_fits *inconf, int medfilt, int linfilt, int niter, int axis, int twod, int takeout_sky, int norm, int wantback, float signeg, float sigpos, casu_fits **backmap, int *status)
Remove small scale background variations.
float casu_med(float *data, unsigned char *bpm, long npts)
void casu_qmedsig(float *data, unsigned char *bpm, long npts, float thresh, int niter, float lowv, float highv, float *median, float *sigma)
float casu_mean(float *data, unsigned char *bpm, long npts)