Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using Qt To Draw the Graph of Sin(x)

Tags:

qt

I'm experimenting with ways to draw a sinusoidal graph.

My widget is only expecting to get passed in a few arbitrary data points. I have to fit these data points to a sinusoidal line curve:

Sin(x)

So far, I've tried a few methods using QPainterPath.

  1. QPainterPath::lineTo - I tried using this function to plot the curve by taking my data points and creating so many points BETWEEN them, that the line actually smooths out a bit. This is a little too computationally intensive though, I feel.
  2. QPainterPath::cubicTo - From what I gathered from RTFM, this is the best way to go. The only problem is that I'm not sure how to plot my control points at spots where it will consistently and programmatically smooth out the curve the way I want it to. I was unable to get the desired result with this function.

After some googling, I came across a few forum posts that were using Qwt for curve plotting. It would be great if I could use Qwt, but it's not an option since I'm restricted to only using Qt.

Does anyone have helpful feedback/suggestions?

like image 738
kwikness Avatar asked Aug 03 '11 04:08

kwikness


2 Answers

I am doing a very similar thing currently with painting the bode sweep of a parametric EQ (a long line with multiple sweeping curves). The way I'm doing it (pseudo style):

qreal yCoords[GRAPH_WIDTH];
...
QPainter Painter(this);
Painter.setRenderHint(QPainter::Antialiasing, true);
//Painter.setRenderHint(QPainter::HighQualityAntialiasing, true); //opengl specific
for(int xCoord = 0; xCoord < GRAPH_WIDTH; x++)
  Path.lineTo(QPointF(xCoord, yCoord[xCoord]));
...
Painter.drawPath(Path);

The combination of the calls to setRenderHint and drawing lines with QPointF (i.e. two qreal) rather than QPoint (two int) makes the line very smooth.

We're using this on an SBC running Ubuntu and getting redraw timings (including all of the complex math to get the points in the first place) of ~80ms for a 600x300px graph. Initial tests show that enabling opengl rendering reduces this to ~8ms (clearly the processor intensive task is the painting with antialiasing), so if you can do that, I think this solution will work for you.

like image 147
sam-w Avatar answered Oct 02 '22 17:10

sam-w


QCustomPlot is a free and easy to use class that can be found online. It may be better for what you are looking to do.

like image 30
Mike Avatar answered Oct 02 '22 17:10

Mike