NEW: stacked barcharts may have a small separation (default 1pt)

NEW: autoscaling for barcharts works now, also when stacked and unstacked charts are combined in one plot
NEW: proper styling for financial graphs in style.ini-files
REWORKED: separation and gruping factor for barcharts on autoscaling
doc update
This commit is contained in:
jkriege2 2024-02-12 22:21:13 +01:00
parent dd940ab569
commit f40bb2010d
116 changed files with 457 additions and 48 deletions

4
.gitignore vendored
View File

@ -183,3 +183,7 @@ Sicherungskopie_*
/doc/images/JKQTPGLabelCenteredOnData_small.png
/lib/jkqtplotter/resources/styles/default.ini.export.png
/lib/jkqtplotter/resources/styles/default.ini.png
/doc/images/JKQTPBarHorizontalAutoscaleMaxWidthOnly_small.png
/doc/images/JKQTPBarHorizontalAutoscaleShrinkOnly_small.png
/doc/images/JKQTPBarVerticalAutoscaleMaxWidthOnly_small.png
/doc/images/JKQTPBarVerticalAutoscaleShrinkOnly_small.png

View File

@ -260,7 +260,7 @@ if(JKQtPlotter_BUILD_EXAMPLES)
stackedbars/JKQTPbarVerticalGraphStacked,JKQTPbarHorizontalGraphStacked/--smallscreenshotplot
scatter/JKQTPXYScatterGraph,JKQTPXYScatterErrorGraph/--smallscreenshotplot
simpletest/JKQTPXYLineGraph/--smallscreenshotplot
barchart/JKQTPBarVerticalGraph,JKQTPBarHorizontalGraph,JKQTPBarVerticalGraphNoBaseline,JKQTPBarHorizontalGraphNoBaseline,JKQTPBarVerticalGraphBaseline,JKQTPBarHorizontalGraphBaseline/--iteratefunctorsteps--smallscreenshotplot
barchart/JKQTPBarVerticalGraph,JKQTPBarHorizontalGraph,JKQTPBarVerticalGraphNoBaseline,JKQTPBarHorizontalGraphNoBaseline,JKQTPBarVerticalGraphBaseline,JKQTPBarHorizontalGraphBaseline,JKQTPBarVerticalAutoscaleShrinkOnly,JKQTPBarHorizontalAutoscaleShrinkOnly,JKQTPBarVerticalAutoscaleMaxWidthOnly,JKQTPBarHorizontalAutoscaleMaxWidthOnly/--iteratefunctorsteps--smallscreenshotplot
barchart_twocolor/JKQTPBarVerticalGraphTwoColorFilling,JKQTPBarHorizontalGraphTwoColorFilling/--smallscreenshotplot
barchart_errorbars/JKQTPBarVerticalErrorGraph,JKQTPBarHorizontalErrorGraph/--smallscreenshotplot
barchart_functorfill/JKQTPBarVerticalGraphFunctorFilling,JKQTPBarHorizontalGraphFunctorFilling/--smallscreenshotplot

View File

@ -64,6 +64,7 @@ Changes, compared to \ref page_whatsnew_V4_0_0 "v4.0.0" include:
<li>FIXED/REWORKED issue <a href="https://github.com/jkriege2/JKQtPlotter/issues/111">#111: Can't write to PDF files with JKQTPlotter::saveImage() when passing a filename ending in ".pdf"</a> (thanks to <a href="https://github.com/fpalazzolo">user:fpalazzolo</a> for reporting):<br/>While fixing this issue, the functions JKQTBasePlotter::saveImage() etc. gained a bool return value to indicate whether sacing was successful.</li>
<li>IMPROVED/FIXED outside space requirements for color bars. Text was sometime too close to the plot border.</li>
<li>REWORKED JKQTBasePlotter::saveData() with a more consistent interface and a bool return value to indicate success or failure + improved documentation, added methods to JKQTPSaveDataAdapter that allow to specify file extensions and an ID for the plugin.</li>
<li>REWORKED: separation and gruping factor for barcharts on autoscaling</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>IMPROVED: added missing override declarations</li>
@ -132,6 +133,8 @@ Changes, compared to \ref page_whatsnew_V4_0_0 "v4.0.0" include:
<li>NEW: JKQTPVectorFieldGraph for drawing "simple" vector fields/quiver plots (+example \ref JKQTPlotterVectorFieldExample)</li>
<li>NEW: JKQTPParametrizedVectorFieldGraph for drawing color-coded vector fields/quiver plots (+example \ref JKQTPParametrizedVectorFieldGraphExample)</li>
<li>NEW: JKQTPFinancialGraph for drawing candlestick or OHLC graphs of financial data, such as stock amrket prices (+example \ref JKQTPlotterFinancialChartExample)</li>
<li>NEW: stacked barcharts may have a small separation (default 1pt)</li>
<li>NEW: autoscaling for barcharts works now, also when stacked and unstacked charts are combined in one plot</li>
</ul></li>
<li>JKQTMathText:<ul>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 61 KiB

After

Width:  |  Height:  |  Size: 65 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 61 KiB

After

Width:  |  Height:  |  Size: 62 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 15 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 15 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 15 KiB

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.8 KiB

After

Width:  |  Height:  |  Size: 3.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 14 KiB

After

Width:  |  Height:  |  Size: 15 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 14 KiB

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 14 KiB

After

Width:  |  Height:  |  Size: 15 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.8 KiB

After

Width:  |  Height:  |  Size: 3.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 17 KiB

After

Width:  |  Height:  |  Size: 18 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.3 KiB

After

Width:  |  Height:  |  Size: 6.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 16 KiB

After

Width:  |  Height:  |  Size: 17 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.1 KiB

After

Width:  |  Height:  |  Size: 6.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.7 KiB

After

Width:  |  Height:  |  Size: 3.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 27 KiB

After

Width:  |  Height:  |  Size: 27 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 27 KiB

After

Width:  |  Height:  |  Size: 27 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 37 KiB

After

Width:  |  Height:  |  Size: 37 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 34 KiB

After

Width:  |  Height:  |  Size: 34 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 28 KiB

After

Width:  |  Height:  |  Size: 28 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 28 KiB

After

Width:  |  Height:  |  Size: 28 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 13 KiB

After

Width:  |  Height:  |  Size: 13 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 33 KiB

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 33 KiB

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 32 KiB

After

Width:  |  Height:  |  Size: 32 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 40 KiB

After

Width:  |  Height:  |  Size: 40 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 5.6 KiB

After

Width:  |  Height:  |  Size: 5.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 211 B

After

Width:  |  Height:  |  Size: 212 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 137 KiB

After

Width:  |  Height:  |  Size: 141 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 142 KiB

After

Width:  |  Height:  |  Size: 146 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 177 KiB

After

Width:  |  Height:  |  Size: 180 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 166 KiB

After

Width:  |  Height:  |  Size: 168 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 151 KiB

After

Width:  |  Height:  |  Size: 154 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 30 KiB

After

Width:  |  Height:  |  Size: 30 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 139 KiB

After

Width:  |  Height:  |  Size: 142 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 105 KiB

After

Width:  |  Height:  |  Size: 112 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 158 KiB

After

Width:  |  Height:  |  Size: 160 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 30 KiB

After

Width:  |  Height:  |  Size: 30 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 135 KiB

After

Width:  |  Height:  |  Size: 138 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 30 KiB

After

Width:  |  Height:  |  Size: 30 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 138 KiB

After

Width:  |  Height:  |  Size: 140 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 30 KiB

After

Width:  |  Height:  |  Size: 30 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 140 KiB

After

Width:  |  Height:  |  Size: 146 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 30 KiB

After

Width:  |  Height:  |  Size: 30 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 96 KiB

After

Width:  |  Height:  |  Size: 104 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 30 KiB

After

Width:  |  Height:  |  Size: 30 KiB

View File

