Qt 6.11 is out! See what's new in the release
blog
QOpenGLWidget::Update() and QPainter redraw seems to be very sporadic.
-
Hello,
I am trying to write a program that does some simple target motion analysis. So I need to be able to redraw the QOpenGLWidget multiple times.
Right now I am calling the update function from within my redraw function from other classes. When the update is called it seems to almost be randomly redraw the graphics I want and sometimes it won't redraw at all.
I am still pretty new to Qt graphics. I attached my QOpenGLWidget class I created..
Thanks!
#include "oglwidget.h" #include "qpainter.h" #include "MK309_Mainwindow.h" #include "TargetCalc.h" #include "OwnshipCalc.h" // // OpenGL window size is 600 x 400 // x-center = 260 // y-center = 200 // int count = 0; OGLWidget::OGLWidget(QWidget *parent): QOpenGLWidget(parent) { // allows the timer to fire more than one shot /*animationTimer.setSingleShot(false); connect(&animationTimer, SIGNAL(timeout()), this, SLOT(animate())); animationTimer.start(25);*/ } OGLWidget::~OGLWidget() { } void OGLWidget::animate() { qDebug() << "Animate fire shot!" << endl; OGLWidget::update(); } void OGLWidget::initializeGL() { glClearColor(0,0,0,1); glEnable(GL_DEPTH_TEST); glEnable(GL_LIGHT0); glEnable(GL_LIGHTING); glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE); glEnable(GL_COLOR_MATERIAL); this->setEnabled(true); OGLWidget::setUpdatesEnabled(true); qDebug() << "The opengl widget was set up properly ---> " << OGLWidget::isValid(); } void OGLWidget::paintGL() { MK309_TMA *TMA_item = GetTMAitems(); TARGET *target = GetTargetItems(); TargetCalc target_calc; // Draws outer circle and the center ownship OGLWidget::TacticalCircle(); if (TMA_item->redraw) { qDebug() << "Redraw happening" << endl; OGLWidget::badSubSurfaceTarget(TMA_item->target_x, TMA_item->target_y); OGLWidget::unknownSurfaceTarget(500,50); OGLWidget::torpedoInWater(500,100); OGLWidget::knownGoodSurfaceTarget(500,150); OGLWidget::torpedoInterceptPoint(500,200); // draw ownship velocity line OGLWidget::DrawOwnshipVelocityLine(); } qDebug() << " Paint GL function hit " << endl; } void OGLWidget::DrawOwnshipHistory(QPainter *painter) { OWNSHIP *ownship = GetOwnshipItems(); OwnshipCalc ownship_calc; double dist = sqrt(((ownship->endPointX - xc) * (ownship->endPointX - xc)) + ((ownship->endPointY - yc) * (ownship->endPointY - yc))); double n = ownship_calc.DetermineOwnshipHistoryLength(); int tempDotDivide = 0; int dotSpotX[5]; int dotSpotY[5]; int i; for (i = 0; i < 5; i++) { tempDotDivide = tempDotDivide + n; double r = tempDotDivide / dist; dotSpotX[i] = (int) (r * ownship->endPointX + (1 - r) * xc) ; dotSpotY[i] = (int) (r * ownship->endPointY + (1 - r) * yc) ; int tempSpotX = dotSpotX[i] - xc; int tempSpotY = dotSpotY[i] - yc; dotSpotX[i] = xc - tempSpotX; dotSpotY[i] = yc - tempSpotY; painter->drawEllipse(dotSpotX[i]-1, dotSpotY[i]+2, 2, 2); } } void OGLWidget::DrawOwnshipVelocityLine() { OwnshipCalc ownship_calc; OWNSHIP *ownship = GetOwnshipItems(); MK309_TMA *TMA_item = GetTMAitems(); QPainter painter(this); QPen myPen(Qt::white, 1, Qt::SolidLine); painter.setPen(myPen); double convertToDegree = PI / 180; ownship->Vx = sin(ownship->CQO * convertToDegree); ownship->Vy = cos(ownship->CQO * convertToDegree); ownship->endPointX = (ownship->Vx * xc) + xc; ownship->endPointY = (ownship->Vy * yc) + yc; ownship_calc.CalcOwnshipVelocityEndpoint(); painter.drawLine(xc, yc, ownship->endPointX, ownship->endPointY); QPainter *pntr_ptr = &painter; DrawOwnshipHistory(pntr_ptr); painter.end(); } void OGLWidget::redraw() { MK309_TMA *TMA_item = GetTMAitems(); TMA_item->redraw = true; QOpenGLWidget::update(); OGLWidget::update(); qApp->processEvents(); } void OGLWidget::TacticalCircle() { // params (x, y, width, height) // starts at (x,y) with width and height QRectF outerCircle(70,10,380,380); QRectF innerCircle(250,190,20,20); QPainter painter(this); QPen myPen(Qt::white, 1, Qt::SolidLine); painter.setPen(myPen); // draw both of the circles painter.drawEllipse(outerCircle); painter.drawEllipse(innerCircle); // 4 corners of rectangle ellipse painter.drawPoint(450, 390); painter.drawPoint(70, 390); painter.drawPoint(450, 10); painter.drawPoint(70, 10); // center, ownship center // drawLine(x1,y1, x2,y2) // (x1,y1) -> (x2,y2) painter.drawPoint(260,200); painter.drawLine(260,190,260,210); painter.drawLine(250,200,270,200); // draws the outerlines painter.drawLine(260,5,260,15); painter.drawLine(445,200,455,200); painter.drawLine(260,385,260,395); painter.drawLine(65,200,75,200); // draw the angles for testing painter.drawText(260,25, "0"); painter.drawText(460,200, "90"); painter.drawText(245,380, "180"); painter.drawText(40,200, "270"); // end painter to avoid graphical corruption painter.end(); } void OGLWidget::badSubSurfaceTarget(int x, int y) { TARGET *target = GetTargetItems(); TargetCalc target_calc; // target point center at (x,y) QPainter badTargetPainter(this); QPen myPen(Qt::red, 1, Qt::SolidLine); badTargetPainter.setPen(myPen); badTargetPainter.drawLine(x,y,x-10,y-10); badTargetPainter.drawLine(x,y,x+10,y-10); QPen myPen1(Qt::red, 2, Qt::SolidLine); badTargetPainter.setPen(myPen1); badTargetPainter.drawPoint(x, y-9); target->centerX = x; target->centerY = y - 9; // Set pen width back to 1 badTargetPainter.setPen(myPen); QPainter *pntr_ptr = &badTargetPainter; DrawTargetVelocityLine(target->centerX, target->centerY, pntr_ptr); DrawTargetHistoryPoints(target->centerX, target->centerY, pntr_ptr); badTargetPainter.end(); } void OGLWidget::DrawTargetHistoryPoints(int x, int y, QPainter *painter) { TARGET *target = GetTargetItems(); TargetCalc target_calc; double n1 = target_calc.DetermineTargetHistoryLength(); double n2 = n1 + n1; int dotSpotX1; int dotSpotY1; int dotSpotX2; int dotSpotY2; int deltaSpotY; int deltaSpotX; double dist = sqrt(((target->endPointX - x) * (target->endPointX - x)) + ((target->endPointY - y) * (target->endPointY - y))); double r1 = n1 / dist; double r2 = n2 / dist; dotSpotX1 = (int) (r1 * target->endPointX + (1 - r1) * x); dotSpotY1 = (int) (r1 * target->endPointY + (1 - r1) * y); dotSpotX2 = (int) (r2 * target->endPointX + (1 - r2) * x); dotSpotY2 = (int) (r2 * target->endPointY + (1 - r2) * y); deltaSpotX = dotSpotX2 - dotSpotX1; deltaSpotY = dotSpotY2 - dotSpotY1; int i; for (i = 1; i < 6; i++) { int targetHistoryX = target->centerX - (deltaSpotX * i); int targetHistoryY = target->centerY - (deltaSpotY * i); painter->drawEllipse(targetHistoryX-1, targetHistoryY+2, 2, 2); qDebug() << "\nThe history points are x: " << targetHistoryX << " y: " << targetHistoryY << endl; } // draw target interception //TargetInterception(); // kill painter //painter->end(); } void OGLWidget::DrawTargetVelocityLine(int x, int y, QPainter *painter) { TARGET *target = GetTargetItems(); MK309_TMA *TMA_item = GetTMAitems(); TargetCalc target_calc; double convertToDegree = PI / 180; //qDebug() << "target->CT = " << target->CT << "target->DMHT = " << target->DMHT << endl; target->Vx = sin(target->CT * convertToDegree); target->Vy = cos(target->CT * convertToDegree); //qDebug() << "Vx: " << target->Vx << " Vy: \n" << target->Vy << endl; target->endPointX = (target->Vx * x) + x; target->endPointY = (target->Vy * y) + y; //qDebug() << " target endpoint x: " << target->endPointX << " y: " << target->endPointY << endl; target_calc.CalcTargetVelocityEndPoint(x, y); // fix the target endpoint Y painter->drawLine(x,y,target->endPointX,target->endPointY); //qDebug() << " starting point of x: " << x << " y: " << y << endl; //painter->end(); } void OGLWidget::unknownSurfaceTarget(int x, int y) { // target point center at (x,y) QPainter usTargetPainter(this); QPen myPen(Qt::blue, 1, Qt::SolidLine); usTargetPainter.setPen(myPen); usTargetPainter.drawLine(x+7,y,x-7,y); usTargetPainter.drawLine(x-7,y,x-7,y-14); usTargetPainter.drawLine(x+7,y,x+7,y-14); usTargetPainter.drawPoint(x,y-12); usTargetPainter.end(); } void OGLWidget::knownGoodSurfaceTarget(int x, int y) { // Use QPainter drawArc QPainter goodTargetPainter(this); QPen myPen(Qt::blue, 1, Qt::SolidLine); goodTargetPainter.setPen(myPen); int startAngle = 160 * 16; int spanAngle = 225 * 16; goodTargetPainter.drawArc(x-7,y,15,15,startAngle,spanAngle); goodTargetPainter.drawPoint(x+1,y+5); goodTargetPainter.end(); } void OGLWidget::torpedoInterceptPoint(int x, int y) { // Use QPainter drawArc QPainter TIPPainter(this); QPen myPen(Qt::yellow, 1, Qt::SolidLine); TIPPainter.setPen(myPen); int startAngle = 160 * 16; int spanAngle = 225 * 16; // draw first arc TIPPainter.drawArc(x-10,y,10,10,startAngle,spanAngle); // draw 2nd arc TIPPainter.drawArc(x,y,10,10,startAngle,spanAngle); QPen myPen2(Qt::white, 1, Qt::SolidLine); TIPPainter.setPen(myPen2); //TIPPainter.drawPoint(x+8,y+5); TIPPainter.end(); } void OGLWidget::torpedoInWater(int x, int y) { QRectF tiw(x-5,y,10,10); // target point center at (x,y) QPainter TIWPainter(this); QPen myPen(Qt::green, 1, Qt::SolidLine); TIWPainter.setPen(myPen); TIWPainter.drawEllipse(tiw); TIWPainter.drawLine(x,y+5,x,y+17); //TIWPainter.drawPoint(x,y+5);// center of tiw circle TIWPainter.drawLine(x,y+5,x+11,y-8); TIWPainter.drawLine(x,y+5,x-11,y-8); TIWPainter.end(); } void OGLWidget::resizeGL(int w, int h) { glViewport(0,0,w,h); glMatrixMode(GL_PROJECTION); glLoadIdentity(); gluPerspective(45, (float)w/h, 0.01, 100.0); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); gluLookAt(0,0,5,0,0,0,0,1,0); }