mirror of
https://github.com/Mahdi-zarei/nekoray.git
synced 2025-12-19 13:50:12 +08:00
Fix threading issues
This commit is contained in:
parent
16d951eed1
commit
546b023dbc
@ -167,11 +167,11 @@ void ActivateWindow(QWidget *w);
|
||||
|
||||
//
|
||||
|
||||
void runOnUiThread(const std::function<void()> &callback);
|
||||
void runOnUiThread(const std::function<void()> &callback, bool wait = false);
|
||||
|
||||
void runOnNewThread(const std::function<void()> &callback);
|
||||
void runOnNewThread(const std::function<void()> &callback, bool wait = false);
|
||||
|
||||
void runOnThread(const std::function<void()> &callback, QObject *parent);
|
||||
void runOnThread(const std::function<void()> &callback, QObject *parent, bool wait = false);
|
||||
|
||||
template<typename EMITTER, typename SIGNAL, typename RECEIVER, typename ReceiverFunc>
|
||||
inline void connectOnce(EMITTER *emitter, SIGNAL signal, RECEIVER *receiver, ReceiverFunc f,
|
||||
|
||||
@ -249,38 +249,84 @@ void ActivateWindow(QWidget *w) {
|
||||
w->activateWindow();
|
||||
}
|
||||
|
||||
void runOnUiThread(const std::function<void()> &callback) {
|
||||
void runOnUiThread(const std::function<void()> &callback, bool wait) {
|
||||
// any thread
|
||||
auto *timer = new QTimer();
|
||||
auto thread = mainwindow->thread();
|
||||
timer->moveToThread(thread);
|
||||
timer->setSingleShot(true);
|
||||
QObject::connect(timer, &QTimer::timeout, [=]() {
|
||||
|
||||
QEventLoop loop;
|
||||
QObject::connect(timer, &QTimer::timeout, [=, &loop]() {
|
||||
// main thread
|
||||
callback();
|
||||
timer->deleteLater();
|
||||
|
||||
if (wait)
|
||||
{
|
||||
QMetaObject::invokeMethod(&loop, "quit", Qt::QueuedConnection);
|
||||
}
|
||||
});
|
||||
QMetaObject::invokeMethod(timer, "start", Qt::QueuedConnection, Q_ARG(int, 0));
|
||||
|
||||
if (wait && QThread::currentThread() != thread) {
|
||||
loop.exec();
|
||||
}
|
||||
}
|
||||
|
||||
void runOnNewThread(const std::function<void()> &callback) {
|
||||
createQThread(callback)->start();
|
||||
void runOnNewThread(const std::function<void()> &callback, bool wait) {
|
||||
auto *timer = new QTimer();
|
||||
auto thread = new QThread();
|
||||
timer->moveToThread(thread);
|
||||
timer->setSingleShot(true);
|
||||
|
||||
thread->start();
|
||||
QObject::connect(thread, &QThread::finished, thread, &QObject::deleteLater);
|
||||
|
||||
QEventLoop loop;
|
||||
QObject::connect(timer, &QTimer::timeout, [=, &loop]() {
|
||||
callback();
|
||||
timer->deleteLater();
|
||||
QMetaObject::invokeMethod(thread, "quit", Qt::QueuedConnection);
|
||||
|
||||
if (wait)
|
||||
{
|
||||
QMetaObject::invokeMethod(&loop, "quit", Qt::QueuedConnection);
|
||||
}
|
||||
});
|
||||
QMetaObject::invokeMethod(timer, "start", Qt::QueuedConnection, Q_ARG(int, 0));
|
||||
|
||||
if (wait && QThread::currentThread() != thread) {
|
||||
loop.exec();
|
||||
}
|
||||
}
|
||||
|
||||
void runOnThread(const std::function<void()> &callback, QObject *parent) {
|
||||
void runOnThread(const std::function<void()> &callback, QObject *parent, bool wait) {
|
||||
auto *timer = new QTimer();
|
||||
auto thread = dynamic_cast<QThread *>(parent);
|
||||
if (thread == nullptr) {
|
||||
timer->moveToThread(parent->thread());
|
||||
thread = parent->thread();
|
||||
} else {
|
||||
timer->moveToThread(thread);
|
||||
}
|
||||
timer->setSingleShot(true);
|
||||
QObject::connect(timer, &QTimer::timeout, [=]() {
|
||||
|
||||
QEventLoop loop;
|
||||
QObject::connect(timer, &QTimer::timeout, [=, &loop]() {
|
||||
callback();
|
||||
timer->deleteLater();
|
||||
|
||||
if (wait)
|
||||
{
|
||||
QMetaObject::invokeMethod(&loop, "quit", Qt::QueuedConnection);
|
||||
}
|
||||
});
|
||||
QMetaObject::invokeMethod(timer, "start", Qt::QueuedConnection, Q_ARG(int, 0));
|
||||
|
||||
if (wait && QThread::currentThread() != thread) {
|
||||
loop.exec();
|
||||
}
|
||||
}
|
||||
|
||||
void setTimeout(const std::function<void()> &callback, QObject *obj, int timeout) {
|
||||
|
||||
@ -62,7 +62,10 @@ namespace Configs_sys {
|
||||
if (restarting) return;
|
||||
|
||||
MW_show_log("[Fatal] " + QObject::tr("Core exited, cleaning up..."));
|
||||
runOnUiThread([=, this]
|
||||
{
|
||||
GetMainWindow()->profile_stop(true, true);
|
||||
}, true);
|
||||
|
||||
// Retry rate limit
|
||||
if (coreRestartTimer.isValid()) {
|
||||
|
||||
@ -570,7 +570,10 @@ void MainWindow::profile_start(int _id) {
|
||||
runOnNewThread([=, this] {
|
||||
// stop current running
|
||||
if (running != nullptr) {
|
||||
runOnUiThread([=, this]
|
||||
{
|
||||
profile_stop(false, true, true);
|
||||
}, true);
|
||||
}
|
||||
// do start
|
||||
MW_show_log(">>>>>>>> " + tr("Starting profile %1").arg(ent->bean->DisplayTypeAndName()));
|
||||
|
||||
Loading…
Reference in New Issue
Block a user