From b1d5c7c116c589c2712f00167fcffe48ae2423f1 Mon Sep 17 00:00:00 2001 From: Ilya Fedin Date: Sun, 19 Nov 2023 22:04:41 +0400 Subject: [PATCH] Allow Ui::GL::CheckCapapilities to work without QWidget --- ui/gl/gl_detection.cpp | 44 +++++++++++++++++++++++++++++++++--------- ui/gl/gl_detection.h | 4 +++- 2 files changed, 38 insertions(+), 10 deletions(-) diff --git a/ui/gl/gl_detection.cpp b/ui/gl/gl_detection.cpp index 3d2a542..df38f90 100644 --- a/ui/gl/gl_detection.cpp +++ b/ui/gl/gl_detection.cpp @@ -14,9 +14,11 @@ #include #include +#include #include #include #include +#include #include #ifdef Q_OS_WIN @@ -56,7 +58,7 @@ void CrashCheckStart() { const char kOptionAllowLinuxNvidiaOpenGL[] = "allow-linux-nvidia-opengl"; -Capabilities CheckCapabilities(QWidget *widget) { +Capabilities CheckCapabilities(QWidget *widget, bool avoidWidgetCreation) { if (ForceDisabled) { LOG_ONCE(("OpenGL: Force-disabled.")); return {}; @@ -88,19 +90,43 @@ Capabilities CheckCapabilities(QWidget *widget) { } CrashCheckStart(); - auto tester = QOpenGLWidget(widget); - tester.setFormat(format); - tester.grabFramebuffer(); // Force initialize(). - if (!tester.window()->windowHandle()) { - tester.window()->createWinId(); - } + const auto tester = [&] { + std::unique_ptr result; + if (avoidWidgetCreation) { + const auto w = new QOpenGLWindow(); + auto e = QResizeEvent(QSize(), QSize()); + w->setFormat(format); + w->create(); + static_cast(w)->event(&e); // Force initialize(). + w->grabFramebuffer(); // Force makeCurrent(). + result.reset(w); + } else { + const auto w = new QOpenGLWidget(widget); + w->setFormat(format); + w->grabFramebuffer(); // Force initialize(). + if (!w->window()->windowHandle()) { + w->window()->createWinId(); + } + result.reset(w); + } + return result; + }(); + const auto testerWidget = avoidWidgetCreation + ? nullptr + : static_cast(tester.get()); + const auto testerWindow = avoidWidgetCreation + ? static_cast(tester.get()) + : nullptr; + /*const auto testerQWindow = avoidWidgetCreation + ? static_cast(tester.get()) + : testerWidget->window()->windowHandle();*/ CrashCheckFinish(); - const auto context = tester.context(); + const auto context = avoidWidgetCreation ? testerWindow->context() : testerWidget->context(); if (!context || !context->isValid()/* // This check doesn't work for a widget with WA_NativeWindow. - || !context->makeCurrent(tester.window()->windowHandle())*/) { + || !context->makeCurrent(testerQWindow)*/) { LOG_ONCE(("OpenGL: Could not create widget in a window.")); return {}; } diff --git a/ui/gl/gl_detection.h b/ui/gl/gl_detection.h index 8ea77be..97e6606 100644 --- a/ui/gl/gl_detection.h +++ b/ui/gl/gl_detection.h @@ -24,7 +24,9 @@ struct Capabilities { bool transparency = false; }; -[[nodiscard]] Capabilities CheckCapabilities(QWidget *widget = nullptr); +[[nodiscard]] Capabilities CheckCapabilities( + QWidget *widget = nullptr, + bool avoidWidgetCreation = false); [[nodiscard]] Backend ChooseBackendDefault(Capabilities capabilities); void ForceDisable(bool disable);