4
*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8
* Author: E.BERTIN (IAP)
10
* Contents: functions dealing with background computation.
12
* Last modify: 25/08/2010
14
*%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
32
#include "fits/fitscat.h"
39
/******************************** make_back **********************************/
41
Background maps are established from the images themselves; thus we need to
42
make at least one first pass through the data.
44
void make_back(fieldstruct *field, fieldstruct *wfield, int wscale_flag)
47
backstruct *backmesh,*wbackmesh, *bm,*wbm;
48
tabstruct *tab, *wtab;
49
PIXTYPE *buf,*wbuf, *buft,*wbuft;
50
size_t bufsize, bufsize2,
51
bufshift, size,meshsize,jumpsize;
52
off_t fcurpos,wfcurpos, wfcurpos2,fcurpos2;
53
int i,j,k,m,n, step, nlines,
56
float *ratio,*ratiop, *weight, *sigma,
59
/* If the weight-map is not an external one, no stats are needed for it */
60
if (wfield && (wfield->flags&BACKRMS_FIELD))
66
wtab = NULL; /* to avoid gcc -Wall warnings */
74
NFPRINTF(OUTPUT, "Setting up background maps");
76
/* Decide if it is worth displaying progress each 16 lines */
78
lflag = (field->width*field->backh >= (size_t)65536);
80
/* Save current positions in files */
82
wfcurpos = wfcurpos2 = 0; /* to avoid gcc -Wall warnings */
83
QFSEEK(tab->cat->file, tab->bodypos, SEEK_SET, field->filename);
84
QFTELL(fcurpos, tab->cat->file, field->filename);
87
QFSEEK(wtab->cat->file, wtab->bodypos, SEEK_SET, wfield->filename);
88
QFTELL(wfcurpos, wtab->cat->file, wfield->filename);
91
/* Allocate a correct amount of memory to store pixels */
93
bufsize = (size_t)w*bh;
96
if (bufsize > (size_t)BACK_BUFSIZE)
98
nlines = BACK_BUFSIZE/w;
99
step = (field->backh-1)/nlines+1;
100
bufsize = (size_t)(nlines = field->backh/step)*w;
101
bufshift = (step/2)*(size_t)w;
102
jumpsize = (step-1)*(size_t)w;
105
bufshift = jumpsize = 0; /* to avoid gcc -Wall warnings */
107
/* Allocate some memory */
108
QMALLOC(backmesh, backstruct, nx); /* background information */
109
QMALLOC(buf, PIXTYPE, bufsize); /* pixel buffer */
111
QMALLOC(field->back, float, nb); /* background map */
112
free(field->backline);
113
QMALLOC(field->backline, PIXTYPE, w); /* current background line */
115
QMALLOC(field->sigma, float, nb); /* sigma map */
118
QMALLOC(wbackmesh, backstruct, nx); /* background information */
119
QMALLOC(wbuf, PIXTYPE, bufsize); /* pixel buffer */
121
QMALLOC(wfield->back, float, nb); /* background map */
123
QMALLOC(wfield->sigma, float, nb); /* sigma map */
124
wfield->sigfac = 1.0;
125
set_weightconv(wfield); /* Prepare conversion */
133
/* Loop over the data packets */
138
"\33[1M> Setting up background map at line:%7d / %-7d\n\33[1A",
139
j*bh, field->height);
142
/*---- The image is small enough so that we can make exhaustive stats */
143
if (j == ny-1 && field->npix%bufsize)
144
bufsize = field->npix%bufsize;
145
read_body(tab, buf, bufsize);
148
read_body(wtab, wbuf, bufsize);
149
weight_to_var(wbuf, bufsize);
151
/*---- Build the histograms */
152
backstat(backmesh, wbackmesh, buf, wbuf, bufsize,nx, w, bw,
153
wfield?wfield->weight_thresh:0.0);
155
for (m=nx; m--; bm++)
156
if (bm->mean <= -BIG)
159
QCALLOC(bm->histo, int, bm->nlevels);
163
for (m=nx; m--; wbm++)
164
if (wbm->mean <= -BIG)
167
QCALLOC(wbm->histo, int, wbm->nlevels);
169
backhisto(backmesh, wbackmesh, buf, wbuf, bufsize,nx, w, bw,
170
wfield?wfield->weight_thresh:0.0);
174
/*---- Image size too big, we have to skip a few data !*/
175
QFTELL(fcurpos2, tab->cat->file, field->filename);
177
QFTELL(wfcurpos2, wtab->cat->file, wfield->filename);
178
if (j == ny-1 && (n=field->height%field->backh))
180
meshsize = n*(size_t)w;
181
nlines = BACK_BUFSIZE/w;
182
step = (n-1)/nlines+1;
183
bufsize = (nlines = n/step)*(size_t)w;
184
bufshift = (step/2)*(size_t)w;
185
jumpsize = (step-1)*(size_t)w;
187
QMALLOC(buf, PIXTYPE, bufsize); /* pixel buffer */
191
QMALLOC(wbuf, PIXTYPE, bufsize); /* pixel buffer */
195
/*---- Read and skip, read and skip, etc... */
196
QFSEEK(tab->cat->file, bufshift*tab->bytepix, SEEK_CUR, field->filename);
198
for (i=nlines; i--; buft += w)
200
read_body(tab, buft, w);
202
QFSEEK(tab->cat->file, jumpsize*tab->bytepix, SEEK_CUR,
208
/*------ Read and skip, read and skip, etc... now on the weight-map */
209
QFSEEK(wtab->cat->file,bufshift*wtab->bytepix, SEEK_CUR,
212
for (i=nlines; i--; wbuft += w)
214
read_body(wtab, wbuft, w);
215
weight_to_var(wbuft, w);
217
QFSEEK(wtab->cat->file, jumpsize*wtab->bytepix, SEEK_CUR,
221
backstat(backmesh, wbackmesh, buf, wbuf, bufsize, nx, w, bw,
222
wfield?wfield->weight_thresh:0.0);
223
QFSEEK(tab->cat->file, fcurpos2, SEEK_SET, field->filename);
225
for (m=nx; m--; bm++)
226
if (bm->mean <= -BIG)
229
QCALLOC(bm->histo, int, bm->nlevels);
232
QFSEEK(wtab->cat->file, wfcurpos2, SEEK_SET, wfield->filename);
234
for (m=nx; m--; wbm++)
235
if (wbm->mean <= -BIG)
238
QCALLOC(wbm->histo, int, wbm->nlevels);
240
/*---- Build (progressively this time) the histograms */
241
for(size=meshsize, bufsize2=bufsize; size>0; size -= bufsize2)
245
read_body(tab, buf, bufsize2);
248
read_body(wtab, wbuf, bufsize2);
249
weight_to_var(wbuf, bufsize2);
251
backhisto(backmesh, wbackmesh, buf, wbuf, bufsize2, nx, w, bw,
252
wfield?wfield->weight_thresh:0.0);
256
/*-- Compute background statistics from the histograms */
258
for (m=0; m<nx; m++, bm++)
261
backguess(bm, field->back+k, field->sigma+k);
267
for (m=0; m<nx; m++, wbm++)
270
backguess(wbm, wfield->back+k, wfield->sigma+k);
285
/* Go back to the original position */
286
QFSEEK(field->tab->cat->file, fcurpos, SEEK_SET, field->filename);
288
QFSEEK(wfield->tab->cat->file, wfcurpos, SEEK_SET, wfield->filename);
290
/* Median-filter and check suitability of the background map */
291
NFPRINTF(OUTPUT, "Filtering background map(s)");
296
/* Compute normalization for variance- or weight-maps*/
297
if (wfield && wscale_flag && wfield->flags&(VAR_FIELD|WEIGHT_FIELD))
300
QMALLOC(ratio, float, wfield->nback);
302
weight = wfield->back;
303
sigma = field->sigma;
304
for (i=wfield->nback; i--; sigma++)
305
if ((sratio=*(weight++)) > 0.0
306
&& (sratio = *sigma/sqrt(sratio)) > 0.0)
308
*(ratiop++) = sratio;
311
wfield->sigfac = (double)hmedian(ratio, nr);
312
for (i=0; i<nr && ratio[i]<=0.0; i++);
314
wfield->sigfac = (double)hmedian(ratio+i, nr-i);
317
warning("Null or negative global weighting factor:","defaulted to 1");
318
wfield->sigfac = 1.0;
321
/*-- Update weight threshold */
322
wfield->weight_thresh *= (PIXTYPE)(wfield->sigfac*wfield->sigfac);
327
/* Compute 2nd derivatives along the y-direction */
328
NFPRINTF(OUTPUT, "Computing backgound d-map");
330
field->dback = make_backspline(field, field->back);
331
NFPRINTF(OUTPUT, "Computing backgound-noise d-map");
333
field->dsigma = make_backspline(field, field->sigma);
334
/* If asked for, force the backmean parameter to the supplied value */
335
if (field->back_type == BACK_ABSOLUTE)
336
field->backmean = field->backdefault;
338
field->fbackmean = field->backmean*field->fascale;
339
field->fbacksig = field->backsig*field->fascale;
345
/******************************** backstat **********************************/
347
Compute robust statistical estimators in a row of meshes.
349
void backstat(backstruct *backmesh, backstruct *wbackmesh,
350
PIXTYPE *buf, PIXTYPE *wbuf, size_t bufsize,
351
int n, int w, int bw, PIXTYPE wthresh)
354
backstruct *bm, *wbm;
355
double pix,wpix, sig, mean,wmean, sigma,wsigma, step;
356
PIXTYPE *buft,*wbuft, lcut,wlcut, hcut,whcut;
357
int m,h,x,y, npix,wnpix, offset, lastbite;
363
step = sqrt(2/PI)*QUANTIF_NSIGMA/QUANTIF_AMIN;
364
wmean = wsigma = wlcut = whcut = 0.0; /* to avoid gcc -Wall warnings */
365
for (m = n; m--; bm++,buf+=bw)
367
if (!m && (lastbite=w%bw))
374
/*-- We separate the weighted case at this level to avoid penalty in CPU */
378
wmean = wsigma = 0.0;
380
for (y=h; y--; buft+=offset,wbuft+=offset)
384
if ((wpix = *(wbuft++)) < wthresh && pix > -BIG)
396
for (y=h; y--; buft+=offset)
398
if ((pix = *(buft++)) > -BIG)
406
/*-- If not enough valid pixels, discard this mesh */
407
if ((float)npix < (float)(bw*h*BACK_MINGOODFRAC))
409
bm->mean = bm->sigma = -BIG;
412
wbm->mean = wbm->sigma = -BIG;
420
wmean /= (double)npix;
421
wsigma = (sig = wsigma/npix - wmean*wmean)>0.0? sqrt(sig):0.0;
422
wlcut = wbm->lcut = (PIXTYPE)(wmean - 2.0*wsigma);
423
whcut = wbm->hcut = (PIXTYPE)(wmean + 2.0*wsigma);
425
mean /= (double)npix;
426
sigma = (sig = sigma/npix - mean*mean)>0.0? sqrt(sig):0.0;
427
lcut = bm->lcut = (PIXTYPE)(mean - 2.0*sigma);
428
hcut = bm->hcut = (PIXTYPE)(mean + 2.0*sigma);
434
wmean = wsigma = 0.0;
436
for (y=h; y--; buft+=offset, wbuft+=offset)
440
if ((wpix = *(wbuft++))<wthresh && pix<=hcut && pix>=lcut)
445
if (wpix<=whcut && wpix>=wlcut)
455
for (y=h; y--; buft+=offset)
459
if (pix<=hcut && pix>=lcut)
468
mean /= (double)npix;
469
sig = sigma/npix - mean*mean;
470
sigma = sig>0.0 ? sqrt(sig):0.0;
473
if ((bm->nlevels = (int)(step*npix+1)) > QUANTIF_NMAXLEVELS)
474
bm->nlevels = QUANTIF_NMAXLEVELS;
475
bm->qscale = sigma>0.0? 2*QUANTIF_NSIGMA*sigma/bm->nlevels : 1.0;
476
bm->qzero = mean - QUANTIF_NSIGMA*sigma;
480
wmean /= (double)wnpix;
481
sig = wsigma/wnpix - wmean*wmean;
482
wsigma = sig>0.0 ? sqrt(sig):0.0;
485
if ((wbm->nlevels = (int)(step*wnpix+1)) > QUANTIF_NMAXLEVELS)
486
wbm->nlevels = QUANTIF_NMAXLEVELS;
487
wbm->qscale = wsigma>0.0? 2*QUANTIF_NSIGMA*wsigma/wbm->nlevels : 1.0;
488
wbm->qzero = wmean - QUANTIF_NSIGMA*wsigma;
498
/******************************** backhisto *********************************/
500
Compute robust statistical estimators in a row of meshes.
502
void backhisto(backstruct *backmesh, backstruct *wbackmesh,
503
PIXTYPE *buf, PIXTYPE *wbuf, size_t bufsize,
504
int n, int w, int bw, PIXTYPE wthresh)
507
PIXTYPE *buft,*wbuft,
509
float qscale,wqscale, cste,wcste, wpix;
511
int h,m,x,y, nlevels,wnlevels, lastbite, offset, bin;
517
for (m=0; m++<n; bm++ , buf+=bw)
519
if (m==n && (lastbite=w%bw))
524
/*-- Skip bad meshes */
525
if (bm->mean <= -BIG)
534
nlevels = bm->nlevels;
537
cste = 0.499999 - bm->qzero/qscale;
541
wnlevels = wbm->nlevels;
543
wqscale = wbm->qscale;
544
wcste = 0.499999 - wbm->qzero/wqscale;
546
for (y=h; y--; buft+=offset, wbuft+=offset)
549
bin = (int)((pix=*(buft++))/qscale + cste);
550
if ((wpix = *(wbuft++))<wthresh && pix>-BIG && bin<nlevels && bin>=0)
553
bin = (int)(wpix/wqscale + wcste);
554
if (bin>=0 && bin<wnlevels)
562
for (y=h; y--; buft += offset)
565
bin = (int)((pix=*(buft++))/qscale + cste);
566
if (bin>=0 && bin<nlevels && pix>-BIG)
574
/******************************* backguess **********************************/
576
Estimate the background from a histogram;
578
float backguess(backstruct *bkg, float *mean, float *sigma)
580
#define EPS (1e-4) /* a small number */
583
int *histo, *hilow, *hihigh, *histot;
584
unsigned int lowsum, highsum, sum;
585
double ftemp, mea, sig, sig1, med, dpix;
586
int i, n, lcut,hcut, nlevelsm1, pix;
588
/* Leave here if the mesh is already classified as `bad' */
591
*mean = *sigma = -BIG;
596
hcut = nlevelsm1 = bkg->nlevels-1;
599
sig = 10.0*nlevelsm1;
601
mea = med = bkg->mean;
602
for (n=100; n-- && (sig>=0.1) && (fabs(sig/sig1-1.0)>EPS);)
605
sum = mea = sig = 0.0;
606
lowsum = highsum = 0;
607
histot = hilow = histo+lcut;
609
for (i=lcut; i<=hcut; i++)
612
lowsum += *(hilow++);
614
highsum += *(hihigh--);
615
sum += (pix = *(histot++));
616
mea += (dpix = (double)pix*i);
621
((hihigh-histo)+0.5+((double)highsum-lowsum)/(2.0*(*hilow>*hihigh?
628
sig = sig/sum - mea*mea;
630
sig = sig>0.0?sqrt(sig):0.0;
631
lcut = (ftemp=med-3.0*sig)>0.0 ?(int)(ftemp>0.0?ftemp+0.5:ftemp-0.5):0;
632
hcut = (ftemp=med+3.0*sig)<nlevelsm1 ?(int)(ftemp>0.0?ftemp+0.5:ftemp-0.5)
636
*mean = fabs(sig)>0.0? (fabs(bkg->sigma/(sig*bkg->qscale)-1) < 0.0 ?
637
bkg->qzero+mea*bkg->qscale
638
:(fabs((mea-med)/sig)< 0.3 ?
639
bkg->qzero+(2.5*med-1.5*mea)*bkg->qscale
640
:bkg->qzero+med*bkg->qscale))
641
:bkg->qzero+mea*bkg->qscale;
643
*sigma = sig*bkg->qscale;
650
/******************************* filter_back *********************************/
652
Median filtering of the background map to remove the contribution from bright
655
void filter_back(fieldstruct *field)
658
float *back,*sigma, *back2,*sigma2, *bmask,*smask, *sigmat,
659
d2,d2min, fthresh, med, val,sval;
660
int i,j,px,py, np, nx,ny, npx,npx2, npy,npy2, dpx,dpy, x,y, nmin;
662
fthresh = prefs.back_fthresh;
666
npx = field->nbackfx/2;
667
npy = field->nbackfy/2;
670
QMALLOC(bmask, float, (2*npx+1)*(2*npy+1));
671
QMALLOC(smask, float, (2*npx+1)*(2*npy+1));
672
QMALLOC(back2, float, np);
673
QMALLOC(sigma2, float, np);
676
sigma = field->sigma;
677
val = sval = 0.0; /* to avoid gcc -Wall warnings */
679
/* Look for `bad' meshes and interpolate them if necessary */
680
for (i=0,py=0; py<ny; py++)
681
for (px=0; px<nx; px++,i++)
682
if ((back2[i]=back[i])<=-BIG)
684
/*------ Seek the closest valid mesh */
687
for (j=0,y=0; y<ny; y++)
688
for (x=0; x<nx; x++,j++)
691
d2 = (float)(x-px)*(x-px)+(y-py)*(y-py);
706
back2[i] = nmin? val/nmin: 0.0;
707
sigma[i] = nmin? sval/nmin: 1.0;
709
memcpy(back, back2, (size_t)np*sizeof(float));
711
/* Do the actual filtering */
712
for (py=0; py<np; py+=nx)
719
for (px=0; px<nx; px++)
727
for (dpy = -npy2; dpy<=npy2; dpy+=nx)
730
for (dpx = -npx2; dpx <= npx2; dpx++)
733
bmask[i] = back[x+y];
734
smask[i++] = sigma[x+y];
737
if (fabs((med=hmedian(bmask, i))-back[px+py])>=fthresh)
740
sigma2[px+py] = hmedian(smask, i);
744
back2[px+py] = back[px+py];
745
sigma2[px+py] = sigma[px+py];
752
memcpy(back, back2, np*sizeof(float));
753
field->backmean = (double)hmedian(back2, np);
755
memcpy(sigma, sigma2, np*sizeof(float));
756
field->backsig = (double)hmedian(sigma2, np);
758
if (field->backsig<=0.0)
761
for (i=np; i-- && *(--sigmat)>0.0;);
762
if (i>=0 && i<(np-1))
763
field->backsig = hmedian(sigmat+1, np-1-i);
766
if (field->flags&(DETECT_FIELD|MEASURE_FIELD))
767
warning("Image contains mainly constant data; ",
768
"I'll try to cope with that...");
769
field->backsig = 1.0;
780
/******************************* make_backspline *****************************/
782
Pre-compute 2nd derivatives along the y direction at background nodes.
784
float *make_backspline(fieldstruct *field, float *map)
787
int x,y, nbx,nby,nbym1;
788
float *dmap,*dmapt,*mapt, *u, temp;
793
QMALLOC(dmap, float, field->nback);
794
for (x=0; x<nbx; x++)
800
QMALLOC(u, float, nbym1); /* temporary array */
801
*dmapt = *u = 0.0; /* "natural" lower boundary condition */
803
for (y=1; y<nbym1; y++, mapt+=nbx)
805
temp = -1/(*dmapt+4);
806
*(dmapt += nbx) = temp;
807
temp *= *(u++) - 6*(*(mapt+nbx)+*(mapt-nbx)-2**mapt);
810
*(dmapt+=nbx) = 0.0; /* "natural" upper boundary condition */
815
*dmapt = (*dmapt*temp+*(u--))/6.0;
827
/******************************** backline **********************************/
829
Interpolate background at line y (bicubic spline interpolation between
830
background map vertices).
832
void backline(fieldstruct *field, int y, PIXTYPE *line)
835
int i,j,x,yl, nbx,nbxm1,nby, nx,width, ystep, changepoint;
836
float dx,dx0,dy,dy3, cdx,cdy,cdy3, temp, xstep,
837
*node,*nodep,*dnode, *blo,*bhi,*dblo,*dbhi, *u;
840
width = field->width;
842
if (field->back_type==BACK_ABSOLUTE)
844
/*-- In absolute background mode, just subtract a cste */
845
bval = (PIXTYPE)field->backmean;
856
dy = (float)y/field->backh - 0.5;
857
dy -= (yl = (int)dy);
865
yl = nby<2 ? 0 : nby-2;
868
/*-- Interpolation along y for each node */
871
cdy3 = (cdy*cdy*cdy-cdy);
873
blo = field->back + ystep;
875
dblo = field->dback + ystep;
877
QMALLOC(node, float, nbx); /* Interpolated background */
880
*(nodep++) = cdy**(blo++) + dy**(bhi++) + cdy3**(dblo++) + dy3**(dbhi++);
882
/*-- Computation of 2nd derivatives along x */
883
QMALLOC(dnode, float, nbx); /* 2nd derivative along x */
886
QMALLOC(u, float, nbxm1); /* temporary array */
887
*dnode = *u = 0.0; /* "natural" lower boundary condition */
889
for (x=nbxm1; --x; nodep++)
891
temp = -1/(*(dnode++)+4);
893
temp *= *(u++) - 6*(*(nodep+1)+*(nodep-1)-2**nodep);
896
*(++dnode) = 0.0; /* "natural" upper boundary condition */
900
*dnode = (*dnode*temp+*(u--))/6.0;
908
/*-- No interpolation and no new 2nd derivatives needed along y */
910
dnode = field->dback;
913
/*-- Interpolation along x */
919
dx = (xstep - 1)/2; /* dx of the first pixel in the row */
920
dx0 = ((nx+1)%2)*xstep/2; /* dx of the 1st pixel right to a bkgnd node */
925
for (x=i=0,j=width; j--; i++, dx += xstep)
927
if (i==changepoint && x>0 && x<nbxm1)
936
*(line++) = (PIXTYPE)(cdx*(*blo+(cdx*cdx-1)**dblo)
937
+ dx*(*bhi+(dx*dx-1)**dbhi));
947
*(line++) = (PIXTYPE)*node;
959
/******************************* backrmsline ********************************
960
PROTO void backrmsline(fieldstruct *field, int y, PIXTYPE *line)
961
PURPOSE Bicubic-spline interpolation of the background noise along the current
963
INPUT Measurement or detection field pointer,
964
Current line position.
965
Where to put the data.
967
NOTES Most of the code is a copy of subbackline(), for optimization reasons.
968
AUTHOR E. Bertin (IAP & Leiden & ESO)
971
void backrmsline(fieldstruct *field, int y, PIXTYPE *line)
974
int i,j,x,yl, nbx,nbxm1,nby, nx,width, ystep, changepoint;
975
float dx,dx0,dy,dy3, cdx,cdy,cdy3, temp, xstep,
976
*node,*nodep,*dnode, *blo,*bhi,*dblo,*dbhi, *u;
983
dy = (float)y/field->backh - 0.5;
984
dy -= (yl = (int)dy);
992
yl = nby<2 ? 0 : nby-2;
995
/*-- Interpolation along y for each node */
998
cdy3 = (cdy*cdy*cdy-cdy);
1000
blo = field->sigma + ystep;
1002
dblo = field->dsigma + ystep;
1004
QMALLOC(node, float, nbx); /* Interpolated background */
1007
*(nodep++) = cdy**(blo++) + dy**(bhi++) + cdy3**(dblo++) + dy3**(dbhi++);
1009
/*-- Computation of 2nd derivatives along x */
1010
QMALLOC(dnode, float, nbx); /* 2nd derivative along x */
1013
QMALLOC(u, float, nbxm1); /* temporary array */
1014
*dnode = *u = 0.0; /* "natural" lower boundary condition */
1016
for (x=nbxm1; --x; nodep++)
1018
temp = -1/(*(dnode++)+4);
1020
temp *= *(u++) - 6*(*(nodep+1)+*(nodep-1)-2**nodep);
1023
*(++dnode) = 0.0; /* "natural" upper boundary condition */
1027
*dnode = (*dnode*temp+*(u--))/6.0;
1035
/*-- No interpolation and no new 2nd derivatives needed along y */
1036
node = field->sigma;
1037
dnode = field->dsigma;
1040
/*-- Interpolation along x */
1041
width = field->width;
1047
dx = (xstep - 1)/2; /* dx of the first pixel in the row */
1048
dx0 = ((nx+1)%2)*xstep/2; /* dx of the 1st pixel right to a bkgnd node */
1053
for (x=i=0,j=width; j--; i++, dx += xstep)
1055
if (i==changepoint && x>0 && x<nbxm1)
1064
*(line++) = (PIXTYPE)(cdx*(*blo+(cdx*cdx-1)**dblo)
1065
+ dx*(*bhi+(dx*dx-1)**dbhi));
1075
*(line++) = (PIXTYPE)*node;
1087
/********************************* end_back **********************************/
1089
Terminate background procedures (mainly freeing memory).
1091
void end_back(fieldstruct *field)
1097
free(field->dsigma);
1098
free(field->backline);