00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127
00128 #ifdef HAVE_CONFIG_H
00129 # include <config.h>
00130 #endif
00131 #include "sinfo_vltPort.h"
00132 #include <math.h>
00133
00134
00135
00136
00137
00138
00139
00140
00141 #include "sinfo_function_1d.h"
00142 #include "sinfo_recipes.h"
00143 #include "sinfo_wavecal.h"
00144 #include "sinfo_wave_calibration.h"
00145 #include "sinfo_solve_poly_root.h"
00146 #include "sinfo_utils_wrappers.h"
00147 #include "sinfo_error.h"
00148
00149 #include "sinfo_svd.h"
00150
00151
00152
00153 static Bcoeffs *
00154 sinfo_new_b_coeffs( int n_slitlets,
00155 int n_acoeffs,
00156 int n_bcoeffs ) ;
00157
00158 static void
00159 sinfo_new_destroy_b_coeffs ( Bcoeffs * bco ) ;
00160
00161 static int
00162 sinfo_new_coeffs_cross_slit_fit ( int n_columns,
00163 float ** acoefs,
00164 float ** dacoefs,
00165 Bcoeffs* bco,
00166 float sigma_factor,
00167 float dispersion,
00168 float pixel_dist,
00169 float * chisq ) ;
00170
00171
00172 static int
00173 sinfo_new_spred_coeffs_cross_slit_fit ( int n_columns,
00174 float ** acoefs,
00175 float ** dacoefs,
00176 Bcoeffs* bco,
00177 float sigma_factor,
00178 float dispersion,
00179 float pixel_dist,
00180 float * chisq,
00181 float ** sinfo_slit_pos) ;
00182
00183
00184
00200 static Bcoeffs *
00201 sinfo_new_b_coeffs( int n_slitlets,
00202 int n_acoeffs,
00203 int n_bcoeffs )
00204 {
00205 int i, n ;
00206 Bcoeffs * returnbco ;
00207
00208 if(NULL == (returnbco=(Bcoeffs*) cpl_calloc(n_slitlets, sizeof(Bcoeffs))) )
00209 {
00210 sinfo_msg_error ("could not allocate memory") ;
00211 return NULL ;
00212 }
00213 returnbco -> n_slitlets = n_slitlets ;
00214 returnbco -> n_acoeffs = n_acoeffs ;
00215 returnbco -> n_bcoeffs = n_bcoeffs ;
00216 for ( i = 0 ; i < n_slitlets ; i++ )
00217 {
00218 returnbco[i].slitlet = i ;
00219 if ( NULL == (returnbco[i].b = (float**)cpl_calloc(n_acoeffs,
00220 sizeof(float*)) ) )
00221 {
00222 sinfo_msg_error ("could not allocate memory") ;
00223 return NULL ;
00224 }
00225 for ( n = 0 ; n < n_acoeffs ; n++ )
00226 {
00227 if ( NULL == (returnbco[i].b[n] = (float*)cpl_calloc(n_bcoeffs,
00228 sizeof(float))) )
00229 {
00230 sinfo_msg_error ("could not allocate memory") ;
00231 return NULL ;
00232 }
00233 }
00234 }
00235 return returnbco ;
00236 }
00237
00245 static void
00246 sinfo_new_destroy_b_coeffs ( Bcoeffs * bco )
00247 {
00248 int i, n ;
00249
00250 for ( i = 0 ; i < bco->n_slitlets ; i++ )
00251 {
00252 for ( n = 0 ; n < bco->n_acoeffs ; n++ )
00253 {
00254 cpl_free (bco[i].b[n]) ;
00255 }
00256 cpl_free(bco[i].b) ;
00257 }
00258
00259 cpl_free (bco) ;
00260 }
00261
00287 static int
00288 sinfo_new_coeffs_cross_slit_fit ( int n_columns,
00289 float ** acoefs,
00290 float ** dacoefs,
00291 Bcoeffs* bco,
00292 float sigma_factor,
00293 float dispersion,
00294 float pixel_dist,
00295 float * chisq )
00296 {
00297 float col_index;
00298 float ** ucoefs, **vcoefs, **covar ;
00299 float * acoefsclean ;
00300 double sum, sumq, mean ;
00301 double sigma ;
00302 double cliphi, cliplo ;
00303 float offset ;
00304 float threshold ;
00305 float* sub_col_index=NULL ;
00306 float* sub_acoefs=NULL;
00307 float* sub_dacoefs=NULL ;
00308 float* wcoefs=NULL ;
00309 int* edge=NULL ;
00310
00311 int ed1, ed2 ;
00312 int i, n, num, ndata ;
00313 int nc, ns ;
00314 int loc_index ;
00315 int last_i=PIXEL;
00316
00317 if ( n_columns < 1 )
00318 {
00319 sinfo_msg_error("wrong number of image columns given") ;
00320 return -1 ;
00321 }
00322 if ( acoefs == NULL || dacoefs == NULL )
00323 {
00324 sinfo_msg_error("acoeffs or errors of coefficients are not given") ;
00325 return -1 ;
00326 }
00327 if ( bco == NULL )
00328 {
00329 sinfo_msg_error("bcoeffs are not allocated") ;
00330 return -1 ;
00331 }
00332 if ( sigma_factor <= 0. )
00333 {
00334 sinfo_msg_error("impossible sigma_factor given!") ;
00335 return -1 ;
00336 }
00337 if ( dispersion == 0. )
00338 {
00339 sinfo_msg_error("impossible dispersion given!") ;
00340 return -1 ;
00341 }
00342
00343
00344
00345
00346
00347
00348
00349 edge=cpl_calloc(bco->n_slitlets,sizeof(int)) ;
00350 wcoefs=cpl_calloc(bco->n_bcoeffs,sizeof(float)) ;
00351
00352 n = 0 ;
00353 threshold = pixel_dist * fabs(dispersion) ;
00354 for ( i = PIXEL ; i < n_columns - PIXEL ; )
00355 {
00356 if ( !isnan(acoefs[0][i+1]) &&
00357 acoefs[0][i+1] != 0. &&
00358 acoefs[0][i] != 0. &&
00359 dacoefs[0][i+1] != 0.)
00360 {
00361 if ( isnan(acoefs[0][i]) || acoefs[0][i] == 0. )
00362 {
00363 if (fabs(acoefs[0][i+1] - acoefs[0][i-1]) >= threshold )
00364 {
00365 if( (i-last_i) < 60 && (i > 80) ) {
00366 sinfo_msg_warning("skip1 i=%d diff=%d\n",i,i-last_i);
00367 goto skip;
00368 } else {
00369
00370
00371
00372
00373
00374 edge[n] = i+1 ;
00375
00376 n++ ;
00377 last_i = i;
00378 i += PIXEL ;
00379 }
00380 }
00381 }
00382 else
00383 {
00384 if ((fabs(acoefs[0][i+1] - acoefs[0][i]) >= threshold) ||
00385 (i-last_i) > 63 )
00386 {
00387 if( (i-last_i) < 60 && ((i> 80) || (i<PIXEL+2))) {
00388 sinfo_msg_warning("skip2 i=%d diff=%d\n",i,i-last_i);
00389 goto skip;
00390 } else {
00391
00392
00393
00394
00395
00396
00397
00398
00399
00400 edge[n] = i+1 ;
00401
00402 n++ ;
00403 last_i = i;
00404 i += PIXEL ;
00405 }
00406 }
00407 }
00408
00409
00410 if( ( (i-last_i) > 63 ) &&
00411 ( isnan(fabs(acoefs[0][i+1] - acoefs[0][i])) ||
00412 isnan(fabs(acoefs[0][i+1] - acoefs[0][i-1])) ) )
00413 {
00414 edge[n] = i+1 ;
00415
00416 n++ ;
00417 last_i = i;
00418 sinfo_msg_warning("recovered slitlet edge i=%d",i);
00419 i += PIXEL ;
00420
00421 }
00422 }
00423 skip:
00424 i++ ;
00425 }
00426
00427
00428
00429
00430 if ( n != bco->n_slitlets - 1 )
00431 {
00432 sinfo_msg_error("could not find the right number "
00433 "of slitlets, found: %d",n+1) ;
00434 return -1 ;
00435 }
00436
00437 sub_col_index=cpl_calloc(n_columns,sizeof(float)) ;
00438 sub_acoefs=cpl_calloc(n_columns,sizeof(float));
00439 sub_dacoefs=cpl_calloc(n_columns,sizeof(float)) ;
00440
00441
00442 for ( loc_index = 0 ; loc_index < bco->n_acoeffs ; loc_index++ )
00443 {
00444
00445 for ( ns = 0 ; ns < bco->n_slitlets ; ns++ )
00446 {
00447
00448 if ( ns == 0 )
00449 {
00450 ed1 = 0 ;
00451 ed2 = edge[0] ;
00452 }
00453 else if ( ns == bco->n_slitlets - 1 )
00454 {
00455 ed1 = edge[bco->n_slitlets - 2] ;
00456 ed2 = n_columns ;
00457 }
00458 else
00459 {
00460 ed1 = edge[ns-1] ;
00461 ed2 = edge[ns] ;
00462 }
00463
00464 nc = 0 ;
00465 for ( i = ed1 ; i < ed2 ; i++ )
00466 {
00467 if ( isnan(acoefs[loc_index][i]) ||
00468 acoefs[loc_index][i] == 0. ||
00469 dacoefs[loc_index][i] == 0. )
00470 {
00471 continue ;
00472 }
00473 else
00474 {
00475 nc++ ;
00476 }
00477 }
00478 if (NULL==(acoefsclean = (float*) cpl_calloc(nc , sizeof(float))) )
00479 {
00480 sinfo_msg_error("could not allocate memory for acoefsclean!") ;
00481 return -1 ;
00482 }
00483 nc = 0 ;
00484 for ( i = ed1 ; i < ed2 ; i++ )
00485 {
00486 if ( isnan(acoefs[loc_index][i]) ||
00487 acoefs[loc_index][i] == 0. ||
00488 dacoefs[loc_index][i] == 0. )
00489 {
00490 continue ;
00491 }
00492 else
00493 {
00494 acoefsclean[nc] = acoefs[loc_index][i] ;
00495 nc++ ;
00496 }
00497 }
00498
00499
00500
00501
00502
00503 sinfo_pixel_qsort(acoefsclean, nc) ;
00504
00505 sum = 0. ;
00506 sumq = 0. ;
00507 mean = 0. ;
00508 sigma = 0. ;
00509 n = 0 ;
00510 for ( i = (int)((float)nc*LOW_REJECT) ;
00511 i < (int)((float)nc*HIGH_REJECT) ; i++ )
00512 {
00513 sum += (double)acoefsclean[i] ;
00514 sumq += ((double)acoefsclean[i] * (double)acoefsclean[i]) ;
00515 n ++ ;
00516 }
00517 mean = sum/(double)n ;
00518 sigma = sqrt( sumq/(double)n - (mean * mean) ) ;
00519 cliphi = mean + sigma * (double)sigma_factor ;
00520 cliplo = mean - sigma * (double)sigma_factor ;
00521
00522 num = 0 ;
00523 col_index = 0 ;
00524
00525
00526
00527 for ( i = ed1 ; i < ed2 ; i++ )
00528 {
00529
00530
00531
00532
00533
00534 if ( !isnan(acoefs[loc_index][i]) &&
00535 (acoefs[loc_index][i] <= cliphi) &&
00536 (acoefs[loc_index][i] >= cliplo) &&
00537 (dacoefs[loc_index][i] != 0. ) &&
00538 (acoefs[loc_index][i] != 0.) )
00539 {
00540 sub_acoefs[num] = acoefs[loc_index][i] ;
00541 sub_dacoefs[num] = dacoefs[loc_index][i] ;
00542 sub_col_index[num] = col_index ;
00543 num ++ ;
00544 }
00545 col_index++ ;
00546 }
00547 ndata = num ;
00548 offset = (float)(col_index-1) / 2. ;
00549
00550
00551 if ( ndata < bco->n_bcoeffs )
00552 {
00553 sinfo_msg_error("not enough data found in slitlet %d to "
00554 "determine the fit coefficients.", ns) ;
00555 cpl_free(acoefsclean) ;
00556 return -1 ;
00557 }
00558
00559
00560 ucoefs = sinfo_matrix(1, ndata, 1, bco->n_bcoeffs) ;
00561 vcoefs = sinfo_matrix(1, ndata, 1, bco->n_bcoeffs) ;
00562 covar = sinfo_matrix(1, bco->n_bcoeffs, 1, bco->n_bcoeffs) ;
00563
00564
00565 for ( i = 0 ; i < ndata ; i++ )
00566 {
00567 sub_col_index[i] = (sub_col_index[i] - offset) / offset ;
00568 }
00569
00570
00571 sinfo_svd_fitting ( sub_col_index-1, sub_acoefs-1,
00572 sub_dacoefs-1, ndata, bco[ns].b[loc_index]-1,
00573 bco->n_bcoeffs, ucoefs, vcoefs,
00574 wcoefs-1, covar, &chisq[ns], sinfo_fpol ) ;
00575
00576
00577 for ( i = 0 ; i < bco->n_bcoeffs ; i ++ )
00578 {
00579 bco[ns].b[loc_index][i] /= pow( offset, i ) ;
00580 }
00581
00582
00583 cpl_free (acoefsclean) ;
00584 sinfo_free_matrix( ucoefs, 1, 1) ;
00585 sinfo_free_matrix( vcoefs, 1, 1) ;
00586 sinfo_free_matrix( covar, 1,
00587 1) ;
00588
00589
00590 col_index = 0 ;
00591 for ( i = ed1 ; i < ed2 ; i++ )
00592 {
00593 acoefs[loc_index][i] = 0. ;
00594 for ( n = 0 ; n < bco->n_bcoeffs ; n++ )
00595 {
00596 acoefs[loc_index][i] += bco[ns].b[loc_index][n] *
00597 pow(col_index - offset, n) ;
00598 }
00599 col_index++ ;
00600 }
00601
00602 }
00603 }
00604
00605 cpl_free(sub_col_index) ;
00606 cpl_free(sub_acoefs) ;
00607 cpl_free(sub_dacoefs) ;
00608
00609
00610 cpl_free(edge) ;
00611 cpl_free(wcoefs) ;
00612
00613 return 0 ;
00614 }
00615
00616
00629 cpl_image * sinfo_new_wave_map_slit ( float ** acoefs,
00630 int n_acoefs,
00631 int n_rows,
00632 int n_columns )
00633 {
00634 cpl_image * newIm=NULL ;
00635 float lambda=0 ;
00636 float offset=0 ;
00637 int col=0;
00638 int row=0 ;
00639 int i=0 ;
00640 float row_index=0 ;
00641 float* podata=NULL;
00642 if ( NULL == acoefs )
00643 {
00644 sinfo_msg_error (" no coefficient sinfo_matrix given!") ;
00645 return NULL ;
00646 }
00647
00648
00649 if ( NULL == (newIm = cpl_image_new(n_columns , n_rows,CPL_TYPE_FLOAT)) )
00650 {
00651 sinfo_msg_error ("could not allocate new image!") ;
00652 return NULL ;
00653 }
00654 podata=cpl_image_get_data_float(newIm);
00655
00656
00657 offset = (float)(n_rows - 1) / 2. ;
00658
00659
00660 for ( col = 0 ; col < n_columns ; col++ )
00661 {
00662
00663 for ( row = 0 ; row < n_rows ; row++ )
00664 {
00665 lambda = 0. ;
00666 row_index = (float)row - offset ;
00667 for ( i = 0 ; i < n_acoefs ; i++ )
00668 {
00669 lambda += acoefs[i][col] * pow(row_index, i) ;
00670 }
00671 podata[col+row*n_columns] = lambda ;
00672 }
00673 }
00674 return newIm ;
00675 }
00676
00677
00724 cpl_image * sinfo_new_wave_cal( cpl_image * image,
00725 FitParams ** par ,
00726 float ** abuf,
00727 int n_slitlets,
00728 int ** row_clean,
00729 float ** wavelength_clean,
00730 int * n_found_lines,
00731 float dispersion,
00732 int halfWidth,
00733 float minAmplitude,
00734 float max_residual,
00735 float fwhm,
00736 int n_a_fitcoefs,
00737 int n_b_fitcoefs,
00738 float sigmaFactor,
00739 float pixel_dist,
00740 float pixel_tolerance )
00741
00742 {
00743 int i=0, j=0, k=0 ;
00744 int n_fit=0 ;
00745 int n_reject=0 ;
00746 float * acoefs=NULL ;
00747 float * dacoefs=NULL ;
00748 float ** dabuf=NULL ;
00749 float chisq_poly=0 ;
00750 float * chisq_cross=NULL ;
00751 int zeroind=0 ;
00752 int crossInd=0 ;
00753 Bcoeffs * bco=NULL ;
00754 cpl_image * wavemap=NULL ;
00755 int ilx=0;
00756 int ily=0;
00757 float* pidata=NULL;
00758
00759
00760 if ( NULL == image )
00761 {
00762 sinfo_msg_error("no image given") ;
00763 return NULL ;
00764 }
00765 check_nomsg(ilx=cpl_image_get_size_x(image));
00766 check_nomsg(ily=cpl_image_get_size_y(image));
00767 check_nomsg(pidata=cpl_image_get_data_float(image));
00768
00769 if ( par == NULL )
00770 {
00771 sinfo_msg_error("no fit parameter data structure given") ;
00772 return NULL ;
00773 }
00774 if ( abuf == NULL )
00775 {
00776 sinfo_msg_error("no buffer for fit coefficients given") ;
00777 return NULL ;
00778 }
00779 if ( n_slitlets <= 0 )
00780 {
00781 sinfo_msg_error("impossible number of slitlets given") ;
00782 return NULL ;
00783 }
00784 if ( row_clean == NULL )
00785 {
00786 sinfo_msg_error("no row_clean array given") ;
00787 return NULL ;
00788 }
00789 if ( wavelength_clean == NULL )
00790 {
00791 sinfo_msg_error("no wavelength_clean array given") ;
00792 return NULL ;
00793 }
00794
00795 if ( dispersion == 0. )
00796 {
00797 sinfo_msg_error("impossible dispersion given") ;
00798 return NULL ;
00799 }
00800
00801 if ( halfWidth <= 0 || halfWidth > ily/2 )
00802 {
00803 sinfo_msg_error("impossible half width of the fitting box given") ;
00804 return NULL ;
00805 }
00806 if ( minAmplitude < 1. )
00807 {
00808 sinfo_msg_error("impossible minimal amplitude") ;
00809 return NULL ;
00810 }
00811
00812 if ( max_residual <= 0. || max_residual > 1. )
00813 {
00814 sinfo_msg_error("impossible max_residual given") ;
00815 return NULL ;
00816 }
00817 if ( fwhm <= 0. || fwhm > 10. )
00818 {
00819 sinfo_msg_error("impossible fwhm given") ;
00820 return NULL ;
00821 }
00822
00823 if ( n_a_fitcoefs <= 0 || n_a_fitcoefs > 9 )
00824 {
00825 sinfo_msg_error("unrealistic n_a_fitcoefs given") ;
00826 return NULL ;
00827 }
00828
00829 if ( n_b_fitcoefs <= 0 || n_b_fitcoefs > 9 )
00830 {
00831 sinfo_msg_error("unrealistic n_b_fitcoefs given") ;
00832 return NULL ;
00833 }
00834 if ( sigmaFactor <= 0. )
00835 {
00836 sinfo_msg_error("impossible sigmaFactor given") ;
00837 return NULL ;
00838 }
00839
00840
00841 n_reject = 0 ;
00842 n_fit = 0 ;
00843
00844
00845
00846
00847 if ( 0 > (n_fit = sinfo_new_fit_lines( image , par, fwhm, n_found_lines,
00848 row_clean, wavelength_clean,
00849 halfWidth, minAmplitude )) )
00850 {
00851 sinfo_msg_error("cannot fit the lines, error code of "
00852 "sinfo_fitLines: %d", n_fit) ;
00853 return NULL ;
00854 }
00855
00856
00857 if ( -1 == sinfo_new_check_for_fake_lines (par, dispersion,
00858 wavelength_clean,
00859 row_clean, n_found_lines,
00860 ilx, pixel_tolerance) )
00861 {
00862 sinfo_msg_error("cannot fit the lines, error code of "
00863 "sinfo_fitLines: %d", n_fit) ;
00864 return NULL ;
00865 }
00866
00867
00868 if (NULL == (acoefs = (float*) cpl_calloc(n_a_fitcoefs, sizeof(float))) ||
00869 NULL == (dacoefs = (float*) cpl_calloc(n_a_fitcoefs, sizeof(float))) ||
00870 NULL == (dabuf = (float**) cpl_calloc(n_a_fitcoefs, sizeof(float*))) ||
00871 NULL == (chisq_cross = (float*) cpl_calloc(n_slitlets, sizeof(float))))
00872 {
00873 sinfo_msg_error("cannot allocate memory\n") ;
00874 return NULL ;
00875 }
00876 for ( i = 0 ; i < n_a_fitcoefs ; i++ )
00877 {
00878 if ( NULL == (dabuf[i] = (float*) cpl_calloc(ilx, sizeof(float))) )
00879 {
00880 sinfo_msg_error("cannot allocate memory") ;
00881 sinfo_free_float (&acoefs ) ;
00882 sinfo_free_float ( &dacoefs ) ;
00883 sinfo_free_float ( &chisq_cross ) ;
00884 sinfo_free_float_array(&dabuf,n_a_fitcoefs) ;
00885 return NULL ;
00886 }
00887 }
00888
00889
00890
00891 k = 0 ;
00892 for ( i = 0 ; i < ilx ; i++ )
00893 {
00894 zeroind = 0 ;
00895 if ( FLT_MAX == (chisq_poly = sinfo_new_polyfit( par, i,
00896 n_found_lines[i],
00897 ily, dispersion,
00898 max_residual, acoefs,
00899 dacoefs, &n_reject,
00900 n_a_fitcoefs)) )
00901 {
00902
00903
00904
00905 for ( j = 0 ; j < n_a_fitcoefs ; j++ )
00906 {
00907 acoefs[j] = ZERO ;
00908 dacoefs[j] = ZERO ;
00909 }
00910 }
00911
00912 for ( j = 0 ; j < n_a_fitcoefs ; j++ )
00913 {
00914
00915 if ( acoefs[0] <= 0. || acoefs[1] ==0. ||
00916 dacoefs[j] == 0. || isnan(acoefs[j]) )
00917 {
00918 zeroind = 1 ;
00919 }
00920 }
00921 for ( j = 0 ; j < n_a_fitcoefs ; j++ )
00922 {
00923 if ( zeroind == 0 )
00924 {
00925 abuf[j][i] = acoefs[j] ;
00926 dabuf[j][i] = dacoefs[j] ;
00927 }
00928 else
00929 {
00930 abuf[j][i] = ZERO ;
00931 dabuf[j][i] = ZERO ;
00932 }
00933 }
00934 }
00935
00936
00937 if ( NULL == ( bco = sinfo_new_b_coeffs( n_slitlets,
00938 n_a_fitcoefs, n_b_fitcoefs)) )
00939 {
00940 sinfo_msg_error ("cannot allocate memory for the bcoeffs") ;
00941 sinfo_free_float_array(&dabuf,n_a_fitcoefs) ;
00942 sinfo_free_float (&acoefs ) ;
00943 sinfo_free_float (&dacoefs ) ;
00944 sinfo_free_float (&chisq_cross ) ;
00945 return NULL ;
00946 }
00947
00948
00949 if ( -1 == ( crossInd = sinfo_new_coeffs_cross_slit_fit( ilx,
00950 abuf,
00951 dabuf,
00952 bco,
00953 sigmaFactor,
00954 dispersion,
00955 pixel_dist,
00956 chisq_cross )) )
00957 {
00958 sinfo_msg_error ("cannot carry out the fitting of "
00959 "coefficients across the columns") ;
00960 sinfo_free_float_array(&dabuf,n_a_fitcoefs) ;
00961 sinfo_free_float (&acoefs ) ;
00962 sinfo_free_float (&dacoefs ) ;
00963 sinfo_free_float (&chisq_cross ) ;
00964 return NULL ;
00965 }
00966
00967
00968 if ( NULL == (wavemap = sinfo_new_wave_map_slit (abuf, n_a_fitcoefs,
00969 ily, ilx)) )
00970 {
00971 sinfo_msg_error ("cannot carry out wavemap creation") ;
00972 sinfo_free_float_array(&dabuf,n_a_fitcoefs) ;
00973 sinfo_free_float (&acoefs ) ;
00974 sinfo_free_float (&dacoefs ) ;
00975 sinfo_free_float (&chisq_cross ) ;
00976 sinfo_new_destroy_b_coeffs(bco) ;
00977 return NULL ;
00978 }
00979
00980
00981 sinfo_free_float_array(&dabuf,n_a_fitcoefs) ;
00982 sinfo_free_float (&acoefs ) ;
00983 sinfo_free_float (&dacoefs ) ;
00984 sinfo_free_float (&chisq_cross ) ;
00985 sinfo_new_destroy_b_coeffs(bco) ;
00986
00987 return wavemap ;
00988 cleanup:
00989 sinfo_free_float (&acoefs ) ;
00990 sinfo_free_float ( &dacoefs ) ;
00991 sinfo_free_float ( &chisq_cross ) ;
00992 sinfo_free_float_array(&dabuf,n_a_fitcoefs) ;
00993 sinfo_new_destroy_b_coeffs(bco) ;
00994 return NULL;
00995 }
00996
00997
00998
01021 int sinfo_new_check_for_fake_lines ( FitParams ** par,
01022 float dispersion,
01023 float ** wavelength_clean,
01024 int ** row_clean,
01025 int * n_found_lines,
01026 int n_columns,
01027 float pixel_tolerance )
01028 {
01029 int i, k ;
01030 int col ;
01031 int found ;
01032 float row ;
01033 float * beginWave ;
01034 float firstWave ;
01035
01036 if ( par == NULL )
01037 {
01038 sinfo_msg_error("no fit parameter data structure given") ;
01039 return -1 ;
01040 }
01041 if ( dispersion == 0. )
01042 {
01043 sinfo_msg_error("dispersion zero given!") ;
01044 return -1 ;
01045 }
01046 if ( wavelength_clean == NULL )
01047 {
01048 sinfo_msg_error("no wavelength array given!") ;
01049 return -1 ;
01050 }
01051 if ( row_clean == NULL )
01052 {
01053 sinfo_msg_error("no row array given!") ;
01054 return -1 ;
01055 }
01056 if ( n_found_lines == NULL )
01057 {
01058 sinfo_msg_error("no number of lines given!") ;
01059 return -1 ;
01060 }
01061 if ( n_columns < 200 )
01062 {
01063 sinfo_msg_error("wrong number of columns given!") ;
01064 return -1 ;
01065 }
01066
01067
01068 for ( col = 0 ; col < n_columns ; col++ )
01069 {
01070 if ( n_found_lines[col] == 0 )
01071 {
01072 continue ;
01073 }
01074 if ( NULL == (beginWave = (float*) cpl_calloc( n_found_lines[col],
01075 sizeof(float) ) ) )
01076 {
01077 sinfo_msg_error("could not allocate memory!") ;
01078 return -1 ;
01079 }
01080 for ( k = 0 ; k < n_found_lines[col] ; k++ )
01081 {
01082 beginWave[k] = wavelength_clean[col][k] -
01083 (float)row_clean[col][k] * dispersion ;
01084 }
01085
01086
01087 if ( FLT_MAX == (firstWave = sinfo_new_clean_mean (beginWave,
01088 n_found_lines[col],
01089 10., 10.) ) )
01090 {
01091 sinfo_msg_error("clean mean did not work!") ;
01092 return -1 ;
01093 }
01094
01095 cpl_free (beginWave) ;
01096
01097
01098 for ( k = 0 ; k < n_found_lines[col] ; k++ )
01099 {
01100
01101 row = ( wavelength_clean[col][k] - firstWave ) / dispersion ;
01102
01103
01104 found = -1 ;
01105 for ( i = 0 ; i < (par[0] -> n_params) ; i ++ )
01106 {
01107
01108
01109 if ( (par[i] -> column == col) && (par[i] -> line == k) &&
01110 (par[i] -> wavelength == wavelength_clean[col][k]) )
01111 {
01112 found = i ;
01113 break ;
01114 }
01115 }
01116 if ( found != -1 )
01117 {
01118
01119
01120
01121 if ( fabs(row - par[found]->fit_par[2]) > pixel_tolerance )
01122 {
01123 sinfo_msg_warning("found bad line in col: "
01124 "%d line: %d in row: %f difference: %f",
01125 col, k, par[found]->fit_par[2],
01126 row - par[found]->fit_par[2]) ;
01127 par[found]->fit_par[2] = 0. ;
01128 }
01129 }
01130 else
01131 {
01132 sinfo_msg_warning("fit parameter of col %d and line "
01133 "no %d not found!\n", col, k ) ;
01134 }
01135 }
01136 }
01137
01138 return 0 ;
01139 }
01140
01159 cpl_image *
01160 sinfo_new_create_shifted_slit_wavemap ( cpl_image * lineIm,
01161 float ** coeffs,
01162 int n_fitcoeffs,
01163 float * wavelength,
01164 float * intensity,
01165 int n_lines,
01166 int magFactor )
01167 {
01168 cpl_image * wavemap ;
01169 float* emline=NULL ;
01170 float* spec=NULL ;
01171 float* wave=NULL ;
01172 double* a=NULL ;
01173 float* par=NULL ;
01174 float* derv_par=NULL ;
01175 double* z=NULL ;
01176
01177 double * result ;
01178 float * filter_spec ;
01179 float centreval ;
01180 float centrepix ;
01181 float cenpos, cenpix ;
01182 float pixvalue ;
01183 float wavelag ;
01184 float angst ;
01185 float a_initial ;
01186 int numpar, its ;
01187 int * mpar ;
01188 float tol, lab ;
01189 float * xdat, * wdat ;
01190 Vector * peak;
01191 int iters, xdim, ndat ;
01192 int row , col ;
01193 int i, j, k ;
01194 int sign, found, line, width ;
01195 int var, maxlag, cmin, cmax ;
01196 gsl_poly_complex_workspace * w ;
01197 double xcorr_max ;
01198 int delta ;
01199 int ilx=0;
01200 int ily=0;
01201 int olx=0;
01202 int oly=0;
01203 float* pidata=NULL;
01204 float* podata=NULL;
01205
01206
01207 if ( lineIm == NULL )
01208 {
01209 sinfo_msg_error ("no input image given!") ;
01210 return NULL ;
01211 }
01212 ilx=cpl_image_get_size_x(lineIm);
01213 ily=cpl_image_get_size_y(lineIm);
01214 pidata=cpl_image_get_data_float(lineIm);
01215
01216 if ( coeffs == NULL )
01217 {
01218 sinfo_msg_error ("no coefficient sinfo_matrix given!") ;
01219 return NULL ;
01220 }
01221 if ( n_fitcoeffs < 2 )
01222 {
01223 sinfo_msg_error ("wrong number of polynomial coefficients given!") ;
01224 return NULL ;
01225 }
01226 if ( wavelength == NULL || intensity == NULL )
01227 {
01228 sinfo_msg_error ("no input image given!") ;
01229 return NULL ;
01230 }
01231 if ( n_lines < 1 )
01232 {
01233 sinfo_msg_error ("no input image given!") ;
01234 return NULL ;
01235 }
01236
01237
01238 if ( wavelength[0] > 10000. )
01239 {
01240
01241 angst = 10000. ;
01242 }
01243 else if ( wavelength[0] > 1000. && wavelength[0] < 10000. )
01244 {
01245
01246 angst = 1000. ;
01247 }
01248 else
01249 {
01250
01251 angst = 1. ;
01252 }
01253
01254
01255 if ( NULL == (wavemap = cpl_image_new ( ilx, ily, CPL_TYPE_FLOAT)) )
01256 {
01257 sinfo_msg_error ("could not allocate memory!") ;
01258 return NULL ;
01259 }
01260 olx=cpl_image_get_size_x(wavemap);
01261 oly=cpl_image_get_size_y(wavemap);
01262 podata=cpl_image_get_data_float(wavemap);
01263
01264 var = (magFactor-1)*(magFactor-1) ;
01265
01266
01267
01268 emline=cpl_calloc(ily,sizeof(float)) ;
01269 spec=cpl_calloc(ily,sizeof(float)) ;
01270 wave=cpl_calloc(n_lines,sizeof(float)) ;
01271 par=cpl_calloc(MAXPAR,sizeof(float)) ;
01272 derv_par=cpl_calloc(MAXPAR,sizeof(float)) ;
01273
01274 a=cpl_calloc(n_fitcoeffs,sizeof(double)) ;
01275 z=cpl_calloc(2*(n_fitcoeffs - 1),sizeof(double)) ;
01276
01277
01278
01279 for ( col = 0 ; col < ilx ; col++ )
01280 {
01281
01282 for ( i = 0 ; i < ily ; i++ )
01283 {
01284 emline[i] = 0. ;
01285 }
01286
01287 for ( i = 0 ; i < n_fitcoeffs ; i++ )
01288 {
01289
01290 if (i < n_fitcoeffs-1)
01291 {
01292 z[2*i] = 0. ;
01293 z[2*i+1] = 0. ;
01294 }
01295 a[i] = coeffs[i][col] ;
01296 }
01297
01298 a_initial = coeffs[0][col] ;
01299
01300 for ( line = 0 ; line < n_lines ; line++ )
01301 {
01302
01303 wave[line] = wavelength[line]/angst ;
01304
01305
01306
01307
01308
01309 a[0] = a_initial - wave[line] ;
01310
01311 if(NULL==(w=sinfo_gsl_poly_complex_workspace_alloc(n_fitcoeffs)))
01312 {
01313 sinfo_msg_error("could not allocate complex workspace!") ;
01314 cpl_image_delete(wavemap) ;
01315 return NULL ;
01316 }
01317 if (-1 == sinfo_gsl_poly_complex_solve(a, n_fitcoeffs, w, z))
01318 {
01319 sinfo_msg_error("sinfo_gsl_poly_complex_solve did not work!") ;
01320 cpl_image_delete(wavemap) ;
01321 return NULL ;
01322 }
01323 sinfo_gsl_poly_complex_workspace_free(w) ;
01324
01325 j = 0 ;
01326 found = -1 ;
01327 for ( i = 0 ; i < n_fitcoeffs - 1 ; i++ )
01328 {
01329
01330 if( (z[2*i] > (-1.)*(float) ily/2. &&
01331 z[2*i] < (float)ily/2.) && z[2*i+1] == 0. )
01332 {
01333 found = 2*i ;
01334 j ++ ;
01335 }
01336 else
01337 {
01338 continue ;
01339 }
01340 }
01341 if ( j == 0 )
01342 {
01343 sinfo_msg_warning("no offset solution found for line %d in "
01344 "column %d", line, col) ;
01345 continue ;
01346 }
01347 else if ( j == 1 )
01348 {
01349 cenpos = z[found] + (float) ily /2. ;
01350 }
01351 else
01352 {
01353 sinfo_msg_warning("two or more offset solutions found for "
01354 "line %d in column %d", line, col) ;
01355 continue ;
01356 }
01357
01358
01359
01360
01361 cenpix = cenpos ;
01362
01363
01364
01365 cmin = (sinfo_new_nint(cenpix) - (var-1)) > 0 ?
01366 sinfo_new_nint(cenpix) - (var-1) : 0 ;
01367 cmax = (sinfo_new_nint(cenpix) + (var-1)) < ily ?
01368 sinfo_new_nint(cenpix) + (var-1) : ily ;
01369
01370
01371 for ( j = cmin ; j < cmax ; j++ )
01372 {
01373 emline[j] += intensity[line] *
01374 exp((double)(-0.5*(j-cenpix)*(j-cenpix))/(double)var) ;
01375 }
01376 }
01377
01378
01379
01380
01381
01382
01383 for ( k = 0 ; k < ily ; k++ )
01384 {
01385 spec[k] = 0. ;
01386 }
01387
01388
01389
01390 for ( row = 0 ; row < ily ; row++ )
01391 {
01392
01393 if (!isnan(pidata[col + row*ilx]) &&
01394 (pidata[col + row*ilx] > 0.))
01395 {
01396 spec[row] = pidata[col + row*ilx] ;
01397 }
01398 else
01399 {
01400 spec[row] = 0. ;
01401 }
01402 }
01403
01404 filter_spec = sinfo_function1d_filter_lowpass(spec, ily,
01405 LOW_PASS_GAUSSIAN,
01406 magFactor) ;
01407
01408
01409 result = sinfo_new_xcorrel( filter_spec, ily, emline, ily,
01410 ily/2, &delta, &maxlag, &xcorr_max) ;
01411
01412 if ( xcorr_max <= 0. )
01413 {
01414 sinfo_msg_warning("no positive cross correlation sum , "
01415 "col %d set to ZERO \n", col) ;
01416 for ( row = 0 ; row < ily ; row++ )
01417 {
01418 podata[col + row*ilx] = ZERO ;
01419 }
01420 sinfo_function1d_del(filter_spec) ;
01421 cpl_free(result) ;
01422 continue ;
01423 }
01424
01425
01426
01427
01428 i = maxlag; j = i+1;
01429 while (result[j] < result[i])
01430 {
01431 i++; j++;
01432 }
01433 i = maxlag; k = i-1;
01434 while (result[k] < result[i])
01435 {
01436 i--; k--;
01437 }
01438 width = j-k+1;
01439
01440 if ( NULL == (peak = sinfo_new_vector (width)) )
01441 {
01442 sinfo_msg_error ("cannot allocate new Vector \n") ;
01443 sinfo_function1d_del(filter_spec) ;
01444 cpl_free(result) ;
01445 return NULL ;
01446 }
01447
01448
01449
01450 xdat = (float *) cpl_calloc( peak -> n_elements, sizeof (float) ) ;
01451 wdat = (float *) cpl_calloc( peak -> n_elements, sizeof (float) ) ;
01452 mpar = (int *) cpl_calloc( MAXPAR, sizeof (int) ) ;
01453
01454
01455
01456
01457 for ( i = 0 ; i < width ; i++ )
01458 {
01459 peak -> data[i] = result[k+i]/xcorr_max * 100. ;
01460 xdat[i] = i;
01461 wdat[i] = 1.0;
01462 }
01463
01464
01465 xdim = XDIM;
01466 ndat = peak -> n_elements ;
01467 numpar = MAXPAR ;
01468 tol = TOL ;
01469 lab = LAB ;
01470 its = ITS ;
01471 par[1] = width/2.0 ;
01472 par[2] = (float) (maxlag - k) ;
01473 par[3] = (peak -> data[0] + peak -> data[peak->n_elements - 1]) / 2.0 ;
01474 par[0] = result[maxlag]/xcorr_max * 100. - (par[3]) ;
01475
01476 for ( i = 0 ; i < MAXPAR ; i++ )
01477 {
01478 derv_par[i] = 0.0 ;
01479 mpar[i] = 1 ;
01480 }
01481
01482
01483 if ( 0 > ( iters = sinfo_new_lsqfit_c( xdat, &xdim,
01484 peak -> data, wdat,
01485 &ndat, par, derv_par, mpar,
01486 &numpar, &tol, &its, &lab )) )
01487 {
01488 sinfo_msg_warning ("sinfo_new_lsqfit_c: least squares fit failed "
01489 "in col: %d, error no.: %d", col, iters) ;
01490 sinfo_new_destroy_vector ( peak ) ;
01491 cpl_free ( xdat ) ;
01492 cpl_free ( wdat ) ;
01493 cpl_free ( mpar ) ;
01494 sinfo_function1d_del(filter_spec) ;
01495 cpl_free(result) ;
01496 continue ;
01497 }
01498
01499 sinfo_new_destroy_vector ( peak ) ;
01500 cpl_free (xdat) ;
01501 cpl_free (wdat) ;
01502 cpl_free (mpar) ;
01503 sinfo_function1d_del(filter_spec) ;
01504 cpl_free(result) ;
01505
01506 wavelag =((float)ily/2 - (float)k - par[2]) ;
01507
01508 if ( fabs(wavelag) > (float)ily/20. )
01509 {
01510 sinfo_msg_warning("wavelag very big , col %d set to ZERO", col) ;
01511 for ( row = 0 ; row < ily ; row++ )
01512 {
01513 podata[col + row*ilx] = ZERO ;
01514 }
01515 continue ;
01516 }
01517
01518
01519
01520
01521
01522
01523
01524
01525 centreval = a_initial ;
01526 for ( i = 1 ; i < n_fitcoeffs ; i++ )
01527 {
01528 if ( i%2 == 0 )
01529 {
01530 sign = -1 ;
01531 }
01532 else
01533 {
01534 sign = 1 ;
01535 }
01536 centreval += (float)sign * coeffs[i][col]*pow(wavelag, i) ;
01537 }
01538
01539
01540 for ( row = 0 ; row < oly ; row++ )
01541 {
01542 centrepix = (float)row - ((float)oly - 1.)/2. ;
01543 pixvalue = 0. ;
01544 for ( i = 1 ; i < n_fitcoeffs ; i++ )
01545 {
01546 pixvalue += coeffs[i][col]*pow(centrepix, i) ;
01547 }
01548 podata[col+row*olx] = centreval + pixvalue ;
01549 }
01550 }
01551
01552
01553 cpl_free(emline) ;
01554 cpl_free(spec) ;
01555 cpl_free(wave) ;
01556 cpl_free(par) ;
01557 cpl_free(derv_par) ;
01558
01559 cpl_free(a) ;
01560 cpl_free(z) ;
01561
01562
01563
01564 return wavemap ;
01565 }
01566
01591 cpl_image * sinfo_new_create_shifted_slit_wavemap2 ( cpl_image * lineIm,
01592 float ** coeffs,
01593 int n_fitcoeffs,
01594 float * wavelength,
01595 float * intensity,
01596 int n_lines,
01597 int magFactor,
01598 float dispersion,
01599 float pixel_dist )
01600 {
01601 cpl_image * wavemap ;
01602 double * result ;
01603 float * filter_spec ;
01604 float centreval ;
01605 float centrepix ;
01606 float cenpos, cenpix ;
01607 float pixvalue ;
01608 float wavelag ;
01609
01610 float angst ;
01611
01612 float a_initial ;
01613 int numpar, its ;
01614 int * mpar ;
01615 float tol, lab ;
01616 float * xdat, * wdat ;
01617 Vector * peak;
01618 int iters, xdim, ndat ;
01619 int row , col ;
01620 int i, j, k, n ;
01621 int sign, found, line, width ;
01622 int var, maxlag, cmin, cmax ;
01623 float offset2 ;
01624 float threshold ;
01625 int ed1, ed2 ;
01626
01627 int edge[N_SLITLETS] ;
01628 float par[MAXPAR] ;
01629 float derv_par[MAXPAR] ;
01630
01631 float* emline=NULL ;
01632 float* spec=NULL ;
01633 float* wave=NULL ;
01634 float* a0=NULL ;
01635 float* a0_clean=NULL ;
01636
01637
01638 float* sub_col_index=NULL ;
01639 float* sub_acoefs=NULL;
01640 float* sub_dacoefs=NULL ;
01641 double* z=NULL ;
01642 double* a=NULL ;
01643
01644 float** bcoef=NULL ;
01645 float* wcoefs=NULL ;
01646
01647
01648 int ns, nc ;
01649 float * acoefsclean ;
01650 float col_index;
01651
01652 float ** ucoefs, **vcoefs, **covar ;
01653 double sum, sumq, mean ;
01654 double sigma ;
01655 double cliphi, cliplo ;
01656 float chisq ;
01657 int num, ndata ;
01658 gsl_poly_complex_workspace * w ;
01659 double xcorr_max ;
01660 int delta ;
01661 int ilx=0;
01662 int ily=0;
01663 int olx=0;
01664 int oly=0;
01665 float* pidata=NULL;
01666 float* podata=NULL;
01667
01668
01669 if ( lineIm == NULL )
01670 {
01671 sinfo_msg_error (" no input image given!\n") ;
01672 return NULL ;
01673 }
01674
01675 ilx=cpl_image_get_size_x(lineIm);
01676 ily=cpl_image_get_size_y(lineIm);
01677 pidata=cpl_image_get_data_float(lineIm);
01678
01679 if ( coeffs == NULL )
01680 {
01681 sinfo_msg_error (" no coefficient sinfo_matrix given!\n") ;
01682 return NULL ;
01683 }
01684 if ( n_fitcoeffs < 2 )
01685 {
01686 sinfo_msg_error (" wrong number of polynomial coefficients given!\n") ;
01687 return NULL ;
01688 }
01689 if ( wavelength == NULL || intensity == NULL )
01690 {
01691 sinfo_msg_error (" no input image given!\n") ;
01692 return NULL ;
01693 }
01694 if ( n_lines < 1 || magFactor < 1 )
01695 {
01696 sinfo_msg_error (" no input image given!\n") ;
01697 return NULL ;
01698 }
01699 var = (magFactor - 1)*(magFactor - 1) ;
01700
01701 if ( wavelength[0] > 10000. )
01702 {
01703
01704 angst = 10000. ;
01705 }
01706 else if ( wavelength[0] > 1000. && wavelength[0] < 10000. )
01707 {
01708
01709 angst = 1000. ;
01710 }
01711 else
01712 {
01713
01714 angst = 1. ;
01715 }
01716
01717 bcoef=sinfo_new_2Dfloatarray(N_SLITLETS,n_fitcoeffs) ;
01718 wcoefs=cpl_calloc(n_fitcoeffs,sizeof(float)) ;
01719
01720 emline=cpl_calloc(ily,sizeof(float)) ;
01721 spec=cpl_calloc(ily,sizeof(float)) ;
01722 wave=cpl_calloc(n_lines,sizeof(float)) ;
01723 a0=cpl_calloc(ilx,sizeof(float)) ;
01724 a0_clean=cpl_calloc(ilx,sizeof(float)) ;
01725
01726
01727
01728 sub_col_index=cpl_calloc(ilx,sizeof(float)) ;
01729 sub_acoefs=cpl_calloc(ilx,sizeof(float));
01730 sub_dacoefs=cpl_calloc(ilx,sizeof(float)) ;
01731
01732 a=cpl_calloc(n_fitcoeffs,sizeof(double)) ;
01733 z=cpl_calloc(2*(n_fitcoeffs - 1),sizeof(double)) ;
01734
01735
01736 n = 0 ;
01737 threshold = pixel_dist * fabs(dispersion) ;
01738 for ( i = PIXEL ; i < ilx - PIXEL ; )
01739 {
01740 if (fabs(coeffs[0][i+1] - coeffs[0][i]) >= threshold )
01741 {
01742 edge[n] = i+1 ;
01743 n++ ;
01744 i += PIXEL ;
01745 }
01746 i++ ;
01747 }
01748
01749
01750
01751 if ( NULL == (wavemap = cpl_image_new ( ilx, ily, CPL_TYPE_FLOAT)) )
01752 {
01753 sinfo_msg_error (" could not allocate memory!\n") ;
01754 return NULL ;
01755 }
01756 olx=cpl_image_get_size_x(wavemap);
01757 oly=cpl_image_get_size_y(wavemap);
01758 podata=cpl_image_get_data_float(wavemap);
01759
01760
01761 for ( col = 0 ; col < ilx ; col++ )
01762 {
01763
01764 for ( i = 0 ; i < ily ; i++ )
01765 {
01766 emline[i] = 0. ;
01767 }
01768
01769 for ( i = 0 ; i < n_fitcoeffs ; i++ )
01770 {
01771
01772 if (i < n_fitcoeffs-1)
01773 {
01774 z[2*i] = 0. ;
01775 z[2*i+1] = 0. ;
01776 }
01777 a[i] = coeffs[i][col] ;
01778 }
01779
01780 a_initial = coeffs[0][col] ;
01781
01782 for ( line = 0 ; line < n_lines ; line++ )
01783 {
01784
01785 wave[line] = wavelength[line]/angst ;
01786
01787
01788
01789
01790
01791 a[0] = a_initial - wave[line] ;
01792
01793 if (NULL==(w=sinfo_gsl_poly_complex_workspace_alloc(n_fitcoeffs)))
01794 {
01795 sinfo_msg_error(" could not allocate complex workspace!") ;
01796 cpl_image_delete(wavemap) ;
01797 return NULL ;
01798 }
01799 if (-1 == sinfo_gsl_poly_complex_solve(a, n_fitcoeffs, w, z))
01800 {
01801 sinfo_msg_error(" sinfo_gsl_poly_complex_solve did not work!") ;
01802 cpl_image_delete(wavemap) ;
01803 return NULL ;
01804 }
01805 sinfo_gsl_poly_complex_workspace_free(w) ;
01806
01807 j = 0 ;
01808 found = -1 ;
01809 for ( i = 0 ; i < n_fitcoeffs - 1 ; i++ )
01810 {
01811
01812 if( (z[2*i] > (-1.)*(float) ily/2. &&
01813 z[2*i] < (float)ily/2.) && z[2*i+1] == 0. )
01814 {
01815 found = 2*i ;
01816 j ++ ;
01817 }
01818 else
01819 {
01820 continue ;
01821 }
01822 }
01823 if ( j == 0 )
01824 {
01825 sinfo_msg_warning(" no offset solution found for "
01826 "line %d in column %d\n", line, col) ;
01827 continue ;
01828 }
01829 else if ( j == 1 )
01830 {
01831 cenpos = z[found] + (float) ily/2. ;
01832 }
01833 else
01834 {
01835 sinfo_msg_warning(" two or more offset solutions found "
01836 "for line %d in column %d", line, col) ;
01837 continue ;
01838 }
01839
01840
01841
01842
01843 cenpix = cenpos ;
01844
01845
01846
01847 cmin = (sinfo_new_nint(cenpix) - (var-1)) > 0 ?
01848 sinfo_new_nint(cenpix) - (var-1) : 0 ;
01849 cmax = (sinfo_new_nint(cenpix) + (var-1)) < ily ?
01850 sinfo_new_nint(cenpix) + (var-1) : ily ;
01851
01852
01853 for ( j = cmin ; j < cmax ; j++ )
01854 {
01855 emline[j] += intensity[line] *
01856 exp((double)(-0.5*(j-cenpix)*(j-cenpix))/(double)var) ;
01857 }
01858 }
01859
01860
01861
01862
01863
01864
01865 for ( k = 0 ; k < ily ; k++ )
01866 {
01867 spec[k] = 0. ;
01868 }
01869
01870
01871
01872 for ( row = 0 ; row < ily ; row++ )
01873 {
01874
01875 if (!isnan(pidata[col + row*ilx]) &&
01876 (pidata[col + row*ilx] > 0.))
01877 {
01878 spec[row] = pidata[col + row*ilx] ;
01879 }
01880 else
01881 {
01882 spec[row] = 0. ;
01883 }
01884 }
01885
01886 filter_spec = sinfo_function1d_filter_lowpass(spec,ily,
01887 LOW_PASS_GAUSSIAN,
01888 magFactor) ;
01889
01890
01891 result = sinfo_new_xcorrel( filter_spec, ily, emline, ily,
01892 ily/2, &delta, &maxlag, &xcorr_max) ;
01893
01894 if ( xcorr_max <= 0. )
01895 {
01896 sinfo_msg_warning("no positive cross sinfo_correlation "
01897 "sum , col %d set to ZERO \n", col) ;
01898 for ( row = 0 ; row < ily ; row++ )
01899 {
01900 podata[col + row*ilx] = ZERO ;
01901 }
01902 sinfo_function1d_del(filter_spec) ;
01903 cpl_free(result) ;
01904 continue ;
01905 }
01906
01907
01908
01909
01910 i = maxlag; j = i+1;
01911 while (result[j] < result[i])
01912 {
01913 i++; j++;
01914 }
01915 i = maxlag; k = i-1;
01916 while (result[k] < result[i])
01917 {
01918 i--; k--;
01919 }
01920 width = j-k+1;
01921
01922 if ( NULL == (peak = sinfo_new_vector (width)) )
01923 {
01924 sinfo_msg_error (" cannot allocate new Vector \n") ;
01925 sinfo_function1d_del(filter_spec) ;
01926 cpl_free(result) ;
01927 return NULL ;
01928 }
01929
01930
01931
01932 xdat = (float *) cpl_calloc( peak -> n_elements, sizeof (float) ) ;
01933 wdat = (float *) cpl_calloc( peak -> n_elements, sizeof (float) ) ;
01934 mpar = (int *) cpl_calloc( MAXPAR, sizeof (int) ) ;
01935
01936
01937
01938
01939 for ( i = 0 ; i < width ; i++ )
01940 {
01941 peak -> data[i] = result[k+i]/xcorr_max * 100. ;
01942 xdat[i] = i;
01943 wdat[i] = 1.0;
01944 }
01945
01946
01947 xdim = XDIM;
01948 ndat = peak -> n_elements ;
01949 numpar = MAXPAR ;
01950 tol = TOL ;
01951 lab = LAB ;
01952 its = ITS ;
01953 par[1] = width/2.0 ;
01954 par[2] = (float) (maxlag - k) ;
01955 par[3] = (peak -> data[0] + peak -> data[peak->n_elements - 1]) / 2.0 ;
01956 par[0] = result[maxlag]/xcorr_max * 100. - (par[3]) ;
01957
01958 for ( i = 0 ; i < MAXPAR ; i++ )
01959 {
01960 derv_par[i] = 0.0 ;
01961 mpar[i] = 1 ;
01962 }
01963
01964
01965 if ( 0 > ( iters = sinfo_new_lsqfit_c( xdat, &xdim, peak -> data,
01966 wdat, &ndat, par,
01967 derv_par, mpar,
01968 &numpar, &tol, &its, &lab )) )
01969 {
01970 sinfo_msg_warning (" sinfo_new_lsqfit_c: least squares fit "
01971 "failed in col: %d, error no.: %d", col, iters);
01972 sinfo_new_destroy_vector ( peak ) ;
01973 cpl_free ( xdat ) ;
01974 cpl_free ( wdat ) ;
01975 cpl_free ( mpar ) ;
01976 sinfo_function1d_del(filter_spec) ;
01977 cpl_free(result) ;
01978 continue ;
01979 }
01980
01981 sinfo_new_destroy_vector ( peak ) ;
01982 cpl_free (xdat) ;
01983 cpl_free (wdat) ;
01984 cpl_free (mpar) ;
01985 sinfo_function1d_del(filter_spec) ;
01986 cpl_free(result) ;
01987
01988 wavelag =((float)ily/2 - (float)k - par[2]) ;
01989
01990 if ( fabs(wavelag) > (float)ily/20. )
01991 {
01992 sinfo_msg_warning("wavelag very big , col %d set to ZERO ", col) ;
01993 for ( row = 0 ; row < ily ; row++ )
01994 {
01995 podata[col + row*ilx] = ZERO ;
01996 }
01997 continue ;
01998 }
01999
02000
02001
02002
02003
02004
02005
02006
02007 centreval = a_initial ;
02008 for ( i = 1 ; i < n_fitcoeffs ; i++ )
02009 {
02010 if ( i%2 == 0 )
02011 {
02012 sign = -1 ;
02013 }
02014 else
02015 {
02016 sign = 1 ;
02017 }
02018 centreval += (float)sign * coeffs[i][col]*pow(wavelag, i) ;
02019 }
02020 a0[col] = centreval ;
02021 }
02022
02023
02024 for ( ns = 0 ; ns < N_SLITLETS ; ns++ )
02025 {
02026
02027 if ( ns == 0 )
02028 {
02029 ed1 = 0 ;
02030 ed2 = edge[0] ;
02031 }
02032 else if ( ns == N_SLITLETS - 1 )
02033 {
02034 ed1 = edge[N_SLITLETS - 2] ;
02035 ed2 = ilx ;
02036 }
02037 else
02038 {
02039 ed1 = edge[ns-1] ;
02040 ed2 = edge[ns] ;
02041 }
02042
02043 nc = 0 ;
02044 for ( i = ed1 ; i < ed2 ; i++ )
02045 {
02046 if ( isnan(a0[i]) || a0[i] == 0. )
02047 {
02048 continue ;
02049 }
02050 else
02051 {
02052 nc++ ;
02053 }
02054 }
02055 if ( NULL == (acoefsclean = (float*) cpl_calloc(nc , sizeof(float))) )
02056 {
02057 sinfo_msg_error("could not allocate memory for acoefsclean!\n") ;
02058 return NULL ;
02059 }
02060 nc = 0 ;
02061 for ( i = ed1 ; i < ed2 ; i++ )
02062 {
02063 if ( isnan(a0[i]) || a0[i] == 0. )
02064 {
02065 continue ;
02066 }
02067 else
02068 {
02069 acoefsclean[nc] = a0[i] ;
02070 nc++ ;
02071 }
02072 }
02073
02074
02075
02076
02077
02078 sinfo_pixel_qsort(acoefsclean, nc) ;
02079 sum = 0. ;
02080 sumq = 0. ;
02081 mean = 0. ;
02082 sigma = 0. ;
02083 n = 0 ;
02084 for ( i = (int)((float)nc*LOW_REJECT) ;
02085 i < (int)((float)nc*HIGH_REJECT) ; i++ )
02086 {
02087 sum += (double)acoefsclean[i] ;
02088 sumq += ((double)acoefsclean[i] * (double)acoefsclean[i]) ;
02089 n ++ ;
02090 }
02091 mean = sum/(double)n ;
02092 sigma = sqrt( sumq/(double)n - (mean * mean) ) ;
02093 cliphi = mean + sigma * (double)3. ;
02094 cliplo = mean - sigma * (double)3. ;
02095
02096 num = 0 ;
02097 col_index = 0 ;
02098 for ( i = ed1 ; i < ed2 ; i++ )
02099 {
02100
02101 if ( !isnan(a0[i]) && (a0[i] <= cliphi) && (a0[i] >= cliplo) &&
02102 (a0[i] != 0.) )
02103 {
02104 sub_acoefs[num] = a0[i] ;
02105 sub_dacoefs[num] = 0.0000005 ;
02106 sub_col_index[num] = col_index ;
02107 num ++ ;
02108 }
02109 col_index++ ;
02110 }
02111 ndata = num ;
02112 offset2 = (float)(col_index-1) / 2. ;
02113
02114 if ( ndata < n_fitcoeffs )
02115 {
02116 sinfo_msg_error(" not enough data found in slitlet %d\
02117 to determine the fit coefficients.\n", ns) ;
02118 cpl_free(acoefsclean) ;
02119 return NULL ;
02120 }
02121
02122
02123
02124 ucoefs = sinfo_matrix(1, ndata, 1, n_fitcoeffs) ;
02125 vcoefs = sinfo_matrix(1, ndata, 1, n_fitcoeffs) ;
02126 covar = sinfo_matrix(1, n_fitcoeffs, 1, n_fitcoeffs) ;
02127
02128
02129 for ( i = 0 ; i < ndata ; i++ )
02130 {
02131 sub_col_index[i] = (sub_col_index[i] - offset2) / offset2 ;
02132 }
02133
02134
02135 sinfo_svd_fitting ( sub_col_index-1, sub_acoefs-1,
02136 sub_dacoefs-1, ndata, bcoef[ns]-1,
02137 n_fitcoeffs, ucoefs, vcoefs, wcoefs-1,
02138 covar, &chisq, sinfo_fpol ) ;
02139
02140
02141 for ( i = 0 ; i < n_fitcoeffs ; i ++ )
02142 {
02143 bcoef[ns][i] /= pow( offset2, i ) ;
02144 }
02145
02146
02147 cpl_free (acoefsclean) ;
02148 sinfo_free_matrix( ucoefs, 1, 1) ;
02149 sinfo_free_matrix( vcoefs, 1, 1) ;
02150 sinfo_free_matrix( covar, 1, 1) ;
02151
02152
02153 col_index = 0 ;
02154 for ( i = ed1 ; i < ed2 ; i++ )
02155 {
02156 a0_clean[i] = 0. ;
02157 for ( n = 0 ; n < n_fitcoeffs ; n++ )
02158 {
02159 a0_clean[i] += bcoef[ns][n] *
02160 pow((float)col_index - offset2, n) ;
02161 }
02162 col_index++ ;
02163 }
02164
02165 }
02166
02167 for ( col = 0 ; col < ilx ; col++ )
02168 {
02169
02170 for ( row = 0 ; row < oly ; row++ )
02171 {
02172 centrepix = (float)row - ((float)oly - 1.)/2. ;
02173 pixvalue = 0. ;
02174 for ( i = 1 ; i < n_fitcoeffs ; i++ )
02175 {
02176 pixvalue += coeffs[i][col]*pow(centrepix, i) ;
02177 }
02178 podata[col+row*olx] = a0_clean[col] + pixvalue ;
02179 }
02180 }
02181
02182
02183 cpl_free(emline) ;
02184 cpl_free(spec) ;
02185 cpl_free(wave) ;
02186 cpl_free(a0) ;
02187 cpl_free(a0_clean) ;
02188
02189
02190 cpl_free(sub_col_index) ;
02191 cpl_free(sub_acoefs);
02192 cpl_free(sub_dacoefs) ;
02193
02194 cpl_free(a) ;
02195 cpl_free(z) ;
02196
02197 sinfo_new_destroy_2Dfloatarray(&bcoef,n_fitcoeffs) ;
02198 cpl_free(wcoefs) ;
02199
02200 return wavemap ;
02201 }
02202
02226 cpl_image * sinfo_new_create_shifted_slit_wavemap3 ( cpl_image * lineIm,
02227 float ** coeffs,
02228 int n_fitcoeffs,
02229 float * wavelength,
02230 float * intensity,
02231 int n_lines,
02232 int magFactor )
02233 {
02234
02235 cpl_image * wavemap ;
02236 double * result ;
02237 float * filter_spec ;
02238 float centreval ;
02239 float centrepix ;
02240 float cenpos, cenpix ;
02241 float pixvalue ;
02242 float wavelag_mean ;
02243
02244 float angst ;
02245
02246 float a_initial ;
02247
02248
02249 float par[MAXPAR] ;
02250 float derv_par[MAXPAR] ;
02251 int numpar, its ;
02252 int * mpar ;
02253 float tol, lab ;
02254 float * xdat, * wdat ;
02255 Vector * peak;
02256 int iters, xdim, ndat ;
02257 int row , col ;
02258 int i, j, k ;
02259 int sign, found, line, width ;
02260 int var, maxlag, cmin, cmax ;
02261
02262 float* emline=NULL ;
02263 float* spec=NULL ;
02264 float* wavelag=NULL ;
02265 float* wave=NULL ;
02266 double* a=NULL ;
02267 double* z=NULL ;
02268
02269 gsl_poly_complex_workspace * w ;
02270 double xcorr_max ;
02271 int delta ;
02272
02273 int ilx=0;
02274 int ily=0;
02275 float* pidata=NULL;
02276 int olx=0;
02277 int oly=0;
02278 float* podata=NULL;
02279
02280
02281
02282 if ( lineIm == NULL )
02283 {
02284 sinfo_msg_error (" no input image given!\n") ;
02285 return NULL ;
02286 }
02287 ilx=cpl_image_get_size_x(lineIm);
02288 ily=cpl_image_get_size_y(lineIm);
02289 pidata=cpl_image_get_data_float(lineIm);
02290
02291 if ( coeffs == NULL )
02292 {
02293 sinfo_msg_error (" no coefficient sinfo_matrix given!\n") ;
02294 return NULL ;
02295 }
02296 if ( n_fitcoeffs < 2 )
02297 {
02298 sinfo_msg_error (" wrong number of polynomial coefficients given!\n") ;
02299 return NULL ;
02300 }
02301
02302 if ( wavelength == NULL || intensity == NULL )
02303 {
02304 sinfo_msg_error (" no wavelength list given!\n") ;
02305 return NULL ;
02306 }
02307 if ( n_lines < 1 || magFactor < 1 )
02308 {
02309 sinfo_msg_error (" wrong n_lines or magFactor given!\n") ;
02310 return NULL ;
02311 }
02312
02313 var = (magFactor - 1)*(magFactor - 1) ;
02314
02315 if ( wavelength[0] > 10000. )
02316 {
02317
02318 angst = 10000. ;
02319 }
02320 else if ( wavelength[0] > 1000. && wavelength[0] < 10000. )
02321 {
02322
02323 angst = 1000. ;
02324 }
02325 else
02326 {
02327
02328 angst = 1. ;
02329 }
02330
02331
02332
02333
02334 if ( NULL == (wavemap = cpl_image_new ( ilx, ily,CPL_TYPE_FLOAT)) )
02335 {
02336 sinfo_msg_error (" could not allocate memory!\n") ;
02337 return NULL ;
02338 }
02339 podata=cpl_image_get_data_float(lineIm);
02340 olx=ilx;
02341 oly=ily;
02342
02343 emline=cpl_calloc(ily,sizeof(float)) ;
02344 spec=cpl_calloc(ily,sizeof(float)) ;
02345 wavelag=cpl_calloc(ilx,sizeof(float)) ;
02346 wave=cpl_calloc(n_lines,sizeof(float)) ;
02347 a=cpl_calloc(n_fitcoeffs,sizeof(double)) ;
02348 z=cpl_calloc(2*(n_fitcoeffs - 1),sizeof(double)) ;
02349
02350
02351
02352 for ( col = 0 ; col < ilx ; col++ )
02353 {
02354
02355 for ( i = 0 ; i < ily ; i++ )
02356 {
02357 emline[i] = 0. ;
02358 }
02359
02360 for ( i = 0 ; i < n_fitcoeffs ; i++ )
02361 {
02362
02363 if (i < n_fitcoeffs-1)
02364 {
02365 z[2*i] = 0. ;
02366 z[2*i+1] = 0. ;
02367 }
02368 a[i] = coeffs[i][col] ;
02369 }
02370
02371 a_initial = coeffs[0][col] ;
02372
02373 for ( line = 0 ; line < n_lines ; line++ )
02374 {
02375
02376 wave[line] = wavelength[line]/angst ;
02377
02378
02379
02380
02381
02382 a[0] = a_initial - wave[line] ;
02383
02384 if (NULL==(w=sinfo_gsl_poly_complex_workspace_alloc(n_fitcoeffs)))
02385 {
02386 sinfo_msg_error(" could not allocate complex workspace!") ;
02387 cpl_image_delete(wavemap) ;
02388 return NULL ;
02389 }
02390 if (-1 == sinfo_gsl_poly_complex_solve(a, n_fitcoeffs, w, z))
02391 {
02392 sinfo_msg_error("sinfo_gsl_poly_complex_solve did not work!") ;
02393 cpl_image_delete(wavemap) ;
02394 return NULL ;
02395 }
02396 sinfo_gsl_poly_complex_workspace_free(w) ;
02397
02398 j = 0 ;
02399 found = -1 ;
02400 for ( i = 0 ; i < n_fitcoeffs - 1 ; i++ )
02401 {
02402
02403 if( (z[2*i] > (-1.)*(float) ily/2. &&
02404 z[2*i] < (float)ily/2.) && z[2*i+1] == 0. )
02405 {
02406 found = 2*i ;
02407 j ++ ;
02408 }
02409 else
02410 {
02411 continue ;
02412 }
02413 }
02414 if ( j == 0 )
02415 {
02416 sinfo_msg_warning("no offset solution found for line %d "
02417 "in column %d\n", line, col) ;
02418 continue ;
02419 }
02420 else if ( j == 1 )
02421 {
02422 cenpos = z[found] + (float) ily /2. ;
02423 }
02424 else
02425 {
02426 sinfo_msg_warning("two or more offset solutions found for "
02427 "line %d in column %d\n", line, col) ;
02428 continue ;
02429 }
02430
02431
02432
02433
02434 cenpix = cenpos ;
02435
02436
02437
02438 cmin = (sinfo_new_nint(cenpix) - (var-1)) > 0 ?
02439 sinfo_new_nint(cenpix) - (var-1) : 0 ;
02440 cmax = (sinfo_new_nint(cenpix) + (var-1)) < ily ?
02441 sinfo_new_nint(cenpix) + (var-1) : ily ;
02442
02443
02444 for ( j = cmin ; j < cmax ; j++ )
02445 {
02446 emline[j] += intensity[line] *
02447 exp((double)(-0.5*(j-cenpix)*(j-cenpix))/(double)var) ;
02448 }
02449 }
02450
02451
02452
02453
02454
02455
02456 for ( k = 0 ; k < ily ; k++ )
02457 {
02458 spec[k] = 0. ;
02459 }
02460
02461
02462
02463 for ( row = 0 ; row < ily ; row++ )
02464 {
02465
02466 if (!isnan(pidata[col + row*ilx]) &&
02467 (pidata[col + row*ilx] > 0.))
02468 {
02469 spec[row] = pidata[col + row*ilx] ;
02470 }
02471 else
02472 {
02473 spec[row] = 0. ;
02474 }
02475 }
02476
02477 filter_spec = sinfo_function1d_filter_lowpass(spec, ily,
02478 LOW_PASS_GAUSSIAN,
02479 magFactor) ;
02480
02481
02482 result = sinfo_new_xcorrel( filter_spec, ily, emline, ily,
02483 ily/2, &delta, &maxlag, &xcorr_max) ;
02484
02485 if ( xcorr_max <= 0. )
02486 {
02487 sinfo_msg_warning("no positive cross correlation sum , "
02488 "col %d set to ZERO \n", col) ;
02489 for ( row = 0 ; row < ily ; row++ )
02490 {
02491 podata[col + row*ilx] = ZERO ;
02492 }
02493 sinfo_function1d_del(filter_spec) ;
02494 cpl_free(result) ;
02495 continue ;
02496 }
02497
02498
02499
02500
02501 i = maxlag; j = i+1;
02502 while (result[j] < result[i])
02503 {
02504 i++; j++;
02505 }
02506 i = maxlag; k = i-1;
02507 while (result[k] < result[i])
02508 {
02509 i--; k--;
02510 }
02511 width = j-k+1;
02512
02513 if ( NULL == (peak = sinfo_new_vector (width)) )
02514 {
02515 sinfo_msg_error (" cannot allocate new Vector \n") ;
02516 sinfo_function1d_del(filter_spec) ;
02517 cpl_free(result) ;
02518 return NULL ;
02519 }
02520
02521
02522
02523 xdat = (float *) cpl_calloc( peak -> n_elements, sizeof (float) ) ;
02524 wdat = (float *) cpl_calloc( peak -> n_elements, sizeof (float) ) ;
02525 mpar = (int *) cpl_calloc( MAXPAR, sizeof (int) ) ;
02526
02527
02528
02529
02530 for ( i = 0 ; i < width ; i++ )
02531 {
02532 peak -> data[i] = result[k+i]/xcorr_max * 100. ;
02533 xdat[i] = i;
02534 wdat[i] = 1.0;
02535 }
02536
02537
02538 xdim = XDIM;
02539 ndat = peak -> n_elements ;
02540 numpar = MAXPAR ;
02541 tol = TOL ;
02542 lab = LAB ;
02543 its = ITS ;
02544 par[1] = width/2.0 ;
02545 par[2] = (float) (maxlag - k) ;
02546 par[3] = (peak -> data[0] + peak -> data[peak->n_elements - 1]) / 2.0 ;
02547 par[0] = result[maxlag]/xcorr_max * 100. - (par[3]) ;
02548
02549 for ( i = 0 ; i < MAXPAR ; i++ )
02550 {
02551 derv_par[i] = 0.0 ;
02552 mpar[i] = 1 ;
02553 }
02554
02555
02556 if ( 0 > ( iters = sinfo_new_lsqfit_c( xdat, &xdim,
02557 peak -> data, wdat,
02558 &ndat, par, derv_par, mpar,
02559 &numpar, &tol, &its, &lab )) )
02560 {
02561 sinfo_msg_warning (" sinfo_new_lsqfit_c: least squares fit"
02562 " failed in col: %d, error no.: %d\n",
02563 col, iters) ;
02564 sinfo_new_destroy_vector ( peak ) ;
02565 cpl_free ( xdat ) ;
02566 cpl_free ( wdat ) ;
02567 cpl_free ( mpar ) ;
02568 sinfo_function1d_del(filter_spec) ;
02569 cpl_free(result) ;
02570 continue ;
02571 }
02572
02573 sinfo_new_destroy_vector ( peak ) ;
02574 cpl_free (xdat) ;
02575 cpl_free (wdat) ;
02576 cpl_free (mpar) ;
02577 sinfo_function1d_del(filter_spec) ;
02578 cpl_free(result) ;
02579
02580 wavelag[col] =((float)ily/2 - (float)k - par[2]) ;
02581
02582 }
02583
02584 if (FLT_MAX==(wavelag_mean=sinfo_new_clean_mean(wavelag, ilx, 10., 10.)) )
02585 {
02586 sinfo_msg_error(" could not determine a mean offset\n") ;
02587 return NULL ;
02588 }
02589
02590 if ( fabs(wavelag_mean) > (float)ily/20. )
02591 {
02592 sinfo_msg_error(" wavelag too big \n") ;
02593 return NULL ;
02594 }
02595
02596
02597
02598 for ( col = 0 ; col < ilx ; col++ )
02599 {
02600
02601
02602
02603
02604
02605
02606
02607 a_initial = coeffs[0][col] ;
02608 centreval = a_initial ;
02609 for ( i = 1 ; i < n_fitcoeffs ; i++ )
02610 {
02611 if ( i%2 == 0 )
02612 {
02613 sign = -1 ;
02614 }
02615 else
02616 {
02617 sign = 1 ;
02618 }
02619 centreval += (float)sign * coeffs[i][col]*pow(wavelag_mean, i) ;
02620 }
02621
02622
02623
02624 for ( row = 0 ; row < oly ; row++ )
02625 {
02626 centrepix = (float)row - ((float)oly - 1.)/2. ;
02627 pixvalue = 0. ;
02628 for ( i = 1 ; i < n_fitcoeffs ; i++ )
02629 {
02630 pixvalue += coeffs[i][col]*pow(centrepix, i) ;
02631 }
02632 podata[col+row*olx] = centreval + pixvalue ;
02633 }
02634 }
02635
02636
02637
02638 cpl_free(emline) ;
02639 cpl_free(spec) ;
02640 cpl_free(wavelag) ;
02641 cpl_free(wave) ;
02642 cpl_free(a) ;
02643 cpl_free(z) ;
02644
02645
02646 return wavemap ;
02647 }
02648
02671 float sinfo_new_check_line_positions ( cpl_image * lineIm,
02672 float ** coeffs,
02673 int n_fitcoeffs,
02674 float gdisp1,
02675 FitParams ** par )
02676 {
02677 float wave_shift=0 ;
02678 float amp[100] ;
02679 float sort_amp[100] ;
02680 float offset=0 ;
02681 float shift=0 ;
02682 float position=0;
02683 float lambda=0;
02684 float wave=0 ;
02685 int i=0;
02686 int j=0;
02687 int k=0;
02688 int l=0;
02689 int m=0;
02690 int n=0;
02691 int col=0;
02692 int firstj=0;
02693 float* shift_col=NULL ;
02694 int* foundit=NULL ;
02695 int n_lines=0;
02696 int lin, found=0 ;
02697 int lx=0;
02698 int ly=0;
02699 float* pdata=NULL;
02700
02701 if ( lineIm == NULL )
02702 {
02703 sinfo_msg_error (" no input image given!\n") ;
02704 return FLAG ;
02705 }
02706 lx=cpl_image_get_size_x(lineIm);
02707 ly=cpl_image_get_size_y(lineIm);
02708 pdata=cpl_image_get_data_float(lineIm);
02709
02710 if ( coeffs == NULL )
02711 {
02712 sinfo_msg_error (" no coefficient sinfo_matrix given!\n") ;
02713 return FLAG ;
02714 }
02715 if ( par == NULL )
02716 {
02717 sinfo_msg_error (" no fit parameters given!\n") ;
02718 return FLAG ;
02719 }
02720 if ( n_fitcoeffs < 2 )
02721 {
02722 sinfo_msg_error (" wrong number of polynomial coefficients given!\n") ;
02723 return FLAG ;
02724 }
02725
02726 offset = (float) (ly -1.) / 2. ;
02727 n_lines = par[0]->n_params/lx ;
02728
02729 shift_col=cpl_calloc(lx,sizeof(float)) ;
02730 foundit=cpl_calloc(par[0]->n_params,sizeof(int)) ;
02731
02732
02733
02734 for ( col = 0 ; col < lx ; col++ )
02735 {
02736 n = 0 ;
02737 for ( i = 0 ; i < par[0]->n_params ; i++ )
02738 {
02739 if (par[i]->column == col && par[i]->fit_par[2] != 0. &&
02740 par[i]->fit_par[1] > 1. && par[i]->fit_par[1] < 7. )
02741 {
02742 foundit[n] = i ;
02743 amp[n] = par[i]->fit_par[0] ;
02744 sort_amp[n] = amp[n] ;
02745 n++ ;
02746 }
02747 }
02748 sinfo_pixel_qsort(sort_amp, n) ;
02749
02750 if ( n > 5 )
02751 {
02752 firstj = n - 5 ;
02753 }
02754 else
02755 {
02756 firstj = 0 ;
02757 }
02758 l = 0 ;
02759 shift = 0 ;
02760 for ( j = firstj ; j < n ; j++ )
02761 {
02762 for ( m = 0 ; m < n ; m++ )
02763 {
02764 if ( sort_amp[j] == amp[m] )
02765 {
02766 position = par[foundit[m]]->fit_par[2] ;
02767 lambda = par[foundit[m]]->wavelength ;
02768 wave = 0 ;
02769 for ( k = 0 ; k < n_fitcoeffs ; k++ )
02770 {
02771 wave += coeffs[k][col]*pow(position-offset, k) ;
02772 }
02773 shift += lambda - wave ;
02774 l++ ;
02775 }
02776 }
02777 }
02778 if ( l == 0 ) continue ;
02779 shift_col[col] = shift/(float)l ;
02780 }
02781 wave_shift = sinfo_new_clean_mean(shift_col, lx, 10., 10.) ;
02782 sinfo_msg("Overall positioning error: %3.2g [um] %3.2g [pix]",
02783 wave_shift,wave_shift/fabs(gdisp1)) ;
02784
02785
02786
02787 for ( lin = 0 ; lin < n_lines ; lin++ )
02788 {
02789 for ( col = 0 ; col < lx ; col++ )
02790 {
02791 shift_col[col] = 0. ;
02792 found = -1 ;
02793 for ( i = 0 ; i < par[0]->n_params ; i++ )
02794 {
02795 if (par[i]->column == col && par[i]->fit_par[2] != 0. &&
02796 par[i]->fit_par[1] > 1. && par[i]->fit_par[1] < 7. &&
02797 par[i]->line == lin )
02798 {
02799 found = i ;
02800 }
02801 }
02802 if (found == -1) break ;
02803
02804 position = par[found]->fit_par[2] ;
02805 lambda = par[found]->wavelength ;
02806 wave = 0 ;
02807 for ( k = 0 ; k < n_fitcoeffs ; k++ )
02808 {
02809 wave += coeffs[k][col]*pow(position-offset, k) ;
02810 }
02811 shift_col[col] = lambda - wave ;
02812 }
02813 if (found != -1 )
02814 {
02815 sinfo_msg("shift: %3.2g [um] %3.2g (pix) at: %4.3f [um]",
02816 sinfo_new_clean_mean(shift_col,lx, 10., 10.),
02817 sinfo_new_clean_mean(shift_col,lx, 10., 10.)/fabs(gdisp1),
02818 lambda) ;
02819 }
02820 }
02821 cpl_free(shift_col) ;
02822 cpl_free(foundit) ;
02823
02824 return wave_shift ;
02825 }
02826
02827
02856 float sinfo_new_check_correlated_line_positions ( cpl_image * lineIm,
02857 float ** coeffs,
02858 int n_fitcoeffs,
02859 float * wavelength,
02860 float * intensity,
02861 int n_lines,
02862 float fwhm,
02863 float width,
02864 float min_amplitude,
02865 float dispersion,
02866 FitParams ** par )
02867 {
02868 float wave_shift=0 ;
02869 float offset=0;
02870 float shift=0;
02871 float position=0;
02872 float lambda=0;
02873 float wave=0;
02874 int i=0;
02875 int j=0;
02876 int k=0;
02877 int n=0;
02878 int c=0;
02879 int z=0;
02880 int col=0;
02881 int found=0;
02882 int line=0;
02883 int result=0;
02884 float cenpos=0;
02885 float angst=0;
02886 float a_initial=0;
02887
02888 int* foundit=NULL ;
02889 float* shift_col=NULL ;
02890 float* wave_cor=NULL ;
02891 double* a=NULL ;
02892 double* zroot=NULL ;
02893
02894 gsl_poly_complex_workspace * w=NULL ;
02895 Vector * vline=NULL;
02896 int * mpar=NULL;
02897 float * xdat=NULL;
02898 float * wdat=NULL;
02899 int lx=0;
02900 int ly=0;
02901 float* pdata=NULL;
02902
02903 if ( lineIm == NULL )
02904 {
02905 sinfo_msg_error (" no input image given!\n") ;
02906 return FLAG ;
02907 }
02908 lx=cpl_image_get_size_x(lineIm);
02909 ly=cpl_image_get_size_y(lineIm);
02910 pdata=cpl_image_get_data_float(lineIm);
02911
02912
02913 if ( coeffs == NULL )
02914 {
02915 sinfo_msg_error (" no coefficient sinfo_matrix given!\n") ;
02916 return FLAG ;
02917 }
02918 if ( par == NULL )
02919 {
02920 sinfo_msg_error (" no fit parameters given!\n") ;
02921 return FLAG ;
02922 }
02923 if ( n_fitcoeffs < 2 )
02924 {
02925 sinfo_msg_error (" wrong number of polynomial coefficients given!\n") ;
02926 return FLAG ;
02927 }
02928 if ( wavelength == NULL || intensity == NULL )
02929 {
02930 sinfo_msg_error (" no line list given!\n") ;
02931 return FLAG ;
02932 }
02933 if ( fwhm <= 0 )
02934 {
02935 sinfo_msg_error (" wrong guess fwhm given!\n") ;
02936 return FLAG ;
02937 }
02938 if ( width <= 0 )
02939 {
02940 sinfo_msg_error (" wrong half width given!\n") ;
02941 return FLAG ;
02942 }
02943 if ( min_amplitude <= 0 )
02944 {
02945 sinfo_msg_error (" wrong guess amplitude given!\n") ;
02946 return FLAG ;
02947 }
02948
02949
02950 if ( NULL == (vline = sinfo_new_vector (2*width + 1)) )
02951 {
02952 sinfo_msg_error (" cannot allocate new Vector \n") ;
02953 return -14 ;
02954 }
02955
02956 xdat = (float *) cpl_calloc( vline -> n_elements, sizeof (float) ) ;
02957 wdat = (float *) cpl_calloc( vline -> n_elements, sizeof (float) ) ;
02958 mpar = (int *) cpl_calloc( MAXPAR, sizeof (int) ) ;
02959
02960
02961 foundit=cpl_calloc(par[0]->n_params,sizeof(int)) ;
02962 shift_col=cpl_calloc(lx,sizeof(float)) ;
02963 wave_cor=cpl_calloc(n_lines,sizeof(float)) ;
02964 a=cpl_calloc(n_fitcoeffs,sizeof(float)) ;
02965 zroot=cpl_calloc(2*(n_fitcoeffs - 1),sizeof(float)) ;
02966
02967
02968
02969
02970
02971
02972 if ( wavelength[0] > 10000. )
02973 {
02974
02975 angst = 10000. ;
02976 }
02977 else if ( wavelength[0] > 1000. && wavelength[0] < 10000. )
02978 {
02979
02980 angst = 1000. ;
02981 }
02982 else
02983 {
02984
02985 angst = 1. ;
02986 }
02987 offset = ((float) ly -1.) / 2. ;
02988
02989 k = 0 ;
02990 for ( col = 10 ; col < 25 ; col++ )
02991 {
02992
02993 for ( i = 0 ; i < n_fitcoeffs ; i++ )
02994 {
02995
02996 if (i < n_fitcoeffs-1)
02997 {
02998 zroot[2*i] = 0. ;
02999 zroot[2*i+1] = 0. ;
03000 }
03001 a[i] = coeffs[i][col] ;
03002 }
03003 a_initial = a[0] ;
03004
03005
03006 for ( line = 0 ; line < n_lines ; line++ )
03007 {
03008
03009 wave_cor[line] = wavelength[line]/angst ;
03010 if (line > 0 && line < n_lines-1)
03011 {
03012 if (fabs((wave_cor[line] - wave_cor[line-1]) /
03013 dispersion ) < 2*width ||
03014 fabs((wave_cor[line] - wave_cor[line+1]) /
03015 dispersion ) < 2*width )
03016 {
03017 continue ;
03018 }
03019 }
03020
03021 a[0] = a_initial - wave_cor[line] ;
03022
03023 if (NULL==(w=sinfo_gsl_poly_complex_workspace_alloc(n_fitcoeffs)))
03024 {
03025 sinfo_msg_error(" could not allocate complex workspace!") ;
03026 return FLAG ;
03027 }
03028 if (-1 == sinfo_gsl_poly_complex_solve(a, n_fitcoeffs, w, zroot))
03029 {
03030 sinfo_msg_error(" sinfo_gsl_poly_complex_solve did not work!") ;
03031 return FLAG ;
03032 }
03033 sinfo_gsl_poly_complex_workspace_free(w) ;
03034
03035 j = 0 ;
03036 found = -1 ;
03037 for ( i = 0 ; i < n_fitcoeffs - 1 ; i++ )
03038 {
03039
03040 if( (zroot[2*i] > (-1.)*(float) ly/2. &&
03041 zroot[2*i] < (float)ly/2.) && zroot[2*i+1] == 0. )
03042 {
03043 found = 2*i ;
03044 j ++ ;
03045 }
03046 else
03047 {
03048 continue ;
03049 }
03050 }
03051
03052 if ( j == 0 )
03053 {
03054 sinfo_msg_warning(" no offset solution found for line %d "
03055 "in column %d\n", line, col) ;
03056 continue ;
03057 }
03058 else if ( j == 1 )
03059 {
03060 cenpos = zroot[found] + (float)ly / 2. ; ;
03061 }
03062 else
03063 {
03064 sinfo_msg_warning(" two or more offset solutions found for \
03065 line %d in column %d\n", line, col) ;
03066 continue ;
03067 }
03068
03069 if ( cenpos <= 0 )
03070 {
03071 continue ;
03072 }
03073
03074
03075
03076
03077
03078
03079 if ( (result = sinfo_new_line_fit ( lineIm, par[k],
03080 fwhm, line, col,
03081 width, cenpos, min_amplitude, vline,
03082 mpar, xdat, wdat ) ) < 0 )
03083 {
03084 sinfo_msg_debug ("sinfo_linefit failed, error no.: %d, "
03085 "column: %d, row: %f, line: %d\n",
03086 result, col, cenpos, line) ;
03087 continue ;
03088 }
03089 if ( (par[k] -> fit_par[0] <= 0.) || (par[k] -> fit_par[1] <= 0.)
03090 || (par[k] -> fit_par[2] <= 0.) )
03091 {
03092 sinfo_msg_warning ("negative fit parameters in column: %d, "
03093 "line: %d\n", col, line) ;
03094 continue ;
03095 }
03096 par[k] -> wavelength = wavelength[line] ;
03097 k++ ;
03098 }
03099
03100 }
03101
03102
03103 sinfo_new_destroy_vector(vline);
03104 cpl_free(xdat);
03105 cpl_free(wdat);
03106 cpl_free(mpar);
03107
03108
03109 c = 0 ;
03110 for ( col = 10 ; col < 25 ; col++ )
03111 {
03112 n = 0 ;
03113 for ( i = 0 ; i < k ; i++ )
03114 {
03115 if (par[i]->column == col && par[i]->fit_par[2] != 0. &&
03116 par[i]->fit_par[1] > 1. && par[i]->fit_par[1] < 7. )
03117 {
03118 foundit[n] = i ;
03119 n++ ;
03120 }
03121 }
03122 if ( n == 0 ) continue ;
03123
03124 shift = 0 ;
03125 z = 0 ;
03126 for ( j = 0 ; j < n ; j++ )
03127 {
03128 position = par[foundit[j]]->fit_par[2] ;
03129 lambda = par[foundit[j]]->wavelength ;
03130 line = par[foundit[j]]->line ;
03131 if (line > 0 && line < n_lines-1)
03132 {
03133 if (fabs((wave_cor[line] - wave_cor[line-1]) /
03134 dispersion ) < 2*width ||
03135 fabs((wave_cor[line] - wave_cor[line+1]) /
03136 dispersion ) < 2*width )
03137 {
03138 continue ;
03139 }
03140 }
03141 wave = 0 ;
03142 for ( i = 0 ; i < n_fitcoeffs ; i++ )
03143 {
03144 wave += coeffs[i][col]*pow(position-offset, i) ;
03145 }
03146 shift += lambda - wave ;
03147 z++ ;
03148 }
03149 shift_col[c] = shift/(float)z ;
03150 c++ ;
03151 }
03152 if ( c > 0 )
03153 {
03154 wave_shift = sinfo_new_clean_mean(shift_col, c, 10., 10.) ;
03155 sinfo_msg("overall positioning error in microns: %g", wave_shift) ;
03156 }
03157
03158
03159 for ( line = 0 ; line < n_lines ; line++ )
03160 {
03161 if (line > 0 && line < n_lines-1)
03162 {
03163 if (fabs((wave_cor[line] - wave_cor[line-1]) / dispersion ) <
03164 2*width ||
03165 fabs((wave_cor[line] - wave_cor[line+1]) / dispersion ) <
03166 2*width )
03167 {
03168 continue ;
03169 }
03170 }
03171
03172 c = 0 ;
03173 for ( col = 10 ; col < 25 ; col++ )
03174 {
03175 shift_col[c] = 0. ;
03176 found = -1 ;
03177 for ( i = 0 ; i < k ; i++ )
03178 {
03179 if (par[i]->column == col && par[i]->fit_par[2] != 0. &&
03180 par[i]->fit_par[1] > 1. && par[i]->fit_par[1] < 7. &&
03181 par[i]->line == line )
03182 {
03183 found = i ;
03184 }
03185 }
03186 if (found == -1) break ;
03187
03188 position = par[found]->fit_par[2] ;
03189 lambda = par[found]->wavelength ;
03190 wave = 0 ;
03191 for ( i = 0 ; i < n_fitcoeffs ; i++ )
03192 {
03193 wave += coeffs[i][col]*pow(position-offset, i) ;
03194 }
03195 shift_col[c] = lambda - wave ;
03196 c++ ;
03197 }
03198 if (found != -1 && c > 0 )
03199 {
03200 sinfo_msg("shift in microns: %g at wavelength: %f\n",
03201 sinfo_new_clean_mean(shift_col, c, 20., 20.), lambda) ;
03202 }
03203 }
03204
03205
03206
03207 cpl_free(foundit) ;
03208 cpl_free(shift_col) ;
03209 cpl_free(wave_cor) ;
03210 cpl_free(a) ;
03211 cpl_free(zroot) ;
03212
03213 return wave_shift ;
03214 }
03215
03216
03217
03242 static int
03243 sinfo_new_spred_coeffs_cross_slit_fit ( int n_columns,
03244 float ** acoefs,
03245 float ** dacoefs,
03246 Bcoeffs* bco,
03247 float sigma_factor,
03248 float dispersion,
03249 float pixel_dist,
03250 float * chisq,
03251 float ** sinfo_slit_pos )
03252 {
03253 float col_index;
03254
03255
03256 float ** ucoefs, **vcoefs, **covar ;
03257 float * acoefsclean ;
03258 double sum, sumq, mean ;
03259 double sigma ;
03260 double cliphi, cliplo ;
03261 float offset ;
03262 float threshold ;
03263
03264 int* edge=NULL ;
03265 float* sub_col_index=NULL ;
03266 float* sub_acoefs=NULL;
03267 float* sub_dacoefs=NULL ;
03268 float* wcoefs=NULL ;
03269
03270
03271 int ed1, ed2 ;
03272 int i, n, num, ndata ;
03273 int nc, ns ;
03274 int loc_index ;
03275 int sl_index;
03276 int last_i=PIXEL;
03277
03278 if ( n_columns < 1 )
03279 {
03280 sinfo_msg_error(" wrong number of image columns given\n") ;
03281 return -1 ;
03282 }
03283 if ( acoefs == NULL || dacoefs == NULL )
03284 {
03285 sinfo_msg_error(" acoeffs or errors of coefficients are not given") ;
03286 return -1 ;
03287 }
03288 if ( bco == NULL )
03289 {
03290 sinfo_msg_error(" bcoeffs are not allocated\n") ;
03291 return -1 ;
03292 }
03293 if ( sigma_factor <= 0. )
03294 {
03295 sinfo_msg_error(" impossible sigma_factor given!\n") ;
03296 return -1 ;
03297 }
03298 if ( dispersion == 0. )
03299 {
03300 sinfo_msg_error(" impossible dispersion given!\n") ;
03301 return -1 ;
03302 }
03303
03304
03305 edge=cpl_calloc(bco->n_slitlets,sizeof(int)) ;
03306 sub_col_index=cpl_calloc(n_columns,sizeof(float)) ;
03307 sub_acoefs=cpl_calloc(n_columns,sizeof(float));
03308 sub_dacoefs=cpl_calloc(n_columns,sizeof(float)) ;
03309
03310 wcoefs=cpl_calloc(bco->n_bcoeffs,sizeof(float)) ;
03311
03312
03313
03314
03315
03316
03317 n = 0 ;
03318 threshold = pixel_dist * fabs(dispersion) ;
03319 sinfo_slit_pos[0][0]=0 ;
03320 sl_index = 0;
03321
03322 for ( i = 0 ; i < n_columns - PIXEL ; )
03323 {
03324 if ( !isnan(acoefs[0][i+1]) &&
03325 acoefs[0][i+1] != 0. &&
03326 acoefs[0][i] != 0.
03327 && dacoefs[0][i+1] != 0.)
03328 {
03329 if ( isnan(acoefs[0][i]) || acoefs[0][i] == 0. )
03330 {
03331 if (fabs(acoefs[0][i+1] - acoefs[0][i-1]) >= threshold )
03332 {
03333
03334 edge[n] = i+1 ;
03335 sinfo_slit_pos[sl_index][1] = i ;
03336 sinfo_slit_pos[sl_index+1][0] = i + 1 ;
03337 sl_index++;
03338 n++ ;
03339 last_i = i;
03340 i += PIXEL ;
03341 }
03342 }
03343 else
03344 {
03345 if (fabs(acoefs[0][i+1] - acoefs[0][i]) >= threshold )
03346 {
03347
03348 edge[n] = i+1 ;
03349 sinfo_slit_pos[sl_index][1] = i ;
03350 sinfo_slit_pos[sl_index+1][0] = i + 1 ;
03351 sl_index++;
03352 n++ ;
03353 last_i = i;
03354 i += PIXEL ;
03355 }
03356 }
03357
03358
03359
03360
03361 if( ( (i-last_i) > 63 ) &&
03362 ( isnan(fabs(acoefs[0][i+1] - acoefs[0][i])) ||
03363 isnan(fabs(acoefs[0][i+1] - acoefs[0][i-1])) ) )
03364 {
03365 edge[n] = i+1 ;
03366 sinfo_slit_pos[sl_index][1] = i ;
03367 sinfo_slit_pos[sl_index+1][0] = i + 1 ;
03368 sl_index++;
03369 n++ ;
03370
03371 last_i = i;
03372 sinfo_msg_warning("2 recovered slitlet edge i=%d",i);
03373 i += PIXEL ;
03374
03375 }
03376 }
03377 i++ ;
03378 }
03379 sinfo_slit_pos[sl_index][1] = 2047;
03380
03381 if ( n != bco->n_slitlets - 1 )
03382 {
03383 sinfo_msg_error("could not find the right number of "
03384 "slitlets, found: %d\n",n+1) ;
03385 return -1 ;
03386 }
03387
03388
03389 for ( loc_index = 0 ; loc_index < bco->n_acoeffs ; loc_index++ )
03390 {
03391
03392 for ( ns = 0 ; ns < bco->n_slitlets ; ns++ )
03393 {
03394
03395 if ( ns == 0 )
03396 {
03397 ed1 = 0 ;
03398 ed2 = edge[0] ;
03399 }
03400 else if ( ns == bco->n_slitlets - 1 )
03401 {
03402 ed1 = edge[bco->n_slitlets - 2] ;
03403 ed2 = n_columns ;
03404 }
03405 else
03406 {
03407 ed1 = edge[ns-1] ;
03408 ed2 = edge[ns] ;
03409 }
03410
03411 nc = 0 ;
03412 for ( i = ed1 ; i < ed2 ; i++ )
03413 {
03414 if ( isnan(acoefs[loc_index][i]) ||
03415 acoefs[loc_index][i] == 0. ||
03416 dacoefs[loc_index][i] == 0. )
03417 {
03418 continue ;
03419 }
03420 else
03421 {
03422 nc++ ;
03423 }
03424 }
03425 if (NULL==(acoefsclean=(float*) cpl_calloc(nc , sizeof(float))) )
03426 {
03427 sinfo_msg_error("could not allocate memory for acoefsclean!");
03428 return -1 ;
03429 }
03430 nc = 0 ;
03431 for ( i = ed1 ; i < ed2 ; i++ )
03432 {
03433 if ( isnan(acoefs[loc_index][i]) ||
03434 acoefs[loc_index][i] == 0. ||
03435 dacoefs[loc_index][i] == 0. )
03436 {
03437 continue ;
03438 }
03439 else
03440 {
03441 acoefsclean[nc] = acoefs[loc_index][i] ;
03442 nc++ ;
03443 }
03444 }
03445
03446
03447
03448
03449
03450 sinfo_pixel_qsort(acoefsclean, nc) ;
03451
03452 sum = 0. ;
03453 sumq = 0. ;
03454 mean = 0. ;
03455 sigma = 0. ;
03456 n = 0 ;
03457 for ( i = (int)((float)nc*LOW_REJECT) ;
03458 i < (int)((float)nc*HIGH_REJECT) ; i++ )
03459 {
03460 sum += (double)acoefsclean[i] ;
03461 sumq += ((double)acoefsclean[i] * (double)acoefsclean[i]) ;
03462 n ++ ;
03463 }
03464 mean = sum/(double)n ;
03465 sigma = sqrt( sumq/(double)n - (mean * mean) ) ;
03466 cliphi = mean + sigma * (double)sigma_factor ;
03467 cliplo = mean - sigma * (double)sigma_factor ;
03468
03469 num = 0 ;
03470 col_index = 0 ;
03471 for ( i = ed1 ; i < ed2 ; i++ )
03472 {
03473
03474 if ( !isnan(acoefs[loc_index][i]) &&
03475 (acoefs[loc_index][i] <= cliphi) &&
03476 (acoefs[loc_index][i] >= cliplo) &&
03477 (dacoefs[loc_index][i] != 0. ) &&
03478 (acoefs[loc_index][i] != 0.) )
03479 {
03480 sub_acoefs[num] = acoefs[loc_index][i] ;
03481 sub_dacoefs[num] = dacoefs[loc_index][i] ;
03482 sub_col_index[num] = col_index ;
03483 num ++ ;
03484 }
03485 col_index++ ;
03486 }
03487 ndata = num ;
03488 offset = (float)(col_index-1) / 2. ;
03489
03490 if ( ndata < bco->n_bcoeffs )
03491 {
03492 sinfo_msg_error(" not enough data found in slitlet %da"
03493 " to determine the fit coefficients.\n", ns) ;
03494 cpl_free(acoefsclean) ;
03495 return -1 ;
03496 }
03497
03498
03499 ucoefs = sinfo_matrix(1, ndata, 1, bco->n_bcoeffs) ;
03500 vcoefs = sinfo_matrix(1, ndata, 1, bco->n_bcoeffs) ;
03501 covar = sinfo_matrix(1, bco->n_bcoeffs, 1, bco->n_bcoeffs) ;
03502
03503
03504 for ( i = 0 ; i < ndata ; i++ )
03505 {
03506 sub_col_index[i] = (sub_col_index[i] - offset) / offset ;
03507 }
03508
03509
03510 sinfo_svd_fitting ( sub_col_index-1, sub_acoefs-1,
03511 sub_dacoefs-1, ndata, bco[ns].b[loc_index]-1,
03512 bco->n_bcoeffs, ucoefs, vcoefs, wcoefs-1,
03513 covar, &chisq[ns], sinfo_fpol ) ;
03514
03515
03516 for ( i = 0 ; i < bco->n_bcoeffs ; i ++ )
03517 {
03518 bco[ns].b[loc_index][i] /= pow( offset, i ) ;
03519 }
03520
03521
03522 cpl_free (acoefsclean) ;
03523 sinfo_free_matrix( ucoefs, 1, 1) ;
03524 sinfo_free_matrix( vcoefs, 1, 1) ;
03525 sinfo_free_matrix( covar, 1,
03526 1) ;
03527
03528
03529 col_index = 0 ;
03530 for ( i = ed1 ; i < ed2 ; i++ )
03531 {
03532 acoefs[loc_index][i] = 0. ;
03533 for ( n = 0 ; n < bco->n_bcoeffs ; n++ )
03534 {
03535 acoefs[loc_index][i] += bco[ns].b[loc_index][n] *
03536 pow(col_index - offset, n) ;
03537 }
03538 col_index++ ;
03539 }
03540
03541 }
03542 }
03543
03544
03545 cpl_free(edge) ;
03546 cpl_free(sub_col_index) ;
03547 cpl_free(sub_acoefs);
03548 cpl_free(sub_dacoefs) ;
03549 cpl_free(wcoefs) ;
03550
03551 return 0 ;
03552 }
03553
03554
03603 cpl_image * sinfo_new_spred_wave_cal( cpl_image * image,
03604 FitParams ** par ,
03605 float ** abuf,
03606 int n_slitlets,
03607 int ** row_clean,
03608 float ** wavelength_clean,
03609 int * n_found_lines,
03610 float dispersion,
03611 int halfWidth,
03612 float minAmplitude,
03613 float max_residual,
03614 float fwhm,
03615 int n_a_fitcoefs,
03616 int n_b_fitcoefs,
03617 float sigmaFactor,
03618 float pixel_dist,
03619 float pixel_tolerance,
03620 float ** sinfo_slit_pos)
03621
03622
03623 {
03624 int i, j, k ;
03625 int n_fit ;
03626 int n_reject ;
03627 float * acoefs ;
03628 float * dacoefs ;
03629 float ** dabuf ;
03630 float chisq_poly ;
03631 float * chisq_cross ;
03632 int zeroind ;
03633 int crossInd ;
03634 Bcoeffs * bco ;
03635 cpl_image * wavemap ;
03636 int ilx=0;
03637 int ily=0;
03638 float* pidata=NULL;
03639
03640
03641 if ( NULL == image )
03642 {
03643 sinfo_msg_error(" no image given\n") ;
03644 return NULL ;
03645 }
03646 ilx=cpl_image_get_size_x(image);
03647 ily=cpl_image_get_size_y(image);
03648 pidata=cpl_image_get_data_float(image);
03649
03650 if ( par == NULL )
03651 {
03652 sinfo_msg_error(" no fit parameter data structure given\n") ;
03653 return NULL ;
03654 }
03655 if ( abuf == NULL )
03656 {
03657 sinfo_msg_error(" no buffer for fit coefficients given\n") ;
03658 return NULL ;
03659 }
03660 if ( n_slitlets <= 0 )
03661 {
03662 sinfo_msg_error(" impossible number of slitlets given\n") ;
03663 return NULL ;
03664 }
03665 if ( row_clean == NULL )
03666 {
03667 sinfo_msg_error(" no row_clean array given\n") ;
03668 return NULL ;
03669 }
03670 if ( wavelength_clean == NULL )
03671 {
03672 sinfo_msg_error(" no wavelength_clean array given\n") ;
03673 return NULL ;
03674 }
03675
03676 if ( dispersion == 0. )
03677 {
03678 sinfo_msg_error(" impossible dispersion given\n") ;
03679 return NULL ;
03680 }
03681
03682 if ( halfWidth <= 0 || halfWidth > ily/2 )
03683 {
03684 sinfo_msg_error(" impossible half width of the fitting box given\n") ;
03685 return NULL ;
03686 }
03687 if ( minAmplitude < 1. )
03688 {
03689 sinfo_msg_error(" impossible minimal amplitude\n") ;
03690 return NULL ;
03691 }
03692
03693 if ( max_residual <= 0. || max_residual > 1. )
03694 {
03695 sinfo_msg_error(" impossible max_residual given\n") ;
03696 return NULL ;
03697 }
03698 if ( fwhm <= 0. || fwhm > 10. )
03699 {
03700 sinfo_msg_error(" impossible fwhm given\n") ;
03701 return NULL ;
03702 }
03703
03704 if ( n_a_fitcoefs <= 0 || n_a_fitcoefs > 9 )
03705 {
03706 sinfo_msg_error(" unrealistic n_a_fitcoefs given\n") ;
03707 return NULL ;
03708 }
03709
03710 if ( n_b_fitcoefs <= 0 || n_b_fitcoefs > 9 )
03711 {
03712 sinfo_msg_error(" unrealistic n_b_fitcoefs given\n") ;
03713 return NULL ;
03714 }
03715 if ( sigmaFactor <= 0. )
03716 {
03717 sinfo_msg_error(" impossible sigmaFactor given\n") ;
03718 return NULL ;
03719 }
03720
03721
03722 n_reject = 0 ;
03723 n_fit = 0 ;
03724
03725
03726
03727 if ( 0 > (n_fit = sinfo_new_fit_lines( image , par, fwhm, n_found_lines,
03728 row_clean, wavelength_clean,
03729 halfWidth, minAmplitude )) )
03730 {
03731 sinfo_msg_error(" cannot fit the lines, error code of "
03732 "sinfo_fitLines: %d", n_fit) ;
03733 return NULL ;
03734 }
03735
03736
03737 if ( -1 == sinfo_new_check_for_fake_lines (par,
03738 dispersion,
03739 wavelength_clean,
03740 row_clean,
03741 n_found_lines,
03742 ilx,
03743 pixel_tolerance) )
03744 {
03745 sinfo_msg_error(" cannot fit the lines, error code of "
03746 " sinfo_fitLines: %d\n", n_fit) ;
03747 return NULL ;
03748 }
03749
03750
03751
03752 if (NULL==(acoefs = (float*) cpl_calloc (n_a_fitcoefs, sizeof(float))) ||
03753 NULL==(dacoefs = (float*) cpl_calloc (n_a_fitcoefs, sizeof(float))) ||
03754 NULL==(dabuf = (float**) cpl_calloc (n_a_fitcoefs, sizeof(float*))) ||
03755 NULL==(chisq_cross = (float*) cpl_calloc(n_slitlets, sizeof(float))) )
03756 {
03757 sinfo_msg_error(" cannot allocate memory\n") ;
03758 return NULL ;
03759 }
03760 for ( i = 0 ; i < n_a_fitcoefs ; i++ )
03761 {
03762 if ( NULL == (dabuf[i] = (float*) cpl_calloc(ilx, sizeof(float))) )
03763 {
03764 sinfo_msg_error(" cannot allocate memory\n") ;
03765 cpl_free ( acoefs ) ;
03766 cpl_free ( dacoefs ) ;
03767 cpl_free ( chisq_cross ) ;
03768 cpl_free(dabuf) ;
03769 return NULL ;
03770 }
03771 }
03772
03773
03774 k = 0 ;
03775 for ( i = 0 ; i < ilx ; i++ )
03776 {
03777 zeroind = 0 ;
03778 if ( FLT_MAX == (chisq_poly = sinfo_new_polyfit( par, i,
03779 n_found_lines[i],
03780 ily, dispersion,
03781 max_residual, acoefs,
03782 dacoefs, &n_reject,
03783 n_a_fitcoefs)) )
03784 {
03785 sinfo_msg_warning (" error in sinfo_polyfit in column: %d\n", i) ;
03786 for ( j = 0 ; j < n_a_fitcoefs ; j++ )
03787 {
03788 acoefs[j] = ZERO ;
03789 dacoefs[j] = ZERO ;
03790 }
03791 }
03792
03793 for ( j = 0 ; j < n_a_fitcoefs ; j++ )
03794 {
03795
03796 if ( acoefs[0] <= 0. || acoefs[1] ==0. ||
03797 dacoefs[j] == 0. || isnan(acoefs[j]) )
03798 {
03799 zeroind = 1 ;
03800 }
03801 }
03802 for ( j = 0 ; j < n_a_fitcoefs ; j++ )
03803 {
03804 if ( zeroind == 0 )
03805 {
03806 abuf[j][i] = acoefs[j] ;
03807 dabuf[j][i] = dacoefs[j] ;
03808 }
03809 else
03810 {
03811 abuf[j][i] = ZERO ;
03812 dabuf[j][i] = ZERO ;
03813 }
03814 }
03815 }
03816
03817
03818 if ( NULL == ( bco = sinfo_new_b_coeffs( n_slitlets,
03819 n_a_fitcoefs, n_b_fitcoefs)) )
03820 {
03821 sinfo_msg_error (" cannot allocate memory for the bcoeffs\n") ;
03822 for ( i = 0 ; i < n_a_fitcoefs ; i++ )
03823 {
03824 cpl_free (dabuf[i]) ;
03825 }
03826 cpl_free (dabuf) ;
03827 cpl_free ( acoefs ) ;
03828 cpl_free ( dacoefs ) ;
03829 cpl_free ( chisq_cross ) ;
03830 return NULL ;
03831 }
03832
03833
03834 if ( -1 == ( crossInd = sinfo_new_spred_coeffs_cross_slit_fit( ilx, abuf,
03835 dabuf,
03836 bco, sigmaFactor,
03837 dispersion,
03838 pixel_dist,
03839 chisq_cross,
03840 sinfo_slit_pos )) )
03841 {
03842 sinfo_msg_error (" cannot carry out the fitting of "
03843 "coefficients across the columns\n") ;
03844 for ( i = 0 ; i < n_a_fitcoefs ; i++ )
03845 {
03846 cpl_free (dabuf[i]) ;
03847 }
03848
03849 cpl_free (dabuf) ;
03850 cpl_free ( acoefs ) ;
03851 cpl_free ( dacoefs ) ;
03852 sinfo_new_destroy_b_coeffs(bco) ;
03853 cpl_free ( chisq_cross ) ;
03854 return NULL ;
03855 }
03856
03857 if ( NULL == (wavemap = sinfo_new_wave_map_slit (abuf, n_a_fitcoefs,
03858 ily, ilx)))
03859 {
03860 sinfo_msg_error (" cannot carry out wavemap creation\n") ;
03861 for ( i = 0 ; i < n_a_fitcoefs ; i++ )
03862 {
03863 cpl_free (dabuf[i]) ;
03864 }
03865
03866 cpl_free (dabuf) ;
03867 cpl_free ( acoefs ) ;
03868 cpl_free ( dacoefs ) ;
03869 sinfo_new_destroy_b_coeffs(bco) ;
03870 cpl_free ( chisq_cross ) ;
03871 return NULL ;
03872 }
03873
03874
03875 for ( i = 0 ; i < n_a_fitcoefs ; i++ )
03876 {
03877 cpl_free (dabuf[i]) ;
03878 }
03879 cpl_free (dabuf) ;
03880 cpl_free ( acoefs ) ;
03881 cpl_free ( dacoefs ) ;
03882 sinfo_new_destroy_b_coeffs(bco) ;
03883 cpl_free ( chisq_cross ) ;
03884
03885 return wavemap ;
03886 }
03887
03889