On Freitag, 9. August 2013 10:18:02 CEST, Jan Kundrát wrote:

Qt5's QTimer contains a special case for QTimer::singleShot(0) (I suspect a lot of stuff would break if it was removed).
s/a/the/ - and yes, probably removing the special case wasn't a good idea.

I'd like to improve my Qt-fu, so I'm curious -- why do you consider this an abuse?

Well, you "abuse" the QTimer API to call QMetaObject.
QTimer more or less needs to special case "0" so if you call
QTimer::singleShot(timeout, foo, SLOT(bar())) and "timeout" is -randomly- 0, it 
doesn't block (thus act like for every other value of timeout)

If one would consider the "QMetaObject API too cumbersome", QObject (or any inheritence 
or a namespace or you use preproc #define's) could just have a static QObject::defer(QObject *o, 
const char *member) any maybe even a nonstatic QObject::defer(const char *member), so you would 
just call defer("bar"), what is far more condensed and explicit than either calling 
QTimer or QMetaObject.

I don't say it's terribly wrong to use QTimer, but saying
#include <QTimer>
QTimer::singleShot(0, foo, SLOT(bar()))

only to have it call
QMetaObject::invokeMetod(foo, "bar", Qt::QueuedConnection)

is at least not the direct way.


Finally and ultimately and why I tend to call "this some sort of abuse":
I've seen such too often (not talking about trojita here, but in general)
--------------------------

int m_foo;
private slots:
void bar(); // helper to call fooBar(int) delayed
void fooBar(int);

m_foo = foo;
QTimer::singleShot(0, this, SLOT(bar()));

void bar() {
  fooBar(m_foo);
}

-------

What clearly says:
you used QTimer because you either didn't know about QMO or you opened the API 
page for QMO, got scared and ran away ;-)

Cheers,
Thomas

PS:
this is your project and if you say "i like QTimer::singleShot better and want  to 
use it as long as it works" that's just fine - i mentioned an opinion, not a dogma.

Reply via email to