annotate widgets/Plotter.cpp @ 282:d9319859a4cf tip

(none)
author benoitrigolleau
date Fri, 31 Oct 2008 11:00:24 +0000
parents e006f4a57f86
children
rev   line source
benoitrigolleau@211 1 /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */
benoitrigolleau@211 2
benoitrigolleau@211 3 /* Sound Access
benoitrigolleau@211 4 EASAIER client application.
benoitrigolleau@211 5 Silogic 2007. Benoit Rigolleau.
benoitrigolleau@211 6
benoitrigolleau@211 7 This program is free software; you can redistribute it and/or
benoitrigolleau@211 8 modify it under the terms of the GNU General Public License as
benoitrigolleau@211 9 published by the Free Software Foundation; either version 2 of the
benoitrigolleau@211 10 License, or (at your option) any later version. See the file
benoitrigolleau@211 11 COPYING included with this distribution for more information.
benoitrigolleau@211 12 */
benoitrigolleau@211 13
benoitrigolleau@211 14 #include "Plotter.h"
benoitrigolleau@231 15 #include <math.h>
benoitrigolleau@211 16 #include <QtGui>
benoitrigolleau@211 17
benoitrigolleau@211 18 Plotter::Plotter(QWidget *parent):
benoitrigolleau@211 19 m_signalWidth(400),
lbajardsilogic@233 20 m_signalHeight(120),
benoitrigolleau@211 21 m_margin(5),
lbajardsilogic@235 22 m_curveMaskActive(false),
lbajardsilogic@235 23 m_enableDrawCurve(false)
benoitrigolleau@211 24 {
lbajardsilogic@229 25 //m_curveMask = new int[m_signalWidth];
benoitrigolleau@211 26 for(int i = 0 ; i < m_signalWidth ; i++){
lbajardsilogic@229 27 m_curveMask.push_back(0);
benoitrigolleau@211 28 }
benoitrigolleau@240 29 m_oldCurveMask = m_curveMask;
benoitrigolleau@211 30
benoitrigolleau@240 31 setMinimumSize(QSize(m_signalWidth + 2*m_margin, m_signalHeight + 2*m_margin + 10));
benoitrigolleau@211 32
benoitrigolleau@211 33 refreshPixmap();
benoitrigolleau@211 34
benoitrigolleau@211 35 }
benoitrigolleau@211 36
benoitrigolleau@211 37 void Plotter::setCurveData(const QVector<QPoint> &data){
benoitrigolleau@211 38 m_curve = data;
benoitrigolleau@211 39 refreshPixmap();
benoitrigolleau@211 40 }
benoitrigolleau@211 41
lbajardsilogic@229 42 void Plotter::setCurve(float * curve)
lbajardsilogic@229 43 {
lbajardsilogic@229 44 m_curve.clear();
benoitrigolleau@231 45 for (int i=0; i< m_signalWidth; i++)
lbajardsilogic@229 46 {
lbajardsilogic@233 47 int m = m_signalHeight*2/3 +(int) floor(curve[i]/0.1);
lbajardsilogic@233 48 m_curve.push_back(QPoint(i, m));
lbajardsilogic@229 49 }
lbajardsilogic@229 50 refreshPixmap();
lbajardsilogic@229 51 }
lbajardsilogic@229 52
benoitrigolleau@211 53 void Plotter::clearCurve(){
benoitrigolleau@211 54 m_curve.clear();
benoitrigolleau@211 55 refreshPixmap();
benoitrigolleau@211 56 }
benoitrigolleau@211 57
benoitrigolleau@211 58 void Plotter::paintEvent(QPaintEvent *event){
benoitrigolleau@211 59 QStylePainter painter(this);
benoitrigolleau@211 60 painter.drawPixmap(0, 0, m_pixmap);
benoitrigolleau@211 61 }
benoitrigolleau@211 62
benoitrigolleau@211 63 void Plotter::resizeEvent(QResizeEvent *event){
benoitrigolleau@211 64 refreshPixmap();
benoitrigolleau@211 65 }
benoitrigolleau@211 66
benoitrigolleau@211 67 void Plotter::mousePressEvent(QMouseEvent *event){
benoitrigolleau@211 68 QRect rect(m_margin, m_margin,
benoitrigolleau@239 69 m_signalWidth , m_signalHeight );
benoitrigolleau@211 70
lbajardsilogic@235 71 if (m_enableDrawCurve)
lbajardsilogic@235 72 {
lbajardsilogic@235 73 if (event->button() == Qt::LeftButton) {
lbajardsilogic@235 74 if (rect.contains(event->pos())) {
lbajardsilogic@235 75 m_curveMaskActive = true;
lbajardsilogic@235 76 int x = event->pos().x()- m_margin;
lbajardsilogic@235 77 int y = event->pos().y()- m_margin;
lbajardsilogic@235 78 m_curveMask[x] = y;
lbajardsilogic@235 79 m_lastPoint.setX(x);
lbajardsilogic@235 80 m_lastPoint.setY(y);
lbajardsilogic@235 81 setCursor(Qt::CrossCursor);
lbajardsilogic@235 82 refreshPixmap();
lbajardsilogic@235 83 }
lbajardsilogic@235 84 }
lbajardsilogic@235 85 }
benoitrigolleau@211 86 }
benoitrigolleau@211 87
benoitrigolleau@211 88 void Plotter::mouseMoveEvent(QMouseEvent *event){
benoitrigolleau@211 89 QRect rect(m_margin, m_margin,
benoitrigolleau@239 90 m_signalWidth , m_signalHeight);
benoitrigolleau@211 91
lbajardsilogic@235 92 if (m_enableDrawCurve)
lbajardsilogic@235 93 {
lbajardsilogic@235 94 if(m_curveMaskActive && rect.contains(event->pos())){
lbajardsilogic@235 95 int x = event->pos().x() - m_margin;
lbajardsilogic@235 96 int y = event->pos().y() - m_margin;
lbajardsilogic@235 97 if(y>m_signalHeight-1)
lbajardsilogic@235 98 y= m_signalHeight-1;
lbajardsilogic@235 99 if(x>m_signalWidth-1)
lbajardsilogic@235 100 y= m_signalWidth-1;
lbajardsilogic@235 101 int xlast = m_lastPoint.x();
lbajardsilogic@235 102 int ylast = m_lastPoint.y();
benoitrigolleau@211 103
lbajardsilogic@235 104 //regul mask curve
lbajardsilogic@235 105 int minx, maxx, miny, maxy;
lbajardsilogic@235 106 if(x>xlast){
lbajardsilogic@235 107 minx = xlast;
lbajardsilogic@235 108 maxx = x;
lbajardsilogic@235 109 }else{
lbajardsilogic@235 110 minx = x;
lbajardsilogic@235 111 maxx = xlast;
lbajardsilogic@235 112 }
lbajardsilogic@235 113 if(y>ylast){
lbajardsilogic@235 114 miny = ylast;
lbajardsilogic@235 115 maxy = y;
lbajardsilogic@235 116 }else{
lbajardsilogic@235 117 miny = y;
lbajardsilogic@235 118 maxy = ylast;
lbajardsilogic@235 119 }
benoitrigolleau@211 120
lbajardsilogic@235 121 if((maxx - minx)>1){
lbajardsilogic@235 122 double incr = (double)(maxy - miny)/(double)(maxx - minx);
lbajardsilogic@235 123 if(x>xlast){
lbajardsilogic@235 124 for (int i = xlast + 1 ; i < x ; i++){
lbajardsilogic@235 125 if(ylast > y){
lbajardsilogic@235 126 m_curveMask[i] = ylast - (i-xlast)*incr;
lbajardsilogic@235 127 }else{
lbajardsilogic@235 128 m_curveMask[i] = ylast + (i-xlast)*incr;
lbajardsilogic@235 129 }
benoitrigolleau@211 130 }
lbajardsilogic@235 131 }else{
lbajardsilogic@235 132 for (int i = xlast - 1 ; i > x ; i--){
lbajardsilogic@235 133 if(ylast > y){
lbajardsilogic@235 134 m_curveMask[i] = ylast + (i-xlast)*incr;
lbajardsilogic@235 135 }else{
lbajardsilogic@235 136 m_curveMask[i] = ylast - (i-xlast)*incr;
lbajardsilogic@235 137 }
benoitrigolleau@211 138 }
benoitrigolleau@211 139 }
benoitrigolleau@211 140 }
lbajardsilogic@235 141 m_curveMask[x] = y;
lbajardsilogic@235 142 m_lastPoint.setX(x);
lbajardsilogic@235 143 m_lastPoint.setY(y);
lbajardsilogic@235 144 refreshPixmap();
benoitrigolleau@240 145 emit filterChanged(m_curveMask);
benoitrigolleau@211 146 }
benoitrigolleau@211 147 }
benoitrigolleau@211 148 }
benoitrigolleau@211 149
benoitrigolleau@211 150 void Plotter::mouseReleaseEvent(QMouseEvent *event){
lbajardsilogic@235 151 if (m_enableDrawCurve)
lbajardsilogic@235 152 {
lbajardsilogic@235 153 if ((event->button() == Qt::LeftButton) && m_curveMaskActive) {
lbajardsilogic@235 154 m_curveMaskActive = false;
lbajardsilogic@235 155 unsetCursor();
benoitrigolleau@240 156 //emit filterChanged(m_curveMask);
lbajardsilogic@235 157 }
lbajardsilogic@235 158 }
benoitrigolleau@211 159 }
benoitrigolleau@211 160
benoitrigolleau@211 161 void Plotter::drawGrid(QPainter *painter){
benoitrigolleau@211 162 QPixmap pm(":icons/grid.png");
benoitrigolleau@240 163 painter->setPen(Qt::white);
benoitrigolleau@211 164 painter->drawPixmap(0,0,pm);
benoitrigolleau@240 165
benoitrigolleau@240 166
benoitrigolleau@240 167 /**VLines **************/
benoitrigolleau@240 168
benoitrigolleau@240 169 // middle line
benoitrigolleau@240 170 painter->drawLine(m_signalWidth/2+m_margin, m_margin, m_signalWidth/2+m_margin , m_signalHeight + m_margin);
benoitrigolleau@240 171 //quater lines
benoitrigolleau@240 172 painter->drawLine(m_signalWidth/4+m_margin, m_margin, m_signalWidth/4+m_margin , m_signalHeight + m_margin);
benoitrigolleau@240 173 painter->drawLine(3*m_signalWidth/4+m_margin, m_margin, 3*m_signalWidth/4+m_margin , m_signalHeight + m_margin);
benoitrigolleau@240 174
benoitrigolleau@240 175 // border lines
benoitrigolleau@240 176 painter->drawLine(m_margin, m_margin, m_margin , m_signalHeight + m_margin);
benoitrigolleau@240 177 painter->drawLine(m_signalWidth+m_margin, m_margin, m_signalWidth+m_margin , m_signalHeight + m_margin);
benoitrigolleau@240 178
benoitrigolleau@240 179 /** HLines *************/
benoitrigolleau@240 180
benoitrigolleau@240 181
benoitrigolleau@240 182 /** Labels *************/
benoitrigolleau@240 183 painter->setPen(Qt::darkGray);
benoitrigolleau@240 184 painter->drawText(0, m_signalHeight+2*m_margin+10, "10Hz");
benoitrigolleau@240 185 painter->drawText(m_signalWidth/4 -10, m_signalHeight+2*m_margin+10, "100Hz");
benoitrigolleau@240 186 painter->drawText(m_signalWidth/2 -10, m_signalHeight+2*m_margin+10, "1000Hz");
benoitrigolleau@240 187 painter->drawText(3*m_signalWidth/4 -10, m_signalHeight+2*m_margin+10, "10000Hz");
benoitrigolleau@240 188 painter->drawText(m_signalWidth -22, m_signalHeight+2*m_margin+10, "22KHz");
benoitrigolleau@240 189
benoitrigolleau@240 190
benoitrigolleau@211 191 }
benoitrigolleau@211 192
benoitrigolleau@211 193 void Plotter::drawCurve(QPainter *painter){
benoitrigolleau@231 194 //painter->setRenderHint (QPainter::Antialiasing, true );
benoitrigolleau@211 195 QPolygonF polyline(m_signalWidth);
benoitrigolleau@231 196
benoitrigolleau@211 197 for(int i = 0 ; i < m_curve.count() ; i++){
lbajardsilogic@233 198 int m = m_curve.at(i).y(); // Calculates pixel coordinate and Plots FFT (in green)
benoitrigolleau@231 199 if (m>m_signalHeight){m = m_signalHeight;}
benoitrigolleau@231 200 if (m<0){m = 0;}
benoitrigolleau@231 201 int y= m_signalHeight - m;
benoitrigolleau@231 202 polyline[i] = QPoint(m_curve.at(i).x() + m_margin, /*m_curve.at(i).y()*/y + m_margin);
benoitrigolleau@211 203 }
benoitrigolleau@231 204
benoitrigolleau@211 205 painter->setPen(Qt::green);
benoitrigolleau@211 206 painter->drawPolyline(polyline);
benoitrigolleau@239 207
benoitrigolleau@211 208 }
benoitrigolleau@211 209
benoitrigolleau@211 210 void Plotter::drawMaskCurve(QPainter *painter){
benoitrigolleau@211 211
benoitrigolleau@220 212 painter->setRenderHint (QPainter::Antialiasing, true );
benoitrigolleau@220 213
benoitrigolleau@211 214 QPolygonF polyline(m_signalWidth);
benoitrigolleau@211 215
benoitrigolleau@211 216 for(int i = 0 ; i < m_signalWidth ; i++){
benoitrigolleau@211 217 polyline[i] = QPoint(i+m_margin, m_curveMask[i]+m_margin);
benoitrigolleau@211 218 }
benoitrigolleau@211 219 painter->setPen(Qt::red);
benoitrigolleau@211 220 painter->drawPolyline(polyline);
benoitrigolleau@211 221 }
benoitrigolleau@211 222
benoitrigolleau@211 223 void Plotter::refreshPixmap(){
benoitrigolleau@211 224 m_pixmap = QPixmap(size());
benoitrigolleau@211 225 m_pixmap.fill(this, 0, 0);
benoitrigolleau@211 226
benoitrigolleau@211 227 QPainter painter(&m_pixmap);
benoitrigolleau@211 228 painter.initFrom(this);
benoitrigolleau@211 229 drawGrid(&painter);
benoitrigolleau@211 230 drawCurve(&painter);
benoitrigolleau@211 231 drawMaskCurve(&painter);
benoitrigolleau@211 232 update();
benoitrigolleau@211 233 }
benoitrigolleau@211 234
benoitrigolleau@211 235 void Plotter::setMargin(int margin){
benoitrigolleau@211 236 m_margin = margin;
lbajardsilogic@232 237 }
lbajardsilogic@232 238
lbajardsilogic@232 239 void Plotter::setFilter(float* filter)
lbajardsilogic@232 240 {
benoitrigolleau@240 241
lbajardsilogic@232 242 m_curveMask.clear();
lbajardsilogic@232 243 for (int i=0; i<m_signalWidth; i++)
lbajardsilogic@232 244 {
lbajardsilogic@233 245 m_curveMask.push_back((int) (m_signalHeight - filter[i]*(m_signalHeight/2-1)));
lbajardsilogic@232 246 }
lbajardsilogic@232 247 refreshPixmap();
lbajardsilogic@235 248 }
lbajardsilogic@235 249
lbajardsilogic@235 250 void Plotter::enableDrawCurve(bool enable)
lbajardsilogic@235 251 {
benoitrigolleau@240 252 if(enable!=m_enableDrawCurve){
benoitrigolleau@240 253 QVector<float> aux = m_curveMask;
benoitrigolleau@240 254 m_curveMask = m_oldCurveMask;
benoitrigolleau@240 255 m_oldCurveMask = aux;
benoitrigolleau@240 256 refreshPixmap();
benoitrigolleau@240 257 if(enable){
benoitrigolleau@240 258 emit filterChanged(m_curveMask);
benoitrigolleau@240 259 }
benoitrigolleau@240 260 }
lbajardsilogic@235 261 m_enableDrawCurve = enable;
benoitrigolleau@211 262 }