The main screen, flowview, and graphing screens are now linked. If you double click a frame on the main window or a graph in flowview or the graphing window the other two windows will update to show that data as well.

This commit is contained in:
Collin Kidder
2015-08-23 15:45:56 -04:00
parent 32c38e2331
commit e1eb1f9ab1
9 changed files with 158 additions and 6 deletions
+15
View File
@@ -398,6 +398,21 @@ void CANFrameModel::insertFrames(const QVector<CANFrame> &newFrames)
if (needFilterRefresh) emit updatedFiltersList();
}
int CANFrameModel::getIndexFromTimeID(int ID, double timestamp)
{
int bestIndex = -1;
uint64_t intTimeStamp = timestamp * 1000000l;
for (int i = 0; i < frames.count(); i++)
{
if ((frames[i].ID == ID))
{
if (frames[i].timestamp <= intTimeStamp) bestIndex = i;
else break; //drop out of loop as soon as we pass the proper timestamp
}
}
return bestIndex;
}
void CANFrameModel::loadFilterFile(QString filename)
{
QFile *inFile = new QFile(filename);
+1
View File
@@ -41,6 +41,7 @@ public:
void recalcOverwrite();
bool needsFilterRefresh();
void insertFrames(const QVector<CANFrame> &newFrames);
int getIndexFromTimeID(int ID, double timestamp);
const QVector<CANFrame> *getListReference() const; //thou shalt not modify these frames externally!
const QVector<CANFrame> *getFilteredListReference() const; //Thus saith the Lord, NO.
const QMap<int, bool> *getFiltersReference() const; //this neither
+1 -1
View File
@@ -1,7 +1,7 @@
#ifndef CONFIG
#define CONFIG
#define VERSION 135
#define VERSION 136
//try to keep this in sync.
//SavvyCAN will complain if you connect a GVRET board with a revision
+54 -1
View File
@@ -67,7 +67,8 @@ FlowViewWindow::FlowViewWindow(const QVector<CANFrame> *frames, QWidget *parent)
connect(ui->spinPlayback, SIGNAL(valueChanged(int)), this, SLOT(changePlaybackSpeed(int)));
connect(ui->cbLoopPlayback, SIGNAL(clicked(bool)), this, SLOT(changeLooping(bool)));
connect(ui->listFrameID, SIGNAL(currentTextChanged(QString)), this, SLOT(changeID(QString)));
connect(playbackTimer, SIGNAL(timeout()), this, SLOT(timerTriggered()));
connect(playbackTimer, SIGNAL(timeout()), this, SLOT(timerTriggered()));
connect(ui->graphView, SIGNAL(plottableDoubleClick(QCPAbstractPlottable*,QMouseEvent*)), this, SLOT(plottableDoubleClick(QCPAbstractPlottable*,QMouseEvent*)));
connect(MainWindow::getReference(), SIGNAL(framesUpdated(int)), this, SLOT(updatedFrames(int)));
@@ -143,6 +144,58 @@ void FlowViewWindow::writeSettings()
}
}
void FlowViewWindow::plottableDoubleClick(QCPAbstractPlottable* plottable, QMouseEvent* event)
{
int id = 0;
//apply transforms to get the X axis value where we double clicked
double coord = plottable->keyAxis()->pixelToCoord(event->localPos().x());
if (frameCache.count() > 0) id = frameCache[0].ID;
if (secondsMode) emit sendCenterTimeID(id, coord);
else emit sendCenterTimeID(id, coord / 1000000.0);
}
void FlowViewWindow::gotCenterTimeID(int32_t ID, double timestamp)
{
if (secondsMode) timestamp *= 1000000.0; //frames always store timestamp in microseconds
qDebug() << "timestamp: " << timestamp;
changeID(QString::number(ID)); //to be sure we're focused on the proper ID
for (int j = 0; j < ui->listFrameID->count(); j++)
{
int thisNum = Utility::ParseStringToNum(ui->listFrameID->item(j)->text());
if (thisNum == ID)
{
ui->listFrameID->setCurrentRow(j);
break;
}
}
int bestIdx = -1;
for (int i = 0; i < frameCache.count(); i++)
{
if (frameCache[i].timestamp > timestamp)
{
bestIdx = i - 1;
break;
}
}
qDebug() << "Best index " << bestIdx;
if (bestIdx > -1)
{
currentPosition = bestIdx;
if (ui->cbAutoRef->isChecked())
{
memcpy(refBytes, currBytes, 8);
}
memcpy(currBytes, frameCache.at(currentPosition).data, 8);
updateDataView();
}
}
void FlowViewWindow::contextMenuRequestFlow(QPoint pos)
{
QMenu *menu = new QMenu(this);
+6
View File
@@ -2,6 +2,7 @@
#define FLOWVIEWWINDOW_H
#include <QDialog>
#include "qcustomplot.h"
#include "can_structs.h"
namespace Ui {
@@ -33,6 +34,11 @@ private slots:
void contextMenuRequestGraph(QPoint pos);
void saveFileFlow();
void saveFileGraph();
void plottableDoubleClick(QCPAbstractPlottable* plottable, QMouseEvent* event);
void gotCenterTimeID(int32_t ID, double timestamp);
signals:
void sendCenterTimeID(int32_t ID, double timestamp);
private:
Ui::FlowViewWindow *ui;
+33 -1
View File
@@ -45,6 +45,7 @@ GraphingWindow::GraphingWindow(DBCHandler *handler, const QVector<CANFrame> *fra
connect(ui->graphingView, SIGNAL(selectionChangedByUser()), this, SLOT(selectionChanged()));
//connect up the mouse controls
connect(ui->graphingView, SIGNAL(mousePress(QMouseEvent*)), this, SLOT(mousePress()));
connect(ui->graphingView, SIGNAL(plottableDoubleClick(QCPAbstractPlottable*,QMouseEvent*)), this, SLOT(plottableDoubleClick(QCPAbstractPlottable*,QMouseEvent*)));
connect(ui->graphingView, SIGNAL(mouseWheel(QWheelEvent*)), this, SLOT(mouseWheel()));
// make bottom and left axes transfer their ranges to top and right axes:
@@ -152,6 +153,32 @@ void GraphingWindow::updatedFrames(int numFrames)
}
}
void GraphingWindow::plottableDoubleClick(QCPAbstractPlottable* plottable, QMouseEvent* event)
{
int id = 0;
//apply transforms to get the X axis value where we double clicked
double coord = plottable->keyAxis()->pixelToCoord(event->localPos().x());
id = plottable->property("id").toInt();
if (secondsMode) emit sendCenterTimeID(id, coord);
else emit sendCenterTimeID(id, coord / 1000000.0);
}
void GraphingWindow::gotCenterTimeID(int32_t ID, double timestamp)
{
//its problematic to try to highlight a graph since we get the ID
//and timestamp not the signal in question so there is no real way
//to know which graph. But, if that changes here is a stub
//for (int i = 0; i < graphParams.count(); i++)
//{
//}
QCPRange range = ui->graphingView->xAxis->range();
double offset = range.size() / 2.0;
if (!secondsMode) timestamp *= 1000000.0; //timestamp is always in seconds when being passed so convert if necessary
ui->graphingView->xAxis->setRange(timestamp - offset, timestamp + offset);
ui->graphingView->replot();
}
void GraphingWindow::titleDoubleClick(QMouseEvent* event, QCPPlotTitle* title)
{
Q_UNUSED(event)
@@ -802,6 +829,9 @@ void GraphingWindow::createGraph(GraphParams &params, bool createGraphParam)
}
}
params.xbias = 0;
/*
for (int ct = 0; ct < params.x.count(); ct++)
{
params.x[ct] -= xminval;
@@ -809,9 +839,10 @@ void GraphingWindow::createGraph(GraphParams &params, bool createGraphParam)
params.xbias = xminval;
xmaxval -= xminval;
xminval = 0;
*/
ui->graphingView->addGraph();
params.ref = ui->graphingView->graph();
params.ref = ui->graphingView->graph();
if (createGraphParam)
{
graphParams.append(params);
@@ -826,6 +857,7 @@ void GraphingWindow::createGraph(GraphParams &params, bool createGraphParam)
if ((params.endByte != -1) && (params.endByte != params.startByte)) params.graphName += "-" + QString::number(params.endByte);
}
ui->graphingView->graph()->setName(params.graphName);
ui->graphingView->graph()->setProperty("id", params.ID);
ui->graphingView->graph()->setData(refParam->x,refParam->y);
ui->graphingView->graph()->setLineStyle(QCPGraph::lsLine); //connect points with lines
+5
View File
@@ -42,6 +42,7 @@ private slots:
void titleDoubleClick(QMouseEvent *event, QCPPlotTitle *title);
void axisLabelDoubleClick(QCPAxis* axis, QCPAxis::SelectablePart part);
void legendDoubleClick(QCPLegend* legend, QCPAbstractLegendItem* item);
void plottableDoubleClick(QCPAbstractPlottable* plottable,QMouseEvent* event);
void selectionChanged();
void mousePress();
void mouseWheel();
@@ -57,6 +58,10 @@ private slots:
void appendToGraph(GraphParams &params, CANFrame &frame);
void editSelectedGraph();
void updatedFrames(int);
void gotCenterTimeID(int32_t ID, double timestamp);
signals:
void sendCenterTimeID(int32_t ID, double timestamp);
private:
Ui::GraphingWindow *ui;
+39 -2
View File
@@ -126,6 +126,7 @@ MainWindow::MainWindow(QWidget *parent) :
connect(ui->actionLoad_DBC_File, SIGNAL(triggered(bool)), this, SLOT(handleLoadDBC()));
connect(ui->actionSave_DBC_File, SIGNAL(triggered(bool)), this, SLOT(handleSaveDBC()));
connect(ui->canFramesView, SIGNAL(clicked(QModelIndex)), this, SLOT(gridClicked(QModelIndex)));
connect(ui->canFramesView, SIGNAL(doubleClicked(QModelIndex)), this, SLOT(gridDoubleClicked(QModelIndex)));
connect(ui->cbInterpret, SIGNAL(toggled(bool)), this, SLOT(interpretToggled(bool)));
connect(ui->cbOverwrite, SIGNAL(toggled(bool)), this, SLOT(overwriteToggled(bool)));
connect(ui->actionEdit_Messages_Signals, SIGNAL(triggered(bool)), this, SLOT(showDBCEditor()));
@@ -263,7 +264,8 @@ void MainWindow::readUpdateableSettings()
useHex = settings.value("Main/UseHex", true).toBool();
model->setHexMode(useHex);
Utility::decimalMode = !useHex;
model->setSecondsMode(settings.value("Main/TimeSeconds", false).toBool());
secondsMode = settings.value("Main/TimeSeconds", false).toBool();
model->setSecondsMode(secondsMode);
useFiltered = settings.value("Main/UseFiltered", false).toBool();
}
@@ -289,6 +291,13 @@ void MainWindow::gridClicked(QModelIndex idx)
}
}
void MainWindow::gridDoubleClicked(QModelIndex idx)
{
//grab ID and timestamp and send them away
CANFrame frame = model->getListReference()->at(idx.row());
emit sendCenterTimeID(frame.ID, frame.timestamp / 1000000.0);
}
void MainWindow::interpretToggled(bool state)
{
model->setInterpetMode(state);
@@ -383,6 +392,17 @@ void MainWindow::addFrameToDisplay(CANFrame &frame, bool autoRefresh = false)
}
}
//A sub-window is sending us a center on timestamp and ID signal
//try to find the relevant frame in the list and focus on it.
void MainWindow::gotCenterTimeID(int32_t ID, double timestamp)
{
int idx = model->getIndexFromTimeID(ID, timestamp);
if (idx > -1)
{
ui->canFramesView->selectRow(idx);
}
}
void MainWindow::clearFrames()
{
ui->canFramesView->scrollToTop();
@@ -397,6 +417,7 @@ void MainWindow::clearFrames()
void MainWindow::normalizeTiming()
{
model->normalizeTiming();
emit framesUpdated(-2); //claim an all new set of frames because every frame was updated.
}
void MainWindow::changeBaudRates()
@@ -900,6 +921,14 @@ void MainWindow::showGraphingWindow()
{
if (!graphingWindow) {
graphingWindow = new GraphingWindow(dbcHandler, model->getListReference());
connect(graphingWindow, SIGNAL(sendCenterTimeID(int32_t,double)), this, SLOT(gotCenterTimeID(int32_t,double)));
connect(this, SIGNAL(sendCenterTimeID(int32_t,double)), graphingWindow, SLOT(gotCenterTimeID(int32_t,double)));
}
if (flowViewWindow) //connect the two external windows together
{
connect(graphingWindow, SIGNAL(sendCenterTimeID(int32_t,double)), flowViewWindow, SLOT(gotCenterTimeID(int32_t,double)));
connect(flowViewWindow, SIGNAL(sendCenterTimeID(int32_t,double)), graphingWindow, SLOT(gotCenterTimeID(int32_t,double)));
}
graphingWindow->show();
}
@@ -987,11 +1016,19 @@ void MainWindow::showFlowViewWindow()
flowViewWindow = new FlowViewWindow(model->getListReference());
else
flowViewWindow = new FlowViewWindow(model->getFilteredListReference());
connect(flowViewWindow, SIGNAL(sendCenterTimeID(int32_t,double)), this, SLOT(gotCenterTimeID(int32_t,double)));
connect(this, SIGNAL(sendCenterTimeID(int32_t,double)), flowViewWindow, SLOT(gotCenterTimeID(int32_t,double)));
}
if (graphingWindow)
{
connect(graphingWindow, SIGNAL(sendCenterTimeID(int32_t,double)), flowViewWindow, SLOT(gotCenterTimeID(int32_t,double)));
connect(flowViewWindow, SIGNAL(sendCenterTimeID(int32_t,double)), graphingWindow, SLOT(gotCenterTimeID(int32_t,double)));
}
flowViewWindow->show();
}
//this one always gets the unfiltered list intentionally.
void MainWindow::showDBCEditor()
{
+4 -1
View File
@@ -59,6 +59,7 @@ private slots:
void gotDeviceInfo(int, int);
void connectionSucceeded(int, int);
void gridClicked(QModelIndex);
void gridDoubleClicked(QModelIndex);
void interpretToggled(bool);
void overwriteToggled(bool);
void showDBCEditor();
@@ -72,7 +73,7 @@ private slots:
public slots:
void gotFrames(int, int);
void updateSettings();
void gotCenterTimeID(int32_t ID, double timestamp);
signals:
void sendSerialPort(QSerialPortInfo *port);
@@ -85,6 +86,7 @@ signals:
//-1 = frames cleared, -2 = a new file has been loaded (so all frames are different), otherwise # of new frames
void framesUpdated(int numFrames); //something has updated the frame list
void settingsUpdated();
void sendCenterTimeID(int32_t ID, double timestamp);
private:
Ui::MainWindow *ui;
@@ -100,6 +102,7 @@ private:
bool inhibitFilterUpdate;
bool useHex;
bool allowCapture;
bool secondsMode;
bool bDirty; //have frames been added or subtracted since the last save/load?
bool useFiltered; //should sub-windows use the unfiltered or filtered frames list?