render/vk: Implement buffer_pass_options.clear_buffer

This commit is contained in:
Julia Tatz 2023-12-14 20:35:55 -05:00
parent 4ba290a7a9
commit be23ce9683
3 changed files with 31 additions and 19 deletions

View file

@ -193,6 +193,7 @@ struct wlr_vk_render_format_setup {
struct wl_list link; // wlr_vk_renderer.render_format_setups struct wl_list link; // wlr_vk_renderer.render_format_setups
const struct wlr_vk_format *render_format; // used in renderpass const struct wlr_vk_format *render_format; // used in renderpass
bool has_blending_buffer; bool has_blending_buffer;
bool clear_on_load;
VkRenderPass render_pass; VkRenderPass render_pass;
VkPipeline output_pipe; VkPipeline output_pipe;
@ -311,7 +312,7 @@ struct wlr_vk_texture_view {
struct wlr_vk_render_format_setup *find_or_create_render_setup( struct wlr_vk_render_format_setup *find_or_create_render_setup(
struct wlr_vk_renderer *renderer, const struct wlr_vk_format *format, struct wlr_vk_renderer *renderer, const struct wlr_vk_format *format,
bool has_blending_buffer); bool has_blending_buffer, bool clear_on_load);
struct wlr_vk_pipeline *setup_get_or_create_pipeline( struct wlr_vk_pipeline *setup_get_or_create_pipeline(
struct wlr_vk_render_format_setup *setup, struct wlr_vk_render_format_setup *setup,
const struct wlr_vk_pipeline_key *key); const struct wlr_vk_pipeline_key *key);
@ -350,7 +351,7 @@ struct wlr_vk_render_pass {
}; };
struct wlr_vk_render_pass *vulkan_begin_render_pass(struct wlr_vk_renderer *renderer, struct wlr_vk_render_pass *vulkan_begin_render_pass(struct wlr_vk_renderer *renderer,
struct wlr_vk_render_buffer *buffer); struct wlr_vk_render_buffer *buffer, const struct wlr_render_color *clear_color);
// Suballocates a buffer span with the given size that can be mapped // Suballocates a buffer span with the given size that can be mapped
// and used as staging buffer. The allocation is implicitly released when the // and used as staging buffer. The allocation is implicitly released when the

View file

@ -650,7 +650,7 @@ static const struct wlr_render_pass_impl render_pass_impl = {
}; };
struct wlr_vk_render_pass *vulkan_begin_render_pass(struct wlr_vk_renderer *renderer, struct wlr_vk_render_pass *vulkan_begin_render_pass(struct wlr_vk_renderer *renderer,
struct wlr_vk_render_buffer *buffer) { struct wlr_vk_render_buffer *buffer, const struct wlr_render_color *clear_color) {
struct wlr_vk_render_pass *pass = calloc(1, sizeof(*pass)); struct wlr_vk_render_pass *pass = calloc(1, sizeof(*pass));
if (pass == NULL) { if (pass == NULL) {
return NULL; return NULL;
@ -662,7 +662,7 @@ struct wlr_vk_render_pass *vulkan_begin_render_pass(struct wlr_vk_renderer *rend
bool has_blending_buffer = buffer->blend_image != VK_NULL_HANDLE; bool has_blending_buffer = buffer->blend_image != VK_NULL_HANDLE;
struct wlr_vk_render_format_setup *render_setup = find_or_create_render_setup( struct wlr_vk_render_format_setup *render_setup = find_or_create_render_setup(
renderer, buffer->fmt, has_blending_buffer); renderer, buffer->fmt, has_blending_buffer, clear_color != NULL);
if (render_setup == NULL) { if (render_setup == NULL) {
free(pass); free(pass);
return NULL; return NULL;
@ -697,6 +697,17 @@ struct wlr_vk_render_pass *vulkan_begin_render_pass(struct wlr_vk_renderer *rend
VkRect2D rect = { .extent = { width, height } }; VkRect2D rect = { .extent = { width, height } };
VkImageView attachments[2] = {0}; VkImageView attachments[2] = {0};
uint32_t attachment_count = 0; uint32_t attachment_count = 0;
VkClearValue clear_values[2] = { 0 };
if (clear_color) {
clear_values[0] = clear_values[1] = (VkClearValue){
.color.float32 = {
color_to_linear(clear_color->r),
color_to_linear(clear_color->g),
color_to_linear(clear_color->b),
clear_color->a,
}
};
}
if (buffer->blend_image_view != VK_NULL_HANDLE) { if (buffer->blend_image_view != VK_NULL_HANDLE) {
attachments[attachment_count++] = buffer->blend_image_view; attachments[attachment_count++] = buffer->blend_image_view;
@ -714,7 +725,8 @@ struct wlr_vk_render_pass *vulkan_begin_render_pass(struct wlr_vk_renderer *rend
.renderArea = rect, .renderArea = rect,
.renderPass = render_setup->render_pass, .renderPass = render_setup->render_pass,
.framebuffer = framebuffer->vk, .framebuffer = framebuffer->vk,
.clearValueCount = 0, .clearValueCount = clear_color ? attachment_count : 0,
.pClearValues = clear_values,
}; };
vkCmdBeginRenderPass(cb->vk, &rp_info, VK_SUBPASS_CONTENTS_INLINE); vkCmdBeginRenderPass(cb->vk, &rp_info, VK_SUBPASS_CONTENTS_INLINE);

View file

@ -1287,18 +1287,15 @@ static struct wlr_render_pass *vulkan_begin_buffer_pass(struct wlr_renderer *wlr
} }
} }
struct wlr_vk_render_pass *render_pass = vulkan_begin_render_pass(renderer, render_buffer); const struct wlr_render_color *clear_color = NULL;
if (options->clear_buffer) {
clear_color = &options->clear_color;
}
struct wlr_vk_render_pass *render_pass = vulkan_begin_render_pass(renderer, render_buffer, clear_color);
if (render_pass == NULL) { if (render_pass == NULL) {
return NULL; return NULL;
} }
// TODO: switch to using `VkRenderPassBeginInfo.pClearValues`
if (options->clear_buffer) {
wlr_render_pass_add_rect(&render_pass->base, &(struct wlr_render_rect_options){
.box = { .width = buffer->width, .height = buffer->height },
.color = options->clear_color,
.blend_mode = WLR_RENDER_BLEND_MODE_NONE,
});
}
return &render_pass->base; return &render_pass->base;
} }
@ -1869,10 +1866,10 @@ static bool init_static_render_data(struct wlr_vk_renderer *renderer) {
struct wlr_vk_render_format_setup *find_or_create_render_setup( struct wlr_vk_render_format_setup *find_or_create_render_setup(
struct wlr_vk_renderer *renderer, const struct wlr_vk_format *format, struct wlr_vk_renderer *renderer, const struct wlr_vk_format *format,
bool has_blending_buffer) { bool has_blending_buffer, bool clear_on_load) {
struct wlr_vk_render_format_setup *setup; struct wlr_vk_render_format_setup *setup;
wl_list_for_each(setup, &renderer->render_format_setups, link) { wl_list_for_each(setup, &renderer->render_format_setups, link) {
if (setup->render_format == format && setup->has_blending_buffer == has_blending_buffer) { if (setup->render_format == format && setup->has_blending_buffer == has_blending_buffer && setup->clear_on_load == clear_on_load) {
return setup; return setup;
} }
} }
@ -1885,19 +1882,21 @@ struct wlr_vk_render_format_setup *find_or_create_render_setup(
setup->render_format = format; setup->render_format = format;
setup->has_blending_buffer = has_blending_buffer; setup->has_blending_buffer = has_blending_buffer;
setup->clear_on_load = clear_on_load;
setup->renderer = renderer; setup->renderer = renderer;
wl_list_init(&setup->pipelines); wl_list_init(&setup->pipelines);
wl_list_init(&setup->framebuffers); wl_list_init(&setup->framebuffers);
VkDevice dev = renderer->dev->dev; VkDevice dev = renderer->dev->dev;
VkResult res; VkResult res;
VkAttachmentLoadOp load_op = clear_on_load ? VK_ATTACHMENT_LOAD_OP_CLEAR : VK_ATTACHMENT_LOAD_OP_LOAD;
if (has_blending_buffer) { if (has_blending_buffer) {
VkAttachmentDescription attachments[2] = { VkAttachmentDescription attachments[2] = {
{ {
.format = VK_FORMAT_R16G16B16A16_SFLOAT, .format = VK_FORMAT_R16G16B16A16_SFLOAT,
.samples = VK_SAMPLE_COUNT_1_BIT, .samples = VK_SAMPLE_COUNT_1_BIT,
.loadOp = VK_ATTACHMENT_LOAD_OP_LOAD, .loadOp = load_op,
.storeOp = VK_ATTACHMENT_STORE_OP_STORE, .storeOp = VK_ATTACHMENT_STORE_OP_STORE,
.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE, .stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
.stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE, .stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
@ -1907,7 +1906,7 @@ struct wlr_vk_render_format_setup *find_or_create_render_setup(
{ {
.format = format->vk, .format = format->vk,
.samples = VK_SAMPLE_COUNT_1_BIT, .samples = VK_SAMPLE_COUNT_1_BIT,
.loadOp = VK_ATTACHMENT_LOAD_OP_LOAD, .loadOp = load_op,
.storeOp = VK_ATTACHMENT_STORE_OP_STORE, .storeOp = VK_ATTACHMENT_STORE_OP_STORE,
.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE, .stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
.stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE, .stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
@ -2013,7 +2012,7 @@ struct wlr_vk_render_format_setup *find_or_create_render_setup(
VkAttachmentDescription attachment = { VkAttachmentDescription attachment = {
.format = format->vk_srgb, .format = format->vk_srgb,
.samples = VK_SAMPLE_COUNT_1_BIT, .samples = VK_SAMPLE_COUNT_1_BIT,
.loadOp = VK_ATTACHMENT_LOAD_OP_LOAD, .loadOp = load_op,
.storeOp = VK_ATTACHMENT_STORE_OP_STORE, .storeOp = VK_ATTACHMENT_STORE_OP_STORE,
.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE, .stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
.stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE, .stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,