Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. multi precise timer delay functions compare

multi precise timer delay functions compare

Scheduled Pinned Locked Moved Solved General and Desktop
9 Posts 5 Posters 827 Views
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • Q Offline
    Q Offline
    QtTester
    wrote on last edited by
    #1

    Hi guys:
    I have tried these code for a delay function, finally found the last one is the most precise delay.
    However, in a thread , the delay sometimes may not be the result i found.
    for example , simpleWait(50) will delay for 50 msec. but sometimes it will delay 100 msec.
    why? any help will be appreciated.

    void MyAction::simpleWait(int msec)
    {
        if(msec <= 0)
            return;
    
      // func1: tick has 10ms
        /*QTime dieTime = QTime::currentTime().addMSecs(msec);
     
        while (QTime::currentTime() < dieTime)
            QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);*/
     
        // func2: more 2~3sec than wanted
        /*QDeadlineTimer timer(msec,Qt::PreciseTimer);
        while(!timer.hasExpired())
            QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);*/
     
        // func3: longer
        /*QElapsedTimer timer;
     
        timer.start();
        while(!timer.hasExpired(msec))
            QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);*/
    
       // the precise one works for me:
        QTimer timer;
    
        timer.setTimerType(Qt::PreciseTimer);
        timer.start(msec);
        while(timer.remainingTime() > 0)
            QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);
    }
    

    I use this code to measure tick:

    qint64 start = QDateTime::currentMSecsSinceEpoch();
    simpleWait(50);
    qDebug()<<"move:" <<(QDateTime::currentMSecsSinceEpoch() - start );
    // most delay = 50, sometimes = 100 or more
    
    JKSHJ 1 Reply Last reply
    0
    • Q QtTester

      Hi guys:
      I have tried these code for a delay function, finally found the last one is the most precise delay.
      However, in a thread , the delay sometimes may not be the result i found.
      for example , simpleWait(50) will delay for 50 msec. but sometimes it will delay 100 msec.
      why? any help will be appreciated.

      void MyAction::simpleWait(int msec)
      {
          if(msec <= 0)
              return;
      
        // func1: tick has 10ms
          /*QTime dieTime = QTime::currentTime().addMSecs(msec);
       
          while (QTime::currentTime() < dieTime)
              QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);*/
       
          // func2: more 2~3sec than wanted
          /*QDeadlineTimer timer(msec,Qt::PreciseTimer);
          while(!timer.hasExpired())
              QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);*/
       
          // func3: longer
          /*QElapsedTimer timer;
       
          timer.start();
          while(!timer.hasExpired(msec))
              QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);*/
      
         // the precise one works for me:
          QTimer timer;
      
          timer.setTimerType(Qt::PreciseTimer);
          timer.start(msec);
          while(timer.remainingTime() > 0)
              QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);
      }
      

      I use this code to measure tick:

      qint64 start = QDateTime::currentMSecsSinceEpoch();
      simpleWait(50);
      qDebug()<<"move:" <<(QDateTime::currentMSecsSinceEpoch() - start );
      // most delay = 50, sometimes = 100 or more
      
      JKSHJ Offline
      JKSHJ Offline
      JKSH
      Moderators
      wrote on last edited by
      #2

      @QtTester said in multi precise timer delay functions compare:

      why?

      What is your operating system?

      Windows is a non-deterministic, non-real-time OS so it doesn't guarantee timings. The OS can decide to allocate CPU time to other programs, for example.

      If it is important for you to always get exactly 50ms, then you need a real-time operating system such as https://www.linux.com/news/inside-real-time-linux/

          while(timer.remainingTime() > 0)
              QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);
      

      This code is a bit like a spinlock (https://en.wikipedia.org/wiki/Spinlock ) which is quite inefficient and burns your CPU.

      May I ask why you need a "delay" function? Asynchronous, event-driven programming is usually better.

      Qt Doc Search for browsers: forum.qt.io/topic/35616/web-browser-extension-for-improved-doc-searches

      Q 1 Reply Last reply
      3
      • JKSHJ JKSH

        @QtTester said in multi precise timer delay functions compare:

        why?

        What is your operating system?

        Windows is a non-deterministic, non-real-time OS so it doesn't guarantee timings. The OS can decide to allocate CPU time to other programs, for example.

        If it is important for you to always get exactly 50ms, then you need a real-time operating system such as https://www.linux.com/news/inside-real-time-linux/

            while(timer.remainingTime() > 0)
                QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);
        

        This code is a bit like a spinlock (https://en.wikipedia.org/wiki/Spinlock ) which is quite inefficient and burns your CPU.

        May I ask why you need a "delay" function? Asynchronous, event-driven programming is usually better.

        Q Offline
        Q Offline
        QtTester
        wrote on last edited by
        #3

        @JKSH thanks for reply.
        My Os is Windows 10. qt is 15.4.1.
        delay is needed to check external hardware's position, for example the servo motor runs to some position.

        int32_t MyAction::moveXY(uint32_t motorId1,uint32_t motorId2, int32_t pos1, int32_t pos2,int spdLevel,uint32_t timeOut)
        {
            int32_t ret = ERR_NONE;
            uint32_t tOut = 0;
        
            ret = m_mcBase->absMove(motorId1, pos1, spdLevel);
            if(ret == ERR_NONE)
                ret = m_mcBase->absMove(motorId2, pos2, spdLevel);
            if(ret != ERR_NONE)
                return ret;
        
          // check motor position 
            while(true){
                if(m_mcBase->checkPositionDone(motorId1) && m_mcBase->checkPositionDone(motorId2))
                    break;
        
                simpleWait(1);
                if(tOut++ > timeOut){
                    return ERR_TIME_OUT;
                }
            }
            return ret;
        }
        

        Finally , I found if QTimer is a global member, like QTimer *m_threadTimer, the function works fine.
        Do not know why when it is as a local variable it will not work sometimes.

        JKSHJ kshegunovK 2 Replies Last reply
        0
        • Q QtTester

          @JKSH thanks for reply.
          My Os is Windows 10. qt is 15.4.1.
          delay is needed to check external hardware's position, for example the servo motor runs to some position.

          int32_t MyAction::moveXY(uint32_t motorId1,uint32_t motorId2, int32_t pos1, int32_t pos2,int spdLevel,uint32_t timeOut)
          {
              int32_t ret = ERR_NONE;
              uint32_t tOut = 0;
          
              ret = m_mcBase->absMove(motorId1, pos1, spdLevel);
              if(ret == ERR_NONE)
                  ret = m_mcBase->absMove(motorId2, pos2, spdLevel);
              if(ret != ERR_NONE)
                  return ret;
          
            // check motor position 
              while(true){
                  if(m_mcBase->checkPositionDone(motorId1) && m_mcBase->checkPositionDone(motorId2))
                      break;
          
                  simpleWait(1);
                  if(tOut++ > timeOut){
                      return ERR_TIME_OUT;
                  }
              }
              return ret;
          }
          

          Finally , I found if QTimer is a global member, like QTimer *m_threadTimer, the function works fine.
          Do not know why when it is as a local variable it will not work sometimes.

          JKSHJ Offline
          JKSHJ Offline
          JKSH
          Moderators
          wrote on last edited by
          #4

          @QtTester said in multi precise timer delay functions compare:

          Finally , I found if QTimer is a global member, like QTimer *m_threadTimer, the function works fine.
          Do not know why when it is as a local variable it will not work sometimes.

          Well, it is expensive to create and destroy a QObject several hundred times per second.

          delay is needed to check external hardware's position, for example the servo motor runs to some position.

          Could you not connect the QTimer::timeout() signal to run a slot at fixed intervals to check the position?

          Qt Doc Search for browsers: forum.qt.io/topic/35616/web-browser-extension-for-improved-doc-searches

          Q 1 Reply Last reply
          0
          • JKSHJ JKSH

            @QtTester said in multi precise timer delay functions compare:

            Finally , I found if QTimer is a global member, like QTimer *m_threadTimer, the function works fine.
            Do not know why when it is as a local variable it will not work sometimes.

            Well, it is expensive to create and destroy a QObject several hundred times per second.

            delay is needed to check external hardware's position, for example the servo motor runs to some position.

            Could you not connect the QTimer::timeout() signal to run a slot at fixed intervals to check the position?

            Q Offline
            Q Offline
            QtTester
            wrote on last edited by
            #5

            @JKSH
            We donot know when the position is done ,and need to return as soon as possible, 1 msec delay is the best way.
            time is money in factory, And if you donot use the CPU , it still does nothing right there :-)

            jsulmJ 1 Reply Last reply
            0
            • Q QtTester

              @JKSH
              We donot know when the position is done ,and need to return as soon as possible, 1 msec delay is the best way.
              time is money in factory, And if you donot use the CPU , it still does nothing right there :-)

              jsulmJ Offline
              jsulmJ Offline
              jsulm
              Lifetime Qt Champion
              wrote on last edited by kshegunov
              #6

              @QtTester said in multi precise timer delay functions compare:

              1 msec delay is the best way

              You can can't have 1msec timeout with QTimer...

              [Edit: Typo fixed ~kshegunov]

              https://forum.qt.io/topic/113070/qt-code-of-conduct

              1 Reply Last reply
              0
              • Q QtTester

                @JKSH thanks for reply.
                My Os is Windows 10. qt is 15.4.1.
                delay is needed to check external hardware's position, for example the servo motor runs to some position.

                int32_t MyAction::moveXY(uint32_t motorId1,uint32_t motorId2, int32_t pos1, int32_t pos2,int spdLevel,uint32_t timeOut)
                {
                    int32_t ret = ERR_NONE;
                    uint32_t tOut = 0;
                
                    ret = m_mcBase->absMove(motorId1, pos1, spdLevel);
                    if(ret == ERR_NONE)
                        ret = m_mcBase->absMove(motorId2, pos2, spdLevel);
                    if(ret != ERR_NONE)
                        return ret;
                
                  // check motor position 
                    while(true){
                        if(m_mcBase->checkPositionDone(motorId1) && m_mcBase->checkPositionDone(motorId2))
                            break;
                
                        simpleWait(1);
                        if(tOut++ > timeOut){
                            return ERR_TIME_OUT;
                        }
                    }
                    return ret;
                }
                

                Finally , I found if QTimer is a global member, like QTimer *m_threadTimer, the function works fine.
                Do not know why when it is as a local variable it will not work sometimes.

                kshegunovK Offline
                kshegunovK Offline
                kshegunov
                Moderators
                wrote on last edited by
                #7

                @QtTester said in multi precise timer delay functions compare:

                delay is needed to check external hardware's position, for example the servo motor runs to some position.

                That's why drivers (and interrupts) were invented. Do you have a driver with a corresponding client library for said machine?

                Read and abide by the Qt Code of Conduct

                Q 1 Reply Last reply
                2
                • kshegunovK kshegunov

                  @QtTester said in multi precise timer delay functions compare:

                  delay is needed to check external hardware's position, for example the servo motor runs to some position.

                  That's why drivers (and interrupts) were invented. Do you have a driver with a corresponding client library for said machine?

                  Q Offline
                  Q Offline
                  QtTester
                  wrote on last edited by QtTester
                  #8

                  @kshegunov said in multi precise timer delay functions compare:

                  That's why drivers (and interrupts) were invented. Do you have a driver with a corresponding client library for said machine?

                  driver still does the same thing to check flag and signal app.

                  @jsulm said in multi precise timer delay functions compare:

                  You can can't have 1msec timeout with QTimer...

                  seems works for me.

                  jeremy_kJ 1 Reply Last reply
                  0
                  • Q QtTester

                    @kshegunov said in multi precise timer delay functions compare:

                    That's why drivers (and interrupts) were invented. Do you have a driver with a corresponding client library for said machine?

                    driver still does the same thing to check flag and signal app.

                    @jsulm said in multi precise timer delay functions compare:

                    You can can't have 1msec timeout with QTimer...

                    seems works for me.

                    jeremy_kJ Online
                    jeremy_kJ Online
                    jeremy_k
                    wrote on last edited by
                    #9

                    If high precision busy waiting is the goal, QDeadlineTimer is a better choice than QTimer.

                    Asking a question about code? http://eel.is/iso-c++/testcase/

                    1 Reply Last reply
                    3

                    • Login

                    • Login or register to search.
                    • First post
                      Last post
                    0
                    • Categories
                    • Recent
                    • Tags
                    • Popular
                    • Users
                    • Groups
                    • Search
                    • Get Qt Extensions
                    • Unsolved