@ -66,7 +66,7 @@ std::vector<TCHART*> doExample(JKQTPlotter& plot, const QString& title)
// This function searches all JKQTPBarHorizontalGraph in the current
// plot and sets their shift/scale so they form a nice plot with
// side-by-side groups
graph1->autoscaleBarWidthAndShift(0.75, 1);
graph1->autoscaleBarWidthAndShift();
if (dynamic_cast<JKQTPBarVerticalGraph*>(graph1)!=nullptr) {
// 7. data is grouped into 5 numbere groups (1..5), but we also have string
@ -126,6 +126,8 @@ int main(int argc, char* argv[])
plotV.getYAxis()->setShowZeroAxis(false);
plotH.getXAxis()->setShowZeroAxis(false);
plotH.getYAxis()->setShowZeroAxis(false);
plotV.redrawPlot();
plotH.redrawPlot();
});
app.addExportStepFunctor([&](){
@ -139,6 +141,42 @@ int main(int argc, char* argv[])
plotV.getYAxis()->setShowZeroAxis(false);
plotH.getXAxis()->setShowZeroAxis(false);
plotH.getYAxis()->setShowZeroAxis(false);
plotV.redrawPlot();
plotH.redrawPlot();
});
app.addExportStepFunctor([&](){
for (auto g: gV) {
g->setDrawBaseline(false);
}
for (auto g: gH) {
g->setDrawBaseline(false);
}
gV[0]->autoscaleBarWidthAndShift(1,0.9);
gH[0]->autoscaleBarWidthAndShift(1,0.9);
plotV.getXAxis()->setShowZeroAxis(false);
plotV.getYAxis()->setShowZeroAxis(false);
plotH.getXAxis()->setShowZeroAxis(false);
plotH.getYAxis()->setShowZeroAxis(false);
plotV.redrawPlot();
plotH.redrawPlot();
});
app.addExportStepFunctor([&](){
for (auto g: gV) {
g->setDrawBaseline(false);
}
for (auto g: gH) {
g->setDrawBaseline(false);
}
gV[0]->autoscaleBarWidthAndShift(0.75,1);
gH[0]->autoscaleBarWidthAndShift(0.75,1);
plotV.getXAxis()->setShowZeroAxis(false);
plotV.getYAxis()->setShowZeroAxis(false);
plotH.getXAxis()->setShowZeroAxis(false);
plotH.getYAxis()->setShowZeroAxis(false);
plotV.redrawPlot();
plotH.redrawPlot();
});
return app.exec();
}

View File

@ -97,10 +97,10 @@ This test results in the following numbers (on my AMD Ryzen5 8/16-core laptop):
<b>VERSION:</b> 5.0.0
<b>BUILD MODE:</b> Debug
<u><b>SERIAL RESULTS:</b></u><br/>runtime, overall = 13010.9ms<br/>single runtimes = (542.0 +/- 1807.8) ms<br/>speedup = 1.00x<br/>threads / available = 1 / 16<br/><br/><br/>
<u><b>SERIAL RESULTS:</b></u><br/>runtime, overall = 12224.1ms<br/>single runtimes = (509.2 +/- 1614.8) ms<br/>speedup = 1.00x<br/>threads / available = 1 / 16<br/><br/><br/>
<u><b>PARALLEL RESULTS:</b></u><br/>
runtime, overall = 2652.2ms<br/>single runtimes = (690.9 +/- 79.5) ms<br/>speedup = 6.25x<br/>threads / available = 8 / 16<br/>batch runs = 3<br/><br/><b>speedup vs. serial = 4.9x</b>
runtime, overall = 2905.3ms<br/>single runtimes = (746.9 +/- 66.6) ms<br/>speedup = 6.17x<br/>threads / available = 8 / 16<br/>batch runs = 3<br/><br/><b>speedup vs. serial = 4.2x</b>
[comment]:RESULTS_END

View File

