mirror of
https://github.com/hrydgard/ppsspp.git
synced 2025-04-02 11:01:50 -04:00
Vulkan: Present using FIFO for vsync.
This allows the setting to be changed at runtime in Vulkan too. Should help #10105.
This commit is contained in:
parent
3c1e8abcfe
commit
2a3fd05651
7 changed files with 43 additions and 20 deletions
|
@ -949,20 +949,17 @@ bool VulkanContext::InitSwapchain() {
|
||||||
ILOG("Supported present mode: %d (%s)", presentModes[i], PresentModeString(presentModes[i]));
|
ILOG("Supported present mode: %d (%s)", presentModes[i], PresentModeString(presentModes[i]));
|
||||||
}
|
}
|
||||||
for (size_t i = 0; i < presentModeCount; i++) {
|
for (size_t i = 0; i < presentModeCount; i++) {
|
||||||
if (swapchainPresentMode == VK_PRESENT_MODE_MAX_ENUM_KHR) {
|
bool match = false;
|
||||||
// Default to the first present mode from the list.
|
match = match || ((flags_ & VULKAN_FLAG_PRESENT_MAILBOX) && presentModes[i] == VK_PRESENT_MODE_MAILBOX_KHR);
|
||||||
|
match = match || ((flags_ & VULKAN_FLAG_PRESENT_FIFO_RELAXED) && presentModes[i] == VK_PRESENT_MODE_FIFO_RELAXED_KHR);
|
||||||
|
match = match || ((flags_ & VULKAN_FLAG_PRESENT_FIFO) && presentModes[i] == VK_PRESENT_MODE_FIFO_KHR);
|
||||||
|
match = match || ((flags_ & VULKAN_FLAG_PRESENT_IMMEDIATE) && presentModes[i] == VK_PRESENT_MODE_IMMEDIATE_KHR);
|
||||||
|
|
||||||
|
// Default to the first present mode from the list.
|
||||||
|
if (match || swapchainPresentMode == VK_PRESENT_MODE_MAX_ENUM_KHR) {
|
||||||
swapchainPresentMode = presentModes[i];
|
swapchainPresentMode = presentModes[i];
|
||||||
}
|
}
|
||||||
if ((flags_ & VULKAN_FLAG_PRESENT_MAILBOX) && presentModes[i] == VK_PRESENT_MODE_MAILBOX_KHR) {
|
if (match) {
|
||||||
swapchainPresentMode = VK_PRESENT_MODE_MAILBOX_KHR;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if ((flags_ & VULKAN_FLAG_PRESENT_FIFO_RELAXED) && presentModes[i] == VK_PRESENT_MODE_FIFO_RELAXED_KHR) {
|
|
||||||
swapchainPresentMode = VK_PRESENT_MODE_FIFO_RELAXED_KHR;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if ((flags_ & VULKAN_FLAG_PRESENT_IMMEDIATE) && presentModes[i] == VK_PRESENT_MODE_IMMEDIATE_KHR) {
|
|
||||||
swapchainPresentMode = VK_PRESENT_MODE_IMMEDIATE_KHR;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,6 +13,7 @@ enum {
|
||||||
VULKAN_FLAG_PRESENT_MAILBOX = 2,
|
VULKAN_FLAG_PRESENT_MAILBOX = 2,
|
||||||
VULKAN_FLAG_PRESENT_IMMEDIATE = 4,
|
VULKAN_FLAG_PRESENT_IMMEDIATE = 4,
|
||||||
VULKAN_FLAG_PRESENT_FIFO_RELAXED = 8,
|
VULKAN_FLAG_PRESENT_FIFO_RELAXED = 8,
|
||||||
|
VULKAN_FLAG_PRESENT_FIFO = 16,
|
||||||
};
|
};
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
|
@ -136,6 +137,7 @@ public:
|
||||||
VkDevice GetDevice() const { return device_; }
|
VkDevice GetDevice() const { return device_; }
|
||||||
VkInstance GetInstance() const { return instance_; }
|
VkInstance GetInstance() const { return instance_; }
|
||||||
uint32_t GetFlags() const { return flags_; }
|
uint32_t GetFlags() const { return flags_; }
|
||||||
|
void UpdateFlags(uint32_t flags) { flags_ = flags; }
|
||||||
|
|
||||||
VulkanDeleteList &Delete() { return globalDeleteList_; }
|
VulkanDeleteList &Delete() { return globalDeleteList_; }
|
||||||
|
|
||||||
|
|
|
@ -553,7 +553,12 @@ static void DoFrameTiming(bool &throttle, bool &skipFrame, float timestep) {
|
||||||
// we have nothing to do here.
|
// we have nothing to do here.
|
||||||
bool doFrameSkip = g_Config.iFrameSkip != 0;
|
bool doFrameSkip = g_Config.iFrameSkip != 0;
|
||||||
|
|
||||||
if (!throttle && g_Config.bFrameSkipUnthrottle) {
|
bool unthrottleNeedsSkip = g_Config.bFrameSkipUnthrottle;
|
||||||
|
if (g_Config.bVSync && GetGPUBackend() == GPUBackend::VULKAN) {
|
||||||
|
// Vulkan doesn't support the interval setting, so we force frameskip.
|
||||||
|
unthrottleNeedsSkip = true;
|
||||||
|
}
|
||||||
|
if (!throttle && unthrottleNeedsSkip) {
|
||||||
doFrameSkip = true;
|
doFrameSkip = true;
|
||||||
skipFrame = true;
|
skipFrame = true;
|
||||||
if (numSkippedFrames >= 7) {
|
if (numSkippedFrames >= 7) {
|
||||||
|
|
|
@ -342,7 +342,11 @@ void GameSettingsScreen::CreateViews() {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
graphicsSettings->Add(new CheckBox(&g_Config.bVSync, gr->T("VSync")));
|
CheckBox *vSync = graphicsSettings->Add(new CheckBox(&g_Config.bVSync, gr->T("VSync")));
|
||||||
|
vSync->OnClick.Add([=](EventParams &e) {
|
||||||
|
NativeResized();
|
||||||
|
return UI::EVENT_CONTINUE;
|
||||||
|
});
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
CheckBox *hwTransform = graphicsSettings->Add(new CheckBox(&g_Config.bHardwareTransform, gr->T("Hardware Transform")));
|
CheckBox *hwTransform = graphicsSettings->Add(new CheckBox(&g_Config.bHardwareTransform, gr->T("Hardware Transform")));
|
||||||
|
|
|
@ -74,6 +74,15 @@ static VulkanContext *g_Vulkan;
|
||||||
|
|
||||||
static VulkanLogOptions g_LogOptions;
|
static VulkanLogOptions g_LogOptions;
|
||||||
|
|
||||||
|
static uint32_t FlagsFromConfig() {
|
||||||
|
uint32_t flags = 0;
|
||||||
|
flags = g_Config.bVSync ? VULKAN_FLAG_PRESENT_FIFO : VULKAN_FLAG_PRESENT_MAILBOX;
|
||||||
|
if (g_validate_) {
|
||||||
|
flags |= VULKAN_FLAG_VALIDATE;
|
||||||
|
}
|
||||||
|
return flags;
|
||||||
|
}
|
||||||
|
|
||||||
bool WindowsVulkanContext::Init(HINSTANCE hInst, HWND hWnd, std::string *error_message) {
|
bool WindowsVulkanContext::Init(HINSTANCE hInst, HWND hWnd, std::string *error_message) {
|
||||||
*error_message = "N/A";
|
*error_message = "N/A";
|
||||||
|
|
||||||
|
@ -100,10 +109,7 @@ bool WindowsVulkanContext::Init(HINSTANCE hInst, HWND hWnd, std::string *error_m
|
||||||
VulkanContext::CreateInfo info{};
|
VulkanContext::CreateInfo info{};
|
||||||
info.app_name = "PPSSPP";
|
info.app_name = "PPSSPP";
|
||||||
info.app_ver = gitVer.ToInteger();
|
info.app_ver = gitVer.ToInteger();
|
||||||
info.flags = VULKAN_FLAG_PRESENT_MAILBOX;
|
info.flags = FlagsFromConfig();
|
||||||
if (g_validate_) {
|
|
||||||
info.flags |= VULKAN_FLAG_VALIDATE;
|
|
||||||
}
|
|
||||||
if (VK_SUCCESS != g_Vulkan->CreateInstance(info)) {
|
if (VK_SUCCESS != g_Vulkan->CreateInstance(info)) {
|
||||||
*error_message = g_Vulkan->InitError();
|
*error_message = g_Vulkan->InitError();
|
||||||
delete g_Vulkan;
|
delete g_Vulkan;
|
||||||
|
@ -184,6 +190,7 @@ void WindowsVulkanContext::Resize() {
|
||||||
draw_->HandleEvent(Draw::Event::LOST_BACKBUFFER, g_Vulkan->GetBackbufferWidth(), g_Vulkan->GetBackbufferHeight());
|
draw_->HandleEvent(Draw::Event::LOST_BACKBUFFER, g_Vulkan->GetBackbufferWidth(), g_Vulkan->GetBackbufferHeight());
|
||||||
g_Vulkan->DestroyObjects();
|
g_Vulkan->DestroyObjects();
|
||||||
|
|
||||||
|
g_Vulkan->UpdateFlags(FlagsFromConfig());
|
||||||
g_Vulkan->ReinitSurface();
|
g_Vulkan->ReinitSurface();
|
||||||
|
|
||||||
g_Vulkan->InitObjects();
|
g_Vulkan->InitObjects();
|
||||||
|
|
|
@ -739,6 +739,7 @@ namespace MainWindow {
|
||||||
|
|
||||||
case ID_OPTIONS_VSYNC:
|
case ID_OPTIONS_VSYNC:
|
||||||
g_Config.bVSync = !g_Config.bVSync;
|
g_Config.bVSync = !g_Config.bVSync;
|
||||||
|
NativeResized();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case ID_OPTIONS_FRAMESKIP_AUTO:
|
case ID_OPTIONS_FRAMESKIP_AUTO:
|
||||||
|
|
|
@ -81,6 +81,13 @@ AndroidVulkanContext::~AndroidVulkanContext() {
|
||||||
g_Vulkan = nullptr;
|
g_Vulkan = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static uint32_t FlagsFromConfig() {
|
||||||
|
if (g_Config.bVSync) {
|
||||||
|
return VULKAN_FLAG_PRESENT_FIFO;
|
||||||
|
}
|
||||||
|
return VULKAN_FLAG_PRESENT_MAILBOX | VULKAN_FLAG_PRESENT_FIFO_RELAXED;
|
||||||
|
}
|
||||||
|
|
||||||
bool AndroidVulkanContext::InitAPI() {
|
bool AndroidVulkanContext::InitAPI() {
|
||||||
ILOG("AndroidVulkanContext::Init");
|
ILOG("AndroidVulkanContext::Init");
|
||||||
init_glslang();
|
init_glslang();
|
||||||
|
@ -105,7 +112,7 @@ bool AndroidVulkanContext::InitAPI() {
|
||||||
VulkanContext::CreateInfo info{};
|
VulkanContext::CreateInfo info{};
|
||||||
info.app_name = "PPSSPP";
|
info.app_name = "PPSSPP";
|
||||||
info.app_ver = gitVer.ToInteger();
|
info.app_ver = gitVer.ToInteger();
|
||||||
info.flags = VULKAN_FLAG_PRESENT_MAILBOX | VULKAN_FLAG_PRESENT_FIFO_RELAXED;
|
info.flags = FlagsFromConfig();
|
||||||
VkResult res = g_Vulkan->CreateInstance(info);
|
VkResult res = g_Vulkan->CreateInstance(info);
|
||||||
if (res != VK_SUCCESS) {
|
if (res != VK_SUCCESS) {
|
||||||
ELOG("Failed to create vulkan context: %s", g_Vulkan->InitError().c_str());
|
ELOG("Failed to create vulkan context: %s", g_Vulkan->InitError().c_str());
|
||||||
|
@ -216,7 +223,7 @@ void AndroidVulkanContext::Resize() {
|
||||||
draw_->HandleEvent(Draw::Event::LOST_BACKBUFFER, g_Vulkan->GetBackbufferWidth(), g_Vulkan->GetBackbufferHeight());
|
draw_->HandleEvent(Draw::Event::LOST_BACKBUFFER, g_Vulkan->GetBackbufferWidth(), g_Vulkan->GetBackbufferHeight());
|
||||||
g_Vulkan->DestroyObjects();
|
g_Vulkan->DestroyObjects();
|
||||||
|
|
||||||
// backbufferResize updated these values. TODO: Notify another way?
|
g_Vulkan->UpdateFlags(FlagsFromConfig());
|
||||||
g_Vulkan->ReinitSurface();
|
g_Vulkan->ReinitSurface();
|
||||||
g_Vulkan->InitObjects();
|
g_Vulkan->InitObjects();
|
||||||
draw_->HandleEvent(Draw::Event::GOT_BACKBUFFER, g_Vulkan->GetBackbufferWidth(), g_Vulkan->GetBackbufferHeight());
|
draw_->HandleEvent(Draw::Event::GOT_BACKBUFFER, g_Vulkan->GetBackbufferWidth(), g_Vulkan->GetBackbufferHeight());
|
||||||
|
|
Loading…
Add table
Reference in a new issue