aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorladevieq <qladevie@wanadev.fr>2021-02-10 14:00:37 +0100
committerladevieq <qladevie@wanadev.fr>2021-02-10 14:00:37 +0100
commit5e39b7485d08345a4eb3686b344840791888d1f9 (patch)
tree0d2a51845709a5ecd25fecedd60cc65b2999c61e
parent3a43bab624f271588401daca46c512a1f85593f6 (diff)
Accumulation working
-rw-r--r--include/utils.hpp4
-rw-r--r--include/vk-renderer.hpp2
-rw-r--r--shaders/compute.comp22
-rw-r--r--src/main.cpp14
-rw-r--r--src/utils.cpp7
-rw-r--r--src/vk-api.cpp2
-rw-r--r--src/vk-renderer.cpp23
7 files changed, 50 insertions, 24 deletions
diff --git a/include/utils.hpp b/include/utils.hpp
index 830b006..85b50cf 100644
--- a/include/utils.hpp
+++ b/include/utils.hpp
@@ -27,11 +27,13 @@ struct input_data {
// Output image resolution
uint32_t width;
uint32_t height;
+
+ uint32_t sample_index;
};
std::vector<uint8_t> get_shader_code(const char* path);
-struct input_data create_inputs(uint32_t width, uint32_t height);
+struct input_data create_inputs(uint32_t width, uint32_t height, uint32_t samples_per_pixel);
#define PI 3.14159265359
diff --git a/include/vk-renderer.hpp b/include/vk-renderer.hpp
index 1180d0a..318e6cc 100644
--- a/include/vk-renderer.hpp
+++ b/include/vk-renderer.hpp
@@ -15,7 +15,7 @@ class vkrenderer {
~vkrenderer();
- void compute(uint32_t width, uint32_t height);
+ void compute(uint32_t width, uint32_t height, bool clear);
void recreate_swapchain();
diff --git a/shaders/compute.comp b/shaders/compute.comp
index 1e903b0..01a0f71 100644
--- a/shaders/compute.comp
+++ b/shaders/compute.comp
@@ -62,9 +62,12 @@ layout(set = 0, binding = 0) buffer Inputs {
uint samples_per_pixel;
uint width;
uint height;
+
+ uint sample_index;
+ uint[3] padding;
};
-layout(set = 0, binding = 1, rgba8) uniform writeonly image2D output_image;
+layout(set = 0, binding = 1, rgba8) uniform image2D output_image;
vec3 at(ray r, float t) {
return r.origin + r.direction * t;
@@ -214,16 +217,15 @@ void main() {
vec4 out_color = vec4(0.0);
- for (uint sample_index = 0; sample_index < samples_per_pixel; sample_index++) {
- vec2 jittered_uvs = uv + vec2(random_disk[sample_index].x / (width - 1), random_disk[sample_index].y / (height - 1));
- vec2 lens_disk = random_disk[sample_index] * cam.lens_radius;
- vec3 offset = lens_disk.x * cam.right.xyz + lens_disk.y * cam.up.xyz;
- vec4 proj_plane_pos = cam.first_pixel + jittered_uvs.x * cam.horizontal + jittered_uvs.y * cam.vertical;
- ray r = ray(cam.position.xyz + offset, proj_plane_pos.xyz - cam.position.xyz - offset);
+ vec2 jittered_uvs = uv + vec2(random_disk[sample_index].x / (width - 1), random_disk[sample_index].y / (height - 1));
+ vec2 lens_disk = random_disk[sample_index] * cam.lens_radius;
+ vec3 offset = lens_disk.x * cam.right.xyz + lens_disk.y * cam.up.xyz;
+ vec4 proj_plane_pos = cam.first_pixel + jittered_uvs.x * cam.horizontal + jittered_uvs.y * cam.vertical;
+ ray r = ray(cam.position.xyz + offset, proj_plane_pos.xyz - cam.position.xyz - offset);
- out_color += ray_color(r, sample_index);
- }
+ out_color += ray_color(r, sample_index);
float spp_scale = (1.0 / samples_per_pixel);
- imageStore(output_image, ivec2(x, y), sqrt(out_color * spp_scale));
+ vec4 acc_color = imageLoad(output_image, ivec2(x, y));
+ imageStore(output_image, ivec2(x, y), acc_color + (out_color * spp_scale));
}
diff --git a/src/main.cpp b/src/main.cpp
index 37ebddb..c87e57a 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -46,13 +46,14 @@ int main() {
const float aspect_ratio = 16.0 / 9.0;
uint32_t width = 400;
uint32_t height = width / aspect_ratio;
+ const uint32_t samples_per_pixel = 10;
window wnd { width , height };
float delta_time = 0.f;
auto start = std::chrono::high_resolution_clock::now();
auto end = std::chrono::high_resolution_clock::now();
- auto inputs = create_inputs(width, height);
+ auto inputs = create_inputs(width, height, samples_per_pixel);
auto canRender = true;
vkrenderer renderer { wnd, inputs };
@@ -113,6 +114,10 @@ int main() {
((input_data*) renderer.compute_shader_buffer.mapped_ptr)->cam.move(move_vec);
+ if (!move_vec.near_zero()) {
+ ((input_data*) renderer.compute_shader_buffer.mapped_ptr)->sample_index = 0;
+ }
+
break;
}
default:
@@ -129,7 +134,12 @@ int main() {
if(rdoc_api) rdoc_api->StartFrameCapture(NULL, NULL);
if (canRender) {
- renderer.compute(width, height);
+ if (((input_data*) renderer.compute_shader_buffer.mapped_ptr)->sample_index < samples_per_pixel) {
+ bool clear = ((input_data*) renderer.compute_shader_buffer.mapped_ptr)->sample_index == 0;
+ renderer.compute(width, height, clear);
+
+ ((input_data*) renderer.compute_shader_buffer.mapped_ptr)->sample_index++;
+ }
}
// stop the capture
diff --git a/src/utils.cpp b/src/utils.cpp
index 00745dc..a2cf8f9 100644
--- a/src/utils.cpp
+++ b/src/utils.cpp
@@ -89,11 +89,10 @@ void random_scene(sphere *world) {
world[world_sphere_index + 2] = { { 4, 1, 0 }, material3, 1.0 };
}
-struct input_data create_inputs(uint32_t width, uint32_t height) {
+struct input_data create_inputs(uint32_t width, uint32_t height, uint32_t samples_per_pixel) {
// Image dimensions
const float aspect_ratio = (float)width / (float) height;
- const uint32_t samples_per_pixel = 10;
const uint32_t max_depth = 5;
const vec3 camera_position{ 13.0, 2.0, 3.0 };
@@ -113,7 +112,9 @@ struct input_data create_inputs(uint32_t width, uint32_t height) {
.max_bounce = max_depth,
.samples_per_pixel = samples_per_pixel,
.width = width,
- .height = height
+ .height = height,
+
+ .sample_index = 0,
};
// Random numbers pools
diff --git a/src/vk-api.cpp b/src/vk-api.cpp
index 2ecd06f..92e9a80 100644
--- a/src/vk-api.cpp
+++ b/src/vk-api.cpp
@@ -123,7 +123,7 @@ Image vkapi::create_image(VkExtent3D size, VkFormat format, VkImageUsageFlags us
return std::move(image);
}
void vkapi::destroy_image(Image &image) {
- vkDestroyImage(context.device, image.handle, nullptr);
+ vmaDestroyImage(context.allocator, image.handle, image.alloc);
vkDestroyImageView(context.device, image.view, nullptr);
}
diff --git a/src/vk-renderer.cpp b/src/vk-renderer.cpp
index 2054ae3..32bee48 100644
--- a/src/vk-renderer.cpp
+++ b/src/vk-renderer.cpp
@@ -50,7 +50,7 @@ vkrenderer::vkrenderer(window& wnd, const input_data& inputs) {
.height = swapchain.extent.height,
.depth = 1,
};
- accumulation_image = api.create_image(image_size, swapchain.surface_format.format, VK_IMAGE_USAGE_STORAGE_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT);
+ accumulation_image = api.create_image(image_size, swapchain.surface_format.format, VK_IMAGE_USAGE_STORAGE_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT);
submission_fences = api.create_fences(swapchain.image_count);
execution_semaphores = api.create_semaphores(swapchain.image_count);
@@ -74,6 +74,7 @@ vkrenderer::~vkrenderer() {
api.destroy_semaphores(acquire_semaphores);
api.destroy_descriptor_sets(compute_shader_sets);
+ api.destroy_image(accumulation_image);
api.destroy_command_buffers(command_buffers);
api.destroy_compute_pipeline(compute_pipeline);
@@ -82,7 +83,8 @@ vkrenderer::~vkrenderer() {
api.destroy_surface(platform_surface);
}
-void vkrenderer::compute(uint32_t width, uint32_t height) {
+
+void vkrenderer::compute(uint32_t width, uint32_t height, bool clear) {
VKRESULT(vkWaitForFences(api.context.device, 1, &submission_fences[frame_index], VK_TRUE, UINT64_MAX))
VKRESULT(vkResetFences(api.context.device, 1, &submission_fences[frame_index]))
@@ -94,16 +96,25 @@ void vkrenderer::compute(uint32_t width, uint32_t height) {
api.start_record(cmd_buf);
- api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_GENERAL, VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, 0, VK_ACCESS_SHADER_WRITE_BIT, accumulation_image);
+ if (clear) {
+ api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0, VK_ACCESS_TRANSFER_WRITE_BIT, accumulation_image);
+
+ VkClearColorValue color = { 0.f, 0.f, 0.f, 1.f };
+ vkCmdClearColorImage(cmd_buf, accumulation_image.handle, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &color, 1, &accumulation_image.subresource_range);
+
+ api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_IMAGE_LAYOUT_GENERAL, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, VK_ACCESS_TRANSFER_WRITE_BIT, VK_ACCESS_SHADER_WRITE_BIT, accumulation_image);
+ } else {
+ api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_GENERAL, VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, 0, VK_ACCESS_SHADER_WRITE_BIT, accumulation_image);
+ }
api.run_compute_pipeline(cmd_buf, compute_pipeline, compute_shader_sets[swapchain_image_index], width / 8, height / 8, 1);
- api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_GENERAL, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_ACCESS_SHADER_WRITE_BIT, VK_ACCESS_COLOR_ATTACHMENT_READ_BIT, accumulation_image);
+ api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_GENERAL, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_ACCESS_SHADER_WRITE_BIT, VK_ACCESS_TRANSFER_READ_BIT, accumulation_image);
- api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0, VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, swapchain.images[swapchain_image_index]);
+ api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_UNDEFINED, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0, VK_ACCESS_TRANSFER_WRITE_BIT, swapchain.images[swapchain_image_index]);
api.blit_full(cmd_buf, accumulation_image, swapchain.images[swapchain_image_index]);
- api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, VK_ACCESS_COLOR_ATTACHMENT_READ_BIT, swapchain.images[swapchain_image_index]);
+ api.image_barrier(cmd_buf, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_IMAGE_LAYOUT_PRESENT_SRC_KHR, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_ACCESS_TRANSFER_WRITE_BIT, VK_ACCESS_COLOR_ATTACHMENT_READ_BIT, swapchain.images[swapchain_image_index]);
api.end_record(cmd_buf);