source: trunk/FACT++/gui/RawEventsViewer/RawEventsViewer.cc

Last change on this file was 19692, checked in by tbretz, 3 months ago
The average curve errorneously took into account empty channels.
File size: 75.8 KB
Line 
1/*
2 * QtGl.cpp
3 *
4 *  Created on: Jul 19, 2011
5 *      Author: lyard
6 *
7 ******
8 */
9#include <math.h>
10#include <fstream>
11
12#include <boost/date_time/local_time/local_time.hpp>
13
14#include "RawEventsViewer.h"
15
16#include <QFileDialog>
17#include <QMouseEvent>
18
19#include <qwt_symbol.h>
20#include <qwt_plot_grid.h>
21#pragma GCC diagnostic push
22#pragma GCC diagnostic ignored "-Woverloaded-virtual"
23#include <qwt_plot_zoomer.h>
24#pragma GCC diagnostic pop
25
26#include "src/Configuration.h"
27#include "externals/factfits.h"
28
29
30using namespace std;
31
32#undef ACTUAL_NUM_PIXELS
33#define ACTUAL_NUM_PIXELS 1440
34
35//bounding box for diplaying the impulse curve
36float bboxMin[2] = {-0.8,-0.9};
37float bboxMax[2] = {0.8,-0.3};
38/************************************************************
39 * CALC BLUR COLOR if in blur display mode, calculate the interpolated
40 * colour for a given vertex
41 ************************************************************/
42void RawDataViewer::calcBlurColor(int pixel,  int vertex)
43{
44    GLfloat color[3];
45    int first, second;
46    first = vertex-1;
47    second = vertex;
48    if (first < 0)
49        first = 5;
50
51    first = neighbors[pixel][first];
52    second = neighbors[pixel][second];
53//    cout << pixel << " " << vertex << " " << "first: " << first << " second: " << second << endl;
54    for (int i=0;i<3;i++)
55        color[i] = pixelsColor[pixel][i];
56    float divide = 1;
57    if (first != -1)
58    {
59        divide++;
60        for (int i=0;i<3;i++)
61            color[i] += pixelsColor[first][i];
62    }
63    if (second != -1)
64    {
65        divide++;
66        for (int i=0;i<3;i++)
67            color[i] += pixelsColor[second][i];
68    }
69    for (int i=0;i<3;i++)
70        color[i] /= divide;
71
72//    cout << color[0] << " " << color[1] << " " << color[2] << endl;
73
74    glColor3fv(color);
75}
76void RawDataViewer::calcMidBlurColor(int pixel, int vertex)
77{
78    GLfloat color[3];
79    int first;
80    first = vertex-1;
81    if (first < 0)
82        first = 5;
83    first = neighbors[pixel][first];
84    for (int i=0;i<3;i++)
85        color[i] = pixelsColor[pixel][i];
86    float divide = 1;
87    if (first != -1)
88    {
89        divide++;
90        for (int i=0;i<3;i++)
91            color[i] += pixelsColor[first][i];
92    }
93    for (int i=0;i<3;i++)
94        color[i] /= divide;
95    glColor3fv(color);
96}
97/************************************************************
98 * DRAW BLURRY HEXAGON. draws a solid hexagon, with interpolated colours
99 ************************************************************/
100void RawDataViewer::drawBlurryHexagon(int index)
101{
102
103//per-pixel mesh
104    GLfloat color[3];
105    for (int i=0;i<3;i++)
106        color[i] = pixelsColor[index][i];
107    glBegin(GL_TRIANGLES);
108    calcBlurColor(index, 0);
109    glVertex2fv(verticesList[verticesIndices[index][0]]);
110    glColor3fv(color);
111    glVertex2fv(pixelsCoords[index]);
112
113    calcBlurColor(index, 1);
114    glVertex2fv(verticesList[verticesIndices[index][1]]);
115
116    glVertex2fv(verticesList[verticesIndices[index][1]]);
117    glColor3fv(color);
118    glVertex2fv(pixelsCoords[index]);
119
120    calcBlurColor(index, 2);
121    glVertex2fv(verticesList[verticesIndices[index][2]]);
122
123    glVertex2fv(verticesList[verticesIndices[index][2]]);
124    glColor3fv(color);
125    glVertex2fv(pixelsCoords[index]);
126
127    calcBlurColor(index, 3);
128    glVertex2fv(verticesList[verticesIndices[index][3]]);
129
130    glVertex2fv(verticesList[verticesIndices[index][3]]);
131    glColor3fv(color);
132    glVertex2fv(pixelsCoords[index]);
133
134    calcBlurColor(index, 4);
135    glVertex2fv(verticesList[verticesIndices[index][4]]);
136
137    glVertex2fv(verticesList[verticesIndices[index][4]]);
138    glColor3fv(color);
139    glVertex2fv(pixelsCoords[index]);
140
141    calcBlurColor(index, 5);
142    glVertex2fv(verticesList[verticesIndices[index][5]]);
143
144    glVertex2fv(verticesList[verticesIndices[index][5]]);
145    glColor3fv(color);
146    glVertex2fv(pixelsCoords[index]);
147
148    calcBlurColor(index, 0);
149    glVertex2fv(verticesList[verticesIndices[index][0]]);
150    glEnd();
151
152    return;
153}
154
155/************************************************************
156 * DRAW CAMERA draws all the camera pixels
157 ************************************************************/
158void RawDataViewer::drawCamera(bool alsoWire)
159{
160    glLoadIdentity();
161    if (!drawImpulse)
162    {
163        glTranslatef(0,-0.44,0);
164        glRotatef(cameraRotation, 0,0,-1);
165        if (cameraRotation == 90)
166        {
167            glTranslatef(-0.45,-0.45,0);
168        }
169        if (cameraRotation == -90)
170        {
171            glTranslatef(0.45,-0.45,0);
172        }
173        glScalef(1.5,1.5,1);
174    }
175    else
176    {
177        glRotatef(cameraRotation, 0,0,-1);
178          if (cameraRotation == 90)
179        {
180            glTranslatef(-0.45/1.5,-0.45/1.5,0);
181        }
182        if (cameraRotation == -90)
183        {
184            glTranslatef(0.45/1.5,-0.45/1.5,0);
185        }
186  }
187    glColor3f(0.5,0.5,0.5);
188    glLineWidth(1.0);
189    float color;
190
191    for (int i=0;i<ACTUAL_NUM_PIXELS;i++)
192    {
193        if (!nRoi)
194          color = (float)(i)/(float)(ACTUAL_NUM_PIXELS);
195        else
196
197//        if (_softwareOrdering)
198//            color = float(eventData[nRoi*i + whichSlice] + (VALUES_SPAN/2))/(float)(VALUES_SPAN-1);
199//        else
200            color = i<nPixels ? float(eventData[nRoi*hardwareMapping[i] + whichSlice]+(VALUES_SPAN/2))/(float)(VALUES_SPAN-1) : 0;
201        if (logScale)
202        {
203            color *= 9;
204            color += 1;
205            color = log10(color);
206        }
207
208        if (color < ss[0])
209        {
210            pixelsColor[i][0] = tooLowValueCoulour[0];
211            pixelsColor[i][1] = tooLowValueCoulour[1];
212            pixelsColor[i][2] = tooLowValueCoulour[2];
213            continue;
214        }
215        if (color > ss[4])
216        {
217            pixelsColor[i][0] = tooHighValueCoulour[0];
218            pixelsColor[i][1] = tooHighValueCoulour[1];
219            pixelsColor[i][2] = tooHighValueCoulour[2];
220            continue;
221        }
222        int index = 0;
223        while (ss[index] < color && index < 4)
224            index++;
225        index--;
226        if (index < 0) index = 0;
227        float weight0 = (color-ss[index]) / (ss[index+1]-ss[index]);
228        if (weight0 > 1.0f) weight0 = 1.0f;
229        if (weight0 < 0.0f) weight0 = 0.0f;
230        float weight1 = 1.0f-weight0;
231        pixelsColor[i][0] = weight1*rr[index] + weight0*rr[index+1];
232        pixelsColor[i][1] = weight1*gg[index] + weight0*gg[index+1];
233        pixelsColor[i][2] = weight1*bb[index] + weight0*bb[index+1];
234    }
235
236    for (int i=0;i<ACTUAL_NUM_PIXELS;i++)
237    {
238
239        glColor3fv(pixelsColor[i]);
240        glLoadName(i);
241if (drawBlur)
242    drawBlurryHexagon(i);
243else
244    drawHexagon(i,true);
245
246    }
247    if (!alsoWire)
248        return;
249    glTranslatef(0,0,0.1f);
250    glColor3f(0.0f,0.0f,0.0f);
251    for (int i=0;i<ACTUAL_NUM_PIXELS;i++)
252    {
253
254        drawHexagon(i, false);
255    }
256
257}
258
259/************************************************************
260 * DRAW PIXEL CURVE. draws the raw impulse curve of the currently selected pixel
261 ************************************************************/
262void RawDataViewer::drawPixelCurve()
263{
264    float xRange = bboxMax[0] - bboxMin[0];
265    float yRange = bboxMax[1] - bboxMin[1];
266
267    glBegin(GL_LINES);
268    glLineWidth(1.0f);
269    glColor3f(0.0,0.0,0.0);
270    glVertex2f(bboxMin[0], bboxMin[1]);
271    glVertex2f(bboxMax[0], bboxMin[1]);
272    glVertex2f(bboxMin[0], bboxMin[1]);
273    glVertex2f(bboxMin[0], bboxMax[1]);
274    glVertex2f(bboxMin[0], (bboxMin[1]+bboxMax[1])/2.0f);
275    glVertex2f(bboxMax[0], (bboxMin[1]+bboxMax[1])/2.0f);
276    glVertex2f(bboxMin[0] + xRange*nRoi/(float)(nRoi+nRoiTM),
277               bboxMin[1]);
278    glVertex2f(bboxMin[0] + xRange*nRoi/(float)(nRoi+nRoiTM),
279               bboxMax[1]);
280   glEnd();
281    glTranslatef(0,0,0.1f);
282    if (!nRoi)
283          return;
284     glBegin(GL_LINES);
285    glColor3f(1.0f,1.0f,0.0f);
286    float divideMe = (float)(VALUES_SPAN-1);
287    float plusMe = (float)(VALUES_SPAN)/2;
288    if (divideMe <= 0)
289        divideMe = 1;
290
291    /*
292    if (drawCalibrationLoaded)
293        plusMe += 0;//VALUES_SPAN/2;
294    if (drawCalibrationLoaded && calibrationLoaded)
295    {
296        divideMe /=2;
297        plusMe = 0 ;///=2;
298        }*/
299
300//    int mapping = _softwareOrdering ? selectedPixel : hardwareMapping[selectedPixel];
301    int mapping = hardwareMapping[selectedPixel];
302    const int hw = mapping;
303    const PixelMapEntry& mapEntry = fPixelMap.index(selectedPixel);
304    const int pixelIdInPatch = mapEntry.pixel();
305    const int patchId = mapEntry.patch();
306    const int boardId = mapEntry.board();
307    const int crateId = mapEntry.crate();
308
309    if (selectedPixel != -1)
310    {
311    for (int i=0;i<nRoi-1;i++)
312    {
313        float d1 = eventData[nRoi*hw + i]+plusMe;
314        float d2 = eventData[nRoi*hw + i+1]+plusMe;
315        if (!finite(d1)) d1 = 20000;
316        if (!finite(d2)) d2 = 20000;
317        glVertex2f(bboxMin[0] + xRange*i/(float)(nRoi+nRoiTM),
318                   bboxMin[1] + yRange*(d1) /divideMe);
319        glVertex2f(bboxMin[0] + xRange*(i+1)/(float)(nRoi+nRoiTM),
320                   bboxMin[1] + yRange*(d2) /divideMe);
321    }
322    glEnd();
323
324    glColor3f(0.0f, 1.0f, 1.0f);
325    glBegin(GL_LINES);
326    if (pixelIdInPatch == 8)//this channel has a time marker
327    {
328
329        for (int i=0;i<nRoiTM-1;i++)
330        {
331            float d1 = eventData[nRoi*1440 + nRoiTM*(40*crateId + 4*boardId + patchId) + i] + plusMe;
332            float d2 = eventData[nRoi*1440 + nRoiTM*(40*crateId + 4*boardId + patchId) + i+1] + plusMe;
333            if (!finite(d1)) d1 = 20000;
334            if (!finite(d2)) d2 = 20000;
335            glVertex2f(bboxMin[0] + xRange*(i+nRoi)/(float)(nRoi+nRoiTM),
336                       bboxMin[1] + yRange*(d1)/divideMe);
337            glVertex2f(bboxMin[0] + xRange*(i+1+nRoi)/(float)(nRoi+nRoiTM),
338                       bboxMin[1] + yRange*(d2) / divideMe);
339        }
340    }
341
342    }
343    glEnd();
344    glTranslatef(0,0,0.1f);
345    glBegin(GL_LINES);
346    glColor3f(1.0,0.0,0.0);
347    glVertex2f(bboxMin[0] + xRange*whichSlice/(float)(nRoi+nRoiTM),
348               bboxMin[1]);
349    glVertex2f(bboxMin[0] + xRange*whichSlice/(float)(nRoi+nRoiTM),
350               bboxMax[1]);
351
352    glEnd();
353
354}
355/************************************************************
356 * CONSTRUCTOR.
357 ************************************************************/
358RawDataViewer::RawDataViewer(QWidget *cParent) : BasicGlCamera(cParent), RMSvalues(1440), Meanvalues(1440), Maxvalues(1440), PosOfMaxvalues(1440), VALUES_SPAN(4096)
359
360{
361
362    whichSlice = 0;
363
364    nRoi = 0;
365    nRoiTM = 0;
366    offSetRoi = 0;
367    eventNum = 0;
368    rowNum = -1;
369    eventStep = 1;
370    selectedPixel = 393;
371    inputFile = NULL;
372    drawPatch = false;
373    drawImpulse = true;
374    drawBlur = false;
375    loopCurrentEvent = false;
376    fIsDrsCalibration = false;
377    SetAutoRefresh(true);
378    runType = "unkown";
379
380
381}
382
383void RawDataViewer::assignPixelMapFile(const string& map)
384{
385    PixelMap mypMap;
386    if (map.empty())
387    {
388        if (!mypMap.Read("FACTmap111030.txt"))
389        {
390            if (!mypMap.Read("/swdev_nfs/FACT++/FACTmap111030.txt"))
391            {
392                if (!mypMap.Read("./FACTmap111030.txt"))
393                {
394                    cerr << "ERROR - Problems reading FACTmap111030.txt" << endl;
395                    exit(-1);
396                }
397            }
398        }
399    }
400    else
401    {
402        if (!mypMap.Read(map))
403        {
404            cerr << "ERROR - Problems reading mapping file '" << map << "'" << endl;
405            exit(-1);
406        }
407    }
408
409    assignPixelMap(mypMap);
410
411    for (int i=0;i<160;i++)
412    {
413        const float color[3] = { 0.5, 0.5, 0.3 };
414
415        for (int j=0;j<3;j++)
416            patchesColor[i][j] = color[j];
417    }
418    //fZeroArray = NULL;
419
420    _softwareOrdering = false;
421}
422/************************************************************
423 *  DESTRUCTOR
424 ************************************************************/
425RawDataViewer::~RawDataViewer()
426{
427    if (inputFile != NULL)
428    {
429        inputFile->close();
430        delete inputFile;
431    }
432    //if (fZeroArray != NULL)
433    //    delete[] fZeroArray;
434}
435/*
436void RawDataViewer::allocateZeroArray()
437{
438    if (fZeroArray == NULL)
439    {
440        fZeroArray = new char[8192];
441    }
442}
443*/
444/************************************************************
445 * PAINT GL. main drawing function.
446 ************************************************************/
447void RawDataViewer::paintGL()
448{
449    //Should not be required, but apparently it helps when piping it through X forwarding
450    glFinish();
451    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
452    glLoadIdentity();
453
454    glTranslatef(0,0,-0.5);
455
456    if (drawBlur)
457    {
458        glShadeModel(GL_SMOOTH);
459        drawCamera(false);
460    }
461    else
462    {
463        glShadeModel(GL_FLAT);
464        drawCamera(true);
465    }
466    glTranslatef(0,0,0.1f);
467    if (drawPatch)
468        drawPatches();
469    glTranslatef(0,0,0.1f);
470   if (!drawBlur && (selectedPixel != -1))
471   {
472        glLineWidth(1.0f);
473        glColor3f(1.0,1.0,1.0);
474        drawHexagon(selectedPixel, false);
475   }
476   glTranslatef(0,0,0.1f);
477   if (drawImpulse)
478   {
479    //   glRotatef(cameraRotation, 0,0,1);
480       glLoadIdentity();
481       glLineWidth(2.0);
482       drawPixelCurve();
483   }
484   glTranslatef(0,0,0.1f);
485   DrawScale();
486}
487
488/************************************************************
489 * MOUSE PRESS EVENT. mouse click handler.
490 ************************************************************/
491void RawDataViewer::mousePressEvent(QMouseEvent *cEvent)
492{
493    if (cEvent->pos().x() > width()-(width()/50.f))
494    {
495        toggleInterfaceDisplay();
496        return;
497    }
498    lastPos = cEvent->pos();
499    if (setCorrectSlice(cEvent))
500        return;
501    int face = PixelAtPosition(cEvent->pos());
502
503        selectedPixel = face;
504        emit signalCurrentPixel(face);
505
506    updateGL();
507}
508
509/************************************************************
510 * SET CORRECT SLICE. if displayed, figures out if the graph was
511 * clicked, and if so, which slice should be displayed
512 ************************************************************/
513bool RawDataViewer::setCorrectSlice(QMouseEvent* cEvent)
514{
515    if (!drawImpulse)
516        return false;
517    float cx = (float)cEvent->x() * pixelSize - shownSizex/2;
518    float cy = ((float)height()-(float)cEvent->y())*pixelSize - shownSizey/2;
519    if (cx < bboxMin[0] ||
520        cx > bboxMax[0] ||
521        cy < bboxMin[1] ||
522        cy > bboxMax[1])
523        return false;
524    whichSlice = (cx - bboxMin[0])*(nRoi+nRoiTM)/(bboxMax[0] - bboxMin[0]);
525    if (whichSlice >= nRoi)
526        whichSlice = nRoi-1;
527    emit signalCurrentSlice(whichSlice);
528    return true;
529}
530
531/************************************************************
532 * MOUSE MOVE EVENT. used to track the dragging of slices display
533 ************************************************************/
534void RawDataViewer::mouseMoveEvent(QMouseEvent *cEvent)
535{
536    if (cEvent->buttons() & Qt::LeftButton) {
537        setCorrectSlice(cEvent);
538        updateGL();
539    } else if (cEvent->buttons() & Qt::RightButton) {
540        updateGL();
541    }
542    lastPos = cEvent->pos();
543}
544
545/************************************************************
546 * MOUSE DOUBLE CLICK EVENT. used to select pixels
547 ************************************************************/
548void RawDataViewer::mouseDoubleClickEvent(QMouseEvent *cEvent)
549{
550    int face = PixelAtPosition(cEvent->pos());
551    if (face != -1) {
552        selectedPixel = face;
553        emit signalCurrentPixel(face);
554        updateGL();
555        }
556}
557
558/************************************************************
559 * OPEN FILE. opens a new fits file
560 ************************************************************/
561void RawDataViewer::openFile(string file, bool reopen)
562{
563    if (inputFile)
564    {
565        inputFile->close();
566        delete inputFile;
567    }
568    try {
569        inputFile = reopen && fIsDrsCalibration ? new zfits(file, "Events") :  new factfits(file, "Events");
570    }
571    catch (std::runtime_error e)
572    {
573        cout << "Something went wrong while loading fits. Aborting: " << e.what() << endl;
574        return;
575    }
576    if (!*inputFile)
577    {
578        delete inputFile;
579        inputFile = NULL;
580        return;
581    }
582    vector<string> entriesToCheck;
583    if (inputFile->IsCompressedFITS())
584        entriesToCheck.push_back("ZNAXIS2");
585    else
586        entriesToCheck.push_back("NAXIS2");
587    entriesToCheck.push_back("NROI");
588    entriesToCheck.push_back("REVISION");
589    entriesToCheck.push_back("RUNID");
590    entriesToCheck.push_back("NBOARD");
591    entriesToCheck.push_back("NPIX");
592    entriesToCheck.push_back("NROITM");
593    entriesToCheck.push_back("TIMESYS");
594    entriesToCheck.push_back("DATE");
595    entriesToCheck.push_back("NIGHT");
596    entriesToCheck.push_back("CAMERA");
597    entriesToCheck.push_back("DAQ");
598    entriesToCheck.push_back("TSTART");
599    entriesToCheck.push_back("TSTOP");
600
601
602    for (vector<string>::const_iterator it=entriesToCheck.begin(); it != entriesToCheck.end(); it++)
603    {
604        try {
605        if (!inputFile->HasKey(*it)){
606            cout << "Warning: header keyword " << *it << " missing." << endl;
607            }
608        }
609        catch (std::runtime_error e)
610        {
611            cout << e.what() << endl;
612            return;
613        }
614    }
615
616    nRows = 0;
617    if (inputFile->IsCompressedFITS())
618        nRows = inputFile->HasKey("ZNAXIS2") ? inputFile->GetInt("ZNAXIS2") : 0;
619    else
620        nRows = inputFile->HasKey("NAXIS2") ? inputFile->GetInt("NAXIS2") : 0;
621    nRoi =           inputFile->HasKey("NROI") ?  inputFile->GetInt("NROI") : 0;
622    runNumber =      inputFile->HasKey("RUNID") ?  inputFile->GetInt("RUNID") : -1;
623    nTM =            inputFile->HasKey("NTMARK") ? inputFile->GetInt("NTMARK") : 0;
624
625    runType = "unknown";
626    if (inputFile->HasKey("RUNTYPE"))
627    {
628        runType = inputFile->GetStr("RUNTYPE");
629        if (runType == "")
630            runType = "unknown";
631    }
632    firstDataTime =  inputFile->HasKey("TSTART") ? inputFile->GetInt("TSTART") : -1;
633    lastDataTime =   inputFile->HasKey("TSTOP") ? inputFile->GetInt("TSTOP"): -1;
634    nRoiTM =         inputFile->HasKey("NROITM") ? inputFile->GetInt("NROITM") : 0;
635    revision =       inputFile->HasKey("REVISION") ? inputFile->GetInt("REVISION") : -1;
636    builderVersion = inputFile->HasKey("BLDVER") ? inputFile->GetInt("BLDVER") : -1;
637    nBoards =        inputFile->HasKey("NBOARD") ? inputFile->GetInt("NBOARD") : 0;
638    nPixels =        inputFile->HasKey("NPIX") ?  inputFile->GetInt("NPIX") : 0;
639    timeSystem =     inputFile->HasKey("TIMESYS") ? inputFile->GetStr("TIMESYS") : "";
640    creationDate =   inputFile->HasKey("DATE") ? inputFile->GetStr("DATE") : "";
641    nightInt =       inputFile->HasKey("NIGHT") ? inputFile->GetInt("NIGHT") : 0;
642    camera =         inputFile->HasKey("CAMERA") ? inputFile->GetStr("CAMERA") : "";
643    daq =            inputFile->HasKey("DAQ") ? inputFile->GetStr("DAQ") : "";
644    adcCount =       inputFile->HasKey("ADCRANGE") ? inputFile->GetFloat("ADCRANGE") : 2000;
645    if (nPixels == 0)
646    {
647        cout << "could not read num pixels from fits header. Assuming 1440 (FACT)." << endl;
648        nPixels = 1440;
649    }
650    if (nPixels > 1440)
651        cout << "More than 1440 pixels not supported." << endl;
652    if (nPixels==1440 && nRoi!=0)
653        cout << "Time marker not suppoerted with number of pixel not euqal 1440." << endl;
654
655    if (nRoi == 0 && !inputFile->HasKey("NROI"))
656    {//let's try to figure out the roi from the column's format
657        const fits::Table::Columns& cols = inputFile->GetColumns();
658        if (cols.find("Data") == cols.end())
659        {
660            cout << "ERROR: Column \"Data\" could not be found. abortin load." << endl;
661            return;
662        }
663        const fits::Table::Columns::const_iterator col = cols.find("Data");
664        if (col->second.type != 'I')
665        {
666            cout << "ERROR: Data Column has type " << col->second.type << " while viewer expects I" << endl;
667            return;
668        }
669        if (col->second.num % nPixels != 0)
670        {
671            cout << "ERROR: Num pixels (" << nPixels << ") does not match Data length (" << col->second.num << "). Aborting" << endl;
672            return;
673        }
674        nRoi = col->second.num/nPixels;
675        cout << "Estimate num samples per pixels to be " << nRoi;
676        _softwareOrdering = true;
677    }
678    else
679        _softwareOrdering = inputFile->Get<string>("ISMC", "F")=="T";
680
681    if (inputFile->HasKey("OFFSET"))
682        offSetRoi = inputFile->GetInt("OFFSET");
683
684    nbOk = 0;//inputFile->GetInt("NBEVTOK");
685    nbRej = 0;//inputFile->GetInt("NBEVTREJ");
686    nbBad = 0;//inputFile->GetInt("NBEVTBAD");
687
688    eventNum = 1;
689
690    eventData.resize(1440*nRoi + 160*nRoiTM);
691    rawEventData.resize(1440*nRoi + 160*nRoiTM);
692    waveLetArray.resize(1024*1440);
693    try
694    {
695        inputFile->SetPtrAddress("Data", rawEventData.data());
696        if (inputFile->HasColumn("EventNum"))
697            inputFile->SetPtrAddress("EventNum", &eventNum);
698        else
699            cout << "Warning: could not find column \"EventNum\"" << endl;
700        if (inputFile->HasColumn("TriggerType"))
701            inputFile->SetPtrAddress("TriggerType", &triggerType);
702        else
703            cout << "Warning: could not find column \"TriggerType\"" << endl;
704        if (inputFile->HasColumn("SoftTrig"))
705            inputFile->SetPtrAddress("SoftTrig", &softTrig);
706        else
707            cout << "Warning: could not find column \"SoftTrig\"" << endl;
708        if (inputFile->HasColumn("BoardTime"))
709            inputFile->SetPtrAddress("BoardTime", boardTime);
710        else
711            cout << "Warning: could not find column \"BoardTime\"" << endl;
712        if (inputFile->HasColumn("StartCellData"))
713            inputFile->SetPtrAddress("StartCellData", startPix);
714        else
715            cout << "Warning: could not find column \"StartCellData\"" << endl;
716        if (inputFile->HasColumn("StartCellTimeMarker"))
717            inputFile->SetPtrAddress("StartCellTimeMarker", startTM);
718        else
719            cout << "Warning: could not find column \"StartCellTimeMarker\"" << endl;
720        if (inputFile->HasColumn("TimeMarker"))
721            inputFile->SetPtrAddress("TimeMarker", rawEventData.data()+1440*nRoi);
722        else
723            cout << "Warning: could not find column \"TimeMarker\"" << endl;
724    }
725    catch (const runtime_error &e)
726    {
727        cout << e.what() << endl;
728        cout << "Loading aborted." << endl;
729
730        nRoi = nRows = 0;
731
732        return;
733    }
734
735    try
736    {
737        pcTime[0] = pcTime[1] = 0;
738        if (inputFile->HasColumn("UnixTimeUTC"))
739            inputFile->SetPtrAddress("UnixTimeUTC", pcTime);
740    }
741    catch (const runtime_error&)
742    {
743            try
744        {
745            if (inputFile->HasColumn("PCTime"))
746                inputFile->SetPtrAddress("PCTime", pcTime);
747            else
748                cout << "Warning: could not find column \"UnixTimeUTC\" nor \"PCTime\"" << endl;
749
750        }
751        catch (const runtime_error&)
752        {
753
754        }
755    }
756
757
758    if (!reopen)
759    {
760        int backupStep = eventStep;
761        rowNum = -1;
762        eventStep = 1;
763        plusEvent();
764        eventStep = backupStep;
765    }
766    else
767        readEvent();
768
769    emit newFileLoaded();
770    emit signalCurrentPixel(selectedPixel);
771}
772
773void RawDataViewer::openCalibFile(string& file)
774{
775    //calibrationLoaded = false;
776    string msg;
777    try
778    {
779        msg = fDrsCalib.ReadFitsImp(file);
780        if (msg.empty())
781        {
782            emit newFileLoaded();
783            updateGL();
784            return;
785        }
786    }
787    catch (const runtime_error &e)
788    {
789        msg = string("Something went wrong while loading Drs Calib: ") + e.what() + string(".. Aborting file loading");
790    }
791    cerr << msg << endl;
792    fDrsCalib.Clear();
793}
794
795template <typename T>
796void RawDataViewer::getCalibrationDataForDisplay(const CalibDataTypes/* calibTypes*/,
797                                                 const vector<T>& inputData,
798                                                 const int roi,
799                                                 const int roiTM)
800{
801    eventData.assign(inputData.begin(), inputData.end());
802    nRoi=roi;
803    nRoiTM=roiTM;
804
805    long long min, max, mean;
806    min = max = inputData[0];
807    mean=0;
808    for (int i=0;i<1440*roi + 160*roiTM;i++) {
809        mean += inputData[i];
810        if (inputData[i] > max)
811            max = inputData[i];
812        if (inputData[i] < min)
813            min = inputData[i];
814    }
815    mean /= 1440*roi + 160*roiTM;
816    for (int i=0;i<1440*roi + 160*roiTM;i++)
817        eventData[i] -= (float)mean;
818    VALUES_SPAN = max - min;
819//    cout << VALUES_SPAN << " " << min << " " << max << " " << mean << endl;
820//    cout << 1440*roi + 160*roiTM << " " << roi << " " << roiTM << " " << inputData.size() << endl;
821}
822/************************************************************
823 * PLUS EVENT
824 ************************************************************/
825void RawDataViewer::plusEvent()
826{
827    eventStepping(true);
828}
829/************************************************************
830 * MINUS EVENT
831 ************************************************************/
832void RawDataViewer::minusEvent()
833{
834    eventStepping(false);
835}
836/************************************************************
837 * SET EVENT STEP
838 ************************************************************/
839void RawDataViewer::setEventStep(int step)
840{
841    eventStep = step;
842}
843/************************************************************
844 * EVENT STEPPING
845 ************************************************************/
846
847void RawDataViewer::ApplyCalibration()
848{
849    eventData.assign(rawEventData.begin(), rawEventData.end());
850
851    if (fIsDrsCalibration)
852    {
853        fDrsCalib.Apply(eventData.data(), rawEventData.data(), startPix, nRoi);
854        DrsCalibrate::RemoveSpikes3(eventData.data(), nRoi*1440);
855        //TODO apply calibration to the Time markers
856    }
857
858    vector<float> pixelStatsData(1440*4);
859    DrsCalibrate::GetPixelStats(pixelStatsData.data(), eventData.data(), nRoi, 15, nRoiTM>0?5:60);
860
861    for (vector<PixelMapEntry>::const_iterator it=fPixelMap.begin(); it!=fPixelMap.end(); it++)
862    {
863        //if (it->index>=nPixels)
864        //    continue;
865
866        Meanvalues[it->index]     = pixelStatsData[0*1440+it->hw()];
867        RMSvalues[it->index]      = pixelStatsData[1*1440+it->hw()];
868        Maxvalues[it->index]      = pixelStatsData[2*1440+it->hw()];
869        PosOfMaxvalues[it->index] = pixelStatsData[3*1440+it->hw()];
870    }
871
872    if (isVisible())
873        updateGL();
874}
875
876void RawDataViewer::eventStepping(bool plus)
877{
878    if (plus)
879        rowNum += eventStep;
880    else
881        rowNum -= eventStep;
882    if (rowNum >= nRows)
883        rowNum -= nRows;
884    if (rowNum < 0)
885        rowNum += nRows;
886
887    readEvent();
888}
889
890void RawDataViewer::readEvent()
891{
892    if (inputFile == NULL)
893        return;
894    inputFile->GetRow(rowNum);
895    if (_softwareOrdering)
896    {//remap pixels data according to hardware id
897        if (nRoiTM != 0)
898            cout << "Warning: did not expect Time Markers data from Monte-Carlo simulations. These will not be mapped properly." << endl;
899
900        //first copy the data
901        const vector<int16_t> tempData(rawEventData);//.begin(), rawEventData.begin()+1440*nRoi);
902        rawEventData.assign(rawEventData.size(), 0);
903        //copy back the data and re-map it on the fly
904        for (int i=0;i<1440;i++)
905            if (softwareMapping[i]<nPixels)
906                for (int j=0;j<nRoi;j++)
907                    rawEventData[i*nRoi + j] = tempData[softwareMapping[i]*nRoi + j];
908    }
909//    cout << "Getting row " << rowNum << endl;
910
911    ApplyCalibration();
912
913    emit signalCurrentEvent(eventNum);
914    emit signalCurrentPixel(selectedPixel);
915}
916
917/************************************************************
918 * NEXT SLICE. deprec ?
919 ************************************************************/
920void RawDataViewer::nextSlice()
921{
922    whichSlice++;
923    if (whichSlice >= nRoi)
924    {
925        whichSlice = 0;
926        if (!loopCurrentEvent)
927        {
928            int backupStep = eventStep;
929            eventStep = 1;
930            eventStepping(true);
931            eventStep = backupStep;
932        }
933    }
934    emit signalCurrentSlice(whichSlice);
935    updateGL();
936}
937void RawDataViewer::previousSlice()
938{
939    whichSlice--;
940    if (whichSlice < 0)
941    {
942        whichSlice = nRoi-1;
943        if (!loopCurrentEvent)
944        {
945            int backupStep = eventStep;
946            eventStep = 1;
947            eventStepping(false);
948            eventStep = backupStep;
949        }
950    }
951    emit signalCurrentSlice(whichSlice);
952    updateGL();
953}
954void RawDataViewer::setCurrentPixel(int pix)
955{
956 //   if (pix == -1)
957 //       return;
958    selectedPixel = pix;
959    if (isVisible())
960    updateGL();
961     emit signalCurrentPixel(pix);
962}
963/*
964void RawDataViewer::computePulsesStatistics()
965{
966    if (!inputFile)
967    {
968        cout << "A FITS file must be open in order to complete this operation" << endl;
969        return;
970    }
971
972
973//    for (int i=0;i<nRows;i++)//for all events
974//    {
975//        inputFile->GetRow(rowNum);
976//        for (int i=0;i<(1440+160)*nRoi;i++)
977//            eventData[i] = (float)rawEventData[i];
978
979//        for (int j=0;j<ACTUAL_NUM_PIXELS;j++)
980///        {
981    int j = selectedPixel;
982    if (j == -1)
983        return;
984            for (int i=0;i<nRoi;i++)
985            {
986                aMeas[i] = eventData[j*nRoi+i];// * adcCount;
987
988            }
989            for (int i=0;i<nRoi;i++)
990            {
991                if (i==0)
992                    n1mean[i] = aMeas[i+1];
993                else
994                {
995                    if (i==1023)
996                        n1mean[i] = aMeas[i-1];
997                    else
998                        n1mean[i] = (aMeas[i-1]+aMeas[i+1])/2.f;
999                }
1000            }
1001            //find spike
1002            for (int i=0;i<nRoi-3;i++)
1003            {
1004                const float fract = 0.8f;
1005                float xx, xp, xpp;
1006                vCorr[i] = 0;//aMeas[i];
1007                xx = aMeas[i] - n1mean[i];
1008                if (xx < -8.f)
1009                {
1010                    xp = aMeas[i+1] - n1mean[i+1];
1011                    xpp = aMeas[i+2] - n1mean[i+2];
1012                    if ((aMeas[i+2] - (aMeas[i] + aMeas[i+3])/2.f) > 10.f)
1013                    {
1014                        vCorr[i+1] = (aMeas[i] + aMeas[i+3])/2.f;
1015                        vCorr[i+2] = (aMeas[i] + aMeas[i+3])/2.f;
1016                        i = i+2;
1017                    }
1018                    else
1019                    {
1020                        if ((xp > -2.*xx*fract) && (xpp < -10.f))
1021                        {
1022                            vCorr[i+1] = n1mean[i+1];
1023                            n1mean[i+2] = aMeas[i+1] - aMeas[i+3]/2.f;
1024                            i++;
1025                        }
1026                    }
1027                }
1028            }
1029            for (int i=0;i<nRoi;i++)
1030                n1mean[i] = aMeas[i]-n1mean[i];
1031 //       }
1032 //   }
1033}
1034*/
1035/************************************************************
1036 * UICONNECTOR CONSTRUCTOR
1037 ************************************************************/
1038UIConnector::UIConnector(QWidget *p)
1039{
1040    setupUi(this);
1041    initHistograms();
1042
1043    updateSpinnerDisplay = true;
1044    updating = false;
1045
1046    timer.setInterval(10.0);
1047    QObject::connect(&timer, SIGNAL(timeout()),
1048                     this, SLOT(nextSlicePlease()));
1049
1050    QButtonGroup &scaleGroup = *new QButtonGroup(p);// = new QButtonGroup(canvas);
1051    QButtonGroup &animateGroup = *new QButtonGroup(p);// = new QButtonGroup(canvas);
1052
1053    scaleGroup.addButton(currentPixelScale);
1054    scaleGroup.addButton(entireCameraScale);
1055
1056    animateGroup.addButton(playEventsRadio);
1057    animateGroup.addButton(playSlicesRadio);
1058    animateGroup.addButton(playPixelsRadio);
1059
1060    entireCameraScale->setChecked(true);
1061
1062    RMS_window->enableText(false);
1063    Mean_window->enableText(false);
1064    PosOfMax_window->enableText(false);
1065    Max_window->enableText(false);
1066
1067 //   RMS_window->ShowPatchCursor(true);
1068
1069    QObject::connect(GLWindow, SIGNAL(colorPaletteHasChanged()),
1070                     this, SLOT(on_autoScaleColor_clicked()));
1071    QObject::connect(GLWindow, SIGNAL(signalCurrentSlice(int)),
1072                     this, SLOT(currentSliceHasChanged(int)));
1073    QObject::connect(GLWindow, SIGNAL(signalCurrentEvent(int)),
1074                     this, SLOT(currentEventHasChanged(int)));
1075    QObject::connect(GLWindow, SIGNAL(signalCurrentPixel(int)),
1076                     this, SLOT(pixelChanged(int)));
1077    QObject::connect(GLWindow, SIGNAL(newFileLoaded()),
1078                     this, SLOT(newFileLoaded()));
1079
1080    QObject::connect(RMS_window, SIGNAL(signalCurrentPixel(int)),
1081                     GLWindow, SLOT(setCurrentPixel(int)));
1082    QObject::connect(Max_window, SIGNAL(signalCurrentPixel(int)),
1083                     GLWindow, SLOT(setCurrentPixel(int)));
1084    QObject::connect(PosOfMax_window, SIGNAL(signalCurrentPixel(int)),
1085                     GLWindow, SLOT(setCurrentPixel(int)));
1086    QObject::connect(Mean_window, SIGNAL(signalCurrentPixel(int)),
1087                     GLWindow, SLOT(setCurrentPixel(int)));
1088
1089
1090
1091    show();
1092}
1093UIConnector::~UIConnector()
1094{
1095    grid1->detach();
1096    grid2->detach();
1097    grid3->detach();
1098    grid4->detach();
1099    grid5->detach();
1100    grid6->detach();
1101    boardsTimeHistoItem.detach();
1102    startCellHistoItem.detach();
1103    startTimeMarkHistoItem.detach();
1104    pixelValueCurveItem.detach();
1105    pixelAverageCurveItem.detach();
1106    aMeanCurveItem.detach();
1107    vCorrCurveItem.detach();
1108    meanCurveItem.detach();
1109}
1110void UIConnector::slicesPlusPlus()
1111{
1112    GLWindow->nextSlice();
1113}
1114void UIConnector::slicesMinusMinus()
1115{
1116    GLWindow->previousSlice();
1117}
1118void UIConnector::on_calibratedCheckBox_stateChanged(int state)
1119{
1120    GLWindow->fIsDrsCalibration = state;
1121
1122    if (currentCalibFile.empty())
1123        GLWindow->openFile(currentFile, true);
1124
1125    GLWindow->ApplyCalibration();
1126
1127    threeD_Window->setData(GLWindow->eventData.data());
1128
1129    if (autoScaleColor->isChecked())
1130        on_autoScaleColor_clicked();
1131    pixelChanged(GLWindow->selectedPixel);
1132
1133}
1134/************************************************************
1135 * DRAW PATCHES CHECK CHANGE. checkbox handler
1136 ************************************************************/
1137void UIConnector::on_drawPatchCheckBox_stateChanged(int state)
1138{
1139    GLWindow->drawPatch = state;
1140    GLWindow->updateGL();
1141    RMS_window->fDrawPatch = state;
1142    RMS_window->updateGL();
1143    Mean_window->fDrawPatch = state;
1144    Mean_window->updateGL();
1145    Max_window->fDrawPatch = state;
1146    Max_window->updateGL();
1147    PosOfMax_window->fDrawPatch = state;
1148    PosOfMax_window->updateGL();
1149}
1150/************************************************************
1151 * DRAW IMPULSE CHECK CHANGE. checkbox handler
1152 ************************************************************/
1153void UIConnector::on_drawImpulseCheckBox_stateChanged(int state)
1154{
1155    GLWindow->drawImpulse = state;
1156    TriggerOffset_window->drawImpulse = state;
1157    Gain_window->drawImpulse = state;
1158    Baseline_window->drawImpulse = state;
1159    GLWindow->updateGL();
1160    TriggerOffset_window->updateGL();
1161    Gain_window->updateGL();
1162    Baseline_window->updateGL();
1163}
1164/************************************************************
1165 * DRAW BLUR CHECK CHANGE. checkbox handler
1166 ************************************************************/
1167void UIConnector::on_drawBlurCheckBox_stateChanged(int state)
1168{
1169    GLWindow->drawBlur = state;
1170    GLWindow->updateGL();
1171}
1172void UIConnector::on_loopOverCurrentEventBox_stateChanged(int state)
1173{
1174    GLWindow->loopCurrentEvent = state;
1175}
1176
1177/************************************************************
1178 * NEXT SLICE PLEASE
1179 ************************************************************/
1180void UIConnector::nextSlicePlease()
1181{
1182    if (playEventsRadio->isChecked ())
1183        GLWindow->eventStepping(true);
1184    else
1185        if (playPixelsRadio->isChecked())
1186            GLWindow->setCurrentPixel((GLWindow->getCurrentPixel()+1)%1440);
1187        else
1188            GLWindow->nextSlice();
1189}
1190
1191/************************************************************
1192 * SET VIEWER.
1193 ************************************************************/
1194//void UIConnector::setViewer(RawDataViewer* v)
1195//{
1196//    viewer = v;
1197//}
1198/************************************************************
1199 * SLICES PER SECOND CHANGED. timing ui handler
1200 ************************************************************/
1201void UIConnector::slicesPerSecondChanged(double value)
1202{
1203    timer.setInterval(1000.0/value);
1204}
1205
1206void UIConnector::on_colorRange0_valueChanged(double value) { GLWindow->ss[0] = (float)value; GLWindow->updateGL(); }
1207void UIConnector::on_colorRange1_valueChanged(double value) { GLWindow->ss[1] = (float)value; GLWindow->updateGL(); }
1208void UIConnector::on_colorRange2_valueChanged(double value) { GLWindow->ss[2] = (float)value; GLWindow->updateGL(); }
1209void UIConnector::on_colorRange3_valueChanged(double value) { GLWindow->ss[3] = (float)value; GLWindow->updateGL(); }
1210void UIConnector::on_colorRange4_valueChanged(double value) { GLWindow->ss[4] = (float)value; GLWindow->updateGL(); }
1211
1212void UIConnector::on_redValue0_valueChanged(double value) { GLWindow->rr[0] = (float)value; GLWindow->updateGL(); }
1213void UIConnector::on_redValue1_valueChanged(double value) { GLWindow->rr[1] = (float)value; GLWindow->updateGL(); }
1214void UIConnector::on_redValue2_valueChanged(double value) { GLWindow->rr[2] = (float)value; GLWindow->updateGL(); }
1215void UIConnector::on_redValue3_valueChanged(double value) { GLWindow->rr[3] = (float)value; GLWindow->updateGL(); }
1216void UIConnector::on_redValue4_valueChanged(double value) { GLWindow->rr[4] = (float)value; GLWindow->updateGL(); }
1217
1218void UIConnector::on_greenValue0_valueChanged(double value) { GLWindow->gg[0] = (float)value; GLWindow->updateGL(); }
1219void UIConnector::on_greenValue1_valueChanged(double value) { GLWindow->gg[1] = (float)value; GLWindow->updateGL(); }
1220void UIConnector::on_greenValue2_valueChanged(double value) { GLWindow->gg[2] = (float)value; GLWindow->updateGL(); }
1221void UIConnector::on_greenValue3_valueChanged(double value) { GLWindow->gg[3] = (float)value; GLWindow->updateGL(); }
1222void UIConnector::on_greenValue4_valueChanged(double value) { GLWindow->gg[4] = (float)value; GLWindow->updateGL(); }
1223
1224void UIConnector::on_blueValue0_valueChanged(double value) { GLWindow->bb[0] = (float)value; GLWindow->updateGL(); }
1225void UIConnector::on_blueValue1_valueChanged(double value) { GLWindow->bb[1] = (float)value; GLWindow->updateGL(); }
1226void UIConnector::on_blueValue2_valueChanged(double value) { GLWindow->bb[2] = (float)value; GLWindow->updateGL(); }
1227void UIConnector::on_blueValue3_valueChanged(double value) { GLWindow->bb[3] = (float)value; GLWindow->updateGL(); }
1228void UIConnector::on_blueValue4_valueChanged(double value) { GLWindow->bb[4] = (float)value; GLWindow->updateGL(); }
1229
1230/************************************************************
1231 * LOAD NEW FILE CLICKED. button handler
1232 ************************************************************/
1233void UIConnector::on_loadNewFileButton_clicked()
1234{
1235    QFileDialog dialog;
1236    dialog.setFileMode(QFileDialog::ExistingFile);
1237    dialog.open(this, SLOT(fileSelected(QString)));
1238    dialog.setVisible(true);
1239    dialog.exec();
1240}
1241void UIConnector::on_loadDRSCalibButton_clicked()
1242{
1243    QFileDialog dialog;
1244    dialog.setFileMode(QFileDialog::ExistingFile);
1245    dialog.open(this, SLOT(calibFileSelected(QString)));
1246    dialog.setVisible(true);
1247    dialog.exec();
1248}
1249/************************************************************
1250 * FILE SELECTED. return of the file open dialog handler
1251 ************************************************************/
1252void UIConnector::fileSelected(QString file)
1253{
1254    const bool reopen = !currentFile.empty();
1255
1256    currentFile = file.toStdString();
1257    if (!currentFile.empty())
1258        GLWindow->openFile(currentFile, reopen && currentCalibFile.empty());
1259}
1260void UIConnector::calibFileSelected(QString file)
1261{
1262    const bool reopen = currentCalibFile.empty();
1263
1264    currentCalibFile = file.toStdString();
1265    if (reopen && !currentFile.empty())
1266        GLWindow->openFile(currentFile, true);
1267    if (currentCalibFile != "")
1268        GLWindow->openCalibFile(currentCalibFile);
1269
1270
1271    if (GLWindow->fDrsCalib.fRoi != 0)
1272    {//spread the calibration data to the displayers
1273        Baseline_window->getCalibrationDataForDisplay(RawDataViewer::CALIB_BASELINE,
1274                                                      GLWindow->fDrsCalib.fOffset,
1275                                                      GLWindow->fDrsCalib.fRoi,
1276                                                      GLWindow->fDrsCalib.fNumTm);
1277
1278        Gain_window->getCalibrationDataForDisplay(RawDataViewer::CALIB_GAIN,
1279                                                  GLWindow->fDrsCalib.fGain,
1280                                                  GLWindow->fDrsCalib.fRoi,
1281                                                  GLWindow->fDrsCalib.fNumTm);
1282
1283        TriggerOffset_window->getCalibrationDataForDisplay(RawDataViewer::CALIB_TRIG_OFFSET,
1284                                                           GLWindow->fDrsCalib.fTrgOff,
1285                                                           GLWindow->fDrsCalib.fRoi,
1286                                                           GLWindow->fDrsCalib.fNumTm);
1287
1288    }
1289}
1290/************************************************************
1291 * NEW FILE LOADED. update of the UI after a new file has been loaded
1292 ************************************************************/
1293void UIConnector::newFileLoaded()
1294{
1295    ostringstream str;
1296
1297    //extract the file name only (no path) from the full name
1298    str << "File: ";
1299    if (currentFile.size() > 2)
1300        str << currentFile.substr(currentFile.find_last_of("//")+1, currentFile.size()) << "\n";
1301    else
1302        str << "--\n";
1303    str << "Calibration: ";
1304    if (currentCalibFile.size() > 2)
1305        str << currentCalibFile.substr(currentCalibFile.find_last_of("//")+1, currentCalibFile.size()) << "\n";
1306    else
1307        str << "--\n";
1308//    fileLoadedLabel->setText(QString(str.str().c_str()));
1309//    str.str("");
1310    str << "Run number: " << GLWindow->runNumber << "\n";
1311//    runNumberLabel->setText(QString(str.str().c_str()));
1312//    str.str("");
1313    str << "Number of Events: " << GLWindow->nRows << "\n";
1314
1315    displayingEventBox->setMaximum(GLWindow->nRows-1);
1316
1317    str << "Number of Slices: " << GLWindow->nRoi << "\n";// << "/1024";
1318//    numberOfSlicesLabel->setText(QString(str.str().c_str()));
1319//    str.str("");
1320    str << "Number of Time Marks: " << GLWindow->nTM << "\n";
1321//    numberOfTimeMarksLabel->setText(QString(str.str().c_str()));
1322
1323//    str.str("");
1324    str << "Run Type: " << GLWindow->runType << "\n";
1325//    runTypeLabel->setText(QString(str.str().c_str()));
1326//    str.str("");
1327    str << "Time of 1st data: " << GLWindow->firstDataTime << "\n";
1328//    firstTimeLabel->setText(QString(str.str().c_str()));
1329//    str.str("");
1330    str << "Time of last data: " << GLWindow->lastDataTime << "\n";
1331//    lastTimeLabel->setText(QString(str.str().c_str()));
1332//    str.str("");
1333    str << "SVN revision: " << GLWindow->revision << '\n';
1334    str << "Number of boards: " << GLWindow->nBoards << '\n';
1335    str << "Number of pixels: " << GLWindow->nPixels << '\n';
1336    str << "Number of Slices TM: " << GLWindow->nRoiTM << '\n';
1337    str << "Time system: " << GLWindow->timeSystem << '\n';
1338    str << "Date: " << GLWindow->creationDate << '\n';
1339    str << "Night: " << GLWindow->nightInt << '\n';
1340    str << "Camera: " << GLWindow->camera << '\n';
1341    str << "DAQ: " << GLWindow->daq << '\n';
1342    str << "ADC Count: " << GLWindow->adcCount << '\n';
1343    str << "NB Evts OK:" << GLWindow->nbOk << '\n';
1344    str << "NB Evts Rejected: " << GLWindow->nbRej << '\n';
1345    str << "NB Evts Bad: " << GLWindow->nbBad << '\n';
1346    extraInfoLabel->setText(QString(str.str().c_str()));
1347
1348    /*
1349    if (GLWindow->calibrationLoaded)
1350    {
1351        drawCalibrationCheckBox->setEnabled(true);
1352    }*/
1353
1354
1355}
1356/************************************************************
1357 * PLAY PAUSE CLICKED. ui handler
1358 ************************************************************/
1359void UIConnector::on_playPauseButton_clicked()
1360{
1361    if (timer.isActive())
1362        timer.stop();
1363    else
1364        timer.start();
1365}
1366
1367void UIConnector::displaySliceValue()
1368{
1369    if (!GLWindow->nRoi)
1370        return;
1371    if (GLWindow->selectedPixel == -1)
1372    {
1373        ostringstream str;
1374        str << " Current Pixel val.: --";
1375        currentPixelValue->setText(QString(str.str().c_str()));
1376        return;
1377    }
1378//    int mapping = GLWindow->_softwareOrdering ? GLWindow->selectedPixel : GLWindow->hardwareMapping[GLWindow->selectedPixel];
1379    int mapping = GLWindow->hardwareMapping[GLWindow->selectedPixel];
1380    const int idx = GLWindow->nRoi*mapping + GLWindow->whichSlice;
1381
1382    ostringstream str;
1383    str << "Current Pixel val.: " << GLWindow->eventData[idx];
1384    currentPixelValue->setText(QString(str.str().c_str()));
1385}
1386
1387/************************************************************
1388 * CURRENT SLICE HAS CHANGE. ui handler
1389 ************************************************************/
1390void UIConnector::currentSliceHasChanged(int slice)
1391{
1392    if (!GLWindow->nRoi)
1393        return;
1394
1395    if (updateSpinnerDisplay)
1396        displayingSliceBox->setValue(slice);
1397
1398    displaySliceValue();
1399}
1400
1401/*****
1402 *******************************************************
1403 * CURRENT EVENT HAS CHANGED. ui handler
1404 ************************************************************/
1405
1406double xval[50000];
1407double yval[50000];
1408void UIConnector::on_displayingEventBox_valueChanged(int cEvent)
1409{
1410//    cout << "Here " << updateSpinnerDisplay << endl;
1411    if (!updateSpinnerDisplay)
1412        return;
1413    updateSpinnerDisplay = false;
1414//    currentEventHasChanged(cEvent);
1415    GLWindow->rowNum = cEvent - GLWindow->eventStep;
1416    GLWindow->eventStepping(true);
1417    updateSpinnerDisplay = true;
1418
1419//    GLWindow->updateGL();
1420}
1421void UIConnector::on_slicesPerSecValue_valueChanged(double value)
1422{
1423    timer.setInterval(1000.0/value);
1424}
1425void UIConnector::on_displayingSliceBox_valueChanged(int cSlice)
1426{
1427    updateSpinnerDisplay = false;
1428    currentSliceHasChanged(cSlice);
1429    updateSpinnerDisplay = true;
1430    GLWindow->whichSlice = cSlice;
1431    GLWindow->updateGL();
1432}
1433void UIConnector::currentEventHasChanged(int )
1434{
1435
1436    RMS_window->SetData(GLWindow->RMSvalues);
1437    Mean_window->SetData(GLWindow->Meanvalues);
1438    PosOfMax_window->SetData(GLWindow->PosOfMaxvalues);
1439    Max_window->SetData(GLWindow->Maxvalues);
1440    threeD_Window->setData(GLWindow->eventData.data());//rawEventData);
1441
1442    if (RMS_window->isVisible())
1443        RMS_window->updateGL();
1444    if (Mean_window->isVisible())
1445        Mean_window->updateGL();
1446    if (PosOfMax_window->isVisible())
1447        PosOfMax_window->updateGL();
1448    if (Max_window->isVisible())
1449        Max_window->updateGL();
1450    ostringstream str;
1451//    str << "Displaying Event " << cEvent;
1452//    QString qstr(str.str().c_str());
1453//    emit updateCurrentEventDisplay(qstr);
1454    if (updateSpinnerDisplay)
1455    {
1456        updateSpinnerDisplay = false;
1457        displayingEventBox->setValue(GLWindow->rowNum);
1458        updateSpinnerDisplay = true;
1459    }
1460
1461 //   GLWindow->doWaveLetOnCurrentEventPlease();
1462
1463        //retrieve the data that we want to display
1464    boost::posix_time::ptime hrTime( boost::gregorian::date(1970, boost::gregorian::Jan, 1),
1465            boost::posix_time::seconds(GLWindow->pcTime[0]) +  boost::posix_time::microsec(GLWindow->pcTime[1]));
1466
1467    str.str("");
1468    str << "PC Time: " << boost::posix_time::to_iso_extended_string(hrTime);
1469    PCTimeLabel->setText(QString(str.str().c_str()));
1470
1471    str.str("");
1472    str << "Software Trigger: " << GLWindow->softTrig;
1473    softwareTriggerLabel->setText(QString(str.str().c_str()));
1474
1475    str.str("");
1476    str << "Trigger Type: " << GLWindow->triggerType;
1477    triggerTypeLabel->setText(QString(str.str().c_str()));
1478
1479    displaySliceValue();
1480
1481    if (autoScaleColor->isChecked())
1482        emit GLWindow->colorPaletteHasChanged();//autoScalePressed();
1483
1484    boardsTimeList->clear();
1485    startPixelsList->clear();
1486    startTimeMarksList->clear();
1487    triggerDelayList->clear();
1488    std::map<int, int> boardsHistoMap;
1489    for (int i=0;i <NBOARDS; i++)
1490    {
1491        str.str("");
1492        str << i;
1493        if (i<10) str << " ";
1494        if (i<100) str << " ";
1495        if (i<1000) str << " ";
1496        str << ": " << GLWindow->boardTime[i];
1497        boardsTimeList->addItem(QString(str.str().c_str()));
1498        if (boardsHistoMap.find(GLWindow->boardTime[i]) != boardsHistoMap.end())
1499            boardsHistoMap[GLWindow->boardTime[i]]++;
1500        else
1501            boardsHistoMap[GLWindow->boardTime[i]] = 1;
1502    }
1503    std::map<int, int> pixelHistoMap;
1504    for (int i=0;i <NPIX; i++)
1505    {
1506        str.str("");
1507        str << i;
1508        if (i<10) str << " ";
1509        if (i<100) str << " ";
1510        if (i<1000) str << " ";
1511        str << ": " << GLWindow->startPix[i];
1512        startPixelsList->addItem(QString(str.str().c_str()));
1513        if (pixelHistoMap.find(GLWindow->startPix[i]) != pixelHistoMap.end())
1514            pixelHistoMap[GLWindow->startPix[i]]++;
1515        else
1516            pixelHistoMap[GLWindow->startPix[i]] = 1;
1517    }
1518
1519    std::map<int, int> timeMarksMap;
1520    for (int i=0;i <NTMARK; i++)
1521    {
1522        str.str("");
1523        str << i;
1524        if (i<10) str << " ";
1525        if (i<100) str << " ";
1526        if (i<1000) str << " ";
1527        str << ": " << GLWindow->startTM[i];
1528        startTimeMarksList->addItem(QString(str.str().c_str()));
1529        if (timeMarksMap.find(GLWindow->startTM[i]) != timeMarksMap.end())
1530            timeMarksMap[GLWindow->startTM[i]]++;
1531        else
1532            timeMarksMap[GLWindow->startTM[i]] = 1;
1533    }
1534    std::map<int,int> delayMap;
1535    triggerDelayList->addItem(QString("Patch | Slice:Delay Slice:Delay..."));
1536    for (int i=0;i<NTMARK; i++)
1537    {
1538        str.str("");
1539        str << i << " | ";
1540        for (int j=0;j<GLWindow->nRoiTM;j++)
1541        {
1542            int value = GLWindow->eventData[1440*GLWindow->nRoi + i*GLWindow->nRoiTM + j];
1543            if (delayMap.find(value) != delayMap.end())
1544                 delayMap[value]++;
1545             else
1546                 delayMap[value] = 1;
1547            str << j << ":" << value << " ";
1548         }
1549        triggerDelayList->addItem(QString(str.str().c_str()));
1550    }
1551
1552    std::map<int,int>::iterator it = boardsHistoMap.begin();
1553    int nsamples = 0;
1554    int previousValue = it->first-10;
1555    for (unsigned int i=0;i<boardsHistoMap.size();i++)
1556    {
1557        if (previousValue != it->first-1)
1558        {
1559            xval[nsamples] = previousValue+1;
1560            yval[nsamples] = 0;
1561            nsamples++;
1562            xval[nsamples] = it->first-1;
1563            yval[nsamples] = 0;
1564            nsamples++;
1565        }
1566        xval[nsamples] = it->first;
1567        yval[nsamples] = it->second;
1568        previousValue = it->first;
1569        it++;
1570        nsamples++;
1571        xval[nsamples] = previousValue;
1572        yval[nsamples] = 0;
1573        nsamples++;
1574        if (nsamples > 4090)
1575        {
1576            cout << "Error: Maximum number of samples reached for histograms. skipping what's remaining" << endl;
1577            break;
1578        }
1579    }
1580    xval[nsamples] = it==boardsHistoMap.begin() ? 0 : (--it)->first+1;
1581    yval[nsamples] = 0;
1582    nsamples++;
1583 //   if (nsamples > 5)
1584#if QWT_VERSION < 0x060000
1585       boardsTimeHistoItem.setData(xval, yval, nsamples);
1586#else
1587       boardsTimeHistoItem.setSamples(xval, yval, nsamples);
1588#endif
1589
1590    it = pixelHistoMap.begin();
1591    nsamples = 0;
1592    previousValue = it->first-10;
1593    for (unsigned int i=0;i<pixelHistoMap.size();i++)
1594    {
1595        if (previousValue != it->first-1)
1596        {
1597            xval[nsamples] = previousValue+1;
1598            yval[nsamples] = 0;
1599            nsamples++;
1600            xval[nsamples] = it->first-1;
1601            yval[nsamples] = 0;
1602            nsamples++;
1603        }
1604        xval[nsamples] = it->first;
1605        yval[nsamples] = it->second;
1606        previousValue = it->first;
1607        it++;
1608        nsamples++;
1609        xval[nsamples] = previousValue;
1610        yval[nsamples] = 0;
1611        nsamples++;
1612        if (nsamples > 4090)
1613        {
1614            cout << "Error: Maximum number of samples reached for histograms. skipping what's remaining" << endl;
1615            break;
1616        }
1617   }
1618    xval[nsamples] = it==pixelHistoMap.begin() ? 0 : (--it)->first+1;
1619    yval[nsamples] = 0;
1620    nsamples++;
1621//    if (nsamples > 5)
1622#if QWT_VERSION < 0x060000
1623       startCellHistoItem.setData(xval, yval, nsamples);
1624#else
1625       startCellHistoItem.setSamples(xval, yval, nsamples);
1626#endif
1627
1628    it = timeMarksMap.begin();
1629    nsamples = 0;
1630    previousValue = it->first-10;
1631    for (unsigned int i=0;i<timeMarksMap.size();i++)
1632    {
1633        if (previousValue != it->first-1)
1634        {
1635            xval[nsamples] = previousValue+1;
1636            yval[nsamples] = 0;
1637            nsamples++;
1638            xval[nsamples] = it->first-1;
1639            yval[nsamples] = 0;
1640            nsamples++;
1641        }
1642        xval[nsamples] = it->first;
1643        yval[nsamples] = it->second;
1644        previousValue = it->first;
1645        it++;
1646        nsamples++;
1647        xval[nsamples] = previousValue;
1648        yval[nsamples] = 0;
1649        nsamples++;
1650        if (nsamples > 4090)
1651        {
1652            cout << "Error: Maximum number of samples reached for histograms. skipping what's remaining" << endl;
1653            break;
1654        }
1655    }
1656    xval[nsamples] = it==timeMarksMap.begin() ? 0 : (--it)->first+1;
1657    yval[nsamples] = 0;
1658    nsamples++;
1659 //   if (nsamples > 5)
1660#if QWT_VERSION < 0x060000
1661       startTimeMarkHistoItem.setData(xval, yval, nsamples);
1662#else
1663       startTimeMarkHistoItem.setSamples(xval, yval, nsamples);
1664#endif
1665
1666    it = delayMap.begin();
1667    nsamples = 0;
1668    previousValue = it->first-10;
1669    for (unsigned int i=0;i<delayMap.size();i++)
1670    {
1671        if (previousValue != it->first-1)
1672        {
1673            xval[nsamples] = previousValue+1;
1674            yval[nsamples] = 0;
1675            nsamples++;
1676            xval[nsamples] = it->first-1;
1677            yval[nsamples] = 0;
1678            nsamples++;
1679        }
1680        xval[nsamples] = it->first;
1681        yval[nsamples] = it->second;
1682        previousValue = it->first;
1683        it++;
1684        nsamples++;
1685        xval[nsamples] = previousValue;
1686        yval[nsamples] = 0;
1687        nsamples++;
1688        if (nsamples > 4090)
1689        {
1690            cout << "Error: Maximum number of samples reached for histograms. skipping what's remaining" << endl;
1691            break;
1692        }
1693    }
1694    xval[nsamples] = it==delayMap.begin() ? 0 : (--it)->first+1;
1695    yval[nsamples] = 0;
1696    nsamples++;
1697  //  if (nsamples > 5)
1698#if QWT_VERSION < 0x060000
1699       triggerDelayHistoItem.setData(xval, yval, nsamples);
1700#else
1701       triggerDelayHistoItem.setSamples(xval, yval, nsamples);
1702#endif
1703       //WAVELETS HACK
1704/*       std::map<int, int> valuesHistoMap;
1705       std::map<int, int> waveletHistoMap;
1706       for (int i=0;i<1024*1440;i++)
1707       {
1708           if (valuesHistoMap.find(GLWindow->rawEventData[i]) != valuesHistoMap.end())
1709               valuesHistoMap[GLWindow->rawEventData[i]]++;
1710           else
1711               valuesHistoMap[GLWindow->rawEventData[i]] = 1;
1712           if (waveletHistoMap.find(GLWindow->waveLetArray[i]) != waveletHistoMap.end())
1713               waveletHistoMap[GLWindow->waveLetArray[i]]++;
1714           else
1715               waveletHistoMap[GLWindow->waveLetArray[i]] = 1;
1716       }
1717
1718       it = valuesHistoMap.begin();
1719       nsamples = 0;
1720       previousValue = it->first-10;
1721       cout << "Num values Original: " << valuesHistoMap.size() << endl;
1722       for (unsigned int i=0;i<valuesHistoMap.size();i++)
1723       {
1724           if (previousValue != it->first-1)
1725           {
1726               xval[nsamples] = previousValue+1;
1727               yval[nsamples] = 0;
1728               nsamples++;
1729               xval[nsamples] = it->first-1;
1730               yval[nsamples] = 0;
1731               nsamples++;
1732           }
1733           xval[nsamples] = it->first;
1734           yval[nsamples] = it->second;
1735           previousValue = it->first;
1736           it++;
1737           nsamples++;
1738           xval[nsamples] = previousValue;
1739           yval[nsamples] = 0;
1740           nsamples++;
1741           if (nsamples > 50000)
1742           {
1743               cout << "Error: Maximum number of samples reached for histograms. skipping what's remaining" << endl;
1744               break;
1745           }
1746       }
1747       xval[nsamples] = it==valuesHistoMap.begin() ? 0 : (--it)->first+1;
1748       yval[nsamples] = 0;
1749       nsamples++;
1750     //  if (nsamples > 5)
1751   #if QWT_VERSION < 0x060000
1752          triggerDelayHistoItem.setData(xval, yval, nsamples);
1753   #else
1754          triggerDelayHistoItem.setSamples(xval, yval, nsamples);
1755   #endif
1756
1757          it = waveletHistoMap.begin();
1758          nsamples = 0;
1759          previousValue = it->first-10;
1760          cout << "Num values WaveLets: " << waveletHistoMap.size() << endl;
1761          for (unsigned int i=0;i<waveletHistoMap.size();i++)
1762          {
1763              if (previousValue != it->first-1)
1764              {
1765                  xval[nsamples] = previousValue+1;
1766                  yval[nsamples] = 0;
1767                  nsamples++;
1768                  xval[nsamples] = it->first-1;
1769                  yval[nsamples] = 0;
1770                  nsamples++;
1771              }
1772              xval[nsamples] = it->first;
1773              yval[nsamples] = it->second;
1774              previousValue = it->first;
1775              it++;
1776              nsamples++;
1777              xval[nsamples] = previousValue;
1778              yval[nsamples] = 0;
1779              nsamples++;
1780              if (nsamples > 50000)
1781              {
1782                  cout << "Error: Maximum number of samples reached for histograms. skipping what's remaining" << endl;
1783                  break;
1784              }
1785          }
1786          xval[nsamples] = it==waveletHistoMap.begin() ? 0 : (--it)->first+1;
1787          yval[nsamples] = 0;
1788          nsamples++;
1789        //  if (nsamples > 5)
1790      #if QWT_VERSION < 0x060000
1791          startTimeMarkHistoItem.setData(xval, yval, nsamples);
1792      #else
1793          startTimeMarkHistoItem.setSamples(xval, yval, nsamples);
1794      #endif
1795*/
1796//END OF WAVELETS HACK
1797       //    startCellHistoZoom->setZoomBase(startCellHistoItem.boundingRect());
1798    QStack< QRectF > stack;
1799//    QRectF cRectangle = boardsTimeHistoItem.boundingRect();
1800    stack.push(scaleBoundingRectangle(boardsTimeHistoItem.boundingRect(), 1.05f));//cRectangle);//boardsTimeHistoItem.boundingRect());
1801    boardsTimeHistoZoom->setZoomStack(stack);
1802    stack.pop();
1803    stack.push(scaleBoundingRectangle(startCellHistoItem.boundingRect(), 1.05f));
1804    startCellHistoZoom->setZoomStack(stack);
1805    stack.pop();
1806    stack.push(scaleBoundingRectangle(startTimeMarkHistoItem.boundingRect(), 1.05f));
1807    startTimeMarkHistoZoom->setZoomStack(stack);
1808    stack.pop();
1809    stack.push(scaleBoundingRectangle(triggerDelayHistoItem.boundingRect(), 1.05f));
1810    triggerDelayHistoZoom->setZoomStack(stack);
1811    stack.pop();
1812
1813    pixelChanged(GLWindow->selectedPixel);
1814}
1815//can't use a ref to rectangle, as the type must be converted first
1816QRectF UIConnector::scaleBoundingRectangle(QRectF rectangle, float scale)
1817{
1818    QPointF bottomRight = rectangle.bottomRight();
1819    QPointF topLeft = rectangle.topLeft();
1820    QPointF center = rectangle.center();
1821    return QRectF(topLeft + (topLeft-center)*(scale-1.0f), //top left
1822                  bottomRight + (bottomRight-center)*(scale-1.0f)); //bottom right
1823}
1824void UIConnector::initHistograms()
1825{
1826//    QwtPlot*     boardsTimeHisto;
1827//    QwtPlotHistogram boardsTimeHistoItem;
1828    grid1 = new QwtPlotGrid;
1829    grid1->enableX(false);
1830    grid1->enableY(true);
1831    grid1->enableXMin(false);
1832    grid1->enableYMin(false);
1833    grid1->setMajPen(QPen(Qt::black, 0, Qt::DotLine));
1834    grid1->attach(boardsTimeHisto);
1835
1836    grid2 = new QwtPlotGrid;
1837    grid2->enableX(false);
1838    grid2->enableY(true);
1839    grid2->enableXMin(false);
1840    grid2->enableYMin(false);
1841    grid2->setMajPen(QPen(Qt::black, 0, Qt::DotLine));
1842    grid2->attach(startCellsHisto);
1843
1844    grid3 = new QwtPlotGrid;
1845    grid3->enableX(false);
1846    grid3->enableY(true);
1847    grid3->enableXMin(false);
1848    grid3->enableYMin(false);
1849    grid3->setMajPen(QPen(Qt::black, 0, Qt::DotLine));
1850    grid3->attach(startTimeMarkHisto);
1851
1852    grid4 = new QwtPlotGrid;
1853    grid4->enableX(false);
1854    grid4->enableY(true);
1855    grid4->enableXMin(false);
1856    grid4->enableYMin(false);
1857    grid4->setMajPen(QPen(Qt::black, 0, Qt::DotLine));
1858    grid4->attach(pixelValueCurve);
1859
1860    grid6 = new QwtPlotGrid;
1861    grid6->enableX(false);
1862    grid6->enableY(true);
1863    grid6->enableXMin(false);
1864    grid6->enableYMin(false);
1865    grid6->setMajPen(QPen(Qt::black, 0, Qt::DotLine));
1866    grid6->attach(pixelAverageCurve);
1867
1868    grid5 = new QwtPlotGrid;
1869    grid5->enableX(false);
1870    grid5->enableY(true);
1871    grid5->enableXMin(false);
1872    grid5->enableYMin(false);
1873    grid5->setMajPen(QPen(Qt::black, 0, Qt::DotLine));
1874    grid5->attach(triggerDelayHisto);
1875
1876    boardsTimeHisto->setAutoReplot(true);
1877    startCellsHisto->setAutoReplot(true);
1878    startTimeMarkHisto->setAutoReplot(true);
1879    pixelValueCurve->setAutoReplot(true);
1880    pixelAverageCurve->setAutoReplot(true);
1881    triggerDelayHisto->setAutoReplot(true);
1882    boardsTimeHisto->setTitle("Boards time values");
1883    startCellsHisto->setTitle("Start Cell values");
1884    startTimeMarkHisto->setTitle("Start Time Marks values");
1885    pixelValueCurve->setTitle("Current pixel values");
1886    pixelAverageCurve->setTitle("Average pixels values");
1887    triggerDelayHisto->setTitle("Trigger Delays");
1888
1889 //   boardsTimeHistoItem.setBrush(QBrush(Qt::red));
1890//    startCellHistoItem.setBrush(QBrush(Qt::red));
1891//    startTimeMarkHistoItem.setBrush(QBrush(Qt::red));
1892//    triggerDelayHistoItem.setBrush(QBrush(Qt::red));
1893//    pixelValueCurveItem.setBrush(QBrush(Qt::red));
1894
1895    boardsTimeHistoItem.setPen(QColor(Qt::darkGreen));
1896    boardsTimeHistoItem.setStyle(QwtPlotCurve::Steps);
1897    startCellHistoItem.setPen(QColor(Qt::darkGreen));
1898    startCellHistoItem.setStyle(QwtPlotCurve::Steps);
1899    startTimeMarkHistoItem.setPen(QColor(Qt::darkGreen));
1900    startTimeMarkHistoItem.setStyle(QwtPlotCurve::Steps);
1901    triggerDelayHistoItem.setPen(QColor(Qt::darkGreen));
1902    triggerDelayHistoItem.setStyle(QwtPlotCurve::Steps);
1903
1904    boardsTimeHistoItem.attach(boardsTimeHisto);
1905    startCellHistoItem.attach(startCellsHisto);
1906    startTimeMarkHistoItem.attach(startTimeMarkHisto);
1907    triggerDelayHistoItem.attach(triggerDelayHisto);
1908
1909    //curve
1910//    pixelValueCurveItem.setSymbol(new QwtSymbol(QwtSymbol::Cross, Qt::NoBrush, QPen(Qt::black), QSize(5,5)));
1911    pixelValueCurveItem.setPen(QColor(Qt::black));
1912    pixelAverageCurveItem.setPen(QColor(Qt::black));
1913    aMeanCurveItem.setPen(QColor(Qt::darkGreen));
1914    vCorrCurveItem.setPen(QColor(Qt::red));
1915    meanCurveItem.setPen(QColor(Qt::blue));
1916    pixelValueCurveItem.setStyle(QwtPlotCurve::Lines);
1917    pixelAverageCurveItem.setStyle(QwtPlotCurve::Lines);
1918    aMeanCurveItem.setStyle(QwtPlotCurve::Lines);
1919    vCorrCurveItem.setStyle(QwtPlotCurve::Lines);
1920    meanCurveItem.setStyle(QwtPlotCurve::Lines);
1921
1922//    pixelValueCurveItem.setCurveAttribute(QwtPlotCurve::Fitted);
1923    pixelValueCurveItem.attach(pixelValueCurve);
1924    pixelAverageCurveItem.attach(pixelAverageCurve);
1925//    aMeanCurveItem.attach(pixelValueCurve);
1926 //   vCorrCurveItem.attach(pixelValueCurve);
1927//    meanCurveItem.attach(pixelValueCurve);
1928
1929    //FIXME delete these pointers with the destructor
1930    curveZoom = new QwtPlotZoomer(pixelValueCurve->canvas());
1931    curveZoom->setRubberBandPen(QPen(Qt::gray, 2, Qt::DotLine));
1932    curveZoom->setTrackerPen(QPen(Qt::gray));
1933    averageCurveZoom = new QwtPlotZoomer(pixelAverageCurve->canvas());
1934    averageCurveZoom->setRubberBandPen(QPen(Qt::gray, 2, Qt::DotLine));
1935    averageCurveZoom->setTrackerPen(QPen(Qt::gray));
1936
1937    boardsTimeHistoZoom = new QwtPlotZoomer(boardsTimeHisto->canvas());
1938    boardsTimeHistoZoom->setRubberBandPen(QPen(Qt::gray, 2, Qt::DotLine));
1939    boardsTimeHistoZoom->setTrackerPen(QPen(Qt::gray));
1940
1941    startCellHistoZoom = new QwtPlotZoomer(startCellsHisto->canvas());
1942    startCellHistoZoom->setRubberBandPen(QPen(Qt::gray, 2, Qt::DotLine));
1943    startCellHistoZoom->setTrackerPen(QPen(Qt::gray));
1944
1945    startTimeMarkHistoZoom = new QwtPlotZoomer(startTimeMarkHisto->canvas());
1946    startTimeMarkHistoZoom->setRubberBandPen(QPen(Qt::gray, 2, Qt::DotLine));
1947    startTimeMarkHistoZoom->setTrackerPen(QPen(Qt::gray));
1948
1949    triggerDelayHistoZoom = new QwtPlotZoomer(triggerDelayHisto->canvas());
1950    triggerDelayHistoZoom->setRubberBandPen(QPen(Qt::gray, 2, Qt::DotLine));
1951    triggerDelayHistoZoom->setTrackerPen(QPen(Qt::gray));
1952
1953
1954}
1955
1956void UIConnector::pixelChanged(int pixel)
1957{
1958    RMS_window->fWhite = pixel;
1959    Mean_window->fWhite = pixel;
1960    Max_window->fWhite = pixel;
1961    PosOfMax_window->fWhite = pixel;
1962    if (pixel != -1)
1963    {
1964        RMS_window->fWhitePatch = RMS_window->pixelsPatch[pixel];
1965        Mean_window->fWhitePatch = Mean_window->pixelsPatch[pixel];
1966        Max_window->fWhitePatch = Max_window->pixelsPatch[pixel];
1967        PosOfMax_window->fWhitePatch = PosOfMax_window->pixelsPatch[pixel];
1968    }
1969    else
1970    {
1971        RMS_window->fWhitePatch = -1;
1972        Mean_window->fWhitePatch = -1;
1973        Max_window->fWhitePatch = -1;
1974        PosOfMax_window->fWhitePatch = -1;
1975    }
1976    if (pixel == -1)
1977        return;
1978    int softwarePix = pixel;
1979//    if (!GLWindow->_softwareOrdering)
1980        pixel = GLWindow->hardwareMapping[pixel];
1981
1982    HwIDBox->setValue(pixel);
1983
1984    if (!GLWindow->nRoi)
1985        return;
1986
1987int currentPixel = pixel;
1988
1989    for (int i=0;i<GLWindow->nRoi;i++)
1990    {
1991        xval[i] = i;
1992        yval[i] = GLWindow->eventData[GLWindow->nRoi*currentPixel + i];
1993    }
1994
1995int realNumSamples = GLWindow->nRoi;
1996    if (GLWindow->nRoiTM != 0)
1997    {
1998        const PixelMapEntry& mapEntry = GLWindow->fPixelMap.index(softwarePix);
1999        const int pixelIdInPatch = mapEntry.pixel();
2000        const int patchId = mapEntry.patch();
2001        const int boardId = mapEntry.board();
2002        const int crateId = mapEntry.crate();
2003        if (pixelIdInPatch == 8)
2004        {
2005            int TMIndex = 0;
2006            int xIndex = GLWindow->nRoi;
2007            int arrayIndex = GLWindow->nRoi;
2008            if (GLWindow->offSetRoi < 0)
2009                TMIndex -= GLWindow->offSetRoi;
2010            if (GLWindow->offSetRoi > 0)
2011                xIndex += GLWindow->offSetRoi;
2012            for (int i=TMIndex;i<GLWindow->nRoiTM;i++, xIndex++, arrayIndex++)
2013            {
2014                xval[arrayIndex] = xIndex;
2015                yval[arrayIndex] = GLWindow->eventData[GLWindow->nRoi*1440 + GLWindow->nRoiTM*(40*crateId + 4*boardId + patchId) + i];
2016            }
2017            realNumSamples += GLWindow->nRoiTM - TMIndex;
2018        }
2019      //  cout << pixelIdInPatch << " " ;
2020    }
2021
2022#if QWT_VERSION < 0x060000
2023    pixelValueCurveItem.setData(xval, yval, realNumSamples);
2024#else
2025       pixelValueCurveItem.setSamples(xval, yval, realNumSamples);
2026#endif
2027
2028//now compute the average value of all pixels
2029       currentPixel = 0;
2030       for (int i=0;i<GLWindow->nRoi;i++)
2031           yval[i] = 0;
2032       for (int j=0;j<1440;j++) {
2033           currentPixel = j;
2034           if (GLWindow->softwareMapping[j]>=GLWindow->nPixels)
2035               continue;
2036           for (int i=0;i<GLWindow->nRoi;i++)
2037           {
2038               xval[i] = i;
2039               yval[i] += GLWindow->eventData[GLWindow->nRoi*currentPixel + i];
2040           }
2041       }
2042       for (int i=0;i<GLWindow->nRoi;i++)
2043           yval[i] /= GLWindow->nPixels;
2044#if QWT_VERSION < 0x060000
2045       pixelAverageCurveItem.setData(xval, yval, GLWindow->nRoi);
2046#else
2047    pixelAverageCurveItem.setSamples(xval, yval, realNumSamples);
2048#endif
2049
2050    QStack< QRectF > stack;
2051    stack.push(scaleBoundingRectangle(pixelValueCurveItem.boundingRect(), 1.5f));
2052    curveZoom->setZoomBase(scaleBoundingRectangle(pixelValueCurveItem.boundingRect(), 1.5f));
2053    curveZoom->setZoomStack(stack);
2054    stack.pop();
2055    stack.push(scaleBoundingRectangle(pixelAverageCurveItem.boundingRect(), 1.5f));
2056    averageCurveZoom->setZoomBase(scaleBoundingRectangle(pixelAverageCurveItem.boundingRect(), 1.5f));
2057    averageCurveZoom->setZoomStack(stack);
2058    stack.pop();
2059
2060    displaySliceValue();
2061    if (autoScaleColor->isChecked())
2062        on_autoScaleColor_clicked();
2063}
2064
2065void UIConnector::on_HwIDBox_valueChanged(int)
2066{
2067    updating = true;
2068
2069    const int hwID = HwIDBox->value();
2070
2071    const int crateID =  hwID/360;
2072    const int boardID = (hwID%360)/36;
2073    const int patchID = (hwID%36 )/9;
2074    const int pixelID =  hwID%9;
2075
2076    SwIDBox->setValue(GLWindow->softwareMapping[hwID]);
2077
2078    crateIDBox->setValue(crateID);
2079    boardIDBox->setValue(boardID);
2080    patchIDBox->setValue(patchID);
2081    pixelIDBox->setValue(pixelID);
2082
2083    updating = false;
2084
2085    GLWindow->selectedPixel = GLWindow->softwareMapping[hwID];
2086    GLWindow->updateGL();
2087
2088    pixelChanged(GLWindow->selectedPixel);
2089}
2090
2091void UIConnector::cbpxChanged()
2092{
2093    if (updating)
2094        return;
2095
2096    const int hwid = crateIDBox->value()*360 + boardIDBox->value()*36 + patchIDBox->value()*9 + pixelIDBox->value();
2097    HwIDBox->setValue(hwid);
2098}
2099
2100void UIConnector::on_SwIDBox_valueChanged(int swid)
2101{
2102    if (updating)
2103        return;
2104
2105//    if (GLWindow->_softwareOrdering)
2106//        HwIDBox->setValue(swid);
2107//    else
2108        HwIDBox->setValue(GLWindow->hardwareMapping[swid]);
2109}
2110
2111void UIConnector::on_autoScaleColor_clicked()
2112{
2113    if (!autoScaleColor->isChecked())
2114    {
2115        GLWindow->ss[0] = 0.496;
2116        GLWindow->ss[1] = 0.507;
2117        GLWindow->ss[2] = 0.518;
2118        GLWindow->ss[3] = 0.529;
2119        GLWindow->ss[4] = 0.540;;
2120        colorRange0->setValue(GLWindow->ss[0]);
2121        colorRange1->setValue(GLWindow->ss[1]);
2122        colorRange2->setValue(GLWindow->ss[2]);
2123        colorRange3->setValue(GLWindow->ss[3]);
2124        colorRange4->setValue(GLWindow->ss[4]);
2125        return;
2126    }
2127    if (!GLWindow->nRoi)
2128        return;
2129
2130    int start = 0;
2131    int end   = 1440;
2132
2133    if (!entireCameraScale->isChecked())
2134    {
2135        start = GLWindow->selectedPixel;
2136        end   = GLWindow->selectedPixel+1;
2137        if (end == 0)
2138        {
2139            start = 0;
2140            end = 1440;
2141        }
2142    }
2143
2144    int min =  100000; //real min = -2048, int_16 = -32768 to 32767
2145    int max = -100000; //real max = 2047
2146
2147    long average = 0;
2148    long numSamples = 0;
2149    int errorDetected = -1;
2150
2151    for (int i=start;i<end;i++)
2152    {
2153        if (i==863)//keep crazy pixel out of the autoscale
2154            continue;
2155
2156        if (GLWindow->softwareMapping[i]>=GLWindow->nPixels)
2157            continue;
2158
2159        for (int j=10;j<GLWindow->nRoi-50;j++)
2160        {
2161            int cValue = GLWindow->eventData[i*GLWindow->nRoi+j];
2162            if (cValue > max && cValue < 32767)
2163                max = cValue;
2164            if (cValue < min && cValue > -32768)
2165               min = cValue;
2166            if (cValue < 32767 && cValue > -32768)
2167            {
2168                average+=cValue;
2169                numSamples++;
2170            }
2171            else
2172            {
2173                errorDetected = i;
2174            }
2175//            numSamples++;
2176        }
2177    }
2178    average /= numSamples;
2179    if (errorDetected != -1)
2180    {
2181        cout << "Overflow detected at pixel " << errorDetected << " (at least)" << endl;
2182    }
2183//    cout << "min: " << min << " max: " << max << " average: " << average << endl;
2184    float minRange = (float)(min+(GLWindow->VALUES_SPAN/2))/(float)(GLWindow->VALUES_SPAN-1);
2185    float maxRange = (float)(max+(GLWindow->VALUES_SPAN/2))/(float)(GLWindow->VALUES_SPAN-1);
2186    float midRange = (float)(average+(GLWindow->VALUES_SPAN/2))/(float)(GLWindow->VALUES_SPAN-1);
2187    if (GLWindow->logScale)
2188    {
2189        minRange *= 9;
2190        maxRange *= 9;
2191//        midRange *= 9;
2192        minRange += 1;
2193        maxRange += 1;
2194//        midRange += 1;
2195        minRange = log10(minRange);
2196        maxRange = log10(maxRange);
2197//        midRange = (minRange + maxRange)/2.f;
2198        midRange = log10(midRange);
2199    }
2200
2201    GLWindow->ss[0] = minRange;
2202    colorRange0->setValue(GLWindow->ss[0]);
2203    GLWindow->ss[4] = maxRange;
2204    colorRange4->setValue(GLWindow->ss[4]);
2205//    GLWindow->ss[2] = midRange;
2206//    range2->setValue(GLWindow->ss[2]);
2207//    GLWindow->ss[1] = (minRange+midRange)/2;
2208//    range1->setValue(GLWindow->ss[1]);
2209//    GLWindow->ss[3] = (maxRange+midRange)/2;
2210//    range3->setValue(GLWindow->ss[3]);
2211
2212    GLWindow->ss[2] = (maxRange+minRange)/2;
2213    colorRange2->setValue(GLWindow->ss[2]);
2214
2215    GLWindow->ss[1] = minRange+(maxRange-minRange)/4;
2216    colorRange1->setValue(GLWindow->ss[1]);
2217
2218    GLWindow->ss[3] = minRange+3*(maxRange-minRange)/4;
2219    colorRange3->setValue(GLWindow->ss[3]);
2220}
2221
2222void PrintUsage()
2223{
2224    cout << "\n"
2225        "The FACT++ raw data viewer.\n"
2226        "\n"
2227        "Usage: viewer [OPTIONS] [datafile.fits[.gz|.fz] [calibration.drs.fits[.gz]]]\n"
2228        "  or:  viewer [OPTIONS]\n";
2229    cout << endl;
2230
2231}
2232
2233void PrintHelp()
2234{
2235    cout <<
2236            "\n"
2237         << endl;
2238}
2239
2240int UIConnector::SetupConfiguration(Configuration &conf)
2241{
2242    RawDataViewer *canvas = GLWindow;
2243
2244    if (conf.Has("mappingFile"))
2245    {
2246        canvas->assignPixelMapFile(conf.GetPrefixedString("mappingFile"));
2247    }
2248    else
2249        canvas->assignPixelMapFile("");
2250
2251    if (!canvas->isFACT())
2252    {
2253        HwIDBox->setMaximum(71);
2254        SwIDBox->setMaximum(71);
2255        SwIDBox->setValue(0);
2256        HwIDBox->setValue(19);
2257        crateIDBox->setMaximum(0);
2258        crateIDBox->setEnabled(false);
2259        boardIDBox->setMaximum(1);
2260    }
2261
2262    if (conf.Has("color.range"))
2263    {
2264        vector<double> value = conf.Vec<double>("color.range");
2265        if (value.size() != 5)
2266        {
2267            cout << "Error, colorRange option should have exactly 5 double values" << endl;
2268            return -1;
2269        }
2270        for (int i=0;i<5;i++)
2271            canvas->ss[i] = value[i];
2272    }
2273
2274    if (conf.Has("color.red"))
2275    {
2276        vector<double> value = conf.Vec<double>("color.red");
2277        if (value.size() != 5)
2278        {
2279            cout << "Error, colorRed option should have exactly 5 double values" << endl;
2280            return -1;
2281        }
2282        for (int i=0;i<5;i++)
2283            canvas->rr[i] = value[i];
2284    }
2285
2286    if (conf.Has("color.green"))
2287    {
2288        vector<double> value = conf.Vec<double>("color.green");
2289        if (value.size() != 5)
2290        {
2291            cout << "Error, colorGreen option should have exactly 5 double values" << endl;
2292            return -1;
2293        }
2294        for (int i=0;i<5;i++)
2295            canvas->gg[i] = value[i];
2296    }
2297
2298    if (conf.Has("color.blue"))
2299    {
2300        vector<double> value = conf.Vec<double>("color.blue");
2301        if (value.size() != 5)
2302        {
2303            cout << "Error, colorBlue option should have exactly 5 double values" << endl;
2304            return -1;
2305        }
2306        for (int i=0;i<5;i++)
2307            canvas->bb[i] = value[i];
2308    }
2309
2310    colorRange0->setValue(canvas->ss[0]);
2311    colorRange1->setValue(canvas->ss[1]);
2312    colorRange2->setValue(canvas->ss[2]);
2313    colorRange3->setValue(canvas->ss[3]);
2314    colorRange4->setValue(canvas->ss[4]);
2315    redValue0->setValue(canvas->rr[0]);
2316    redValue1->setValue(canvas->rr[1]);
2317    redValue2->setValue(canvas->rr[2]);
2318    redValue3->setValue(canvas->rr[3]);
2319    redValue4->setValue(canvas->rr[4]);
2320    greenValue0->setValue(canvas->gg[0]);
2321    greenValue1->setValue(canvas->gg[1]);
2322    greenValue2->setValue(canvas->gg[2]);
2323    greenValue3->setValue(canvas->gg[3]);
2324    greenValue4->setValue(canvas->gg[4]);
2325    blueValue0->setValue(canvas->bb[0]);
2326    blueValue1->setValue(canvas->bb[1]);
2327    blueValue2->setValue(canvas->bb[2]);
2328    blueValue3->setValue(canvas->bb[3]);
2329    blueValue4->setValue(canvas->bb[4]);
2330
2331    if (conf.Has("drs"))
2332    {
2333        const QString qstr(conf.Get<string>("drs").c_str());
2334        calibFileSelected(qstr);
2335    }
2336
2337    if (conf.Has("file"))
2338    {
2339        const QString qstr(conf.Get<string>("file").c_str());
2340        fileSelected(qstr);
2341    }
2342
2343
2344    return 0;
2345}
2346
2347void SetupConfiguration(Configuration& conf)
2348{
2349    po::options_description configs("Raw Events Viewer Options");
2350    configs.add_options()
2351        ("color.range", vars<double>(), "Range of the display colours")
2352        ("color.red",   vars<double>(), "Range of red values")
2353        ("color.green", vars<double>(), "Range of green values")
2354        ("color.blue",  vars<double>(), "Range of blue values")
2355        ("file,f",      var<string>(),  "File to be loaded")
2356        ("drs,d",       var<string>(),  "DRS calibration file to be loaded")
2357        ("mappingFile", var<string>(),  "Which pixels mapping file to use")
2358        ;
2359    conf.AddOptions(configs);
2360
2361    po::positional_options_description p;
2362    p.add("file", 1); // The first positional options
2363    p.add("drs",  2); // The first positional options
2364    conf.SetArgumentPositions(p);
2365
2366}
2367
2368/************************************************************
2369 * MAIN PROGRAM FUNCTION.
2370 ************************************************************/
2371int main(int argc, const char *argv[])
2372{
2373    QApplication app(argc, const_cast<char**>(argv));
2374
2375    if (!QGLFormat::hasOpenGL()) {
2376        std::cerr << "This system has no OpenGL support" << std::endl;
2377        return 1;
2378    }
2379
2380    Configuration conf(argv[0]);
2381    conf.SetPrintUsage(PrintUsage);
2382    SetupConfiguration(conf);
2383    if (!conf.DoParse(argc, argv, PrintHelp))
2384        return 2;
2385
2386    UIConnector myUi;
2387    if (myUi.SetupConfiguration(conf)<0)
2388        return 3;
2389
2390    return app.exec();
2391}
2392
Note: See TracBrowser for help on using the repository browser.