Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Qml timer not triggered in the right interval

I've created a timer QML app, and I'm using Timer qml component. The interval is set to 1000 milliseconds (the default one)... but it seems to be working properly only when the app is with focus on it. When I put it in background it seems that it's not triggered every time, and because of that I got some mistakes in the app.

I've tried to find anything related to that in the documentation, but I couldn't The timer code is really simple:

Timer {
    id: timer
    repeat: true
    onTriggered: {msRemaining -= 1000; Core.secondsToText(type);}
}

Anyone has any idea about that and how to fix it?

Versions: Qt 5.2 QML 2.0 OS X 10.9

like image 825
dfranca Avatar asked Mar 31 '14 01:03

dfranca


2 Answers

The QML Timer element is synchronized with the animation timer. Since the animation timer is usually set to 60fps, the resolution of Timer will be at best 16ms. You should also note that in Qt Quick 2 the animation timer is synced to the screen refresh (while in Qt Quick 1 it is hard-coded to 16ms). So when your app runs in background i think the refreshing is stopped and consequently your timer which is synced to screen refresh will stop working properly.

If you want to show elapsed time using a timer as you did is not a good idea because it is not precise. You can use javascript Date() function like:

import QtQuick 2.0

Item  {
    id: root
    width: 200; height: 230

    property double startTime: 0
    property int secondsElapsed: 0

    function restartCounter()  {

            root.startTime = 0;

        }

    function timeChanged()  {
        if(root.startTime==0)
        {
            root.startTime = new Date().getTime(); //returns the number of milliseconds since the epoch (1970-01-01T00:00:00Z);
        }
        var currentTime = new Date().getTime();
        root.secondsElapsed = (currentTime-startTime)/1000;
    }

    Timer  {
        id: elapsedTimer
        interval: 1000;
        running: true;
        repeat: true;
        onTriggered: root.timeChanged()
    }

    Text {
        id: counterText
        text: root.secondsElapsed
    }
}
like image 72
Nejat Avatar answered Sep 24 '22 13:09

Nejat


I have a QML app with a Timer object, running on Android:

  • With Qt 4.8, the Timer works fine when the QML app is in the background.

  • With Qt 5.4, the Timer no longer works when the QML app is in the background. For example, the QML app can no longer receive onTriggered() signal. When the QML app is brought back to the foreground again, the Timer starts working again. It appears that the Qt signals are blocked while the QML app is in the background.

So this looks like a regression in Qt. And the best solution would be to wait until this regression is fixed.

like image 39
jonathanzh Avatar answered Sep 22 '22 13:09

jonathanzh