Trolltech Home | Qt-interest Home | Recent Threads | All Threads | Author | Date
All threads index page 5

Qt-interest Archive, May 2008
QThread & QTimer - where does the slot run?


Message 1 in thread

I am designing a system where I want to check a port
to see if a particular event has occurred and then process
it. I wanted to stick this in an independent thread: :
(I'm just giving an outline - not full code)

Class DeviceStatus :: QThread
{
   Q_OBJECT

   QTimer* timer;
...
...
};

DeviceStatus::DeviceStatus() 
{
    timer = 0;
}
DeviceStatus::~DeviceStatus()
{
   timer->stop();
   quit();
}
void DeviceStatus::run()
{
    timer = new QTimer;
    connect(timer, SIGNAL(timeout()), this, SLOT(CheckForEvent()));
    timer->start(40);
    exec();
}
void DeviceStatus::CheckForEvent()
{
....
....

     if(bEvent[i])
         ProcessEvent(i);
}      
void DeviceStatus::ProcessEvent(int k)
{
   // do lots of stuff 
   // emit signals depending on type of event
}

Now if I understand the documentation (which is not very clear on this
issue), the CheckForEvent slot will actually run in the thread in which 
DeviceStatus does - NOT in the thread created by run (am I right or
wrong on this?) which seems to make a timer in a thread essentially
useless.

I thought that the only way around this was the following:

void DeviceStatus::run()
{
    forever
    {
      if(bAbort)  // add in the appropriate bool bAbort in constructor and destructor
          return;
      QTime t;
      t->start();
      if(CheckForEvent())  //change the return to bool
         ProcessEvent();
      int duration = 40-(t->elapsed());
      if(duration > 0)
          msleep(duration);
   }
}

I'd like comments from those of you more expert than I with
Qt (i.e. most of you!)

DS


      __________________________________________________________________
Looking for the perfect gift? Give the gift of Flickr! 

http://www.flickr.com/gift/

--
 [ signature omitted ] 

Message 2 in thread

David Scriven wrote:
>I am designing a system where I want to check a port
>to see if a particular event has occurred and then process
>it. I wanted to stick this in an independent thread: :
>(I'm just giving an outline - not full code)
[snip code]

>Now if I understand the documentation (which is not very clear on this
>issue), the CheckForEvent slot will actually run in the thread in which
>DeviceStatus does - NOT in the thread created by run (am I right or
>wrong on this?) which seems to make a timer in a thread essentially
>useless.

Your question did not make much sense. I think you're confusing the 
concepts.

Your DeviceStatus class is a QThread. When you call QThread::start(), it 
creates a new thread and calls the run() function from it.

When you set up an AutoConnection (the default connection type), each slot 
is always called in the thread in which the object was created. So, in 
your example, your QTimer object belongs to the DeviceStatus thread, but 
the DeviceStatus object itself doesn't.

So, yeah, the CheckForEvent slot is run in the thread that created 
DeviceStatus, not the DeviceStatus thread.

>I thought that the only way around this was the following:
>
>void DeviceStatus::run()
>{
>    forever
>    {
>      if(bAbort)  // add in the appropriate bool bAbort in constructor
> and destructor return;
>      QTime t;
>      t->start();
>      if(CheckForEvent())  //change the return to bool
>         ProcessEvent();
>      int duration = 40-(t->elapsed());
>      if(duration > 0)
>          msleep(duration);
>   }
>}
>
>I'd like comments from those of you more expert than I with
>Qt (i.e. most of you!)

Looks fine.

Except that the number "40 milliseconds" seems awfully arbitrary to me. 
Usually, arbitrary sleeps and timers indicate a flaw in the design (not 
always, but usually). Maybe you want to take a look at that again.

-- 
 [ signature omitted ] 

Attachment: signature.asc
Description: This is a digitally signed message part.