QTimer acting unreliable with QOpenGLWidget



  • I have a situation where the QTimer or QBasicTimer will not always start running when I use a QOpenGLWidget or a QGLWidget. If you created a basic project with the code I've provided below, I find that about 1 out of every 5 runs, the QTimer refuses to intiialize. Pretty frustrating. Wonder if anyone has any suggestions?

    Here's the code:

    // main.cpp
    #include "MainWindow.h"
    #include <QApplication>
    
    int main(int argc, char *argv[])
    {
        QApplication a(argc, argv);
        MainWindow w;
        w.show();
        return a.exec();
    }
    
    #ifndef MAINWINDOW_H
    #define MAINWINDOW_H
    
    #include <QMainWindow>
    
    class GLView;
    namespace Ui {
        class MainWindow;
    }
    
    class MainWindow : public QMainWindow
    {
        Q_OBJECT
    public:
        explicit MainWindow(QWidget *parent = 0);
        ~MainWindow();
    private:
        Ui::MainWindow *ui;
        int m_timerId;
    
    private:
        GLView *m_glview;
    };
    
    #endif // MAINWINDOW_H@
    
    #include "MainWindow.h"
    #include "ui_MainWindow.h"
    #include <QDebug>
    #include <QGLFormat>
    #include "GLView.h"
    
    MainWindow::MainWindow(QWidget *parent) :
        QMainWindow(parent),
        ui(new Ui::MainWindow)
    {
        ui->setupUi(this);
        m_glview = new GLView(this);
        m_glview->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
        setCentralWidget(m_glview);
    }
    
    MainWindow::~MainWindow()
    {
        delete ui;
    }
    
    #ifndef GLVIEW_H
    #define GLVIEW_H
    #include <QOpenGLWidget>
    #include <QOpenGLFunctions>
    #include <QBasicTimer>
    
    class Trackball;
    class GLView : public QOpenGLWidget, QOpenGLFunctions
    {
        Q_OBJECT
        public:
        explicit GLView(QWidget *parent = 0 );
        ~GLView();
    
    protected:
        void initializeGL();
        void resizeGL(int w, int h);
        void paintGL();
    
        void timerEvent(QTimerEvent *event);
    
    private:
        QBasicTimer   m_timer;
        int m_timerId;
    };
    
    #endif // GLVIEW_H
    
    #include "GLView.h"
    #include <QDebug>
    
    GLView::GLView(QWidget *parent )
    : QOpenGLWidget(parent)
    {
    }
    
    GLView::~GLView()
    {
    }
    
    void GLView::initializeGL()
    {
        qDebug() << "!!!!!!!!!!!!!!!!!!! Initializing GLView !!!!!!!!!!!!!!!!!!!";
        initializeOpenGLFunctions();
        m_timer.start(16, this);
    }
    
    void GLView::resizeGL(int w, int h)
    {
    }
    
    void GLView::paintGL()
    {
        update();
    }
    
    void GLView::timerEvent(QTimerEvent *event)
    {
        makeCurrent();
        static int count = 0;
        qDebug() << "run: " << count++;
    
        glClearColor( 255,
                0,
                0,
                255
                );
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
        doneCurrent();
    }
    

    [edit: updated code style SGaist]


  • Lifetime Qt Champion

    Hi,

    Do you have any error message on the console by any chance ?
    What about using startTimer directly on your widget ?


  • Moderators

    Hi,

    Do you have an infinite loop anywhere in your code? If so, that might block your timer from firing.

    Note that QBasicTimer + timerEvent() only uses Qt::CoarseTimer. Depending on your platform, it might not fire precisely every 16 ms. Consider using QTimer and set it to Qt::PreciseTimer instead.


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.