X-shooter Pipeline Reference Manual 3.8.15
xsh_data_order.c
Go to the documentation of this file.
1/* *
2 * This file is part of the ESO X-shooter Pipeline *
3 * Copyright (C) 2006 European Southern Observatory *
4 * *
5 * This library is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
9 * *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
14 * *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the Free Software *
17 * Foundation, 51 Franklin St, Fifth Floor, Boston, MA 02111-1307 USA *
18 * */
19
20/*
21 * $Author: amodigli $
22 * $Date: 2012-12-09 15:13:34 $
23 * $Revision: 1.96 $
24 * $Name: not supported by cvs2svn $
25 */
26
27#ifdef HAVE_CONFIG_H
28#include <config.h>
29#endif
30
31/*---------------------------------------------------------------------------*/
36/*---------------------------------------------------------------------------*/
37
41/*-----------------------------------------------------------------------------
42 Includes
43 ----------------------------------------------------------------------------*/
44
45#include <math.h>
46#include <xsh_data_order.h>
47#include <xsh_utils.h>
48#include <xsh_error.h>
49#include <xsh_utils_wrappers.h>
50#include <xsh_msg.h>
51#include <xsh_pfits.h>
52#include <xsh_dfs.h>
53#include <cpl.h>
54#include <xsh_utils_table.h>
55#include <xsh_data_instrument.h>
57
58/*----------------------------------------------------------------------------
59 Function implementation
60 ----------------------------------------------------------------------------*/
67void xsh_order_list_dump( xsh_order_list* list, const char * fname )
68{
69 int i ;
70 FILE * fout ;
71
72 if ( fname == NULL ) fout = stdout ;
73 else fout = fopen( fname, "w" ) ;
74 fprintf( fout, "Found %d orders\n", list->size ) ;
75
76 for( i = 0 ; i<list->size ; i++ ) {
77 int degree;
78 cpl_size j;
79
80 fprintf( fout, "order: %d, ", list->list[i].absorder ) ;
81 fprintf( fout, "Starty: %d, Endy: %d\n", list->list[i].starty,
82 list->list[i].endy ) ;
83 degree = cpl_polynomial_get_degree( list->list[i].cenpoly ) ;
84 for( j = 0 ; j<= degree ; j++ )
85 fprintf( fout, " %lf ",
86 cpl_polynomial_get_coeff( list->list[i].cenpoly, &j ) ) ;
87 for( j = 0 ; j<= degree ; j++ )
88 fprintf( fout, "%lf ",
89 cpl_polynomial_get_coeff( list->list[i].edglopoly, &j ) ) ;
90 for( j = 0 ; j<= degree ; j++ )
91 fprintf( fout, " %lf ",
92 cpl_polynomial_get_coeff( list->list[i].edguppoly, &j ) ) ;
93 fprintf( fout, "\n" ) ;
94 }
95 if ( fname != NULL ) fclose( fout ) ;
96}
97
106{
107 int i ;
108 /*
109 Verify that data are correct
110 */
111
112 for( i = 0 ; i<list->size ; i++ )
113 if ( list->list[i].endy <= list->list[i].starty ) {
114 list->list[i].endy = ny;
115 list->list[i].starty = 1;
116 }
117
118 return ;
119}
120
121/*--------------------------------------------------------------------------*/
129/*---------------------------------------------------------------------------*/
131{
132 xsh_order_list* result = NULL;
133
135 XSH_CALLOC(result,xsh_order_list,1);
136 result->size = size;
137 XSH_CALLOC(result->list, xsh_order, result->size);
139
140 cleanup:
141 if (cpl_error_get_code() != CPL_ERROR_NONE) {
142 xsh_order_list_free(&result);
143 }
144 return result;
145}
146
147/*--------------------------------------------------------------------------*/
154/*---------------------------------------------------------------------------*/
156{
157 xsh_order_list* result = NULL;
158 int size;
159 XSH_INSTRCONFIG * config = NULL;
160
161 /* check input parameters */
162 XSH_ASSURE_NOT_NULL(instr);
163 check( config = xsh_instrument_get_config( instr ) ) ;
164 XSH_ASSURE_NOT_NULL( config ) ;
165 size = config->orders;
166 check( result = xsh_order_list_new( size));
167 result->instrument = instr;
168 result->absorder_min = config->order_min;
169 result->absorder_max = config->order_max;
170 result->bin_x = xsh_instrument_get_binx( instr ) ;
171 result->bin_y = xsh_instrument_get_biny( instr ) ;
172
173 cleanup:
174 if (cpl_error_get_code() != CPL_ERROR_NONE) {
175 xsh_order_list_free(&result);
176 }
177 return result;
178}
179
180/*---------------------------------------------------------------------------*/
189/*---------------------------------------------------------------------------*/
191{
192 cpl_table* table = NULL;
193 cpl_propertylist* header = NULL;
194 const char* tablename = NULL;
195 xsh_order_list* result = NULL;
196 int i = 0, pol_degree = 0;
197 cpl_size k=0;
198 /* check input parameters */
199 XSH_ASSURE_NOT_NULL( frame);
200 XSH_ASSURE_NOT_NULL( instr);
201
202 /* get table filename */
203 check( tablename = cpl_frame_get_filename(frame));
204
205 XSH_TABLE_LOAD( table, tablename);
206 /* to be able to run with less orders in spectral format tab */
207
208 check(result = xsh_order_list_create(instr));
209 check(header = cpl_propertylist_load(tablename,0));
210 check(cpl_propertylist_append(result->header, header));
211 /*
212 xsh_msg("size=%d check=%d",result->size, cpl_table_get_nrow(table));
213 XSH_ASSURE_NOT_ILLEGAL(result->size == cpl_table_get_nrow(table));
214 */
215
216 for(i=0;i<result->size;i++){
217 /* load the order in structure */
219 CPL_TYPE_INT, i, &(result->list[i].order)));
221 CPL_TYPE_INT, i, &(result->list[i].absorder)));
222 /* Get the polynomial degree */
224 CPL_TYPE_INT, i, &pol_degree);
225 if ( cpl_error_get_code() != CPL_ERROR_NONE ) {
226 pol_degree = 2 ;
227 cpl_error_reset() ;
228 }
229
230 result->list[i].pol_degree = pol_degree ;
231
232 check(result->list[i].edguppoly = cpl_polynomial_new(1));
233 check(result->list[i].cenpoly = cpl_polynomial_new(1));
234 check(result->list[i].edglopoly = cpl_polynomial_new(1));
235
236 check(result->list[i].slicuppoly = cpl_polynomial_new(1));
237 check(result->list[i].sliclopoly = cpl_polynomial_new(1));
238
239 for( k = 0 ; k <= pol_degree ; k++ ) {
240 char colname[32] ;
241 float coef ;
242
243 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_CENTER, k);
244 check(xsh_get_table_value(table, colname, CPL_TYPE_FLOAT, i, &coef));
245 check(cpl_polynomial_set_coeff(result->list[i].cenpoly,
246 &k,coef));
247
248 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_EDGLO, k);
249 check(xsh_get_table_value(table, colname, CPL_TYPE_FLOAT, i, &coef));
250 check(cpl_polynomial_set_coeff(result->list[i].edglopoly,
251 &k,coef));
252
253 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_EDGUP, k);
254 check(xsh_get_table_value(table, colname, CPL_TYPE_FLOAT, i, &coef));
255 check(cpl_polynomial_set_coeff(result->list[i].edguppoly,
256 &k,coef));
257
258 /* Compatibility with old order table (had only SLIT) */
259 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_SLICUP, k);
260 if ( cpl_table_has_column( table, colname ) == 1 ) {
261 check(xsh_get_table_value(table, colname, CPL_TYPE_FLOAT, i, &coef));
262 check(cpl_polynomial_set_coeff(result->list[i].slicuppoly,
263 &k,coef));
264 }
265 else check(cpl_polynomial_set_coeff(result->list[i].slicuppoly,
266 &k, 0.));
267
268 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_SLICLO, k);
269 if ( cpl_table_has_column( table, colname ) == 1 ) {
270 check(xsh_get_table_value(table, colname, CPL_TYPE_FLOAT, i, &coef));
271 check(cpl_polynomial_set_coeff(result->list[i].sliclopoly,
272 &k,coef));
273 }
274 else check(cpl_polynomial_set_coeff(result->list[i].sliclopoly,
275 &k, 0.));
276
277 }
278
279 /* Starty/Endy */
281 CPL_TYPE_INT, i, &result->list[i].starty));
283 CPL_TYPE_INT, i, &result->list[i].endy));
284
285 /*check_msg(
286 result->list[i].cencoefsig0 = cpl_table_get_float(table,
287 "CENCOEFSIG0",i,flag),
288 "try to load column CENCOEFSIG0 , line %d",i);
289 check_msg(
290 result->list[i].cencoefsig1 = cpl_table_get_float(table,
291 "CENCOEFSIG1",i,flag),
292 "try to load column CENCOEFSIG1 , line %d",i);
293 check_msg(
294 result->list[i].cencoefsig2 = cpl_table_get_float(table,
295 "CENCOEFSIG2",i,flag),
296 "try to load column CENCOEFSIG2 , line %d",i);
297 check_msg(
298 result->list[i].edgupcoefsig0 = cpl_table_get_float(table,
299 "EDGUPCOEFSIG0",i,flag),
300 "Try to load column EDGUPCOEFSIG0, line %d",i);
301 check_msg(
302 result->list[i].edgupcoefsig1 = cpl_table_get_float(table,
303 "EDGUPCOEFSIG1",i,flag),
304 "try to load column EDGUPCOEFSIG1, line %d",i);
305 check_msg(
306 result->list[i].edgupcoefsig2 = cpl_table_get_float(table,
307 "EDGUPCOEFSIG2",i,flag),
308 "try to load column EDGUPCOEFSIG2, line %d",i);
309 check_msg(
310 result->list[i].edglocoefsig0 = cpl_table_get_float(table,
311 "EDGLOCOEFSIG0",i,flag),
312 "try to load column EDGLOCOEFSIG0, line %d",i);
313 check_msg(
314 result->list[i].edglocoefsig1 = cpl_table_get_float(table,
315 "EDGLOCOEFSIG1",i,flag),
316 "try to load column EDGLOCOEFSIG1, line %d",i);
317 check_msg(
318 result->list[i].edglocoefsig2 = cpl_table_get_float(table,
319 "EDGLOCOEFSIG2",i,flag),
320 "try to load column EDGLOCOEFSIG2, line %d",i);
321 */
322 }
323
324 result->bin_x = xsh_instrument_get_binx( instr ) ;
325 result->bin_y = xsh_instrument_get_biny( instr ) ;
326 xsh_msg_dbg_medium( "Order Table Load, Binning: %d x %d", result->bin_x,
327 result->bin_y);
328
329 cleanup:
330 if (cpl_error_get_code () != CPL_ERROR_NONE) {
331 xsh_error_msg("can't load frame %s",cpl_frame_get_filename(frame));
332 xsh_order_list_free(&result);
333 }
334 xsh_free_propertylist(&header);
335 XSH_TABLE_FREE( table);
336 return result;
337}
338
339/*---------------------------------------------------------------------------*/
349/*---------------------------------------------------------------------------*/
350
352 double* posx, double* posy, int deg_poly)
353{
354 int ordersize, i, nborder, nb_keep_order;
355 cpl_vector *vx = NULL, *vy = NULL;
356
357 XSH_ASSURE_NOT_NULL( list);
359 XSH_ASSURE_NOT_NULL( posx);
360 XSH_ASSURE_NOT_NULL( posy);
361 XSH_ASSURE_NOT_ILLEGAL( deg_poly >= 0);
362
363 ordersize = 0;
364 nborder = 0;
365 nb_keep_order = 0;
366 xsh_msg("Fit order traces");
367 xsh_msg_dbg_high("List size=%d",size);
368 xsh_msg_dbg_high("Fit a polynomial of degree %d by order",deg_poly);
369 xsh_msg_dbg_high("Search from order %d to %d", list->absorder_min,
370 list->absorder_max);
371 for(i=1; i <= size; i++) {
372 if ( i < size && fabs(order[i-1] - order[i] ) < 0.0001) {
373 ordersize++;
374 }
375 else {
376 int absorder = order[i-1];
377
378 if( (absorder >= list->absorder_min) &&
379 (absorder <= list->absorder_max) ){
380
381 ordersize++;
382 check( vx = cpl_vector_wrap( ordersize, &(posx[i-ordersize])));
383 check( vy = cpl_vector_wrap( ordersize, &(posy[i-ordersize])));
384 xsh_msg_dbg_low("%d) absorder %lg nbpoints %d",
385 nborder+1, order[i-1],ordersize);
386 XSH_ASSURE_NOT_ILLEGAL_MSG(ordersize > deg_poly,
387 "You must have more points to fit correctly this order (may be detectarclines-ordertab-deg-y is too large or (for xsh_predict) detectarclines-min-sn is too large)");
388 check( list->list[nb_keep_order].cenpoly =
389 xsh_polynomial_fit_1d_create(vy, vx, deg_poly,NULL));
390 list->list[nb_keep_order].order = nborder;
391 list->list[nb_keep_order].absorder = (int)(order[i-1]);
392
395 nb_keep_order++;
396 }
397 else{
398 xsh_msg("WARNING skipping absorder %d because is not in range",
399 absorder);
400 }
401 nborder++;
402 ordersize = 0;
403 }
404 }
405 XSH_ASSURE_NOT_ILLEGAL_MSG( list->size == nb_keep_order,"to fix this, in xsh_predict, you may try to decrease detectarclines-min-sn");
406 cleanup:
409 return;
410}
411
412/*---------------------------------------------------------------------------*/
417/*---------------------------------------------------------------------------*/
419{
420 int i = 0;
421
422 if (list && *list){
423 /* free the list */
424 for (i = 0; i < (*list)->size; i++){
425 xsh_free_polynomial(&(*list)->list[i].cenpoly);
426 xsh_free_polynomial(&(*list)->list[i].edguppoly);
427 xsh_free_polynomial(&(*list)->list[i].edglopoly);
428 xsh_free_polynomial(&(*list)->list[i].slicuppoly);
429 xsh_free_polynomial(&(*list)->list[i].sliclopoly);
430 xsh_free_polynomial(&(*list)->list[i].blazepoly);
431 }
432 if ((*list)->list){
433 cpl_free( (*list)->list);
434 }
435 xsh_free_propertylist(&((*list)->header));
436 cpl_free( *list);
437 *list = NULL;
438 }
439}
440
441/*---------------------------------------------------------------------------*/
442/*
443 @brief
444 Get index by absorder
445 @param[in] list
446 The order_list
447 @param[in] absorder
448 The abs order
449 @return
450 The index in order list corresponding to the absorder
451*/
452/*---------------------------------------------------------------------------*/
454 double absorder)
455{
456 int idx = 0;
457 int size = 0;
458
459 XSH_ASSURE_NOT_NULL( list);
460 size = list->size;
461 while (idx < size && (list->list[idx].absorder != absorder)){
462 idx++;
463 }
465
466 cleanup:
467 return idx;
468
469}
470/*---------------------------------------------------------------------------*/
476/*---------------------------------------------------------------------------*/
478{
479 cpl_propertylist * res = NULL;
480
482 res = list->header;
483 cleanup:
484 return res;
485}
486/*---------------------------------------------------------------------------*/
493/*---------------------------------------------------------------------------*/
495{
496 int res = 0;
497 /* check input parameters */
499 XSH_ASSURE_NOT_ILLEGAL(i >= 0 && i< list->size);
500 res = floor( convert_data_to_bin( list->list[i].starty, list->bin_y)+0.5);
501
502 cleanup:
503 return res;
504}
505
506/*---------------------------------------------------------------------------*/
513/*---------------------------------------------------------------------------*/
515{
516 int res = 100000000;
517 /* check input parameters */
519 XSH_ASSURE_NOT_ILLEGAL(i >= 0 && i< list->size);
520 res = floor(convert_data_to_bin( (double)list->list[i].endy,
521 list->bin_y)+0.5);
522 cleanup:
523 return res;
524}
525
526int xsh_order_list_get_order( xsh_order_list * list, int absorder )
527{
528 int i = 0 ;
529
531
532 for( i = 0 ; i<list->size ; i++ )
533 if ( list->list[i].absorder == absorder ) return i ;
534
535 return -1 ;
536 cleanup:
537 return -1 ;
538}
539
540/*---------------------------------------------------------------------------*/
541/*
542 @brief
543 Merge to list in a new list
544 @param[in] lista
545 The first order list
546 @param[in] listb
547 The second order list
548 @return
549 A new list corresponding to (lista,listb)
550*/
551/*---------------------------------------------------------------------------*/
553 xsh_order_list* listb)
554{
555 xsh_order_list* result = NULL;
556 int size = 0;
557 int i,j;
558
559 XSH_ASSURE_NOT_NULL( lista);
560 XSH_ASSURE_NOT_NULL( listb);
561
562 size = lista->size+listb->size;
563 check( result = xsh_order_list_new( size));
564
565 for( i=0; i< lista->size; i++){
566 result->list[i].order = i;
567 result->list[i].absorder = lista->list[i].absorder;
568 result->list[i].starty = lista->list[i].starty;
569 result->list[i].endy = lista->list[i].endy;
570 result->list[i].cenpoly = cpl_polynomial_duplicate(
571 lista->list[i].cenpoly);
572 result->list[i].edguppoly = cpl_polynomial_duplicate(
573 lista->list[i].edguppoly);
574 result->list[i].edglopoly = cpl_polynomial_duplicate(
575 lista->list[i].edglopoly);
576 result->list[i].slicuppoly = cpl_polynomial_duplicate(
577 lista->list[i].slicuppoly);
578 result->list[i].sliclopoly = cpl_polynomial_duplicate(
579 lista->list[i].sliclopoly);
580 }
581
582 for( i=0; i< listb->size; i++){
583 j= lista->size+i;
584 result->list[j].order = i;
585 result->list[j].absorder = listb->list[i].absorder;
586 result->list[j].starty = listb->list[i].starty;
587 result->list[j].endy = listb->list[i].endy;
588 result->list[j].cenpoly = cpl_polynomial_duplicate(
589 listb->list[i].cenpoly);
590 result->list[j].edguppoly = cpl_polynomial_duplicate(
591 listb->list[i].edguppoly);
592 result->list[j].edglopoly = cpl_polynomial_duplicate(
593 listb->list[i].edglopoly);
594 result->list[j].slicuppoly = cpl_polynomial_duplicate(
595 listb->list[i].slicuppoly);
596 result->list[j].sliclopoly = cpl_polynomial_duplicate(
597 listb->list[i].sliclopoly);
598 }
599
600 cleanup:
601 if (cpl_error_get_code() != CPL_ERROR_NONE) {
602 xsh_order_list_free(&result);
603 }
604 return result;
605}
606
607
608/*---------------------------------------------------------------------------*/
617/*---------------------------------------------------------------------------*/
619{
620 XSH_ASSURE_NOT_NULL( list);
621 list->bin_x = bin;
622
623 cleanup:
624 return;
625}
626
627/*---------------------------------------------------------------------------*/
636/*---------------------------------------------------------------------------*/
638{
639 XSH_ASSURE_NOT_NULL( list);
640 list->bin_y = bin;
641
642 cleanup:
643 return;
644}
645
646/*---------------------------------------------------------------------------*/
658/*---------------------------------------------------------------------------*/
659double xsh_order_list_eval( xsh_order_list* list, cpl_polynomial *poly,
660 double y)
661{
662 double result=0;
663 double y_no_bin;
664 double x_no_bin;
665
666 XSH_ASSURE_NOT_NULL( list);
667 XSH_ASSURE_NOT_NULL( poly);
668
669 y_no_bin = convert_bin_to_data( y, list->bin_y);
670 check( x_no_bin = cpl_polynomial_eval_1d( poly, y_no_bin, NULL));
671 result = convert_data_to_bin( x_no_bin, list->bin_x);
672
673 cleanup:
674 return result;
675}
676
677/*---------------------------------------------------------------------------*/
691/*---------------------------------------------------------------------------*/
692int xsh_order_list_eval_int( xsh_order_list* list, cpl_polynomial *poly,
693 double y)
694{
695 double res = 0.0;
696 int result=0;
697
698 XSH_ASSURE_NOT_NULL( list);
699 XSH_ASSURE_NOT_NULL( poly);
700
701 check( res = xsh_order_list_eval( list, poly, y));
702 result = floor( res+0.5);
703
704 cleanup:
705 return result;
706}
707
708
709/*---------------------------------------------------------------------------*/
721/*---------------------------------------------------------------------------*/
722void xsh_order_list_apply_shift( xsh_order_list *list, double xshift,
723 double yshift)
724{
725 cpl_polynomial *p = NULL;
726 double coef;
727 cpl_size pows = 0;
728 int i;
729
730 XSH_ASSURE_NOT_NULL( list);
731
732 for( i=0; i< list->size; i++){
733 p = list->list[i].cenpoly;
734 check( coef = cpl_polynomial_get_coeff( p, &pows));
735 coef += xshift;
736 check( cpl_polynomial_set_coeff( p, &pows, coef));
737
738 p = list->list[i].edguppoly;
739 if ( p != NULL){
740 check( coef = cpl_polynomial_get_coeff( p, &pows));
741 coef += xshift;
742 check( cpl_polynomial_set_coeff( p, &pows, coef));
743 }
744 p = list->list[i].edglopoly;
745 if ( p != NULL){
746 check( coef = cpl_polynomial_get_coeff( p, &pows));
747 coef += xshift;
748 check( cpl_polynomial_set_coeff( p, &pows, coef));
749 }
750 p = list->list[i].sliclopoly;
751 if ( p != NULL){
752 check( coef = cpl_polynomial_get_coeff( p, &pows));
753 coef += xshift;
754 check( cpl_polynomial_set_coeff( p, &pows, coef));
755 }
756 p = list->list[i].slicuppoly;
757 if ( p != NULL){
758 check( coef = cpl_polynomial_get_coeff( p, &pows));
759 coef += xshift;
760 check( cpl_polynomial_set_coeff( p, &pows, coef));
761 }
762 }
763
764 cleanup:
765 return;
766}
767/*---------------------------------------------------------------------------*/
768
769/*---------------------------------------------------------------------------*/
787/*---------------------------------------------------------------------------*/
788cpl_frame*
790 const char* filename, const char* tag,const int ny)
791{
792 cpl_table* table = NULL;
793 cpl_table* tabqc = NULL;
794 cpl_frame * result = NULL ;
795 int i=0;
796 cpl_size k ;
797 int pol_degree ;
798 char colname[32] ;
799 int PointStep = 8 ;
800 //XSH_INSTRCONFIG *config = NULL;
801 int nraw;
802 int* porder=NULL;
803 int* pabsorder=NULL;
804 double* pcenterx=NULL;
805 double* pcentery=NULL;
806 double* pedgeupx=NULL;
807 double* pedgelox=NULL;
808 double* pslicupx=NULL;
809 double* psliclox=NULL;
810 int iorder=0;
811 int iy=0;
812 cpl_table *tab_ext = NULL;
813 int norder=0;
814 /* check input parameters */
815 XSH_ASSURE_NOT_NULL( order_list);
816 XSH_ASSURE_NOT_NULL( filename);
819
820 //check( config = xsh_instrument_get_config( instrument));
821 check( pol_degree = cpl_polynomial_get_degree(
822 order_list->list[0].cenpoly));
823 XSH_ASSURE_NOT_ILLEGAL_MSG( pol_degree > 0,"Possibly detectarclines-ordertab-deg-y is too small" );
824
825 /* create a table */
826 check(table = cpl_table_new( order_list->size));
827
828 /* create column names */
829 check(
830 cpl_table_new_column( table, XSH_ORDER_TABLE_COLNAME_ORDER,
831 CPL_TYPE_INT));
832 check(
833 cpl_table_new_column( table, XSH_ORDER_TABLE_COLNAME_ABSORDER,
834 CPL_TYPE_INT));
835
836 /* Create as many column as needed, according to the polynomial degree */
837 for( k = 0 ; k<= pol_degree ; k++ ) {
838
839 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_CENTER, k);
840 check(
841 cpl_table_new_column(table, colname, CPL_TYPE_FLOAT));
842 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_EDGUP, k);
843 check(
844 cpl_table_new_column(table, colname, CPL_TYPE_FLOAT));
845 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_EDGLO, k);
846 check(
847 cpl_table_new_column(table, colname, CPL_TYPE_FLOAT));
848
849 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_SLICUP, k);
850 check(
851 cpl_table_new_column(table, colname, CPL_TYPE_FLOAT));
852
853 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_SLICLO, k);
854 check(
855 cpl_table_new_column(table, colname, CPL_TYPE_FLOAT));
856 }
857 check( cpl_table_new_column( table, XSH_ORDER_TABLE_DEGY, CPL_TYPE_INT ) ) ;
858
859 check(
860 cpl_table_new_column(table,XSH_ORDER_TABLE_COLNAME_STARTY,
861 CPL_TYPE_INT));
862 check(
863 cpl_table_new_column(table,XSH_ORDER_TABLE_COLNAME_ENDY,
864 CPL_TYPE_INT));
865 check(cpl_table_set_size(table,order_list->size));
866
867
868 /* insert data */
869 for(i=0;i<order_list->size;i++){
870 check(cpl_table_set_int(table,XSH_ORDER_TABLE_COLNAME_ORDER,
871 i,order_list->list[i].order));
872 check(cpl_table_set_int(table,XSH_ORDER_TABLE_COLNAME_ABSORDER,
873 i,order_list->list[i].absorder));
874 check(cpl_table_set_int(table,XSH_ORDER_TABLE_COLNAME_STARTY,
875 i,order_list->list[i].starty));
876 check(cpl_table_set_int(table,XSH_ORDER_TABLE_COLNAME_ENDY,
877 i,order_list->list[i].endy));
878
879 for( k = 0 ; k <= pol_degree ; k++ ) {
880 double coef ;
881
882 /* Get and Write coef from center polynomial */
883 check(coef = cpl_polynomial_get_coeff(order_list->list[i].cenpoly,&k));
884 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_CENTER, k);
885 check(cpl_table_set(table, colname,i,coef));
886
887 /* Get and Write coef from upper polynomial */
888 if ( order_list->list[i].edguppoly != NULL ) {
889 check(coef = cpl_polynomial_get_coeff(order_list->list[i].edguppoly,&k));
890 }
891 else coef = 0.0 ;
892 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_EDGUP, k);
893 check(cpl_table_set(table, colname,i,coef));
894
895 /* Get and Write coef from lower polynomial */
896 if ( order_list->list[i].edglopoly != NULL ) {
897 check(coef = cpl_polynomial_get_coeff(order_list->list[i].edglopoly,&k));
898 }
899 else coef = 0.0;
900 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_EDGLO, k);
901 check(cpl_table_set(table, colname,i,coef));
902
903 /* Get and Write coef from slic lower polynomial */
904 if ( order_list->list[i].sliclopoly != NULL ) {
905 check(coef = cpl_polynomial_get_coeff(order_list->list[i].sliclopoly,&k));
906 }
907 else coef = 0.0 ;
908 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_SLICLO, k);
909 check(cpl_table_set(table, colname, i, coef));
910
911 /* Get and Write coef from slic upper polynomial */
912 if ( order_list->list[i].slicuppoly != NULL ) {
913 check(coef = cpl_polynomial_get_coeff(order_list->list[i].slicuppoly,&k));
914 }
915 else coef = 0.0 ;
916 sprintf(colname, "%s%"CPL_SIZE_FORMAT, XSH_ORDER_TABLE_COLNAME_SLICUP, k);
917 check(cpl_table_set(table, colname, i, coef));
918
919 }
920 check( cpl_table_set(table, XSH_ORDER_TABLE_DEGY, i, pol_degree ) ) ;
921 }
922
923
924 //Now we dump detailed centre/edge/slicer traces info in a table extension
925 nraw = order_list->size*(ny/PointStep+0.5);
926
927 check( tabqc = cpl_table_new(nraw));
928 cpl_table_new_column(tabqc,XSH_ORDER_TABLE_COLNAME_ORDER,CPL_TYPE_INT);
929 cpl_table_new_column(tabqc,XSH_ORDER_TABLE_COLNAME_ABSORDER,CPL_TYPE_INT);
930 cpl_table_new_column(tabqc,XSH_ORDER_TABLE_COLNAME_CENTERX,CPL_TYPE_DOUBLE);
931 cpl_table_new_column(tabqc,XSH_ORDER_TABLE_COLNAME_CENTERY,CPL_TYPE_DOUBLE);
932
933 cpl_table_fill_column_window(tabqc,XSH_ORDER_TABLE_COLNAME_ORDER,0,nraw,-1);
934 cpl_table_fill_column_window(tabqc,XSH_ORDER_TABLE_COLNAME_ABSORDER,0,nraw,-1);
935 cpl_table_fill_column_window(tabqc,XSH_ORDER_TABLE_COLNAME_CENTERX,0,nraw,-1);
936 cpl_table_fill_column_window(tabqc,XSH_ORDER_TABLE_COLNAME_CENTERY,0,nraw,-1);
937
938 porder=cpl_table_get_data_int(tabqc,XSH_ORDER_TABLE_COLNAME_ORDER);
939 pabsorder=cpl_table_get_data_int(tabqc,XSH_ORDER_TABLE_COLNAME_ABSORDER);
940 pcenterx=cpl_table_get_data_double(tabqc,XSH_ORDER_TABLE_COLNAME_CENTERX);
941 pcentery=cpl_table_get_data_double(tabqc,XSH_ORDER_TABLE_COLNAME_CENTERY);
942
944 cpl_table_new_column(tabqc,XSH_ORDER_TABLE_COLNAME_EDGLOX,CPL_TYPE_DOUBLE);
945 cpl_table_new_column(tabqc,XSH_ORDER_TABLE_COLNAME_EDGUPX,CPL_TYPE_DOUBLE);
946 cpl_table_fill_column_window(tabqc,XSH_ORDER_TABLE_COLNAME_EDGLOX,0,nraw,-1);
947 cpl_table_fill_column_window(tabqc,XSH_ORDER_TABLE_COLNAME_EDGUPX,0,nraw,-1);
948 pedgelox=cpl_table_get_data_double(tabqc,XSH_ORDER_TABLE_COLNAME_EDGLOX);
949 pedgeupx=cpl_table_get_data_double(tabqc,XSH_ORDER_TABLE_COLNAME_EDGUPX);
950
951 if ( order_list->list[0].slicuppoly != NULL ) {
952 cpl_table_new_column(tabqc,XSH_ORDER_TABLE_COLNAME_SLICLOX,CPL_TYPE_DOUBLE);
953 cpl_table_new_column(tabqc,XSH_ORDER_TABLE_COLNAME_SLICUPX,CPL_TYPE_DOUBLE);
954
955 cpl_table_fill_column_window(tabqc,XSH_ORDER_TABLE_COLNAME_SLICLOX,0,nraw,-1);
956 cpl_table_fill_column_window(tabqc,XSH_ORDER_TABLE_COLNAME_SLICUPX,0,nraw,-1);
957
958 psliclox=cpl_table_get_data_double(tabqc,XSH_ORDER_TABLE_COLNAME_SLICLOX);
959 pslicupx=cpl_table_get_data_double(tabqc,XSH_ORDER_TABLE_COLNAME_SLICUPX);
960 }
961 }
962 /* insert qc data */
963 //Note that to work with ds9 coordinates we add 0.5 both to x and y pos
964 k=0;
965 for( iorder=0; iorder< order_list->size; iorder++){
966 int starty, endy;
967
968 xsh_msg_dbg_high(" Produce solution for order %d",
969 order_list->list[iorder].absorder);
970 /* AMO this fixes the problem with EDGE order table found for UVB at com1*/
971 check( starty = order_list->list[iorder].starty);
972 check( endy = order_list->list[iorder].endy);
973#if 0
974 if ( starty == -1 && endy == -1 ) {
975 xsh_msg( " **** Order %d Discarded", order_list->list[iorder].absorder);
976 continue ;
977 }
978#endif
979 if (starty == 0){
980 xsh_msg("Warning starty equal zero, put starty ==> 1");
981 starty = 1;
982 }
983 if ( endy == 0){
984 xsh_msg("Warning starty equal zero, put endy ==> %d",ny);
985 endy = ny;
986 }
987 /* xsh_msg("Y start %d %d",starty,endy); */
988 for( iy=starty; iy<=endy; iy= iy+PointStep){
989 float dx;
990
991 check( dx = cpl_polynomial_eval_1d( order_list->list[iorder].cenpoly,
992 iy, NULL));
993 porder[k]=iorder;
994 pabsorder[k]=order_list->list[iorder].absorder;
995 pcenterx[k]=dx;
996 pcentery[k]=iy;
997 /* xsh_msg("cx=%g cy=%d pcx=%g pcy=%g",dx,iy,pcenterx[k],pcentery[k]); */
999 check(dx=cpl_polynomial_eval_1d(order_list->list[iorder].edglopoly,
1000 iy, NULL ) ) ;
1001 pedgelox[k]=dx;
1002 check(dx=cpl_polynomial_eval_1d(order_list->list[iorder].edguppoly,
1003 iy, NULL ) ) ;
1004 pedgeupx[k]=dx;
1005 /* Check if IFU */
1006 if ( order_list->list[iorder].slicuppoly != NULL ) {
1007 check(dx=cpl_polynomial_eval_1d(order_list->list[iorder].slicuppoly,
1008 iy, NULL ) ) ;
1009 pslicupx[k]=dx;
1010 }
1011 if ( order_list->list[iorder].sliclopoly != NULL ) {
1012 check(dx=cpl_polynomial_eval_1d(order_list->list[iorder].sliclopoly,
1013 iy, NULL ) ) ;
1014 psliclox[k]=dx;
1015 }
1016 } //end check on edges
1017 k++;
1018 } //end loop on y
1019 if(starty!=-999) {
1020 /* -999 can occur only in QC mode and is used as flag to skip
1021 edge detection on a given order. This was explitly asked by QC.
1022 Normal user mode should never have this behaviour.
1023 */
1024 norder++;
1025 }
1026 } //end loop on orders
1027
1028 check( cpl_table_and_selected_int( tabqc, XSH_ORDER_TABLE_COLNAME_ORDER,
1029 CPL_GREATER_THAN, -1));
1030
1031 tab_ext = cpl_table_extract_selected( tabqc);
1032
1033 /* create fits file */
1034 check( xsh_pfits_set_pcatg( order_list->header, tag));
1035 if (strstr(tag, "EDGE") != NULL) {
1036 cpl_propertylist_append_int(order_list->header,XSH_QC_ORD_EDGE_NDET, norder);
1037 cpl_propertylist_set_comment(order_list->header,XSH_QC_ORD_EDGE_NDET,
1038 "number of detected order edges");
1039 }
1040 check( cpl_table_save(table, order_list->header, NULL, filename,
1041 CPL_IO_DEFAULT));
1042 check( cpl_table_save(tab_ext, NULL, NULL, filename,
1043 CPL_IO_EXTEND));
1044
1045 /* Create the frame */
1046 check( result = xsh_frame_product( filename, tag, CPL_FRAME_TYPE_TABLE,
1047 CPL_FRAME_GROUP_PRODUCT, CPL_FRAME_LEVEL_TEMPORARY));
1048
1049 cleanup:
1050 xsh_free_table( &tab_ext);
1051 xsh_free_table( &tabqc);
1052 xsh_free_table( &table);
1053 return result;
1054}
1055
1056
1057void xsh_order_split_qth_d2( cpl_frame* order_tab_frame,
1058 cpl_frame* spectralformat_frame, cpl_frame** qth_order_tab_frame,
1059 cpl_frame** d2_order_tab_frame, xsh_instrument *instr)
1060{
1061 cpl_table *order_tab = NULL;
1062 cpl_table *order_tab_ext = NULL;
1063 const char* order_tab_name = NULL;
1064 int order_tab_size;
1065 cpl_table *order_tab_qth = NULL;
1066 cpl_table *order_tab_d2 = NULL;
1067 cpl_table *order_tab_ext_qth = NULL;
1068 cpl_table *order_tab_ext_d2 = NULL;
1069 xsh_spectralformat_list *spectralformat = NULL;
1070 cpl_propertylist *header = NULL;
1071 int i=0;
1072
1073 XSH_ASSURE_NOT_NULL( order_tab_frame);
1074 XSH_ASSURE_NOT_NULL( spectralformat_frame);
1075 XSH_ASSURE_NOT_NULL( qth_order_tab_frame);
1076 XSH_ASSURE_NOT_NULL( d2_order_tab_frame);
1077 XSH_ASSURE_NOT_NULL( instr);
1078
1079 check( spectralformat = xsh_spectralformat_list_load( spectralformat_frame,
1080 instr));
1081 check( order_tab_name = cpl_frame_get_filename( order_tab_frame));
1082 XSH_TABLE_LOAD( order_tab, order_tab_name);
1083 check(order_tab_ext=cpl_table_load(order_tab_name,2,0));
1084 check( header = cpl_propertylist_load( order_tab_name, 0));
1085 check( order_tab_size = cpl_table_get_nrow( order_tab));
1086 for (i=0; i< order_tab_size; i++){
1087 int absorder;
1088 const char* lamp = NULL;
1089
1091 CPL_TYPE_INT, i, &absorder));
1092 check( lamp = xsh_spectralformat_list_get_lamp( spectralformat,
1093 absorder));
1094 XSH_ASSURE_NOT_NULL( lamp);
1095 if ( strcmp(lamp,"QTH")==0){
1096 check( cpl_table_select_row( order_tab, i));
1097 }
1098 else{
1099 check( cpl_table_unselect_row( order_tab, i));
1100 }
1101 }
1102
1103 check( order_tab_qth = cpl_table_extract_selected( order_tab));
1104 check( cpl_table_not_selected( order_tab));
1105 check( order_tab_d2 = cpl_table_extract_selected( order_tab));
1106
1107 cpl_table_and_selected_int(order_tab_ext,"ABSORDER",CPL_GREATER_THAN,XSH_ORDER_MIN_UVB_D2-1);
1108 check( order_tab_ext_d2 = cpl_table_extract_selected( order_tab_ext));
1109 cpl_table_select_all(order_tab_ext);
1110
1111 cpl_table_and_selected_int(order_tab_ext,"ABSORDER",CPL_LESS_THAN,XSH_ORDER_MAX_UVB_QTH+1);
1112 check( order_tab_ext_qth = cpl_table_extract_selected( order_tab_ext));
1113
1114
1115 check( cpl_table_save( order_tab_qth, header, NULL, "ORDER_TAB_CENTR_QTH_UVB.fits", CPL_IO_DEFAULT));
1116 check( cpl_table_save( order_tab_ext_qth, header, NULL, "ORDER_TAB_CENTR_QTH_UVB.fits", CPL_IO_EXTEND));
1117 check( cpl_table_save( order_tab_d2, header, NULL, "ORDER_TAB_CENTR_D2_UVB.fits", CPL_IO_DEFAULT));
1118 check( cpl_table_save( order_tab_ext_d2, header, NULL, "ORDER_TAB_CENTR_D2_UVB.fits", CPL_IO_EXTEND));
1119 xsh_add_temporary_file("ORDER_TAB_CENTR_QTH_UVB.fits");
1120 xsh_add_temporary_file("ORDER_TAB_CENTR_D2_UVB.fits");
1121 *qth_order_tab_frame = cpl_frame_new();
1122 cpl_frame_set_filename( *qth_order_tab_frame, "ORDER_TAB_CENTR_QTH_UVB.fits");
1123 *d2_order_tab_frame = cpl_frame_new();
1124 cpl_frame_set_filename( *d2_order_tab_frame, "ORDER_TAB_CENTR_D2_UVB.fits");
1125 cleanup:
1126 xsh_spectralformat_list_free( &spectralformat);
1127 xsh_free_propertylist( &header);
1128 xsh_free_table( &order_tab);
1129 xsh_free_table( &order_tab_qth);
1130 xsh_free_table( &order_tab_d2);
1131 xsh_free_table( &order_tab_ext);
1132 xsh_free_table( &order_tab_ext_d2);
1133 xsh_free_table( &order_tab_ext_qth);
1134
1135 return;
1136}
static int starty
static int endy
static int degree
static int norder
static xsh_instrument * instrument
static int PointStep
xsh_order_list * xsh_order_list_create(xsh_instrument *instr)
create an empty order list
void xsh_order_split_qth_d2(cpl_frame *order_tab_frame, cpl_frame *spectralformat_frame, cpl_frame **qth_order_tab_frame, cpl_frame **d2_order_tab_frame, xsh_instrument *instr)
void xsh_order_list_set_bin_y(xsh_order_list *list, int bin)
Set the bin of image in y.
int xsh_order_list_get_index_by_absorder(xsh_order_list *list, double absorder)
void xsh_order_list_apply_shift(xsh_order_list *list, double xshift, double yshift)
Shift a order list.
cpl_frame * xsh_order_list_save(xsh_order_list *order_list, xsh_instrument *instrument, const char *filename, const char *tag, const int ny)
Save an order list to a frame.
void xsh_order_list_set_bin_x(xsh_order_list *list, int bin)
Set the bin of image in x.
int xsh_order_list_eval_int(xsh_order_list *list, cpl_polynomial *poly, double y)
Evaluate an order list poly but return the central pixel position rounding the polynomial.
xsh_order_list * xsh_order_list_load(cpl_frame *frame, xsh_instrument *instr)
load an order list from a frame
xsh_order_list * xsh_order_list_merge(xsh_order_list *lista, xsh_order_list *listb)
cpl_propertylist * xsh_order_list_get_header(xsh_order_list *list)
get header of the table
int xsh_order_list_get_starty(xsh_order_list *list, int i)
get position on Y axis of first pixel detected on order
void xsh_order_list_dump(xsh_order_list *list, const char *fname)
void xsh_order_list_fit(xsh_order_list *list, int size, double *order, double *posx, double *posy, int deg_poly)
fit the polynomial solution of given points
int xsh_order_list_get_endy(xsh_order_list *list, int i)
get position on Y axis of last pixel detected on order
int xsh_order_list_get_order(xsh_order_list *list, int absorder)
xsh_order_list * xsh_order_list_new(int size)
Create a new order list from size (no check)
void xsh_order_list_free(xsh_order_list **list)
free memory associated to an order_list
void xsh_order_list_verify(xsh_order_list *list, int ny)
double xsh_order_list_eval(xsh_order_list *list, cpl_polynomial *poly, double y)
Evaluate an order list poly.
const char * xsh_spectralformat_list_get_lamp(xsh_spectralformat_list *list, int absorder)
xsh_spectralformat_list * xsh_spectralformat_list_load(cpl_frame *frame, xsh_instrument *instr)
Load a spectralformat list from a frame.
void xsh_spectralformat_list_free(xsh_spectralformat_list **list)
Free memory associated to an spactralformat_list.
#define XSH_ASSURE_NOT_ILLEGAL(cond)
Definition: xsh_error.h:107
#define check(COMMAND)
Definition: xsh_error.h:71
#define XSH_ASSURE_NOT_ILLEGAL_MSG(cond, msg)
Definition: xsh_error.h:111
#define xsh_error_msg(...)
Definition: xsh_error.h:94
#define XSH_ASSURE_NOT_NULL(pointer)
Definition: xsh_error.h:99
int xsh_instrument_get_binx(xsh_instrument *instrument)
XSH_INSTRCONFIG * xsh_instrument_get_config(xsh_instrument *i)
Get the instrument default set of keywords.
int xsh_instrument_get_biny(xsh_instrument *instrument)
int size
int * y
#define xsh_msg_dbg_medium(...)
Definition: xsh_msg.h:44
#define xsh_msg(...)
Print a message on info level.
Definition: xsh_msg.h:121
#define xsh_msg_dbg_low(...)
Definition: xsh_msg.h:48
#define xsh_msg_dbg_high(...)
Definition: xsh_msg.h:40
void xsh_pfits_set_pcatg(cpl_propertylist *plist, const char *value)
Write the PCATG value.
Definition: xsh_pfits.c:1008
void xsh_unwrap_vector(cpl_vector **v)
Unwrap a vector and set the pointer to NULL.
Definition: xsh_utils.c:2345
void xsh_free_polynomial(cpl_polynomial **p)
Deallocate a polynomial and set the pointer to NULL.
Definition: xsh_utils.c:2194
double convert_data_to_bin(double data, int binning)
Definition: xsh_utils.c:3246
double convert_bin_to_data(double bin_data, int binning)
Definition: xsh_utils.c:3228
void xsh_free_table(cpl_table **t)
Deallocate a table and set the pointer to NULL.
Definition: xsh_utils.c:2133
void xsh_free_propertylist(cpl_propertylist **p)
Deallocate a property list and set the pointer to NULL.
Definition: xsh_utils.c:2179
cpl_error_code xsh_get_table_value(const cpl_table *table, const char *colname, cpl_type coltype, int i, void *result)
Read a table value from a fits table.
void xsh_add_temporary_file(const char *name)
Add temporary file to temprary files list.
Definition: xsh_utils.c:1432
xsh_instrument * instrument
cpl_propertylist * header
xsh_order * list
cpl_polynomial * edguppoly
cpl_polynomial * edglopoly
cpl_polynomial * slicuppoly
cpl_polynomial * sliclopoly
cpl_polynomial * cenpoly
#define XSH_ORDER_MIN_UVB_D2
#define XSH_ORDER_MAX_UVB_QTH
#define XSH_ORDER_TABLE_COLNAME_SLICUP
#define XSH_ORDER_TABLE_COLNAME_SLICUPX
#define XSH_ORDER_TABLE_COLNAME_SLICLOX
#define XSH_ORDER_TABLE_COLNAME_EDGLOX
#define XSH_ORDER_TABLE_COLNAME_SLICLO
#define XSH_ORDER_TABLE_COLNAME_ENDY
#define XSH_ORDER_TABLE_COLNAME_EDGUP
#define XSH_ORDER_TABLE_COLNAME_CENTERX
#define XSH_ORDER_TABLE_COLNAME_STARTY
#define XSH_ORDER_TABLE_COLNAME_EDGLO
#define XSH_ORDER_TABLE_COLNAME_CENTERY
#define XSH_ORDER_TABLE_COLNAME_ABSORDER
#define XSH_ORDER_TABLE_COLNAME_CENTER
#define XSH_ORDER_TABLE_COLNAME_EDGUPX
#define XSH_ORDER_TABLE_DEGY
#define XSH_ORDER_TABLE_COLNAME_ORDER
int ny
int order
Definition: xsh_detmon_lg.c:80
cpl_frame * xsh_frame_product(const char *fname, const char *tag, cpl_frame_type type, cpl_frame_group group, cpl_frame_level level)
Creates a frame with given characteristics.
Definition: xsh_dfs.c:930
#define XSH_ORDER_TAB_EDGES
Definition: xsh_dfs.h:554
#define XSH_CMP_TAG_LAMP(tag_in, TAG)
Definition: xsh_dfs.h:1536
#define XSH_QC_ORD_EDGE_NDET
Definition: xsh_pfits_qc.h:123
#define XSH_NEW_PROPERTYLIST(POINTER)
Definition: xsh_utils.h:70
#define XSH_CALLOC(POINTER, TYPE, SIZE)
Definition: xsh_utils.h:56
#define XSH_TABLE_LOAD(TABLE, NAME)
#define XSH_TABLE_FREE(TABLE)
cpl_polynomial * xsh_polynomial_fit_1d_create(const cpl_vector *x_pos, const cpl_vector *values, int degree, double *mse)