@ -5,6 +5,7 @@
#include "jkqtplotter/graphs/jkqtpbarchart.h"
#include "jkqtplotter/graphs/jkqtpimage.h"
#include "jkqtplotter/graphs/jkqtpgeometric.h"
#include "jkqtplotter/graphs/jkqtpfinancial.h"
#include "jkqtplotter/graphs/jkqtpgeoannotations.h"
#include "jkqtplotter/graphs/jkqtpboxplot.h"
#include "jkqtplotter/graphs/jkqtpfilledcurve.h"
@ -30,6 +31,7 @@ inline void setupGridPrintingAndDatastores(QVector<JKQTBasePlotter*>& plots, QSi
}
inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
JKQTPFinancialGraph::clearColorAssignStore();
// 0. get a pointer to the internal datastore (for convenience)
JKQTPDatastore* ds=plots.first()->getDatastore();
@ -41,7 +43,7 @@ inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
ds->clear();
// 2. now we create data for a simple plot (a sine curve)
QVector<double> X, Y1, Y2, img, X3, Y3, Y3err, Xbar, Ybar, Ybar2, Ybar3, Y4, Y5, XImp, YImp, XBP, MinBP, Q25BP, MeanBP, MedianBP, Q75BP, MaxBP;
QVector<double> X, Y1, Y2, img, X3, Y3, Y3err, Xbar, Ybar, Ybar2, Ybar2s1, Ybar2s2, Ybar3, Y4, Y5, XImp, YImp, XBP, MinBP, Q25BP, MeanBP, MedianBP, Q75BP, MaxBP, TFin, OFin1,CFin1,LFin1,HFin1, OFin2,CFin2,LFin2,HFin2;
const int Ndata=50;
for (int i=0; i<Ndata; i++) {
const double x=double(i)/double(Ndata)*8.0*JKQTPSTATISTICS_PI;
@ -58,7 +60,9 @@ inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
if (i>0 && i%16==0) {
Xbar<<x;
Ybar<<(double(i+5)/double(Ndata)*(1.5));
Ybar2<<(double(i+5)/double(Ndata)*(1.2));
Ybar2<<(double(i+5)/double(Ndata)*(0.6));
Ybar2s1 << 0.1+(double(i+5)/double(Ndata)*(0.3));
Ybar2s2 << 0.5-(double(i+5)/double(Ndata)*(0.4));
Ybar3<<(3.0-(double(i+5)/double(Ndata)*(3.7)));
}
if (i%8==0) {
@ -74,6 +78,17 @@ inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
Q75BP<<(i*1.3+6.0);
MaxBP<<(i*1.35+7.5);
}
if (i<=10) {
TFin << (i+1);
OFin1 << CFin1.value(CFin1.size()-1,30)+3.0*sin(i);
CFin1 << OFin1.value(OFin1.size()-1,30)+3.0*cos(i);
HFin1 << qMax(OFin1.last(),CFin1.last())+2;
LFin1 << qMin(OFin1.last(),CFin1.last())-2;
OFin2 << CFin2.value(CFin2.size()-1,20)+2.0*cos(i);
CFin2 << OFin2.value(OFin2.size()-1,20)+2.0*sin(i);
HFin2 << qMax(OFin2.last(),CFin2.last())+2;
LFin2 << qMin(OFin2.last(),CFin2.last())-2;
}
}
auto fgauss=[](double x, double y, double x0, double y0, double sx, double sy) {
return exp(-2.0*(x-x0)*(x-x0)/sx/sx-2.0*(y-y0)*(y-y0)/sy/sy);
@ -99,6 +114,8 @@ inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
size_t columnXbar=ds->addCopiedColumn(Xbar, "xbar");
size_t columnYbar=ds->addCopiedColumn(Ybar, "ybar");
size_t columnYbar2=ds->addCopiedColumn(Ybar2, "Ybar2");
size_t columnYbar2s1=ds->addCopiedColumn(Ybar2s1, "Ybar2, stack1");
size_t columnYbar2s2=ds->addCopiedColumn(Ybar2s2, "Ybar2, stack2");
size_t columnYbar3=ds->addCopiedColumn(Ybar3, "Ybar3");
size_t columnY4=ds->addCopiedColumn(Y4, "y4");
size_t columnY5=ds->addCopiedColumn(Y5, "y5");
@ -113,6 +130,8 @@ inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
size_t columnQ75BP=ds->addCopiedColumn(Q75BP, "Q75BP");
size_t columnMaxBP=ds->addCopiedColumn(MaxBP, "MaxBP");
size_t columnFinT=ds->addCopiedColumn(TFin, "FinT");
// 4. create diverse graphs in the plot:
JKQTPFilledCurveXGraph* graphf4=new JKQTPFilledCurveXGraph(plots[2]);
graphf4->setXColumn(columnX);
@ -201,18 +220,33 @@ inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
graphb->setTitle(QObject::tr("barchart"));
plots[3]->addGraph(graphb);
JKQTPBarVerticalGraph* graphb2=new JKQTPBarVerticalGraph(plots[3]);
JKQTPBarVerticalStackableGraph* graphb2=new JKQTPBarVerticalStackableGraph(plots[3]);
graphb2->setXColumn(columnXbar);
graphb2->setYColumn(columnYbar2);
graphb2->setTitle(QObject::tr("2^{nd} barchart"));
plots[3]->addGraph(graphb2);
JKQTPBarVerticalStackableGraph* graphb2s1=new JKQTPBarVerticalStackableGraph(plots[3]);
graphb2s1->setXColumn(columnXbar);
graphb2s1->setYColumn(columnYbar2s1);
graphb2s1->setTitle(QObject::tr("3^{rd} barchart"));
plots[3]->addGraph(graphb2s1);
graphb2s1->stackUpon(graphb2);
JKQTPBarVerticalStackableGraph* graphb2s2=new JKQTPBarVerticalStackableGraph(plots[3]);
graphb2s2->setXColumn(columnXbar);
graphb2s2->setYColumn(columnYbar2s2);
graphb2s2->setTitle(QObject::tr("4^{th} barchart"));
plots[3]->addGraph(graphb2s2);
graphb2s2->stackUpon(graphb2s1);
JKQTPBarVerticalGraph* graphb3=new JKQTPBarVerticalGraph(plots[3]);
graphb3->setXColumn(columnXbar);
graphb3->setYColumn(columnYbar3);
graphb3->setTitle(QObject::tr("3^{nd} barchart"));
graphb3->setTitle(QObject::tr("5^{th} barchart"));
plots[3]->addGraph(graphb3);
graphb3->autoscaleBarWidthAndShiftSeparatedGroups();
plots[3]->getMainKey()->setPosition(JKQTPKeyInsideTopLeft);
JKQTPBoxplotVerticalGraph* graphBP=new JKQTPBoxplotVerticalGraph(plots[plots.size()/2]);
@ -225,6 +259,26 @@ inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
graphBP->setMaxColumn(columnMaxBP);
plots[plots.size()/2]->addGraph(graphBP);
JKQTPFinancialGraph* graphF1=new JKQTPFinancialGraph(plots[plots.size()/2+1]);
graphF1->setXColumn(columnFinT);
graphF1->setOpenColumn(ds->addCopiedColumn(OFin1, "OFin1"));
graphF1->setHighColumn(ds->addCopiedColumn(HFin1, "HFin1"));
graphF1->setLowColumn(ds->addCopiedColumn(LFin1, "LFin1"));
graphF1->setCloseColumn(ds->addCopiedColumn(CFin1, "CFin1"));
graphF1->setGraphType(JKQTPFinancialGraph::OHLC);
graphF1->setTitle("OHLC");
plots[plots.size()/2+1]->addGraph(graphF1);
JKQTPFinancialGraph* graphF2=new JKQTPFinancialGraph(plots[plots.size()/2+1]);
graphF2->setXColumn(columnFinT);
graphF2->setOpenColumn(ds->addCopiedColumn(OFin2, "OFin2"));
graphF2->setHighColumn(ds->addCopiedColumn(HFin2, "HFin2"));
graphF2->setLowColumn(ds->addCopiedColumn(LFin2, "LFin2"));
graphF2->setCloseColumn(ds->addCopiedColumn(CFin2, "CFin2"));
graphF2->setGraphType(JKQTPFinancialGraph::CandleStick);
graphF2->setTitle("CandleStick");
plots[plots.size()/2+1]->addGraph(graphF2);
auto plotgeo=*(plots.rbegin()+1);
JKQTPGeoSymbol* annotSym=new JKQTPGeoSymbol(plotgeo, -1.5, 3);
plotgeo->addGraph(annotSym);
@ -253,6 +307,8 @@ inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
plotgeo->setMaintainAxisAspectRatio(true);
plotgeo->getXAxis()->setRange(-2.5,4);
plotgeo->getYAxis()->setRange(-2.5,4);
plots[plots.size()/2+1]->getXAxis()->setAxisLabel("time");
plots[plots.size()/2+1]->getYAxis()->setAxisLabel("price [\\euro]");
plots[0]->setPlotLabel("Line Graphs");
@ -260,6 +316,7 @@ inline void buildPlots(QVector<JKQTBasePlotter*>& plots) {
plots[2]->setPlotLabel("Filled Graphs");
plots[3]->setPlotLabel("Bar Charts");
plots[plots.size()/2]->setPlotLabel("Boxplots");
plots[plots.size()/2+1]->setPlotLabel("Financial Graphs");
plotgeo->setPlotLabel("Geometry & Annotations");
plots.last()->setPlotLabel("Image Plot");

View File

@ -68,9 +68,9 @@ QMap<int, JKQTPImageTools::LUTData > JKQTPImageTools::getDefaultLUTs() {
lst<<jkqtp_qRgbOpaque(0xBB0000);
lst<<jkqtp_qRgbOpaque(0x00C11D);
lst<<jkqtp_qRgbOpaque(0x0039D6);
lst<<jkqtp_qRgbOpaque(0xFFDD00);
lst<<jkqtp_qRgbOpaque(0xC05FFF);
lst<<jkqtp_qRgbOpaque(0xDE7704);
lst<<jkqtp_qRgbOpaque(0xC05FFF);
lst<<jkqtp_qRgbOpaque(0xFFDD00);
lst<<jkqtp_qRgbOpaque(0x03039A);

View File

@ -25,6 +25,7 @@
#include <QDebug>
#include <iostream>
#include "jkqtplotter/jkqtptools.h"
#include "jkqtcommon/jkqtpstringtools.h"
#include "jkqtplotter/jkqtplotter.h"
#define SmallestGreaterZeroCompare_xvsgz() if ((xvsgz>10.0*DBL_MIN)&&((smallestGreaterZero<10.0*DBL_MIN) || (xvsgz<smallestGreaterZero))) smallestGreaterZero=xvsgz;
@ -58,6 +59,8 @@ void JKQTPBarVerticalGraph::draw(JKQTPEnhancedPainter& painter) {
const QPen p=getLinePenForRects(painter, parent);
const auto fillFunctor=std::bind(constructFillBrushFunctor(), std::placeholders::_1, std::placeholders::_2, std::ref(painter), this);
const double stackSep=parent->pt2px(painter, getStackSeparation());
const double lw=parent->pt2px(painter, getLineWidth());
int imax=0;
int imin=0;
@ -88,7 +91,7 @@ void JKQTPBarVerticalGraph::draw(JKQTPEnhancedPainter& painter) {
if (hasStackPar) {
double stackLastY=getParentStackedMax(i);
const double yvold=yv;
yv0=transformY(stackLastY)-(getLineWidth());
yv0=transformY(stackLastY)-stackSep;
yv=stackLastY+yvold;
}
if (sr<0 && lr<0) { // only one x-value
@ -239,6 +242,9 @@ void JKQTPBarHorizontalGraph::draw(JKQTPEnhancedPainter& painter) {
const QPen p=getLinePenForRects(painter, parent);
const auto fillFunctor=std::bind(constructFillBrushFunctor(), std::placeholders::_1, std::placeholders::_2, std::ref(painter), this);
const double stackSep=parent->pt2px(painter, getStackSeparation());
const double lw=parent->pt2px(painter, getLineWidth());
int imax=0;
int imin=0;
@ -270,7 +276,7 @@ void JKQTPBarHorizontalGraph::draw(JKQTPEnhancedPainter& painter) {
if (hasStackPar) {
double stackLastX=getParentStackedMax(i);
const double xvold=xv;
xv0=transformX(stackLastX)+(getLineWidth());
xv0=transformX(stackLastX)+stackSep;
xv=stackLastX+xvold;
}
@ -600,6 +606,13 @@ double JKQTPBarVerticalStackableGraph::getStackedMax(int index) const
}
}
JKQTPBarGraphBase *JKQTPBarVerticalStackableGraph::getBottomOfStack()
{
if (stackParent) return stackParent->getBottomOfStack();
else return this;
}
JKQTPBarHorizontalStackableGraph::JKQTPBarHorizontalStackableGraph(JKQTBasePlotter *parent):
JKQTPBarHorizontalGraph(parent), stackParent(nullptr)
{
@ -647,6 +660,13 @@ double JKQTPBarHorizontalStackableGraph::getStackedMax(int index) const
}
}
JKQTPBarGraphBase *JKQTPBarHorizontalStackableGraph::getBottomOfStack()
{
if (stackParent) return stackParent->getBottomOfStack();
else return this;
}
double JKQTPBarHorizontalStackableGraph::getParentStackedMax(int index) const
{
if (stackParent) {

View File

@ -265,7 +265,7 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarHorizontalErrorGraph: public JKQTPBarHorizo
*
* \see JKQTPBarVerticalGraph, \ref JKQTPlotterStackedBarChart
*/
class JKQTPLOTTER_LIB_EXPORT JKQTPBarVerticalStackableGraph: public JKQTPBarVerticalGraph {
class JKQTPLOTTER_LIB_EXPORT JKQTPBarVerticalStackableGraph: public JKQTPBarVerticalGraph, public JKQTPBarGraphStackInternalInterface {
Q_OBJECT
public:
/** \brief class constructor */
@ -293,10 +293,13 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarVerticalStackableGraph: public JKQTPBarVert
double getParentStackedMax(int index) const ;
/** \brief returns \c true, if a stack parent is set (if available) */
bool hasStackParent() const ;
/** \copydoc JKQTPBarGraphBase::hasStackParent() */
virtual bool hasStackParent() const override;
/** \brief used to generate stacked plots: returns the upper boundary of this plot in a stack, for the index-th datapoint */
double getStackedMax(int index) const;
/** \copydoc JKQTPBarGraphStackInternalInterface::getBottomOfStack() */
virtual JKQTPBarGraphBase* getBottomOfStack() override;
};
@ -315,7 +318,7 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarVerticalStackableGraph: public JKQTPBarVert
*
* \see JKQTPBarHorizontalGraph, \ref JKQTPlotterStackedBarChart
*/
class JKQTPLOTTER_LIB_EXPORT JKQTPBarHorizontalStackableGraph: public JKQTPBarHorizontalGraph {
class JKQTPLOTTER_LIB_EXPORT JKQTPBarHorizontalStackableGraph: public JKQTPBarHorizontalGraph, public JKQTPBarGraphStackInternalInterface {
Q_OBJECT
public:
/** \brief class constructor */
@ -342,10 +345,12 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarHorizontalStackableGraph: public JKQTPBarHo
/** \brief used to generate stacked plots: returns the upper boundary of the parent plot in a stack, for the index-th datapoint */
virtual double getParentStackedMax(int index) const override;
/** \brief returns \c true, if a stack parent is set (if available) */
/** \copydoc JKQTPBarGraphBase::hasStackParent() */
virtual bool hasStackParent() const override;
/** \brief used to generate stacked plots: returns the upper boundary of this plot in a stack, for the index-th datapoint */
double getStackedMax(int index) const;
/** \copydoc JKQTPBarGraphStackInternalInterface::getBottomOfStack() */
virtual JKQTPBarGraphBase* getBottomOfStack() override;
};

View File

@ -40,7 +40,8 @@ JKQTPBarGraphBase::JKQTPBarGraphBase(JKQTBasePlotter* parent):
shift(0),
rectRadiusAtValue(0),
rectRadiusAtBaseline(0),
m_drawBaseline(parent->getCurrentPlotterStyle().graphsStyle.barchartStyle.drawBaseline),
m_drawBaseline(false),
m_stackSeparation(1),
m_fillMode(FillMode::SingleFilling),
m_lineColorDerivationModeForSpecialFill(parent->getCurrentPlotterStyle().graphsStyle.barchartStyle.graphColorDerivationMode),
m_useCustomDrawFunctor(false)
@ -48,11 +49,15 @@ JKQTPBarGraphBase::JKQTPBarGraphBase(JKQTBasePlotter* parent):
initFillStyle(parent, parentPlotStyle, JKQTPPlotStyleType::Barchart);
initLineStyle(parent, parentPlotStyle, JKQTPPlotStyleType::Barchart);
m_fillStyleBelow.initFillStyleInvertedColor(this);
m_baselineStyle.setLineColor(parent->getCurrentPlotterStyle().xAxisStyle.colorZeroAxis);
m_baselineStyle.setLineStyle(Qt::SolidLine);
if (parent) {
m_baselineStyle.setLineColor(parent->getCurrentPlotterStyle().xAxisStyle.colorZeroAxis);
m_baselineStyle.setLineWidth(parent->getCurrentPlotterStyle().xAxisStyle.lineWidthZeroAxis);
rectRadiusAtBaseline= parent->getCurrentPlotterStyle().graphsStyle.barchartStyle.defaultRectRadiusAtBaseline;
rectRadiusAtValue= parent->getCurrentPlotterStyle().graphsStyle.barchartStyle.defaultRectRadiusAtValue;
m_drawBaseline=parent->getCurrentPlotterStyle().graphsStyle.barchartStyle.drawBaseline;
m_stackSeparation=parent->getCurrentPlotterStyle().graphsStyle.barchartStyle.stackSeparation;
}
}
@ -86,11 +91,18 @@ QColor JKQTPBarGraphBase::getKeyLabelColor() const {
void JKQTPBarGraphBase::autoscaleBarWidthAndShift(double maxWidth, double shrinkFactor)
{
if (parent) {
auto isStackBase=[](JKQTPBarGraphBase* other) {
const auto vg=dynamic_cast<JKQTPBarGraphStackInternalInterface*>(other);
return (vg && !other->hasStackParent());
};
auto isStackable=[](JKQTPBarGraphBase* other) {
return dynamic_cast<JKQTPBarGraphStackInternalInterface*>(other);
};
double cntH=0;
for (size_t i=0; i<parent->getGraphCount(); i++) {
JKQTPPlotElement* g=parent->getGraph(i);
JKQTPBarGraphBase* gb=qobject_cast<JKQTPBarGraphBase*>(g);
if (gb && considerForAutoscaling(gb)) {
if (gb && considerForAutoscaling(gb) && (isStackBase(gb) || !isStackable(gb))) {
cntH++;
}
@ -102,23 +114,37 @@ void JKQTPBarGraphBase::autoscaleBarWidthAndShift(double maxWidth, double shrink
for (size_t i=0; i<parent->getGraphCount(); i++) {
JKQTPPlotElement* g=parent->getGraph(i);
JKQTPBarGraphBase* gb=qobject_cast<JKQTPBarGraphBase*>(g);
if (gb && considerForAutoscaling(gb)) {
if (gb && considerForAutoscaling(gb) && (isStackBase(gb) || !isStackable(gb))) {
if (cntH>1) {
gb->width=widthH;
gb->shift=h-0.5;
h=h+dH;
} else {
gb->width=maxWidth;
gb->shift=0.0;
}
}
}
for (size_t i=0; i<parent->getGraphCount(); i++) {
JKQTPPlotElement* g=parent->getGraph(i);
JKQTPBarGraphStackInternalInterface* gbo=dynamic_cast<JKQTPBarGraphStackInternalInterface*>(g);
JKQTPBarGraphBase* gb=qobject_cast<JKQTPBarGraphBase*>(g);
if (gbo && gb) {
auto stackBottom=gbo->getBottomOfStack();
if (g!=stackBottom && stackBottom) {
gb->width=stackBottom->width;
gb->shift=stackBottom->shift;
}
}
}
}
}
void JKQTPBarGraphBase::autoscaleBarWidthAndShiftSeparatedGroups(double groupWidth) {
autoscaleBarWidthAndShift(groupWidth, 1);
autoscaleBarWidthAndShift(groupWidth);
}
@ -184,11 +210,21 @@ void JKQTPBarGraphBase::setDrawBaseline(bool __value)
m_drawBaseline=__value;
}
void JKQTPBarGraphBase::setStackSeparation(double __value)
{
m_stackSeparation=__value;
}
bool JKQTPBarGraphBase::getDrawBaseline() const
{
return this->m_drawBaseline;
}
double JKQTPBarGraphBase::getStackSeparation() const
{
return m_stackSeparation;
}
JKQTPGraphLineStyleMixin &JKQTPBarGraphBase::baselineStyle()
{
return m_baselineStyle;

View File

@ -223,6 +223,8 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarGraphBase: public JKQTPXYBaselineGraph, pub
bool usesCustomDrawFunctor() const;
/** \copydoc m_drawBaseline */
bool getDrawBaseline() const;
/** \copydoc m_stackSeparation */
double getStackSeparation() const;
/** \copydoc m_baselineStyle */
JKQTPGraphLineStyleMixin &baselineStyle();
/** \copydoc m_baselineStyle */
@ -255,10 +257,31 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarGraphBase: public JKQTPXYBaselineGraph, pub
* \param shrinkFactor factor, by which the bar are shrinked compared to the available space
*
* \note This function will scale ALL graphs of the parent plot, which were derived from JKQTPBarHorizontalGraph, that match in orientation (as returned by isHorizontal() ).
*
* Using \c autoscaleBarWidthAndSHift(0.75,1.0) You can separate the different groups by soe distance, but the bars touch each other:
*
* \image html JKQTPBarVerticalAutoscaleMaxWidthOnly.png
*
* On the other hand, using the other extreme \c autoscaleBarWidthAndSHift(1.0,0.9) there is no grouping of the bars, but they have a slight distance between each other.
*
* \image html JKQTPBarVerticalAutoscaleShrinkOnly.png
*
* Finally the default parameters \c autoscaleBarWidthAndSHift(0.75,0.9) will lead to a separation of the bars AND a grouping:
*
* \image html JKQTPBarVerticalGraph.png
*
*/
virtual void autoscaleBarWidthAndShift(double maxWidth=0.9, double shrinkFactor=0.8);
virtual void autoscaleBarWidthAndShift(double maxWidth=0.75, double shrinkFactor=0.9);
/** \brief equivalent to \c autoscaleBarWidthAndShift(groupWidth,1);
/** \brief equivalent to \c autoscaleBarWidthAndShift(groupWidth,0.9);
*
* The default parameters \c autoscaleBarWidthAndShiftSeparatedGroups(0.75) will lead to a separation of the bars AND a grouping:
*
* \image html JKQTPBarVerticalGraph.png
*
* On the other hand, using \c autoscaleBarWidthAndShiftSeparatedGroups(1.0) there is no grouping of the bars, but they have a slight distance between each other.
*
* \image html JKQTPBarVerticalAutoscaleShrinkOnly.png
*/
void autoscaleBarWidthAndShiftSeparatedGroups(double groupWidth=0.75);
/** \copydoc shift */
@ -268,6 +291,8 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarGraphBase: public JKQTPXYBaselineGraph, pub
/** \copydoc m_drawBaseline */
void setDrawBaseline(bool __value);
/** \copydoc m_stackSeparation */
void setStackSeparation(double __value);
/** \copydoc rectRadiusAtValue */
void setRectRadiusAtValue(double __value);
/** \copydoc rectRadiusAtBaseline */
@ -302,13 +327,19 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarGraphBase: public JKQTPXYBaselineGraph, pub
/** \brief the width of the bargraphs, relative to the distance between the current and the next x-value
*
* See the following graphic to understand this concept:
* \image html bargraph_basics.png
* \image html bargraph_basics_width.png
*
* \note this parameter can be combined with shift !
*
* \see setWidth(), getWidth(), setShift(), getShift(), shift, autoscaleBarWidthAndShift(), autoscaleBarWidthAndShiftSeparatedGroups()
*/
double width;
/** \brief the shift of the bargraphs, relative to the distance between the current and the next x-value
*
* See the following graphic to understand this concept:
* \image html bargraph_basics.png
*
* \see setShift(), getShift(), setWidth(), getWidth(), autoscaleBarWidthAndShift(), autoscaleBarWidthAndShiftSeparatedGroups()
*/
double shift;
/** \brief corner radius (in pt) for bars at the "value" end */
@ -329,6 +360,8 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarGraphBase: public JKQTPXYBaselineGraph, pub
* \see baselineStyle() , setDrawBaseline() , m_baselineStyle
*/
bool m_drawBaseline;
/** \brief separation (in pt) between two bars in a stack of bars */
double m_stackSeparation;
/** \brief specifies how the area of the graph is filles
*
* \note If any fill style other than FillStyle::SingleFill is used, the peroperty m_lineColorDerivationModeForSpecialFill
@ -411,7 +444,9 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarGraphBase: public JKQTPXYBaselineGraph, pub
virtual FillBrushFunctor constructFillBrushFunctor() const;
/** \brief this function is used by autoscaleBarWidthAndShift() to determine whether a given graph shall be taken into account when autoscaling.
* Typically this returns \c true for all JKQTPBarGraphBase-derved objects with the same orientation (horizontal or vertical) */
* Typically this returns \c true for all JKQTPBarGraphBase-derived objects with the same orientation (horizontal or vertical). For stacked
* graphs it excludes everything except the bottom of the stack
*/
virtual bool considerForAutoscaling( JKQTPBarGraphBase* other) const=0;
/** \brief used to generate stacked plots: returns the upper boundary of the parent plot in a stack, for the index-th datapoint */
@ -434,7 +469,23 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPBarGraphBase: public JKQTPXYBaselineGraph, pub
/** \brief This is an interface-class for all stackable bargraphs ... it is used internally for autoscaling only
* \ingroup jkqtplotter_barcharts
*
* \c dynamic_cast 'ing to this indicates that a barchart is stackable.
*
*
*/
class JKQTPLOTTER_LIB_EXPORT JKQTPBarGraphStackInternalInterface {
public:
inline virtual ~JKQTPBarGraphStackInternalInterface() {};
protected:
/** \brief returns the barchart at the bottom of this stack (i.e. traverses the stack until there are no more parents */
virtual JKQTPBarGraphBase* getBottomOfStack()=0;
friend class JKQTPBarGraphBase;
};

View File

@ -31,7 +31,11 @@
QSet<JKQTBasePlotter*> JKQTPFinancialGraph::parentsAlreadySeen={};
void JKQTPFinancialGraph::clearColorAssignStore() {
parentsAlreadySeen.clear();
}
JKQTPFinancialGraph::JKQTPFinancialGraph(JKQTBasePlotter* parent):
@ -45,24 +49,31 @@ JKQTPFinancialGraph::JKQTPFinancialGraph(JKQTBasePlotter* parent):
shift(0)
{
m_fillStylePositive.initFillStyle(parent, parentPlotStyle, JKQTPPlotStyleType::Boxplot);
m_fillStyleNegative.initFillStyleInvertedColor(&m_fillStylePositive);
//qDebug()<<"1: pos: "<<m_lineStylePositive.getLineColor()<<", fill: "<<m_fillStylePositive.getFillColor();
//qDebug()<<"1: neg: "<<m_lineStyleNegative.getLineColor()<<", fill: "<<m_fillStyleNegative.getFillColor();
m_fillStylePositive.initFillStyle(parent, parentPlotStyle, JKQTPPlotStyleType::FinancialPositive);
m_fillStyleNegative.initFillStyle(parent, parentPlotStyle, JKQTPPlotStyleType::FinancialNegative);
m_lineStylePositive.initLineStyle(parent, parentPlotStyle, JKQTPPlotStyleType::Boxplot);
m_lineStyleNegative.initLineStyle(parent, parentPlotStyle, JKQTPPlotStyleType::Boxplot);
m_lineStyleNegative.setLineColor(m_fillStyleNegative.getFillColor());
m_lineStylePositive.initLineStyle(parent, parentPlotStyle, JKQTPPlotStyleType::FinancialPositive);
m_lineStyleNegative.initLineStyle(parent, parentPlotStyle, JKQTPPlotStyleType::FinancialNegative);
//qDebug()<<"2: pos: "<<m_lineStylePositive.getLineColor()<<", fill: "<<m_fillStylePositive.getFillColor();
//qDebug()<<"2: neg: "<<m_lineStyleNegative.getLineColor()<<", fill: "<<m_fillStyleNegative.getFillColor();
static QSet<JKQTBasePlotter*> parentsAlreadySeen;
if (!parentsAlreadySeen.contains(parent)) {
if (parent && !parentsAlreadySeen.contains(parent)) {
// ensure, the first graph in a plot has default red/green colors
// further plots will have colors
m_fillStylePositive.setFillColor(QColor("darkgreen"));
m_fillStyleNegative.setFillColor(QColor("maroon"));
m_lineStylePositive.setLineColor(QColor("darkgreen"));
m_lineStyleNegative.setLineColor(QColor("maroon"));
//qDebug()<<"FIRST!"<<parent;
m_fillStylePositive.setFillColor(parent->getCurrentPlotterStyle().graphsStyle.financialStyle.positiveDefaultColor);
m_fillStyleNegative.setFillColor(parent->getCurrentPlotterStyle().graphsStyle.financialStyle.negativeDefaultColor);
m_lineStylePositive.setLineColor(parent->getCurrentPlotterStyle().graphsStyle.financialStyle.positiveDefaultColor);
m_lineStyleNegative.setLineColor(parent->getCurrentPlotterStyle().graphsStyle.financialStyle.negativeDefaultColor);
}
parentsAlreadySeen.insert(parent);
//qDebug()<<"3: pos: "<<m_lineStylePositive.getLineColor()<<", fill: "<<m_fillStylePositive.getFillColor();
//qDebug()<<"3: neg: "<<m_lineStyleNegative.getLineColor()<<", fill: "<<m_fillStyleNegative.getFillColor();
}

View File

@ -166,6 +166,7 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPFinancialGraph: public JKQTPXGraph {
Q_PROPERTY(int lowColumn READ getLowColumn WRITE setLowColumn)
Q_PROPERTY(FinancialGraphType graphType READ getGraphType WRITE setGraphType)
static void clearColorAssignStore();
public Q_SLOTS:
/** \brief finds all financial charts of the same orientation and determines width and shift, so they stand side by side
@ -260,6 +261,7 @@ class JKQTPLOTTER_LIB_EXPORT JKQTPFinancialGraph: public JKQTPXGraph {
void setLowColumn (size_t __value);
protected:
static QSet<JKQTBasePlotter*> parentsAlreadySeen;
/** \brief type of the financial graph (OHLC or candle-stick)
*
* \see setGraphType(), getGraphType(), FinancialGraphType

View File

@ -1392,7 +1392,7 @@ void JKQTPXGraph::intSortData()
if (parent==nullptr) return ;
if (sortData==JKQTPXYLineGraph::Unsorted) return ;
if (sortData==JKQTPXGraph::Unsorted) return ;
JKQTPDatastore* datastore=parent->getDatastore();
int imin=0;

View File

@ -35,6 +35,14 @@ void JKQTGraphsSpecificStyleProperties::modifyForDefaultStyle(JKQTPPlotStyleType
switch(type) {
case JKQTPPlotStyleType::Default:
break;
case JKQTPPlotStyleType::FinancialNegative:
defaultLineWidth=1;
fillColorDerivationMode=JKQTPColorDerivationMode::JKQTPFFCMSameColor;
break;
case JKQTPPlotStyleType::FinancialPositive:
defaultLineWidth=1;
fillColorDerivationMode=JKQTPColorDerivationMode::JKQTPFFCMSameColor;
break;
case JKQTPPlotStyleType::Filled:
fillColorDerivationMode=JKQTPColorDerivationMode::JKQTPFFCMLighterAndTransparentColor;
break;
@ -95,6 +103,7 @@ void JKQTGraphsSpecificStyleProperties::saveSettings(QSettings &settings, const
settings.setValue(group+"error_color_mode", JKQTPColorDerivationMode2String(errorColorDerivationMode));
settings.setValue(group+"error_fill_color_mode", JKQTPColorDerivationMode2String(errorFillColorDerivationMode));
settings.setValue(group+"symbol_fill_color_mode", JKQTPColorDerivationMode2String(symbolFillColorDerivationMode));
}
@ -204,6 +213,7 @@ JKQTGraphsBaseStyle::JKQTGraphsBaseStyle(const JKQTBasePlotterStyle& parent):
impulseStyle(parent),
geometricStyle(parent),
annotationStyle(parent),
financialStyle(parent),
defaultPalette(JKQTPMathImageColorPalette::JKQTPMathImageMATLAB),
defaultGraphColors(getDefaultGraphColors()),
defaultGraphPenStyles(getDefaultGraphPenStyles()),
@ -334,6 +344,7 @@ void JKQTGraphsBaseStyle::loadSettings(const QSettings &settings, const QString
impulseStyle.loadSettings(settings, group+"graphs_impulses/", JKQTImpulseSpecificStyleProperties(parent, defaultGraphStyle));
geometricStyle.loadSettings(settings, group+"graphs_geometric/", JKQTGeometricSpecificStyleProperties(parent, defaultGraphStyle));
annotationStyle.loadSettings(settings, group+"graphs_annotation/", JKQTAnnotationsSpecificStyleProperties(parent, defaultGraphStyle));
financialStyle.loadSettings(settings, group+"graphs_financial/", JKQTFinancialSpecificStyleProperties(parent, defaultGraphStyle));
}
@ -410,6 +421,7 @@ void JKQTGraphsBaseStyle::saveSettings(QSettings &settings, const QString &group
impulseStyle.saveSettings(settings, group+"graphs_impulses/");
geometricStyle.saveSettings(settings, group+"graphs_geometric/");
annotationStyle.saveSettings(settings, group+"graphs_annotation/");
financialStyle.saveSettings(settings, group+"graphs_financial/");
}
const JKQTGraphsSpecificStyleProperties &JKQTGraphsBaseStyle::getGraphStyleByType(JKQTPPlotStyleType type) const
@ -429,6 +441,9 @@ const JKQTGraphsSpecificStyleProperties &JKQTGraphsBaseStyle::getGraphStyleByTyp
return geometricStyle;
case JKQTPPlotStyleType::Annotation:
return annotationStyle;
case JKQTPPlotStyleType::FinancialNegative:
case JKQTPPlotStyleType::FinancialPositive:
return financialStyle;
}
return defaultGraphStyle;
}
@ -439,7 +454,8 @@ JKQTBarchartSpecificStyleProperties::JKQTBarchartSpecificStyleProperties(const J
JKQTGraphsSpecificStyleProperties(JKQTPPlotStyleType::Barchart, parent),
defaultRectRadiusAtValue(0),
defaultRectRadiusAtBaseline(0),
drawBaseline(false)
drawBaseline(false),
stackSeparation(1)
{
}
@ -448,7 +464,8 @@ JKQTBarchartSpecificStyleProperties::JKQTBarchartSpecificStyleProperties(const J
JKQTGraphsSpecificStyleProperties(JKQTPPlotStyleType::Barchart, other),
defaultRectRadiusAtValue(0),
defaultRectRadiusAtBaseline(0),
drawBaseline(false)
drawBaseline(false),
stackSeparation(1)
{
}
@ -459,6 +476,7 @@ void JKQTBarchartSpecificStyleProperties::loadSettings(const QSettings &settings
defaultRectRadiusAtValue=settings.value(group+"radius_at_value", defaultStyle.defaultRectRadiusAtValue).toDouble();
defaultRectRadiusAtBaseline=settings.value(group+"radius_at_baseline", defaultStyle.defaultRectRadiusAtBaseline).toDouble();
drawBaseline=settings.value(group+"draw_baseline", defaultStyle.drawBaseline).toBool();
stackSeparation=settings.value(group+"stack_separation", defaultStyle.stackSeparation).toDouble();
}
void JKQTBarchartSpecificStyleProperties::saveSettings(QSettings &settings, const QString &group) const
@ -467,7 +485,7 @@ void JKQTBarchartSpecificStyleProperties::saveSettings(QSettings &settings, cons
settings.setValue(group+"radius_at_value", defaultRectRadiusAtValue);
settings.setValue(group+"radius_at_baseline", defaultRectRadiusAtBaseline);
settings.setValue(group+"draw_baseline", drawBaseline);
settings.setValue(group+"stack_separation", stackSeparation);
}
@ -499,6 +517,48 @@ void JKQTImpulseSpecificStyleProperties::saveSettings(QSettings &settings, const
}
JKQTFinancialSpecificStyleProperties::JKQTFinancialSpecificStyleProperties(const JKQTBasePlotterStyle &parent):
JKQTGraphsSpecificStyleProperties(JKQTPPlotStyleType::Default, parent),
positiveDefaultColor("darkgreen"),
negativeDefaultColor("maroon"),
negativeGraphColorDerivationMode(JKQTPColorDerivationMode::JKQTPFFCMInvertedColor),
positiveFillStyle(Qt::SolidPattern),
negativeFillStyle(Qt::SolidPattern)
{
defaultLineWidth=1;
}
JKQTFinancialSpecificStyleProperties::JKQTFinancialSpecificStyleProperties(const JKQTBasePlotterStyle &parent, const JKQTGraphsSpecificStyleProperties &other):
JKQTGraphsSpecificStyleProperties(JKQTPPlotStyleType::Default, parent),
positiveDefaultColor("darkgreen"),
negativeDefaultColor("maroon"),
negativeGraphColorDerivationMode(JKQTPColorDerivationMode::JKQTPFFCMInvertedColor),
positiveFillStyle(Qt::SolidPattern),
negativeFillStyle(Qt::SolidPattern)
{
defaultLineWidth=1;
}
void JKQTFinancialSpecificStyleProperties::loadSettings(const QSettings &settings, const QString &group, const JKQTFinancialSpecificStyleProperties &defaultStyle)
{
JKQTGraphsSpecificStyleProperties::loadSettings(settings, group, defaultStyle);
positiveDefaultColor=jkqtp_String2QColor(settings.value(group+"default_positive_color", jkqtp_QColor2String(positiveDefaultColor)).toString());
negativeDefaultColor=jkqtp_String2QColor(settings.value(group+"default_negative_color", jkqtp_QColor2String(negativeDefaultColor)).toString());
positiveFillStyle=JKQTFillStyleSummmary::fromString(settings.value(group+"positive_fill_style", positiveFillStyle.toCSSString()).toString());
negativeFillStyle=JKQTFillStyleSummmary::fromString(settings.value(group+"negative_fill_style", negativeFillStyle.toCSSString()).toString());
negativeGraphColorDerivationMode=String2JKQTPColorDerivationMode(settings.value(group+"negative_graph_color_mode", JKQTPColorDerivationMode2String(defaultStyle.negativeGraphColorDerivationMode)).toString());
}
void JKQTFinancialSpecificStyleProperties::saveSettings(QSettings &settings, const QString &group) const
{
JKQTGraphsSpecificStyleProperties::saveSettings(settings, group);
settings.setValue(group+"default_positive_color", jkqtp_QColor2String(positiveDefaultColor));
settings.setValue(group+"default_negative_color", jkqtp_QColor2String(negativeDefaultColor));
settings.setValue(group+"positive_fill_style", positiveFillStyle.toCSSString());
settings.setValue(group+"negative_fill_style", negativeFillStyle.toCSSString());
settings.setValue(group+"negative_graph_color_mode", JKQTPColorDerivationMode2String(negativeGraphColorDerivationMode));
}
JKQTFillStyleSummmary::JKQTFillStyleSummmary(Qt::BrushStyle style, const QGradient& grad):
brushStyle(style), gradient(grad)
@ -532,3 +592,4 @@ QString JKQTFillStyleSummmary::toCSSString() const
{
return jkqtp_QBrushStyle2String(brushStyle);
}

View File

@ -273,6 +273,8 @@ public:
double defaultRectRadiusAtBaseline;
/** \brief indicates whether to draw a baseline (style is derived from axis style) */
bool drawBaseline;
/** \brief separation between consecutive pars in a stack of bars [in pt] */
double stackSeparation;
};
@ -321,6 +323,61 @@ public:
/** \brief Support Class for JKQTBasePlotter, which summarizes all properties that define the visual styling of impulse/stick graph elements
* \ingroup jkqtpplotter_styling_classes
*
* \see JKQTBasePlotter, \ref jkqtpplotter_styling
*/
class JKQTPLOTTER_LIB_EXPORT JKQTFinancialSpecificStyleProperties: public JKQTGraphsSpecificStyleProperties {
#ifndef JKQTPLOTTER_WORKAROUND_QGADGET_BUG
Q_GADGET
#endif
public:
explicit JKQTFinancialSpecificStyleProperties(const JKQTBasePlotterStyle& parent);
JKQTFinancialSpecificStyleProperties(const JKQTBasePlotterStyle& parent, const JKQTGraphsSpecificStyleProperties& other);
JKQTFinancialSpecificStyleProperties(const JKQTFinancialSpecificStyleProperties& other)=default;
JKQTFinancialSpecificStyleProperties(JKQTFinancialSpecificStyleProperties&& other)=default;
JKQTFinancialSpecificStyleProperties& operator=(const JKQTFinancialSpecificStyleProperties& other)=default;
JKQTFinancialSpecificStyleProperties& operator=(JKQTFinancialSpecificStyleProperties&& other)=default;
/** \brief loads the plot properties from a <a href="http://doc.qt.io/qt-5/qsettings.html")">QSettings</a> object
*
* \param settings QSettings-object to read from
* \param group Group in the QSettings-object to read from
* \param defaultStyle If a setting cannot be found in \a settings, default values are taken from this object
* By default, this is a default-constructed object
*/
void loadSettings(const QSettings &settings, const QString& group, const JKQTFinancialSpecificStyleProperties &defaultStyle);
/** \brief saves the plot properties into a <a href="http://doc.qt.io/qt-5/qsettings.html")">QSettings</a> object.
*
* \param settings QSettings-object to save to
* \param group Group in the QSettings-object to save to
*/
void saveSettings(QSettings& settings, const QString& group) const;
/** \brief default color to use for the (first) financial graph, positive elements */
QColor positiveDefaultColor;
/** \brief default color to use for the (first) financial graph, negative elements */
QColor negativeDefaultColor;
/** \brief defines how to derive the basic graph color for negative elements in a new graph from the color selected from JKQTGraphsBaseStyle::defaultGraphColors
*
* This property is usually JKQTPFFCMSameColor, but can be changed to allow to e.g. fill
* barcharts always with a lighter color than the full color ...
*/
JKQTPColorDerivationMode negativeGraphColorDerivationMode;
/** \brief graph fill style used for positive element */
JKQTFillStyleSummmary positiveFillStyle;
/** \brief graph fill style used for negative element */
JKQTFillStyleSummmary negativeFillStyle;
};
/** \brief Support Class for JKQTBasePlotter, which summarizes all properties that define the visual styling of a JKQTBasePlotter
* \ingroup jkqtpplotter_styling_classes
*
@ -374,6 +431,8 @@ class JKQTPLOTTER_LIB_EXPORT JKQTGraphsBaseStyle {
JKQTGeometricSpecificStyleProperties geometricStyle;
/** \brief styling options for annotation elements */
JKQTAnnotationsSpecificStyleProperties annotationStyle;
/** \brief styling options for financial elements */
JKQTFinancialSpecificStyleProperties financialStyle;
/** \brief returns defaultGraphStyle, barchartStyle, ..., depending on the value of \a type */
const JKQTGraphsSpecificStyleProperties& getGraphStyleByType(JKQTPPlotStyleType type) const;

View File

@ -43,6 +43,22 @@ void JKQTPGraphLineStyleMixin::initLineStyle(JKQTBasePlotter* parent, int &paren
m_lineWidth=m_linePen.widthF();
m_highlightingLineColor=getLineColor();
m_highlightingLineColor.setAlphaF(0.5);
} else if (styletype==JKQTPPlotStyleType::FinancialPositive) {
if (parentPlotStyle<0) parentPlotStyle=parent->getNextStyle();
const JKQTBasePlotter::JKQTPPen pen=parent->getPlotStyle(parentPlotStyle, styletype);
m_linePen.setColor(pen.color());
m_linePen.setStyle(Qt::SolidLine);
m_lineWidth=pen.widthF();
m_highlightingLineColor=getLineColor();
m_highlightingLineColor.setAlphaF(0.5);
} else if (styletype==JKQTPPlotStyleType::FinancialNegative) {
if (parentPlotStyle<0) parentPlotStyle=parent->getNextStyle();
const JKQTBasePlotter::JKQTPPen pen=parent->getPlotStyle(parentPlotStyle, styletype);
m_linePen.setColor(JKQTPGetDerivedColor(parent->getCurrentPlotterStyle().graphsStyle.financialStyle.negativeGraphColorDerivationMode, pen.color()));
m_linePen.setStyle(Qt::SolidLine);
m_lineWidth=pen.widthF();
m_highlightingLineColor=getLineColor();
m_highlightingLineColor.setAlphaF(0.5);
} else {
if (parentPlotStyle<0) parentPlotStyle=parent->getNextStyle();
const JKQTBasePlotter::JKQTPPen pen=parent->getPlotStyle(parentPlotStyle, styletype);
@ -428,6 +444,16 @@ void JKQTPGraphFillStyleMixin::initFillStyle(JKQTBasePlotter *parent, int &paren
if (styletype==JKQTPPlotStyleType::Annotation) {
m_fillColor=JKQTPGetDerivedColor(parent->getCurrentPlotterStyle().graphsStyle.annotationStyle.fillColorDerivationMode, parent->getCurrentPlotterStyle().graphsStyle.annotationStyle.defaultColor);
m_fillBrush=parent->getCurrentPlotterStyle().graphsStyle.annotationStyle.defaultFillStyle.brush(m_fillColor);
} else if (styletype==JKQTPPlotStyleType::FinancialPositive) {
if (parentPlotStyle<0) parentPlotStyle=parent->getNextStyle();
const JKQTBasePlotter::JKQTPPen pen=parent->getPlotStyle(parentPlotStyle, styletype);
m_fillColor=pen.color();
m_fillBrush=parent->getCurrentPlotterStyle().graphsStyle.financialStyle.positiveFillStyle.brush(m_fillColor);
} else if (styletype==JKQTPPlotStyleType::FinancialNegative) {
if (parentPlotStyle<0) parentPlotStyle=parent->getNextStyle();
const JKQTBasePlotter::JKQTPPen pen=parent->getPlotStyle(parentPlotStyle, styletype);
m_fillColor=JKQTPGetDerivedColor(parent->getCurrentPlotterStyle().graphsStyle.financialStyle.negativeGraphColorDerivationMode, pen.color());
m_fillBrush=parent->getCurrentPlotterStyle().graphsStyle.financialStyle.negativeFillStyle.brush(m_fillColor);
} else {
if (parentPlotStyle<0) parentPlotStyle=parent->getNextStyle();
const JKQTBasePlotter::JKQTPPen pen=parent->getPlotStyle(parentPlotStyle, styletype);

View File

@ -73,6 +73,8 @@ enum class JKQTPPlotStyleType {
Impulses, /*!< impulse-type graphs */
Geometric, /*!< geometric elements (e.g. rectangles, circles, lines, ...) */
Annotation, /*!< annotation elements */
FinancialPositive, /*!< financial positive elements */
FinancialNegative, /*!< financial negative elements */
};
/** \brief Styles in which to mark single positions during user actions in JKQTPlotter

View File

@ -0,0 +1 @@
/*.png

View File

@ -74,3 +74,9 @@ graphs\auto_styles\fill_style3=ver
graphs\auto_styles\fill_style4=hor
graphs\auto_styles\fill_style5=cross
graphs\auto_styles\fill_style6=diagcross
graphs\graphs_barchart\stack_separation=0
graphs\graphs_financial\default_positive_color=grey50
graphs\graphs_financial\default_negative_color=black
graphs\graphs_financial\positive_fill_style=none
graphs\graphs_financial\negative_fill_style=solid
graphs\graphs_financial\negative_graph_color_mode=lighter

View File

@ -66,3 +66,5 @@ graphs\auto_styles\color3="#E6EE9C"
graphs\auto_styles\color4="#FFB74D"
graphs\auto_styles\color5="#CE93D8"
graphs\graphs_base\symbol_fill_color_mode=lighter_color(130)
graphs\graphs_financial\default_positive_color=limegreen
graphs\graphs_financial\default_negative_color=red

View File

@ -71,4 +71,6 @@ graphs\graphs_annotation\text_color=white
graphs\graphs_base\fill_color_mode="same_color,more_transparent(0.5)"
graphs\graphs_filled\fill_color_mode="same_color,more_transparent(0.33)"
graphs\graphs_boxplot\fill_color_mode="lighter,more_transparent(0.5)"
graphs\graphs_barchart\stack_separation=0
graphs\graphs_financial\default_positive_color=limegreen
graphs\graphs_financial\default_negative_color=red

View File

@ -72,4 +72,5 @@ graphs\graphs_annotation\text_color=white
graphs\graphs_base\fill_color_mode="same_color,more_transparent(0.5)"
graphs\graphs_filled\fill_color_mode="same_color,more_transparent(0.33)"
graphs\graphs_boxplot\fill_color_mode="lighter,more_transparent(0.5)"
graphs\graphs_financial\default_positive_color=limegreen
graphs\graphs_financial\default_negative_color=red

View File

@ -308,6 +308,7 @@ graphs\graphs_barchart\symbol_fill_color_mode=lighter
graphs\graphs_barchart\radius_at_value=0
graphs\graphs_barchart\radius_at_baseline=0
graphs\graphs_barchart\draw_baseline=false
graphs\graphs_barchart\stack_separation=1
graphs\graphs_boxplot\linewidth=1
graphs\graphs_boxplot\symbol_size=10
graphs\graphs_boxplot\symbol_line_width=1
@ -380,3 +381,20 @@ graphs\graphs_annotation\fill_style=solid
graphs\graphs_annotation\text_color=black
graphs\graphs_annotation\font_size=12
graphs\graphs_annotation\font_name=GUI+FIRA
graphs\graphs_financial\linewidth=2
graphs\graphs_financial\symbol_size=10
graphs\graphs_financial\symbol_line_width=1
graphs\graphs_financial\error_indicator_width=1
graphs\graphs_financial\head_decorator_size_factor=8
graphs\graphs_financial\head_decorator_type=filled_arrow
graphs\graphs_financial\error_fill_style=solid
graphs\graphs_financial\graph_color_mode=same
graphs\graphs_financial\fill_color_mode=lighter
graphs\graphs_financial\error_color_mode=darker
graphs\graphs_financial\error_fill_color_mode=lighter_transparent
graphs\graphs_financial\symbol_fill_color_mode=lighter
graphs\graphs_financial\default_positive_color=darkgreen
graphs\graphs_financial\default_negative_color=maroon
graphs\graphs_financial\positive_fill_style=solid
graphs\graphs_financial\negative_fill_style=solid
graphs\graphs_financial\negative_graph_color_mode=inverted

View File

@ -414,3 +414,4 @@ graphs\graphs_annotation\fill_style=solid
graphs\graphs_annotation\text_color=black
graphs\graphs_annotation\font_size=12
graphs\graphs_annotation\font_name=GUI
graphs\graphs_barchart\stack_separation=0

View File

@ -315,7 +315,8 @@ graphs\graphs_base\fill_color_mode=lighter_transparent
graphs\graphs_base\error_color_mode=same
graphs\graphs_base\error_fill_color_mode=lighter_transparent
graphs\graphs_base\symbol_fill_color_mode=same
graphs\graphs_barchart\linewidth=1
graphs\graphs_barchart\linewidth=0
graphs\graphs_barchart\stack_separation=1
graphs\graphs_barchart\symbol_size=10
graphs\graphs_barchart\symbol_line_width=1
graphs\graphs_barchart\error_indicator_width=1
@ -398,3 +399,5 @@ graphs\graphs_annotation\fill_style=solid
graphs\graphs_annotation\text_color=black
graphs\graphs_annotation\font_size=12
graphs\graphs_annotation\font_name=GUI
graphs\graphs_financial\default_positive_color=seagreen
graphs\graphs_financial\default_negative_color=maroon

Binary file not shown.

Before

Width:  |  Height:  |  Size: 12 KiB

After

Width:  |  Height:  |  Size: 13 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 13 KiB

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.8 KiB

After

Width:  |  Height:  |  Size: 3.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.8 KiB

After

Width:  |  Height:  |  Size: 3.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 60 KiB

After

Width:  |  Height:  |  Size: 62 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 27 KiB

After

Width:  |  Height:  |  Size: 31 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 198 KiB

After

Width:  |  Height:  |  Size: 198 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 47 KiB

After

Width:  |  Height:  |  Size: 47 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 61 KiB

After

Width:  |  Height:  |  Size: 60 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 37 KiB

After

Width:  |  Height:  |  Size: 38 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 54 KiB

After

Width:  |  Height:  |  Size: 55 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 60 KiB

After

Width:  |  Height:  |  Size: 61 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

After

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 12 KiB

After

Width:  |  Height:  |  Size: 12 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 125 KiB

After

Width:  |  Height:  |  Size: 128 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 32 KiB

After

Width:  |  Height:  |  Size: 34 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 57 KiB

After

Width:  |  Height:  |  Size: 59 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 12 KiB

After

Width:  |  Height:  |  Size: 12 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 88 KiB

After

Width:  |  Height:  |  Size: 90 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 12 KiB

After

Width:  |  Height:  |  Size: 12 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 57 KiB

After

Width:  |  Height:  |  Size: 58 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 56 KiB

After

Width:  |  Height:  |  Size: 56 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 17 KiB

After

Width:  |  Height:  |  Size: 17 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 17 KiB

After

Width:  |  Height:  |  Size: 17 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 57 KiB

After

Width:  |  Height:  |  Size: 58 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 36 KiB

After

Width:  |  Height:  |  Size: 36 KiB

Some files were not shown because too many files have changed in this diff Show More