mirror of
https://github.com/RetroDECK/Duckstation.git
synced 2024-11-26 23:55:40 +00:00
Qt: Support Vulkan
This commit is contained in:
parent
d168947ae4
commit
49a9f01327
|
@ -58,10 +58,12 @@ add_executable(duckstation-qt
|
|||
settingsdialog.cpp
|
||||
settingsdialog.h
|
||||
settingsdialog.ui
|
||||
vulkanhostdisplay.cpp
|
||||
vulkanhostdisplay.h
|
||||
)
|
||||
|
||||
target_include_directories(duckstation-qt PRIVATE "${Qt5Gui_PRIVATE_INCLUDE_DIRS}")
|
||||
target_link_libraries(duckstation-qt PRIVATE frontend-common core common imgui glad minizip scmversion Qt5::Core Qt5::Gui Qt5::Widgets Qt5::Network)
|
||||
target_link_libraries(duckstation-qt PRIVATE frontend-common core common imgui glad minizip scmversion vulkan-loader Qt5::Core Qt5::Gui Qt5::Widgets Qt5::Network)
|
||||
|
||||
if(WIN32)
|
||||
target_sources(duckstation-qt PRIVATE
|
||||
|
|
|
@ -214,7 +214,7 @@ bool D3D11HostDisplay::createDeviceContext(bool debug_device)
|
|||
m_allow_tearing_supported = (allow_tearing_supported == TRUE);
|
||||
}
|
||||
|
||||
return true;
|
||||
return createSwapChain();
|
||||
}
|
||||
|
||||
void D3D11HostDisplay::destroyDeviceContext()
|
||||
|
@ -232,7 +232,7 @@ bool D3D11HostDisplay::shouldUseFlipModelSwapChain() const
|
|||
return m_widget->parent() == nullptr;
|
||||
}
|
||||
|
||||
bool D3D11HostDisplay::createSurface()
|
||||
bool D3D11HostDisplay::createSwapChain()
|
||||
{
|
||||
m_using_flip_model_swap_chain = shouldUseFlipModelSwapChain();
|
||||
|
||||
|
@ -282,11 +282,7 @@ bool D3D11HostDisplay::createSurface()
|
|||
if (FAILED(hr))
|
||||
Log_WarningPrintf("MakeWindowAssociation() to disable ALT+ENTER failed");
|
||||
|
||||
if (!createSwapChainRTV())
|
||||
return false;
|
||||
|
||||
emit m_widget->windowResizedEvent(m_window_width, m_window_height);
|
||||
return true;
|
||||
return createSwapChainRTV();
|
||||
}
|
||||
|
||||
bool D3D11HostDisplay::createSwapChainRTV()
|
||||
|
@ -314,6 +310,11 @@ bool D3D11HostDisplay::createSwapChainRTV()
|
|||
return true;
|
||||
}
|
||||
|
||||
bool D3D11HostDisplay::recreateSurface()
|
||||
{
|
||||
return createSwapChain();
|
||||
}
|
||||
|
||||
void D3D11HostDisplay::destroySurface()
|
||||
{
|
||||
m_swap_chain_rtv.Reset();
|
||||
|
|
|
@ -22,7 +22,7 @@ public:
|
|||
bool hasDeviceContext() const override;
|
||||
bool createDeviceContext(bool debug_device) override;
|
||||
void destroyDeviceContext() override;
|
||||
bool createSurface() override;
|
||||
bool recreateSurface() override;
|
||||
void destroySurface() override;
|
||||
|
||||
RenderAPI GetRenderAPI() const override;
|
||||
|
@ -50,6 +50,7 @@ private:
|
|||
void destroyDeviceResources() override;
|
||||
|
||||
bool shouldUseFlipModelSwapChain() const;
|
||||
bool createSwapChain();
|
||||
bool createSwapChainRTV();
|
||||
|
||||
void renderDisplay();
|
||||
|
|
|
@ -59,8 +59,10 @@
|
|||
<ClCompile Include="qtsettingsinterface.cpp" />
|
||||
<ClCompile Include="qtutils.cpp" />
|
||||
<ClCompile Include="settingsdialog.cpp" />
|
||||
<ClCompile Include="vulkanhostdisplay.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="vulkanhostdisplay.h" />
|
||||
<QtMoc Include="aboutdialog.h" />
|
||||
<QtMoc Include="audiosettingswidget.h" />
|
||||
<QtMoc Include="controllersettingswidget.h" />
|
||||
|
@ -97,6 +99,9 @@
|
|||
<ProjectReference Include="..\..\dep\minizip\minizip.vcxproj">
|
||||
<Project>{8bda439c-6358-45fb-9994-2ff083babe06}</Project>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\..\dep\vulkan-loader\vulkan-loader.vcxproj">
|
||||
<Project>{9c8ddeb0-2b8f-4f5f-ba86-127cdf27f035}</Project>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\common\common.vcxproj">
|
||||
<Project>{ee054e08-3799-4a59-a422-18259c105ffd}</Project>
|
||||
</ProjectReference>
|
||||
|
@ -335,7 +340,7 @@
|
|||
<PreprocessorDefinitions>WITH_DISCORD_PRESENCE=1;_CRT_SECURE_NO_WARNINGS;WIN32;_DEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x86\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)dep\vulkan-loader\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x86\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<MinimalRebuild>false</MinimalRebuild>
|
||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
||||
|
@ -356,7 +361,7 @@
|
|||
<PreprocessorDefinitions>WITH_DISCORD_PRESENCE=1;_CRT_SECURE_NO_WARNINGS;WIN32;_DEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)dep\vulkan-loader\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<MinimalRebuild>false</MinimalRebuild>
|
||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
||||
|
@ -377,7 +382,7 @@
|
|||
<PreprocessorDefinitions>WITH_DISCORD_PRESENCE=1;_ITERATOR_DEBUG_LEVEL=1;_CRT_SECURE_NO_WARNINGS;WIN32;_DEBUGFAST;_DEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x86\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)dep\vulkan-loader\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x86\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<BasicRuntimeChecks>Default</BasicRuntimeChecks>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<MinimalRebuild>false</MinimalRebuild>
|
||||
|
@ -400,7 +405,7 @@
|
|||
<PreprocessorDefinitions>WITH_DISCORD_PRESENCE=1;_ITERATOR_DEBUG_LEVEL=1;_CRT_SECURE_NO_WARNINGS;WIN32;_DEBUGFAST;_DEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)dep\vulkan-loader\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<BasicRuntimeChecks>Default</BasicRuntimeChecks>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<MinimalRebuild>false</MinimalRebuild>
|
||||
|
@ -422,7 +427,7 @@
|
|||
<Optimization>MaxSpeed</Optimization>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<PreprocessorDefinitions>WITH_DISCORD_PRESENCE=1;_CRT_SECURE_NO_WARNINGS;WIN32;NDEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x86\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)dep\vulkan-loader\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x86\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<WholeProgramOptimization>false</WholeProgramOptimization>
|
||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
||||
|
@ -445,7 +450,7 @@
|
|||
<Optimization>MaxSpeed</Optimization>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<PreprocessorDefinitions>WITH_DISCORD_PRESENCE=1;_CRT_SECURE_NO_WARNINGS;WIN32;NDEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x86\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)dep\vulkan-loader\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x86\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
||||
|
@ -469,7 +474,7 @@
|
|||
<Optimization>MaxSpeed</Optimization>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<PreprocessorDefinitions>WITH_DISCORD_PRESENCE=1;_CRT_SECURE_NO_WARNINGS;WIN32;NDEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)dep\vulkan-loader\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<WholeProgramOptimization>false</WholeProgramOptimization>
|
||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
||||
|
@ -492,7 +497,7 @@
|
|||
<Optimization>MaxSpeed</Optimization>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<PreprocessorDefinitions>WITH_DISCORD_PRESENCE=1;_CRT_SECURE_NO_WARNINGS;WIN32;NDEBUG;_CONSOLE;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>$(SolutionDir)dep\glad\Include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\zlib\include;$(SolutionDir)dep\minizip\include;$(SolutionDir)dep\vulkan-loader\include;$(SolutionDir)src;$(SolutionDir)dep\msvc\qt5-x64\include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
||||
|
@ -512,4 +517,4 @@
|
|||
<ImportGroup Label="ExtensionTargets">
|
||||
<Import Project="..\..\dep\msvc\vsprops\QtCompile.targets" />
|
||||
</ImportGroup>
|
||||
</Project>
|
||||
</Project>
|
|
@ -16,7 +16,6 @@
|
|||
<ClCompile Include="$(IntDir)moc_mainwindow.cpp" />
|
||||
<ClCompile Include="$(IntDir)moc_qthostinterface.cpp" />
|
||||
<ClCompile Include="$(IntDir)moc_settingsdialog.cpp" />
|
||||
<ClCompile Include="$(IntDir)moc_portsettingswidget.cpp" />
|
||||
<ClCompile Include="gpusettingswidget.cpp" />
|
||||
<ClCompile Include="$(IntDir)moc_gpusettingswidget.cpp" />
|
||||
<ClCompile Include="inputbindingwidgets.cpp" />
|
||||
|
@ -39,6 +38,13 @@
|
|||
<ClCompile Include="gamepropertiesdialog.cpp" />
|
||||
<ClCompile Include="$(IntDir)moc_gamepropertiesdialog.cpp" />
|
||||
<ClCompile Include="controllersettingswidget.cpp" />
|
||||
<ClCompile Include="aboutdialog.cpp" />
|
||||
<ClCompile Include="memorycardsettingswidget.cpp" />
|
||||
<ClCompile Include="$(IntDir)moc_aboutdialog.cpp" />
|
||||
<ClCompile Include="$(IntDir)moc_controllersettingswidget.cpp" />
|
||||
<ClCompile Include="$(IntDir)moc_memorycardsettingswidget.cpp" />
|
||||
<ClCompile Include="$(IntDir)qrc_icons.cpp" />
|
||||
<ClCompile Include="vulkanhostdisplay.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="qtsettingsinterface.h" />
|
||||
|
@ -48,6 +54,7 @@
|
|||
<ClInclude Include="d3d11hostdisplay.h" />
|
||||
<ClInclude Include="openglhostdisplay.h" />
|
||||
<ClInclude Include="resource.h" />
|
||||
<ClInclude Include="vulkanhostdisplay.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Filter Include="resources">
|
||||
|
@ -74,6 +81,8 @@
|
|||
<QtMoc Include="advancedsettingswidget.h" />
|
||||
<QtMoc Include="gamepropertiesdialog.h" />
|
||||
<QtMoc Include="controllersettingswidget.h" />
|
||||
<QtMoc Include="aboutdialog.h" />
|
||||
<QtMoc Include="memorycardsettingswidget.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<QtUi Include="consolesettingswidget.ui" />
|
||||
|
@ -85,6 +94,7 @@
|
|||
<QtUi Include="generalsettingswidget.ui" />
|
||||
<QtUi Include="advancedsettingswidget.ui" />
|
||||
<QtUi Include="gamepropertiesdialog.ui" />
|
||||
<QtUi Include="aboutdialog.ui" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Natvis Include="qt5.natvis" />
|
||||
|
@ -95,4 +105,4 @@
|
|||
<ItemGroup>
|
||||
<Image Include="duckstation-qt.ico" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
</Project>
|
|
@ -103,13 +103,6 @@ void MainWindow::createDisplay(QThread* worker_thread, bool use_debug_device, bo
|
|||
return;
|
||||
}
|
||||
|
||||
if (!m_host_display->createSurface())
|
||||
{
|
||||
reportError(tr("Failed to create host display surface."));
|
||||
m_host_display->destroyDeviceContext();
|
||||
return;
|
||||
}
|
||||
|
||||
m_host_display->deactivateDeviceContext();
|
||||
}
|
||||
|
||||
|
@ -151,7 +144,7 @@ void MainWindow::updateDisplay(QThread* worker_thread, bool fullscreen, bool ren
|
|||
// we need the surface visible.. this might be able to be replaced with something else
|
||||
QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);
|
||||
|
||||
if (!m_host_display->createSurface())
|
||||
if (!m_host_display->recreateSurface())
|
||||
Panic("Failed to recreate surface on new widget.");
|
||||
|
||||
m_display_widget->setFocus();
|
||||
|
|
|
@ -4,15 +4,10 @@
|
|||
#include "imgui.h"
|
||||
#include "qtdisplaywidget.h"
|
||||
#include "qthostinterface.h"
|
||||
#include <QtCore/QDebug>
|
||||
#include <QtGui/QGuiApplication>
|
||||
#include <QtGui/QKeyEvent>
|
||||
#include <QtGui/QWindow>
|
||||
#include <array>
|
||||
#include <imgui_impl_opengl3.h>
|
||||
#if !defined(WIN32) && !defined(APPLE)
|
||||
#include <qpa/qplatformnativeinterface.h>
|
||||
#endif
|
||||
#include <tuple>
|
||||
Log_SetChannel(OpenGLHostDisplay);
|
||||
|
||||
|
@ -193,49 +188,16 @@ bool OpenGLHostDisplay::hasDeviceContext() const
|
|||
return static_cast<bool>(m_gl_context);
|
||||
}
|
||||
|
||||
WindowInfo OpenGLHostDisplay::getWindowInfo() const
|
||||
{
|
||||
WindowInfo wi;
|
||||
|
||||
// Windows and Apple are easy here since there's no display connection.
|
||||
#if defined(WIN32)
|
||||
wi.type = WindowInfo::Type::Win32;
|
||||
wi.window_handle = reinterpret_cast<void*>(m_widget->winId());
|
||||
#elif defined(__APPLE__)
|
||||
wi.type = WindowInfo::Type::MacOS;
|
||||
wi.window_handle = reinterpret_cast<void*>(m_widget->winId());
|
||||
#else
|
||||
QPlatformNativeInterface* pni = QGuiApplication::platformNativeInterface();
|
||||
const QString platform_name = QGuiApplication::platformName();
|
||||
if (platform_name == QStringLiteral("xcb"))
|
||||
{
|
||||
wi.type = WindowInfo::Type::X11;
|
||||
wi.display_connection = pni->nativeResourceForWindow("display", m_widget->windowHandle());
|
||||
wi.window_handle = reinterpret_cast<void*>(m_widget->winId());
|
||||
}
|
||||
else if (platform_name == QStringLiteral("wayland"))
|
||||
{
|
||||
wi.type = WindowInfo::Type::Wayland;
|
||||
wi.display_connection = pni->nativeResourceForWindow("display", m_widget->windowHandle());
|
||||
wi.window_handle = pni->nativeResourceForWindow("surface", m_widget->windowHandle());
|
||||
}
|
||||
else
|
||||
{
|
||||
qCritical() << "Unknown PNI platform " << platform_name;
|
||||
return wi;
|
||||
}
|
||||
#endif
|
||||
|
||||
wi.surface_width = m_widget->width();
|
||||
wi.surface_height = m_widget->height();
|
||||
wi.surface_format = WindowInfo::SurfaceFormat::RGB8;
|
||||
|
||||
return wi;
|
||||
}
|
||||
|
||||
bool OpenGLHostDisplay::createDeviceContext(bool debug_device)
|
||||
{
|
||||
m_gl_context = GL::Context::Create(getWindowInfo());
|
||||
m_window_width = m_widget->scaledWindowWidth();
|
||||
m_window_height = m_widget->scaledWindowHeight();
|
||||
|
||||
std::optional<WindowInfo> wi = getWindowInfo();
|
||||
if (!wi.has_value())
|
||||
return false;
|
||||
|
||||
m_gl_context = GL::Context::Create(wi.value());
|
||||
if (!m_gl_context)
|
||||
{
|
||||
Log_ErrorPrintf("Failed to create any GL context");
|
||||
|
@ -245,7 +207,7 @@ bool OpenGLHostDisplay::createDeviceContext(bool debug_device)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool OpenGLHostDisplay::initializeDeviceContext(bool debug_device)
|
||||
bool OpenGLHostDisplay::initializeDeviceContext(std::string_view shader_cache_directory, bool debug_device)
|
||||
{
|
||||
if (debug_device && GLAD_GL_KHR_debug)
|
||||
{
|
||||
|
@ -254,7 +216,7 @@ bool OpenGLHostDisplay::initializeDeviceContext(bool debug_device)
|
|||
glEnable(GL_DEBUG_OUTPUT_SYNCHRONOUS);
|
||||
}
|
||||
|
||||
if (!QtHostDisplay::initializeDeviceContext(debug_device))
|
||||
if (!QtHostDisplay::initializeDeviceContext(shader_cache_directory, debug_device))
|
||||
{
|
||||
m_gl_context->DoneCurrent();
|
||||
return false;
|
||||
|
@ -286,14 +248,17 @@ void OpenGLHostDisplay::destroyDeviceContext()
|
|||
m_gl_context.reset();
|
||||
}
|
||||
|
||||
bool OpenGLHostDisplay::createSurface()
|
||||
bool OpenGLHostDisplay::recreateSurface()
|
||||
{
|
||||
m_window_width = m_widget->scaledWindowWidth();
|
||||
m_window_height = m_widget->scaledWindowHeight();
|
||||
emit m_widget->windowResizedEvent(m_window_width, m_window_height);
|
||||
|
||||
if (m_gl_context)
|
||||
m_gl_context->ChangeSurface(getWindowInfo());
|
||||
{
|
||||
std::optional<WindowInfo> wi = getWindowInfo();
|
||||
if (!wi.has_value() || !m_gl_context->ChangeSurface(wi.value()))
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -27,11 +27,11 @@ public:
|
|||
|
||||
bool hasDeviceContext() const override;
|
||||
bool createDeviceContext(bool debug_device) override;
|
||||
bool initializeDeviceContext(bool debug_device) override;
|
||||
bool initializeDeviceContext(std::string_view shader_cache_directory, bool debug_device) override;
|
||||
bool activateDeviceContext() override;
|
||||
void deactivateDeviceContext() override;
|
||||
void destroyDeviceContext() override;
|
||||
bool createSurface() override;
|
||||
bool recreateSurface() override;
|
||||
void destroySurface();
|
||||
|
||||
RenderAPI GetRenderAPI() const override;
|
||||
|
@ -54,8 +54,6 @@ private:
|
|||
const char* GetGLSLVersionString() const;
|
||||
std::string GetGLSLVersionHeader() const;
|
||||
|
||||
WindowInfo getWindowInfo() const;
|
||||
|
||||
bool createImGuiContext() override;
|
||||
void destroyImGuiContext() override;
|
||||
bool createDeviceResources() override;
|
||||
|
|
|
@ -4,7 +4,12 @@
|
|||
#include "imgui.h"
|
||||
#include "qtdisplaywidget.h"
|
||||
#include "qthostinterface.h"
|
||||
#include <QtGui/QGuiApplication>
|
||||
#include <QtCore/QDebug>
|
||||
#include <cmath>
|
||||
#if !defined(WIN32) && !defined(APPLE)
|
||||
#include <qpa/qplatformnativeinterface.h>
|
||||
#endif
|
||||
|
||||
QtHostDisplay::QtHostDisplay(QtHostInterface* host_interface) : m_host_interface(host_interface) {}
|
||||
|
||||
|
@ -42,7 +47,7 @@ bool QtHostDisplay::createDeviceContext(bool debug_device)
|
|||
return false;
|
||||
}
|
||||
|
||||
bool QtHostDisplay::initializeDeviceContext(bool debug_device)
|
||||
bool QtHostDisplay::initializeDeviceContext(std::string_view shader_cache_directory, bool debug_device)
|
||||
{
|
||||
if (!createImGuiContext() || !createDeviceResources())
|
||||
return false;
|
||||
|
@ -63,7 +68,7 @@ void QtHostDisplay::destroyDeviceContext()
|
|||
destroyDeviceResources();
|
||||
}
|
||||
|
||||
bool QtHostDisplay::createSurface()
|
||||
bool QtHostDisplay::recreateSurface()
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
@ -118,3 +123,43 @@ void QtHostDisplay::updateImGuiDisplaySize()
|
|||
io.DisplaySize.x = static_cast<float>(m_window_width);
|
||||
io.DisplaySize.y = static_cast<float>(m_window_height);
|
||||
}
|
||||
|
||||
std::optional<WindowInfo> QtHostDisplay::getWindowInfo() const
|
||||
{
|
||||
WindowInfo wi;
|
||||
|
||||
// Windows and Apple are easy here since there's no display connection.
|
||||
#if defined(WIN32)
|
||||
wi.type = WindowInfo::Type::Win32;
|
||||
wi.window_handle = reinterpret_cast<void*>(m_widget->winId());
|
||||
#elif defined(__APPLE__)
|
||||
wi.type = WindowInfo::Type::MacOS;
|
||||
wi.window_handle = reinterpret_cast<void*>(m_widget->winId());
|
||||
#else
|
||||
QPlatformNativeInterface* pni = QGuiApplication::platformNativeInterface();
|
||||
const QString platform_name = QGuiApplication::platformName();
|
||||
if (platform_name == QStringLiteral("xcb"))
|
||||
{
|
||||
wi.type = WindowInfo::Type::X11;
|
||||
wi.display_connection = pni->nativeResourceForWindow("display", m_widget->windowHandle());
|
||||
wi.window_handle = reinterpret_cast<void*>(m_widget->winId());
|
||||
}
|
||||
else if (platform_name == QStringLiteral("wayland"))
|
||||
{
|
||||
wi.type = WindowInfo::Type::Wayland;
|
||||
wi.display_connection = pni->nativeResourceForWindow("display", m_widget->windowHandle());
|
||||
wi.window_handle = pni->nativeResourceForWindow("surface", m_widget->windowHandle());
|
||||
}
|
||||
else
|
||||
{
|
||||
qCritical() << "Unknown PNI platform " << platform_name;
|
||||
return std::nullopt;
|
||||
}
|
||||
#endif
|
||||
|
||||
wi.surface_width = m_widget->width();
|
||||
wi.surface_height = m_widget->height();
|
||||
wi.surface_format = WindowInfo::SurfaceFormat::RGB8;
|
||||
|
||||
return wi;
|
||||
}
|
||||
|
|
|
@ -1,6 +1,9 @@
|
|||
#pragma once
|
||||
#include "common/types.h"
|
||||
#include "common/window_info.h"
|
||||
#include "core/host_display.h"
|
||||
#include <optional>
|
||||
#include <string_view>
|
||||
|
||||
class QThread;
|
||||
class QWidget;
|
||||
|
@ -22,11 +25,11 @@ public:
|
|||
|
||||
virtual bool hasDeviceContext() const;
|
||||
virtual bool createDeviceContext(bool debug_device);
|
||||
virtual bool initializeDeviceContext(bool debug_device);
|
||||
virtual bool initializeDeviceContext(std::string_view shader_cache_directory, bool debug_device);
|
||||
virtual bool activateDeviceContext();
|
||||
virtual void deactivateDeviceContext();
|
||||
virtual void destroyDeviceContext();
|
||||
virtual bool createSurface();
|
||||
virtual bool recreateSurface();
|
||||
virtual void destroySurface();
|
||||
|
||||
virtual void WindowResized(s32 new_window_width, s32 new_window_height) override;
|
||||
|
@ -39,6 +42,8 @@ protected:
|
|||
virtual bool createDeviceResources();
|
||||
virtual void destroyDeviceResources();
|
||||
|
||||
std::optional<WindowInfo> getWindowInfo() const;
|
||||
|
||||
QtHostInterface* m_host_interface;
|
||||
QtDisplayWidget* m_widget = nullptr;
|
||||
};
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
#include "qtprogresscallback.h"
|
||||
#include "qtsettingsinterface.h"
|
||||
#include "qtutils.h"
|
||||
#include "vulkanhostdisplay.h"
|
||||
#include <QtCore/QCoreApplication>
|
||||
#include <QtCore/QDateTime>
|
||||
#include <QtCore/QDebug>
|
||||
|
@ -327,7 +328,7 @@ bool QtHostInterface::AcquireHostDisplay()
|
|||
}
|
||||
|
||||
if (!getHostDisplay()->activateDeviceContext() ||
|
||||
!getHostDisplay()->initializeDeviceContext(m_settings.gpu_use_debug_device))
|
||||
!getHostDisplay()->initializeDeviceContext(GetShaderCacheDirectory(), m_settings.gpu_use_debug_device))
|
||||
{
|
||||
getHostDisplay()->destroyDeviceContext();
|
||||
emit destroyDisplayRequested();
|
||||
|
@ -343,14 +344,26 @@ QtHostDisplay* QtHostInterface::createHostDisplay()
|
|||
{
|
||||
Assert(!getHostDisplay());
|
||||
|
||||
#ifdef WIN32
|
||||
if (m_settings.gpu_renderer == GPURenderer::HardwareOpenGL)
|
||||
m_display = new OpenGLHostDisplay(this);
|
||||
else
|
||||
m_display = new D3D11HostDisplay(this);
|
||||
#else
|
||||
m_display = new OpenGLHostDisplay(this);
|
||||
switch (m_settings.gpu_renderer)
|
||||
{
|
||||
case GPURenderer::HardwareVulkan:
|
||||
m_display = new VulkanHostDisplay(this);
|
||||
break;
|
||||
|
||||
case GPURenderer::HardwareOpenGL:
|
||||
#ifndef WIN32
|
||||
default:
|
||||
#endif
|
||||
m_display = new OpenGLHostDisplay(this);
|
||||
break;
|
||||
|
||||
#ifdef WIN32
|
||||
case GPURenderer::HardwareD3D11:
|
||||
default:
|
||||
m_display = new D3D11HostDisplay(this);
|
||||
break;
|
||||
#endif
|
||||
}
|
||||
|
||||
return getHostDisplay();
|
||||
}
|
||||
|
|
168
src/duckstation-qt/vulkanhostdisplay.cpp
Normal file
168
src/duckstation-qt/vulkanhostdisplay.cpp
Normal file
|
@ -0,0 +1,168 @@
|
|||
#include "vulkanhostdisplay.h"
|
||||
#include "common/assert.h"
|
||||
#include "common/log.h"
|
||||
#include "imgui.h"
|
||||
#include "qtdisplaywidget.h"
|
||||
Log_SetChannel(VulkanHostDisplay);
|
||||
|
||||
VulkanHostDisplay::VulkanHostDisplay(QtHostInterface* host_interface) : QtHostDisplay(host_interface) {}
|
||||
|
||||
VulkanHostDisplay::~VulkanHostDisplay() = default;
|
||||
|
||||
HostDisplay::RenderAPI VulkanHostDisplay::GetRenderAPI() const
|
||||
{
|
||||
return m_vulkan_display.GetRenderAPI();
|
||||
}
|
||||
|
||||
void* VulkanHostDisplay::GetRenderDevice() const
|
||||
{
|
||||
return m_vulkan_display.GetRenderDevice();
|
||||
}
|
||||
|
||||
void* VulkanHostDisplay::GetRenderContext() const
|
||||
{
|
||||
return m_vulkan_display.GetRenderContext();
|
||||
}
|
||||
|
||||
std::unique_ptr<HostDisplayTexture> VulkanHostDisplay::CreateTexture(u32 width, u32 height, const void* initial_data,
|
||||
u32 initial_data_stride, bool dynamic)
|
||||
{
|
||||
return m_vulkan_display.CreateTexture(width, height, initial_data, initial_data_stride, dynamic);
|
||||
}
|
||||
|
||||
void VulkanHostDisplay::UpdateTexture(HostDisplayTexture* texture, u32 x, u32 y, u32 width, u32 height,
|
||||
const void* texture_data, u32 texture_data_stride)
|
||||
{
|
||||
m_vulkan_display.UpdateTexture(texture, x, y, width, height, texture_data, texture_data_stride);
|
||||
}
|
||||
|
||||
bool VulkanHostDisplay::DownloadTexture(const void* texture_handle, u32 x, u32 y, u32 width, u32 height, void* out_data,
|
||||
u32 out_data_stride)
|
||||
{
|
||||
return m_vulkan_display.DownloadTexture(texture_handle, x, y, width, height, out_data, out_data_stride);
|
||||
}
|
||||
|
||||
void VulkanHostDisplay::SetVSync(bool enabled)
|
||||
{
|
||||
m_vulkan_display.SetVSync(enabled);
|
||||
}
|
||||
|
||||
bool VulkanHostDisplay::hasDeviceContext() const
|
||||
{
|
||||
return m_vulkan_display.HasContext();
|
||||
}
|
||||
|
||||
bool VulkanHostDisplay::createDeviceContext(bool debug_device)
|
||||
{
|
||||
std::optional<WindowInfo> wi = getWindowInfo();
|
||||
if (!wi || !m_vulkan_display.CreateContextAndSwapChain(wi.value(), debug_device))
|
||||
return false;
|
||||
|
||||
m_window_width = static_cast<s32>(m_vulkan_display.GetSwapChainWidth());
|
||||
m_window_height = static_cast<s32>(m_vulkan_display.GetSwapChainHeight());
|
||||
return true;
|
||||
}
|
||||
|
||||
bool VulkanHostDisplay::initializeDeviceContext(std::string_view shader_cache_directory, bool debug_device)
|
||||
{
|
||||
m_vulkan_display.CreateShaderCache(shader_cache_directory, debug_device);
|
||||
|
||||
return QtHostDisplay::initializeDeviceContext(shader_cache_directory, debug_device);
|
||||
}
|
||||
|
||||
bool VulkanHostDisplay::activateDeviceContext()
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
void VulkanHostDisplay::deactivateDeviceContext() {}
|
||||
|
||||
void VulkanHostDisplay::destroyDeviceContext()
|
||||
{
|
||||
QtHostDisplay::destroyDeviceContext();
|
||||
m_vulkan_display.DestroyShaderCache();
|
||||
m_vulkan_display.DestroySwapChain();
|
||||
m_vulkan_display.DestroyContext();
|
||||
}
|
||||
|
||||
bool VulkanHostDisplay::recreateSurface()
|
||||
{
|
||||
std::optional<WindowInfo> wi = getWindowInfo();
|
||||
if (!wi.has_value())
|
||||
return false;
|
||||
|
||||
if (!m_vulkan_display.RecreateSwapChain(wi.value()))
|
||||
return false;
|
||||
|
||||
m_window_width = static_cast<s32>(m_vulkan_display.GetSwapChainWidth());
|
||||
m_window_height = static_cast<s32>(m_vulkan_display.GetSwapChainHeight());
|
||||
return true;
|
||||
}
|
||||
|
||||
void VulkanHostDisplay::destroySurface()
|
||||
{
|
||||
m_vulkan_display.DestroySwapChain();
|
||||
}
|
||||
|
||||
void VulkanHostDisplay::WindowResized(s32 new_window_width, s32 new_window_height)
|
||||
{
|
||||
QtHostDisplay::WindowResized(new_window_width, new_window_height);
|
||||
|
||||
m_vulkan_display.ResizeSwapChain(static_cast<u32>(new_window_width), static_cast<u32>(new_window_height));
|
||||
m_window_width = static_cast<s32>(m_vulkan_display.GetSwapChainWidth());
|
||||
m_window_height = static_cast<s32>(m_vulkan_display.GetSwapChainHeight());
|
||||
}
|
||||
|
||||
bool VulkanHostDisplay::createDeviceResources()
|
||||
{
|
||||
if (!QtHostDisplay::createDeviceResources())
|
||||
return false;
|
||||
|
||||
return m_vulkan_display.CreateResources();
|
||||
}
|
||||
|
||||
void VulkanHostDisplay::destroyDeviceResources()
|
||||
{
|
||||
QtHostDisplay::destroyDeviceResources();
|
||||
m_vulkan_display.DestroyResources();
|
||||
}
|
||||
|
||||
bool VulkanHostDisplay::createImGuiContext()
|
||||
{
|
||||
if (!QtHostDisplay::createImGuiContext() || !m_vulkan_display.CreateImGuiContext())
|
||||
return false;
|
||||
|
||||
ImGui::NewFrame();
|
||||
return true;
|
||||
}
|
||||
|
||||
void VulkanHostDisplay::destroyImGuiContext()
|
||||
{
|
||||
m_vulkan_display.DestroyImGuiContext();
|
||||
QtHostDisplay::destroyImGuiContext();
|
||||
}
|
||||
|
||||
void VulkanHostDisplay::Render()
|
||||
{
|
||||
if (!m_vulkan_display.HasSwapChain() || !m_vulkan_display.BeginRender())
|
||||
return;
|
||||
|
||||
if (HasDisplayTexture())
|
||||
{
|
||||
const auto [left, top, width, height] = CalculateDrawRect(m_window_width, m_window_height, m_display_top_margin);
|
||||
m_vulkan_display.RenderDisplay(left, top, width, height, m_display_texture_handle, m_display_texture_width,
|
||||
m_display_texture_height, m_display_texture_view_x, m_display_texture_view_y,
|
||||
m_display_texture_view_width, m_display_texture_view_height,
|
||||
m_display_linear_filtering);
|
||||
}
|
||||
|
||||
m_vulkan_display.RenderImGui();
|
||||
|
||||
if (HasSoftwareCursor())
|
||||
{
|
||||
const auto [left, top, width, height] = CalculateSoftwareCursorDrawRect();
|
||||
m_vulkan_display.RenderSoftwareCursor(left, top, width, height, m_cursor_texture.get());
|
||||
}
|
||||
|
||||
m_vulkan_display.EndRenderAndPresent();
|
||||
}
|
49
src/duckstation-qt/vulkanhostdisplay.h
Normal file
49
src/duckstation-qt/vulkanhostdisplay.h
Normal file
|
@ -0,0 +1,49 @@
|
|||
#pragma once
|
||||
#include "common/window_info.h"
|
||||
#include "core/host_display.h"
|
||||
#include "qtdisplaywidget.h"
|
||||
#include "qthostdisplay.h"
|
||||
#include "frontend-common/vulkan_host_display.h"
|
||||
#include <memory>
|
||||
|
||||
class QtHostInterface;
|
||||
|
||||
class VulkanHostDisplay final : public QtHostDisplay
|
||||
{
|
||||
public:
|
||||
VulkanHostDisplay(QtHostInterface* host_interface);
|
||||
~VulkanHostDisplay();
|
||||
|
||||
bool hasDeviceContext() const override;
|
||||
bool createDeviceContext(bool debug_device) override;
|
||||
bool initializeDeviceContext(std::string_view shader_cache_directory, bool debug_device) override;
|
||||
bool activateDeviceContext() override;
|
||||
void deactivateDeviceContext() override;
|
||||
void destroyDeviceContext() override;
|
||||
bool recreateSurface() override;
|
||||
void destroySurface();
|
||||
|
||||
RenderAPI GetRenderAPI() const override;
|
||||
void* GetRenderDevice() const override;
|
||||
void* GetRenderContext() const override;
|
||||
void WindowResized(s32 new_window_width, s32 new_window_height) override;
|
||||
|
||||
std::unique_ptr<HostDisplayTexture> CreateTexture(u32 width, u32 height, const void* initial_data,
|
||||
u32 initial_data_stride, bool dynamic) override;
|
||||
void UpdateTexture(HostDisplayTexture* texture, u32 x, u32 y, u32 width, u32 height, const void* texture_data,
|
||||
u32 texture_data_stride) override;
|
||||
bool DownloadTexture(const void* texture_handle, u32 x, u32 y, u32 width, u32 height, void* out_data,
|
||||
u32 out_data_stride) override;
|
||||
|
||||
void SetVSync(bool enabled) override;
|
||||
|
||||
void Render() override;
|
||||
|
||||
private:
|
||||
bool createImGuiContext() override;
|
||||
void destroyImGuiContext() override;
|
||||
bool createDeviceResources() override;
|
||||
void destroyDeviceResources() override;
|
||||
|
||||
FrontendCommon::VulkanHostDisplay m_vulkan_display;
|
||||
};
|
Loading…
Reference in a new issue