Skip to content

Commit

Permalink
Encapsulate managed swapchain capabilities in abstract interface
Browse files Browse the repository at this point in the history
  • Loading branch information
shg8 committed Apr 3, 2024
1 parent 15211be commit 89d1a1b
Show file tree
Hide file tree
Showing 18 changed files with 121 additions and 93 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@
B0608E432BA54D8E00CE9114 /* DummyImguiManager.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = DummyImguiManager.cpp; path = VulkanSplatting/DummyImguiManager.cpp; sourceTree = SOURCE_ROOT; };
B0608E472BA5522500CE9114 /* MetalWindow.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = MetalWindow.cpp; sourceTree = "<group>"; };
B0608E482BA5522500CE9114 /* MetalWindow.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = MetalWindow.h; sourceTree = "<group>"; };
B0608E4D2BA5557A00CE9114 /* RenderingTarget.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RenderingTarget.h; sourceTree = "<group>"; };
B0608E4D2BA5557A00CE9114 /* RenderTarget.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RenderTarget.h; sourceTree = "<group>"; };
B0608E4E2BA55BBB00CE9114 /* VulkanSplatting.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = VulkanSplatting.cpp; path = ../../../src/VulkanSplatting.cpp; sourceTree = "<group>"; };
B0A860112BA56169008B0F4F /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist; path = Info.plist; sourceTree = "<group>"; };
B0B7FB3C2BA7856600DA3A53 /* project.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = project.xcconfig; sourceTree = "<group>"; };
Expand Down Expand Up @@ -620,7 +620,7 @@
B0EA8A922BA302E6003B92F7 /* vulkan */ = {
isa = PBXGroup;
children = (
B0608E4D2BA5557A00CE9114 /* RenderingTarget.h */,
B0608E4D2BA5557A00CE9114 /* RenderTarget.h */,
B0608E492BA5522500CE9114 /* windowing */,
B0608E432BA54D8E00CE9114 /* DummyImguiManager.cpp */,
B0EA8A932BA302E6003B92F7 /* Utils.h */,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
#include "ImguiManager.h"

ImguiManager::ImguiManager(std::shared_ptr<VulkanContext> context, std::shared_ptr<Swapchain> swapchain,
std::shared_ptr<RenderingTarget> window) {
std::shared_ptr<RenderTarget> window) {
}

void ImguiManager::createCommandPool() {
Expand Down
4 changes: 2 additions & 2 deletions apps/vr_viewer/src/VRViewer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
#include <memory>
#include <openxr/openxr_platform.h>

#include "OXRContext.h"
#include "oxr/OXRContext.h"
#include "3dgs.h"
#include "spdlog/spdlog.h"

Expand All @@ -20,7 +20,7 @@ void VRViewer::run() {
configuration.postVulkanInit = std::bind(&VRViewer::finishSetup, this, std::placeholders::_1, std::placeholders::_2,
std::placeholders::_3, std::placeholders::_4, std::placeholders::_5);

auto renderingTarget = VulkanSplatting::createOpenXRRenderingTarget(configuration);
auto renderingTarget = VulkanSplatting::createOpenXRRenderTarget(configuration);
}

void VRViewer::finishSetup(void *vkInstance, void *vkPhysicalDevice, void *vkDevice, uint32_t vkQueueFamilyIndex,
Expand Down
2 changes: 1 addition & 1 deletion apps/vr_viewer/src/oxr/Layer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -132,7 +132,7 @@ namespace OXR {

void Layer::createProjectionViews(std::shared_ptr<OXRContext> context, uint64_t flags) {
for (int i = 0; i < 2; i++) {
views[i].pose = {.position = { 0.0f, 0.0f, 0.0f }, .orientation = { 0.0f, 0.0f, 0.0f, 1.0f }};
views[i].pose = {.orientation = { 0.0f, 0.0f, 0.0f, 1.0f }, .position = { 0.0f, 0.0f, 0.0f }};
views[i].subImage.swapchain = swapchains[i];
views[i].subImage.imageRect.offset = {0, 0};
views[i].subImage.imageRect.extent = {static_cast<int32_t>(context->views[i].recommendedImageRectWidth),
Expand Down
3 changes: 1 addition & 2 deletions apps/vr_viewer/src/oxr/Layer.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,9 @@
#include <cstdint>
#include <memory>
#include <vector>
#include <openxr/openxr.h>
#include <openxr/openxr_platform.h>

#include "OXRContext.h"
#include <openxr/openxr_platform.h>

namespace OXR {

Expand Down
10 changes: 5 additions & 5 deletions include/3dgs/3dgs.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
#include <memory>
#include <vector>

class RenderingTarget;
class RenderTarget;
class Renderer;

class VulkanSplatting {
Expand All @@ -23,17 +23,17 @@ class VulkanSplatting {
float far = 1000.0f;
bool enableGui = false;

std::shared_ptr<RenderingTarget> renderingTarget;
std::shared_ptr<RenderTarget> renderingTarget;
};

explicit VulkanSplatting(RendererConfiguration configuration) : configuration(configuration) {}

#ifdef VKGS_ENABLE_GLFW
static std::shared_ptr<RenderingTarget> createGlfwWindow(std::string name, int width, int height);
static std::shared_ptr<RenderTarget> createGlfwWindow(std::string name, int width, int height);
#endif

#ifdef VKGS_ENABLE_METAL
static std::shared_ptr<RenderingTarget> createMetalWindow(void *caMetalLayer, int width, int height);
static std::shared_ptr<RenderTarget> createMetalWindow(void *caMetalLayer, int width, int height);
#endif

#ifdef VKGS_ENABLE_OPENXR
Expand All @@ -44,7 +44,7 @@ class VulkanSplatting {
std::function<void*(void*)> getPhysicalDevice;
std::function<void(void*, void*, void*, uint32_t, uint32_t)> postVulkanInit;
};
static std::shared_ptr<RenderingTarget> createOpenXRRenderingTarget(OpenXRConfiguration configuration);
static std::shared_ptr<RenderTarget> createOpenXRRenderTarget(OpenXRConfiguration configuration);
#endif

void start();
Expand Down
6 changes: 3 additions & 3 deletions src/3dgs.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,19 +4,19 @@

#ifdef VKGS_ENABLE_GLFW
#include "vulkan/targets/GLFWWindow.h"
std::shared_ptr<RenderingTarget> VulkanSplatting::createGlfwWindow(std::string name, int width, int height) {
std::shared_ptr<RenderTarget> VulkanSplatting::createGlfwWindow(std::string name, int width, int height) {
return std::make_shared<GLFWWindow>(name, width, height);
}
#endif

#ifdef VKGS_ENABLE_METAL
#include "vulkan/windowing/MetalWindow.h"
std::shared_ptr<RenderingTarget> VulkanSplatting::createMetalWindow(void *caMetalLayer, int width, int height) {
std::shared_ptr<RenderTarget> VulkanSplatting::createMetalWindow(void *caMetalLayer, int width, int height) {
return std::make_shared<MetalWindow>(caMetalLayer, width, height);
}
#endif

std::shared_ptr<RenderingTarget> VulkanSplatting::createOpenXRRenderingTarget(OpenXRConfiguration configuration) {
std::shared_ptr<RenderTarget> VulkanSplatting::createOpenXRRenderTarget(OpenXRConfiguration configuration) {
auto target = std::make_shared<OpenXRStereo>(configuration);
return target;
}
Expand Down
55 changes: 18 additions & 37 deletions src/Renderer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -101,21 +101,15 @@ void Renderer::retrieveTimestamps() {
}
}

void Renderer::recreateSwapchain() {
auto oldExtent = swapchain->swapchainExtent;
spdlog::debug("Recreating swapchain");
swapchain->recreate();
if (swapchain->swapchainExtent == oldExtent) {
return;
}

auto [width, height] = swapchain->swapchainExtent;
void Renderer::recreatePipelines() {
auto [width, height] = swapchain->currentExtent();
auto tileX = (width + 16 - 1) / 16;
auto tileY = (height + 16 - 1) / 16;
tileBoundaryBuffer->realloc(tileX * tileY * sizeof(uint32_t) * 2);

recordPreprocessCommandBuffer();
createRenderPipeline();
return;
}

void Renderer::initializeVulkan() {
Expand Down Expand Up @@ -328,7 +322,7 @@ void Renderer::createPreprocessSortPipeline() {

void Renderer::createTileBoundaryPipeline() {
spdlog::debug("Creating tile boundary pipeline");
auto [width, height] = swapchain->swapchainExtent;
auto [width, height] = swapchain->currentExtent();
auto tileX = (width + 16 - 1) / 16;
auto tileY = (height + 16 - 1) / 16;
tileBoundaryBuffer = Buffer::storage(context, tileX * tileY * sizeof(uint32_t) * 2, false);
Expand Down Expand Up @@ -383,14 +377,15 @@ void Renderer::draw() {
}
context->device->resetFences(inflightFences[0].get());

auto res = context->device->acquireNextImageKHR(swapchain->swapchain.get(), UINT64_MAX,
swapchain->imageAvailableSemaphores[0].get(),
nullptr, &currentImageIndex);
if (res == vk::Result::eErrorOutOfDateKHR) {
recreateSwapchain();
auto [optionalImageIndex, extentChanged] = swapchain->acquireNextImage();
if (extentChanged) {
recreatePipelines();
}

if (!optionalImageIndex.has_value()) {
return;
} else if (res != vk::Result::eSuccess && res != vk::Result::eSuboptimalKHR) {
throw std::runtime_error("Failed to acquire swapchain image");
} else {
currentImageIndex = optionalImageIndex.value();
}

startOfRenderLoop:
Expand All @@ -417,24 +412,10 @@ void Renderer::draw() {
.setWaitDstStageMask(waitStage);
context->queues[VulkanContext::Queue::COMPUTE].queue.submit(submitInfo, inflightFences[0].get());

vk::PresentInfoKHR presentInfo{};
presentInfo.waitSemaphoreCount = 1;
presentInfo.pWaitSemaphores = &renderFinishedSemaphores[0].get();
presentInfo.swapchainCount = 1;
presentInfo.pSwapchains = &swapchain->swapchain.get();
presentInfo.pImageIndices = &currentImageIndex;

try {
ret = context->queues[VulkanContext::Queue::PRESENT].queue.presentKHR(presentInfo);
} catch (vk::OutOfDateKHRError &e) {
recreateSwapchain();
return;
}
extentChanged = swapchain->present(std::vector<vk::Semaphore>{renderFinishedSemaphores[0].get()}, currentImageIndex);

if (ret == vk::Result::eErrorOutOfDateKHR || ret == vk::Result::eSuboptimalKHR) {
recreateSwapchain();
} else if (ret != vk::Result::eSuccess) {
throw std::runtime_error("Failed to present swapchain image");
if (extentChanged) {
recreatePipelines();
}
}

Expand Down Expand Up @@ -592,7 +573,7 @@ bool Renderer::recordRenderCommandBuffer(uint32_t currentFrame) {
preprocessSortPipeline->bind(renderCommandBuffer, 0, iters % 2 == 0 ? 0 : 1);
renderCommandBuffer->writeTimestamp(vk::PipelineStageFlagBits::eComputeShader, context->queryPool.get(),
queryManager->registerQuery("preprocess_sort_start"));
uint32_t tileX = (swapchain->swapchainExtent.width + 16 - 1) / 16;
uint32_t tileX = (swapchain->currentExtent().width + 16 - 1) / 16;
// assert(tileX == 50);
renderCommandBuffer->pushConstants(preprocessSortPipeline->pipelineLayout.get(),
vk::ShaderStageFlagBits::eCompute, 0,
Expand Down Expand Up @@ -667,7 +648,7 @@ bool Renderer::recordRenderCommandBuffer(uint32_t currentFrame) {
renderPipeline->bind(renderCommandBuffer, 0, std::vector<uint32_t>{0, currentImageIndex});
renderCommandBuffer->writeTimestamp(vk::PipelineStageFlagBits::eComputeShader, context->queryPool.get(),
queryManager->registerQuery("render_start"));
auto [width, height] = swapchain->swapchainExtent;
auto [width, height] = swapchain->currentExtent();
uint32_t constants[2] = {width, height};
renderCommandBuffer->pushConstants(renderPipeline->pipelineLayout.get(),
vk::ShaderStageFlagBits::eCompute, 0,
Expand Down Expand Up @@ -731,7 +712,7 @@ bool Renderer::recordRenderCommandBuffer(uint32_t currentFrame) {

void Renderer::updateUniforms() {
UniformBuffer data{};
auto [width, height] = swapchain->swapchainExtent;
auto [width, height] = swapchain->currentExtent();
data.width = width;
data.height = height;
data.camera_position = glm::vec4(camera.position, 1.0f);
Expand Down
6 changes: 3 additions & 3 deletions src/Renderer.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
#include <atomic>
#include "3dgs.h"

#include "vulkan/RenderingTarget.h"
#include "vulkan/RenderTarget.h"
#include "GSScene.h"
#include "vulkan/pipelines/ComputePipeline.h"
#include "vulkan/Swapchain.h"
Expand Down Expand Up @@ -66,7 +66,7 @@ class Renderer {

void retrieveTimestamps();

void recreateSwapchain();
void recreatePipelines();

void draw();

Expand All @@ -86,7 +86,7 @@ class Renderer {

private:
VulkanSplatting::RendererConfiguration configuration;
std::shared_ptr<RenderingTarget> window;
std::shared_ptr<RenderTarget> window;
std::shared_ptr<VulkanContext> context;
std::shared_ptr<ImguiManager> imguiManager;
std::shared_ptr<GSScene> scene;
Expand Down
4 changes: 2 additions & 2 deletions src/vulkan/ImguiManager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
#include "targets/GLFWWindow.h"

ImguiManager::ImguiManager(std::shared_ptr<VulkanContext> context, std::shared_ptr<Swapchain> swapchain,
std::shared_ptr<RenderingTarget> window) : context(context), swapchain(swapchain), window(window) {
std::shared_ptr<RenderTarget> window) : context(context), swapchain(swapchain), window(window) {
}

void ImguiManager::createCommandPool() {
Expand Down Expand Up @@ -171,7 +171,7 @@ void ImguiManager::draw(vk::CommandBuffer commandBuffer, uint32_t currentImageIn
vk::RenderingAttachmentInfoKHR attachment_info{
swapchain->swapchainImages[currentImageIndex]->imageView.get(), vk::ImageLayout::eColorAttachmentOptimal
};
vk::RenderingInfoKHR rendering_info{{}, vk::Rect2D{{0, 0}, swapchain->swapchainExtent}, 1, {}, 1, &attachment_info};
vk::RenderingInfoKHR rendering_info{{}, vk::Rect2D{{0, 0}, swapchain->currentExtent()}, 1, {}, 1, &attachment_info};
commandBuffer.beginRenderingKHR(rendering_info);
ImGui_ImplVulkan_RenderDrawData(ImGui::GetDrawData(), commandBuffer);
commandBuffer.endRenderingKHR();
Expand Down
6 changes: 3 additions & 3 deletions src/vulkan/ImguiManager.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,11 @@

#include "VulkanContext.h"
#include "Swapchain.h"
#include "RenderingTarget.h"
#include "RenderTarget.h"

class ImguiManager {
public:
ImguiManager(std::shared_ptr<VulkanContext> context, std::shared_ptr<Swapchain> swapchain, std::shared_ptr<RenderingTarget> window);
ImguiManager(std::shared_ptr<VulkanContext> context, std::shared_ptr<Swapchain> swapchain, std::shared_ptr<RenderTarget> window);

void createCommandPool();

Expand All @@ -25,7 +25,7 @@ class ImguiManager {
private:
std::shared_ptr<VulkanContext> context;
std::shared_ptr<Swapchain> swapchain;
std::shared_ptr<RenderingTarget> window;
std::shared_ptr<RenderTarget> window;
vk::UniqueCommandPool commandPool;
vk::UniqueCommandBuffer commandBuffer;
vk::UniqueFence fence;
Expand Down
4 changes: 2 additions & 2 deletions src/vulkan/RenderingTarget.h → src/vulkan/RenderTarget.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@

#include "VulkanContext.h"

class RenderingTarget {
class RenderTarget {
public:
virtual VkSurfaceKHR createSurface(std::shared_ptr<VulkanContext> context) = 0;

Expand All @@ -34,7 +34,7 @@ class RenderingTarget {
return std::nullopt;
}

virtual ~RenderingTarget() = default;
virtual ~RenderTarget() = default;

};

Expand Down
Loading

0 comments on commit 89d1a1b

Please sign in to comment.