Qt: Fix window close in nogui mode

This commit is contained in:
Connor McLaughlin 2022-08-29 20:31:29 +10:00
parent 28363af3ff
commit 837495d90f
5 changed files with 37 additions and 24 deletions

View File

@ -162,6 +162,23 @@ void DisplayWidget::updateCursor(bool hidden)
} }
} }
void DisplayWidget::handleCloseEvent(QCloseEvent* event)
{
// Closing the separate widget will either cancel the close, or trigger shutdown.
// In the latter case, it's going to destroy us, so don't let Qt do it first.
if (QtHost::IsSystemValid())
{
QMetaObject::invokeMethod(g_main_window, "requestShutdown", Q_ARG(bool, true), Q_ARG(bool, true),
Q_ARG(bool, false));
}
else
{
QMetaObject::invokeMethod(g_main_window, "requestExit");
}
event->ignore();
}
void DisplayWidget::updateCenterPos() void DisplayWidget::updateCenterPos()
{ {
#ifdef _WIN32 #ifdef _WIN32
@ -348,11 +365,7 @@ bool DisplayWidget::event(QEvent* event)
case QEvent::Close: case QEvent::Close:
{ {
// Closing the separate widget will either cancel the close, or trigger shutdown. handleCloseEvent(static_cast<QCloseEvent*>(event));
// In the latter case, it's going to destroy us, so don't let Qt do it first.
QMetaObject::invokeMethod(g_main_window, "requestShutdown", Q_ARG(bool, true), Q_ARG(bool, true),
Q_ARG(bool, false));
event->ignore();
return true; return true;
} }
@ -416,13 +429,9 @@ DisplayWidget* DisplayContainer::removeDisplayWidget()
bool DisplayContainer::event(QEvent* event) bool DisplayContainer::event(QEvent* event)
{ {
if (event->type() == QEvent::Close) if (event->type() == QEvent::Close && m_display_widget)
{ {
// Closing the separate widget will either cancel the close, or trigger shutdown. m_display_widget->handleCloseEvent(static_cast<QCloseEvent*>(event));
// In the latter case, it's going to destroy us, so don't let Qt do it first.
QMetaObject::invokeMethod(g_main_window, "requestShutdown", Q_ARG(bool, true), Q_ARG(bool, true),
Q_ARG(bool, false));
event->ignore();
return true; return true;
} }

View File

@ -5,6 +5,8 @@
#include <QtWidgets/QWidget> #include <QtWidgets/QWidget>
#include <optional> #include <optional>
class QCloseEvent;
class DisplayWidget final : public QWidget class DisplayWidget final : public QWidget
{ {
Q_OBJECT Q_OBJECT
@ -24,6 +26,8 @@ public:
void updateRelativeMode(bool enabled); void updateRelativeMode(bool enabled);
void updateCursor(bool hidden); void updateCursor(bool hidden);
void handleCloseEvent(QCloseEvent* event);
Q_SIGNALS: Q_SIGNALS:
void windowResizedEvent(int width, int height, float scale); void windowResizedEvent(int width, int height, float scale);
void windowRestoredEvent(); void windowRestoredEvent();

View File

@ -2259,9 +2259,6 @@ void MainWindow::closeEvent(QCloseEvent* event)
return; return;
} }
if (g_emu_thread->isRunningFullscreenUI())
g_emu_thread->stopFullscreenUI();
saveGeometryToConfig(); saveGeometryToConfig();
m_is_closing = true; m_is_closing = true;
@ -2412,7 +2409,7 @@ bool MainWindow::requestShutdown(bool allow_confirm /* = true */, bool allow_sav
// Closing the window should shut down everything. If we don't set the closing flag here, // Closing the window should shut down everything. If we don't set the closing flag here,
// the VM shutdown may not complete by the time closeEvent() is called, leading to a confirm. // the VM shutdown may not complete by the time closeEvent() is called, leading to a confirm.
m_is_closing = true; m_is_closing = true;
close(); QGuiApplication::quit();
} }
return true; return true;
@ -2424,7 +2421,9 @@ void MainWindow::requestExit(bool allow_save_to_state /* = true */)
if (!requestShutdown(true, allow_save_to_state, true)) if (!requestShutdown(true, allow_save_to_state, true))
return; return;
close(); // We could use close here, but if we're not visible (e.g. quitting from fullscreen), closing the window
// doesn't quit the application.
QGuiApplication::quit();
} }
void MainWindow::checkForSettingChanges() void MainWindow::checkForSettingChanges()

View File

@ -1373,7 +1373,9 @@ void EmuThread::stop()
void EmuThread::stopInThread() void EmuThread::stopInThread()
{ {
m_shutdown_flag.store(true); stopFullscreenUI();
m_shutdown_flag = true;
m_event_loop->quit(); m_event_loop->quit();
} }
@ -1390,7 +1392,7 @@ void EmuThread::run()
startBackgroundControllerPollTimer(); startBackgroundControllerPollTimer();
// main loop // main loop
while (!m_shutdown_flag.load()) while (!m_shutdown_flag)
{ {
if (System::IsRunning()) if (System::IsRunning())
{ {
@ -1398,9 +1400,6 @@ void EmuThread::run()
} }
else else
{ {
m_event_loop->processEvents(QEventLoop::AllEvents);
CommonHost::PumpMessagesOnCPUThread();
// we want to keep rendering the UI when paused and fullscreen UI is enabled // we want to keep rendering the UI when paused and fullscreen UI is enabled
if (!FullscreenUI::HasActiveWindow() && !System::IsRunning()) if (!FullscreenUI::HasActiveWindow() && !System::IsRunning())
{ {
@ -1409,6 +1408,9 @@ void EmuThread::run()
continue; continue;
} }
m_event_loop->processEvents(QEventLoop::AllEvents);
CommonHost::PumpMessagesOnCPUThread();
if (g_host_display)
renderDisplay(false); renderDisplay(false);
} }
} }

View File

@ -210,8 +210,7 @@ private:
QEventLoop* m_event_loop = nullptr; QEventLoop* m_event_loop = nullptr;
QTimer* m_background_controller_polling_timer = nullptr; QTimer* m_background_controller_polling_timer = nullptr;
std::atomic_bool m_shutdown_flag{false}; bool m_shutdown_flag = false;
bool m_run_fullscreen_ui = false; bool m_run_fullscreen_ui = false;
bool m_is_rendering_to_main = false; bool m_is_rendering_to_main = false;
bool m_is_fullscreen = false; bool m_is_fullscreen = false;