mirror of
https://github.com/jkriege2/JKQtPlotter.git
synced 2024-12-24 17:41:39 +08:00
JKQTPlotter: REORGANIZED: separated line-graphs from jkqtpscatter.h/.cpp into jkqtplines.h/.cpp
This commit is contained in:
parent
a90cbecd9d
commit
fdb8ce2d75
@ -24,6 +24,7 @@ Changes, compared to \ref page_whatsnew_V4_0_0 "v4.0.0" include:
|
||||
<li>FIXED issue <a href="https://github.com/jkriege2/JKQtPlotter/pull/70">#70: Typo in jkqtplotter/CMakeLists.txt</a>, thanks to <a href="https://github.com/tedlinlab">user:tedlinlab</a></li>
|
||||
<li>FIXED issue <a href="https://github.com/jkriege2/JKQtPlotter/pull/80">#80: Bug with multiple inheritance with Q_GDAGET with CLANG</a>, thanks to <a href="https://github.com/igormironchik">user:igormironchik</a>, caused by <a href="https://bugreports.qt.io/browse/QTBUG-104874">QTBUG-104874</a></li>
|
||||
<li>FIXED: styling was not properly applied to coordinate axes of colorbars outside the plot</li>
|
||||
<li>REORGANIZED: separated line-graphs from jkqtpscatter.h/.cpp into jkqtplines.h/.cpp</li>
|
||||
<li>IMPROVED: QT6-compatibility by removing deprecated warnings</li>
|
||||
<li>NEW: JKQTPFilledCurveXGraph and JKQTPFilledCurveYGraph can now plot wiggle plots with different fill styles above and below the baseline (feature request <a href="https://github.com/jkriege2/JKQtPlotter/issues/68">#68 Wiggle Plots</a> from <a href="https://github.com/xichaoqiang">user:xichaoqiang</a> </li>
|
||||
<li>NEW/BREAKING CHANGE: data tooltip can now also be shown when "just" moving the mouse (so far this was only possible when dragging the mouse with a button pressed). This also removes JKQtPlotter::getActMouseLeftAsToolTip() and adds JKQtPlotter::getActMouseMoveToolTip() instead! Also the default toolbars and context menus changed!</li>
|
||||
|
@ -55,6 +55,7 @@ isEmpty(JKQTP_PLOTTER_PRI_INCLUDED) {
|
||||
$$PWD/jkqtplotter/graphs/jkqtpbarchartbase.h \
|
||||
$$PWD/jkqtplotter/graphs/jkqtpbarchart.h \
|
||||
$$PWD/jkqtplotter/graphs/jkqtpevaluatedparametriccurve.h \
|
||||
$$PWD/jkqtplotter/graphs/jkqtplines.h \
|
||||
$$PWD/jkqtplotter/gui/jkqtpcomboboxes.h \
|
||||
$$PWD/jkqtplotter/gui/jkqtpenhancedspinboxes.h \
|
||||
$$PWD/jkqtplotter/gui/jkqtpenhancedtableview.h \
|
||||
@ -107,6 +108,7 @@ isEmpty(JKQTP_PLOTTER_PRI_INCLUDED) {
|
||||
$$PWD/jkqtplotter/graphs/jkqtpbarchartbase.cpp \
|
||||
$$PWD/jkqtplotter/graphs/jkqtpbarchart.cpp \
|
||||
$$PWD/jkqtplotter/graphs/jkqtpevaluatedparametriccurve.cpp \
|
||||
$$PWD/jkqtplotter/graphs/jkqtplines.cpp \
|
||||
$$PWD/jkqtplotter/gui/jkqtpcomboboxes.cpp \
|
||||
$$PWD/jkqtplotter/gui/jkqtpenhancedspinboxes.cpp \
|
||||
$$PWD/jkqtplotter/gui/jkqtpenhancedtableview.cpp \
|
||||
|
@ -66,6 +66,7 @@ set(SOURCES_GRAPHS
|
||||
${CMAKE_CURRENT_LIST_DIR}/graphs/jkqtpviolinplotstylingmixins.cpp
|
||||
${CMAKE_CURRENT_LIST_DIR}/graphs/jkqtpstatisticsadaptors.cpp
|
||||
${CMAKE_CURRENT_LIST_DIR}/graphs/jkqtpevaluatedparametriccurve.cpp
|
||||
${CMAKE_CURRENT_LIST_DIR}/graphs/jkqtplines.cpp
|
||||
)
|
||||
set(SOURCES_GUI
|
||||
${CMAKE_CURRENT_LIST_DIR}/gui/jkqtpcomboboxes.cpp
|
||||
@ -169,6 +170,8 @@ set(HEADERS_GRAPHS
|
||||
$<INSTALL_INTERFACE:graphs/jkqtpbarchart.h>
|
||||
$<BUILD_INTERFACE:${CMAKE_CURRENT_LIST_DIR}/graphs/jkqtpevaluatedparametriccurve.h>
|
||||
$<INSTALL_INTERFACE:graphs/jkqtpevaluatedparametriccurve.h>
|
||||
$<BUILD_INTERFACE:${CMAKE_CURRENT_LIST_DIR}/graphs/jkqtplines.h>
|
||||
$<INSTALL_INTERFACE:graphs/jkqtplines.h>
|
||||
)
|
||||
set(HEADERS_GUI
|
||||
$<BUILD_INTERFACE:${CMAKE_CURRENT_LIST_DIR}/gui/jkqtpcomboboxes.h>
|
||||
|
307
lib/jkqtplotter/graphs/jkqtplines.cpp
Normal file
307
lib/jkqtplotter/graphs/jkqtplines.cpp
Normal file
@ -0,0 +1,307 @@
|
||||
/*
|
||||
Copyright (c) 2008-2022 Jan W. Krieger (<jan@jkrieger.de>)
|
||||
|
||||
|
||||
|
||||
This software is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License (LGPL) as published by
|
||||
the Free Software Foundation, either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License (LGPL) for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License (LGPL)
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
#include "jkqtplotter/graphs/jkqtplines.h"
|
||||
#include "jkqtplotter/jkqtpbaseplotter.h"
|
||||
#include <stdlib.h>
|
||||
#include <QDebug>
|
||||
#include <QMarginsF>
|
||||
#include <iostream>
|
||||
#include "jkqtcommon/jkqtpdrawingtools.h"
|
||||
#include "jkqtplotter/jkqtptools.h"
|
||||
#include "jkqtplotter/jkqtpimagetools.h"
|
||||
#include "jkqtplotter/graphs/jkqtpimage.h"
|
||||
#include "jkqtplotter/jkqtpbaseelements.h"
|
||||
#include "jkqtplotter/jkqtplotter.h"
|
||||
#define SmallestGreaterZeroCompare_xvsgz() if ((xvsgz>10.0*DBL_MIN)&&((smallestGreaterZero<10.0*DBL_MIN) || (xvsgz<smallestGreaterZero))) smallestGreaterZero=xvsgz;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
JKQTPXYLineGraph::JKQTPXYLineGraph(JKQTPlotter* parent):
|
||||
JKQTPXYLineGraph(parent->getPlotter())
|
||||
{
|
||||
}
|
||||
|
||||
JKQTPXYLineGraph::JKQTPXYLineGraph(JKQTBasePlotter* parent):
|
||||
JKQTPXYGraph(parent),
|
||||
drawLine(true)
|
||||
{
|
||||
sortData=JKQTPXYGraph::Unsorted;
|
||||
|
||||
initLineStyle(parent, parentPlotStyle, JKQTPPlotStyleType::Default);
|
||||
initSymbolStyle(parent, parentPlotStyle, JKQTPPlotStyleType::Default);
|
||||
}
|
||||
|
||||
void JKQTPXYLineGraph::draw(JKQTPEnhancedPainter& painter) {
|
||||
#ifdef JKQTBP_AUTOTIMER
|
||||
JKQTPAutoOutputTimer jkaaot("JKQTPXYLineGraph::draw");
|
||||
#endif
|
||||
if (parent==nullptr) return;
|
||||
const JKQTPDatastore* datastore=parent->getDatastore();
|
||||
if (datastore==nullptr) return;
|
||||
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw();";
|
||||
|
||||
drawErrorsBefore(painter);
|
||||
{
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<1;
|
||||
painter.save(); auto __finalpaint=JKQTPFinally([&painter]() {painter.restore();});
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<2;
|
||||
|
||||
const QPen p=getLinePen(painter, parent);
|
||||
const QPen penSelection=getHighlightingLinePen(painter, parent);
|
||||
const auto symType=getSymbolType();
|
||||
const double xmin=transformX(parent->getXAxis()->getMin());
|
||||
const double xmax=transformX(parent->getXAxis()->getMax());
|
||||
const double ymin=transformY(parent->getYAxis()->getMin());
|
||||
const double ymax=transformY(parent->getYAxis()->getMax());
|
||||
const double symbolSize=parent->pt2px(painter, getSymbolSize());
|
||||
const QMarginsF clipMargins=(symType==JKQTPNoSymbol)?QMarginsF(0,0,0,0):QMarginsF(symbolSize,symbolSize,symbolSize,symbolSize);
|
||||
const QRectF cliprect=QRectF(qMin(xmin,xmax),qMin(ymin,ymax),fabs(xmax-xmin),fabs(ymax-ymin))+clipMargins;
|
||||
|
||||
|
||||
int imax=0;
|
||||
int imin=0;
|
||||
if (getIndexRange(imin, imax)) {
|
||||
|
||||
|
||||
QList<QPolygonF> vec_linesP;
|
||||
vec_linesP.push_back(QPolygonF());
|
||||
intSortData();
|
||||
for (int iii=imin; iii<imax; iii++) {
|
||||
const int i=qBound(imin, getDataIndex(iii), imax);
|
||||
const double xv=datastore->get(static_cast<size_t>(xColumn),static_cast<size_t>(i));
|
||||
const double yv=datastore->get(static_cast<size_t>(yColumn),static_cast<size_t>(i));
|
||||
const double x=transformX(xv);
|
||||
const double y=transformY(yv);
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): (xv, yv) = ( "<<xv<<", "<<yv<<" )";
|
||||
if (JKQTPIsOKFloat(xv) && JKQTPIsOKFloat(yv) && JKQTPIsOKFloat(x) && JKQTPIsOKFloat(y)) {
|
||||
|
||||
//if (isHighlighted() && getSymbolType()!=JKQTPNoSymbol) {
|
||||
//JKQTPPlotSymbol(painter, x, y, JKQTPFilledCircle, parent->pt2px(painter, symbolSize*1.5), parent->pt2px(painter, symbolWidth*parent->getLineWidthMultiplier()), penSelection.color(), penSelection.color());
|
||||
//}
|
||||
if ((!parent->getXAxis()->isLogAxis() || xv>0.0) && (!parent->getYAxis()->isLogAxis() || yv>0.0) ) {
|
||||
if (symType!=JKQTPNoSymbol && cliprect.contains(x,y)) plotStyledSymbol(parent, painter, x, y);
|
||||
if (drawLine) {
|
||||
vec_linesP.last() << QPointF(x,y);
|
||||
}
|
||||
} else {
|
||||
if (drawLine) {
|
||||
if (vec_linesP.size()==0 || vec_linesP.last().size()>0)
|
||||
vec_linesP.push_back(QPolygonF());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<4<<" lines="<<lines.size();
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<5<<" p="<<painter.pen();
|
||||
if (drawLine) {
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): vec_linesP.size()=="<<vec_linesP.size();
|
||||
|
||||
QList<QPolygonF> linesToDraw;
|
||||
if (getUseNonvisibleLineCompression()) linesToDraw=JKQTPClipPolyLines(JKQTPSimplifyPolyLines(vec_linesP, p.widthF()*getNonvisibleLineCompressionAgressiveness()), cliprect);
|
||||
else linesToDraw=JKQTPClipPolyLines(vec_linesP, cliprect);
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): linesToDraw.size()=="<<linesToDraw.size()<<", clip: x="<<xmin<<".."<<xmax<<", y="<<ymin<<".."<<ymax;
|
||||
for (const auto &linesP : linesToDraw) {
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): linesPFromV.size()=="<<linesPFromV.size()<<" useNonvisibleLineCompression="<<getUseNonvisibleLineCompression();
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): --> linesP.size()=="<<linesP.size();
|
||||
if (linesP.size()>0) {
|
||||
if (isHighlighted()) {
|
||||
painter.setPen(penSelection);
|
||||
painter.drawPolyline(linesP);
|
||||
}
|
||||
painter.setPen(p);
|
||||
painter.drawPolyline(linesP);
|
||||
}
|
||||
}
|
||||
}
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<6;
|
||||
}
|
||||
}
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<7;
|
||||
drawErrorsAfter(painter);
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw() ... done";
|
||||
}
|
||||
|
||||
void JKQTPXYLineGraph::drawKeyMarker(JKQTPEnhancedPainter& painter, QRectF& rect) {
|
||||
const double minSize=qMin(rect.width(), rect.height());
|
||||
const double maxSize=qMax(rect.width(), rect.height());
|
||||
double symbolSize=parent->pt2px(painter, this->getSymbolSize());
|
||||
if (symbolSize>minSize*0.9) symbolSize=minSize*0.9;
|
||||
double symbolWidth=parent->pt2px(painter, this->getSymbolLineWidth()*parent->getLineWidthMultiplier());
|
||||
if (symbolWidth>0.3*symbolSize) symbolWidth=0.3*symbolSize;
|
||||
double lineWidth=parent->pt2px(painter, this->getLineWidth()*parent->getLineWidthMultiplier());
|
||||
if (lineWidth>0.5*maxSize) lineWidth=0.5*maxSize;
|
||||
|
||||
painter.save(); auto __finalpaint=JKQTPFinally([&painter]() {painter.restore();});
|
||||
QPen p=getLinePen(painter, parent);
|
||||
p.setColor(getKeyLabelColor());
|
||||
p.setStyle(getLineStyle());
|
||||
p.setWidthF(lineWidth);
|
||||
painter.setPen(p);
|
||||
double y=rect.top()+rect.height()/2.0;
|
||||
if (drawLine) painter.drawLine(QLineF(rect.left(), y, rect.right(), y));
|
||||
JKQTPPlotSymbol(painter, rect.left()+rect.width()/2.0, rect.top()+rect.height()/2.0, getSymbolType(), symbolSize, symbolWidth, getKeyLabelColor(), getSymbolFillColor());
|
||||
|
||||
}
|
||||
|
||||
QColor JKQTPXYLineGraph::getKeyLabelColor() const {
|
||||
return getSymbolColor();
|
||||
}
|
||||
|
||||
void JKQTPXYLineGraph::setDrawLine(bool __value)
|
||||
{
|
||||
this->drawLine = __value;
|
||||
}
|
||||
|
||||
bool JKQTPXYLineGraph::getDrawLine() const
|
||||
{
|
||||
return this->drawLine;
|
||||
}
|
||||
|
||||
void JKQTPXYLineGraph::setColor(QColor c)
|
||||
{
|
||||
setLineColor(c);
|
||||
setSymbolColor(c);
|
||||
setSymbolFillColor(JKQTPGetDerivedColor(parent->getCurrentPlotterStyle().graphsStyle.defaultGraphStyle.fillColorDerivationMode, c));
|
||||
c.setAlphaF(0.5);
|
||||
setHighlightingLineColor(c);
|
||||
}
|
||||
|
||||
|
||||
|
||||
JKQTPXYLineErrorGraph::JKQTPXYLineErrorGraph(JKQTBasePlotter *parent):
|
||||
JKQTPXYLineGraph(parent)
|
||||
{
|
||||
setErrorColorFromGraphColor(getSymbolColor());
|
||||
initErrorStyle(parent, parentPlotStyle);
|
||||
}
|
||||
|
||||
JKQTPXYLineErrorGraph::JKQTPXYLineErrorGraph(JKQTPlotter *parent):
|
||||
JKQTPXYLineErrorGraph(parent->getPlotter())
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
bool JKQTPXYLineErrorGraph::getXMinMax(double &minx, double &maxx, double &smallestGreaterZero) {
|
||||
if (xErrorColumn<0 || xErrorStyle==JKQTPNoError) {
|
||||
return JKQTPXYLineGraph::getXMinMax(minx, maxx, smallestGreaterZero);
|
||||
} else {
|
||||
bool start=true;
|
||||
minx=0;
|
||||
maxx=0;
|
||||
smallestGreaterZero=0;
|
||||
|
||||
if (parent==nullptr) return false;
|
||||
|
||||
const JKQTPDatastore* datastore=parent->getDatastore();
|
||||
int imax=0;
|
||||
int imin=0;
|
||||
if (getIndexRange(imin, imax)) {
|
||||
for (int i=imin; i<imax; i++) {
|
||||
double xv=datastore->get(static_cast<size_t>(xColumn),static_cast<size_t>(i))+getXErrorU(i, datastore);
|
||||
if (JKQTPIsOKFloat(xv)) {
|
||||
if (start || xv>maxx) maxx=xv;
|
||||
if (start || xv<minx) minx=xv;
|
||||
const double xvsgz=xv; SmallestGreaterZeroCompare_xvsgz();
|
||||
start=false;
|
||||
}
|
||||
xv=datastore->get(static_cast<size_t>(xColumn),static_cast<size_t>(i))-getXErrorL(i, datastore);
|
||||
if (JKQTPIsOKFloat(xv)) {
|
||||
if (start || xv>maxx) maxx=xv;
|
||||
if (start || xv<minx) minx=xv;
|
||||
const double xvsgz=xv; SmallestGreaterZeroCompare_xvsgz();
|
||||
start=false;
|
||||
}
|
||||
}
|
||||
return !start;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool JKQTPXYLineErrorGraph::getYMinMax(double &miny, double &maxy, double &smallestGreaterZero) {
|
||||
if (yErrorColumn<0 || yErrorStyle==JKQTPNoError) {
|
||||
return JKQTPXYLineGraph::getYMinMax(miny, maxy, smallestGreaterZero);
|
||||
} else {
|
||||
bool start=true;
|
||||
miny=0;
|
||||
maxy=0;
|
||||
smallestGreaterZero=0;
|
||||
|
||||
if (parent==nullptr) return false;
|
||||
|
||||
const JKQTPDatastore* datastore=parent->getDatastore();
|
||||
int imax=0;
|
||||
int imin=0;
|
||||
if (getIndexRange(imin, imax)) {
|
||||
for (int i=imin; i<imax; i++) {
|
||||
double yv=datastore->get(static_cast<size_t>(yColumn),static_cast<size_t>(i))+getYErrorU(i, datastore);
|
||||
if (JKQTPIsOKFloat(yv)) {
|
||||
if (start || yv>maxy) maxy=yv;
|
||||
if (start || yv<miny) miny=yv;
|
||||
const double xvsgz=yv; SmallestGreaterZeroCompare_xvsgz();
|
||||
start=false;
|
||||
}
|
||||
yv=datastore->get(static_cast<size_t>(yColumn),static_cast<size_t>(i))-getYErrorL(i, datastore);
|
||||
if (JKQTPIsOKFloat(yv)) {
|
||||
if (start || yv>maxy) maxy=yv;
|
||||
if (start || yv<miny) miny=yv;
|
||||
const double xvsgz=yv; SmallestGreaterZeroCompare_xvsgz();
|
||||
start=false;
|
||||
}
|
||||
}
|
||||
return !start;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool JKQTPXYLineErrorGraph::usesColumn(int c) const
|
||||
{
|
||||
return JKQTPXYLineGraph::usesColumn(c)||JKQTPXYGraphErrors::errorUsesColumn(c);
|
||||
}
|
||||
|
||||
void JKQTPXYLineErrorGraph::drawErrorsBefore(JKQTPEnhancedPainter &painter)
|
||||
{
|
||||
intSortData();
|
||||
if (sortData==JKQTPXYGraph::Unsorted) plotErrorIndicators(painter, parent, this, xColumn, yColumn);
|
||||
else plotErrorIndicators(painter, parent, this, xColumn, yColumn, 0, 0, &sortedIndices);
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
139
lib/jkqtplotter/graphs/jkqtplines.h
Normal file
139
lib/jkqtplotter/graphs/jkqtplines.h
Normal file
@ -0,0 +1,139 @@
|
||||
/*
|
||||
Copyright (c) 2008-2022 Jan W. Krieger (<jan@jkrieger.de>)
|
||||
|
||||
|
||||
|
||||
This software is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License (LGPL) as published by
|
||||
the Free Software Foundation, either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License (LGPL) for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License (LGPL)
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef JKQTPLINES_H
|
||||
#define JKQTPLINES_H
|
||||
|
||||
|
||||
#include <QString>
|
||||
#include <QPainter>
|
||||
#include <QPair>
|
||||
#include <functional>
|
||||
#include "jkqtplotter/jkqtptools.h"
|
||||
#include "jkqtplotter/jkqtplotter_imexport.h"
|
||||
#include "jkqtcommon/jkqtpdrawingtools.h"
|
||||
#include "jkqtplotter/jkqtpgraphsbase.h"
|
||||
#include "jkqtcommon/jkqtpenhancedpainter.h"
|
||||
#include "jkqtplotter/jkqtpgraphsbaseerrors.h"
|
||||
#include "jkqtplotter/graphs/jkqtprange.h"
|
||||
#include "jkqtplotter/jkqtpgraphsbasestylingmixins.h"
|
||||
|
||||
// forward declarations
|
||||
class JKQTBasePlotter;
|
||||
class JKQTPlotter;
|
||||
class JKQTPCoordinateAxis;
|
||||
class JKQTPDatastore;
|
||||
//class JKQTPColorPaletteStyleAndToolsMixin;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/*! \brief This implements xy line plots. This also alows to draw symbols at the data points.
|
||||
\ingroup jkqtplotter_linesymbolgraphs_simple
|
||||
|
||||
\image html plot_lineplots.png
|
||||
|
||||
\note This classes can (and does by default) apply a line-compression strategy that improves plotting speed
|
||||
but reduces accuracy a bit. See JKQTPGraphLinesCompressionMixin for details.
|
||||
|
||||
\see \ref JKQTPlotterAdvancedLineAndFillStyling, \ref JKQTPlotterSimpleTest, \ref JKQTPlotterSymbolsAndStyles,
|
||||
jkqtpstatAddVKDE1D(), jkqtpstatAddVKDE1DAutoranged(), jkqtpstatAddHKDE1D(), jkqtpstatAddHKDE1DAutoranged(),
|
||||
JKQTPGraphLinesCompressionMixin
|
||||
*/
|
||||
class JKQTPLOTTER_LIB_EXPORT JKQTPXYLineGraph: public JKQTPXYGraph, public JKQTPGraphLineStyleMixin, public JKQTPGraphSymbolStyleMixin, public JKQTPGraphLinesCompressionMixin {
|
||||
Q_OBJECT
|
||||
public:
|
||||
/** \brief class constructor */
|
||||
explicit JKQTPXYLineGraph(JKQTBasePlotter* parent=nullptr);
|
||||
/** \brief class constructor */
|
||||
JKQTPXYLineGraph(JKQTPlotter* parent);
|
||||
|
||||
/** \brief plots the graph to the plotter object specified as parent */
|
||||
virtual void draw(JKQTPEnhancedPainter& painter) override;
|
||||
/** \brief plots a key marker inside the specified rectangle \a rect */
|
||||
virtual void drawKeyMarker(JKQTPEnhancedPainter& painter, QRectF& rect) override;
|
||||
/** \brief returns the color to be used for the key label */
|
||||
virtual QColor getKeyLabelColor() const override;
|
||||
|
||||
/** \copydoc drawLine */
|
||||
void setDrawLine(bool __value);
|
||||
/** \copydoc drawLine */
|
||||
bool getDrawLine() const;
|
||||
|
||||
/** \brief set color of line and symbol */
|
||||
void setColor(QColor c);
|
||||
|
||||
protected:
|
||||
|
||||
/** \brief indicates whether to draw a line or not */
|
||||
bool drawLine;
|
||||
|
||||
|
||||
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/*! \brief This implements xy line plots with x and y error indicators.
|
||||
\ingroup jkqtplotter_linesymbolgraphs_simple
|
||||
|
||||
\image html plot_errorbarlineplots.png
|
||||
\image html plot_errorlinelineplots.png
|
||||
\image html plot_errorpolygonlineplots.png
|
||||
|
||||
\see jkqtpstatAddXYErrorLineGraph(), jkqtpstatAddXErrorLineGraph(), jkqtpstatAddYErrorLineGraph(), \ref JKQTPlotterErrorBarStyles, \ref JKQTPlotterBasicJKQTPDatastoreStatisticsGroupedStat
|
||||
*/
|
||||
class JKQTPLOTTER_LIB_EXPORT JKQTPXYLineErrorGraph: public JKQTPXYLineGraph, public JKQTPXYGraphErrors {
|
||||
Q_OBJECT
|
||||
public:
|
||||
/** \brief class constructor */
|
||||
JKQTPXYLineErrorGraph(JKQTBasePlotter* parent=nullptr);
|
||||
/** \brief class constructor */
|
||||
JKQTPXYLineErrorGraph(JKQTPlotter* parent);
|
||||
|
||||
/** \brief get the maximum and minimum x-value of the graph
|
||||
*
|
||||
* The result is given in the two parameters which are call-by-reference parameters!
|
||||
*/
|
||||
virtual bool getXMinMax(double& minx, double& maxx, double& smallestGreaterZero) override;
|
||||
/** \brief get the maximum and minimum y-value of the graph
|
||||
*
|
||||
* The result is given in the two parameters which are call-by-reference parameters!
|
||||
*/
|
||||
virtual bool getYMinMax(double& miny, double& maxy, double& smallestGreaterZero) override;
|
||||
/** \copydoc JKQTPGraph::usesColumn() */
|
||||
virtual bool usesColumn(int c) const override;
|
||||
|
||||
protected:
|
||||
/** \brief this function is used to plot error inidcators before plotting the graphs. */
|
||||
virtual void drawErrorsBefore(JKQTPEnhancedPainter& painter) override;
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#endif // JKQTPLINES_H
|
@ -43,267 +43,6 @@
|
||||
|
||||
|
||||
|
||||
JKQTPXYLineGraph::JKQTPXYLineGraph(JKQTPlotter* parent):
|
||||
JKQTPXYLineGraph(parent->getPlotter())
|
||||
{
|
||||
}
|
||||
|
||||
JKQTPXYLineGraph::JKQTPXYLineGraph(JKQTBasePlotter* parent):
|
||||
JKQTPXYGraph(parent),
|
||||
drawLine(true)
|
||||
{
|
||||
sortData=JKQTPXYGraph::Unsorted;
|
||||
|
||||
initLineStyle(parent, parentPlotStyle, JKQTPPlotStyleType::Default);
|
||||
initSymbolStyle(parent, parentPlotStyle, JKQTPPlotStyleType::Default);
|
||||
}
|
||||
|
||||
void JKQTPXYLineGraph::draw(JKQTPEnhancedPainter& painter) {
|
||||
#ifdef JKQTBP_AUTOTIMER
|
||||
JKQTPAutoOutputTimer jkaaot("JKQTPXYLineGraph::draw");
|
||||
#endif
|
||||
if (parent==nullptr) return;
|
||||
const JKQTPDatastore* datastore=parent->getDatastore();
|
||||
if (datastore==nullptr) return;
|
||||
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw();";
|
||||
|
||||
drawErrorsBefore(painter);
|
||||
{
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<1;
|
||||
painter.save(); auto __finalpaint=JKQTPFinally([&painter]() {painter.restore();});
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<2;
|
||||
|
||||
const QPen p=getLinePen(painter, parent);
|
||||
const QPen penSelection=getHighlightingLinePen(painter, parent);
|
||||
const auto symType=getSymbolType();
|
||||
const double xmin=transformX(parent->getXAxis()->getMin());
|
||||
const double xmax=transformX(parent->getXAxis()->getMax());
|
||||
const double ymin=transformY(parent->getYAxis()->getMin());
|
||||
const double ymax=transformY(parent->getYAxis()->getMax());
|
||||
const double symbolSize=parent->pt2px(painter, getSymbolSize());
|
||||
const QMarginsF clipMargins=(symType==JKQTPNoSymbol)?QMarginsF(0,0,0,0):QMarginsF(symbolSize,symbolSize,symbolSize,symbolSize);
|
||||
const QRectF cliprect=QRectF(qMin(xmin,xmax),qMin(ymin,ymax),fabs(xmax-xmin),fabs(ymax-ymin))+clipMargins;
|
||||
|
||||
|
||||
int imax=0;
|
||||
int imin=0;
|
||||
if (getIndexRange(imin, imax)) {
|
||||
|
||||
|
||||
QList<QPolygonF> vec_linesP;
|
||||
vec_linesP.push_back(QPolygonF());
|
||||
intSortData();
|
||||
for (int iii=imin; iii<imax; iii++) {
|
||||
const int i=qBound(imin, getDataIndex(iii), imax);
|
||||
const double xv=datastore->get(static_cast<size_t>(xColumn),static_cast<size_t>(i));
|
||||
const double yv=datastore->get(static_cast<size_t>(yColumn),static_cast<size_t>(i));
|
||||
const double x=transformX(xv);
|
||||
const double y=transformY(yv);
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): (xv, yv) = ( "<<xv<<", "<<yv<<" )";
|
||||
if (JKQTPIsOKFloat(xv) && JKQTPIsOKFloat(yv) && JKQTPIsOKFloat(x) && JKQTPIsOKFloat(y)) {
|
||||
|
||||
//if (isHighlighted() && getSymbolType()!=JKQTPNoSymbol) {
|
||||
//JKQTPPlotSymbol(painter, x, y, JKQTPFilledCircle, parent->pt2px(painter, symbolSize*1.5), parent->pt2px(painter, symbolWidth*parent->getLineWidthMultiplier()), penSelection.color(), penSelection.color());
|
||||
//}
|
||||
if ((!parent->getXAxis()->isLogAxis() || xv>0.0) && (!parent->getYAxis()->isLogAxis() || yv>0.0) ) {
|
||||
if (symType!=JKQTPNoSymbol && cliprect.contains(x,y)) plotStyledSymbol(parent, painter, x, y);
|
||||
if (drawLine) {
|
||||
vec_linesP.last() << QPointF(x,y);
|
||||
}
|
||||
} else {
|
||||
if (drawLine) {
|
||||
if (vec_linesP.size()==0 || vec_linesP.last().size()>0)
|
||||
vec_linesP.push_back(QPolygonF());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<4<<" lines="<<lines.size();
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<5<<" p="<<painter.pen();
|
||||
if (drawLine) {
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): vec_linesP.size()=="<<vec_linesP.size();
|
||||
|
||||
QList<QPolygonF> linesToDraw;
|
||||
if (getUseNonvisibleLineCompression()) linesToDraw=JKQTPClipPolyLines(JKQTPSimplifyPolyLines(vec_linesP, p.widthF()*getNonvisibleLineCompressionAgressiveness()), cliprect);
|
||||
else linesToDraw=JKQTPClipPolyLines(vec_linesP, cliprect);
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): linesToDraw.size()=="<<linesToDraw.size()<<", clip: x="<<xmin<<".."<<xmax<<", y="<<ymin<<".."<<ymax;
|
||||
for (const auto &linesP : linesToDraw) {
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): linesPFromV.size()=="<<linesPFromV.size()<<" useNonvisibleLineCompression="<<getUseNonvisibleLineCompression();
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): --> linesP.size()=="<<linesP.size();
|
||||
if (linesP.size()>0) {
|
||||
if (isHighlighted()) {
|
||||
painter.setPen(penSelection);
|
||||
painter.drawPolyline(linesP);
|
||||
}
|
||||
painter.setPen(p);
|
||||
painter.drawPolyline(linesP);
|
||||
}
|
||||
}
|
||||
}
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<6;
|
||||
}
|
||||
}
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw(): "<<7;
|
||||
drawErrorsAfter(painter);
|
||||
//qDebug()<<"JKQTPXYLineGraph::draw() ... done";
|
||||
}
|
||||
|
||||
void JKQTPXYLineGraph::drawKeyMarker(JKQTPEnhancedPainter& painter, QRectF& rect) {
|
||||
const double minSize=qMin(rect.width(), rect.height());
|
||||
const double maxSize=qMax(rect.width(), rect.height());
|
||||
double symbolSize=parent->pt2px(painter, this->getSymbolSize());
|
||||
if (symbolSize>minSize*0.9) symbolSize=minSize*0.9;
|
||||
double symbolWidth=parent->pt2px(painter, this->getSymbolLineWidth()*parent->getLineWidthMultiplier());
|
||||
if (symbolWidth>0.3*symbolSize) symbolWidth=0.3*symbolSize;
|
||||
double lineWidth=parent->pt2px(painter, this->getLineWidth()*parent->getLineWidthMultiplier());
|
||||
if (lineWidth>0.5*maxSize) lineWidth=0.5*maxSize;
|
||||
|
||||
painter.save(); auto __finalpaint=JKQTPFinally([&painter]() {painter.restore();});
|
||||
QPen p=getLinePen(painter, parent);
|
||||
p.setColor(getKeyLabelColor());
|
||||
p.setStyle(getLineStyle());
|
||||
p.setWidthF(lineWidth);
|
||||
painter.setPen(p);
|
||||
double y=rect.top()+rect.height()/2.0;
|
||||
if (drawLine) painter.drawLine(QLineF(rect.left(), y, rect.right(), y));
|
||||
JKQTPPlotSymbol(painter, rect.left()+rect.width()/2.0, rect.top()+rect.height()/2.0, getSymbolType(), symbolSize, symbolWidth, getKeyLabelColor(), getSymbolFillColor());
|
||||
|
||||
}
|
||||
|
||||
QColor JKQTPXYLineGraph::getKeyLabelColor() const {
|
||||
return getSymbolColor();
|
||||
}
|
||||
|
||||
void JKQTPXYLineGraph::setDrawLine(bool __value)
|
||||
{
|
||||
this->drawLine = __value;
|
||||
}
|
||||
|
||||
bool JKQTPXYLineGraph::getDrawLine() const
|
||||
{
|
||||
return this->drawLine;
|
||||
}
|
||||
|
||||
void JKQTPXYLineGraph::setColor(QColor c)
|
||||
{
|
||||
setLineColor(c);
|
||||
setSymbolColor(c);
|
||||
setSymbolFillColor(JKQTPGetDerivedColor(parent->getCurrentPlotterStyle().graphsStyle.defaultGraphStyle.fillColorDerivationMode, c));
|
||||
c.setAlphaF(0.5);
|
||||
setHighlightingLineColor(c);
|
||||
}
|
||||
|
||||
|
||||
|
||||
JKQTPXYLineErrorGraph::JKQTPXYLineErrorGraph(JKQTBasePlotter *parent):
|
||||
JKQTPXYLineGraph(parent)
|
||||
{
|
||||
setErrorColorFromGraphColor(getSymbolColor());
|
||||
initErrorStyle(parent, parentPlotStyle);
|
||||
}
|
||||
|
||||
JKQTPXYLineErrorGraph::JKQTPXYLineErrorGraph(JKQTPlotter *parent):
|
||||
JKQTPXYLineErrorGraph(parent->getPlotter())
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
bool JKQTPXYLineErrorGraph::getXMinMax(double &minx, double &maxx, double &smallestGreaterZero) {
|
||||
if (xErrorColumn<0 || xErrorStyle==JKQTPNoError) {
|
||||
return JKQTPXYLineGraph::getXMinMax(minx, maxx, smallestGreaterZero);
|
||||
} else {
|
||||
bool start=true;
|
||||
minx=0;
|
||||
maxx=0;
|
||||
smallestGreaterZero=0;
|
||||
|
||||
if (parent==nullptr) return false;
|
||||
|
||||
const JKQTPDatastore* datastore=parent->getDatastore();
|
||||
int imax=0;
|
||||
int imin=0;
|
||||
if (getIndexRange(imin, imax)) {
|
||||
for (int i=imin; i<imax; i++) {
|
||||
double xv=datastore->get(static_cast<size_t>(xColumn),static_cast<size_t>(i))+getXErrorU(i, datastore);
|
||||
if (JKQTPIsOKFloat(xv)) {
|
||||
if (start || xv>maxx) maxx=xv;
|
||||
if (start || xv<minx) minx=xv;
|
||||
const double xvsgz=xv; SmallestGreaterZeroCompare_xvsgz();
|
||||
start=false;
|
||||
}
|
||||
xv=datastore->get(static_cast<size_t>(xColumn),static_cast<size_t>(i))-getXErrorL(i, datastore);
|
||||
if (JKQTPIsOKFloat(xv)) {
|
||||
if (start || xv>maxx) maxx=xv;
|
||||
if (start || xv<minx) minx=xv;
|
||||
const double xvsgz=xv; SmallestGreaterZeroCompare_xvsgz();
|
||||
start=false;
|
||||
}
|
||||
}
|
||||
return !start;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool JKQTPXYLineErrorGraph::getYMinMax(double &miny, double &maxy, double &smallestGreaterZero) {
|
||||
if (yErrorColumn<0 || yErrorStyle==JKQTPNoError) {
|
||||
return JKQTPXYLineGraph::getYMinMax(miny, maxy, smallestGreaterZero);
|
||||
} else {
|
||||
bool start=true;
|
||||
miny=0;
|
||||
maxy=0;
|
||||
smallestGreaterZero=0;
|
||||
|
||||
if (parent==nullptr) return false;
|
||||
|
||||
const JKQTPDatastore* datastore=parent->getDatastore();
|
||||
int imax=0;
|
||||
int imin=0;
|
||||
if (getIndexRange(imin, imax)) {
|
||||
for (int i=imin; i<imax; i++) {
|
||||
double yv=datastore->get(static_cast<size_t>(yColumn),static_cast<size_t>(i))+getYErrorU(i, datastore);
|
||||
if (JKQTPIsOKFloat(yv)) {
|
||||
if (start || yv>maxy) maxy=yv;
|
||||
if (start || yv<miny) miny=yv;
|
||||
const double xvsgz=yv; SmallestGreaterZeroCompare_xvsgz();
|
||||
start=false;
|
||||
}
|
||||
yv=datastore->get(static_cast<size_t>(yColumn),static_cast<size_t>(i))-getYErrorL(i, datastore);
|
||||
if (JKQTPIsOKFloat(yv)) {
|
||||
if (start || yv>maxy) maxy=yv;
|
||||
if (start || yv<miny) miny=yv;
|
||||
const double xvsgz=yv; SmallestGreaterZeroCompare_xvsgz();
|
||||
start=false;
|
||||
}
|
||||
}
|
||||
return !start;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool JKQTPXYLineErrorGraph::usesColumn(int c) const
|
||||
{
|
||||
return JKQTPXYLineGraph::usesColumn(c)||JKQTPXYGraphErrors::errorUsesColumn(c);
|
||||
}
|
||||
|
||||
void JKQTPXYLineErrorGraph::drawErrorsBefore(JKQTPEnhancedPainter &painter)
|
||||
{
|
||||
intSortData();
|
||||
if (sortData==JKQTPXYGraph::Unsorted) plotErrorIndicators(painter, parent, this, xColumn, yColumn);
|
||||
else plotErrorIndicators(painter, parent, this, xColumn, yColumn, 0, 0, &sortedIndices);
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
@ -17,8 +17,8 @@
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef jkqtpgraphs_H
|
||||
#define jkqtpgraphs_H
|
||||
#ifndef jkqtpscatter_H
|
||||
#define jkqtpscatter_H
|
||||
|
||||
|
||||
#include <QString>
|
||||
@ -32,6 +32,7 @@
|
||||
#include "jkqtcommon/jkqtpenhancedpainter.h"
|
||||
#include "jkqtplotter/jkqtpgraphsbaseerrors.h"
|
||||
#include "jkqtplotter/graphs/jkqtprange.h"
|
||||
#include "jkqtplotter/graphs/jkqtplines.h"
|
||||
#include "jkqtplotter/jkqtpgraphsbasestylingmixins.h"
|
||||
|
||||
// forward declarations
|
||||
@ -46,59 +47,6 @@ class JKQTPDatastore;
|
||||
|
||||
|
||||
|
||||
/*! \brief This implements xy line plots. This also alows to draw symbols at the data points.
|
||||
\ingroup jkqtplotter_linesymbolgraphs_simple
|
||||
|
||||
\image html plot_lineplots.png
|
||||
|
||||
\note This classes can (and does by default) apply a line-compression strategy that improves plotting speed
|
||||
but reduces accuracy a bit. See JKQTPGraphLinesCompressionMixin for details.
|
||||
|
||||
\see \ref JKQTPlotterAdvancedLineAndFillStyling, \ref JKQTPlotterSimpleTest, \ref JKQTPlotterSymbolsAndStyles,
|
||||
jkqtpstatAddVKDE1D(), jkqtpstatAddVKDE1DAutoranged(), jkqtpstatAddHKDE1D(), jkqtpstatAddHKDE1DAutoranged(),
|
||||
JKQTPGraphLinesCompressionMixin
|
||||
*/
|
||||
class JKQTPLOTTER_LIB_EXPORT JKQTPXYLineGraph: public JKQTPXYGraph, public JKQTPGraphLineStyleMixin, public JKQTPGraphSymbolStyleMixin, public JKQTPGraphLinesCompressionMixin {
|
||||
Q_OBJECT
|
||||
public:
|
||||
/** \brief class constructor */
|
||||
explicit JKQTPXYLineGraph(JKQTBasePlotter* parent=nullptr);
|
||||
/** \brief class constructor */
|
||||
JKQTPXYLineGraph(JKQTPlotter* parent);
|
||||
|
||||
/** \brief plots the graph to the plotter object specified as parent */
|
||||
virtual void draw(JKQTPEnhancedPainter& painter) override;
|
||||
/** \brief plots a key marker inside the specified rectangle \a rect */
|
||||
virtual void drawKeyMarker(JKQTPEnhancedPainter& painter, QRectF& rect) override;
|
||||
/** \brief returns the color to be used for the key label */
|
||||
virtual QColor getKeyLabelColor() const override;
|
||||
|
||||
/** \copydoc drawLine */
|
||||
void setDrawLine(bool __value);
|
||||
/** \copydoc drawLine */
|
||||
bool getDrawLine() const;
|
||||
|
||||
/** \brief set color of line and symbol */
|
||||
void setColor(QColor c);
|
||||
|
||||
protected:
|
||||
|
||||
/** \brief indicates whether to draw a line or not */
|
||||
bool drawLine;
|
||||
|
||||
|
||||
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/*! \brief This implements xy scatter plots (like JKQTPXYLineGraph), but the color and size of the symbols may be taken from a column.
|
||||
\ingroup jkqtplotter_linesymbolgraphs_param
|
||||
|
||||
@ -383,43 +331,6 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPXYParametrizedScatterGraph: public JKQTPXYGrap
|
||||
|
||||
|
||||
|
||||
/*! \brief This implements xy line plots with x and y error indicators.
|
||||
\ingroup jkqtplotter_linesymbolgraphs_simple
|
||||
|
||||
\image html plot_errorbarlineplots.png
|
||||
\image html plot_errorlinelineplots.png
|
||||
\image html plot_errorpolygonlineplots.png
|
||||
|
||||
\see jkqtpstatAddXYErrorLineGraph(), jkqtpstatAddXErrorLineGraph(), jkqtpstatAddYErrorLineGraph(), \ref JKQTPlotterErrorBarStyles, \ref JKQTPlotterBasicJKQTPDatastoreStatisticsGroupedStat
|
||||
*/
|
||||
class JKQTPLOTTER_LIB_EXPORT JKQTPXYLineErrorGraph: public JKQTPXYLineGraph, public JKQTPXYGraphErrors {
|
||||
Q_OBJECT
|
||||
public:
|
||||
/** \brief class constructor */
|
||||
JKQTPXYLineErrorGraph(JKQTBasePlotter* parent=nullptr);
|
||||
/** \brief class constructor */
|
||||
JKQTPXYLineErrorGraph(JKQTPlotter* parent);
|
||||
|
||||
/** \brief get the maximum and minimum x-value of the graph
|
||||
*
|
||||
* The result is given in the two parameters which are call-by-reference parameters!
|
||||
*/
|
||||
virtual bool getXMinMax(double& minx, double& maxx, double& smallestGreaterZero) override;
|
||||
/** \brief get the maximum and minimum y-value of the graph
|
||||
*
|
||||
* The result is given in the two parameters which are call-by-reference parameters!
|
||||
*/
|
||||
virtual bool getYMinMax(double& miny, double& maxy, double& smallestGreaterZero) override;
|
||||
/** \copydoc JKQTPGraph::usesColumn() */
|
||||
virtual bool usesColumn(int c) const override;
|
||||
|
||||
protected:
|
||||
/** \brief this function is used to plot error inidcators before plotting the graphs. */
|
||||
virtual void drawErrorsBefore(JKQTPEnhancedPainter& painter) override;
|
||||
};
|
||||
|
||||
|
||||
|
||||
/*! \brief This implements xy scatter plots (like JKQTPXYLineGraph), but the color and size of the symbols may be taken from a column. with errorbars
|
||||
\ingroup jkqtplotter_linesymbolgraphs_param
|
||||
|
||||
@ -464,4 +375,4 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPXYParametrizedErrorScatterGraph: public JKQTPX
|
||||
|
||||
|
||||
|
||||
#endif // jkqtpgraphs_H
|
||||
#endif // jkqtpscatter_H
|
||||
|
Loading…
Reference in New Issue
Block a user