/* Copyright (c) 2008-2015 Jan W. Krieger (, ) (DKFZ) & IWR, University of Heidelberg 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 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 . */ #include "jkqtfastplotter.h" #include #include #include #include #include #include #include #include /** * \brief saves the given property (for which also a def_property exists) into the given settings object * \ingroup jkqtfastplotter * \internal */ #define JKQTFPPROPERTYsave(settings, group, var, varname) \ if (var!=def_##var) settings.setValue(group+varname, var); /** * \brief loads the given property from the given settings object * \ingroup jkqtfastplotter * \internal */ #define JKQTFPPROPERTYload(settings, group, var, varname, varconvert) \ var=settings.value(group+varname, var).varconvert; JKQTFPPlot::JKQTFPPlot(JKQTFastPlotter* parent): QObject(parent) { this->parent=parent; this->visible=true; } JKQTFPPlot::~JKQTFPPlot() { }; void JKQTFPPlot::replot() { if (parent) parent->update_data(); }; void JKQTFPPlot::paint(QPainter& painter) { if (visible) drawGraph(painter); } JKQTFastPlotter::JKQTFastPlotter(QWidget *parent) : JKQTFASTPLOTTER_BASEWIDGET_CONSTRUCTOR(parent)//, mutexRepaint(QMutex::Recursive), mutexRepaintData(QMutex::Recursive), mutexRepaintSystem(QMutex::Recursive) { mouseDragStart=QPoint(0,0); mouseDragEnd=QPoint(0,0); dragging=true; dragShapePen=QPen(QColor("red")); dragShapePen.setStyle(Qt::DashLine); dragLine=false; doFullRepaint=false; plotBorderLeft=def_plotBorderLeft=50; plotBorderRight=def_plotBorderRight=30; plotBorderTop=def_plotBorderTop=5; plotBorderBottom=def_plotBorderBottom=30; synchronizeX=nullptr; synchronizeY=nullptr; backgroundColor=def_backgroundColor=palette().color(QPalette::Window); plotBackgroundColor=def_plotBackgroundColor=QColor("white"); drawGrid=def_drawGrid=true; gridColor=def_gridColor=QColor("lightgrey"); gridStyle=def_gridStyle=Qt::DashLine; gridWidth=def_gridWidth=1; labelFontSize=def_labelFontSize=font().pointSizeF(); labelFontName=def_labelFontName=font().family(); tickFontSize=def_tickFontSize=font().pointSizeF(); tickFontName=def_tickFontName=font().family(); tickLength=def_tickLength=3; drawSystemBox=def_drawSystemBox=true; drawZeroAxes=def_drawZeroAxes=true; systemColor=def_systemColor=QColor("black"); systemWidth=def_systemWidth=2; xZeroTick=0; yZeroTick=0; xTickDistance=1; yTickDistance=1; xAxisLabel="x"; yAxisLabel="y"; xAxisLabelVisible=true; yAxisLabelVisible=true; xAxisLog=false; yAxisLog=false; aspectRatio=1; maintainAspectRatio=false; doDrawing=false; xMin=0; xMax=10; yMin=0; yMax=10; resize(400,200); setXRange(0, 10); setYRange(0,10); doDrawing=true; actCopyImage=new QAction(tr("copy image to clipboard"), this); connect(actCopyImage, SIGNAL(triggered()), this, SLOT(copyImage())); addAction(actCopyImage); setContextMenuPolicy(Qt::ActionsContextMenu); update_plot(); setMouseTracking(true); } void JKQTFastPlotter::clearPlots(bool remove) { if (remove) { for (int i=0; isetParent(this); plots.append(g); update_plot(); } void JKQTFastPlotter::deletePlot(int i, bool remove) { if (i>=0 && i=0 && isetRenderHints(QPainter::HighQualityAntialiasing|QPainter::Antialiasing|QPainter::SmoothPixmapTransform); if (painter->isActive()) { //qDebug()<<"JKQTFastPlotter::paintEvent: image: "<compositionMode(); //image.save(objectName()+"_jkqtfastplotter.png"); painter->drawImage(QPoint(0, 0), image); if (dragging) { if (dragLine) { painter->setPen(dragShapePen); painter->drawLine(mouseDragStart, mouseDragEnd); } } } delete painter; event->accept(); mutexRepaint.unlock(); #ifdef DEBUG qDebug()<<"JKQTFastPlotter::paintEvent ... done"; #endif } void JKQTFastPlotter::copyImage() { mutexRepaint.lock(); QClipboard *clipboard = QApplication::clipboard(); clipboard->setImage(image); mutexRepaint.unlock(); } void JKQTFastPlotter::mouseDoubleClickEvent ( QMouseEvent * event ) { if (event->button()==Qt::LeftButton) { double x=p2x(event->x()); double y=p2y(event->y()); emit doubleClicked(x, y); emit doubleClicked(x, y, event->modifiers()); event->accept(); } } void JKQTFastPlotter::mouseMoveEvent ( QMouseEvent * event ) { double x=p2x(event->x()); double y=p2y(event->y()); emit mouseMoved(x, y); //qDebug()<<"JKQTFastPlotter::mouseMoveEvent "<buttons()&Qt::LeftButton) { dragging=true; double xd=p2x(mouseDragStart.x()); double yd=p2y(mouseDragStart.y()); mouseDragEnd=event->pos(); //qDebug()<<"JKQTFastPlotter::mouseMoveEvent: dragged: "<modifiers()); if (dragLine) update(); } event->accept(); } void JKQTFastPlotter::mousePressEvent ( QMouseEvent * event ) { if (event->button()==Qt::LeftButton) { double x=p2x(event->x()); double y=p2y(event->y()); emit clicked(x, y); emit clicked(x, y, event->modifiers()); mouseDragStart=event->pos(); event->accept(); } } void JKQTFastPlotter::mouseReleaseEvent(QMouseEvent *event) { if (event->button()==Qt::LeftButton) { double xd=p2x(mouseDragStart.x()); double yd=p2y(mouseDragStart.y()); double x=p2x(event->x()); double y=p2y(event->y()); emit mouseDragged(xd, yd, x, y, event->modifiers()); emit mouseDragFinished(xd, yd, x, y, event->modifiers()); dragging=false; if (dragLine) update(); } event->accept(); } void JKQTFastPlotter::resizeEvent(QResizeEvent *event) { JKQTFASTPLOTTER_BASEWIDGET::resizeEvent(event); if (width() > image.width() || height() > image.height()) { QImage newImage(QSize(width(), height()), QImage::Format_ARGB32); image=newImage; systemImage=newImage; } //std::cout<<"replotting after resize to ("<accept(); updateGeometry(); } QSize JKQTFastPlotter::minimumSizeHint() const { if (isVisible()) return QSize((int)round((plotBorderLeft+plotBorderRight)*2.0), (int)round((plotBorderTop+plotBorderBottom)*2.0)); else return QSize(0,0); } void JKQTFastPlotter::plotSystem(QPainter& painter) { #ifdef DEBUG_TIMING JKQTPHighResTimer timer; double time_sum=0; double time_gt=0; std::cout<<"timing plotSystem():\n"; timer.start(); #endif painter.save(); /////////////////////////////////////////////////////////////////// // FILL WIDGET BACKGROUND /////////////////////////////////////////////////////////////////// if (backgroundColor!=QColor(Qt::transparent)) painter.fillRect(this->rect(), QBrush(backgroundColor)); /////////////////////////////////////////////////////////////////// // FILL PLOT BACKGROUND /////////////////////////////////////////////////////////////////// //qDebug()<=xMin && cntr<1000) { if (xMin<=x && x<=xMax) { gridPath.moveTo(x2p(x), internalPlotBorderTop); gridPath.lineTo(x2p(x), internalPlotBorderTop+plotHeight); systemPath.moveTo(x2p(x), internalPlotBorderTop+plotHeight+tickLength); systemPath.lineTo(x2p(x), internalPlotBorderTop+plotHeight-tickLength); QString text=QLocale::system().toString(x); painter.drawText(QPointF(x2p(x)-fmTicks.width(text)/2.0, internalPlotBorderTop+plotHeight+fmTicks.ascent()+fmTicks.width("x")/2.0+tickLength), text); } if (xAxisLog) { x=x/10.0; } else { x=x-xTickDistance; } cntr++; } double y=yZeroTick; if (yAxisLog && yZeroTick<=0) y=yMin; while (y<=yMax && cntr<1000) { if (yMin<=y && y<=yMax) { gridPath.moveTo(internalPlotBorderLeft, y2p(y)); gridPath.lineTo(internalPlotBorderLeft+plotWidth, y2p(y)); systemPath.moveTo(internalPlotBorderLeft-tickLength, y2p(y)); systemPath.lineTo(internalPlotBorderLeft+tickLength, y2p(y)); QString text=QLocale::system().toString(y); painter.drawText(QPointF(internalPlotBorderLeft-fmTicks.width("x")/2.0-fmTicks.width(text)-tickLength, y2p(y)+fmTicks.ascent()/2.0), text); } if (yAxisLog) { y=y*10.0; } else { y=y+yTickDistance; } cntr++; } y=yZeroTick; if (yAxisLog && yZeroTick<=0) y=yMin; while (y>=yMin && cntr<1000) { if (yMin<=y && y<=yMax) { gridPath.moveTo(internalPlotBorderLeft, y2p(y)); gridPath.lineTo(internalPlotBorderLeft+plotWidth, y2p(y)); systemPath.moveTo(internalPlotBorderLeft-tickLength, y2p(y)); systemPath.lineTo(internalPlotBorderLeft+tickLength, y2p(y)); QString text=QLocale::system().toString(y); painter.drawText(QPointF(internalPlotBorderLeft-fmTicks.width("x")/2.0-fmTicks.width(text)-tickLength, y2p(y)+fmTicks.ascent()/2.0), text); } if (yAxisLog) { y=y/10.0; } else { y=y-yTickDistance; } cntr++; } #ifdef DEBUG_TIMING time_gt=timer.get_time(); time_sum+=time_gt; std::cout<<" calcing system & grid: "<paint(painter); #ifdef DEBUG_TIMING time_gt=timer.get_time(); time_sum+=time_gt; std::cout<<" drawing graph "<save(); plotSystem(*painter); painter->setClipRect(QRectF(internalPlotBorderLeft+systemWidth/2.0, internalPlotBorderTop+systemWidth/2.0, plotWidth-systemWidth, plotHeight-systemWidth)); plotGraphs(*painter); painter->restore(); } void JKQTFastPlotter::draw(QPainter* painter, QColor background, QSize* size) { QColor oldb=backgroundColor; backgroundColor=background; calcPlotScaling(); if (size) *size=QSize(width(), height()); painter->save(); plotSystem(*painter); //painter->setClipRect(QRectF(internalPlotBorderLeft+systemWidth/2.0, internalPlotBorderTop+systemWidth/2.0, plotWidth-systemWidth, plotHeight-systemWidth)); plotGraphs(*painter); painter->restore(); backgroundColor=oldb; } void JKQTFastPlotter::update_plot() { calcPlotScaling(); if (!doDrawing) { doFullRepaint=true; return; } if (systemImage.isNull()) return; mutexRepaintSystem.lock(); QPainter* painter=new QPainter(&systemImage); //painter->setRenderHints(QPainter::HighQualityAntialiasing|QPainter::Antialiasing|QPainter::SmoothPixmapTransform); if (painter->isActive()) { plotSystem(*painter); } delete painter; mutexRepaintSystem.unlock(); doFullRepaint=false; update_data(); } void JKQTFastPlotter::update_plot_immediate() { calcPlotScaling(); if (!doDrawing) { doFullRepaint=true; return; } if (systemImage.isNull()) return; mutexRepaintSystem.lock(); QPainter* painter=new QPainter(&systemImage); if (painter->isActive()) { plotSystem(*painter); } delete painter; mutexRepaintSystem.unlock(); doFullRepaint=false; update_data_immediate(); } void JKQTFastPlotter::update_data() { if (doFullRepaint) { // as doFullRepaint is set false in updtae_plot() this is NO endles loop!!!!!!! update_plot(); return; } if (!doDrawing) return; if (image.isNull()) return; mutexRepaintData.lock(); emit replotting(); image=systemImage; QPainter* painter=new QPainter(&image); //painter->setRenderHints(QPainter::HighQualityAntialiasing|QPainter::Antialiasing|QPainter::SmoothPixmapTransform); if (painter->isActive()) { /*qDebug()<<"image.format: "<compositionMode(); qDebug()<<"painter.renderHints: "<renderHints();*/ //painter->setClipRect(QRectF(internalPlotBorderLeft+systemWidth/2.0, internalPlotBorderTop+systemWidth/2.0, plotWidth-systemWidth, plotHeight-systemWidth)); plotGraphs(*painter); } delete painter; mutexRepaintData.unlock(); update(); } void JKQTFastPlotter::update_data_immediate() { if (doFullRepaint) { // as doFullRepaint is set false in updtae_plot() this is NO endles loop!!!!!!! update_plot_immediate(); return; } if (!doDrawing) return; if (image.isNull()) return; mutexRepaintData.lock(); emit replotting(); image=systemImage; QPainter* painter=new QPainter(&image); //painter->setRenderHints(QPainter::HighQualityAntialiasing|QPainter::Antialiasing|QPainter::SmoothPixmapTransform); if (painter->isActive()) { //painter->setClipRect(QRectF(internalPlotBorderLeft+systemWidth/2.0, internalPlotBorderTop+systemWidth/2.0, plotWidth-systemWidth, plotHeight-systemWidth)); plotGraphs(*painter); } delete painter; mutexRepaintData.unlock(); repaint(); } void JKQTFastPlotter::calcPlotScaling() { internalPlotBorderBottom=plotBorderBottom; internalPlotBorderTop=plotBorderTop; internalPlotBorderLeft=plotBorderLeft; internalPlotBorderRight=plotBorderRight; plotWidth=width()-internalPlotBorderLeft-internalPlotBorderRight; plotHeight=height()-internalPlotBorderBottom-internalPlotBorderTop; //////////////////////////////////////////////////////////////////// // X AXIS, PRESETTINGS //////////////////////////////////////////////////////////////////// if (xAxisLog) { if (xMin<=0) xMin=1e-30; if (xMax<=0) xMax=xMin+pow(10.0, (int)log10(xMin)); if (xMax==xMin) { xMax=xMin+pow(10.0, (int)log10(xMin)+1); } } if (xMin>xMax) { double h=xMax; xMax=xMin; xMin=h; } else if (xMax==xMin) { xMax=xMin+1.0; } // this is the x- and y-range spanned by the plot xWidth=fabs(xMax-xMin); //////////////////////////////////////////////////////////////////// // Y AXIS, PRESETTING //////////////////////////////////////////////////////////////////// if (yAxisLog) { if (yMin<=0) yMin=1e-30; if (yMax<=0) yMax=yMin+pow(10.0, (int)log10(yMin)); if (yMax==xMin) { yMax=yMin+pow(10.0, (int)log10(yMin)+1); } } if (yMin>yMax) { double h=yMax; yMax=yMin; yMin=h; } else if (yMax==yMin) { yMax=yMin+1.0; } // this is the x- and y-range spanned by the plot yWidth=fabs(yMax-yMin); //////////////////////////////////////////////////////////////////// // ENSURE ASPECT RATIO (if activated) //////////////////////////////////////////////////////////////////// //double pixelWidth=xWidth/(double)plotWidth; //double pixelHeight=yWidth/(double)plotHeight; if (maintainAspectRatio && (!xAxisLog) && (!yAxisLog)) { double currRatio=(double)plotWidth/(double)plotHeight; double newPlotWidth=plotWidth; double newPlotHeight=plotHeight; if (currRatio!=aspectRatio) { if (aspectRatio<=currRatio) { newPlotWidth=aspectRatio*(double)plotHeight; } else { newPlotHeight=(double)plotWidth/aspectRatio; } } double dx=plotWidth-newPlotWidth; double dy=plotHeight-newPlotHeight; internalPlotBorderBottom+=dy/2.0; internalPlotBorderTop+=dy/2.0; internalPlotBorderLeft+=dx/2.0; internalPlotBorderRight+=dx/2.0; } //////////////////////////////////////////////////////////////////// // PLOTTER SYNCHRONIZATION //////////////////////////////////////////////////////////////////// if (synchronizeX!=nullptr) { internalPlotBorderLeft=synchronizeX->get_internalPlotBorderLeft(); internalPlotBorderRight=synchronizeX->get_internalPlotBorderRight(); xMin=synchronizeX->get_xMin(); xMax=synchronizeX->get_xMax(); xAxisLog=synchronizeX->get_xAxisLog(); xAxisLabel=synchronizeX->get_xAxisLabel(); } if (synchronizeY!=nullptr) { internalPlotBorderTop=synchronizeY->get_internalPlotBorderTop(); internalPlotBorderBottom=synchronizeY->get_internalPlotBorderBottom(); yMin=synchronizeY->get_yMin(); yMax=synchronizeY->get_yMax(); yAxisLog=synchronizeY->get_yAxisLog(); yAxisLabel=synchronizeY->get_yAxisLabel(); } plotWidth=width()-internalPlotBorderLeft-internalPlotBorderRight; plotHeight=height()-internalPlotBorderBottom-internalPlotBorderTop; xWidth=fabs(xMax-xMin); yWidth=fabs(yMax-yMin); //////////////////////////////////////////////////////////////////// // X AXIS, CALC PARAMETERS //////////////////////////////////////////////////////////////////// if (xAxisLog) { xScale=plotWidth/(log10(xMax)-log10(xMin)); xOffset=internalPlotBorderLeft-log10(xMin)*xScale; } else { xScale=plotWidth/xWidth; xOffset=internalPlotBorderLeft-xMin*xScale; } //////////////////////////////////////////////////////////////////// // Y AXIS, CALC PARAMETERS //////////////////////////////////////////////////////////////////// if (yAxisLog) { yScale=plotHeight/(log10(yMax)-log10(yMin)); yOffset=internalPlotBorderTop+log10(yMax)*yScale; } else { yScale=plotHeight/yWidth; yOffset=internalPlotBorderTop+yMax*yScale; } emit plotterSizesChanged(); } void JKQTFastPlotter::setXRange(double min, double max, bool logarithmic) { xMin=min; xMax=max; xAxisLog=logarithmic; calcPlotScaling(); update_plot(); } void JKQTFastPlotter::setYRange(double min, double max, bool logarithmic) { yMin=min; yMax=max; yAxisLog=logarithmic; calcPlotScaling(); update_plot(); } void JKQTFastPlotter::setXYRange(double xmin, double xmax, double ymin, double ymax, bool xlogarithmic, bool ylogarithmic) { xMin=xmin; xMax=xmax; xAxisLog=xlogarithmic; yMin=ymin; yMax=ymax; yAxisLog=ylogarithmic; calcPlotScaling(); update_plot(); } /* void JKQTFastPlotter::synchronizeX(JKQTFastPlotter* toWhere) { bool olddo=doDrawing; doDrawing=false; xMin=toWhere->get_xMin(); xMax=toWhere->get_xMax(); xAxisLog=toWhere->get_xAxisLog(); plotBorderLeft=toWhere->get_internalPlotBorderLeft(); plotBorderRight=toWhere->get_internalPlotBorderRight(); std::cout<<"syncX: xMin="<get_yMin(); yMax=toWhere->get_yMax(); yAxisLog=toWhere->get_yAxisLog(); plotBorderTop=toWhere->get_internalPlotBorderTop(); plotBorderBottom=toWhere->get_internalPlotBorderBottom(); std::cout<<"syncY: yMin="<N=N; this->x=x; this->y=y; this->yerr=nullptr; this->xv=nullptr; this->yv=nullptr; this->yerrv=nullptr; this->color=color; this->errorColor=color.lighter(); this->errorStyle=this->style=style; this->errorWidth=this->width=width; datatype=JKQTFPLPPointer; } JKQTFPLinePlot::JKQTFPLinePlot(JKQTFastPlotter* parent, QVector* x, QVector* y, QColor color, Qt::PenStyle style, double width): JKQTFPPlot(parent) { this->N=x->size(); this->x=nullptr; this->y=nullptr; this->yerr=nullptr; this->xv=x; this->yv=y; this->yerrv=nullptr; this->color=color; this->errorColor=color.lighter(); this->errorStyle=this->style=style; this->errorWidth=this->width=width; datatype=JKQTFPLPVector; } void JKQTFPLinePlot::drawGraph(QPainter& painter) { if (datatype==JKQTFPLPPointer) if (N<=0 || !x || !y) return; if (datatype==JKQTFPLPVector) if (!xv || !yv) return; //std::cout<<"JKQTFPLinePlot::drawGraph()\n"; QPen p(color); p.setStyle(style); p.setWidthF(qMax(JKQTFASTPLOTTER_ABS_MIN_LINEWIDTH, width)); p.setCapStyle(Qt::RoundCap); p.setJoinStyle(Qt::RoundJoin); QPen pe(errorColor); pe.setStyle(errorStyle); pe.setWidthF(qMax(JKQTFASTPLOTTER_ABS_MIN_LINEWIDTH, errorWidth)); pe.setCapStyle(Qt::RoundCap); pe.setJoinStyle(Qt::RoundJoin); QPainterPath path, epath; if (datatype==JKQTFPLPPointer) { if (N>0){ path.moveTo(parent->x2p(x[0]), parent->y2p(y[0])); //std::cout<<"plotting graph, starting @ ("<x2p(x[0])<<", "<y2p(y[0])<<")\n"; } for (unsigned int i=1; ix2p(x[i]), parent->y2p(y[i])); //std::cout<<"-> ("<x2p(x[i])<<", "<y2p(y[i])<<")\n"; } if (yerr!=nullptr) { if (N>0){ epath.moveTo(parent->x2p(x[0]), parent->y2p(y[0]+yerr[0])); } for (unsigned int i=1; ix2p(x[i]), parent->y2p(y[i]+yerr[i])); } if (N>0){ epath.moveTo(parent->x2p(x[0]), parent->y2p(y[0]-yerr[0])); } for (unsigned int i=1; ix2p(x[i]), parent->y2p(y[i]-yerr[i])); } } } else if (datatype==JKQTFPLPVector) { if (xv->size()>1 && (yv->size()>=xv->size())){ path.moveTo(parent->x2p((*xv)[0]), parent->y2p((*yv)[0])); //std::cout<<"plotting graph, starting @ ("<x2p(x[0])<<", "<y2p(y[0])<<")\n"; for ( int i=1; isize(); i++) { path.lineTo(parent->x2p((*xv)[i]), parent->y2p((*yv)[i])); //std::cout<<"-> ("<x2p(x[i])<<", "<y2p(y[i])<<")\n"; } } if (yerrv!=nullptr) { if (yerrv->size()>1 && (xv->size()>=yerrv->size()) && (yv->size()>=yerrv->size())){ epath.moveTo(parent->x2p((*xv)[0]), parent->y2p((*yv)[0]+(*yerrv)[0])); //std::cout<<"plotting graph, starting @ ("<x2p(x[0])<<", "<y2p(y[0])<<")\n"; for ( int i=1; isize(); i++) { epath.lineTo(parent->x2p((*xv)[i]), parent->y2p((*yv)[i]+(*yerrv)[i])); //std::cout<<"-> ("<x2p(x[i])<<", "<y2p(y[i])<<")\n"; } epath.moveTo(parent->x2p((*xv)[0]), parent->y2p((*yv)[0]-(*yerrv)[0])); //std::cout<<"plotting graph, starting @ ("<x2p(x[0])<<", "<y2p(y[0])<<")\n"; for ( int i=1; isize(); i++) { epath.lineTo(parent->x2p((*xv)[i]), parent->y2p((*yv)[i]-(*yerrv)[i])); //std::cout<<"-> ("<x2p(x[i])<<", "<y2p(y[i])<<")\n"; } } } } painter.setPen(p); painter.drawPath(path); painter.setPen(pe); painter.drawPath(epath); //std::cout<<"JKQTFPLinePlot::drawGraph() ... done\n"; } JKQTFPVCrossPlot::JKQTFPVCrossPlot(JKQTFastPlotter* parent, unsigned int N, double* x, double* y, QColor color, Qt::PenStyle style, double width): JKQTFPLinePlot(parent, N, x, y, color, style, width) { crossWidth=5; } JKQTFPVCrossPlot::JKQTFPVCrossPlot(JKQTFastPlotter* parent, QVector* x, QVector* y, QColor color, Qt::PenStyle style, double width): JKQTFPLinePlot(parent, x, y, color, style, width) { crossWidth=5; } void JKQTFPVCrossPlot::drawGraph(QPainter& painter) { if (datatype==JKQTFPLPPointer) if (N<=0 || !x || !y) return; if (datatype==JKQTFPLPVector) if (!xv || !yv) return; //std::cout<<"JKQTFPVCrossPlot::drawGraph()\n"; QPen p(color); p.setStyle(style); p.setWidthF(qMax(JKQTFASTPLOTTER_ABS_MIN_LINEWIDTH, width)); p.setCapStyle(Qt::RoundCap); p.setJoinStyle(Qt::RoundJoin); QPen pe(errorColor); pe.setStyle(errorStyle); pe.setWidthF(qMax(JKQTFASTPLOTTER_ABS_MIN_LINEWIDTH, errorWidth)); pe.setCapStyle(Qt::RoundCap); pe.setJoinStyle(Qt::RoundJoin); QPainterPath path, epath; if (datatype==JKQTFPLPPointer) { for (unsigned int i=0; ix2p(x[i])-crossWidth/2.0, parent->y2p(y[i]))); path.lineTo(QPointF(parent->x2p(x[i])+crossWidth/2.0, parent->y2p(y[i]))); path.moveTo(QPointF(parent->x2p(x[i]), parent->y2p(y[i])-crossWidth/2.0)); path.lineTo(QPointF(parent->x2p(x[i]), parent->y2p(y[i])+crossWidth/2.0)); //std::cout<<"-> ("<x2p(x[i])<<", "<y2p(y[i])<<")\n"; } if (yerr!=nullptr) { if (N>0){ epath.moveTo(parent->x2p(x[0]), parent->y2p(y[0]+yerr[0])); } for (unsigned int i=1; ix2p(x[i]), parent->y2p(y[i]+yerr[i])); } if (N>0){ epath.moveTo(parent->x2p(x[0]), parent->y2p(y[0]-yerr[0])); } for (unsigned int i=1; ix2p(x[i]), parent->y2p(y[i]-yerr[i])); } } } else if (datatype==JKQTFPLPVector) { if (xv->size()>0 && (yv->size()>=xv->size())){ for ( int i=0; isize(); i++) { path.moveTo(QPointF(parent->x2p((*xv)[i])-crossWidth/2.0, parent->y2p((*yv)[i]))); path.lineTo(QPointF(parent->x2p((*xv)[i])+crossWidth/2.0, parent->y2p((*yv)[i]))); path.moveTo(QPointF(parent->x2p((*xv)[i]), parent->y2p((*yv)[i])-crossWidth/2.0)); path.lineTo(QPointF(parent->x2p((*xv)[i]), parent->y2p((*yv)[i])+crossWidth/2.0)); //std::cout<<"-> ("<x2p(x[i])<<", "<y2p(y[i])<<")\n"; } } if (yerrv!=nullptr) { if (yerrv->size()>0 && (xv->size()>=yerrv->size()) && (yv->size()>=yerrv->size())){ epath.moveTo(parent->x2p((*xv)[0]), parent->y2p((*yv)[0]+(*yerrv)[0])); //std::cout<<"plotting graph, starting @ ("<x2p(x[0])<<", "<y2p(y[0])<<")\n"; for ( int i=1; isize(); i++) { epath.lineTo(parent->x2p((*xv)[i]), parent->y2p((*yv)[i]+(*yerrv)[i])); //std::cout<<"-> ("<x2p(x[i])<<", "<y2p(y[i])<<")\n"; } epath.moveTo(parent->x2p((*xv)[0]), parent->y2p((*yv)[0]-(*yerrv)[0])); //std::cout<<"plotting graph, starting @ ("<x2p(x[0])<<", "<y2p(y[0])<<")\n"; for ( int i=1; isize(); i++) { epath.lineTo(parent->x2p((*xv)[i]), parent->y2p((*yv)[i]-(*yerrv)[i])); //std::cout<<"-> ("<x2p(x[i])<<", "<y2p(y[i])<<")\n"; } } } } painter.setPen(p); painter.drawPath(path); painter.setPen(pe); painter.drawPath(epath); //std::cout<<"JKQTFPVCrossPlot::drawGraph() ... done\n"; } JKQTFPVBarPlot::JKQTFPVBarPlot(JKQTFastPlotter* parent, unsigned int N, double* x, double* y, QColor color, Qt::PenStyle style, double width): JKQTFPLinePlot(parent, N, x, y, color, style, width) { } JKQTFPVBarPlot::JKQTFPVBarPlot(JKQTFastPlotter* parent, QVector* x, QVector* y, QColor color, Qt::PenStyle style, double width): JKQTFPLinePlot(parent, x, y, color, style, width) { } void JKQTFPVBarPlot::drawGraph(QPainter& painter) { if (datatype==JKQTFPLPPointer) if (N<=0 || !x || !y) return; if (datatype==JKQTFPLPVector) if (!xv || !yv) return; QPen p(color); p.setStyle(style); p.setWidthF(qMax(JKQTFASTPLOTTER_ABS_MIN_LINEWIDTH, width)); p.setCapStyle(Qt::RoundCap); p.setJoinStyle(Qt::RoundJoin); painter.setPen(p); if (!parent->get_yAxisLog()) { if (datatype==JKQTFPLPPointer) { for (unsigned int i=0; ix2p(x[i]); QLineF l(xval, parent->y2p(0), xval, parent->y2p(y[i])); if (l.length()>0) painter.drawLine(l); } } else if (datatype==JKQTFPLPVector) { for ( int i=0; isize(); i++) { double xval=parent->x2p((*xv)[i]); QLineF l(xval, parent->y2p(0), xval, parent->y2p((*yv)[i])); if (l.length()>0) painter.drawLine(l); } } } else { double starty=parent->get_internalPlotBorderTop()+parent->get_plotHeight(); if (datatype==JKQTFPLPPointer) { for (unsigned int i=0; iy2p(y[i]); if (!std::isnan(v) && !std::isinf(v)) { double xval=parent->x2p(x[i]); QLineF l(xval, starty, xval, v); if (l.length()>0) painter.drawLine(l); } } } else if (datatype==JKQTFPLPVector) { for ( int i=0; isize(); i++) { double v=parent->y2p((*yv)[i]); if (!std::isnan(v) && !std::isinf(v)) { double xval=parent->x2p((*xv)[i]); QLineF l(xval, starty, xval, v); if (l.length()>0) painter.drawLine(l); } } } } } JKQTFPXRangePlot::JKQTFPXRangePlot(JKQTFastPlotter* parent, double xmin, double xmax, QColor color, Qt::PenStyle style, double width, Qt::BrushStyle fillStyle): JKQTFPPlot(parent) { this->xmin=xmin; this->xmax=xmax; this->centerline=(xmax+xmin)/2.0; this->showCenterline=false; this->color=color; this->style=style; this->width=width; this->fillColor=color; this->fillColor.setAlphaF(0.5); this->fillStyle=fillStyle; } void JKQTFPXRangePlot::drawGraph(QPainter& painter) { QRectF r(QPointF(parent->x2p(xmin), parent->get_internalPlotBorderTop()), QPointF(parent->x2p(xmax), parent->get_internalPlotBorderTop()+parent->get_plotHeight())); QBrush b(fillStyle); b.setColor(fillColor); QPen p(color); p.setStyle(style); p.setWidthF(qMax(JKQTFASTPLOTTER_ABS_MIN_LINEWIDTH, width)); painter.setPen(p); painter.fillRect(r, b); if (showCenterline) { painter.drawLine(parent->x2p(centerline), parent->get_internalPlotBorderTop(), parent->x2p(centerline), parent->get_internalPlotBorderTop()+parent->get_plotHeight()); } painter.drawRect(r); } JKQTFPQImagePlot::JKQTFPQImagePlot(JKQTFastPlotter* parent, QImage* image, double xmin, double xmax, double ymin, double ymax): JKQTFPPlot(parent) { this->image=image; this->xmin=xmin; this->xmax=xmax; this->ymin=ymin; this->ymax=ymax; } JKQTFPQImagePlot::JKQTFPQImagePlot(JKQTFastPlotter* parent, QImage* image): JKQTFPPlot(parent) { this->image=image; this->xmin=0; this->xmax=image->width(); this->ymin=0; this->ymax=image->height(); } void JKQTFPQImagePlot::drawGraph(QPainter& painter) { if (!image) return; if (image->isNull()) return; double pxmin=parent->x2p(xmin); double pxmax=parent->x2p(xmax); double dx=fabs(pxmax-pxmin); double pymin=parent->y2p(ymin); double pymax=parent->y2p(ymax); double dy=fabs(pymax-pymin); if (dx>0 && dy>0) painter.drawImage(QRectF(pxmin, pymax, dx, dy), *image); } JKQTFPimagePlot::JKQTFPimagePlot(JKQTFastPlotter* parent, void* image, JKQTFPImageFormat imageFormat, unsigned int width, unsigned int height, double xmin, double xmax, double ymin, double ymax, JKQTFPColorPalette palette): JKQTFPPlot(parent) { this->image=image; this->width=width; this->height=height; this->xmin=xmin; this->xmax=xmax; this->ymin=ymin; this->ymax=ymax; colorMin=0; colorMax=0; this->palette=palette; drawColorBar=true; colorBarWidth=15; this->imageFormat=imageFormat; this->rotation=0; } JKQTFPimagePlot::JKQTFPimagePlot(JKQTFastPlotter* parent, void* image, JKQTFPImageFormat imageFormat, unsigned int width, unsigned int height, JKQTFPColorPalette palette): JKQTFPPlot(parent) { this->image=image; this->width=width; this->height=height; colorMin=0; colorMax=0; this->palette=palette; drawColorBar=true; colorBarWidth=15; xmin=0; ymin=0; xmax=width; ymax=height; this->imageFormat=imageFormat; this->rotation=0; } QStringList JKQTFPimagePlot_getPalettes() { QStringList sl; sl<(pic, 32, 1, img, (JKQTFPColorPalette)i, 0, 31); QPixmap pix(16,8); QRect r(0,0,15,7); QPainter p(&pix); p.drawImage(r, img); p.setPen(QPen(QColor("black"))); p.drawRect(r); p.end(); return QIcon(pix); } void JKQTFPimagePlot::drawGraph(QPainter& painter) { if (!image) return; if (width<=0 && height<=0) return; //QPainter::CompositionMode cm=painter.compositionMode(); painter.setCompositionMode(QPainter::CompositionMode_SourceOver); QImage img(width, height, QImage::Format_ARGB32); switch(imageFormat) { case JKQTFP_uint8: JKQTFPimagePlot_array2image((uint8_t*)image, width, height, img, palette, colorMin, colorMax); break; case JKQTFP_uint16: JKQTFPimagePlot_array2image((uint16_t*)image, width, height, img, palette, colorMin, colorMax); break; case JKQTFP_uint32: JKQTFPimagePlot_array2image((uint32_t*)image, width, height, img, palette, colorMin, colorMax); break; case JKQTFP_int64: JKQTFPimagePlot_array2image((int64_t*)image, width, height, img, palette, colorMin, colorMax); break; case JKQTFP_float: JKQTFPimagePlot_array2image((float*)image, width, height, img, palette, colorMin, colorMax); break; case JKQTFP_double: JKQTFPimagePlot_array2image((double*)image, width, height, img, palette, colorMin, colorMax); break; } if (img.isNull()) return; double pxmin=parent->x2p(xmin); double pxmax=parent->x2p(xmax); double dx=fabs(pxmax-pxmin); double pymin=parent->y2p(ymin); double pymax=parent->y2p(ymax); double dy=fabs(pymax-pymin); QTransform trans; trans.reset(); if (rotation==1) trans.rotate(90); else if (rotation==2) trans.rotate(180); else if (rotation==3) trans.rotate(270); if (dx>0 && dy>0) painter.drawImage(QRectF(pxmin, pymax, dx, dy), img.transformed(trans)); if (drawColorBar && parent->get_plotHeight()>3) { uint8_t d[200]; for (int i=0; i<200; i++) d[i]=i; QImage b(1, 200, QImage::Format_ARGB32); JKQTFPimagePlot_array2image(d, 1, 200, b, palette, 0, 199); //std::cout<<"bar.width="<get_internalPlotBorderLeft()+parent->get_plotWidth()+parent->get_tickLength()*2, parent->get_internalPlotBorderTop()+parent->get_plotHeight()*0.15, colorBarWidth, parent->get_plotHeight()*0.8); //std::cout<<"r.left="<image=image; this->width=width; this->height=height; this->xmin=xmin; this->xmax=xmax; this->ymin=ymin; this->ymax=ymax; this->color=color; this->rotation=0; this->showAsSymbols=false; this->linewidth=2; this->symboltype=stCircle; } JKQTFPimageOverlayPlot::JKQTFPimageOverlayPlot(JKQTFastPlotter* parent, bool* image, unsigned int width, unsigned int height, QColor color): JKQTFPPlot(parent) { this->image=image; this->width=width; this->height=height; xmin=0; ymin=0; xmax=width; ymax=height; this->color=color; this->linewidth=2; this->rotation=0; this->showAsSymbols=false; this->symboltype=stCircle; } void JKQTFPimageOverlayPlot::drawGraph(QPainter& painter) { if (!image) return; if (width<=0 && height<=0) return; QTransform trans; trans.reset(); if (rotation==1) trans.rotate(90); else if (rotation==2) trans.rotate(180); else if (rotation==3) trans.rotate(270); double pxmin=parent->x2p(xmin); double pxmax=parent->x2p(xmax); double dx=fabs(pxmax-pxmin); double pymin=parent->y2p(ymin); double pymax=parent->y2p(ymax); double dy=fabs(pymax-pymin); double ddx=dx/double(width); double ddy=dy/double(height); if (showAsSymbols) { QList x,y; for (unsigned int j=0; jx2p(x[i]); double py=parent->y2p(y[i]); QRectF r(px-ddx/2.0, py-ddy/2.0, ddx, ddy); if (this->symboltype==stCircle) painter.drawEllipse(r); else painter.drawRect(r); } painter.restore(); } else { QImage img(width, height, QImage::Format_ARGB32); QColor tc(Qt::transparent); for (unsigned int j=0; j0 && dy>0) { //qDebug()<width=width; this->label=label; this->lineWidth=lineWidth; this->color=color; this->position=JKQTFPQScaleBarXPlot::TopRight; if (parent) { this->font.setFamily(parent->get_labelFontName()); this->font.setPointSizeF(parent->get_labelFontSize()); } } void JKQTFPQScaleBarXPlot::drawGraph(QPainter& painter) { painter.save(); QRectF r(QPointF(parent->get_internalPlotBorderLeft(), parent->get_internalPlotBorderTop()), QPointF(parent->get_internalPlotBorderLeft()+parent->get_plotWidth(), parent->get_internalPlotBorderTop()+parent->get_plotHeight())); double borderfraction=0.1; int yDistance=(double)parent->get_plotHeight()*borderfraction; QPen p(color); p.setWidthF(qMax(JKQTFASTPLOTTER_ABS_MIN_LINEWIDTH, lineWidth)); p.setColor(color); QString s=label.arg(width); double yy1, yy2, xx1, xx2, x1, x2;//, y2, y1; if (position==JKQTFPQScaleBarXPlot::TopRight) { yy1=parent->get_internalPlotBorderTop()+yDistance; yy2=yy1; x2=parent->get_xMax()-borderfraction*(parent->get_xMax()-parent->get_xMin()); x1=x2-width; xx1=parent->x2p(x1); xx2=parent->x2p(x2); painter.drawLine(QLineF(xx1, yy1, xx2, yy2)); painter.setFont(font); QFontMetrics fm=painter.fontMetrics(); painter.drawText(xx1+(xx2-xx1)/2-fm.width(s)/2, yy1+3*lineWidth+fm.ascent(), s); } else if (position==JKQTFPQScaleBarXPlot::TopLeft) { yy1=parent->get_internalPlotBorderTop()+yDistance; yy2=yy1; x1=parent->get_xMin()+borderfraction*(parent->get_xMax()-parent->get_xMin()); x2=x1+width; xx1=parent->x2p(x1); xx2=parent->x2p(x2); painter.drawLine(QLineF(xx1, yy1, xx2, yy2)); painter.setFont(font); QFontMetrics fm=painter.fontMetrics(); painter.drawText(xx1+(xx2-xx1)/2-fm.width(s)/2, yy1+3*lineWidth+fm.ascent(), s); } else if (position==JKQTFPQScaleBarXPlot::BottomLeft) { yy1=parent->get_internalPlotBorderTop()+parent->get_plotHeight()-yDistance; yy2=yy1; x1=parent->get_xMin()+borderfraction*(parent->get_xMax()-parent->get_xMin()); x2=x1+width; xx1=parent->x2p(x1); xx2=parent->x2p(x2); painter.drawLine(QLineF(xx1, yy1, xx2, yy2)); painter.setFont(font); QFontMetrics fm=painter.fontMetrics(); painter.drawText(xx1+(xx2-xx1)/2-fm.width(s)/2, yy1-3*lineWidth-fm.descent(), s); } else if (position==JKQTFPQScaleBarXPlot::BottomRight) { yy1=parent->get_internalPlotBorderTop()+parent->get_plotHeight()-yDistance; yy2=yy1; x2=parent->get_xMax()-borderfraction*(parent->get_xMax()-parent->get_xMin()); x1=x2-width; xx1=parent->x2p(x1); xx2=parent->x2p(x2); painter.drawLine(QLineF(xx1, yy1, xx2, yy2)); painter.setFont(font); QFontMetrics fm=painter.fontMetrics(); painter.drawText(xx1+(xx2-xx1)/2-fm.width(s)/2, yy1-3*lineWidth-fm.descent(), s); } painter.restore(); } QIcon JKQTFPimagePlot_getPaletteIcon(JKQTFPColorPalette palette) { return JKQTFPimagePlot_getPaletteIcon((int)palette); }; JKQTFPQOverlayLinearGridPlot::JKQTFPQOverlayLinearGridPlot(JKQTFastPlotter* parent, double width, QColor color, double lineWidth, Qt::PenStyle style): JKQTFPPlot(parent) { this->width=width; this->color=color; this->lineWidth=lineWidth; this->style=style; } void JKQTFPQOverlayLinearGridPlot::drawGraph(QPainter& painter) { painter.save(); QPen p(color); p.setWidthF(qMax(JKQTFASTPLOTTER_ABS_MIN_LINEWIDTH, lineWidth)); p.setColor(color); p.setStyle(style); double xmin=parent->get_xMin(); double xmax=parent->get_xMax(); double ymin=parent->get_yMin(); double ymax=parent->get_yMax(); double xstart=(floor(xmin/width)-1.0)*width; double ystart=(floor(ymin/width)-1.0)*width; QPainterPath gridPath; double x=xstart; int cntr=0; // used to stop plotting after 1000 grid lines while (x<=xmax && cntr<1000) { if (xmin<=x && x<=xmax) { gridPath.moveTo(parent->x2p(x), parent->get_internalPlotBorderTop()); gridPath.lineTo(parent->x2p(x), parent->get_internalPlotBorderTop()+parent->get_plotHeight()); } x+=width; cntr++; } double y=ystart; cntr=0; while (y<=ymax && cntr<1000) { if (ymin<=y && y<=ymax) { gridPath.moveTo(parent->get_internalPlotBorderLeft(), parent->y2p(y)); gridPath.lineTo(parent->get_internalPlotBorderLeft()+parent->get_plotWidth(), parent->y2p(y)); } y+=width; cntr++; } painter.setPen(p); painter.drawPath(gridPath); painter.restore(); } JKQTFPRGBImageOverlayPlot::JKQTFPRGBImageOverlayPlot(JKQTFastPlotter *parent, void *imageRed, JKQTFPImageFormat imageFormat, unsigned int width, unsigned int height, double xmin, double xmax, double ymin, double ymax): JKQTFPPlot(parent) { this->width=width; this->height=height; this->xmin=xmin; this->xmax=xmax; this->ymin=ymin; this->ymax=ymax; colorMinRed=0; colorMaxRed=0; this->imageRed=imageRed; this->imageFormatRed=imageFormat; colorMinGreen=0; colorMaxGreen=0; this->imageGreen=nullptr; this->imageFormatGreen=JKQTFP_uint16; colorMinBlue=0; colorMaxBlue=0; this->imageBlue=nullptr; this->imageFormatBlue=JKQTFP_uint16; this->rotation=0; } JKQTFPRGBImageOverlayPlot::JKQTFPRGBImageOverlayPlot(JKQTFastPlotter *parent, void *imageRed, JKQTFPImageFormat imageFormat, unsigned int width, unsigned int height): JKQTFPPlot(parent) { this->width=width; this->height=height; this->xmin=0; this->xmax=width-1; this->ymin=0; this->ymax=height-1; colorMinRed=0; colorMaxRed=0; this->imageRed=imageRed; this->imageFormatRed=imageFormat; colorMinGreen=0; colorMaxGreen=0; this->imageGreen=nullptr; this->imageFormatGreen=JKQTFP_uint16; colorMinBlue=0; colorMaxBlue=0; this->imageBlue=nullptr; this->imageFormatBlue=JKQTFP_uint16; this->rotation=0; } JKQTFPRGBImageOverlayPlot::JKQTFPRGBImageOverlayPlot(JKQTFastPlotter *parent): JKQTFPPlot(parent) { this->width=width; this->height=height; this->xmin=0; this->xmax=width-1; this->ymin=0; this->ymax=height-1; colorMinRed=0; colorMaxRed=0; this->imageRed=nullptr; this->imageFormatRed=JKQTFP_uint16; colorMinGreen=0; colorMaxGreen=0; this->imageGreen=nullptr; this->imageFormatGreen=JKQTFP_uint16; colorMinBlue=0; colorMaxBlue=0; this->imageBlue=nullptr; this->imageFormatBlue=JKQTFP_uint16; this->rotation=0; } void JKQTFPRGBImageOverlayPlot::drawGraph(QPainter &painter) { //qDebug()<<"JKQTFPRGBImageOverlayPlot::drawGraph() "<((uint8_t*)imageRed, width, height, img, 0, colorMinRed, colorMaxRed); break; case JKQTFP_uint16: JKQTFPRGBImageOverlayPlot_array2image((uint16_t*)imageRed, width, height, img, 0, colorMinRed, colorMaxRed); break; case JKQTFP_uint32: JKQTFPRGBImageOverlayPlot_array2image((uint32_t*)imageRed, width, height, img, 0, colorMinRed, colorMaxRed); break; case JKQTFP_int64: JKQTFPRGBImageOverlayPlot_array2image((int64_t*)imageRed, width, height, img, 0, colorMinRed, colorMaxRed); break; case JKQTFP_float: JKQTFPRGBImageOverlayPlot_array2image((float*)imageRed, width, height, img, 0, colorMinRed, colorMaxRed); break; case JKQTFP_double: JKQTFPRGBImageOverlayPlot_array2image((double*)imageRed, width, height, img, 0, colorMinRed, colorMaxRed); break; } switch(imageFormatGreen) { case JKQTFP_uint8: JKQTFPRGBImageOverlayPlot_array2image((uint8_t*)imageGreen, width, height, img, 1, colorMinGreen, colorMaxGreen); break; case JKQTFP_uint16: JKQTFPRGBImageOverlayPlot_array2image((uint16_t*)imageGreen, width, height, img, 1, colorMinGreen, colorMaxGreen); break; case JKQTFP_uint32: JKQTFPRGBImageOverlayPlot_array2image((uint32_t*)imageGreen, width, height, img, 1, colorMinGreen, colorMaxGreen); break; case JKQTFP_int64: JKQTFPRGBImageOverlayPlot_array2image((int64_t*)imageGreen, width, height, img, 1, colorMinGreen, colorMaxGreen); break; case JKQTFP_float: JKQTFPRGBImageOverlayPlot_array2image((float*)imageGreen, width, height, img, 1, colorMinGreen, colorMaxGreen); break; case JKQTFP_double: JKQTFPRGBImageOverlayPlot_array2image((double*)imageGreen, width, height, img, 1, colorMinGreen, colorMaxGreen); break; } switch(imageFormatBlue) { case JKQTFP_uint8: JKQTFPRGBImageOverlayPlot_array2image((uint8_t*)imageBlue, width, height, img, 2, colorMinBlue, colorMaxBlue); break; case JKQTFP_uint16: JKQTFPRGBImageOverlayPlot_array2image((uint16_t*)imageBlue, width, height, img, 2, colorMinBlue, colorMaxBlue); break; case JKQTFP_uint32: JKQTFPRGBImageOverlayPlot_array2image((uint32_t*)imageBlue, width, height, img, 2, colorMinBlue, colorMaxBlue); break; case JKQTFP_int64: JKQTFPRGBImageOverlayPlot_array2image((int64_t*)imageBlue, width, height, img, 2, colorMinBlue, colorMaxBlue); break; case JKQTFP_float: JKQTFPRGBImageOverlayPlot_array2image((float*)imageBlue, width, height, img, 2, colorMinBlue, colorMaxBlue); break; case JKQTFP_double: JKQTFPRGBImageOverlayPlot_array2image((double*)imageBlue, width, height, img, 2, colorMinBlue, colorMaxBlue); break; } if (img.isNull()) return; double pxmin=parent->x2p(xmin); double pxmax=parent->x2p(xmax); double dx=fabs(pxmax-pxmin); double pymin=parent->y2p(ymin); double pymax=parent->y2p(ymax); double dy=fabs(pymax-pymin); QTransform trans; trans.reset(); if (rotation==1) trans.rotate(90); else if (rotation==2) trans.rotate(180); else if (rotation==3) trans.rotate(270); if (dx>0 && dy>0) painter.drawImage(QRectF(pxmin, pymax, dx, dy), img.transformed(trans)); } void JKQTFPRGBImageOverlayPlot::set_image(void* imageRed, JKQTFPImageFormat imageFormatRed, unsigned int width, unsigned int height){ this->imageRed=imageRed; this->imageFormatRed=imageFormatRed; this->imageGreen=nullptr; this->imageBlue=nullptr; this->width=width; this->height=height; this->xmin=0; this->xmax=width-1; this->ymin=0; this->ymax=height-1; replot(); } void JKQTFPRGBImageOverlayPlot::set_image(void* imageRed, JKQTFPImageFormat imageFormatRed, void* imageGreen, JKQTFPImageFormat imageFormatGreen, unsigned int width, unsigned int height) { this->imageRed=imageRed; this->imageFormatRed=imageFormatRed; this->imageGreen=imageGreen; this->imageFormatGreen=imageFormatGreen; this->imageBlue=nullptr; this->width=width; this->height=height; this->xmin=0; this->xmax=width-1; this->ymin=0; this->ymax=height-1; replot(); } void JKQTFPRGBImageOverlayPlot::set_image(void* imageRed, JKQTFPImageFormat imageFormatRed, void* imageGreen, JKQTFPImageFormat imageFormatGreen, void* imageBlue, JKQTFPImageFormat imageFormatBlue, unsigned int width, unsigned int height) { this->imageRed=imageRed; this->imageFormatRed=imageFormatRed; this->imageGreen=imageGreen; this->imageFormatGreen=imageFormatGreen; this->imageBlue=imageBlue; this->imageFormatBlue=imageFormatBlue; this->width=width; this->height=height; this->xmin=0; this->xmax=width-1; this->ymin=0; this->ymax=height-1; replot(); } void JKQTFPRGBImageOverlayPlot::set_image(void* imageRed, JKQTFPImageFormat imageFormatRed, unsigned int width, unsigned int height, double xmin, double xmax, double ymin, double ymax){ this->imageRed=imageRed; this->imageFormatRed=imageFormatRed; this->imageRed=nullptr; this->imageBlue=nullptr; this->width=width; this->height=height; this->xmin=xmin; this->xmax=xmax; this->ymin=ymin; this->ymax=ymax; replot(); } void JKQTFPRGBImageOverlayPlot::set_image(void* imageRed, JKQTFPImageFormat imageFormatRed, void* imageGreen, JKQTFPImageFormat imageFormatGreen, unsigned int width, unsigned int height, double xmin, double xmax, double ymin, double ymax) { this->imageRed=imageRed; this->imageFormatRed=imageFormatRed; this->imageGreen=imageGreen; this->imageFormatGreen=imageFormatGreen; this->imageBlue=nullptr; this->width=width; this->height=height; this->xmin=xmin; this->xmax=xmax; this->ymin=ymin; this->ymax=ymax; replot(); } void JKQTFPRGBImageOverlayPlot::set_image(void* imageRed, JKQTFPImageFormat imageFormatRed, void* imageGreen, JKQTFPImageFormat imageFormatGreen, void* imageBlue, JKQTFPImageFormat imageFormatBlue, unsigned int width, unsigned int height, double xmin, double xmax, double ymin, double ymax) { this->imageRed=imageRed; this->imageFormatRed=imageFormatRed; this->imageGreen=imageGreen; this->imageFormatGreen=imageFormatGreen; this->imageBlue=imageBlue; this->imageFormatBlue=imageFormatBlue; this->width=width; this->height=height; this->xmin=xmin; this->xmax=xmax; this->ymin=ymin; this->ymax=ymax; replot(); } JKQTFPYRangePlot::JKQTFPYRangePlot(JKQTFastPlotter *parent, double xmin, double xmax, QColor color, Qt::PenStyle style, double width, Qt::BrushStyle fillStyle): JKQTFPPlot(parent) { this->ymin=xmin; this->ymax=xmax; this->centerline=(xmax+xmin)/2.0; this->showCenterline=false; this->color=color; this->style=style; this->width=width; this->fillColor=color; this->fillColor.setAlphaF(0.5); this->fillStyle=fillStyle; } void JKQTFPYRangePlot::drawGraph(QPainter& painter) { QRectF r(QPointF(parent->get_internalPlotBorderLeft(), parent->y2p(ymin)), QPointF(parent->get_internalPlotBorderLeft()+parent->get_plotWidth(), parent->y2p(ymax))); QBrush b(fillStyle); b.setColor(fillColor); QPen p(color); p.setStyle(style); p.setWidthF(qMax(JKQTFASTPLOTTER_ABS_MIN_LINEWIDTH, width)); painter.setPen(p); painter.fillRect(r, b); if (showCenterline) { painter.drawLine(parent->get_internalPlotBorderLeft(), parent->y2p(centerline), parent->get_internalPlotBorderLeft()+parent->get_plotWidth(), parent->y2p(centerline)); } painter.drawRect(r); }