Merge pull request #37808 from reduz/port-effects-to-compute
Moved most of the effect code to compute.
This commit is contained in:
commit
9dc19f7619
|
@ -1568,17 +1568,22 @@ RID RenderingDeviceVulkan::texture_create(const TextureFormat &p_format, const T
|
|||
#ifndef _MSC_VER
|
||||
#warning TODO check for support via RenderingDevice to enable on mobile when possible
|
||||
#endif
|
||||
// vkCreateImage fails with format list on Android (VK_ERROR_OUT_OF_HOST_MEMORY)
|
||||
|
||||
#ifndef ANDROID_ENABLED
|
||||
|
||||
// vkCreateImage fails with format list on Android (VK_ERROR_OUT_OF_HOST_MEMORY)
|
||||
VkImageFormatListCreateInfoKHR format_list_create_info; //keep out of the if, needed for creation
|
||||
Vector<VkFormat> allowed_formats; //keep out of the if, needed for creation
|
||||
#endif
|
||||
if (p_format.shareable_formats.size()) {
|
||||
image_create_info.flags |= VK_IMAGE_CREATE_MUTABLE_FORMAT_BIT;
|
||||
|
||||
Vector<VkFormat> allowed_formats;
|
||||
#ifndef ANDROID_ENABLED
|
||||
|
||||
for (int i = 0; i < p_format.shareable_formats.size(); i++) {
|
||||
allowed_formats.push_back(vulkan_formats[p_format.shareable_formats[i]]);
|
||||
}
|
||||
|
||||
VkImageFormatListCreateInfoKHR format_list_create_info;
|
||||
format_list_create_info.sType = VK_STRUCTURE_TYPE_IMAGE_FORMAT_LIST_CREATE_INFO_KHR;
|
||||
format_list_create_info.pNext = nullptr;
|
||||
format_list_create_info.viewFormatCount = allowed_formats.size();
|
||||
|
@ -1589,8 +1594,9 @@ RID RenderingDeviceVulkan::texture_create(const TextureFormat &p_format, const T
|
|||
"If supplied a list of shareable formats, the current format must be present in the list");
|
||||
ERR_FAIL_COND_V_MSG(p_view.format_override != DATA_FORMAT_MAX && p_format.shareable_formats.find(p_view.format_override) == -1, RID(),
|
||||
"If supplied a list of shareable formats, the current view format override must be present in the list");
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (p_format.type == TEXTURE_TYPE_CUBE || p_format.type == TEXTURE_TYPE_CUBE_ARRAY) {
|
||||
image_create_info.flags |= VK_IMAGE_CREATE_CUBE_COMPATIBLE_BIT;
|
||||
}
|
||||
|
@ -1766,6 +1772,8 @@ RID RenderingDeviceVulkan::texture_create(const TextureFormat &p_format, const T
|
|||
texture.depth = image_create_info.extent.depth;
|
||||
texture.layers = image_create_info.arrayLayers;
|
||||
texture.mipmaps = image_create_info.mipLevels;
|
||||
texture.base_mipmap = 0;
|
||||
texture.base_layer = 0;
|
||||
texture.usage_flags = p_format.usage_bits;
|
||||
texture.samples = p_format.samples;
|
||||
texture.allowed_shared_formats = p_format.shareable_formats;
|
||||
|
@ -2006,6 +2014,8 @@ RID RenderingDeviceVulkan::texture_create_shared_from_slice(const TextureView &p
|
|||
get_image_format_required_size(texture.format, texture.width, texture.height, texture.depth, p_mipmap + 1, &texture.width, &texture.height);
|
||||
texture.mipmaps = 1;
|
||||
texture.layers = p_slice_type == TEXTURE_SLICE_CUBEMAP ? 6 : 1;
|
||||
texture.base_mipmap = p_mipmap;
|
||||
texture.base_layer = p_layer;
|
||||
|
||||
VkImageViewCreateInfo image_view_create_info;
|
||||
image_view_create_info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO;
|
||||
|
@ -2688,8 +2698,8 @@ Error RenderingDeviceVulkan::texture_clear(RID p_texture, const Color &p_color,
|
|||
src_layer_count *= 6;
|
||||
}
|
||||
|
||||
ERR_FAIL_COND_V(p_base_mipmap + p_mipmaps > src_tex->mipmaps, ERR_INVALID_PARAMETER);
|
||||
ERR_FAIL_COND_V(p_base_layer + p_layers > src_layer_count, ERR_INVALID_PARAMETER);
|
||||
ERR_FAIL_COND_V(src_tex->base_mipmap + p_base_mipmap + p_mipmaps > src_tex->mipmaps, ERR_INVALID_PARAMETER);
|
||||
ERR_FAIL_COND_V(src_tex->base_layer + p_base_layer + p_layers > src_layer_count, ERR_INVALID_PARAMETER);
|
||||
|
||||
VkCommandBuffer command_buffer = p_sync_with_draw ? frames[frame].draw_command_buffer : frames[frame].setup_command_buffer;
|
||||
|
||||
|
@ -2708,9 +2718,9 @@ Error RenderingDeviceVulkan::texture_clear(RID p_texture, const Color &p_color,
|
|||
image_memory_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
image_memory_barrier.image = src_tex->image;
|
||||
image_memory_barrier.subresourceRange.aspectMask = src_tex->read_aspect_mask;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = p_base_mipmap;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = src_tex->base_mipmap + p_base_mipmap;
|
||||
image_memory_barrier.subresourceRange.levelCount = p_mipmaps;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = p_base_layer;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = src_tex->base_layer + p_base_layer;
|
||||
image_memory_barrier.subresourceRange.layerCount = p_layers;
|
||||
|
||||
layout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL;
|
||||
|
@ -2746,9 +2756,9 @@ Error RenderingDeviceVulkan::texture_clear(RID p_texture, const Color &p_color,
|
|||
image_memory_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
image_memory_barrier.image = src_tex->image;
|
||||
image_memory_barrier.subresourceRange.aspectMask = src_tex->read_aspect_mask;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = p_base_mipmap;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = src_tex->base_mipmap + p_base_mipmap;
|
||||
image_memory_barrier.subresourceRange.levelCount = p_mipmaps;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = p_base_layer;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = src_tex->base_layer + p_base_layer;
|
||||
image_memory_barrier.subresourceRange.layerCount = p_layers;
|
||||
|
||||
vkCmdPipelineBarrier(command_buffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_VERTEX_SHADER_BIT | VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, 0, 0, nullptr, 0, nullptr, 1, &image_memory_barrier);
|
||||
|
@ -2846,6 +2856,21 @@ VkRenderPass RenderingDeviceVulkan::_render_pass_create(const Vector<AttachmentF
|
|||
description.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; //don't care what is there
|
||||
}
|
||||
} break;
|
||||
case INITIAL_ACTION_DROP: {
|
||||
if (p_format[i].usage_flags & TEXTURE_USAGE_COLOR_ATTACHMENT_BIT) {
|
||||
description.loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
|
||||
description.initialLayout = is_sampled ? VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL : (is_storage ? VK_IMAGE_LAYOUT_GENERAL : VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL);
|
||||
description.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
|
||||
} else if (p_format[i].usage_flags & TEXTURE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT) {
|
||||
description.loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
|
||||
description.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; //don't care what is there
|
||||
description.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
|
||||
} else {
|
||||
description.loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
|
||||
description.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
|
||||
description.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; //don't care what is there
|
||||
}
|
||||
} break;
|
||||
case INITIAL_ACTION_CONTINUE: {
|
||||
if (p_format[i].usage_flags & TEXTURE_USAGE_COLOR_ATTACHMENT_BIT) {
|
||||
description.loadOp = VK_ATTACHMENT_LOAD_OP_LOAD;
|
||||
|
@ -4325,6 +4350,10 @@ RID RenderingDeviceVulkan::uniform_set_create(const Vector<Uniform> &p_uniforms,
|
|||
attachable_textures.push_back(texture->owner.is_valid() ? texture->owner : uniform.ids[j + 1]);
|
||||
}
|
||||
|
||||
if (texture->usage_flags & TEXTURE_USAGE_STORAGE_BIT) {
|
||||
//can also be used as storage, add to mutable sampled
|
||||
mutable_sampled_textures.push_back(texture);
|
||||
}
|
||||
if (texture->owner.is_valid()) {
|
||||
texture = texture_owner.getornull(texture->owner);
|
||||
ERR_FAIL_COND_V(!texture, RID()); //bug, should never happen
|
||||
|
@ -4333,11 +4362,6 @@ RID RenderingDeviceVulkan::uniform_set_create(const Vector<Uniform> &p_uniforms,
|
|||
img_info.imageLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
||||
|
||||
image_info.push_back(img_info);
|
||||
|
||||
if (texture->usage_flags & TEXTURE_USAGE_STORAGE_BIT) {
|
||||
//can also be used as storage, add to mutable sampled
|
||||
mutable_sampled_textures.push_back(texture);
|
||||
}
|
||||
}
|
||||
|
||||
write.dstArrayElement = 0;
|
||||
|
@ -4377,6 +4401,11 @@ RID RenderingDeviceVulkan::uniform_set_create(const Vector<Uniform> &p_uniforms,
|
|||
attachable_textures.push_back(texture->owner.is_valid() ? texture->owner : uniform.ids[j]);
|
||||
}
|
||||
|
||||
if (texture->usage_flags & TEXTURE_USAGE_STORAGE_BIT) {
|
||||
//can also be used as storage, add to mutable sampled
|
||||
mutable_sampled_textures.push_back(texture);
|
||||
}
|
||||
|
||||
if (texture->owner.is_valid()) {
|
||||
texture = texture_owner.getornull(texture->owner);
|
||||
ERR_FAIL_COND_V(!texture, RID()); //bug, should never happen
|
||||
|
@ -4385,11 +4414,6 @@ RID RenderingDeviceVulkan::uniform_set_create(const Vector<Uniform> &p_uniforms,
|
|||
img_info.imageLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
|
||||
|
||||
image_info.push_back(img_info);
|
||||
|
||||
if (texture->usage_flags & TEXTURE_USAGE_STORAGE_BIT) {
|
||||
//can also be used as storage, add to mutable sampled
|
||||
mutable_sampled_textures.push_back(texture);
|
||||
}
|
||||
}
|
||||
|
||||
write.dstArrayElement = 0;
|
||||
|
@ -4426,6 +4450,11 @@ RID RenderingDeviceVulkan::uniform_set_create(const Vector<Uniform> &p_uniforms,
|
|||
img_info.sampler = VK_NULL_HANDLE;
|
||||
img_info.imageView = texture->view;
|
||||
|
||||
if (texture->usage_flags & TEXTURE_USAGE_SAMPLING_BIT) {
|
||||
//can also be used as storage, add to mutable sampled
|
||||
mutable_storage_textures.push_back(texture);
|
||||
}
|
||||
|
||||
if (texture->owner.is_valid()) {
|
||||
texture = texture_owner.getornull(texture->owner);
|
||||
ERR_FAIL_COND_V(!texture, RID()); //bug, should never happen
|
||||
|
@ -4434,11 +4463,6 @@ RID RenderingDeviceVulkan::uniform_set_create(const Vector<Uniform> &p_uniforms,
|
|||
img_info.imageLayout = VK_IMAGE_LAYOUT_GENERAL;
|
||||
|
||||
image_info.push_back(img_info);
|
||||
|
||||
if (texture->usage_flags & TEXTURE_USAGE_SAMPLING_BIT) {
|
||||
//can also be used as storage, add to mutable sampled
|
||||
mutable_storage_textures.push_back(texture);
|
||||
}
|
||||
}
|
||||
|
||||
write.dstArrayElement = 0;
|
||||
|
@ -6206,9 +6230,9 @@ void RenderingDeviceVulkan::compute_list_bind_uniform_set(ComputeListID p_list,
|
|||
image_memory_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
image_memory_barrier.image = textures_to_sampled[i]->image;
|
||||
image_memory_barrier.subresourceRange.aspectMask = textures_to_sampled[i]->read_aspect_mask;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = 0;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = textures_to_sampled[i]->base_mipmap;
|
||||
image_memory_barrier.subresourceRange.levelCount = textures_to_sampled[i]->mipmaps;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = 0;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = textures_to_sampled[i]->base_layer;
|
||||
image_memory_barrier.subresourceRange.layerCount = textures_to_sampled[i]->layers;
|
||||
|
||||
vkCmdPipelineBarrier(cl->command_buffer, VK_PIPELINE_STAGE_VERTEX_SHADER_BIT | VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, 0, 0, nullptr, 0, nullptr, 1, &image_memory_barrier);
|
||||
|
@ -6237,9 +6261,9 @@ void RenderingDeviceVulkan::compute_list_bind_uniform_set(ComputeListID p_list,
|
|||
image_memory_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
image_memory_barrier.image = textures_to_storage[i]->image;
|
||||
image_memory_barrier.subresourceRange.aspectMask = textures_to_storage[i]->read_aspect_mask;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = 0;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = textures_to_storage[i]->base_mipmap;
|
||||
image_memory_barrier.subresourceRange.levelCount = textures_to_storage[i]->mipmaps;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = 0;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = textures_to_storage[i]->base_layer;
|
||||
image_memory_barrier.subresourceRange.layerCount = textures_to_storage[i]->layers;
|
||||
|
||||
vkCmdPipelineBarrier(cl->command_buffer, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT | VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, 0, 0, nullptr, 0, nullptr, 1, &image_memory_barrier);
|
||||
|
@ -6369,9 +6393,9 @@ void RenderingDeviceVulkan::compute_list_end() {
|
|||
image_memory_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
|
||||
image_memory_barrier.image = E->get()->image;
|
||||
image_memory_barrier.subresourceRange.aspectMask = E->get()->read_aspect_mask;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = 0;
|
||||
image_memory_barrier.subresourceRange.baseMipLevel = E->get()->base_mipmap;
|
||||
image_memory_barrier.subresourceRange.levelCount = E->get()->mipmaps;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = 0;
|
||||
image_memory_barrier.subresourceRange.baseArrayLayer = E->get()->base_layer;
|
||||
image_memory_barrier.subresourceRange.layerCount = E->get()->layers;
|
||||
|
||||
vkCmdPipelineBarrier(compute_list->command_buffer, VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, VK_PIPELINE_STAGE_VERTEX_SHADER_BIT | VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT, 0, 0, nullptr, 0, nullptr, 1, &image_memory_barrier);
|
||||
|
|
|
@ -138,6 +138,8 @@ class RenderingDeviceVulkan : public RenderingDevice {
|
|||
uint32_t layers;
|
||||
uint32_t mipmaps;
|
||||
uint32_t usage_flags;
|
||||
uint32_t base_mipmap;
|
||||
uint32_t base_layer;
|
||||
|
||||
Vector<DataFormat> allowed_shared_formats;
|
||||
|
||||
|
|
|
@ -99,7 +99,7 @@ RID RasterizerEffectsRD::_get_uniform_set_from_texture(RID p_texture, bool p_use
|
|||
u.ids.push_back(p_texture);
|
||||
uniforms.push_back(u);
|
||||
//any thing with the same configuration (one texture in binding 0 for set 0), is good
|
||||
RID uniform_set = RD::get_singleton()->uniform_set_create(uniforms, blur.shader.version_get_shader(blur.shader_version, 0), 0);
|
||||
RID uniform_set = RD::get_singleton()->uniform_set_create(uniforms, tonemap.shader.version_get_shader(tonemap.shader_version, 0), 0);
|
||||
|
||||
texture_to_uniform_set_cache[p_texture] = uniform_set;
|
||||
|
||||
|
@ -204,154 +204,199 @@ RID RasterizerEffectsRD::_get_compute_uniform_set_from_image_pair(RID p_texture1
|
|||
return uniform_set;
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::copy_to_rect_and_linearize(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2 &p_rect, bool p_flip_y, float p_z_near, float p_z_far) {
|
||||
void RasterizerEffectsRD::copy_to_fb_rect(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2i &p_rect, bool p_flip_y, bool p_force_luminance) {
|
||||
zeromem(©_to_fb.push_constant, sizeof(CopyToFbPushConstant));
|
||||
|
||||
zeromem(&blur.push_constant, sizeof(BlurPushConstant));
|
||||
if (p_flip_y) {
|
||||
blur.push_constant.flags |= BLUR_FLAG_FLIP_Y;
|
||||
}
|
||||
|
||||
blur.push_constant.camera_z_near = p_z_near;
|
||||
blur.push_constant.camera_z_far = p_z_far;
|
||||
|
||||
RD::DrawListID draw_list = RD::get_singleton()->draw_list_begin(p_dest_framebuffer, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD, Vector<Color>(), 1.0, 0, p_rect);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, blur.pipelines[BLUR_MODE_LINEARIZE_DEPTH].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_dest_framebuffer)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->draw_list_bind_index_array(draw_list, index_array);
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, &blur.push_constant, sizeof(BlurPushConstant));
|
||||
RD::get_singleton()->draw_list_draw(draw_list, true);
|
||||
RD::get_singleton()->draw_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::copy_to_rect(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2 &p_rect, bool p_flip_y, bool p_force_luminance) {
|
||||
|
||||
zeromem(&blur.push_constant, sizeof(BlurPushConstant));
|
||||
if (p_flip_y) {
|
||||
blur.push_constant.flags |= BLUR_FLAG_FLIP_Y;
|
||||
copy_to_fb.push_constant.flip_y = true;
|
||||
}
|
||||
if (p_force_luminance) {
|
||||
blur.push_constant.flags |= BLUR_COPY_FORCE_LUMINANCE;
|
||||
copy_to_fb.push_constant.force_luminance = true;
|
||||
}
|
||||
|
||||
RD::DrawListID draw_list = RD::get_singleton()->draw_list_begin(p_dest_framebuffer, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD, Vector<Color>(), 1.0, 0, p_rect);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, blur.pipelines[BLUR_MODE_SIMPLY_COPY].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_dest_framebuffer)));
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, copy_to_fb.pipeline.get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_dest_framebuffer)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->draw_list_bind_index_array(draw_list, index_array);
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, &blur.push_constant, sizeof(BlurPushConstant));
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, ©_to_fb.push_constant, sizeof(CopyToFbPushConstant));
|
||||
RD::get_singleton()->draw_list_draw(draw_list, true);
|
||||
RD::get_singleton()->draw_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::region_copy(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2 &p_region) {
|
||||
void RasterizerEffectsRD::copy_to_rect(RID p_source_rd_texture, RID p_dest_texture, const Rect2i &p_rect, bool p_flip_y, bool p_force_luminance, bool p_all_source, bool p_8_bit_dst) {
|
||||
|
||||
zeromem(&blur.push_constant, sizeof(BlurPushConstant));
|
||||
|
||||
if (p_region != Rect2()) {
|
||||
blur.push_constant.flags = BLUR_FLAG_USE_BLUR_SECTION;
|
||||
blur.push_constant.section[0] = p_region.position.x;
|
||||
blur.push_constant.section[1] = p_region.position.y;
|
||||
blur.push_constant.section[2] = p_region.size.width;
|
||||
blur.push_constant.section[3] = p_region.size.height;
|
||||
zeromem(©.push_constant, sizeof(CopyPushConstant));
|
||||
if (p_flip_y) {
|
||||
copy.push_constant.flags |= COPY_FLAG_FLIP_Y;
|
||||
}
|
||||
|
||||
RD::DrawListID draw_list = RD::get_singleton()->draw_list_begin(p_dest_framebuffer, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, blur.pipelines[BLUR_MODE_SIMPLY_COPY].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_dest_framebuffer)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->draw_list_bind_index_array(draw_list, index_array);
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, &blur.push_constant, sizeof(BlurPushConstant));
|
||||
RD::get_singleton()->draw_list_draw(draw_list, true);
|
||||
RD::get_singleton()->draw_list_end();
|
||||
if (p_force_luminance) {
|
||||
copy.push_constant.flags |= COPY_FLAG_FORCE_LUMINANCE;
|
||||
}
|
||||
|
||||
if (p_all_source) {
|
||||
copy.push_constant.flags |= COPY_FLAG_ALL_SOURCE;
|
||||
}
|
||||
|
||||
copy.push_constant.section[0] = 0;
|
||||
copy.push_constant.section[1] = 0;
|
||||
copy.push_constant.section[2] = p_rect.size.width;
|
||||
copy.push_constant.section[3] = p_rect.size.height;
|
||||
copy.push_constant.target[0] = p_rect.position.x;
|
||||
copy.push_constant.target[1] = p_rect.position.y;
|
||||
|
||||
int32_t x_groups = (p_rect.size.width - 1) / 8 + 1;
|
||||
int32_t y_groups = (p_rect.size.height - 1) / 8 + 1;
|
||||
|
||||
RD::ComputeListID compute_list = RD::get_singleton()->compute_list_begin();
|
||||
RD::get_singleton()->compute_list_bind_compute_pipeline(compute_list, copy.pipelines[p_8_bit_dst ? COPY_MODE_SIMPLY_COPY_8BIT : COPY_MODE_SIMPLY_COPY]);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_uniform_set_from_image(p_dest_texture), 3);
|
||||
RD::get_singleton()->compute_list_set_push_constant(compute_list, ©.push_constant, sizeof(CopyPushConstant));
|
||||
RD::get_singleton()->compute_list_dispatch(compute_list, x_groups, y_groups, 1);
|
||||
RD::get_singleton()->compute_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::gaussian_blur(RID p_source_rd_texture, RID p_framebuffer_half, RID p_rd_texture_half, RID p_dest_framebuffer, const Vector2 &p_pixel_size, const Rect2 &p_region) {
|
||||
void RasterizerEffectsRD::copy_depth_to_rect_and_linearize(RID p_source_rd_texture, RID p_dest_texture, const Rect2i &p_rect, bool p_flip_y, float p_z_near, float p_z_far) {
|
||||
|
||||
zeromem(&blur.push_constant, sizeof(BlurPushConstant));
|
||||
zeromem(©.push_constant, sizeof(CopyPushConstant));
|
||||
if (p_flip_y) {
|
||||
copy.push_constant.flags |= COPY_FLAG_FLIP_Y;
|
||||
}
|
||||
|
||||
copy.push_constant.section[0] = 0;
|
||||
copy.push_constant.section[1] = 0;
|
||||
copy.push_constant.section[2] = p_rect.size.width;
|
||||
copy.push_constant.section[3] = p_rect.size.height;
|
||||
copy.push_constant.target[0] = p_rect.position.x;
|
||||
copy.push_constant.target[1] = p_rect.position.y;
|
||||
copy.push_constant.camera_z_far = p_z_far;
|
||||
copy.push_constant.camera_z_near = p_z_near;
|
||||
|
||||
int32_t x_groups = (p_rect.size.width - 1) / 8 + 1;
|
||||
int32_t y_groups = (p_rect.size.height - 1) / 8 + 1;
|
||||
|
||||
RD::ComputeListID compute_list = RD::get_singleton()->compute_list_begin();
|
||||
RD::get_singleton()->compute_list_bind_compute_pipeline(compute_list, copy.pipelines[COPY_MODE_LINEARIZE_DEPTH]);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_uniform_set_from_image(p_dest_texture), 3);
|
||||
RD::get_singleton()->compute_list_set_push_constant(compute_list, ©.push_constant, sizeof(CopyPushConstant));
|
||||
RD::get_singleton()->compute_list_dispatch(compute_list, x_groups, y_groups, 1);
|
||||
RD::get_singleton()->compute_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::copy_depth_to_rect(RID p_source_rd_texture, RID p_dest_texture, const Rect2i &p_rect, bool p_flip_y) {
|
||||
|
||||
zeromem(©.push_constant, sizeof(CopyPushConstant));
|
||||
if (p_flip_y) {
|
||||
copy.push_constant.flags |= COPY_FLAG_FLIP_Y;
|
||||
}
|
||||
|
||||
copy.push_constant.section[0] = 0;
|
||||
copy.push_constant.section[1] = 0;
|
||||
copy.push_constant.section[2] = p_rect.size.width;
|
||||
copy.push_constant.section[3] = p_rect.size.height;
|
||||
copy.push_constant.target[0] = p_rect.position.x;
|
||||
copy.push_constant.target[1] = p_rect.position.y;
|
||||
|
||||
int32_t x_groups = (p_rect.size.width - 1) / 8 + 1;
|
||||
int32_t y_groups = (p_rect.size.height - 1) / 8 + 1;
|
||||
|
||||
RD::ComputeListID compute_list = RD::get_singleton()->compute_list_begin();
|
||||
RD::get_singleton()->compute_list_bind_compute_pipeline(compute_list, copy.pipelines[COPY_MODE_SIMPLY_COPY_DEPTH]);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_uniform_set_from_image(p_dest_texture), 3);
|
||||
RD::get_singleton()->compute_list_set_push_constant(compute_list, ©.push_constant, sizeof(CopyPushConstant));
|
||||
RD::get_singleton()->compute_list_dispatch(compute_list, x_groups, y_groups, 1);
|
||||
RD::get_singleton()->compute_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::gaussian_blur(RID p_source_rd_texture, RID p_texture, RID p_back_texture, const Rect2i &p_region, bool p_8bit_dst) {
|
||||
|
||||
zeromem(©.push_constant, sizeof(CopyPushConstant));
|
||||
|
||||
uint32_t base_flags = 0;
|
||||
if (p_region != Rect2()) {
|
||||
base_flags = BLUR_FLAG_USE_BLUR_SECTION;
|
||||
blur.push_constant.section[0] = p_region.position.x;
|
||||
blur.push_constant.section[1] = p_region.position.y;
|
||||
blur.push_constant.section[2] = p_region.size.width;
|
||||
blur.push_constant.section[3] = p_region.size.height;
|
||||
}
|
||||
|
||||
blur.push_constant.pixel_size[0] = p_pixel_size.x;
|
||||
blur.push_constant.pixel_size[1] = p_pixel_size.y;
|
||||
copy.push_constant.section[0] = p_region.position.x;
|
||||
copy.push_constant.section[1] = p_region.position.y;
|
||||
copy.push_constant.section[2] = p_region.size.width;
|
||||
copy.push_constant.section[3] = p_region.size.height;
|
||||
|
||||
int32_t x_groups = (p_region.size.width - 1) / 8 + 1;
|
||||
int32_t y_groups = (p_region.size.height - 1) / 8 + 1;
|
||||
//HORIZONTAL
|
||||
RD::DrawListID draw_list = RD::get_singleton()->draw_list_begin(p_framebuffer_half, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, blur.pipelines[BLUR_MODE_GAUSSIAN_BLUR].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_framebuffer_half)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->draw_list_bind_index_array(draw_list, index_array);
|
||||
RD::DrawListID compute_list = RD::get_singleton()->compute_list_begin();
|
||||
RD::get_singleton()->compute_list_bind_compute_pipeline(compute_list, copy.pipelines[p_8bit_dst ? COPY_MODE_GAUSSIAN_COPY_8BIT : COPY_MODE_GAUSSIAN_COPY]);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_uniform_set_from_image(p_back_texture), 0);
|
||||
|
||||
blur.push_constant.flags = base_flags | BLUR_FLAG_HORIZONTAL;
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, &blur.push_constant, sizeof(BlurPushConstant));
|
||||
copy.push_constant.flags = base_flags | COPY_FLAG_HORIZONTAL;
|
||||
RD::get_singleton()->compute_list_set_push_constant(compute_list, ©.push_constant, sizeof(CopyPushConstant));
|
||||
|
||||
RD::get_singleton()->draw_list_draw(draw_list, true);
|
||||
RD::get_singleton()->draw_list_end();
|
||||
RD::get_singleton()->compute_list_dispatch(compute_list, x_groups, y_groups, 1);
|
||||
|
||||
RD::get_singleton()->compute_list_add_barrier(compute_list);
|
||||
|
||||
//VERTICAL
|
||||
draw_list = RD::get_singleton()->draw_list_begin(p_dest_framebuffer, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, blur.pipelines[BLUR_MODE_GAUSSIAN_BLUR].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_dest_framebuffer)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_rd_texture_half), 0);
|
||||
RD::get_singleton()->draw_list_bind_index_array(draw_list, index_array);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_back_texture), 0);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_uniform_set_from_image(p_texture), 0);
|
||||
|
||||
blur.push_constant.flags = base_flags;
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, &blur.push_constant, sizeof(BlurPushConstant));
|
||||
copy.push_constant.flags = base_flags;
|
||||
RD::get_singleton()->compute_list_set_push_constant(compute_list, ©.push_constant, sizeof(CopyPushConstant));
|
||||
|
||||
RD::get_singleton()->draw_list_draw(draw_list, true);
|
||||
RD::get_singleton()->draw_list_end();
|
||||
RD::get_singleton()->compute_list_dispatch(compute_list, x_groups, y_groups, 1);
|
||||
RD::get_singleton()->compute_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::gaussian_glow(RID p_source_rd_texture, RID p_framebuffer_half, RID p_rd_texture_half, RID p_dest_framebuffer, const Vector2 &p_pixel_size, float p_strength, bool p_first_pass, float p_luminance_cap, float p_exposure, float p_bloom, float p_hdr_bleed_treshold, float p_hdr_bleed_scale, RID p_auto_exposure, float p_auto_exposure_grey) {
|
||||
void RasterizerEffectsRD::gaussian_glow(RID p_source_rd_texture, RID p_texture, RID p_back_texture, const Size2i &p_size, float p_strength, bool p_first_pass, float p_luminance_cap, float p_exposure, float p_bloom, float p_hdr_bleed_treshold, float p_hdr_bleed_scale, RID p_auto_exposure, float p_auto_exposure_grey) {
|
||||
|
||||
zeromem(&blur.push_constant, sizeof(BlurPushConstant));
|
||||
zeromem(©.push_constant, sizeof(CopyPushConstant));
|
||||
|
||||
BlurMode blur_mode = p_first_pass && p_auto_exposure.is_valid() ? BLUR_MODE_GAUSSIAN_GLOW_AUTO_EXPOSURE : BLUR_MODE_GAUSSIAN_GLOW;
|
||||
CopyMode copy_mode = p_first_pass && p_auto_exposure.is_valid() ? COPY_MODE_GAUSSIAN_GLOW_AUTO_EXPOSURE : COPY_MODE_GAUSSIAN_GLOW;
|
||||
uint32_t base_flags = 0;
|
||||
|
||||
blur.push_constant.pixel_size[0] = p_pixel_size.x;
|
||||
blur.push_constant.pixel_size[1] = p_pixel_size.y;
|
||||
int32_t x_groups = (p_size.width - 1) / 8 + 1;
|
||||
int32_t y_groups = (p_size.height - 1) / 8 + 1;
|
||||
|
||||
blur.push_constant.glow_strength = p_strength;
|
||||
blur.push_constant.glow_bloom = p_bloom;
|
||||
blur.push_constant.glow_hdr_threshold = p_hdr_bleed_treshold;
|
||||
blur.push_constant.glow_hdr_scale = p_hdr_bleed_scale;
|
||||
blur.push_constant.glow_exposure = p_exposure;
|
||||
blur.push_constant.glow_white = 0; //actually unused
|
||||
blur.push_constant.glow_luminance_cap = p_luminance_cap;
|
||||
copy.push_constant.section[2] = p_size.x;
|
||||
copy.push_constant.section[3] = p_size.y;
|
||||
|
||||
blur.push_constant.glow_auto_exposure_grey = p_auto_exposure_grey; //unused also
|
||||
copy.push_constant.glow_strength = p_strength;
|
||||
copy.push_constant.glow_bloom = p_bloom;
|
||||
copy.push_constant.glow_hdr_threshold = p_hdr_bleed_treshold;
|
||||
copy.push_constant.glow_hdr_scale = p_hdr_bleed_scale;
|
||||
copy.push_constant.glow_exposure = p_exposure;
|
||||
copy.push_constant.glow_white = 0; //actually unused
|
||||
copy.push_constant.glow_luminance_cap = p_luminance_cap;
|
||||
|
||||
copy.push_constant.glow_auto_exposure_grey = p_auto_exposure_grey; //unused also
|
||||
|
||||
//HORIZONTAL
|
||||
RD::DrawListID draw_list = RD::get_singleton()->draw_list_begin(p_framebuffer_half, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, blur.pipelines[blur_mode].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_framebuffer_half)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::ComputeListID compute_list = RD::get_singleton()->compute_list_begin();
|
||||
RD::get_singleton()->compute_list_bind_compute_pipeline(compute_list, copy.pipelines[copy_mode]);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_uniform_set_from_image(p_back_texture), 3);
|
||||
if (p_auto_exposure.is_valid() && p_first_pass) {
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_auto_exposure), 1);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_auto_exposure), 1);
|
||||
}
|
||||
RD::get_singleton()->draw_list_bind_index_array(draw_list, index_array);
|
||||
|
||||
blur.push_constant.flags = base_flags | BLUR_FLAG_HORIZONTAL | (p_first_pass ? BLUR_FLAG_GLOW_FIRST_PASS : 0);
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, &blur.push_constant, sizeof(BlurPushConstant));
|
||||
copy.push_constant.flags = base_flags | COPY_FLAG_HORIZONTAL | (p_first_pass ? COPY_FLAG_GLOW_FIRST_PASS : 0);
|
||||
RD::get_singleton()->compute_list_set_push_constant(compute_list, ©.push_constant, sizeof(CopyPushConstant));
|
||||
|
||||
RD::get_singleton()->draw_list_draw(draw_list, true);
|
||||
RD::get_singleton()->draw_list_end();
|
||||
RD::get_singleton()->compute_list_dispatch(compute_list, x_groups, y_groups, 1);
|
||||
RD::get_singleton()->compute_list_add_barrier(compute_list);
|
||||
|
||||
blur_mode = BLUR_MODE_GAUSSIAN_GLOW;
|
||||
copy_mode = COPY_MODE_GAUSSIAN_GLOW;
|
||||
|
||||
//VERTICAL
|
||||
draw_list = RD::get_singleton()->draw_list_begin(p_dest_framebuffer, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, blur.pipelines[blur_mode].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_dest_framebuffer)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_rd_texture_half), 0);
|
||||
RD::get_singleton()->draw_list_bind_index_array(draw_list, index_array);
|
||||
RD::get_singleton()->compute_list_bind_compute_pipeline(compute_list, copy.pipelines[copy_mode]);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_back_texture), 0);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_uniform_set_from_image(p_texture), 3);
|
||||
|
||||
blur.push_constant.flags = base_flags;
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, &blur.push_constant, sizeof(BlurPushConstant));
|
||||
copy.push_constant.flags = base_flags;
|
||||
RD::get_singleton()->compute_list_set_push_constant(compute_list, ©.push_constant, sizeof(CopyPushConstant));
|
||||
|
||||
RD::get_singleton()->draw_list_draw(draw_list, true);
|
||||
RD::get_singleton()->draw_list_end();
|
||||
RD::get_singleton()->compute_list_dispatch(compute_list, x_groups, y_groups, 1);
|
||||
RD::get_singleton()->compute_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::screen_space_reflection(RID p_diffuse, RID p_normal, RenderingServer::EnvironmentSSRRoughnessQuality p_roughness_quality, RID p_roughness, RID p_blur_radius, RID p_blur_radius2, RID p_metallic, const Color &p_metallic_mask, RID p_depth, RID p_scale_depth, RID p_scale_normal, RID p_output, RID p_output_blur, const Size2i &p_screen_size, int p_max_steps, float p_fade_in, float p_fade_out, float p_tolerance, const CameraMatrix &p_camera) {
|
||||
|
@ -560,37 +605,49 @@ void RasterizerEffectsRD::merge_specular(RID p_dest_framebuffer, RID p_specular,
|
|||
RD::get_singleton()->draw_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::make_mipmap(RID p_source_rd_texture, RID p_dest_framebuffer, const Vector2 &p_pixel_size) {
|
||||
void RasterizerEffectsRD::make_mipmap(RID p_source_rd_texture, RID p_dest_texture, const Size2i &p_size) {
|
||||
|
||||
zeromem(&blur.push_constant, sizeof(BlurPushConstant));
|
||||
zeromem(©.push_constant, sizeof(CopyPushConstant));
|
||||
|
||||
blur.push_constant.pixel_size[0] = p_pixel_size.x;
|
||||
blur.push_constant.pixel_size[1] = p_pixel_size.y;
|
||||
copy.push_constant.section[0] = 0;
|
||||
copy.push_constant.section[1] = 0;
|
||||
copy.push_constant.section[2] = p_size.width;
|
||||
copy.push_constant.section[3] = p_size.height;
|
||||
|
||||
RD::DrawListID draw_list = RD::get_singleton()->draw_list_begin(p_dest_framebuffer, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, blur.pipelines[BLUR_MODE_MIPMAP].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_dest_framebuffer)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->draw_list_bind_index_array(draw_list, index_array);
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, &blur.push_constant, sizeof(BlurPushConstant));
|
||||
RD::get_singleton()->draw_list_draw(draw_list, true);
|
||||
RD::get_singleton()->draw_list_end();
|
||||
int32_t x_groups = (p_size.width - 1) / 8 + 1;
|
||||
int32_t y_groups = (p_size.height - 1) / 8 + 1;
|
||||
|
||||
RD::ComputeListID compute_list = RD::get_singleton()->compute_list_begin();
|
||||
RD::get_singleton()->compute_list_bind_compute_pipeline(compute_list, copy.pipelines[COPY_MODE_MIPMAP]);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_uniform_set_from_image(p_dest_texture), 3);
|
||||
RD::get_singleton()->compute_list_set_push_constant(compute_list, ©.push_constant, sizeof(CopyPushConstant));
|
||||
RD::get_singleton()->compute_list_dispatch(compute_list, x_groups, y_groups, 1);
|
||||
RD::get_singleton()->compute_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::copy_cubemap_to_dp(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2 &p_rect, float p_z_near, float p_z_far, float p_bias, bool p_dp_flip) {
|
||||
void RasterizerEffectsRD::copy_cubemap_to_dp(RID p_source_rd_texture, RID p_dest_texture, const Rect2i &p_rect, float p_z_near, float p_z_far, float p_bias, bool p_dp_flip) {
|
||||
|
||||
CopyToDPPushConstant push_constant;
|
||||
push_constant.screen_size[0] = p_rect.size.x;
|
||||
push_constant.screen_size[1] = p_rect.size.y;
|
||||
push_constant.dest_offset[0] = p_rect.position.x;
|
||||
push_constant.dest_offset[1] = p_rect.position.y;
|
||||
push_constant.bias = p_bias;
|
||||
push_constant.z_far = p_z_far;
|
||||
push_constant.z_near = p_z_near;
|
||||
push_constant.z_flip = p_dp_flip;
|
||||
|
||||
RD::DrawListID draw_list = RD::get_singleton()->draw_list_begin(p_dest_framebuffer, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD, Vector<Color>(), 1.0, 0, p_rect);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, copy.pipelines[COPY_MODE_CUBE_TO_DP].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_dest_framebuffer)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->draw_list_bind_index_array(draw_list, index_array);
|
||||
RD::get_singleton()->draw_list_set_push_constant(draw_list, &push_constant, sizeof(CopyToDPPushConstant));
|
||||
RD::get_singleton()->draw_list_draw(draw_list, true);
|
||||
RD::get_singleton()->draw_list_end();
|
||||
int32_t x_groups = (p_rect.size.width - 1) / 8 + 1;
|
||||
int32_t y_groups = (p_rect.size.height - 1) / 8 + 1;
|
||||
|
||||
RD::ComputeListID compute_list = RD::get_singleton()->compute_list_begin();
|
||||
RD::get_singleton()->compute_list_bind_compute_pipeline(compute_list, cube_to_dp.pipeline);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_compute_uniform_set_from_texture(p_source_rd_texture), 0);
|
||||
RD::get_singleton()->compute_list_bind_uniform_set(compute_list, _get_uniform_set_from_image(p_dest_texture), 1);
|
||||
RD::get_singleton()->compute_list_set_push_constant(compute_list, &push_constant, sizeof(CopyToDPPushConstant));
|
||||
RD::get_singleton()->compute_list_dispatch(compute_list, x_groups, y_groups, 1);
|
||||
RD::get_singleton()->compute_list_end();
|
||||
}
|
||||
|
||||
void RasterizerEffectsRD::tonemapper(RID p_source_color, RID p_dst_framebuffer, const TonemapSettings &p_settings) {
|
||||
|
@ -619,7 +676,7 @@ void RasterizerEffectsRD::tonemapper(RID p_source_color, RID p_dst_framebuffer,
|
|||
|
||||
tonemap.push_constant.use_color_correction = p_settings.use_color_correction;
|
||||
|
||||
RD::DrawListID draw_list = RD::get_singleton()->draw_list_begin(p_dst_framebuffer, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_KEEP, RD::FINAL_ACTION_DISCARD);
|
||||
RD::DrawListID draw_list = RD::get_singleton()->draw_list_begin(p_dst_framebuffer, RD::INITIAL_ACTION_DROP, RD::FINAL_ACTION_READ, RD::INITIAL_ACTION_DROP, RD::FINAL_ACTION_DISCARD);
|
||||
RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, tonemap.pipelines[mode].get_render_pipeline(RD::INVALID_ID, RD::get_singleton()->framebuffer_get_format(p_dst_framebuffer)));
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_source_color), 0);
|
||||
RD::get_singleton()->draw_list_bind_uniform_set(draw_list, _get_uniform_set_from_texture(p_settings.exposure_texture), 1);
|
||||
|
@ -1129,33 +1186,38 @@ void RasterizerEffectsRD::render_sky(RD::DrawListID p_list, float p_time, RID p_
|
|||
|
||||
RasterizerEffectsRD::RasterizerEffectsRD() {
|
||||
|
||||
{ // Initialize blur
|
||||
Vector<String> blur_modes;
|
||||
blur_modes.push_back("\n#define MODE_GAUSSIAN_BLUR\n");
|
||||
blur_modes.push_back("\n#define MODE_GAUSSIAN_GLOW\n");
|
||||
blur_modes.push_back("\n#define MODE_GAUSSIAN_GLOW\n#define GLOW_USE_AUTO_EXPOSURE\n");
|
||||
blur_modes.push_back("\n#define MODE_DOF_NEAR_BLUR\n#define DOF_QUALITY_LOW\n");
|
||||
blur_modes.push_back("\n#define MODE_DOF_NEAR_BLUR\n#define DOF_QUALITY_MEDIUM\n");
|
||||
blur_modes.push_back("\n#define MODE_DOF_NEAR_BLUR\n#define DOF_QUALITY_HIGH\n");
|
||||
blur_modes.push_back("\n#define MODE_DOF_NEAR_BLUR\n#define DOF_QUALITY_LOW\n#define DOF_NEAR_BLUR_MERGE\n");
|
||||
blur_modes.push_back("\n#define MODE_DOF_NEAR_BLUR\n#define DOF_QUALITY_MEDIUM\n#define DOF_NEAR_BLUR_MERGE\n");
|
||||
blur_modes.push_back("\n#define MODE_DOF_NEAR_BLUR\n#define DOF_QUALITY_HIGH\n#define DOF_NEAR_BLUR_MERGE\n");
|
||||
blur_modes.push_back("\n#define MODE_DOF_FAR_BLUR\n#define DOF_QUALITY_LOW\n");
|
||||
blur_modes.push_back("\n#define MODE_DOF_FAR_BLUR\n#define DOF_QUALITY_MEDIUM\n");
|
||||
blur_modes.push_back("\n#define MODE_DOF_FAR_BLUR\n#define DOF_QUALITY_HIGH\n");
|
||||
blur_modes.push_back("\n#define MODE_SSAO_MERGE\n");
|
||||
blur_modes.push_back("\n#define MODE_SIMPLE_COPY\n");
|
||||
blur_modes.push_back("\n#define MODE_MIPMAP\n");
|
||||
blur_modes.push_back("\n#define MODE_LINEARIZE_DEPTH_COPY\n");
|
||||
{ // Initialize copy
|
||||
Vector<String> copy_modes;
|
||||
copy_modes.push_back("\n#define MODE_GAUSSIAN_BLUR\n");
|
||||
copy_modes.push_back("\n#define MODE_GAUSSIAN_BLUR\n#define DST_IMAGE_8BIT\n");
|
||||
copy_modes.push_back("\n#define MODE_GAUSSIAN_GLOW\n");
|
||||
copy_modes.push_back("\n#define MODE_GAUSSIAN_GLOW\n#define GLOW_USE_AUTO_EXPOSURE\n");
|
||||
copy_modes.push_back("\n#define MODE_SIMPLE_COPY\n");
|
||||
copy_modes.push_back("\n#define MODE_SIMPLE_COPY\n#define DST_IMAGE_8BIT\n");
|
||||
copy_modes.push_back("\n#define MODE_SIMPLE_COPY_DEPTH\n");
|
||||
copy_modes.push_back("\n#define MODE_MIPMAP\n");
|
||||
copy_modes.push_back("\n#define MODE_LINEARIZE_DEPTH_COPY\n");
|
||||
|
||||
blur.shader.initialize(blur_modes);
|
||||
zeromem(&blur.push_constant, sizeof(BlurPushConstant));
|
||||
blur.shader_version = blur.shader.version_create();
|
||||
copy.shader.initialize(copy_modes);
|
||||
zeromem(©.push_constant, sizeof(CopyPushConstant));
|
||||
copy.shader_version = copy.shader.version_create();
|
||||
|
||||
for (int i = 0; i < BLUR_MODE_MAX; i++) {
|
||||
blur.pipelines[i].setup(blur.shader.version_get_shader(blur.shader_version, i), RD::RENDER_PRIMITIVE_TRIANGLES, RD::PipelineRasterizationState(), RD::PipelineMultisampleState(), RD::PipelineDepthStencilState(), RD::PipelineColorBlendState::create_disabled(), 0);
|
||||
for (int i = 0; i < COPY_MODE_MAX; i++) {
|
||||
copy.pipelines[i] = RD::get_singleton()->compute_pipeline_create(copy.shader.version_get_shader(copy.shader_version, i));
|
||||
}
|
||||
}
|
||||
{
|
||||
Vector<String> copy_modes;
|
||||
copy_modes.push_back("\n");
|
||||
|
||||
copy_to_fb.shader.initialize(copy_modes);
|
||||
|
||||
copy_to_fb.shader_version = copy_to_fb.shader.version_create();
|
||||
|
||||
//use additive
|
||||
|
||||
copy_to_fb.pipeline.setup(copy_to_fb.shader.version_get_shader(copy_to_fb.shader_version, 0), RD::RENDER_PRIMITIVE_TRIANGLES, RD::PipelineRasterizationState(), RD::PipelineMultisampleState(), RD::PipelineDepthStencilState(), RD::PipelineColorBlendState::create_disabled(), 0);
|
||||
}
|
||||
|
||||
{
|
||||
// Initialize roughness
|
||||
|
@ -1202,15 +1264,13 @@ RasterizerEffectsRD::RasterizerEffectsRD() {
|
|||
{
|
||||
// Initialize copier
|
||||
Vector<String> copy_modes;
|
||||
copy_modes.push_back("\n#define MODE_CUBE_TO_DP\n");
|
||||
copy_modes.push_back("\n");
|
||||
|
||||
copy.shader.initialize(copy_modes);
|
||||
cube_to_dp.shader.initialize(copy_modes);
|
||||
|
||||
copy.shader_version = copy.shader.version_create();
|
||||
cube_to_dp.shader_version = cube_to_dp.shader.version_create();
|
||||
|
||||
for (int i = 0; i < COPY_MODE_MAX; i++) {
|
||||
copy.pipelines[i].setup(copy.shader.version_get_shader(copy.shader_version, i), RD::RENDER_PRIMITIVE_TRIANGLES, RD::PipelineRasterizationState(), RD::PipelineMultisampleState(), RD::PipelineDepthStencilState(), RD::PipelineColorBlendState::create_disabled(), 0);
|
||||
}
|
||||
cube_to_dp.pipeline = RD::get_singleton()->compute_pipeline_create(cube_to_dp.shader.version_get_shader(cube_to_dp.shader_version, 0));
|
||||
}
|
||||
|
||||
{
|
||||
|
@ -1482,9 +1542,9 @@ RasterizerEffectsRD::~RasterizerEffectsRD() {
|
|||
RD::get_singleton()->free(index_buffer); //array gets freed as dependency
|
||||
RD::get_singleton()->free(filter.coefficient_buffer);
|
||||
|
||||
blur.shader.version_free(blur.shader_version);
|
||||
bokeh.shader.version_free(bokeh.shader_version);
|
||||
copy.shader.version_free(copy.shader_version);
|
||||
bokeh.shader.version_free(bokeh.shader_version);
|
||||
cube_to_dp.shader.version_free(cube_to_dp.shader_version);
|
||||
cubemap_downsampler.shader.version_free(cubemap_downsampler.shader_version);
|
||||
filter.shader.version_free(filter.shader_version);
|
||||
luminance_reduce.shader.version_free(luminance_reduce.shader_version);
|
||||
|
|
|
@ -33,9 +33,10 @@
|
|||
|
||||
#include "core/math/camera_matrix.h"
|
||||
#include "servers/rendering/rasterizer_rd/render_pipeline_vertex_format_cache_rd.h"
|
||||
#include "servers/rendering/rasterizer_rd/shaders/blur.glsl.gen.h"
|
||||
#include "servers/rendering/rasterizer_rd/shaders/bokeh_dof.glsl.gen.h"
|
||||
#include "servers/rendering/rasterizer_rd/shaders/copy.glsl.gen.h"
|
||||
#include "servers/rendering/rasterizer_rd/shaders/copy_to_fb.glsl.gen.h"
|
||||
#include "servers/rendering/rasterizer_rd/shaders/cube_to_dp.glsl.gen.h"
|
||||
#include "servers/rendering/rasterizer_rd/shaders/cubemap_downsampler.glsl.gen.h"
|
||||
#include "servers/rendering/rasterizer_rd/shaders/cubemap_filter.glsl.gen.h"
|
||||
#include "servers/rendering/rasterizer_rd/shaders/cubemap_roughness.glsl.gen.h"
|
||||
|
@ -55,71 +56,78 @@
|
|||
|
||||
class RasterizerEffectsRD {
|
||||
|
||||
enum BlurMode {
|
||||
BLUR_MODE_GAUSSIAN_BLUR,
|
||||
BLUR_MODE_GAUSSIAN_GLOW,
|
||||
BLUR_MODE_GAUSSIAN_GLOW_AUTO_EXPOSURE,
|
||||
BLUR_MODE_DOF_NEAR_LOW,
|
||||
BLUR_MODE_DOF_NEAR_MEDIUM,
|
||||
BLUR_MODE_DOF_NEAR_HIGH,
|
||||
BLUR_MODE_DOF_NEAR_MERGE_LOW,
|
||||
BLUR_MODE_DOF_NEAR_MERGE_MEDIUM,
|
||||
BLUR_MODE_DOF_NEAR_MERGE_HIGH,
|
||||
BLUR_MODE_DOF_FAR_LOW,
|
||||
BLUR_MODE_DOF_FAR_MEDIUM,
|
||||
BLUR_MODE_DOF_FAR_HIGH,
|
||||
BLUR_MODE_SSAO_MERGE,
|
||||
BLUR_MODE_SIMPLY_COPY,
|
||||
BLUR_MODE_MIPMAP,
|
||||
BLUR_MODE_LINEARIZE_DEPTH,
|
||||
BLUR_MODE_MAX,
|
||||
enum CopyMode {
|
||||
COPY_MODE_GAUSSIAN_COPY,
|
||||
COPY_MODE_GAUSSIAN_COPY_8BIT,
|
||||
COPY_MODE_GAUSSIAN_GLOW,
|
||||
COPY_MODE_GAUSSIAN_GLOW_AUTO_EXPOSURE,
|
||||
COPY_MODE_SIMPLY_COPY,
|
||||
COPY_MODE_SIMPLY_COPY_8BIT,
|
||||
COPY_MODE_SIMPLY_COPY_DEPTH,
|
||||
COPY_MODE_MIPMAP,
|
||||
COPY_MODE_LINEARIZE_DEPTH,
|
||||
COPY_MODE_MAX,
|
||||
|
||||
};
|
||||
|
||||
enum {
|
||||
BLUR_FLAG_HORIZONTAL = (1 << 0),
|
||||
BLUR_FLAG_USE_BLUR_SECTION = (1 << 1),
|
||||
BLUR_FLAG_USE_ORTHOGONAL_PROJECTION = (1 << 2),
|
||||
BLUR_FLAG_DOF_NEAR_FIRST_TAP = (1 << 3),
|
||||
BLUR_FLAG_GLOW_FIRST_PASS = (1 << 4),
|
||||
BLUR_FLAG_FLIP_Y = (1 << 5),
|
||||
BLUR_COPY_FORCE_LUMINANCE = (1 << 6)
|
||||
COPY_FLAG_HORIZONTAL = (1 << 0),
|
||||
COPY_FLAG_USE_COPY_SECTION = (1 << 1),
|
||||
COPY_FLAG_USE_ORTHOGONAL_PROJECTION = (1 << 2),
|
||||
COPY_FLAG_DOF_NEAR_FIRST_TAP = (1 << 3),
|
||||
COPY_FLAG_GLOW_FIRST_PASS = (1 << 4),
|
||||
COPY_FLAG_FLIP_Y = (1 << 5),
|
||||
COPY_FLAG_FORCE_LUMINANCE = (1 << 6),
|
||||
COPY_FLAG_ALL_SOURCE = (1 << 7)
|
||||
};
|
||||
|
||||
struct BlurPushConstant {
|
||||
float section[4];
|
||||
float pixel_size[2];
|
||||
struct CopyPushConstant {
|
||||
|
||||
int32_t section[4];
|
||||
int32_t target[2];
|
||||
uint32_t flags;
|
||||
uint32_t pad;
|
||||
//glow
|
||||
// Glow.
|
||||
float glow_strength;
|
||||
float glow_bloom;
|
||||
float glow_hdr_threshold;
|
||||
float glow_hdr_scale;
|
||||
|
||||
float glow_exposure;
|
||||
float glow_white;
|
||||
float glow_luminance_cap;
|
||||
float glow_auto_exposure_grey;
|
||||
//dof
|
||||
float dof_begin;
|
||||
float dof_end;
|
||||
float dof_radius;
|
||||
float dof_pad;
|
||||
|
||||
float dof_dir[2];
|
||||
// DOF.
|
||||
float camera_z_far;
|
||||
float camera_z_near;
|
||||
|
||||
float ssao_color[4];
|
||||
uint32_t pad2[2];
|
||||
};
|
||||
|
||||
struct Blur {
|
||||
BlurPushConstant push_constant;
|
||||
BlurShaderRD shader;
|
||||
struct Copy {
|
||||
CopyPushConstant push_constant;
|
||||
CopyShaderRD shader;
|
||||
RID shader_version;
|
||||
RenderPipelineVertexFormatCacheRD pipelines[BLUR_MODE_MAX];
|
||||
RID pipelines[COPY_MODE_MAX];
|
||||
|
||||
} blur;
|
||||
} copy;
|
||||
|
||||
struct CopyToFbPushConstant {
|
||||
|
||||
float section[4];
|
||||
float pixel_size[2];
|
||||
uint32_t flip_y;
|
||||
uint32_t use_section;
|
||||
uint32_t force_luminance;
|
||||
uint32_t pad[3];
|
||||
};
|
||||
|
||||
struct CopyToFb {
|
||||
CopyToFbPushConstant push_constant;
|
||||
CopyToFbShaderRD shader;
|
||||
RID shader_version;
|
||||
RenderPipelineVertexFormatCacheRD pipeline;
|
||||
|
||||
} copy_to_fb;
|
||||
|
||||
struct CubemapRoughnessPushConstant {
|
||||
uint32_t face_id;
|
||||
|
@ -164,8 +172,11 @@ class RasterizerEffectsRD {
|
|||
float auto_exposure_grey;
|
||||
};
|
||||
|
||||
/* tonemap actually writes to a framebuffer, which is
|
||||
* better to do using the raster pipeline rather than
|
||||
* comptute, as that framebuffer might be in different formats
|
||||
*/
|
||||
struct Tonemap {
|
||||
|
||||
TonemapPushConstant push_constant;
|
||||
TonemapShaderRD shader;
|
||||
RID shader_version;
|
||||
|
@ -196,23 +207,20 @@ class RasterizerEffectsRD {
|
|||
} luminance_reduce;
|
||||
|
||||
struct CopyToDPPushConstant {
|
||||
int32_t screen_size[2];
|
||||
int32_t dest_offset[2];
|
||||
float bias;
|
||||
float z_far;
|
||||
float z_near;
|
||||
uint32_t z_flip;
|
||||
};
|
||||
|
||||
enum CopyMode {
|
||||
COPY_MODE_CUBE_TO_DP,
|
||||
COPY_MODE_MAX
|
||||
};
|
||||
struct CoptToDP {
|
||||
|
||||
struct Copy {
|
||||
|
||||
CopyShaderRD shader;
|
||||
CubeToDpShaderRD shader;
|
||||
RID shader_version;
|
||||
RenderPipelineVertexFormatCacheRD pipelines[COPY_MODE_MAX];
|
||||
} copy;
|
||||
RID pipeline;
|
||||
} cube_to_dp;
|
||||
|
||||
struct BokehPushConstant {
|
||||
uint32_t size[2];
|
||||
|
@ -392,6 +400,10 @@ class RasterizerEffectsRD {
|
|||
SPECULAR_MERGE_MAX
|
||||
};
|
||||
|
||||
/* Specular merge must be done using raster, rather than compute
|
||||
* because it must continue the existing color buffer
|
||||
*/
|
||||
|
||||
struct SpecularMerge {
|
||||
|
||||
SpecularMergeShaderRD shader;
|
||||
|
@ -537,17 +549,16 @@ class RasterizerEffectsRD {
|
|||
RID _get_compute_uniform_set_from_image_pair(RID p_texture, RID p_texture2);
|
||||
|
||||
public:
|
||||
//TODO must re-do most of the shaders in compute
|
||||
|
||||
void region_copy(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2 &p_region);
|
||||
void copy_to_rect(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2 &p_rect, bool p_flip_y = false, bool p_force_luminance = false);
|
||||
void copy_to_rect_and_linearize(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2 &p_rect, bool p_flip_y, float p_z_near, float p_z_far);
|
||||
void gaussian_blur(RID p_source_rd_texture, RID p_framebuffer_half, RID p_rd_texture_half, RID p_dest_framebuffer, const Vector2 &p_pixel_size, const Rect2 &p_region);
|
||||
void gaussian_glow(RID p_source_rd_texture, RID p_framebuffer_half, RID p_rd_texture_half, RID p_dest_framebuffer, const Vector2 &p_pixel_size, float p_strength = 1.0, bool p_first_pass = false, float p_luminance_cap = 16.0, float p_exposure = 1.0, float p_bloom = 0.0, float p_hdr_bleed_treshold = 1.0, float p_hdr_bleed_scale = 1.0, RID p_auto_exposure = RID(), float p_auto_exposure_grey = 1.0);
|
||||
void copy_to_fb_rect(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2i &p_rect, bool p_flip_y = false, bool p_force_luminance = false);
|
||||
void copy_to_rect(RID p_source_rd_texture, RID p_dest_texture, const Rect2i &p_rect, bool p_flip_y = false, bool p_force_luminance = false, bool p_all_source = false, bool p_8_bit_dst = false);
|
||||
void copy_depth_to_rect(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2i &p_rect, bool p_flip_y = false);
|
||||
void copy_depth_to_rect_and_linearize(RID p_source_rd_texture, RID p_dest_texture, const Rect2i &p_rect, bool p_flip_y, float p_z_near, float p_z_far);
|
||||
void gaussian_blur(RID p_source_rd_texture, RID p_texture, RID p_back_texture, const Rect2i &p_region, bool p_8bit_dst = false);
|
||||
void gaussian_glow(RID p_source_rd_texture, RID p_texture, RID p_back_texture, const Size2i &p_size, float p_strength = 1.0, bool p_first_pass = false, float p_luminance_cap = 16.0, float p_exposure = 1.0, float p_bloom = 0.0, float p_hdr_bleed_treshold = 1.0, float p_hdr_bleed_scale = 1.0, RID p_auto_exposure = RID(), float p_auto_exposure_grey = 1.0);
|
||||
|
||||
void cubemap_roughness(RID p_source_rd_texture, RID p_dest_framebuffer, uint32_t p_face_id, uint32_t p_sample_count, float p_roughness, float p_size);
|
||||
void make_mipmap(RID p_source_rd_texture, RID p_framebuffer_half, const Vector2 &p_pixel_size);
|
||||
void copy_cubemap_to_dp(RID p_source_rd_texture, RID p_dest_framebuffer, const Rect2 &p_rect, float p_z_near, float p_z_far, float p_bias, bool p_dp_flip);
|
||||
void make_mipmap(RID p_source_rd_texture, RID p_dest_texture, const Size2i &p_size);
|
||||
void copy_cubemap_to_dp(RID p_source_rd_texture, RID p_dest_texture, const Rect2i &p_rect, float p_z_near, float p_z_far, float p_bias, bool p_dp_flip);
|
||||
void luminance_reduction(RID p_source_texture, const Size2i p_source_size, const Vector<RID> p_reduce, RID p_prev_luminance, float p_min_luminance, float p_max_luminance, float p_adjust, bool p_set = false);
|
||||
void bokeh_dof(RID p_base_texture, RID p_depth_texture, const Size2i &p_base_texture_size, RID p_secondary_texture, RID p_bokeh_texture1, RID p_bokeh_texture2, bool p_dof_far, float p_dof_far_begin, float p_dof_far_size, bool p_dof_near, float p_dof_near_begin, float p_dof_near_size, float p_bokeh_size, RS::DOFBokehShape p_bokeh_shape, RS::DOFBlurQuality p_quality, bool p_use_jitter, float p_cam_znear, float p_cam_zfar, bool p_cam_orthogonal);
|
||||
|
||||
|
|
|
@ -181,10 +181,9 @@ void RasterizerSceneRD::_update_reflection_mipmaps(ReflectionData &rd) {
|
|||
for (int j = 0; j < rd.layers[i].mipmaps.size() - 1; j++) {
|
||||
for (int k = 0; k < 6; k++) {
|
||||
RID view = rd.layers[i].mipmaps[j].views[k];
|
||||
RID fb = rd.layers[i].mipmaps[j + 1].framebuffers[k];
|
||||
Vector2 size = rd.layers[i].mipmaps[j].size;
|
||||
size = Vector2(1.0 / size.x, 1.0 / size.y);
|
||||
storage->get_effects()->make_mipmap(view, fb, size);
|
||||
RID texture = rd.layers[i].mipmaps[j + 1].views[k];
|
||||
Size2i size = rd.layers[i].mipmaps[j + 1].size;
|
||||
storage->get_effects()->make_mipmap(view, texture, size);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1599,7 +1598,6 @@ void RasterizerSceneRD::shadow_atlas_set_size(RID p_atlas, int p_size) {
|
|||
if (shadow_atlas->depth.is_valid()) {
|
||||
RD::get_singleton()->free(shadow_atlas->depth);
|
||||
shadow_atlas->depth = RID();
|
||||
shadow_atlas->fb = RID();
|
||||
}
|
||||
for (int i = 0; i < 4; i++) {
|
||||
//clear subdivisions
|
||||
|
@ -1625,13 +1623,9 @@ void RasterizerSceneRD::shadow_atlas_set_size(RID p_atlas, int p_size) {
|
|||
tf.format = RD::DATA_FORMAT_R32_SFLOAT;
|
||||
tf.width = shadow_atlas->size;
|
||||
tf.height = shadow_atlas->size;
|
||||
tf.usage_bits = RD::TEXTURE_USAGE_SAMPLING_BIT | RD::TEXTURE_USAGE_COLOR_ATTACHMENT_BIT;
|
||||
tf.usage_bits = RD::TEXTURE_USAGE_SAMPLING_BIT | RD::TEXTURE_USAGE_STORAGE_BIT;
|
||||
|
||||
shadow_atlas->depth = RD::get_singleton()->texture_create(tf, RD::TextureView());
|
||||
|
||||
Vector<RID> fb;
|
||||
fb.push_back(shadow_atlas->depth);
|
||||
shadow_atlas->fb = RD::get_singleton()->framebuffer_create(fb);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1901,7 +1895,6 @@ void RasterizerSceneRD::directional_shadow_atlas_set_size(int p_size) {
|
|||
if (directional_shadow.depth.is_valid()) {
|
||||
RD::get_singleton()->free(directional_shadow.depth);
|
||||
directional_shadow.depth = RID();
|
||||
directional_shadow.fb = RID();
|
||||
}
|
||||
|
||||
if (p_size > 0) {
|
||||
|
@ -1910,12 +1903,9 @@ void RasterizerSceneRD::directional_shadow_atlas_set_size(int p_size) {
|
|||
tf.format = RD::DATA_FORMAT_R32_SFLOAT;
|
||||
tf.width = p_size;
|
||||
tf.height = p_size;
|
||||
tf.usage_bits = RD::TEXTURE_USAGE_SAMPLING_BIT | RD::TEXTURE_USAGE_COLOR_ATTACHMENT_BIT;
|
||||
tf.usage_bits = RD::TEXTURE_USAGE_SAMPLING_BIT | RD::TEXTURE_USAGE_STORAGE_BIT;
|
||||
|
||||
directional_shadow.depth = RD::get_singleton()->texture_create(tf, RD::TextureView());
|
||||
Vector<RID> fb;
|
||||
fb.push_back(directional_shadow.depth);
|
||||
directional_shadow.fb = RD::get_singleton()->framebuffer_create(fb);
|
||||
}
|
||||
|
||||
_base_uniforms_changed();
|
||||
|
@ -3062,7 +3052,7 @@ void RasterizerSceneRD::_allocate_blur_textures(RenderBuffers *rb) {
|
|||
tf.width = rb->width;
|
||||
tf.height = rb->height;
|
||||
tf.type = RD::TEXTURE_TYPE_2D;
|
||||
tf.usage_bits = RD::TEXTURE_USAGE_COLOR_ATTACHMENT_BIT | RD::TEXTURE_USAGE_STORAGE_BIT | RD::TEXTURE_USAGE_SAMPLING_BIT | RD::TEXTURE_USAGE_CAN_COPY_TO_BIT;
|
||||
tf.usage_bits = RD::TEXTURE_USAGE_STORAGE_BIT | RD::TEXTURE_USAGE_SAMPLING_BIT | RD::TEXTURE_USAGE_CAN_COPY_TO_BIT;
|
||||
tf.mipmaps = mipmaps_required;
|
||||
|
||||
rb->blur[0].texture = RD::get_singleton()->texture_create(tf, RD::TextureView());
|
||||
|
@ -3079,11 +3069,6 @@ void RasterizerSceneRD::_allocate_blur_textures(RenderBuffers *rb) {
|
|||
|
||||
RenderBuffers::Blur::Mipmap mm;
|
||||
mm.texture = RD::get_singleton()->texture_create_shared_from_slice(RD::TextureView(), rb->blur[0].texture, 0, i);
|
||||
{
|
||||
Vector<RID> fbs;
|
||||
fbs.push_back(mm.texture);
|
||||
mm.framebuffer = RD::get_singleton()->framebuffer_create(fbs);
|
||||
}
|
||||
|
||||
mm.width = base_width;
|
||||
mm.height = base_height;
|
||||
|
@ -3093,11 +3078,6 @@ void RasterizerSceneRD::_allocate_blur_textures(RenderBuffers *rb) {
|
|||
if (i > 0) {
|
||||
|
||||
mm.texture = RD::get_singleton()->texture_create_shared_from_slice(RD::TextureView(), rb->blur[1].texture, 0, i - 1);
|
||||
{
|
||||
Vector<RID> fbs;
|
||||
fbs.push_back(mm.texture);
|
||||
mm.framebuffer = RD::get_singleton()->framebuffer_create(fbs);
|
||||
}
|
||||
|
||||
rb->blur[1].mipmaps.push_back(mm);
|
||||
}
|
||||
|
@ -3424,9 +3404,9 @@ void RasterizerSceneRD::_render_buffers_post_process_and_tonemap(RID p_render_bu
|
|||
if (env->auto_exposure && rb->luminance.current.is_valid()) {
|
||||
luminance_texture = rb->luminance.current;
|
||||
}
|
||||
storage->get_effects()->gaussian_glow(rb->texture, rb->blur[0].mipmaps[i + 1].framebuffer, rb->blur[0].mipmaps[i + 1].texture, rb->blur[1].mipmaps[i].framebuffer, Vector2(1.0 / vp_w, 1.0 / vp_h), env->glow_strength, true, env->glow_hdr_luminance_cap, env->exposure, env->glow_bloom, env->glow_hdr_bleed_threshold, env->glow_hdr_bleed_scale, luminance_texture, env->auto_exp_scale);
|
||||
storage->get_effects()->gaussian_glow(rb->texture, rb->blur[0].mipmaps[i + 1].texture, rb->blur[1].mipmaps[i].texture, Size2i(vp_w, vp_h), env->glow_strength, true, env->glow_hdr_luminance_cap, env->exposure, env->glow_bloom, env->glow_hdr_bleed_threshold, env->glow_hdr_bleed_scale, luminance_texture, env->auto_exp_scale);
|
||||
} else {
|
||||
storage->get_effects()->gaussian_glow(rb->blur[1].mipmaps[i - 1].texture, rb->blur[0].mipmaps[i + 1].framebuffer, rb->blur[0].mipmaps[i + 1].texture, rb->blur[1].mipmaps[i].framebuffer, Vector2(1.0 / vp_w, 1.0 / vp_h), env->glow_strength);
|
||||
storage->get_effects()->gaussian_glow(rb->blur[1].mipmaps[i - 1].texture, rb->blur[0].mipmaps[i + 1].texture, rb->blur[1].mipmaps[i].texture, Size2i(vp_w, vp_h), env->glow_strength);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -3482,7 +3462,7 @@ void RasterizerSceneRD::_render_buffers_debug_draw(RID p_render_buffers, RID p_s
|
|||
RID shadow_atlas_texture = shadow_atlas_get_texture(p_shadow_atlas);
|
||||
Size2 rtsize = storage->render_target_get_size(rb->render_target);
|
||||
|
||||
effects->copy_to_rect(shadow_atlas_texture, storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize / 2), false, true);
|
||||
effects->copy_to_fb_rect(shadow_atlas_texture, storage->render_target_get_rd_framebuffer(rb->render_target), Rect2i(Vector2(), rtsize / 2), false, true);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3491,7 +3471,7 @@ void RasterizerSceneRD::_render_buffers_debug_draw(RID p_render_buffers, RID p_s
|
|||
RID shadow_atlas_texture = directional_shadow_get_texture();
|
||||
Size2 rtsize = storage->render_target_get_size(rb->render_target);
|
||||
|
||||
effects->copy_to_rect(shadow_atlas_texture, storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize / 2), false, true);
|
||||
effects->copy_to_fb_rect(shadow_atlas_texture, storage->render_target_get_rd_framebuffer(rb->render_target), Rect2i(Vector2(), rtsize / 2), false, true);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3499,24 +3479,24 @@ void RasterizerSceneRD::_render_buffers_debug_draw(RID p_render_buffers, RID p_s
|
|||
if (rb->luminance.current.is_valid()) {
|
||||
Size2 rtsize = storage->render_target_get_size(rb->render_target);
|
||||
|
||||
effects->copy_to_rect(rb->luminance.current, storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize / 8), false, true);
|
||||
effects->copy_to_fb_rect(rb->luminance.current, storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize / 8), false, true);
|
||||
}
|
||||
}
|
||||
|
||||
if (debug_draw == RS::VIEWPORT_DEBUG_DRAW_SSAO && rb->ssao.ao[0].is_valid()) {
|
||||
Size2 rtsize = storage->render_target_get_size(rb->render_target);
|
||||
RID ao_buf = rb->ssao.ao_full.is_valid() ? rb->ssao.ao_full : rb->ssao.ao[0];
|
||||
effects->copy_to_rect(ao_buf, storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize), false, true);
|
||||
effects->copy_to_fb_rect(ao_buf, storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize), false, true);
|
||||
}
|
||||
|
||||
if (debug_draw == RS::VIEWPORT_DEBUG_DRAW_ROUGHNESS_LIMITER && _render_buffers_get_roughness_texture(p_render_buffers).is_valid()) {
|
||||
Size2 rtsize = storage->render_target_get_size(rb->render_target);
|
||||
effects->copy_to_rect(_render_buffers_get_roughness_texture(p_render_buffers), storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize), false, true);
|
||||
effects->copy_to_fb_rect(_render_buffers_get_roughness_texture(p_render_buffers), storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize), false, true);
|
||||
}
|
||||
|
||||
if (debug_draw == RS::VIEWPORT_DEBUG_DRAW_NORMAL_BUFFER && _render_buffers_get_normal_texture(p_render_buffers).is_valid()) {
|
||||
Size2 rtsize = storage->render_target_get_size(rb->render_target);
|
||||
effects->copy_to_rect(_render_buffers_get_normal_texture(p_render_buffers), storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize));
|
||||
effects->copy_to_fb_rect(_render_buffers_get_normal_texture(p_render_buffers), storage->render_target_get_rd_framebuffer(rb->render_target), Rect2(Vector2(), rtsize), false, false);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3628,7 +3608,7 @@ void RasterizerSceneRD::render_shadow(RID p_light, RID p_shadow_atlas, int p_pas
|
|||
ERR_FAIL_COND(!light_instance);
|
||||
|
||||
Rect2i atlas_rect;
|
||||
RID atlas_fb;
|
||||
RID atlas_texture;
|
||||
|
||||
bool using_dual_paraboloid = false;
|
||||
bool using_dual_paraboloid_flip = false;
|
||||
|
@ -3702,7 +3682,7 @@ void RasterizerSceneRD::render_shadow(RID p_light, RID p_shadow_atlas, int p_pas
|
|||
ShadowMap *shadow_map = _get_shadow_map(atlas_rect.size);
|
||||
render_fb = shadow_map->fb;
|
||||
render_texture = shadow_map->depth;
|
||||
atlas_fb = directional_shadow.fb;
|
||||
atlas_texture = directional_shadow.depth;
|
||||
|
||||
} else {
|
||||
//set from shadow atlas
|
||||
|
@ -3729,7 +3709,7 @@ void RasterizerSceneRD::render_shadow(RID p_light, RID p_shadow_atlas, int p_pas
|
|||
|
||||
atlas_rect.size.width = shadow_size;
|
||||
atlas_rect.size.height = shadow_size;
|
||||
atlas_fb = shadow_atlas->fb;
|
||||
atlas_texture = shadow_atlas->depth;
|
||||
|
||||
zfar = storage->light_get_param(light_instance->light, RS::LIGHT_PARAM_RANGE);
|
||||
bias = storage->light_get_param(light_instance->light, RS::LIGHT_PARAM_SHADOW_BIAS);
|
||||
|
@ -3785,9 +3765,9 @@ void RasterizerSceneRD::render_shadow(RID p_light, RID p_shadow_atlas, int p_pas
|
|||
if (finalize_cubemap) {
|
||||
//reblit
|
||||
atlas_rect.size.height /= 2;
|
||||
storage->get_effects()->copy_cubemap_to_dp(render_texture, atlas_fb, atlas_rect, light_projection.get_z_near(), light_projection.get_z_far(), 0.0, false);
|
||||
storage->get_effects()->copy_cubemap_to_dp(render_texture, atlas_texture, atlas_rect, light_projection.get_z_near(), light_projection.get_z_far(), 0.0, false);
|
||||
atlas_rect.position.y += atlas_rect.size.height;
|
||||
storage->get_effects()->copy_cubemap_to_dp(render_texture, atlas_fb, atlas_rect, light_projection.get_z_near(), light_projection.get_z_far(), 0.0, true);
|
||||
storage->get_effects()->copy_cubemap_to_dp(render_texture, atlas_texture, atlas_rect, light_projection.get_z_near(), light_projection.get_z_far(), 0.0, true);
|
||||
}
|
||||
} else {
|
||||
//render shadow
|
||||
|
@ -3796,9 +3776,9 @@ void RasterizerSceneRD::render_shadow(RID p_light, RID p_shadow_atlas, int p_pas
|
|||
|
||||
//copy to atlas
|
||||
if (use_linear_depth) {
|
||||
storage->get_effects()->copy_to_rect_and_linearize(render_texture, atlas_fb, atlas_rect, true, znear, zfar);
|
||||
storage->get_effects()->copy_depth_to_rect_and_linearize(render_texture, atlas_texture, atlas_rect, true, znear, zfar);
|
||||
} else {
|
||||
storage->get_effects()->copy_to_rect(render_texture, atlas_fb, atlas_rect, true);
|
||||
storage->get_effects()->copy_depth_to_rect(render_texture, atlas_texture, atlas_rect, true);
|
||||
}
|
||||
|
||||
//does not work from depth to color
|
||||
|
|
|
@ -533,7 +533,6 @@ private:
|
|||
|
||||
struct DirectionalShadow {
|
||||
RID depth;
|
||||
RID fb; //for copying
|
||||
|
||||
int light_count = 0;
|
||||
int size = 0;
|
||||
|
@ -730,7 +729,6 @@ private:
|
|||
|
||||
struct Mipmap {
|
||||
RID texture;
|
||||
RID framebuffer;
|
||||
int width;
|
||||
int height;
|
||||
};
|
||||
|
|
|
@ -3914,7 +3914,6 @@ void RasterizerStorageRD::_clear_render_target(RenderTarget *rt) {
|
|||
if (rt->backbuffer.is_valid()) {
|
||||
RD::get_singleton()->free(rt->backbuffer);
|
||||
rt->backbuffer = RID();
|
||||
rt->backbuffer_fb = RID();
|
||||
for (int i = 0; i < rt->backbuffer_mipmaps.size(); i++) {
|
||||
//just erase copies, since the rest are erased by dependency
|
||||
RD::get_singleton()->free(rt->backbuffer_mipmaps[i].mipmap_copy);
|
||||
|
@ -4028,17 +4027,11 @@ void RasterizerStorageRD::_create_render_target_backbuffer(RenderTarget *rt) {
|
|||
tf.width = rt->size.width;
|
||||
tf.height = rt->size.height;
|
||||
tf.type = RD::TEXTURE_TYPE_2D;
|
||||
tf.usage_bits = RD::TEXTURE_USAGE_COLOR_ATTACHMENT_BIT | RD::TEXTURE_USAGE_SAMPLING_BIT | RD::TEXTURE_USAGE_CAN_COPY_TO_BIT;
|
||||
tf.usage_bits = RD::TEXTURE_USAGE_STORAGE_BIT | RD::TEXTURE_USAGE_SAMPLING_BIT | RD::TEXTURE_USAGE_CAN_COPY_TO_BIT;
|
||||
tf.mipmaps = mipmaps_required;
|
||||
|
||||
rt->backbuffer = RD::get_singleton()->texture_create(tf, RD::TextureView());
|
||||
|
||||
{
|
||||
Vector<RID> backbuffer_att;
|
||||
RID backbuffer_fb_tex = RD::get_singleton()->texture_create_shared_from_slice(RD::TextureView(), rt->backbuffer, 0, 0);
|
||||
backbuffer_att.push_back(backbuffer_fb_tex);
|
||||
rt->backbuffer_fb = RD::get_singleton()->framebuffer_create(backbuffer_att);
|
||||
}
|
||||
rt->backbuffer_mipmap0 = RD::get_singleton()->texture_create_shared_from_slice(RD::TextureView(), rt->backbuffer, 0, 0);
|
||||
|
||||
//create mipmaps
|
||||
for (uint32_t i = 1; i < mipmaps_required; i++) {
|
||||
|
@ -4046,9 +4039,6 @@ void RasterizerStorageRD::_create_render_target_backbuffer(RenderTarget *rt) {
|
|||
RenderTarget::BackbufferMipmap mm;
|
||||
{
|
||||
mm.mipmap = RD::get_singleton()->texture_create_shared_from_slice(RD::TextureView(), rt->backbuffer, 0, i);
|
||||
Vector<RID> mm_fb_at;
|
||||
mm_fb_at.push_back(mm.mipmap);
|
||||
mm.mipmap_fb = RD::get_singleton()->framebuffer_create(mm_fb_at);
|
||||
}
|
||||
|
||||
{
|
||||
|
@ -4060,9 +4050,6 @@ void RasterizerStorageRD::_create_render_target_backbuffer(RenderTarget *rt) {
|
|||
mmtf.mipmaps = 1;
|
||||
|
||||
mm.mipmap_copy = RD::get_singleton()->texture_create(mmtf, RD::TextureView());
|
||||
Vector<RID> mm_fb_at;
|
||||
mm_fb_at.push_back(mm.mipmap_copy);
|
||||
mm.mipmap_copy_fb = RD::get_singleton()->framebuffer_create(mm_fb_at);
|
||||
}
|
||||
|
||||
rt->backbuffer_mipmaps.push_back(mm);
|
||||
|
@ -4138,7 +4125,12 @@ RID RasterizerStorageRD::render_target_get_rd_framebuffer(RID p_render_target) {
|
|||
|
||||
return rt->framebuffer;
|
||||
}
|
||||
RID RasterizerStorageRD::render_target_get_rd_texture(RID p_render_target) {
|
||||
RenderTarget *rt = render_target_owner.getornull(p_render_target);
|
||||
ERR_FAIL_COND_V(!rt, RID());
|
||||
|
||||
return rt->color;
|
||||
}
|
||||
void RasterizerStorageRD::render_target_request_clear(RID p_render_target, const Color &p_clear_color) {
|
||||
RenderTarget *rt = render_target_owner.getornull(p_render_target);
|
||||
ERR_FAIL_COND(!rt);
|
||||
|
@ -4188,27 +4180,25 @@ void RasterizerStorageRD::render_target_copy_to_back_buffer(RID p_render_target,
|
|||
}
|
||||
|
||||
Rect2i region = p_region;
|
||||
Rect2 blur_region;
|
||||
if (region == Rect2i()) {
|
||||
region.size = rt->size;
|
||||
} else {
|
||||
blur_region = region;
|
||||
blur_region.position /= rt->size;
|
||||
blur_region.size /= rt->size;
|
||||
}
|
||||
|
||||
//single texture copy for backbuffer
|
||||
RD::get_singleton()->texture_copy(rt->color, rt->backbuffer, Vector3(region.position.x, region.position.y, 0), Vector3(region.position.x, region.position.y, 0), Vector3(region.size.x, region.size.y, 1), 0, 0, 0, 0, true);
|
||||
RD::get_singleton()->texture_copy(rt->color, rt->backbuffer_mipmap0, Vector3(region.position.x, region.position.y, 0), Vector3(region.position.x, region.position.y, 0), Vector3(region.size.x, region.size.y, 1), 0, 0, 0, 0, true);
|
||||
//effects.copy(rt->color, rt->backbuffer_fb, blur_region);
|
||||
|
||||
//then mipmap blur
|
||||
RID prev_texture = rt->color; //use color, not backbuffer, as bb has mipmaps.
|
||||
Vector2 pixel_size = Vector2(1.0 / rt->size.width, 1.0 / rt->size.height);
|
||||
|
||||
for (int i = 0; i < rt->backbuffer_mipmaps.size(); i++) {
|
||||
pixel_size *= 2.0; //go halfway
|
||||
region.position.x >>= 1;
|
||||
region.position.y >>= 1;
|
||||
region.size.x = MAX(1, region.size.x >> 1);
|
||||
region.size.y = MAX(1, region.size.y >> 1);
|
||||
|
||||
const RenderTarget::BackbufferMipmap &mm = rt->backbuffer_mipmaps[i];
|
||||
effects.gaussian_blur(prev_texture, mm.mipmap_copy_fb, mm.mipmap_copy, mm.mipmap_fb, pixel_size, blur_region);
|
||||
effects.gaussian_blur(prev_texture, mm.mipmap, mm.mipmap_copy, region, true);
|
||||
prev_texture = mm.mipmap;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -463,13 +463,11 @@ private:
|
|||
bool flags[RENDER_TARGET_FLAG_MAX];
|
||||
|
||||
RID backbuffer; //used for effects
|
||||
RID backbuffer_fb;
|
||||
RID backbuffer_mipmap0;
|
||||
|
||||
struct BackbufferMipmap {
|
||||
RID mipmap;
|
||||
RID mipmap_fb;
|
||||
RID mipmap_copy;
|
||||
RID mipmap_copy_fb;
|
||||
};
|
||||
|
||||
Vector<BackbufferMipmap> backbuffer_mipmaps;
|
||||
|
@ -1105,6 +1103,7 @@ public:
|
|||
|
||||
Size2 render_target_get_size(RID p_render_target);
|
||||
RID render_target_get_rd_framebuffer(RID p_render_target);
|
||||
RID render_target_get_rd_texture(RID p_render_target);
|
||||
|
||||
RS::InstanceType get_base_type(RID p_rid) const;
|
||||
|
||||
|
|
|
@ -5,14 +5,15 @@ Import("env")
|
|||
if "RD_GLSL" in env["BUILDERS"]:
|
||||
env.RD_GLSL("canvas.glsl")
|
||||
env.RD_GLSL("canvas_occlusion.glsl")
|
||||
env.RD_GLSL("blur.glsl")
|
||||
env.RD_GLSL("copy.glsl")
|
||||
env.RD_GLSL("copy_to_fb.glsl")
|
||||
env.RD_GLSL("cubemap_roughness.glsl")
|
||||
env.RD_GLSL("cubemap_downsampler.glsl")
|
||||
env.RD_GLSL("cubemap_filter.glsl")
|
||||
env.RD_GLSL("scene_high_end.glsl")
|
||||
env.RD_GLSL("sky.glsl")
|
||||
env.RD_GLSL("tonemap.glsl")
|
||||
env.RD_GLSL("copy.glsl")
|
||||
env.RD_GLSL("cube_to_dp.glsl")
|
||||
env.RD_GLSL("giprobe.glsl")
|
||||
env.RD_GLSL("giprobe_debug.glsl")
|
||||
env.RD_GLSL("giprobe_sdf.glsl")
|
||||
|
|
|
@ -1,301 +0,0 @@
|
|||
/* clang-format off */
|
||||
[vertex]
|
||||
|
||||
#version 450
|
||||
|
||||
VERSION_DEFINES
|
||||
|
||||
#include "blur_inc.glsl"
|
||||
|
||||
layout(location = 0) out vec2 uv_interp;
|
||||
/* clang-format on */
|
||||
|
||||
void main() {
|
||||
|
||||
vec2 base_arr[4] = vec2[](vec2(0.0, 0.0), vec2(0.0, 1.0), vec2(1.0, 1.0), vec2(1.0, 0.0));
|
||||
uv_interp = base_arr[gl_VertexIndex];
|
||||
|
||||
if (bool(blur.flags & FLAG_USE_BLUR_SECTION)) {
|
||||
uv_interp = blur.section.xy + uv_interp * blur.section.zw;
|
||||
}
|
||||
|
||||
gl_Position = vec4(uv_interp * 2.0 - 1.0, 0.0, 1.0);
|
||||
|
||||
if (bool(blur.flags & FLAG_FLIP_Y)) {
|
||||
uv_interp.y = 1.0 - uv_interp.y;
|
||||
}
|
||||
}
|
||||
|
||||
/* clang-format off */
|
||||
[fragment]
|
||||
|
||||
#version 450
|
||||
|
||||
VERSION_DEFINES
|
||||
|
||||
#include "blur_inc.glsl"
|
||||
|
||||
layout(location = 0) in vec2 uv_interp;
|
||||
/* clang-format on */
|
||||
|
||||
layout(set = 0, binding = 0) uniform sampler2D source_color;
|
||||
|
||||
#ifdef MODE_SSAO_MERGE
|
||||
layout(set = 1, binding = 0) uniform sampler2D source_ssao;
|
||||
#endif
|
||||
|
||||
#ifdef GLOW_USE_AUTO_EXPOSURE
|
||||
layout(set = 1, binding = 0) uniform sampler2D source_auto_exposure;
|
||||
#endif
|
||||
|
||||
layout(location = 0) out vec4 frag_color;
|
||||
|
||||
//DOF
|
||||
#if defined(MODE_DOF_FAR_BLUR) || defined(MODE_DOF_NEAR_BLUR)
|
||||
|
||||
layout(set = 1, binding = 0) uniform sampler2D dof_source_depth;
|
||||
|
||||
#ifdef DOF_NEAR_BLUR_MERGE
|
||||
layout(set = 2, binding = 0) uniform sampler2D source_dof_original;
|
||||
#endif
|
||||
|
||||
#ifdef DOF_QUALITY_LOW
|
||||
const int dof_kernel_size = 5;
|
||||
const int dof_kernel_from = 2;
|
||||
const float dof_kernel[5] = float[](0.153388, 0.221461, 0.250301, 0.221461, 0.153388);
|
||||
#endif
|
||||
|
||||
#ifdef DOF_QUALITY_MEDIUM
|
||||
const int dof_kernel_size = 11;
|
||||
const int dof_kernel_from = 5;
|
||||
const float dof_kernel[11] = float[](0.055037, 0.072806, 0.090506, 0.105726, 0.116061, 0.119726, 0.116061, 0.105726, 0.090506, 0.072806, 0.055037);
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef DOF_QUALITY_HIGH
|
||||
const int dof_kernel_size = 21;
|
||||
const int dof_kernel_from = 10;
|
||||
const float dof_kernel[21] = float[](0.028174, 0.032676, 0.037311, 0.041944, 0.046421, 0.050582, 0.054261, 0.057307, 0.059587, 0.060998, 0.061476, 0.060998, 0.059587, 0.057307, 0.054261, 0.050582, 0.046421, 0.041944, 0.037311, 0.032676, 0.028174);
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
void main() {
|
||||
|
||||
#ifdef MODE_MIPMAP
|
||||
|
||||
vec2 pix_size = blur.pixel_size;
|
||||
vec4 color = texture(source_color, uv_interp + vec2(-0.5, -0.5) * pix_size);
|
||||
color += texture(source_color, uv_interp + vec2(0.5, -0.5) * pix_size);
|
||||
color += texture(source_color, uv_interp + vec2(0.5, 0.5) * pix_size);
|
||||
color += texture(source_color, uv_interp + vec2(-0.5, 0.5) * pix_size);
|
||||
frag_color = color / 4.0;
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef MODE_GAUSSIAN_BLUR
|
||||
|
||||
//Simpler blur uses SIGMA2 for the gaussian kernel for a stronger effect
|
||||
|
||||
if (bool(blur.flags & FLAG_HORIZONTAL)) {
|
||||
|
||||
vec2 pix_size = blur.pixel_size;
|
||||
pix_size *= 0.5; //reading from larger buffer, so use more samples
|
||||
vec4 color = texture(source_color, uv_interp + vec2(0.0, 0.0) * pix_size) * 0.214607;
|
||||
color += texture(source_color, uv_interp + vec2(1.0, 0.0) * pix_size) * 0.189879;
|
||||
color += texture(source_color, uv_interp + vec2(2.0, 0.0) * pix_size) * 0.131514;
|
||||
color += texture(source_color, uv_interp + vec2(3.0, 0.0) * pix_size) * 0.071303;
|
||||
color += texture(source_color, uv_interp + vec2(-1.0, 0.0) * pix_size) * 0.189879;
|
||||
color += texture(source_color, uv_interp + vec2(-2.0, 0.0) * pix_size) * 0.131514;
|
||||
color += texture(source_color, uv_interp + vec2(-3.0, 0.0) * pix_size) * 0.071303;
|
||||
frag_color = color;
|
||||
} else {
|
||||
|
||||
vec2 pix_size = blur.pixel_size;
|
||||
vec4 color = texture(source_color, uv_interp + vec2(0.0, 0.0) * pix_size) * 0.38774;
|
||||
color += texture(source_color, uv_interp + vec2(0.0, 1.0) * pix_size) * 0.24477;
|
||||
color += texture(source_color, uv_interp + vec2(0.0, 2.0) * pix_size) * 0.06136;
|
||||
color += texture(source_color, uv_interp + vec2(0.0, -1.0) * pix_size) * 0.24477;
|
||||
color += texture(source_color, uv_interp + vec2(0.0, -2.0) * pix_size) * 0.06136;
|
||||
frag_color = color;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef MODE_GAUSSIAN_GLOW
|
||||
|
||||
//Glow uses larger sigma 1 for a more rounded blur effect
|
||||
|
||||
#define GLOW_ADD(m_ofs, m_mult) \
|
||||
{ \
|
||||
vec2 ofs = uv_interp + m_ofs * pix_size; \
|
||||
vec4 c = texture(source_color, ofs) * m_mult; \
|
||||
if (any(lessThan(ofs, vec2(0.0))) || any(greaterThan(ofs, vec2(1.0)))) { \
|
||||
c *= 0.0; \
|
||||
} \
|
||||
color += c; \
|
||||
}
|
||||
|
||||
if (bool(blur.flags & FLAG_HORIZONTAL)) {
|
||||
|
||||
vec2 pix_size = blur.pixel_size;
|
||||
pix_size *= 0.5; //reading from larger buffer, so use more samples
|
||||
vec4 color = texture(source_color, uv_interp + vec2(0.0, 0.0) * pix_size) * 0.174938;
|
||||
GLOW_ADD(vec2(1.0, 0.0), 0.165569);
|
||||
GLOW_ADD(vec2(2.0, 0.0), 0.140367);
|
||||
GLOW_ADD(vec2(3.0, 0.0), 0.106595);
|
||||
GLOW_ADD(vec2(-1.0, 0.0), 0.165569);
|
||||
GLOW_ADD(vec2(-2.0, 0.0), 0.140367);
|
||||
GLOW_ADD(vec2(-3.0, 0.0), 0.106595);
|
||||
color *= blur.glow_strength;
|
||||
frag_color = color;
|
||||
} else {
|
||||
|
||||
vec2 pix_size = blur.pixel_size;
|
||||
vec4 color = texture(source_color, uv_interp + vec2(0.0, 0.0) * pix_size) * 0.288713;
|
||||
GLOW_ADD(vec2(0.0, 1.0), 0.233062);
|
||||
GLOW_ADD(vec2(0.0, 2.0), 0.122581);
|
||||
GLOW_ADD(vec2(0.0, -1.0), 0.233062);
|
||||
GLOW_ADD(vec2(0.0, -2.0), 0.122581);
|
||||
color *= blur.glow_strength;
|
||||
frag_color = color;
|
||||
}
|
||||
|
||||
#undef GLOW_ADD
|
||||
|
||||
if (bool(blur.flags & FLAG_GLOW_FIRST_PASS)) {
|
||||
#ifdef GLOW_USE_AUTO_EXPOSURE
|
||||
|
||||
frag_color /= texelFetch(source_auto_exposure, ivec2(0, 0), 0).r / blur.glow_auto_exposure_grey;
|
||||
#endif
|
||||
frag_color *= blur.glow_exposure;
|
||||
|
||||
float luminance = max(frag_color.r, max(frag_color.g, frag_color.b));
|
||||
float feedback = max(smoothstep(blur.glow_hdr_threshold, blur.glow_hdr_threshold + blur.glow_hdr_scale, luminance), blur.glow_bloom);
|
||||
|
||||
frag_color = min(frag_color * feedback, vec4(blur.glow_luminance_cap));
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef MODE_DOF_FAR_BLUR
|
||||
|
||||
vec4 color_accum = vec4(0.0);
|
||||
|
||||
float depth = texture(dof_source_depth, uv_interp, 0.0).r;
|
||||
depth = depth * 2.0 - 1.0;
|
||||
|
||||
if (bool(blur.flags & FLAG_USE_ORTHOGONAL_PROJECTION)) {
|
||||
depth = ((depth + (blur.camera_z_far + blur.camera_z_near) / (blur.camera_z_far - blur.camera_z_near)) * (blur.camera_z_far - blur.camera_z_near)) / 2.0;
|
||||
} else {
|
||||
depth = 2.0 * blur.camera_z_near * blur.camera_z_far / (blur.camera_z_far + blur.camera_z_near - depth * (blur.camera_z_far - blur.camera_z_near));
|
||||
}
|
||||
|
||||
float amount = smoothstep(blur.dof_begin, blur.dof_end, depth);
|
||||
float k_accum = 0.0;
|
||||
|
||||
for (int i = 0; i < dof_kernel_size; i++) {
|
||||
|
||||
int int_ofs = i - dof_kernel_from;
|
||||
vec2 tap_uv = uv_interp + blur.dof_dir * float(int_ofs) * amount * blur.dof_radius;
|
||||
|
||||
float tap_k = dof_kernel[i];
|
||||
|
||||
float tap_depth = texture(dof_source_depth, tap_uv, 0.0).r;
|
||||
tap_depth = tap_depth * 2.0 - 1.0;
|
||||
|
||||
if (bool(blur.flags & FLAG_USE_ORTHOGONAL_PROJECTION)) {
|
||||
|
||||
tap_depth = ((tap_depth + (blur.camera_z_far + blur.camera_z_near) / (blur.camera_z_far - blur.camera_z_near)) * (blur.camera_z_far - blur.camera_z_near)) / 2.0;
|
||||
} else {
|
||||
tap_depth = 2.0 * blur.camera_z_near * blur.camera_z_far / (blur.camera_z_far + blur.camera_z_near - tap_depth * (blur.camera_z_far - blur.camera_z_near));
|
||||
}
|
||||
|
||||
float tap_amount = mix(smoothstep(blur.dof_begin, blur.dof_end, tap_depth), 1.0, int_ofs == 0);
|
||||
tap_amount *= tap_amount * tap_amount; //prevent undesired glow effect
|
||||
|
||||
vec4 tap_color = texture(source_color, tap_uv, 0.0) * tap_k;
|
||||
|
||||
k_accum += tap_k * tap_amount;
|
||||
color_accum += tap_color * tap_amount;
|
||||
}
|
||||
|
||||
if (k_accum > 0.0) {
|
||||
color_accum /= k_accum;
|
||||
}
|
||||
|
||||
frag_color = color_accum; ///k_accum;
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef MODE_DOF_NEAR_BLUR
|
||||
|
||||
vec4 color_accum = vec4(0.0);
|
||||
|
||||
float max_accum = 0.0;
|
||||
|
||||
for (int i = 0; i < dof_kernel_size; i++) {
|
||||
|
||||
int int_ofs = i - dof_kernel_from;
|
||||
vec2 tap_uv = uv_interp + blur.dof_dir * float(int_ofs) * blur.dof_radius;
|
||||
float ofs_influence = max(0.0, 1.0 - float(abs(int_ofs)) / float(dof_kernel_from));
|
||||
|
||||
float tap_k = dof_kernel[i];
|
||||
|
||||
vec4 tap_color = texture(source_color, tap_uv, 0.0);
|
||||
|
||||
float tap_depth = texture(dof_source_depth, tap_uv, 0.0).r;
|
||||
tap_depth = tap_depth * 2.0 - 1.0;
|
||||
if (bool(blur.flags & FLAG_USE_ORTHOGONAL_PROJECTION)) {
|
||||
|
||||
tap_depth = ((tap_depth + (blur.camera_z_far + blur.camera_z_near) / (blur.camera_z_far - blur.camera_z_near)) * (blur.camera_z_far - blur.camera_z_near)) / 2.0;
|
||||
} else {
|
||||
tap_depth = 2.0 * blur.camera_z_near * blur.camera_z_far / (blur.camera_z_far + blur.camera_z_near - tap_depth * (blur.camera_z_far - blur.camera_z_near));
|
||||
}
|
||||
float tap_amount = 1.0 - smoothstep(blur.dof_end, blur.dof_begin, tap_depth);
|
||||
tap_amount *= tap_amount * tap_amount; //prevent undesired glow effect
|
||||
|
||||
if (bool(blur.flags & FLAG_DOF_NEAR_FIRST_TAP)) {
|
||||
tap_color.a = 1.0 - smoothstep(blur.dof_end, blur.dof_begin, tap_depth);
|
||||
}
|
||||
|
||||
max_accum = max(max_accum, tap_amount * ofs_influence);
|
||||
|
||||
color_accum += tap_color * tap_k;
|
||||
}
|
||||
|
||||
color_accum.a = max(color_accum.a, sqrt(max_accum));
|
||||
|
||||
#ifdef DOF_NEAR_BLUR_MERGE
|
||||
{
|
||||
vec4 original = texture(source_dof_original, uv_interp, 0.0);
|
||||
color_accum = mix(original, color_accum, color_accum.a);
|
||||
}
|
||||
#endif
|
||||
|
||||
if (bool(blur.flags & FLAG_DOF_NEAR_FIRST_TAP)) {
|
||||
frag_color = color_accum;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef MODE_SIMPLE_COPY
|
||||
vec4 color = texture(source_color, uv_interp, 0.0);
|
||||
if (bool(blur.flags & FLAG_COPY_FORCE_LUMINANCE)) {
|
||||
color.rgb = vec3(max(max(color.r, color.g), color.b));
|
||||
}
|
||||
frag_color = color;
|
||||
#endif
|
||||
|
||||
#ifdef MODE_LINEARIZE_DEPTH_COPY
|
||||
float depth = texture(source_color, uv_interp, 0.0).r;
|
||||
depth = depth * 2.0 - 1.0;
|
||||
depth = 2.0 * blur.camera_z_near * blur.camera_z_far / (blur.camera_z_far + blur.camera_z_near - depth * (blur.camera_z_far - blur.camera_z_near));
|
||||
frag_color = vec4(depth / blur.camera_z_far);
|
||||
#endif
|
||||
|
||||
#ifdef MODE_SSAO_MERGE
|
||||
vec4 color = texture(source_color, uv_interp, 0.0);
|
||||
float ssao = texture(source_ssao, uv_interp, 0.0).r;
|
||||
frag_color = vec4(mix(color.rgb, color.rgb * mix(blur.ssao_color.rgb, vec3(1.0), ssao), color.a), 1.0);
|
||||
|
||||
#endif
|
||||
}
|
|
@ -1,35 +0,0 @@
|
|||
#define FLAG_HORIZONTAL (1 << 0)
|
||||
#define FLAG_USE_BLUR_SECTION (1 << 1)
|
||||
#define FLAG_USE_ORTHOGONAL_PROJECTION (1 << 2)
|
||||
#define FLAG_DOF_NEAR_FIRST_TAP (1 << 3)
|
||||
#define FLAG_GLOW_FIRST_PASS (1 << 4)
|
||||
#define FLAG_FLIP_Y (1 << 5)
|
||||
#define FLAG_COPY_FORCE_LUMINANCE (1 << 6)
|
||||
|
||||
layout(push_constant, binding = 1, std430) uniform Blur {
|
||||
vec4 section;
|
||||
vec2 pixel_size;
|
||||
uint flags;
|
||||
uint pad;
|
||||
// Glow.
|
||||
float glow_strength;
|
||||
float glow_bloom;
|
||||
float glow_hdr_threshold;
|
||||
float glow_hdr_scale;
|
||||
float glow_exposure;
|
||||
float glow_white;
|
||||
float glow_luminance_cap;
|
||||
float glow_auto_exposure_grey;
|
||||
// DOF.
|
||||
float dof_begin;
|
||||
float dof_end;
|
||||
float dof_radius;
|
||||
float dof_pad;
|
||||
|
||||
vec2 dof_dir;
|
||||
float camera_z_far;
|
||||
float camera_z_near;
|
||||
|
||||
vec4 ssao_color;
|
||||
}
|
||||
blur;
|
|
@ -1,87 +1,220 @@
|
|||
/* clang-format off */
|
||||
[vertex]
|
||||
[compute]
|
||||
|
||||
#version 450
|
||||
|
||||
VERSION_DEFINES
|
||||
|
||||
layout(location = 0) out vec2 uv_interp;
|
||||
layout(local_size_x = 8, local_size_y = 8, local_size_z = 1) in;
|
||||
/* clang-format on */
|
||||
|
||||
void main() {
|
||||
#define FLAG_HORIZONTAL (1 << 0)
|
||||
#define FLAG_USE_BLUR_SECTION (1 << 1)
|
||||
#define FLAG_USE_ORTHOGONAL_PROJECTION (1 << 2)
|
||||
#define FLAG_DOF_NEAR_FIRST_TAP (1 << 3)
|
||||
#define FLAG_GLOW_FIRST_PASS (1 << 4)
|
||||
#define FLAG_FLIP_Y (1 << 5)
|
||||
#define FLAG_FORCE_LUMINANCE (1 << 6)
|
||||
#define FLAG_COPY_ALL_SOURCE (1 << 7)
|
||||
|
||||
vec2 base_arr[4] = vec2[](vec2(0.0, 0.0), vec2(0.0, 1.0), vec2(1.0, 1.0), vec2(1.0, 0.0));
|
||||
uv_interp = base_arr[gl_VertexIndex];
|
||||
layout(push_constant, binding = 1, std430) uniform Params {
|
||||
ivec4 section;
|
||||
ivec2 target;
|
||||
uint flags;
|
||||
uint pad;
|
||||
// Glow.
|
||||
float glow_strength;
|
||||
float glow_bloom;
|
||||
float glow_hdr_threshold;
|
||||
float glow_hdr_scale;
|
||||
|
||||
gl_Position = vec4(uv_interp * 2.0 - 1.0, 0.0, 1.0);
|
||||
}
|
||||
|
||||
/* clang-format off */
|
||||
[fragment]
|
||||
|
||||
#version 450
|
||||
|
||||
VERSION_DEFINES
|
||||
|
||||
layout(location = 0) in vec2 uv_interp;
|
||||
/* clang-format on */
|
||||
|
||||
#ifdef MODE_CUBE_TO_DP
|
||||
|
||||
layout(set = 0, binding = 0) uniform samplerCube source_cube;
|
||||
|
||||
layout(push_constant, binding = 0, std430) uniform Params {
|
||||
float bias;
|
||||
float z_far;
|
||||
float z_near;
|
||||
bool z_flip;
|
||||
float glow_exposure;
|
||||
float glow_white;
|
||||
float glow_luminance_cap;
|
||||
float glow_auto_exposure_grey;
|
||||
// DOF.
|
||||
float camera_z_far;
|
||||
float camera_z_near;
|
||||
uvec2 pad2;
|
||||
}
|
||||
params;
|
||||
|
||||
layout(location = 0) out float depth_buffer;
|
||||
layout(set = 0, binding = 0) uniform sampler2D source_color;
|
||||
|
||||
#ifdef GLOW_USE_AUTO_EXPOSURE
|
||||
layout(set = 1, binding = 0) uniform sampler2D source_auto_exposure;
|
||||
#endif
|
||||
|
||||
#if defined(MODE_LINEARIZE_DEPTH_COPY) || defined(MODE_SIMPLE_COPY_DEPTH)
|
||||
layout(r32f, set = 3, binding = 0) uniform restrict writeonly image2D dest_buffer;
|
||||
#elif defined(DST_IMAGE_8BIT)
|
||||
layout(rgba8, set = 3, binding = 0) uniform restrict writeonly image2D dest_buffer;
|
||||
#else
|
||||
layout(rgba32f, set = 3, binding = 0) uniform restrict writeonly image2D dest_buffer;
|
||||
#endif
|
||||
|
||||
void main() {
|
||||
|
||||
#ifdef MODE_CUBE_TO_DP
|
||||
|
||||
vec3 normal = vec3(uv_interp * 2.0 - 1.0, 0.0);
|
||||
|
||||
normal.z = 0.5 - 0.5 * ((normal.x * normal.x) + (normal.y * normal.y));
|
||||
normal = normalize(normal);
|
||||
|
||||
normal.y = -normal.y; //needs to be flipped to match projection matrix
|
||||
if (!params.z_flip) {
|
||||
normal.z = -normal.z;
|
||||
// Pixel being shaded
|
||||
ivec2 pos = ivec2(gl_GlobalInvocationID.xy);
|
||||
if (any(greaterThan(pos, params.section.zw))) { //too large, do nothing
|
||||
return;
|
||||
}
|
||||
|
||||
float depth = texture(source_cube, normal).r;
|
||||
depth_buffer = depth;
|
||||
#ifdef MODE_MIPMAP
|
||||
|
||||
// absolute values for direction cosines, bigger value equals closer to basis axis
|
||||
vec3 unorm = abs(normal);
|
||||
ivec2 base_pos = (pos + params.section.xy) << 1;
|
||||
vec4 color = texelFetch(source_color, base_pos, 0);
|
||||
color += texelFetch(source_color, base_pos + ivec2(0, 1), 0);
|
||||
color += texelFetch(source_color, base_pos + ivec2(1, 0), 0);
|
||||
color += texelFetch(source_color, base_pos + ivec2(1, 1), 0);
|
||||
color /= 4.0;
|
||||
|
||||
if ((unorm.x >= unorm.y) && (unorm.x >= unorm.z)) {
|
||||
// x code
|
||||
unorm = normal.x > 0.0 ? vec3(1.0, 0.0, 0.0) : vec3(-1.0, 0.0, 0.0);
|
||||
} else if ((unorm.y > unorm.x) && (unorm.y >= unorm.z)) {
|
||||
// y code
|
||||
unorm = normal.y > 0.0 ? vec3(0.0, 1.0, 0.0) : vec3(0.0, -1.0, 0.0);
|
||||
} else if ((unorm.z > unorm.x) && (unorm.z > unorm.y)) {
|
||||
// z code
|
||||
unorm = normal.z > 0.0 ? vec3(0.0, 0.0, 1.0) : vec3(0.0, 0.0, -1.0);
|
||||
imageStore(dest_buffer, pos + params.target, color);
|
||||
#endif
|
||||
|
||||
#ifdef MODE_GAUSSIAN_BLUR
|
||||
|
||||
//Simpler blur uses SIGMA2 for the gaussian kernel for a stronger effect
|
||||
|
||||
if (bool(params.flags & FLAG_HORIZONTAL)) {
|
||||
|
||||
ivec2 base_pos = (pos + params.section.xy) << 1;
|
||||
vec4 color = texelFetch(source_color, base_pos + ivec2(0, 0), 0) * 0.214607;
|
||||
color += texelFetch(source_color, base_pos + ivec2(1, 0), 0) * 0.189879;
|
||||
color += texelFetch(source_color, base_pos + ivec2(2, 0), 0) * 0.131514;
|
||||
color += texelFetch(source_color, base_pos + ivec2(3, 0), 0) * 0.071303;
|
||||
color += texelFetch(source_color, base_pos + ivec2(-1, 0), 0) * 0.189879;
|
||||
color += texelFetch(source_color, base_pos + ivec2(-2, 0), 0) * 0.131514;
|
||||
color += texelFetch(source_color, base_pos + ivec2(-3, 0), 0) * 0.071303;
|
||||
imageStore(dest_buffer, pos + params.target, color);
|
||||
} else {
|
||||
// oh-no we messed up code
|
||||
// has to be
|
||||
unorm = vec3(1.0, 0.0, 0.0);
|
||||
|
||||
ivec2 base_pos = (pos + params.section.xy);
|
||||
vec4 color = texelFetch(source_color, base_pos + ivec2(0, 0), 0) * 0.38774;
|
||||
color += texelFetch(source_color, base_pos + ivec2(0, 1), 0) * 0.24477;
|
||||
color += texelFetch(source_color, base_pos + ivec2(0, 2), 0) * 0.06136;
|
||||
color += texelFetch(source_color, base_pos + ivec2(0, -1), 0) * 0.24477;
|
||||
color += texelFetch(source_color, base_pos + ivec2(0, -2), 0) * 0.06136;
|
||||
imageStore(dest_buffer, pos + params.target, color);
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef MODE_GAUSSIAN_GLOW
|
||||
|
||||
//Glow uses larger sigma 1 for a more rounded blur effect
|
||||
|
||||
#define GLOW_ADD(m_ofs, m_mult) \
|
||||
{ \
|
||||
ivec2 ofs = base_pos + m_ofs; \
|
||||
if (all(greaterThanEqual(ofs, section_begin)) && all(lessThan(ofs, section_end))) { \
|
||||
color += texelFetch(source_color, ofs, 0) * m_mult; \
|
||||
} \
|
||||
}
|
||||
|
||||
float depth_fix = 1.0 / dot(normal, unorm);
|
||||
vec4 color = vec4(0.0);
|
||||
|
||||
depth = 2.0 * depth - 1.0;
|
||||
float linear_depth = 2.0 * params.z_near * params.z_far / (params.z_far + params.z_near - depth * (params.z_far - params.z_near));
|
||||
depth_buffer = (linear_depth * depth_fix) / params.z_far;
|
||||
if (bool(params.flags & FLAG_HORIZONTAL)) {
|
||||
|
||||
ivec2 base_pos = (pos + params.section.xy) << 1;
|
||||
ivec2 section_begin = params.section.xy << 1;
|
||||
ivec2 section_end = section_begin + (params.section.zw << 1);
|
||||
|
||||
GLOW_ADD(ivec2(0, 0), 0.174938);
|
||||
GLOW_ADD(ivec2(1, 0), 0.165569);
|
||||
GLOW_ADD(ivec2(2, 0), 0.140367);
|
||||
GLOW_ADD(ivec2(3, 0), 0.106595);
|
||||
GLOW_ADD(ivec2(-1, 0), 0.165569);
|
||||
GLOW_ADD(ivec2(-2, 0), 0.140367);
|
||||
GLOW_ADD(ivec2(-3, 0), 0.106595);
|
||||
color *= params.glow_strength;
|
||||
} else {
|
||||
|
||||
ivec2 base_pos = pos + params.section.xy;
|
||||
ivec2 section_begin = params.section.xy;
|
||||
ivec2 section_end = section_begin + params.section.zw;
|
||||
|
||||
GLOW_ADD(ivec2(0, 0), 0.288713);
|
||||
GLOW_ADD(ivec2(0, 1), 0.233062);
|
||||
GLOW_ADD(ivec2(0, 2), 0.122581);
|
||||
GLOW_ADD(ivec2(0, -1), 0.233062);
|
||||
GLOW_ADD(ivec2(0, -2), 0.122581);
|
||||
color *= params.glow_strength;
|
||||
}
|
||||
|
||||
#undef GLOW_ADD
|
||||
|
||||
if (bool(params.flags & FLAG_GLOW_FIRST_PASS)) {
|
||||
#ifdef GLOW_USE_AUTO_EXPOSURE
|
||||
|
||||
color /= texelFetch(source_auto_exposure, ivec2(0, 0), 0).r / params.glow_auto_exposure_grey;
|
||||
#endif
|
||||
color *= params.glow_exposure;
|
||||
|
||||
float luminance = max(color.r, max(color.g, color.b));
|
||||
float feedback = max(smoothstep(params.glow_hdr_threshold, params.glow_hdr_threshold + params.glow_hdr_scale, luminance), params.glow_bloom);
|
||||
|
||||
color = min(color * feedback, vec4(params.glow_luminance_cap));
|
||||
}
|
||||
|
||||
imageStore(dest_buffer, pos + params.target, color);
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef MODE_SIMPLE_COPY
|
||||
|
||||
vec4 color;
|
||||
if (bool(params.flags & FLAG_COPY_ALL_SOURCE)) {
|
||||
vec2 uv = vec2(pos) / vec2(params.section.zw);
|
||||
if (bool(params.flags & FLAG_FLIP_Y)) {
|
||||
uv.y = 1.0 - uv.y;
|
||||
}
|
||||
color = textureLod(source_color, uv, 0.0);
|
||||
|
||||
if (bool(params.flags & FLAG_FORCE_LUMINANCE)) {
|
||||
color.rgb = vec3(max(max(color.r, color.g), color.b));
|
||||
}
|
||||
imageStore(dest_buffer, pos + params.target, color);
|
||||
|
||||
} else {
|
||||
color = texelFetch(source_color, pos + params.section.xy, 0);
|
||||
|
||||
if (bool(params.flags & FLAG_FORCE_LUMINANCE)) {
|
||||
color.rgb = vec3(max(max(color.r, color.g), color.b));
|
||||
}
|
||||
|
||||
if (bool(params.flags & FLAG_FLIP_Y)) {
|
||||
pos.y = params.section.w - pos.y - 1;
|
||||
}
|
||||
|
||||
imageStore(dest_buffer, pos + params.target, color);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef MODE_SIMPLE_COPY_DEPTH
|
||||
|
||||
vec4 color = texelFetch(source_color, pos + params.section.xy, 0);
|
||||
|
||||
if (bool(params.flags & FLAG_FLIP_Y)) {
|
||||
pos.y = params.section.w - pos.y - 1;
|
||||
}
|
||||
|
||||
imageStore(dest_buffer, pos + params.target, vec4(color.r));
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef MODE_LINEARIZE_DEPTH_COPY
|
||||
|
||||
float depth = texelFetch(source_color, pos + params.section.xy, 0).r;
|
||||
depth = depth * 2.0 - 1.0;
|
||||
depth = 2.0 * params.camera_z_near * params.camera_z_far / (params.camera_z_far + params.camera_z_near - depth * (params.camera_z_far - params.camera_z_near));
|
||||
vec4 color = vec4(depth / params.camera_z_far);
|
||||
|
||||
if (bool(params.flags & FLAG_FLIP_Y)) {
|
||||
pos.y = params.section.w - pos.y - 1;
|
||||
}
|
||||
|
||||
imageStore(dest_buffer, pos + params.target, color);
|
||||
#endif
|
||||
}
|
||||
|
|
|
@ -0,0 +1,68 @@
|
|||
/* clang-format off */
|
||||
[vertex]
|
||||
|
||||
#version 450
|
||||
|
||||
VERSION_DEFINES
|
||||
|
||||
layout(location = 0) out vec2 uv_interp;
|
||||
/* clang-format on */
|
||||
|
||||
layout(push_constant, binding = 1, std430) uniform Params {
|
||||
vec4 section;
|
||||
vec2 pixel_size;
|
||||
bool flip_y;
|
||||
bool use_section;
|
||||
bool force_luminance;
|
||||
uint pad[3];
|
||||
}
|
||||
params;
|
||||
|
||||
void main() {
|
||||
|
||||
vec2 base_arr[4] = vec2[](vec2(0.0, 0.0), vec2(0.0, 1.0), vec2(1.0, 1.0), vec2(1.0, 0.0));
|
||||
uv_interp = base_arr[gl_VertexIndex];
|
||||
|
||||
if (params.use_section) {
|
||||
uv_interp = params.section.xy + uv_interp * params.section.zw;
|
||||
}
|
||||
|
||||
gl_Position = vec4(uv_interp * 2.0 - 1.0, 0.0, 1.0);
|
||||
|
||||
if (params.flip_y) {
|
||||
uv_interp.y = 1.0 - uv_interp.y;
|
||||
}
|
||||
}
|
||||
|
||||
/* clang-format off */
|
||||
[fragment]
|
||||
|
||||
#version 450
|
||||
|
||||
VERSION_DEFINES
|
||||
|
||||
layout(push_constant, binding = 1, std430) uniform Params {
|
||||
vec4 section;
|
||||
vec2 pixel_size;
|
||||
bool flip_y;
|
||||
bool use_section;
|
||||
bool force_luminance;
|
||||
uint pad[3];
|
||||
} params;
|
||||
|
||||
|
||||
layout(location = 0) in vec2 uv_interp;
|
||||
/* clang-format on */
|
||||
|
||||
layout(set = 0, binding = 0) uniform sampler2D source_color;
|
||||
|
||||
layout(location = 0) out vec4 frag_color;
|
||||
|
||||
void main() {
|
||||
|
||||
vec4 color = texture(source_color, uv_interp, 0.0);
|
||||
if (params.force_luminance) {
|
||||
color.rgb = vec3(max(max(color.r, color.g), color.b));
|
||||
}
|
||||
frag_color = color;
|
||||
}
|
|
@ -0,0 +1,72 @@
|
|||
/* clang-format off */
|
||||
[compute]
|
||||
|
||||
#version 450
|
||||
|
||||
VERSION_DEFINES
|
||||
|
||||
layout(local_size_x = 8, local_size_y = 8, local_size_z = 1) in;
|
||||
/* clang-format on */
|
||||
|
||||
layout(set = 0, binding = 0) uniform samplerCube source_cube;
|
||||
|
||||
layout(push_constant, binding = 1, std430) uniform Params {
|
||||
ivec2 screen_size;
|
||||
ivec2 offset;
|
||||
float bias;
|
||||
float z_far;
|
||||
float z_near;
|
||||
bool z_flip;
|
||||
}
|
||||
params;
|
||||
|
||||
layout(r32f, set = 1, binding = 0) uniform restrict writeonly image2D depth_buffer;
|
||||
|
||||
void main() {
|
||||
|
||||
ivec2 pos = ivec2(gl_GlobalInvocationID.xy);
|
||||
if (any(greaterThan(pos, params.screen_size))) { //too large, do nothing
|
||||
return;
|
||||
}
|
||||
|
||||
vec2 pixel_size = 1.0 / vec2(params.screen_size);
|
||||
vec2 uv = (vec2(pos) + 0.5) * pixel_size;
|
||||
|
||||
vec3 normal = vec3(uv * 2.0 - 1.0, 0.0);
|
||||
|
||||
normal.z = 0.5 - 0.5 * ((normal.x * normal.x) + (normal.y * normal.y));
|
||||
normal = normalize(normal);
|
||||
|
||||
normal.y = -normal.y; //needs to be flipped to match projection matrix
|
||||
if (!params.z_flip) {
|
||||
normal.z = -normal.z;
|
||||
}
|
||||
|
||||
float depth = texture(source_cube, normal).r;
|
||||
|
||||
// absolute values for direction cosines, bigger value equals closer to basis axis
|
||||
vec3 unorm = abs(normal);
|
||||
|
||||
if ((unorm.x >= unorm.y) && (unorm.x >= unorm.z)) {
|
||||
// x code
|
||||
unorm = normal.x > 0.0 ? vec3(1.0, 0.0, 0.0) : vec3(-1.0, 0.0, 0.0);
|
||||
} else if ((unorm.y > unorm.x) && (unorm.y >= unorm.z)) {
|
||||
// y code
|
||||
unorm = normal.y > 0.0 ? vec3(0.0, 1.0, 0.0) : vec3(0.0, -1.0, 0.0);
|
||||
} else if ((unorm.z > unorm.x) && (unorm.z > unorm.y)) {
|
||||
// z code
|
||||
unorm = normal.z > 0.0 ? vec3(0.0, 0.0, 1.0) : vec3(0.0, 0.0, -1.0);
|
||||
} else {
|
||||
// oh-no we messed up code
|
||||
// has to be
|
||||
unorm = vec3(1.0, 0.0, 0.0);
|
||||
}
|
||||
|
||||
float depth_fix = 1.0 / dot(normal, unorm);
|
||||
|
||||
depth = 2.0 * depth - 1.0;
|
||||
float linear_depth = 2.0 * params.z_near * params.z_far / (params.z_far + params.z_near - depth * (params.z_far - params.z_near));
|
||||
depth = (linear_depth * depth_fix) / params.z_far;
|
||||
|
||||
imageStore(depth_buffer, pos + params.offset, vec4(depth));
|
||||
}
|
|
@ -908,6 +908,7 @@ public:
|
|||
enum InitialAction {
|
||||
INITIAL_ACTION_CLEAR, //start rendering and clear the framebuffer (supply params)
|
||||
INITIAL_ACTION_KEEP, //start rendering, but keep attached color texture contents (depth will be cleared)
|
||||
INITIAL_ACTION_DROP, //start rendering, ignore what is there, just write above it
|
||||
INITIAL_ACTION_CONTINUE, //continue rendering (framebuffer must have been left in "continue" state as final action previously)
|
||||
INITIAL_ACTION_MAX
|
||||
};
|
||||
|
|
Loading…
Reference in New Issue