Changeset 15 in flair-src for trunk/tools/FlairGCS/src/Scope.cpp


Ignore:
Timestamp:
04/08/16 15:40:57 (8 years ago)
Author:
Bayard Gildas
Message:

sources reformatted with flair-format-dir script

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/tools/FlairGCS/src/Scope.cpp

    r10 r15  
    2121#define WHEEL_DIVIDOR 30
    2222
    23 Scope::Scope(QString title,float ymin,float ymax,float view_size_s,unsigned int refresh_rate_ms,unsigned int history_size): QwtPlot() {
    24     this->ymin=ymin;
    25     this->ymax=ymax;
    26     this->history_size=history_size;
    27     this->view_size_s=view_size_s;
    28     orig_view_size_s=view_size_s;
    29 
    30     //scroll bar
    31     scrollbar=new ScrollBar(Qt::Horizontal,canvas());
    32     connect(scrollbar,SIGNAL(valueChanged(Qt::Orientation,float,float)),this,SLOT(scrollBarMoved(Qt::Orientation,float,float)));
    33     scrolling=true;
    34 
    35     //minimum size; sinon widget trop grand
    36     setMinimumHeight(10);
    37     setMinimumWidth(1);
    38 
    39     alignScales();//is it necessary?
    40 
    41     //  Initialize data
    42     elapsed_time_s=0;
    43 
    44     // Assign a title
    45     setTitle(title);
    46 
    47     // Axis
    48     setAxisTitle(QwtPlot::xBottom, "Time (s)");
    49     setAxisScale(QwtPlot::xBottom,0, view_size_s);
    50 
    51     setAxisTitle(QwtPlot::yLeft, "Values");
    52     setAxisScale(QwtPlot::yLeft, ymin, ymax);
    53 
    54     // grid
    55     QwtPlotGrid *grid = new QwtPlotGrid;
    56     grid->setPen(QPen(Qt::black, 0, Qt::DotLine));
    57     grid->attach(this);
    58 
    59     //zoomer
    60     QwtPlotMagnifier * zoomer = new QwtPlotMagnifier(canvas());
    61     zoomer->setWheelModifiers( Qt::ControlModifier );
    62     zoomer->setMouseButton(Qt::NoButton);
    63     zoomer->setAxisEnabled(xBottom,0);
    64 
    65     //scroller
    66     QwtPlotPanner *scroller =new QwtPlotPanner(canvas());
    67     scroller->setAxisEnabled(xBottom,0);
    68 
    69     //legend
    70     QwtLegend* new_legend=new QwtLegend();
    71     new_legend->setDefaultItemMode(QwtLegendData::Checkable);
    72     insertLegend(new_legend, QwtPlot::BottomLegend);
    73 
    74     connect( new_legend, SIGNAL( checked( const QVariant &, bool, int ) ), SLOT( legendChecked( const QVariant &, bool ) ) );
    75 
    76     QTimer *timer = new QTimer(this);
    77     connect(timer, SIGNAL(timeout()), this, SLOT(replot()));
    78     timer->start(refresh_rate_ms);
     23Scope::Scope(QString title, float ymin, float ymax, float view_size_s,
     24             unsigned int refresh_rate_ms, unsigned int history_size)
     25    : QwtPlot() {
     26  this->ymin = ymin;
     27  this->ymax = ymax;
     28  this->history_size = history_size;
     29  this->view_size_s = view_size_s;
     30  orig_view_size_s = view_size_s;
     31
     32  // scroll bar
     33  scrollbar = new ScrollBar(Qt::Horizontal, canvas());
     34  connect(scrollbar, SIGNAL(valueChanged(Qt::Orientation, float, float)), this,
     35          SLOT(scrollBarMoved(Qt::Orientation, float, float)));
     36  scrolling = true;
     37
     38  // minimum size; sinon widget trop grand
     39  setMinimumHeight(10);
     40  setMinimumWidth(1);
     41
     42  alignScales(); // is it necessary?
     43
     44  //  Initialize data
     45  elapsed_time_s = 0;
     46
     47  // Assign a title
     48  setTitle(title);
     49
     50  // Axis
     51  setAxisTitle(QwtPlot::xBottom, "Time (s)");
     52  setAxisScale(QwtPlot::xBottom, 0, view_size_s);
     53
     54  setAxisTitle(QwtPlot::yLeft, "Values");
     55  setAxisScale(QwtPlot::yLeft, ymin, ymax);
     56
     57  // grid
     58  QwtPlotGrid *grid = new QwtPlotGrid;
     59  grid->setPen(QPen(Qt::black, 0, Qt::DotLine));
     60  grid->attach(this);
     61
     62  // zoomer
     63  QwtPlotMagnifier *zoomer = new QwtPlotMagnifier(canvas());
     64  zoomer->setWheelModifiers(Qt::ControlModifier);
     65  zoomer->setMouseButton(Qt::NoButton);
     66  zoomer->setAxisEnabled(xBottom, 0);
     67
     68  // scroller
     69  QwtPlotPanner *scroller = new QwtPlotPanner(canvas());
     70  scroller->setAxisEnabled(xBottom, 0);
     71
     72  // legend
     73  QwtLegend *new_legend = new QwtLegend();
     74  new_legend->setDefaultItemMode(QwtLegendData::Checkable);
     75  insertLegend(new_legend, QwtPlot::BottomLegend);
     76
     77  connect(new_legend, SIGNAL(checked(const QVariant &, bool, int)),
     78          SLOT(legendChecked(const QVariant &, bool)));
     79
     80  QTimer *timer = new QTimer(this);
     81  connect(timer, SIGNAL(timeout()), this, SLOT(replot()));
     82  timer->start(refresh_rate_ms);
    7983}
    8084
    8185Scope::~Scope() {
    82     for(int i=0;i<curves.count();i++) {
    83         free(curves.at(i)->data_x);
    84         free(curves.at(i)->data_y);
    85         delete curves.at(i)->plot;
    86         free(curves.at(i));
    87     }
     86  for (int i = 0; i < curves.count(); i++) {
     87    free(curves.at(i)->data_x);
     88    free(curves.at(i)->data_y);
     89    delete curves.at(i)->plot;
     90    free(curves.at(i));
     91  }
    8892}
    8993
    9094void Scope::resetXView(void) {
    91     //setAxisScale(QwtPlot::xBottom,0, orig_view_size_s);
    92     changeViewSize(orig_view_size_s);
    93 }
    94 
    95 void Scope::resetYView(void) {
    96     setAxisScale(QwtPlot::yLeft, ymin, ymax);
    97 }
     95  // setAxisScale(QwtPlot::xBottom,0, orig_view_size_s);
     96  changeViewSize(orig_view_size_s);
     97}
     98
     99void Scope::resetYView(void) { setAxisScale(QwtPlot::yLeft, ymin, ymax); }
    98100
    99101bool Scope::eventFilter(QObject *o, QEvent *e) {
    100     switch(e->type()) {
    101         case QEvent::Resize: {
    102             const int fw = ((QwtPlotCanvas *)canvas())->frameWidth();
    103 
    104             QRect rect;
    105             rect.setSize(((QResizeEvent *)e)->size());
    106             rect.setRect(rect.x() + fw, rect.y() + fw,
    107                 rect.width() - 2 * fw, rect.height() - 2 * fw);
    108 
    109             scrollbar->setGeometry(0, 0, rect.width(), 10);
    110             return true;
    111         }
    112         case QEvent::Wheel: {
    113             //ctrl+wheel is already handled for y zoom
    114             if(!(QApplication::keyboardModifiers() & Qt::ControlModifier)) {
    115                 QWheelEvent *wheelevent = static_cast<QWheelEvent *> (e);
    116                 if(view_size_s+wheelevent->delta()/WHEEL_DIVIDOR>0) changeViewSize(view_size_s+wheelevent->delta()/WHEEL_DIVIDOR);
    117             }
    118             return true;
    119         }
    120         default:
    121             break;
    122     }
    123     return QwtPlot::eventFilter(o, e);
     102  switch (e->type()) {
     103  case QEvent::Resize: {
     104    const int fw = ((QwtPlotCanvas *)canvas())->frameWidth();
     105
     106    QRect rect;
     107    rect.setSize(((QResizeEvent *)e)->size());
     108    rect.setRect(rect.x() + fw, rect.y() + fw, rect.width() - 2 * fw,
     109                 rect.height() - 2 * fw);
     110
     111    scrollbar->setGeometry(0, 0, rect.width(), 10);
     112    return true;
     113  }
     114  case QEvent::Wheel: {
     115    // ctrl+wheel is already handled for y zoom
     116    if (!(QApplication::keyboardModifiers() & Qt::ControlModifier)) {
     117      QWheelEvent *wheelevent = static_cast<QWheelEvent *>(e);
     118      if (view_size_s + wheelevent->delta() / WHEEL_DIVIDOR > 0)
     119        changeViewSize(view_size_s + wheelevent->delta() / WHEEL_DIVIDOR);
     120    }
     121    return true;
     122  }
     123  default:
     124    break;
     125  }
     126  return QwtPlot::eventFilter(o, e);
    124127}
    125128
    126129void Scope::changeViewSize(float new_view_size_s) {
    127     view_size_s=new_view_size_s;
    128 
    129     if(scrolling==false) {
    130         //4 cas: on utilise le temps au milieu de la vue actuelle
    131 
    132         //le temps total est plus petit que le view_size_s, on affiche tout:
    133         if(elapsed_time_s<view_size_s) {
    134             scrolling=true;
    135         } else {
    136             double min=(min_scroll+max_scroll)/2-view_size_s/2;
    137             double max=(min_scroll+max_scroll)/2+view_size_s/2;
    138             //on va du debut jusqu'a view size
    139             if( min<0) {
    140                 min=0;
    141                 max=view_size_s;
    142             }
    143             //on va de fin-viewsize jusqu'a la fin
    144             if(max>elapsed_time_s) {
    145                 min=elapsed_time_s-view_size_s;
    146                 max=elapsed_time_s;
    147             }
    148             scrollbar->moveSlider(min,max);//move slider coupe le signal, on fait aussi le scrollbar
    149             scrollBarMoved(Qt::Horizontal,min,max);
    150         }
    151     }
    152 }
    153 
    154 void Scope::legendChecked( const QVariant &itemInfo, bool on ) {
    155     QwtPlotItem *plotItem=infoToItem(itemInfo);
    156     if(plotItem) showCurve( plotItem, on );
     130  view_size_s = new_view_size_s;
     131
     132  if (scrolling == false) {
     133    // 4 cas: on utilise le temps au milieu de la vue actuelle
     134
     135    // le temps total est plus petit que le view_size_s, on affiche tout:
     136    if (elapsed_time_s < view_size_s) {
     137      scrolling = true;
     138    } else {
     139      double min = (min_scroll + max_scroll) / 2 - view_size_s / 2;
     140      double max = (min_scroll + max_scroll) / 2 + view_size_s / 2;
     141      // on va du debut jusqu'a view size
     142      if (min < 0) {
     143        min = 0;
     144        max = view_size_s;
     145      }
     146      // on va de fin-viewsize jusqu'a la fin
     147      if (max > elapsed_time_s) {
     148        min = elapsed_time_s - view_size_s;
     149        max = elapsed_time_s;
     150      }
     151      scrollbar->moveSlider(
     152          min, max); // move slider coupe le signal, on fait aussi le scrollbar
     153      scrollBarMoved(Qt::Horizontal, min, max);
     154    }
     155  }
     156}
     157
     158void Scope::legendChecked(const QVariant &itemInfo, bool on) {
     159  QwtPlotItem *plotItem = infoToItem(itemInfo);
     160  if (plotItem)
     161    showCurve(plotItem, on);
    157162}
    158163
    159164void Scope::showCurve(QwtPlotItem *item, bool on) {
    160     item->setVisible(on);
    161 
    162     QwtLegend *lgd=qobject_cast<QwtLegend*>(legend());
    163 
    164     QList<QWidget*> legendWidgets=lgd->legendWidgets(itemToInfo(item));
    165 
    166     if(legendWidgets.size()==1) {
    167         QwtLegendLabel *legendLabel=qobject_cast<QwtLegendLabel*>(legendWidgets[0]);
    168 
    169         if(legendLabel) legendLabel->setChecked( on );
    170     }
    171 }
    172 
    173 int Scope::addCurve(QPen pen,QString legend) {
    174     Curve* curve=(Curve*)malloc(sizeof(Curve));
    175     curve->data_x=(double*)calloc(history_size,sizeof(double));
    176     curve->data_y=(double*)calloc(history_size,sizeof(double));
    177     curve->index=0;
    178     curve->min_index=0;
    179     curve->max_index=0;
    180 
    181     // Insert new curve
    182     curve->plot=new QwtPlotCurve(legend);
    183     curve->plot->attach(this);
    184     curve->plot->setPen(pen);
    185     curves.append(curve);
    186 
    187     showCurve(curve->plot, true);
    188 
    189     return curves.count()-1;
    190 }
    191 
    192 void Scope::updateCurve(Curve* curve) {
    193         if(scrolling==true) {
    194         curve->plot->setRawSamples(&curve->data_x[curve->min_index], &curve->data_y[curve->min_index], curve->max_index-curve->min_index);
    195     }
    196 
    197     if(curve->index==history_size) {
    198         //printf("a revoir qd on arrive a la fin, il faudrait faire un realloc pour rien perdre\n");
    199         //attention le setrawdata s'attend a ce que l'adresse change pas, ce qui n'est pas le cas avec lerealloc
    200         //il faudra refaire un setrawdata ici
    201         curve->index=0;
    202         curve->min_index=0;
    203         scrolling=true;
    204     }
    205 
    206     //determine les index pour la visualisation
    207     if(scrolling==true) {
    208         curve->max_index=curve->index;
    209         computeMinIndex(curve,elapsed_time_s-view_size_s);
    210     }
    211 
    212     scrollbar->setBase(0,elapsed_time_s);
    213     if(scrolling==true) {
    214         scrollbar->moveSlider(elapsed_time_s-view_size_s,elapsed_time_s);
    215 
    216         if(elapsed_time_s<view_size_s) {
    217             setAxisScale(QwtPlot::xBottom,0, view_size_s);
    218         } else {
    219             setAxisScale(QwtPlot::xBottom,elapsed_time_s-view_size_s, elapsed_time_s);
    220         }
     165  item->setVisible(on);
     166
     167  QwtLegend *lgd = qobject_cast<QwtLegend *>(legend());
     168
     169  QList<QWidget *> legendWidgets = lgd->legendWidgets(itemToInfo(item));
     170
     171  if (legendWidgets.size() == 1) {
     172    QwtLegendLabel *legendLabel =
     173        qobject_cast<QwtLegendLabel *>(legendWidgets[0]);
     174
     175    if (legendLabel)
     176      legendLabel->setChecked(on);
     177  }
     178}
     179
     180int Scope::addCurve(QPen pen, QString legend) {
     181  Curve *curve = (Curve *)malloc(sizeof(Curve));
     182  curve->data_x = (double *)calloc(history_size, sizeof(double));
     183  curve->data_y = (double *)calloc(history_size, sizeof(double));
     184  curve->index = 0;
     185  curve->min_index = 0;
     186  curve->max_index = 0;
     187
     188  // Insert new curve
     189  curve->plot = new QwtPlotCurve(legend);
     190  curve->plot->attach(this);
     191  curve->plot->setPen(pen);
     192  curves.append(curve);
     193
     194  showCurve(curve->plot, true);
     195
     196  return curves.count() - 1;
     197}
     198
     199void Scope::updateCurve(Curve *curve) {
     200  if (scrolling == true) {
     201    curve->plot->setRawSamples(&curve->data_x[curve->min_index],
     202                               &curve->data_y[curve->min_index],
     203                               curve->max_index - curve->min_index);
     204  }
     205
     206  if (curve->index == history_size) {
     207    // printf("a revoir qd on arrive a la fin, il faudrait faire un realloc pour
     208    // rien perdre\n");
     209    // attention le setrawdata s'attend a ce que l'adresse change pas, ce qui
     210    // n'est pas le cas avec lerealloc
     211    // il faudra refaire un setrawdata ici
     212    curve->index = 0;
     213    curve->min_index = 0;
     214    scrolling = true;
     215  }
     216
     217  // determine les index pour la visualisation
     218  if (scrolling == true) {
     219    curve->max_index = curve->index;
     220    computeMinIndex(curve, elapsed_time_s - view_size_s);
     221  }
     222
     223  scrollbar->setBase(0, elapsed_time_s);
     224  if (scrolling == true) {
     225    scrollbar->moveSlider(elapsed_time_s - view_size_s, elapsed_time_s);
     226
     227    if (elapsed_time_s < view_size_s) {
     228      setAxisScale(QwtPlot::xBottom, 0, view_size_s);
    221229    } else {
    222         scrollbar->moveSlider(min_scroll,max_scroll);
    223     }
     230      setAxisScale(QwtPlot::xBottom, elapsed_time_s - view_size_s,
     231                   elapsed_time_s);
     232    }
     233  } else {
     234    scrollbar->moveSlider(min_scroll, max_scroll);
     235  }
    224236}
    225237
    226238void Scope::alignScales(void) {
    227     // The code below shows how to align the scales to
    228     // the canvas frame, but is also a good example demonstrating
    229     // why the spreaded API needs polishing.
    230 /*
    231     plot->canvas()->setFrameStyle(QFrame::Box | QFrame::Plain );
    232     plot->canvas()->setLineWidth(1);
    233 */
    234     for(int i = 0;i<QwtPlot::axisCnt;i++) {
    235         QwtScaleWidget *scaleWidget = (QwtScaleWidget *)axisWidget(i);
    236         if(scaleWidget) scaleWidget->setMargin(0);
    237 
    238         QwtScaleDraw *scaleDraw=(QwtScaleDraw *)axisScaleDraw(i);
    239         if(scaleDraw) scaleDraw->enableComponent(QwtAbstractScaleDraw::Backbone, false);
    240     }
    241 }
    242 
    243 void Scope::scrollBarMoved(Qt::Orientation o, float min, float max)
    244 {
    245     min_scroll=min;
    246     max_scroll=max;
    247 
    248     if(max==scrollbar->maxBaseValue()) {
    249         scrolling=true;
     239  // The code below shows how to align the scales to
     240  // the canvas frame, but is also a good example demonstrating
     241  // why the spreaded API needs polishing.
     242  /*
     243      plot->canvas()->setFrameStyle(QFrame::Box | QFrame::Plain );
     244      plot->canvas()->setLineWidth(1);
     245  */
     246  for (int i = 0; i < QwtPlot::axisCnt; i++) {
     247    QwtScaleWidget *scaleWidget = (QwtScaleWidget *)axisWidget(i);
     248    if (scaleWidget)
     249      scaleWidget->setMargin(0);
     250
     251    QwtScaleDraw *scaleDraw = (QwtScaleDraw *)axisScaleDraw(i);
     252    if (scaleDraw)
     253      scaleDraw->enableComponent(QwtAbstractScaleDraw::Backbone, false);
     254  }
     255}
     256
     257void Scope::scrollBarMoved(Qt::Orientation o, float min, float max) {
     258  min_scroll = min;
     259  max_scroll = max;
     260
     261  if (max == scrollbar->maxBaseValue()) {
     262    scrolling = true;
     263  } else {
     264    scrolling = false;
     265    setAxisScale(QwtPlot::xBottom, min, max);
     266
     267    // determine les index pour la visualisation
     268    for (int i = 0; i < curves.count(); i++) {
     269      computeMinIndex(curves.at(i), min);
     270      computeMaxIndex(curves.at(i), max);
     271      curves.at(i)->plot->setRawSamples(
     272          &curves.at(i)->data_x[curves.at(i)->min_index],
     273          &curves.at(i)->data_y[curves.at(i)->min_index],
     274          curves.at(i)->max_index - curves.at(i)->min_index);
     275    }
     276  }
     277}
     278
     279// TODO: faire une dichotomie
     280void Scope::computeMinIndex(Curve *curve, float displayed_min_time) {
     281  if (curve->data_x[curve->index] > displayed_min_time) {
     282    if (curve->data_x[curve->min_index] < displayed_min_time) {
     283      while (curve->data_x[curve->min_index] < displayed_min_time &&
     284             curve->min_index != curve->index)
     285        curve->min_index++;
    250286    } else {
    251         scrolling=false;
    252         setAxisScale(QwtPlot::xBottom,min,max);
    253 
    254         //determine les index pour la visualisation
    255         for(int i=0;i<curves.count();i++) {
    256             computeMinIndex(curves.at(i),min);
    257             computeMaxIndex(curves.at(i),max);
    258             curves.at(i)->plot->setRawSamples(&curves.at(i)->data_x[curves.at(i)->min_index], &curves.at(i)->data_y[curves.at(i)->min_index], curves.at(i)->max_index-curves.at(i)->min_index);
    259         }
    260     }
    261 }
    262 
    263 //TODO: faire une dichotomie
    264 void Scope::computeMinIndex(Curve* curve,float displayed_min_time) {
    265     if(curve->data_x[curve->index]>displayed_min_time) {
    266         if(curve->data_x[curve->min_index]<displayed_min_time) {
    267             while(curve->data_x[curve->min_index]<displayed_min_time && curve->min_index!=curve->index) curve->min_index++;
    268         } else {
    269             while(curve->data_x[curve->min_index]>displayed_min_time && curve->min_index!=0) curve->min_index--;
    270         }
    271     }
    272 }
    273 
    274 void Scope::computeMaxIndex(Curve* curve,float displayed_max_time) {
    275     if(curve->data_x[curve->max_index]<displayed_max_time) {
    276         while(curve->data_x[curve->max_index]<displayed_max_time && curve->max_index!=curve->index) curve->max_index++;
    277     } else {
    278         while(curve->data_x[curve->max_index]>displayed_max_time) curve->max_index--;
    279     }
    280 }
     287      while (curve->data_x[curve->min_index] > displayed_min_time &&
     288             curve->min_index != 0)
     289        curve->min_index--;
     290    }
     291  }
     292}
     293
     294void Scope::computeMaxIndex(Curve *curve, float displayed_max_time) {
     295  if (curve->data_x[curve->max_index] < displayed_max_time) {
     296    while (curve->data_x[curve->max_index] < displayed_max_time &&
     297           curve->max_index != curve->index)
     298      curve->max_index++;
     299  } else {
     300    while (curve->data_x[curve->max_index] > displayed_max_time)
     301      curve->max_index--;
     302  }
     303}
Note: See TracChangeset for help on using the changeset viewer.