QSingleShotTimer: de-inline [1/4]: add .cpp file
... and split code between header and .cpp file. The goal here is to just sort the lines into header and .cpp, not to change them, so temporarily define inline away. This allows git to reliably track this as copy instead of independent changes. The inline define will be cleaned up in a follow-up patch; fixing inline and re-indenting would reduce the similarity score too much. Also includemocs and move qsingleshottimer* to the (lexicographically) correct position in CMakeLists.txt's SOURCES. Fixes -Wweak-vtable (and therefore prevents this class from being used outside QtCore (not exported atm)). Amends e0573e73645c0f57e46332a94160e28eb6c8ebac. Change-Id: Ia5304434fd1c9a56eb6f2f1988bd14a80ab61442 Reviewed-by: Thiago Macieira <thiago.macieira@intel.com> (cherry picked from commit 1ef5f50e28edd1bdfcb3828c3858640ba347b2bd) Reviewed-by: Qt Cherry-pick Bot <cherrypick_bot@qt-project.org>
This commit is contained in:
parent
678c839575
commit
e3da82d3b6
@ -176,10 +176,10 @@ qt_internal_add_module(Core
|
||||
kernel/qpropertyprivate.h
|
||||
kernel/qsequentialiterable.cpp kernel/qsequentialiterable.h
|
||||
kernel/qsignalmapper.cpp kernel/qsignalmapper.h
|
||||
kernel/qsingleshottimer.cpp kernel/qsingleshottimer_p.h
|
||||
kernel/qsocketnotifier.cpp kernel/qsocketnotifier.h
|
||||
kernel/qsystemerror.cpp kernel/qsystemerror_p.h
|
||||
kernel/qtestsupport_core.cpp kernel/qtestsupport_core.h
|
||||
kernel/qsingleshottimer_p.h
|
||||
kernel/qtimer.cpp kernel/qtimer.h kernel/qtimer_p.h
|
||||
kernel/qtranslator.cpp kernel/qtranslator.h kernel/qtranslator_p.h
|
||||
kernel/qvariant.cpp kernel/qvariant.h kernel/qvariant_p.h
|
||||
|
89
src/corelib/kernel/qsingleshottimer.cpp
Normal file
89
src/corelib/kernel/qsingleshottimer.cpp
Normal file
@ -0,0 +1,89 @@
|
||||
// Copyright (C) 2022 The Qt Company Ltd.
|
||||
// Copyright (C) 2016 Intel Corporation.
|
||||
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
|
||||
|
||||
#include <QtCore/private/qsingleshottimer_p.h>
|
||||
|
||||
#include "qabstracteventdispatcher.h"
|
||||
#include "qcoreapplication.h"
|
||||
#include "qmetaobject_p.h"
|
||||
#include "private/qnumeric_p.h"
|
||||
|
||||
#include <chrono>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
QSingleShotTimer::QSingleShotTimer(Duration interval, Qt::TimerType timerType,
|
||||
const QObject *r, const char *member)
|
||||
: QObject(QAbstractEventDispatcher::instance())
|
||||
{
|
||||
connect(this, SIGNAL(timeout()), r, member);
|
||||
startTimerForReceiver(interval, timerType, r);
|
||||
}
|
||||
|
||||
QSingleShotTimer::QSingleShotTimer(Duration interval, Qt::TimerType timerType,
|
||||
const QObject *r, QtPrivate::QSlotObjectBase *slotObj)
|
||||
: QObject(QAbstractEventDispatcher::instance())
|
||||
{
|
||||
int signal_index = QMetaObjectPrivate::signalOffset(&staticMetaObject);
|
||||
Q_ASSERT(QMetaObjectPrivate::signal(&staticMetaObject, signal_index).name() == "timeout");
|
||||
QObjectPrivate::connectImpl(this, signal_index, r ? r : this, nullptr, slotObj,
|
||||
Qt::AutoConnection, nullptr, &staticMetaObject);
|
||||
|
||||
startTimerForReceiver(interval, timerType, r);
|
||||
}
|
||||
|
||||
QSingleShotTimer::~QSingleShotTimer()
|
||||
{
|
||||
if (timerId > Qt::TimerId::Invalid)
|
||||
killTimer(timerId);
|
||||
}
|
||||
|
||||
/*
|
||||
Move the timer, and the dispatching and handling of the timer event, into
|
||||
the same thread as where it will be handled, so that it fires reliably even
|
||||
if the thread that set up the timer is busy.
|
||||
*/
|
||||
void QSingleShotTimer::startTimerForReceiver(Duration interval, Qt::TimerType timerType,
|
||||
const QObject *receiver)
|
||||
{
|
||||
if (receiver && receiver->thread() != thread()) {
|
||||
// Avoid leaking the QSingleShotTimer instance in case the application exits before the
|
||||
// timer fires
|
||||
connect(QCoreApplication::instance(), &QCoreApplication::aboutToQuit, this,
|
||||
&QObject::deleteLater);
|
||||
setParent(nullptr);
|
||||
moveToThread(receiver->thread());
|
||||
|
||||
QDeadlineTimer deadline(interval, timerType);
|
||||
auto invokable = [this, deadline, timerType] {
|
||||
if (deadline.hasExpired()) {
|
||||
Q_EMIT timeout();
|
||||
} else {
|
||||
timerId = Qt::TimerId{startTimer(deadline.remainingTimeAsDuration(), timerType)};
|
||||
}
|
||||
};
|
||||
QMetaObject::invokeMethod(this, invokable, Qt::QueuedConnection);
|
||||
} else {
|
||||
timerId = Qt::TimerId{startTimer(interval, timerType)};
|
||||
}
|
||||
}
|
||||
|
||||
void QSingleShotTimer::timerEvent(QTimerEvent *)
|
||||
{
|
||||
// need to kill the timer _before_ we emit timeout() in case the
|
||||
// slot connected to timeout calls processEvents()
|
||||
if (timerId > Qt::TimerId::Invalid)
|
||||
killTimer(std::exchange(timerId, Qt::TimerId::Invalid));
|
||||
|
||||
Q_EMIT timeout();
|
||||
|
||||
// we would like to use delete later here, but it feels like a
|
||||
// waste to post a new event to handle this event, so we just unset the flag
|
||||
// and explicitly delete...
|
||||
delete this;
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#include "moc_qsingleshottimer_p.cpp"
|
@ -31,6 +31,7 @@ class QSingleShotTimer : public QObject
|
||||
|
||||
Qt::TimerId timerId = Qt::TimerId::Invalid;
|
||||
|
||||
#define inline
|
||||
public:
|
||||
// use the same duration type
|
||||
using Duration = QAbstractEventDispatcher::Duration;
|
||||
@ -63,79 +64,9 @@ Q_SIGNALS:
|
||||
|
||||
private:
|
||||
inline void timerEvent(QTimerEvent *) override;
|
||||
#undef inline
|
||||
};
|
||||
|
||||
QSingleShotTimer::QSingleShotTimer(Duration interval, Qt::TimerType timerType,
|
||||
const QObject *r, const char *member)
|
||||
: QObject(QAbstractEventDispatcher::instance())
|
||||
{
|
||||
connect(this, SIGNAL(timeout()), r, member);
|
||||
startTimerForReceiver(interval, timerType, r);
|
||||
}
|
||||
|
||||
QSingleShotTimer::QSingleShotTimer(Duration interval, Qt::TimerType timerType,
|
||||
const QObject *r, QtPrivate::QSlotObjectBase *slotObj)
|
||||
: QObject(QAbstractEventDispatcher::instance())
|
||||
{
|
||||
int signal_index = QMetaObjectPrivate::signalOffset(&staticMetaObject);
|
||||
Q_ASSERT(QMetaObjectPrivate::signal(&staticMetaObject, signal_index).name() == "timeout");
|
||||
QObjectPrivate::connectImpl(this, signal_index, r ? r : this, nullptr, slotObj,
|
||||
Qt::AutoConnection, nullptr, &staticMetaObject);
|
||||
|
||||
startTimerForReceiver(interval, timerType, r);
|
||||
}
|
||||
|
||||
QSingleShotTimer::~QSingleShotTimer()
|
||||
{
|
||||
if (timerId > Qt::TimerId::Invalid)
|
||||
killTimer(timerId);
|
||||
}
|
||||
|
||||
/*
|
||||
Move the timer, and the dispatching and handling of the timer event, into
|
||||
the same thread as where it will be handled, so that it fires reliably even
|
||||
if the thread that set up the timer is busy.
|
||||
*/
|
||||
void QSingleShotTimer::startTimerForReceiver(Duration interval, Qt::TimerType timerType,
|
||||
const QObject *receiver)
|
||||
{
|
||||
if (receiver && receiver->thread() != thread()) {
|
||||
// Avoid leaking the QSingleShotTimer instance in case the application exits before the
|
||||
// timer fires
|
||||
connect(QCoreApplication::instance(), &QCoreApplication::aboutToQuit, this,
|
||||
&QObject::deleteLater);
|
||||
setParent(nullptr);
|
||||
moveToThread(receiver->thread());
|
||||
|
||||
QDeadlineTimer deadline(interval, timerType);
|
||||
auto invokable = [this, deadline, timerType] {
|
||||
if (deadline.hasExpired()) {
|
||||
Q_EMIT timeout();
|
||||
} else {
|
||||
timerId = Qt::TimerId{startTimer(deadline.remainingTimeAsDuration(), timerType)};
|
||||
}
|
||||
};
|
||||
QMetaObject::invokeMethod(this, invokable, Qt::QueuedConnection);
|
||||
} else {
|
||||
timerId = Qt::TimerId{startTimer(interval, timerType)};
|
||||
}
|
||||
}
|
||||
|
||||
void QSingleShotTimer::timerEvent(QTimerEvent *)
|
||||
{
|
||||
// need to kill the timer _before_ we emit timeout() in case the
|
||||
// slot connected to timeout calls processEvents()
|
||||
if (timerId > Qt::TimerId::Invalid)
|
||||
killTimer(std::exchange(timerId, Qt::TimerId::Invalid));
|
||||
|
||||
Q_EMIT timeout();
|
||||
|
||||
// we would like to use delete later here, but it feels like a
|
||||
// waste to post a new event to handle this event, so we just unset the flag
|
||||
// and explicitly delete...
|
||||
delete this;
|
||||
}
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#endif // QSINGLESHOTTIMER_P_H
|
||||
|
Loading…
x
Reference in New Issue
Block a user