mirror of
https://github.com/Nexoniarz/Fry3DX.git
synced 2026-11-03 04:24:26 +00:00
Phones: sideways only; back from the background the Vulkan surface is made again (it was lost), the work saved on the way out and carried on with on the next start if the phone closed it
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
parent
c1991d9f73
commit
a79a6c9020
9 changed files with 87 additions and 2 deletions
|
|
@ -404,6 +404,7 @@ public:
|
|||
}
|
||||
void setVsync(bool on) override { device_.setVsync(on); }
|
||||
void onResize() override { device_.markResized(); }
|
||||
void onSurfaceLost() override { device_.markSurfaceLost(); }
|
||||
|
||||
bool renderScale() const override { return true; }
|
||||
bool blockCompression() const override {
|
||||
|
|
|
|||
|
|
@ -263,6 +263,24 @@ bool Device::createSwapchain() {
|
|||
return true;
|
||||
}
|
||||
|
||||
// A new surface on the window as it is now (Android makes a new one each time the app comes back).
|
||||
bool Device::recreateSurface() {
|
||||
vkDeviceWaitIdle(device_);
|
||||
destroySwapchainViews();
|
||||
if (swapchain_) vkDestroySwapchainKHR(device_, swapchain_, nullptr), swapchain_ = VK_NULL_HANDLE;
|
||||
if (surface_) vkDestroySurfaceKHR(instance_, surface_, nullptr), surface_ = VK_NULL_HANDLE;
|
||||
if (!SDL_Vulkan_CreateSurface(window_->handle(), instance_, nullptr, &surface_)) {
|
||||
log::warn("SDL_Vulkan_CreateSurface (again): {}", SDL_GetError());
|
||||
surface_ = VK_NULL_HANDLE;
|
||||
return false; // (tried again next frame)
|
||||
}
|
||||
VkBool32 present = VK_FALSE;
|
||||
vkGetPhysicalDeviceSurfaceSupportKHR(physical_, queueFamily_, surface_, &present);
|
||||
if (!present) log::warn("The new surface can't be presented to from this queue");
|
||||
surfaceLost_ = false;
|
||||
return createSwapchain();
|
||||
}
|
||||
|
||||
void Device::destroySwapchainViews() {
|
||||
for (VkImageView v : views_) vkDestroyImageView(device_, v, nullptr);
|
||||
for (VkSemaphore s : renderDone_) vkDestroySemaphore(device_, s, nullptr);
|
||||
|
|
@ -271,6 +289,7 @@ void Device::destroySwapchainViews() {
|
|||
}
|
||||
|
||||
VkCommandBuffer Device::beginFrame() {
|
||||
if (surfaceLost_ && !recreateSurface()) return nullptr;
|
||||
if (swapchainDirty_ && !createSwapchain()) return nullptr;
|
||||
|
||||
Frame& f = frames_[frameIndex_];
|
||||
|
|
@ -280,6 +299,10 @@ VkCommandBuffer Device::beginFrame() {
|
|||
swapchainDirty_ = true;
|
||||
return nullptr;
|
||||
}
|
||||
if (r == VK_ERROR_SURFACE_LOST_KHR) {
|
||||
surfaceLost_ = true;
|
||||
return nullptr;
|
||||
}
|
||||
if (r != VK_SUBOPTIMAL_KHR) VK_CHECK(r);
|
||||
VK_CHECK(vkResetFences(device_, 1, &f.inFlight));
|
||||
|
||||
|
|
@ -328,6 +351,7 @@ void Device::endFrame() {
|
|||
}
|
||||
#endif
|
||||
if (r == VK_ERROR_OUT_OF_DATE_KHR || r == VK_SUBOPTIMAL_KHR) swapchainDirty_ = true;
|
||||
else if (r == VK_ERROR_SURFACE_LOST_KHR) surfaceLost_ = true;
|
||||
else VK_CHECK(r);
|
||||
|
||||
frameIndex_ = (frameIndex_ + 1) % kFramesInFlight;
|
||||
|
|
|
|||
|
|
@ -50,6 +50,8 @@ public:
|
|||
|
||||
void setVsync(bool vsync) { vsync_ = vsync; swapchainDirty_ = true; }
|
||||
void markResized() { swapchainDirty_ = true; }
|
||||
// The window's surface went away (a phone: the app was in the background): made again.
|
||||
void markSurfaceLost() { surfaceLost_ = true; }
|
||||
void waitIdle() { vkDeviceWaitIdle(device_); }
|
||||
|
||||
VkInstance instance() const { return instance_; }
|
||||
|
|
@ -81,6 +83,7 @@ private:
|
|||
};
|
||||
|
||||
bool createSwapchain();
|
||||
bool recreateSurface();
|
||||
void destroySwapchainViews();
|
||||
|
||||
const Window* window_ = nullptr;
|
||||
|
|
@ -102,7 +105,7 @@ private:
|
|||
std::vector<VkImageView> views_;
|
||||
std::vector<VkSemaphore> renderDone_; // per swapchain image, so present never reuses one in flight
|
||||
bool vsync_ = true;
|
||||
bool swapchainDirty_ = false;
|
||||
bool swapchainDirty_ = false, surfaceLost_ = false;
|
||||
|
||||
Frame frames_[kFramesInFlight];
|
||||
VkCommandPool immPool_ = VK_NULL_HANDLE;
|
||||
|
|
|
|||
Loading…
Reference in a new issue