diff --git a/config/visual-studio/renderer.vcxproj b/config/visual-studio/renderer.vcxproj
index 6fb2731..def2f7f 100644
--- a/config/visual-studio/renderer.vcxproj
+++ b/config/visual-studio/renderer.vcxproj
@@ -105,7 +105,6 @@
-
@@ -132,7 +131,6 @@
-
@@ -140,9 +138,7 @@
-
-
diff --git a/config/visual-studio/renderer.vcxproj.filters b/config/visual-studio/renderer.vcxproj.filters
index 62a97b6..4e0a0bc 100644
--- a/config/visual-studio/renderer.vcxproj.filters
+++ b/config/visual-studio/renderer.vcxproj.filters
@@ -92,12 +92,6 @@
Source Files
-
- Source Files
-
-
- Source Files
-
Source Files
@@ -157,12 +151,6 @@
Header Files
-
- Source Files
-
-
- Source Files
-
Source Files
diff --git a/src/engine/platform/win_glimp.c b/src/engine/platform/win_glimp.c
index c6e781e..2857f9c 100644
--- a/src/engine/platform/win_glimp.c
+++ b/src/engine/platform/win_glimp.c
@@ -41,9 +41,6 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
#include "glw_win.h"
#include "win_local.h"
-// VULKAN
-#include "../../engine/renderer/vk_demo.h"
-
extern void WG_CheckHardwareGamma( void );
extern void WG_RestoreGamma( void );
@@ -572,7 +569,6 @@ static bool GLW_SetMode(int mode, qboolean fullscreen) {
ri.Printf(PRINT_WARNING, "GLW_SetMode: could not create API compare window");
} else {
g_wv.hWnd_vulkan = hwnd2;
- vulkan_demo = new Vulkan_Demo(glConfig.vidWidth, glConfig.vidHeight);
}
}
} else { // vulkan
@@ -581,7 +577,6 @@ static bool GLW_SetMode(int mode, qboolean fullscreen) {
DestroyWindow(hwnd);
return false;
}
- vulkan_demo = new Vulkan_Demo(glConfig.vidWidth, glConfig.vidHeight);
g_wv.hWnd = hwnd;
g_wv.hWnd_vulkan = hwnd;
diff --git a/src/engine/renderer/tr_backend.c b/src/engine/renderer/tr_backend.c
index 840320f..759fe47 100644
--- a/src/engine/renderer/tr_backend.c
+++ b/src/engine/renderer/tr_backend.c
@@ -23,7 +23,6 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
// VULKAN
#include "vk.h"
-#include "vk_demo.h"
#include "vk_utils.h"
backEndData_t *backEndData[SMP_FRAMES];
@@ -746,23 +745,23 @@ void RE_StretchRaw (int x, int y, int w, int h, int cols, int rows, const byte *
vk_update_cinematic_image(vk_image.image, vk_image.staging_buffer, cols, rows, data);
VkDescriptorImageInfo image_info;
- image_info.sampler = vulkan_demo->texture_image_sampler;
+ image_info.sampler = vk.sampler;
image_info.imageView = vk_image.image_view;
image_info.imageLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
- std::array descriptor_writes;
- descriptor_writes[0].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
- descriptor_writes[0].dstSet = vk_image.descriptor_set;
- descriptor_writes[0].dstBinding = 0;
- descriptor_writes[0].dstArrayElement = 0;
- descriptor_writes[0].descriptorCount = 1;
- descriptor_writes[0].pNext = nullptr;
- descriptor_writes[0].descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
- descriptor_writes[0].pImageInfo = &image_info;
- descriptor_writes[0].pBufferInfo = nullptr;
- descriptor_writes[0].pTexelBufferView = nullptr;
+ VkWriteDescriptorSet descriptor_write;
+ descriptor_write.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
+ descriptor_write.dstSet = vk_image.descriptor_set;
+ descriptor_write.dstBinding = 0;
+ descriptor_write.dstArrayElement = 0;
+ descriptor_write.descriptorCount = 1;
+ descriptor_write.pNext = nullptr;
+ descriptor_write.descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
+ descriptor_write.pImageInfo = &image_info;
+ descriptor_write.pBufferInfo = nullptr;
+ descriptor_write.pTexelBufferView = nullptr;
- vkUpdateDescriptorSets(vk.device, (uint32_t)descriptor_writes.size(), descriptor_writes.data(), 0, nullptr);
+ vkUpdateDescriptorSets(vk.device, 1, &descriptor_write, 0, nullptr);
} else {
if (dirty) {
// otherwise, just subimage upload it so that drivers can tell we are going to be changing
@@ -1053,49 +1052,7 @@ const void *RB_SwapBuffers( const void *data ) {
backEnd.projection2D = qfalse;
// VULKAN
- extern FILE* vk_log_file;
-
- if (r_logFile->integer)
- fprintf(vk_log_file, "end_frame (vb_size %d, ib_size %d)\n",
- vk.xyz_elements * 16 + vk.color_st_elements * 20,
- (int)vk.index_buffer_offset);
-
- vkCmdEndRenderPass(vk.command_buffer);
-
- VkResult result = vkEndCommandBuffer(vk.command_buffer);
- check_vk_result(result, "vkEndCommandBuffer");
-
- if (r_logFile->integer) {
- fprintf(vk_log_file, "present\n");
- fflush(vk_log_file);
- }
-
- VkPipelineStageFlags wait_dst_stage_mask = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT;
- VkSubmitInfo submit_info;
- submit_info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO;
- submit_info.pNext = nullptr;
- submit_info.waitSemaphoreCount = 1;
- submit_info.pWaitSemaphores = &vulkan_demo->image_acquired;
- submit_info.pWaitDstStageMask = &wait_dst_stage_mask;
- submit_info.commandBufferCount = 1;
- submit_info.pCommandBuffers = &vk.command_buffer;
- submit_info.signalSemaphoreCount = 1;
- submit_info.pSignalSemaphores = &vulkan_demo->rendering_finished;
-
- result = vkQueueSubmit(vk.queue, 1, &submit_info, vulkan_demo->rendering_finished_fence);
- check_vk_result(result, "vkQueueSubmit");
-
- VkPresentInfoKHR present_info;
- present_info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR;
- present_info.pNext = nullptr;
- present_info.waitSemaphoreCount = 1;
- present_info.pWaitSemaphores = &vulkan_demo->rendering_finished;
- present_info.swapchainCount = 1;
- present_info.pSwapchains = &vk.swapchain;
- present_info.pImageIndices = &vulkan_demo->swapchain_image_index;
- present_info.pResults = nullptr;
- result = vkQueuePresentKHR(vk.queue, &present_info);
- check_vk_result(result, "vkQueuePresentKHR");
+ vk_end_frame();
return (const void *)(cmd + 1);
}
diff --git a/src/engine/renderer/tr_image.c b/src/engine/renderer/tr_image.c
index 26ef4e1..2f36691 100644
--- a/src/engine/renderer/tr_image.c
+++ b/src/engine/renderer/tr_image.c
@@ -22,9 +22,6 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
// tr_image.c
#include "tr_local.h"
-// VULKAN
-#include "vk_demo.h"
-
static void* q3_stbi_malloc(size_t size) {
return ri.Malloc((int)size);
}
@@ -780,7 +777,7 @@ image_t *R_CreateImage( const char *name, const byte *pic, int width, int height
// VULKAN
Vk_Image& vk_image = tr.vk_resources.images[image->index];
- vk_image.image = vulkan_demo->create_texture(pic, 4, width, height, vk_image.image_view);
+ vk_image.image = vk_create_texture(pic, 4, width, height, vk_image.image_view);
vk_image.descriptor_set = vk_create_descriptor_set(vk_image.image_view);
return image;
diff --git a/src/engine/renderer/tr_local.h b/src/engine/renderer/tr_local.h
index d320946..0d52217 100644
--- a/src/engine/renderer/tr_local.h
+++ b/src/engine/renderer/tr_local.h
@@ -951,11 +951,7 @@ extern glconfig_t glConfig; // outside of TR since it shouldn't be cleared duri
extern glstate_t glState; // outside of TR since it shouldn't be cleared during ref re-init
// VULKAN
-extern Vulkan_Instance vk; // same as above - shouldn't be cleared during ref re-init
-
-// VULKAN
-class Vulkan_Demo;
-extern Vulkan_Demo* vulkan_demo;
+extern Vulkan_Instance vk; // same as above - shouldn't be cleared during ref re-init
//
diff --git a/src/engine/renderer/tr_main.c b/src/engine/renderer/tr_main.c
index ae1e1bc..7e9a7a8 100644
--- a/src/engine/renderer/tr_main.c
+++ b/src/engine/renderer/tr_main.c
@@ -25,9 +25,6 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
trGlobals_t tr;
-// VULKAN
-Vulkan_Demo* vulkan_demo;
-
static float s_flipMatrix[16] = {
// convert from our coordinate system (looking down X)
// to OpenGL's coordinate system (looking down -Z)
diff --git a/src/engine/renderer/tr_scene.c b/src/engine/renderer/tr_scene.c
index a875f26..dc15cfb 100644
--- a/src/engine/renderer/tr_scene.c
+++ b/src/engine/renderer/tr_scene.c
@@ -22,9 +22,6 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
#include "tr_local.h"
-// VULKAN
-#include "vk_demo.h"
-
int r_firstSceneDrawSurf;
int r_numdlights;
diff --git a/src/engine/renderer/tr_shade.c b/src/engine/renderer/tr_shade.c
index 522fe28..9763078 100644
--- a/src/engine/renderer/tr_shade.c
+++ b/src/engine/renderer/tr_shade.c
@@ -23,9 +23,6 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
#include "tr_local.h"
-// VULKAN
-#include "vk_demo.h"
-
/*
THIS ENTIRE FILE IS BACK END
diff --git a/src/engine/renderer/vk.cpp b/src/engine/renderer/vk.cpp
index 8d1213f..20d8817 100644
--- a/src/engine/renderer/vk.cpp
+++ b/src/engine/renderer/vk.cpp
@@ -2,12 +2,12 @@
#include "vk_utils.h"
#include "vk_allocator.h"
-#include "vk_resource_manager.h"
-
-#include "vk_demo.h"
+#include
#include
+FILE* vk_log_file;
+
const int VERTEX_CHUNK_SIZE = 512 * 1024;
const int XYZ_SIZE = 4 * VERTEX_CHUNK_SIZE;
@@ -327,6 +327,8 @@ static VkRenderPass create_render_pass(VkDevice device, VkFormat color_format, V
VkPipeline create_pipeline(const Vk_Pipeline_Desc&);
bool vk_initialize(HWND hwnd) {
+ vk_log_file = fopen("vk_dev.log", "w");
+
try {
auto& g = vk;
@@ -394,7 +396,6 @@ bool vk_initialize(HWND hwnd) {
}
get_allocator()->initialize(vk.physical_device, vk.device);
- get_resource_manager()->initialize(vk.device);
{
VkFormat depth_format = find_depth_format(vk.physical_device);
@@ -412,15 +413,15 @@ bool vk_initialize(HWND hwnd) {
vk.render_pass = create_render_pass(vk.device, vk.surface_format.format, depth_format);
{
- std::array attachments = {VK_NULL_HANDLE, vk.depth_image_view};
+ VkImageView attachments[2] = {VK_NULL_HANDLE, vk.depth_image_view};
VkFramebufferCreateInfo desc;
desc.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO;
desc.pNext = nullptr;
desc.flags = 0;
desc.renderPass = vk.render_pass;
- desc.attachmentCount = static_cast(attachments.size());
- desc.pAttachments = attachments.data();
+ desc.attachmentCount = 2;
+ desc.pAttachments = attachments;
desc.width = glConfig.vidWidth;
desc.height = glConfig.vidHeight;
desc.layers = 1;
@@ -499,7 +500,7 @@ bool vk_initialize(HWND hwnd) {
}
//
- // Create geometry buffers.
+ // Geometry buffers.
//
{
VkBufferCreateInfo desc;
@@ -548,6 +549,34 @@ bool vk_initialize(HWND hwnd) {
vk.index_buffer_ptr = (byte*)data;
}
+ //
+ // Samplers.
+ //
+ {
+ VkSamplerCreateInfo desc;
+ desc.sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO;
+ desc.pNext = nullptr;
+ desc.flags = 0;
+ desc.magFilter = VK_FILTER_LINEAR;
+ desc.minFilter = VK_FILTER_LINEAR;
+ desc.mipmapMode = VK_SAMPLER_MIPMAP_MODE_NEAREST;
+ desc.addressModeU = VK_SAMPLER_ADDRESS_MODE_REPEAT;
+ desc.addressModeV = VK_SAMPLER_ADDRESS_MODE_REPEAT;
+ desc.addressModeW = VK_SAMPLER_ADDRESS_MODE_REPEAT;
+ desc.mipLodBias = 0.0f;
+ desc.anisotropyEnable = VK_TRUE;
+ desc.maxAnisotropy = 1;
+ desc.compareEnable = VK_FALSE;
+ desc.compareOp = VK_COMPARE_OP_ALWAYS;
+ desc.minLod = 0.0f;
+ desc.maxLod = 0.0f;
+ desc.borderColor = VK_BORDER_COLOR_INT_OPAQUE_BLACK;
+ desc.unnormalizedCoordinates = VK_FALSE;
+
+ VkResult result = vkCreateSampler(vk.device, &desc, nullptr, &vk.sampler);
+ check_vk_result(result, "vkCreateSampler");
+ }
+
//
// Skybox pipeline.
//
@@ -561,6 +590,28 @@ bool vk_initialize(HWND hwnd) {
vk.skybox_pipeline = create_pipeline(desc);
}
+ //
+ // Sync primitives.
+ //
+ {
+ VkSemaphoreCreateInfo desc;
+ desc.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO;
+ desc.pNext = nullptr;
+ desc.flags = 0;
+
+ VkResult result = vkCreateSemaphore(vk.device, &desc, nullptr, &vk.image_acquired);
+ check_vk_result(result, "vkCreateSemaphore");
+ result = vkCreateSemaphore(vk.device, &desc, nullptr, &vk.rendering_finished);
+ check_vk_result(result, "vkCreateSemaphore");
+
+ VkFenceCreateInfo fence_desc;
+ fence_desc.sType = VK_STRUCTURE_TYPE_FENCE_CREATE_INFO;
+ fence_desc.pNext = nullptr;
+ fence_desc.flags = VK_FENCE_CREATE_SIGNALED_BIT;
+ result = vkCreateFence(vk.device, &fence_desc, nullptr, &vk.rendering_finished_fence);
+ check_vk_result(result, "vkCreateFence");
+ }
+
} catch (const std::exception&) {
return false;
}
@@ -568,12 +619,13 @@ bool vk_initialize(HWND hwnd) {
}
void vk_deinitialize() {
+ fclose(vk_log_file);
+ vk_log_file = nullptr;
+
auto& g = vk;
- get_resource_manager()->release_resources();
get_allocator()->deallocate_all();
- vkDestroyFence(vk.device, vulkan_demo->rendering_finished_fence, nullptr);
vkDestroyImage(vk.device, vk.depth_image, nullptr);
vkDestroyImageView(vk.device, vk.depth_image_view, nullptr);
@@ -594,7 +646,11 @@ void vk_deinitialize() {
vkDestroyPipelineLayout(vk.device, vk.pipeline_layout, nullptr);
vkDestroyBuffer(vk.device, vk.vertex_buffer, nullptr);
vkDestroyBuffer(vk.device, vk.index_buffer, nullptr);
+ vkDestroySampler(vk.device, vk.sampler, nullptr);
vkDestroyPipeline(vk.device, vk.skybox_pipeline, nullptr);
+ vkDestroySemaphore(vk.device, vk.image_acquired, nullptr);
+ vkDestroySemaphore(vk.device, vk.rendering_finished, nullptr);
+ vkDestroyFence(vk.device, vk.rendering_finished_fence, nullptr);
vkDestroySwapchainKHR(g.device, g.swapchain, nullptr);
vkDestroyDevice(g.device, nullptr);
@@ -604,6 +660,55 @@ void vk_deinitialize() {
g = Vulkan_Instance();
}
+VkImage vk_create_texture(const uint8_t* pixels, int bytes_per_pixel, int image_width, int image_height, VkImageView& image_view) {
+ VkImage staging_image = create_staging_texture(image_width, image_height,
+ bytes_per_pixel == 3 ? VK_FORMAT_R8G8B8_UNORM : VK_FORMAT_R8G8B8A8_UNORM, pixels, bytes_per_pixel);
+
+ Defer_Action destroy_staging_image([&staging_image]() {
+ vkDestroyImage(vk.device, staging_image, nullptr);
+ });
+
+ VkImage texture_image = ::create_texture(image_width, image_height,
+ bytes_per_pixel == 3 ? VK_FORMAT_R8G8B8_UNORM : VK_FORMAT_R8G8B8A8_UNORM);
+
+ record_and_run_commands(vk.command_pool, vk.queue,
+ [&texture_image, &staging_image, &image_width, &image_height](VkCommandBuffer command_buffer) {
+
+ record_image_layout_transition(command_buffer, staging_image, VK_FORMAT_R8G8B8A8_UNORM,
+ VK_ACCESS_HOST_WRITE_BIT, VK_IMAGE_LAYOUT_PREINITIALIZED, VK_ACCESS_TRANSFER_READ_BIT, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL);
+
+ record_image_layout_transition(command_buffer, texture_image, VK_FORMAT_R8G8B8A8_UNORM,
+ 0, VK_IMAGE_LAYOUT_UNDEFINED, VK_ACCESS_TRANSFER_WRITE_BIT, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL);
+
+ // copy staging image's data to device local image
+ VkImageSubresourceLayers subresource_layers;
+ subresource_layers.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT;
+ subresource_layers.mipLevel = 0;
+ subresource_layers.baseArrayLayer = 0;
+ subresource_layers.layerCount = 1;
+
+ VkImageCopy region;
+ region.srcSubresource = subresource_layers;
+ region.srcOffset = {0, 0, 0};
+ region.dstSubresource = subresource_layers;
+ region.dstOffset = {0, 0, 0};
+ region.extent.width = image_width;
+ region.extent.height = image_height;
+ region.extent.depth = 1;
+
+ vkCmdCopyImage(command_buffer,
+ staging_image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL,
+ texture_image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,
+ 1, ®ion);
+
+ record_image_layout_transition(command_buffer, texture_image, VK_FORMAT_R8G8B8A8_UNORM,
+ VK_ACCESS_TRANSFER_WRITE_BIT, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_ACCESS_SHADER_READ_BIT, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL);
+ });
+
+ image_view = create_image_view(texture_image, VK_FORMAT_R8G8B8A8_UNORM, VK_IMAGE_ASPECT_COLOR_BIT);
+ return texture_image;
+}
+
VkImage vk_create_cinematic_image(int width, int height, Vk_Staging_Buffer& staging_buffer) {
VkBufferCreateInfo buffer_desc;
buffer_desc.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO;
@@ -723,14 +828,14 @@ static VkPipeline create_pipeline(const Vk_Pipeline_Desc& desc) {
else
ri.Error(ERR_DROP, "create_pipeline: invalid alpha test state bits\n");
- std::array specialization_entries;
+ VkSpecializationMapEntry specialization_entries[1];
specialization_entries[0].constantID = 0;
specialization_entries[0].offset = offsetof(struct Specialization_Data, alpha_test_func);
specialization_entries[0].size = sizeof(int32_t);
VkSpecializationInfo specialization_info;
- specialization_info.mapEntryCount = uint32_t(specialization_entries.size());
- specialization_info.pMapEntries = specialization_entries.data();
+ specialization_info.mapEntryCount = 1;
+ specialization_info.pMapEntries = specialization_entries;
specialization_info.dataSize = sizeof(Specialization_Data);
specialization_info.pData = &specialization_data;
@@ -1052,23 +1157,23 @@ VkDescriptorSet vk_create_descriptor_set(VkImageView image_view) {
check_vk_result(result, "vkAllocateDescriptorSets");
VkDescriptorImageInfo image_info;
- image_info.sampler = vulkan_demo->texture_image_sampler;
+ image_info.sampler = vk.sampler;
image_info.imageView = image_view;
image_info.imageLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
- std::array descriptor_writes;
- descriptor_writes[0].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
- descriptor_writes[0].dstSet = set;
- descriptor_writes[0].dstBinding = 0;
- descriptor_writes[0].dstArrayElement = 0;
- descriptor_writes[0].descriptorCount = 1;
- descriptor_writes[0].pNext = nullptr;
- descriptor_writes[0].descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
- descriptor_writes[0].pImageInfo = &image_info;
- descriptor_writes[0].pBufferInfo = nullptr;
- descriptor_writes[0].pTexelBufferView = nullptr;
+ VkWriteDescriptorSet descriptor_write;
+ descriptor_write.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
+ descriptor_write.dstSet = set;
+ descriptor_write.dstBinding = 0;
+ descriptor_write.dstArrayElement = 0;
+ descriptor_write.descriptorCount = 1;
+ descriptor_write.pNext = nullptr;
+ descriptor_write.descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
+ descriptor_write.pImageInfo = &image_info;
+ descriptor_write.pBufferInfo = nullptr;
+ descriptor_write.pTexelBufferView = nullptr;
- vkUpdateDescriptorSets(vk.device, (uint32_t)descriptor_writes.size(), descriptor_writes.data(), 0, nullptr);
+ vkUpdateDescriptorSets(vk.device, 1, &descriptor_write, 0, nullptr);
return set;
}
@@ -1287,16 +1392,15 @@ void vk_bind_stage_specific_resources(VkPipeline pipeline, bool multitexture, bo
}
void vk_begin_frame() {
- extern FILE* vk_log_file;
if (r_logFile->integer)
fprintf(vk_log_file, "vk_begin_frame\n");
- VkResult result = vkAcquireNextImageKHR(vk.device, vk.swapchain, UINT64_MAX, vulkan_demo->image_acquired, VK_NULL_HANDLE, &vulkan_demo->swapchain_image_index);
+ VkResult result = vkAcquireNextImageKHR(vk.device, vk.swapchain, UINT64_MAX, vk.image_acquired, VK_NULL_HANDLE, &vk.swapchain_image_index);
check_vk_result(result, "vkAcquireNextImageKHR");
- result = vkWaitForFences(vk.device, 1, &vulkan_demo->rendering_finished_fence, VK_FALSE, 1e9);
+ result = vkWaitForFences(vk.device, 1, &vk.rendering_finished_fence, VK_FALSE, 1e9);
check_vk_result(result, "vkWaitForFences");
- result = vkResetFences(vk.device, 1, &vulkan_demo->rendering_finished_fence);
+ result = vkResetFences(vk.device, 1, &vk.rendering_finished_fence);
check_vk_result(result, "vkResetFences");
VkCommandBufferBeginInfo begin_info;
@@ -1317,7 +1421,7 @@ void vk_begin_frame() {
render_pass_begin_info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO;
render_pass_begin_info.pNext = nullptr;
render_pass_begin_info.renderPass = vk.render_pass;
- render_pass_begin_info.framebuffer = vk.framebuffers[vulkan_demo->swapchain_image_index];
+ render_pass_begin_info.framebuffer = vk.framebuffers[vk.swapchain_image_index];
render_pass_begin_info.renderArea.offset = { 0, 0 };
render_pass_begin_info.renderArea.extent = { (uint32_t)glConfig.vidWidth, (uint32_t)glConfig.vidHeight };
render_pass_begin_info.clearValueCount = 2;
@@ -1331,3 +1435,47 @@ void vk_begin_frame() {
glState.vk_dirty_attachments = false;
}
+
+void vk_end_frame() {
+ if (r_logFile->integer)
+ fprintf(vk_log_file, "end_frame (vb_size %d, ib_size %d)\n",
+ vk.xyz_elements * 16 + vk.color_st_elements * 20,
+ (int)vk.index_buffer_offset);
+
+ vkCmdEndRenderPass(vk.command_buffer);
+
+ VkResult result = vkEndCommandBuffer(vk.command_buffer);
+ check_vk_result(result, "vkEndCommandBuffer");
+
+ if (r_logFile->integer) {
+ fprintf(vk_log_file, "present\n");
+ fflush(vk_log_file);
+ }
+
+ VkPipelineStageFlags wait_dst_stage_mask = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT;
+ VkSubmitInfo submit_info;
+ submit_info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO;
+ submit_info.pNext = nullptr;
+ submit_info.waitSemaphoreCount = 1;
+ submit_info.pWaitSemaphores = &vk.image_acquired;
+ submit_info.pWaitDstStageMask = &wait_dst_stage_mask;
+ submit_info.commandBufferCount = 1;
+ submit_info.pCommandBuffers = &vk.command_buffer;
+ submit_info.signalSemaphoreCount = 1;
+ submit_info.pSignalSemaphores = &vk.rendering_finished;
+
+ result = vkQueueSubmit(vk.queue, 1, &submit_info, vk.rendering_finished_fence);
+ check_vk_result(result, "vkQueueSubmit");
+
+ VkPresentInfoKHR present_info;
+ present_info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR;
+ present_info.pNext = nullptr;
+ present_info.waitSemaphoreCount = 1;
+ present_info.pWaitSemaphores = &vk.rendering_finished;
+ present_info.swapchainCount = 1;
+ present_info.pSwapchains = &vk.swapchain;
+ present_info.pImageIndices = &vk.swapchain_image_index;
+ present_info.pResults = nullptr;
+ result = vkQueuePresentKHR(vk.queue, &present_info);
+ check_vk_result(result, "vkQueuePresentKHR");
+}
diff --git a/src/engine/renderer/vk.h b/src/engine/renderer/vk.h
index d2348a0..fc8193a 100644
--- a/src/engine/renderer/vk.h
+++ b/src/engine/renderer/vk.h
@@ -56,6 +56,7 @@ bool vk_initialize(HWND hwnd);
void vk_deinitialize();
void vk_destroy_resources();
+VkImage vk_create_texture(const uint8_t* pixels, int bytes_per_pixel, int width, int height, VkImageView& image_view);
VkImage vk_create_cinematic_image(int width, int height, Vk_Staging_Buffer& staging_buffer);
void vk_update_cinematic_image(VkImage image, const Vk_Staging_Buffer& staging_buffer, int width, int height, const uint8_t* rgba_pixels);
VkPipeline vk_find_pipeline(const Vk_Pipeline_Desc& desc);
@@ -68,6 +69,7 @@ void vk_bind_resources_shared_between_stages();
void vk_bind_stage_specific_resources(VkPipeline pipeline, bool multitexture, bool sky);
void vk_begin_frame();
+void vk_end_frame();
// Shaders.
@@ -126,7 +128,15 @@ struct Vulkan_Instance {
byte* index_buffer_ptr = nullptr; // pointer to mapped index buffer
VkDeviceSize index_buffer_offset = 0;
+ VkSampler sampler = VK_NULL_HANDLE;
+
VkPipeline skybox_pipeline = VK_NULL_HANDLE;
+
+ VkSemaphore image_acquired = VK_NULL_HANDLE;
+ uint32_t swapchain_image_index = -1;
+
+ VkSemaphore rendering_finished = VK_NULL_HANDLE;
+ VkFence rendering_finished_fence = VK_NULL_HANDLE;
};
struct Vulkan_Resources {
diff --git a/src/engine/renderer/vk_demo.cpp b/src/engine/renderer/vk_demo.cpp
deleted file mode 100644
index 2028573..0000000
--- a/src/engine/renderer/vk_demo.cpp
+++ /dev/null
@@ -1,109 +0,0 @@
-#include "vk_allocator.h"
-#include "vk_resource_manager.h"
-#include "vk_demo.h"
-#include "vk.h"
-#include "vk_utils.h"
-
-#include "stb_image.h"
-
-#include
-#include
-#include
-#include
-#include
-
-#include "tr_local.h"
-
-FILE* vk_log_file;
-
-Vulkan_Demo::Vulkan_Demo(int window_width, int window_height)
-: window_width(window_width)
-, window_height(window_height)
-{
- vk_log_file = fopen("vk_dev.log", "w");
-
- image_acquired = get_resource_manager()->create_semaphore();
- rendering_finished = get_resource_manager()->create_semaphore();
-
- VkFenceCreateInfo fence_desc;
- fence_desc.sType = VK_STRUCTURE_TYPE_FENCE_CREATE_INFO;
- fence_desc.pNext = nullptr;
- fence_desc.flags = VK_FENCE_CREATE_SIGNALED_BIT;
- VkResult result = vkCreateFence(vk.device, &fence_desc, nullptr, &rendering_finished_fence);
- check_vk_result(result, "vkCreateFence");
-
- create_texture_sampler();
-}
-
-VkImage Vulkan_Demo::create_texture(const uint8_t* pixels, int bytes_per_pixel, int image_width, int image_height, VkImageView& image_view) {
- VkImage staging_image = create_staging_texture(image_width, image_height,
- bytes_per_pixel == 3 ? VK_FORMAT_R8G8B8_UNORM : VK_FORMAT_R8G8B8A8_UNORM, pixels, bytes_per_pixel);
-
- Defer_Action destroy_staging_image([this, &staging_image]() {
- vkDestroyImage(vk.device, staging_image, nullptr);
- });
-
- VkImage texture_image = ::create_texture(image_width, image_height,
- bytes_per_pixel == 3 ? VK_FORMAT_R8G8B8_UNORM : VK_FORMAT_R8G8B8A8_UNORM);
-
- record_and_run_commands(vk.command_pool, vk.queue,
- [&texture_image, &staging_image, &image_width, &image_height, this](VkCommandBuffer command_buffer) {
-
- record_image_layout_transition(command_buffer, staging_image, VK_FORMAT_R8G8B8A8_UNORM,
- VK_ACCESS_HOST_WRITE_BIT, VK_IMAGE_LAYOUT_PREINITIALIZED, VK_ACCESS_TRANSFER_READ_BIT, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL);
-
- record_image_layout_transition(command_buffer, texture_image, VK_FORMAT_R8G8B8A8_UNORM,
- 0, VK_IMAGE_LAYOUT_UNDEFINED, VK_ACCESS_TRANSFER_WRITE_BIT, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL);
-
- // copy staging image's data to device local image
- VkImageSubresourceLayers subresource_layers;
- subresource_layers.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT;
- subresource_layers.mipLevel = 0;
- subresource_layers.baseArrayLayer = 0;
- subresource_layers.layerCount = 1;
-
- VkImageCopy region;
- region.srcSubresource = subresource_layers;
- region.srcOffset = {0, 0, 0};
- region.dstSubresource = subresource_layers;
- region.dstOffset = {0, 0, 0};
- region.extent.width = image_width;
- region.extent.height = image_height;
- region.extent.depth = 1;
-
- vkCmdCopyImage(command_buffer,
- staging_image, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL,
- texture_image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL,
- 1, ®ion);
-
- record_image_layout_transition(command_buffer, texture_image, VK_FORMAT_R8G8B8A8_UNORM,
- VK_ACCESS_TRANSFER_WRITE_BIT, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_ACCESS_SHADER_READ_BIT, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL);
- });
-
- image_view = create_image_view(texture_image, VK_FORMAT_R8G8B8A8_UNORM, VK_IMAGE_ASPECT_COLOR_BIT);
- return texture_image;
-}
-
-void Vulkan_Demo::create_texture_sampler() {
- VkSamplerCreateInfo desc;
- desc.sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO;
- desc.pNext = nullptr;
- desc.flags = 0;
- desc.magFilter = VK_FILTER_LINEAR;
- desc.minFilter = VK_FILTER_LINEAR;
- desc.mipmapMode = VK_SAMPLER_MIPMAP_MODE_NEAREST;
- desc.addressModeU = VK_SAMPLER_ADDRESS_MODE_REPEAT;
- desc.addressModeV = VK_SAMPLER_ADDRESS_MODE_REPEAT;
- desc.addressModeW = VK_SAMPLER_ADDRESS_MODE_REPEAT;
- desc.mipLodBias = 0.0f;
- desc.anisotropyEnable = VK_TRUE;
- desc.maxAnisotropy = 1;
- desc.compareEnable = VK_FALSE;
- desc.compareOp = VK_COMPARE_OP_ALWAYS;
- desc.minLod = 0.0f;
- desc.maxLod = 0.0f;
- desc.borderColor = VK_BORDER_COLOR_INT_OPAQUE_BLACK;
- desc.unnormalizedCoordinates = VK_FALSE;
-
- texture_image_sampler = get_resource_manager()->create_sampler(desc);
-}
diff --git a/src/engine/renderer/vk_demo.h b/src/engine/renderer/vk_demo.h
deleted file mode 100644
index 87064eb..0000000
--- a/src/engine/renderer/vk_demo.h
+++ /dev/null
@@ -1,30 +0,0 @@
-#pragma once
-
-#include
-#include