📄 show.cpp
字号:
/*************************************************************************** show.cpp - Implements QwtPlot ------------------- begin : 2002 authors : Linus Gasser emails : linus.gasser@epfl.ch***************************************************************************//*************************************************************************** Changes ------- date - name - description 02-12-19 - ineiti - begin 04/03/25 - ineiti - integrated zoom **************************************************************************//*************************************************************************** * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 2 of the License, or * * (at your option) any later version. * * * ***************************************************************************//** * @short displays the output of one block graphically */#include <qapplication.h>#include <qwt_curve.h>#include <qwt_symbol.h>#include <qwt_plot_zoomer.h>#include <stdlib.h>#include <math.h>#include <qevent.h>#include <qtimer.h>#include <qcombobox.h>#include <qlayout.h>#include <qpushbutton.h>#include <qprinter.h>#include <qfiledialog.h>#include <qregexp.h>#include "show.h"#include "defines.h"#include "global.h"// this is the standard C++-way of using cout <<using namespace std;Show::Show( QString name, Block *b, QWidget *p ) : QwtPlot( p ), block( b ), parent( p ){ int length = block->getNumOfSamples(); setTitle( name + ":\n:" + block->getName() ); freeze = 0; isLine = 1; // Insert new curves signal = insertCurve( "signal" ); switch ( block->getType() ){ case SIG_QUAD_SYMBOL_ICS_AD: // Each quad_symbol has 4 symbols in it... length *= 4; case SIG_SYMBOL_COMPLEX: case SIG_SYMBOL_COMPLEX_S32: case SIG_SYMBOL_MMX: case SIG_DOUBLE_COMPLEX: // Usually small signals are preferred to be in absolute mode, // while large signals are fine in complex-mode if ( length < 200 ) { showType = show_abs; } else { showType = show_complex; isLine = 0; } break; default: showType = show_real; break; } scaleX = scaleY = 0.; zoomIn = 0.4; plotZoomer = NULL; // Set curve styles setCurvePen( signal, QPen( red, 2 ) ); adjustCurve(); setCanvasBackground( QColor( lightGray ) ); // vBox->addWidget( this ); // set a timer to refresh the graph updateTimer = new QTimer(); QObject::connect( updateTimer, SIGNAL( timeout() ), this, SLOT( Update() ) ); updateTimer->start( GRAPH_UPDATE_TIMER, FALSE ); QObject::connect( parent , SIGNAL ( destroyed() ), this, SLOT( close() ) );}void Show::AddTypes( QVBoxLayout *vBox, bool dSignal, bool dPlot, bool dFreeze ){ QHBoxLayout *hBox = new QHBoxLayout( vBox ); if ( dFreeze ){ QPushButton *pbFreeze = new QPushButton( "Freeze", parent ); pbFreeze->setToggleButton( true ); connect( pbFreeze, SIGNAL( toggled( bool ) ), SLOT( slotFreeze( bool ) ) ); hBox->addWidget( pbFreeze ); } if ( dSignal ){ // Add the signal-type-box QComboBox *qcbType = new QComboBox( false, parent, "Type:" ); QString choice( "Complex,Real,Imaginary,Absolute,FFT" ); qcbType->insertStringList( QStringList::split( ",", choice ) ); qcbType->setCurrentItem( showType ); connect( qcbType, SIGNAL( activated( int ) ), SLOT( ShowSig( int ) ) ); hBox->addWidget( qcbType ); } if ( dPlot ){ // Add the point,line-box QComboBox *qcbType = new QComboBox( false, parent, "Type:" ); QString choice = QString( "Point,Line" ); qcbType->insertStringList( QStringList::split( ",", choice ) ); qcbType->setCurrentItem( isLine ); connect( qcbType, SIGNAL( activated( int ) ), SLOT( styling( int ) ) ); hBox->addWidget( qcbType ); }}void Show::AddExport( QVBoxLayout *vBox ){ //create and add an hBox for export button QHBoxLayout *hBox = new QHBoxLayout( 1, "plotWindowHorizontalLayout" ); vBox->addLayout( hBox ); // Add the export ps button QPushButton* expPsButton = new QPushButton( "Export to ps", parent, "expPsButton" ); hBox->addWidget( expPsButton ); connect( expPsButton, SIGNAL( clicked() ), SLOT( slotExportPs() ) ); // Add the export matlab button QPushButton* expMatlabButton = new QPushButton( "Export to Matlab", parent, "expMatlabButton" ); hBox->addWidget( expMatlabButton ); connect( expMatlabButton, SIGNAL( clicked() ), SLOT( slotExportML() ) ); // Add the export binary button QPushButton* expBinaryButton = new QPushButton( "Export to Binary", parent, "expBinaryButton" ); hBox->addWidget( expBinaryButton ); connect( expBinaryButton, SIGNAL( clicked() ), SLOT( slotExportBin() ) );}Show::~Show() {}/** * Change the actual block */void Show::newBlock( QString name, Block *b ) { block = b; setTitle( name + "::" + block->getName() ); adjustCurve();}/** * depending on the block, we have different curve-styles. If the block * is made out of complex values, we chose a Q/I display, else it's a * f(x)=y style display */void Show::adjustCurve() { switch ( block->getType() ) { case SIG_SYMBOL_COMPLEX: case SIG_SYMBOL_COMPLEX_S32: case SIG_SYMBOL_MMX: case SIG_DOUBLE_COMPLEX: case SIG_QUAD_SYMBOL_ICS_AD: dComplex = true; break; default: dComplex = false; break; } if ( dComplex && !showType ) { setCurveStyle( signal, QwtCurve::NoCurve ); setCurveSymbol( signal, QwtSymbol( QwtSymbol::Cross, QBrush( red ), QPen( red ), QSize( 8, 8 ) ) ); } else { setCurveStyle( signal, QwtCurve::Lines ); setCurveSymbol( signal, QwtSymbol( QwtSymbol::Rect, QBrush( red ), QPen( red ), QSize( 1, 1 ) ) ); }}/** * Sometimes it's useful to have the real, imag or absolute values of a * complex-signal, so call this function with * (0,1,2,3) for (complex,real,imag,abs) respectivley */void Show::ShowSig( int t ) { showType = (enum showType_e)t; adjustCurve();}#ifndef fmax#define fmax(a,b) (a)>(b)?(a):(b)#define fmin(a,b) (a)<(b)?(a):(b)#endif#define MAX_LENGTH 1000/** * Read out the data and plot it */void Show::Update() { double * x, *y; int i, len = 0; double min_x = 0., max_x = 0., abs_x, min_y = 0., max_y = 0., abs_y; if ( freeze == 2 ) { return ; } else if ( !freeze ){ // If we don't freeze, show only the MAX_LENGTH last samples if ( showType != show_fft ) { len = MAX_LENGTH; } } else { // Make sure we only show once the whole graph, because this might // be quite huge and take a loooong time... setCanvasBackground( QColor( white ) ); freeze = 2; } len = block->Data( &x, &y, len, showType ); if ( !len ){ return; } // Search for the maximum for ( i = 0; i < len; i++ ) { max_x = fmax( max_x, x[ i ] ); min_x = fmin( min_x, x[ i ] ); max_y = fmax( max_y, y[ i ] ); min_y = fmin( min_y, y[ i ] ); // cout << x[i] << ", " << y[i] << endl; } abs_x = fmax( max_x, -min_x ); abs_y = fmax( max_y, -min_y ); // And do some slow zooming-in if ( abs_x > scaleX ) { scaleX = abs_x; } else { scaleX -= ( scaleX - abs_x ) * zoomIn; } if ( abs_y > scaleY ) { scaleY = abs_y; } else { scaleY -= ( scaleY - abs_y ) * zoomIn; } if ( dComplex ) { if ( showType == show_fft ){ len = min( len / 2, 4096 ); } shapeSignal( x, y, abs_x, abs_y, scaleX, scaleY, len ); } else if ( showType == show_abs || showType == show_fft ){ for ( i=0; i<len; i++ ){ x[i] = 0; } shapeSignal( x, y, abs_x, abs_y, scaleX, scaleY, len ); } else { setAxisAutoScale( yLeft ); setAxisAutoScale( xBottom ); } setCurveData( signal, x, y, len ); replot(); free( x ); free( y ); if ( freeze == 2 ){ // In freezing state, we can zoom in and out plotZoomer = new QwtPlotZoomer( canvas() );
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -