Merge pull request #2328 from opentx/griebd/log_viewer_enhancement_2267_next
log viewer enhancement, now for next
This commit is contained in:
+251
-134
@@ -46,19 +46,35 @@ logsDialog::logsDialog(QWidget *parent) :
|
||||
ui->customPlot->setInteractions(QCP::iRangeDrag | QCP::iRangeZoom |
|
||||
QCP::iSelectAxes | QCP::iSelectLegend | QCP::iSelectPlottables);
|
||||
|
||||
ui->customPlot->xAxis->setLabel(tr("Time (hh:mm:ss)"));
|
||||
ui->customPlot->xAxis->setTickLabelType(QCPAxis::ltDateTime);
|
||||
ui->customPlot->xAxis->setDateTimeFormat("hh:mm:ss");
|
||||
axisRect = ui->customPlot->axisRect();
|
||||
axisRect->axis(QCPAxis::atBottom)->setLabel(tr("Time (hh:mm:ss)"));
|
||||
axisRect->axis(QCPAxis::atBottom)->setTickLabelType(QCPAxis::ltDateTime);
|
||||
axisRect->axis(QCPAxis::atBottom)->setDateTimeFormat("hh:mm:ss");
|
||||
QDateTime now = QDateTime::currentDateTime();
|
||||
ui->customPlot->xAxis->setRange(now.addSecs(-60*60*2).toTime_t(),
|
||||
axisRect->axis(QCPAxis::atBottom)->setRange(now.addSecs(-60*60*2).toTime_t(),
|
||||
now.toTime_t());
|
||||
|
||||
ui->customPlot->yAxis->setTickLabels(false);
|
||||
axisRect->axis(QCPAxis::atLeft)->setTickLabels(false);
|
||||
|
||||
axisRect->addAxis(QCPAxis::atLeft);
|
||||
axisRect->addAxis(QCPAxis::atRight);
|
||||
axisRect->axis(QCPAxis::atLeft, 1)->setVisible(false);
|
||||
axisRect->axis(QCPAxis::atRight, 1)->setVisible(false);
|
||||
|
||||
QFont legendFont = font();
|
||||
legendFont.setPointSize(10);
|
||||
ui->customPlot->legend->setFont(legendFont);
|
||||
ui->customPlot->legend->setSelectedFont(legendFont);
|
||||
axisRect->insetLayout()->setInsetAlignment(0, Qt::AlignTop | Qt::AlignLeft);
|
||||
|
||||
rightLegend = new QCPLegend;
|
||||
axisRect->insetLayout()->addElement(rightLegend, Qt::AlignTop | Qt::AlignRight);
|
||||
rightLegend->setLayer("legend");
|
||||
rightLegend->setFont(legendFont);
|
||||
rightLegend->setSelectedFont(legendFont);
|
||||
rightLegend->setVisible(false);
|
||||
|
||||
ui->customPlot->setAutoAddPlottableToLegend(false);
|
||||
|
||||
QString Path=g.gePath();
|
||||
if (Path.isEmpty() || !QFile(Path).exists()) {
|
||||
@@ -72,7 +88,7 @@ logsDialog::logsDialog(QWidget *parent) :
|
||||
connect(ui->customPlot, SIGNAL(mouseWheel(QWheelEvent*)), this, SLOT(mouseWheel()));
|
||||
|
||||
// make left axes transfer its range to right axes:
|
||||
connect(ui->customPlot->yAxis, SIGNAL(rangeChanged(QCPRange)), this, SLOT(setRangeyAxis2(QCPRange)));
|
||||
connect(axisRect->axis(QCPAxis::atLeft), SIGNAL(rangeChanged(QCPRange)), this, SLOT(yAxisChangeRanges(QCPRange)));
|
||||
|
||||
// connect some interaction slots:
|
||||
connect(ui->customPlot, SIGNAL(titleDoubleClick(QMouseEvent*, QCPPlotTitle*)), this, SLOT(titleDoubleClick(QMouseEvent*, QCPPlotTitle*)));
|
||||
@@ -151,24 +167,43 @@ void logsDialog::selectionChanged()
|
||||
if (plotLock) return;
|
||||
|
||||
// handle bottom axis and tick labels as one selectable object:
|
||||
if (ui->customPlot->xAxis->selectedParts().testFlag(QCPAxis::spAxis) ||
|
||||
ui->customPlot->xAxis->selectedParts().testFlag(QCPAxis::spTickLabels))
|
||||
if (axisRect->axis(QCPAxis::atBottom)->selectedParts().testFlag(QCPAxis::spAxis) ||
|
||||
axisRect->axis(QCPAxis::atBottom)->selectedParts().testFlag(QCPAxis::spTickLabels))
|
||||
{
|
||||
ui->customPlot->xAxis->setSelectedParts(QCPAxis::spAxis |
|
||||
axisRect->axis(QCPAxis::atBottom)->setSelectedParts(QCPAxis::spAxis |
|
||||
QCPAxis::spTickLabels);
|
||||
}
|
||||
// make left and right axes be selected synchronously,
|
||||
// and handle axis and tick labels as one selectable object:
|
||||
if (ui->customPlot->yAxis->selectedParts().testFlag(QCPAxis::spAxis) ||
|
||||
ui->customPlot->yAxis->selectedParts().testFlag(QCPAxis::spTickLabels) ||
|
||||
ui->customPlot->yAxis2->selectedParts().testFlag(QCPAxis::spAxis) ||
|
||||
ui->customPlot->yAxis2->selectedParts().testFlag(QCPAxis::spTickLabels))
|
||||
{
|
||||
ui->customPlot->yAxis->setSelectedParts(QCPAxis::spAxis |
|
||||
if (axisRect->axis(QCPAxis::atLeft)->selectedParts().testFlag(QCPAxis::spAxis) ||
|
||||
axisRect->axis(QCPAxis::atLeft)->selectedParts().testFlag(QCPAxis::spTickLabels) ||
|
||||
(
|
||||
axisRect->axis(QCPAxis::atRight)->visible() &&
|
||||
(axisRect->axis(QCPAxis::atRight)->selectedParts().testFlag(QCPAxis::spAxis) ||
|
||||
axisRect->axis(QCPAxis::atRight)->selectedParts().testFlag(QCPAxis::spTickLabels))
|
||||
) || (
|
||||
axisRect->axis(QCPAxis::atLeft, 1)->visible() &&
|
||||
(axisRect->axis(QCPAxis::atLeft, 1)->selectedParts().testFlag(QCPAxis::spAxis) ||
|
||||
axisRect->axis(QCPAxis::atLeft, 1)->selectedParts().testFlag(QCPAxis::spTickLabels))
|
||||
) || (
|
||||
axisRect->axis(QCPAxis::atRight)->visible() &&
|
||||
(axisRect->axis(QCPAxis::atRight, 1)->selectedParts().testFlag(QCPAxis::spAxis) ||
|
||||
axisRect->axis(QCPAxis::atRight, 1)->selectedParts().testFlag(QCPAxis::spTickLabels))
|
||||
)
|
||||
) {
|
||||
axisRect->axis(QCPAxis::atLeft)->setSelectedParts(QCPAxis::spAxis |
|
||||
QCPAxis::spTickLabels);
|
||||
if (hasyAxis2) {
|
||||
ui->customPlot->yAxis2->setSelectedParts(QCPAxis::spAxis |
|
||||
if (axisRect->axis(QCPAxis::atRight)->visible()) {
|
||||
axisRect->axis(QCPAxis::atRight)->setSelectedParts(QCPAxis::spAxis |
|
||||
QCPAxis::spTickLabels);
|
||||
if (axisRect->axis(QCPAxis::atLeft, 1)->visible()) {
|
||||
axisRect->axis(QCPAxis::atLeft, 1)->setSelectedParts(QCPAxis::spAxis |
|
||||
QCPAxis::spTickLabels);
|
||||
if (axisRect->axis(QCPAxis::atRight, 1)->visible()) {
|
||||
axisRect->axis(QCPAxis::atRight, 1)->setSelectedParts(QCPAxis::spAxis |
|
||||
QCPAxis::spTickLabels);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -177,6 +212,7 @@ void logsDialog::selectionChanged()
|
||||
{
|
||||
QCPGraph *graph = ui->customPlot->graph(i);
|
||||
QCPPlottableLegendItem *item = ui->customPlot->legend->itemWithPlottable(graph);
|
||||
if (item == NULL) item = rightLegend->itemWithPlottable(graph);
|
||||
if (item->selected() || graph->selected())
|
||||
{
|
||||
item->setSelected(true);
|
||||
@@ -339,11 +375,11 @@ void logsDialog::on_mapsButton_clicked()
|
||||
outputStream << "\t\t\t\t\t\t</SchemaData>\n\t\t\t\t\t</ExtendedData>\n\t\t\t\t</gx:Track>\n\t\t\t</Placemark>\n\t\t</Folder>\n\t</Document>\n</kml>";
|
||||
geFile.close();
|
||||
QStringList parameters;
|
||||
#ifdef __APPLE__
|
||||
#ifdef __APPLE__
|
||||
parameters << "-a";
|
||||
parameters << gePath;
|
||||
gePath = "/usr/bin/open";
|
||||
#endif
|
||||
#endif
|
||||
parameters << geFilename;
|
||||
QProcess *process = new QProcess(this);
|
||||
process->start(gePath, parameters);
|
||||
@@ -351,18 +387,17 @@ void logsDialog::on_mapsButton_clicked()
|
||||
ui->logTable->setDisabled(false);
|
||||
}
|
||||
|
||||
|
||||
void logsDialog::mousePress()
|
||||
{
|
||||
// if an axis is selected, only allow the direction of that axis to be dragged
|
||||
// if no axis is selected, both directions may be dragged
|
||||
|
||||
if (ui->customPlot->xAxis->selectedParts().testFlag(QCPAxis::spAxis))
|
||||
ui->customPlot->axisRect()->setRangeDrag(ui->customPlot->xAxis->orientation());
|
||||
else if (ui->customPlot->yAxis->selectedParts().testFlag(QCPAxis::spAxis))
|
||||
ui->customPlot->axisRect()->setRangeDrag(ui->customPlot->yAxis->orientation());
|
||||
if (axisRect->axis(QCPAxis::atBottom)->selectedParts().testFlag(QCPAxis::spAxis))
|
||||
axisRect->setRangeDrag(axisRect->axis(QCPAxis::atBottom)->orientation());
|
||||
else if (axisRect->axis(QCPAxis::atLeft)->selectedParts().testFlag(QCPAxis::spAxis))
|
||||
axisRect->setRangeDrag(axisRect->axis(QCPAxis::atLeft)->orientation());
|
||||
else
|
||||
ui->customPlot->axisRect()->setRangeDrag(Qt::Horizontal | Qt::Vertical);
|
||||
axisRect->setRangeDrag(Qt::Horizontal | Qt::Vertical);
|
||||
}
|
||||
|
||||
void logsDialog::mouseWheel()
|
||||
@@ -377,18 +412,9 @@ void logsDialog::mouseWheel()
|
||||
orientation|=Qt::Vertical;
|
||||
}
|
||||
if (orientation) {
|
||||
ui->customPlot->axisRect()->setRangeZoom((Qt::Orientation)orientation);
|
||||
axisRect->setRangeZoom((Qt::Orientation)orientation);
|
||||
} else {
|
||||
ui->customPlot->axisRect()->setRangeZoom(Qt::Horizontal|Qt::Vertical);
|
||||
}
|
||||
}
|
||||
|
||||
void logsDialog::removeSelectedGraph()
|
||||
{
|
||||
if (ui->customPlot->selectedGraphs().size() > 0)
|
||||
{
|
||||
ui->customPlot->removeGraph(ui->customPlot->selectedGraphs().first());
|
||||
ui->customPlot->replot();
|
||||
axisRect->setRangeZoom(Qt::Horizontal|Qt::Vertical);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -396,8 +422,17 @@ void logsDialog::removeAllGraphs()
|
||||
{
|
||||
ui->customPlot->clearGraphs();
|
||||
ui->customPlot->legend->setVisible(false);
|
||||
ui->customPlot->yAxis2->setVisible(false);
|
||||
ui->customPlot->yAxis->setTickLabels(false);
|
||||
rightLegend->clearItems();
|
||||
rightLegend->setVisible(false);
|
||||
axisRect->axis(QCPAxis::atRight)->setSelectedParts(QCPAxis::spNone);
|
||||
axisRect->axis(QCPAxis::atRight)->setVisible(false);
|
||||
axisRect->axis(QCPAxis::atLeft)->setSelectedParts(QCPAxis::spNone);
|
||||
axisRect->axis(QCPAxis::atLeft)->setTickLabels(false);
|
||||
axisRect->axis(QCPAxis::atLeft, 1)->setVisible(false);
|
||||
axisRect->axis(QCPAxis::atLeft, 1)->setSelectedParts(QCPAxis::spNone);
|
||||
axisRect->axis(QCPAxis::atRight, 1)->setVisible(false);
|
||||
axisRect->axis(QCPAxis::atRight, 1)->setSelectedParts(QCPAxis::spNone);
|
||||
axisRect->axis(QCPAxis::atBottom)->setSelectedParts(QCPAxis::spNone);
|
||||
ui->customPlot->replot();
|
||||
}
|
||||
|
||||
@@ -525,7 +560,6 @@ bool logsDialog::cvsFileParse()
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void logsDialog::on_sessions_CB_currentIndexChanged(int index)
|
||||
{
|
||||
if (plotLock) return;
|
||||
@@ -588,9 +622,9 @@ void logsDialog::plotLogs()
|
||||
coords plotCoords;
|
||||
int plotColumn = plot->row() + 2; // Date and Time first
|
||||
|
||||
plotCoords.min_y = 999999;
|
||||
plotCoords.max_y = -999999;
|
||||
plotCoords.secondRange = false;
|
||||
plotCoords.min_y = INVALID_MIN;
|
||||
plotCoords.max_y = INVALID_MAX;
|
||||
plotCoords.yaxis = firstLeft;
|
||||
plotCoords.name = plot->text();
|
||||
|
||||
for (int row = 0; row < rowCount; row++) {
|
||||
@@ -612,11 +646,8 @@ void logsDialog::plotLogs()
|
||||
y = logValue->text().toDouble();
|
||||
plotCoords.y.push_back(y);
|
||||
|
||||
if (plotCoords.min_y > y) {
|
||||
plotCoords.min_y = y;
|
||||
} else if (plotCoords.max_y < y) {
|
||||
plotCoords.max_y = y;
|
||||
}
|
||||
if (plotCoords.min_y > y) plotCoords.min_y = y;
|
||||
if (plotCoords.max_y < y) plotCoords.max_y = y;
|
||||
|
||||
if (time_str.contains('.')) {
|
||||
time = QDateTime::fromString(time_str, "yyyy-MM-dd HH:mm:ss.zzz")
|
||||
@@ -628,133 +659,219 @@ void logsDialog::plotLogs()
|
||||
}
|
||||
plotCoords.x.push_back(time);
|
||||
|
||||
if (plots.min_x > time) {
|
||||
plots.min_x = time;
|
||||
} else if (plots.max_x < time) {
|
||||
plots.max_x = time;
|
||||
}
|
||||
if (plots.min_x > time) plots.min_x = time;
|
||||
if (plots.max_x < time) plots.max_x = time;
|
||||
}
|
||||
|
||||
double range_inc = (plotCoords.max_y - plotCoords.min_y) / 100;
|
||||
if (range_inc == 0) range_inc = 1;
|
||||
plotCoords.max_y += range_inc;
|
||||
plotCoords.min_y -= range_inc;
|
||||
|
||||
plots.coords.append(plotCoords);
|
||||
}
|
||||
|
||||
plots.rangeOneMin = plots.coords.at(0).min_y;
|
||||
plots.rangeOneMax = plots.coords.at(0).max_y;
|
||||
plots.twoRanges = false;
|
||||
yAxesRanges[firstLeft].min = plots.coords.at(0).min_y;
|
||||
yAxesRanges[firstLeft].max = plots.coords.at(0).max_y;
|
||||
for (int i = firstRight; i < AXES_LIMIT; i++) {
|
||||
yAxesRanges[i].min = INVALID_MIN;
|
||||
yAxesRanges[i].max = INVALID_MAX;
|
||||
}
|
||||
plots.tooManyRanges = false;
|
||||
|
||||
for (int i = 1; i < plots.coords.size(); i++) {
|
||||
if (plots.tooManyRanges) {
|
||||
if (plots.coords.at(i).min_y < plots.rangeOneMin) {
|
||||
plots.rangeOneMin = plots.coords.at(i).min_y;
|
||||
}
|
||||
if (plots.coords.at(i).max_y > plots.rangeOneMax) {
|
||||
plots.rangeOneMax = plots.coords.at(i).max_y;
|
||||
}
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
double actualRange = plots.rangeOneMax - plots.rangeOneMin;
|
||||
double actualRange = yAxesRanges[firstLeft].max - yAxesRanges[firstLeft].min;
|
||||
double thisRange = plots.coords.at(i).max_y - plots.coords.at(i).min_y;
|
||||
|
||||
if (thisRange > actualRange * 1.3 || thisRange * 1.3 < actualRange ||
|
||||
plots.coords.at(i).min_y > plots.rangeOneMax ||
|
||||
plots.coords.at(i).max_y < plots.rangeOneMin) {
|
||||
plots.coords[i].secondRange = true;
|
||||
if (plots.twoRanges) {
|
||||
actualRange = plots.rangeTwoMax - plots.rangeTwoMin;
|
||||
if (thisRange > actualRange * 1.3 || thisRange * 1.3 < actualRange ||
|
||||
plots.coords.at(i).min_y > plots.rangeTwoMax ||
|
||||
plots.coords.at(i).max_y < plots.rangeTwoMin) {
|
||||
while (yAxesRanges[plots.coords.at(i).yaxis].max != INVALID_MAX &&
|
||||
(thisRange > actualRange * 1.3 || thisRange * 1.3 < actualRange ||
|
||||
plots.coords.at(i).min_y > yAxesRanges[plots.coords.at(i).yaxis].max ||
|
||||
plots.coords.at(i).max_y < yAxesRanges[plots.coords.at(i).yaxis].min)
|
||||
) {
|
||||
|
||||
switch (plots.coords[i].yaxis) {
|
||||
case firstLeft:
|
||||
plots.coords[i].yaxis = firstRight;
|
||||
break;
|
||||
case firstRight:
|
||||
plots.coords[i].yaxis = secondLeft;
|
||||
break;
|
||||
case secondLeft:
|
||||
plots.coords[i].yaxis = secondRight;
|
||||
break;
|
||||
case secondRight:
|
||||
plots.tooManyRanges = true;
|
||||
plots.twoRanges = false;
|
||||
if (plots.rangeTwoMin < plots.rangeOneMin) {
|
||||
plots.rangeOneMin = plots.rangeTwoMin;
|
||||
}
|
||||
if (plots.rangeTwoMax > plots.rangeOneMax) {
|
||||
plots.rangeOneMax = plots.rangeTwoMax;
|
||||
}
|
||||
if (plots.coords.at(i).min_y < plots.rangeOneMin) {
|
||||
plots.rangeOneMin = plots.coords.at(i).min_y;
|
||||
}
|
||||
if (plots.coords.at(i).max_y > plots.rangeOneMax) {
|
||||
plots.rangeOneMax = plots.coords.at(i).max_y;
|
||||
}
|
||||
} else {
|
||||
if (plots.coords.at(i).min_y < plots.rangeTwoMin) {
|
||||
plots.rangeTwoMin = plots.coords.at(i).min_y;
|
||||
}
|
||||
if (plots.coords.at(i).max_y > plots.rangeTwoMax) {
|
||||
plots.rangeTwoMax = plots.coords.at(i).max_y;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
plots.twoRanges = true;
|
||||
plots.rangeTwoMax = plots.coords.at(i).max_y;
|
||||
plots.rangeTwoMin = plots.coords.at(i).min_y;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
if (plots.tooManyRanges) break;
|
||||
|
||||
actualRange = yAxesRanges[plots.coords.at(i).yaxis].max
|
||||
- yAxesRanges[plots.coords.at(i).yaxis].min;
|
||||
}
|
||||
|
||||
if (plots.tooManyRanges) {
|
||||
break;
|
||||
} else {
|
||||
if (plots.coords.at(i).min_y < plots.rangeOneMin) {
|
||||
plots.rangeOneMin = plots.coords.at(i).min_y;
|
||||
if (plots.coords.at(i).min_y < yAxesRanges[plots.coords.at(i).yaxis].min) {
|
||||
yAxesRanges[plots.coords.at(i).yaxis].min = plots.coords.at(i).min_y;
|
||||
}
|
||||
if (plots.coords.at(i).max_y > plots.rangeOneMax) {
|
||||
plots.rangeOneMax = plots.coords.at(i).max_y;
|
||||
if (plots.coords.at(i).max_y > yAxesRanges[plots.coords.at(i).yaxis].max) {
|
||||
yAxesRanges[plots.coords.at(i).yaxis].max = plots.coords.at(i).max_y;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (plots.twoRanges) {
|
||||
rangeRatio = (plots.rangeTwoMax - plots.rangeTwoMin) /
|
||||
(plots.rangeOneMax - plots.rangeOneMin);
|
||||
rangeyAxisMin = plots.rangeOneMin;
|
||||
rangeyAxisMax = plots.rangeOneMax;
|
||||
rangeyAxis2Min = plots.rangeTwoMin;
|
||||
rangeyAxis2Max = plots.rangeTwoMax;
|
||||
if (plots.tooManyRanges) {
|
||||
yAxesRanges[firstLeft].max = 101;
|
||||
yAxesRanges[firstLeft].min = -1;
|
||||
yAxesRanges[firstRight].max = INVALID_MAX;
|
||||
yAxesRanges[firstRight].min = INVALID_MIN;
|
||||
yAxesRanges[secondLeft].max = INVALID_MAX;
|
||||
yAxesRanges[secondLeft].min = INVALID_MIN;
|
||||
yAxesRanges[secondRight].max = INVALID_MAX;
|
||||
yAxesRanges[secondRight].min = INVALID_MIN;
|
||||
|
||||
hasyAxis2 = true;
|
||||
for (int i = 0; i < plots.coords.size(); i++) {
|
||||
plots.coords[i].yaxis = firstLeft;
|
||||
|
||||
double factor = 100 / (plots.coords.at(i).max_y - plots.coords.at(i).min_y);
|
||||
for (int j = 0; j < plots.coords.at(i).y.count(); j++) {
|
||||
plots.coords[i].y[j] = factor * (plots.coords.at(i).y.at(j) - plots.coords.at(i).min_y);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
hasyAxis2 = false;
|
||||
for (int i = firstRight; i < AXES_LIMIT; i++) {
|
||||
if (yAxesRanges[i].max == INVALID_MAX) break;
|
||||
|
||||
yAxesRatios[i] = (yAxesRanges[i].max - yAxesRanges[i].min) /
|
||||
(yAxesRanges[firstLeft].max - yAxesRanges[firstLeft].min);
|
||||
}
|
||||
}
|
||||
|
||||
removeAllGraphs();
|
||||
|
||||
ui->customPlot->xAxis->setRange(plots.min_x, plots.max_x);
|
||||
axisRect->axis(QCPAxis::atBottom)->setRange(plots.min_x, plots.max_x);
|
||||
|
||||
ui->customPlot->yAxis->setRange(plots.rangeOneMin, plots.rangeOneMax);
|
||||
ui->customPlot->yAxis->setTickLabels(true);
|
||||
axisRect->axis(QCPAxis::atLeft)->setRange(yAxesRanges[firstLeft].min,
|
||||
yAxesRanges[firstLeft].max);
|
||||
|
||||
if (plots.twoRanges) {
|
||||
ui->customPlot->yAxis2->setRange(plots.rangeTwoMin, plots.rangeTwoMax);
|
||||
ui->customPlot->yAxis2->setVisible(true);
|
||||
if (plots.tooManyRanges) {
|
||||
axisRect->axis(QCPAxis::atLeft)->setTickLabels(false);
|
||||
} else {
|
||||
axisRect->axis(QCPAxis::atLeft)->setTickLabels(true);
|
||||
}
|
||||
|
||||
if (yAxesRanges[firstRight].max != INVALID_MAX) {
|
||||
axisRect->axis(QCPAxis::atRight)->setRange(yAxesRanges[firstRight].min,
|
||||
yAxesRanges[firstRight].max);
|
||||
axisRect->axis(QCPAxis::atRight)->setVisible(true);
|
||||
|
||||
rightLegend->setVisible(true);
|
||||
|
||||
if (yAxesRanges[secondLeft].max != INVALID_MAX) {
|
||||
axisRect->axis(QCPAxis::atLeft, 1)->setVisible(true);
|
||||
axisRect->axis(QCPAxis::atLeft, 1)->setRange(yAxesRanges[secondLeft].min,
|
||||
yAxesRanges[secondLeft].max);
|
||||
|
||||
if (yAxesRanges[secondRight].max != INVALID_MAX) {
|
||||
axisRect->axis(QCPAxis::atRight, 1)->setVisible(true);
|
||||
axisRect->axis(QCPAxis::atRight, 1)->setRange(yAxesRanges[secondRight].min,
|
||||
yAxesRanges[secondRight].max);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (int i = 0; i < plots.coords.size(); i++) {
|
||||
if (plots.coords.at(i).secondRange && plots.twoRanges) {
|
||||
ui->customPlot->addGraph(ui->customPlot->xAxis, ui->customPlot->yAxis2);
|
||||
} else {
|
||||
ui->customPlot->addGraph();
|
||||
switch (plots.coords[i].yaxis) {
|
||||
case firstLeft:
|
||||
ui->customPlot->addGraph();
|
||||
if (yAxesRanges[secondLeft].max != INVALID_MAX) {
|
||||
ui->customPlot->graph(i)->setName(plots.coords.at(i).name + tr(" (L1)"));
|
||||
} else {
|
||||
ui->customPlot->graph(i)->setName(plots.coords.at(i).name);
|
||||
}
|
||||
ui->customPlot->legend->addItem(
|
||||
new QCPPlottableLegendItem(ui->customPlot->legend, ui->customPlot->graph(i)));
|
||||
break;
|
||||
case firstRight:
|
||||
ui->customPlot->addGraph(axisRect->axis(QCPAxis::atBottom),
|
||||
axisRect->axis(QCPAxis::atRight));
|
||||
if (yAxesRanges[secondRight].max != INVALID_MAX) {
|
||||
ui->customPlot->graph(i)->setName(plots.coords.at(i).name + tr(" (R1)"));
|
||||
} else {
|
||||
ui->customPlot->graph(i)->setName(plots.coords.at(i).name);
|
||||
}
|
||||
rightLegend->addItem(
|
||||
new QCPPlottableLegendItem(rightLegend, ui->customPlot->graph(i)));
|
||||
break;
|
||||
case secondLeft:
|
||||
ui->customPlot->addGraph(axisRect->axis(QCPAxis::atBottom),
|
||||
axisRect->axis(QCPAxis::atLeft, 1));
|
||||
ui->customPlot->graph(i)->setName(plots.coords.at(i).name + tr(" (L2)"));
|
||||
ui->customPlot->legend->addItem(
|
||||
new QCPPlottableLegendItem(ui->customPlot->legend, ui->customPlot->graph(i)));
|
||||
break;
|
||||
case secondRight:
|
||||
ui->customPlot->addGraph(axisRect->axis(QCPAxis::atBottom),
|
||||
axisRect->axis(QCPAxis::atRight, 1));
|
||||
ui->customPlot->graph(i)->setName(plots.coords.at(i).name + tr(" (R2)"));
|
||||
rightLegend->addItem(
|
||||
new QCPPlottableLegendItem(rightLegend, ui->customPlot->graph(i)));
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
ui->customPlot->graph(i)->setData(plots.coords.at(i).x,
|
||||
plots.coords.at(i).y);
|
||||
pen.setColor(colors.at(i % colors.size()));
|
||||
ui->customPlot->graph(i)->setPen(pen);
|
||||
ui->customPlot->graph(i)->setName(plots.coords.at(i).name);
|
||||
}
|
||||
|
||||
ui->customPlot->legend->setVisible(true);
|
||||
ui->customPlot->replot();
|
||||
}
|
||||
|
||||
void logsDialog::setRangeyAxis2(QCPRange range)
|
||||
void logsDialog::yAxisChangeRanges(QCPRange range)
|
||||
{
|
||||
if (hasyAxis2) {
|
||||
double lowerChange = (range.lower - rangeyAxisMin) * rangeRatio;
|
||||
double upperChange = (range.upper - rangeyAxisMax) * rangeRatio;
|
||||
rangeyAxisMin = range.lower;
|
||||
rangeyAxisMax = range.upper;
|
||||
rangeyAxis2Min += lowerChange;
|
||||
rangeyAxis2Max += upperChange;
|
||||
if (axisRect->axis(QCPAxis::atRight)->visible()) {
|
||||
double lowerChange = (range.lower - yAxesRanges[firstLeft].min) *
|
||||
yAxesRatios[firstRight];
|
||||
double upperChange = (range.upper - yAxesRanges[firstLeft].max) *
|
||||
yAxesRatios[firstRight];
|
||||
|
||||
ui->customPlot->yAxis2->setRange(rangeyAxis2Min, rangeyAxis2Max);
|
||||
yAxesRanges[firstRight].min += lowerChange;
|
||||
yAxesRanges[firstRight].max += upperChange;
|
||||
axisRect->axis(QCPAxis::atRight)->setRange(yAxesRanges[firstRight].min,
|
||||
yAxesRanges[firstRight].max);
|
||||
|
||||
if (axisRect->axisCount(QCPAxis::atLeft) == 2) {
|
||||
lowerChange = (range.lower - yAxesRanges[firstLeft].min) *
|
||||
yAxesRatios[secondLeft];
|
||||
upperChange = (range.upper - yAxesRanges[firstLeft].max) *
|
||||
yAxesRatios[secondLeft];
|
||||
|
||||
yAxesRanges[secondLeft].min += lowerChange;
|
||||
yAxesRanges[secondLeft].max += upperChange;
|
||||
axisRect->axis(QCPAxis::atLeft, 1)->setRange(yAxesRanges[secondLeft].min,
|
||||
yAxesRanges[secondLeft].max);
|
||||
|
||||
if (axisRect->axisCount(QCPAxis::atRight) == 2) {
|
||||
lowerChange = (range.lower - yAxesRanges[firstLeft].min) *
|
||||
yAxesRatios[secondRight];
|
||||
upperChange = (range.upper - yAxesRanges[firstLeft].max) *
|
||||
yAxesRatios[secondRight];
|
||||
|
||||
yAxesRanges[secondRight].min += lowerChange;
|
||||
yAxesRanges[secondRight].max += upperChange;
|
||||
axisRect->axis(QCPAxis::atRight, 1)->setRange(yAxesRanges[secondRight].min,
|
||||
yAxesRanges[secondRight].max);
|
||||
}
|
||||
}
|
||||
|
||||
yAxesRanges[firstLeft].min = range.lower;
|
||||
yAxesRanges[firstLeft].max = range.upper;
|
||||
}
|
||||
}
|
||||
|
||||
+22
-14
@@ -5,24 +5,35 @@
|
||||
#include <QtGui>
|
||||
#include "qcustomplot/qcustomplot.h"
|
||||
|
||||
#define INVALID_MIN 999999
|
||||
#define INVALID_MAX -999999
|
||||
|
||||
enum yaxes_t {
|
||||
firstLeft = 0,
|
||||
firstRight,
|
||||
secondLeft,
|
||||
secondRight,
|
||||
AXES_LIMIT // = 4
|
||||
};
|
||||
|
||||
struct coords {
|
||||
QVector<double> x, y;
|
||||
double min_y;
|
||||
double max_y;
|
||||
bool secondRange;
|
||||
yaxes_t yaxis;
|
||||
QString name;
|
||||
};
|
||||
|
||||
struct minMax {
|
||||
double min;
|
||||
double max;
|
||||
};
|
||||
|
||||
struct plotsCollection {
|
||||
QVarLengthArray<struct coords> coords;
|
||||
double min_x;
|
||||
double max_x;
|
||||
bool twoRanges;
|
||||
bool tooManyRanges;
|
||||
double rangeOneMin;
|
||||
double rangeOneMax;
|
||||
double rangeTwoMin;
|
||||
double rangeTwoMax;
|
||||
};
|
||||
|
||||
namespace Ui {
|
||||
@@ -44,17 +55,18 @@ private slots:
|
||||
void selectionChanged();
|
||||
void mousePress();
|
||||
void mouseWheel();
|
||||
void removeSelectedGraph();
|
||||
void removeAllGraphs();
|
||||
void plotLogs();
|
||||
void on_fileOpen_BT_clicked();
|
||||
void on_sessions_CB_currentIndexChanged(int index);
|
||||
void on_mapsButton_clicked();
|
||||
void setRangeyAxis2(QCPRange range);
|
||||
void yAxisChangeRanges(QCPRange range);
|
||||
|
||||
private:
|
||||
QList<QStringList> csvlog;
|
||||
Ui::logsDialog *ui;
|
||||
QCPAxisRect *axisRect;
|
||||
QCPLegend *rightLegend;
|
||||
bool cvsFileParse();
|
||||
bool plotLock;
|
||||
QString logFilename;
|
||||
@@ -62,12 +74,8 @@ private:
|
||||
QVarLengthArray<Qt::GlobalColor> colors;
|
||||
QPen pen;
|
||||
|
||||
bool hasyAxis2;
|
||||
double rangeRatio;
|
||||
double rangeyAxisMin;
|
||||
double rangeyAxisMax;
|
||||
double rangeyAxis2Min;
|
||||
double rangeyAxis2Max;
|
||||
double yAxesRatios[AXES_LIMIT];
|
||||
minMax yAxesRanges[AXES_LIMIT];
|
||||
};
|
||||
|
||||
#endif // LOGSDIALOG_H
|
||||
|
||||
@@ -1,3 +1,24 @@
|
||||
#### Version 1.3.1 released on 25.04.15 ####
|
||||
|
||||
Bugfixes:
|
||||
- Fixed bug that prevented automatic axis rescaling when some graphs/curves had only NaN data points
|
||||
- Improved QCPItemBracket selection boundaries, especially bsCurly and bsCalligraphic
|
||||
- Fixed bug of axis rect and colorscale background shifted downward by one logical pixel (visible in scaled png and pdf export)
|
||||
- Replot upon mouse release is now only performed if a selection change has actually happened (improves responsivity on particularly complex plots)
|
||||
- Fixed bug that allowed scatter-only graphs to be selected by clicking the non-existent line between scatters
|
||||
- Fixed crash when trying to select a scatter-only QCPGraph whose only points in the visible key range are at identical key coordinates and vertically off-screen, with adaptive sampling enabled
|
||||
- Fixed pdf export of QCPColorMap with enabled interpolation (didn't appear interpolated in pdf)
|
||||
- Reduced QCPColorMap jitter of internal cell boundaries for small sized maps when viewed with high zoom, by applying oversampling factors dependant on map size
|
||||
- Fixed bug of QCPColorMap::fill() not causing the buffered internal image map to be updated, and thus the change didn't become visible immediately
|
||||
- Axis labels with size set in pixels (setPixelSize) instead of points now correctly calculate the exponent's font size if beautifully typeset powers are enabled
|
||||
- Fixed QCPColorMap appearing at the wrong position for logarithmic axes and color map spanning larger ranges
|
||||
|
||||
Other:
|
||||
- Pdf export used to embed entire QCPColorMaps, potentially leading to large files. Now only the visible portion of the map is embedded in the pdf
|
||||
- Many documentation fixes and extensions, style modernization
|
||||
- Reduced documentation file size (and thus full package size) by automatically reducing image palettes during package build
|
||||
- Fixed MSVC warning message (at warning level 4) due to temporary QLists in some foreach statements
|
||||
|
||||
#### Version 1.3.0 released on 27.12.14 ####
|
||||
|
||||
Added features:
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,7 +1,7 @@
|
||||
/***************************************************************************
|
||||
** **
|
||||
** QCustomPlot, an easy to use, modern plotting widget for Qt **
|
||||
** Copyright (C) 2011, 2012, 2013, 2014 Emanuel Eichhammer **
|
||||
** Copyright (C) 2011-2015 Emanuel Eichhammer **
|
||||
** **
|
||||
** 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 **
|
||||
@@ -19,8 +19,8 @@
|
||||
****************************************************************************
|
||||
** Author: Emanuel Eichhammer **
|
||||
** Website/Contact: http://www.qcustomplot.com/ **
|
||||
** Date: 27.12.14 **
|
||||
** Version: 1.3.0 **
|
||||
** Date: 25.04.15 **
|
||||
** Version: 1.3.1 **
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef QCUSTOMPLOT_H
|
||||
@@ -3099,7 +3099,7 @@ protected:
|
||||
bool mTightBoundary;
|
||||
QPointer<QCPColorScale> mColorScale;
|
||||
// non-property members:
|
||||
QImage mMapImage;
|
||||
QImage mMapImage, mUndersampledMapImage;
|
||||
QPixmap mLegendIcon;
|
||||
bool mMapImageInvalidated;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user