Fix VRS issues
This commit is contained in:
parent
5993209b26
commit
616ba8745f
7 changed files with 40 additions and 15 deletions
|
@ -3826,7 +3826,7 @@ VkRenderPass RenderingDeviceVulkan::_render_pass_create(const Vector<AttachmentF
|
|||
vrs_reference.layout = VK_IMAGE_LAYOUT_FRAGMENT_SHADING_RATE_ATTACHMENT_OPTIMAL_KHR;
|
||||
vrs_reference.aspectMask = VK_IMAGE_ASPECT_NONE;
|
||||
|
||||
Size2i texel_size = context->get_vrs_capabilities().max_texel_size;
|
||||
Size2i texel_size = context->get_vrs_capabilities().texel_size;
|
||||
|
||||
VkFragmentShadingRateAttachmentInfoKHR &vrs_attachment_info = vrs_attachment_info_array[i];
|
||||
vrs_attachment_info.sType = VK_STRUCTURE_TYPE_FRAGMENT_SHADING_RATE_ATTACHMENT_INFO_KHR;
|
||||
|
@ -9724,6 +9724,12 @@ uint64_t RenderingDeviceVulkan::limit_get(Limit p_limit) const {
|
|||
VulkanContext::SubgroupCapabilities subgroup_capabilities = context->get_subgroup_capabilities();
|
||||
return subgroup_capabilities.supported_operations_flags_rd();
|
||||
}
|
||||
case LIMIT_VRS_TEXEL_WIDTH: {
|
||||
return context->get_vrs_capabilities().texel_size.x;
|
||||
}
|
||||
case LIMIT_VRS_TEXEL_HEIGHT: {
|
||||
return context->get_vrs_capabilities().texel_size.y;
|
||||
}
|
||||
default:
|
||||
ERR_FAIL_V(0);
|
||||
}
|
||||
|
|
|
@ -625,6 +625,9 @@ Error VulkanContext::_check_capabilities() {
|
|||
vrs_capabilities.pipeline_vrs_supported = false;
|
||||
vrs_capabilities.primitive_vrs_supported = false;
|
||||
vrs_capabilities.attachment_vrs_supported = false;
|
||||
vrs_capabilities.min_texel_size = Size2i();
|
||||
vrs_capabilities.max_texel_size = Size2i();
|
||||
vrs_capabilities.texel_size = Size2i();
|
||||
multiview_capabilities.is_supported = false;
|
||||
multiview_capabilities.geometry_shader_is_supported = false;
|
||||
multiview_capabilities.tessellation_shader_is_supported = false;
|
||||
|
@ -788,6 +791,10 @@ Error VulkanContext::_check_capabilities() {
|
|||
vrs_capabilities.max_texel_size.x = vrsProperties.maxFragmentShadingRateAttachmentTexelSize.width;
|
||||
vrs_capabilities.max_texel_size.y = vrsProperties.maxFragmentShadingRateAttachmentTexelSize.height;
|
||||
|
||||
// We'll attempt to default to a texel size of 16x16
|
||||
vrs_capabilities.texel_size.x = CLAMP(16, vrs_capabilities.min_texel_size.x, vrs_capabilities.max_texel_size.x);
|
||||
vrs_capabilities.texel_size.y = CLAMP(16, vrs_capabilities.min_texel_size.y, vrs_capabilities.max_texel_size.y);
|
||||
|
||||
print_verbose(String(" Attachment fragment shading rate") + String(", min texel size: (") + itos(vrs_capabilities.min_texel_size.x) + String(", ") + itos(vrs_capabilities.min_texel_size.y) + String(")") + String(", max texel size: (") + itos(vrs_capabilities.max_texel_size.x) + String(", ") + itos(vrs_capabilities.max_texel_size.y) + String(")"));
|
||||
}
|
||||
|
||||
|
|
|
@ -76,6 +76,8 @@ public:
|
|||
|
||||
Size2i min_texel_size;
|
||||
Size2i max_texel_size;
|
||||
|
||||
Size2i texel_size; // The texel size we'll use
|
||||
};
|
||||
|
||||
struct ShaderCapabilities {
|
||||
|
|
|
@ -92,18 +92,15 @@ void VRS::copy_vrs(RID p_source_rd_texture, RID p_dest_framebuffer, bool p_multi
|
|||
}
|
||||
|
||||
Size2i VRS::get_vrs_texture_size(const Size2i p_base_size) const {
|
||||
// TODO we should find some way to store this properly, we're assuming 16x16 as this seems to be the standard but in our vrs_capacities we
|
||||
// obtain a minimum and maximum size, and we should choose something within this range and then make sure that is consistently set when creating
|
||||
// our frame buffer. Also it is important that we make the resulting size we calculate down below available to the end user so they know the size
|
||||
// of the VRS buffer to supply.
|
||||
Size2i texel_size = Size2i(16, 16);
|
||||
int32_t texel_width = RD::get_singleton()->limit_get(RD::LIMIT_VRS_TEXEL_WIDTH);
|
||||
int32_t texel_height = RD::get_singleton()->limit_get(RD::LIMIT_VRS_TEXEL_HEIGHT);
|
||||
|
||||
int width = p_base_size.x / texel_size.x;
|
||||
if (p_base_size.x % texel_size.x != 0) {
|
||||
int width = p_base_size.x / texel_width;
|
||||
if (p_base_size.x % texel_width != 0) {
|
||||
width++;
|
||||
}
|
||||
int height = p_base_size.y / texel_size.y;
|
||||
if (p_base_size.y % texel_size.y != 0) {
|
||||
int height = p_base_size.y / texel_height;
|
||||
if (p_base_size.y % texel_height != 0) {
|
||||
height++;
|
||||
}
|
||||
return Size2i(width, height);
|
||||
|
|
|
@ -63,10 +63,18 @@ void main() {
|
|||
|
||||
#ifdef MULTIVIEW
|
||||
vec4 color = textureLod(source_color, uv, 0.0);
|
||||
frag_color = uint(color.r * 255.0);
|
||||
#else /* MULTIVIEW */
|
||||
vec4 color = textureLod(source_color, uv, 0.0);
|
||||
#endif /* MULTIVIEW */
|
||||
|
||||
// See if we can change the sampler to one that returns int...
|
||||
frag_color = uint(color.r * 256.0);
|
||||
// for user supplied VRS map we do a color mapping
|
||||
color.r *= 3.0;
|
||||
frag_color = int(color.r) << 2;
|
||||
|
||||
color.g *= 3.0;
|
||||
frag_color += int(color.g);
|
||||
|
||||
// note 1x4, 4x1, 1x8, 8x1, 2x8 and 8x2 are not supported
|
||||
// 4x8, 8x4 and 8x8 are only available on some GPUs
|
||||
#endif /* MULTIVIEW */
|
||||
}
|
||||
|
|
|
@ -1257,6 +1257,8 @@ public:
|
|||
LIMIT_SUBGROUP_SIZE,
|
||||
LIMIT_SUBGROUP_IN_SHADERS, // Set flags using SHADER_STAGE_VERTEX_BIT, SHADER_STAGE_FRAGMENT_BIT, etc.
|
||||
LIMIT_SUBGROUP_OPERATIONS,
|
||||
LIMIT_VRS_TEXEL_WIDTH,
|
||||
LIMIT_VRS_TEXEL_HEIGHT,
|
||||
};
|
||||
|
||||
virtual uint64_t limit_get(Limit p_limit) const = 0;
|
||||
|
|
|
@ -167,11 +167,12 @@ RID XRInterface::get_vrs_texture() {
|
|||
// Default logic will return a standard VRS image based on our target size and default projections.
|
||||
// Note that this only gets called if VRS is supported on the hardware.
|
||||
|
||||
Size2 texel_size = Size2(16.0, 16.0); // For now we assume we always use 16x16 texels, seems to be the standard.
|
||||
int32_t texel_width = RD::get_singleton()->limit_get(RD::LIMIT_VRS_TEXEL_WIDTH);
|
||||
int32_t texel_height = RD::get_singleton()->limit_get(RD::LIMIT_VRS_TEXEL_HEIGHT);
|
||||
int view_count = get_view_count();
|
||||
Size2 target_size = get_render_target_size();
|
||||
real_t aspect = target_size.x / target_size.y; // is this y/x ?
|
||||
Size2 vrs_size = Size2(round(0.5 + target_size.x / texel_size.x), round(0.5 + target_size.y / texel_size.y));
|
||||
Size2 vrs_size = Size2(round(0.5 + target_size.x / texel_width), round(0.5 + target_size.y / texel_height));
|
||||
real_t radius = vrs_size.length() * 0.5;
|
||||
Size2 vrs_sizei = vrs_size;
|
||||
|
||||
|
@ -179,6 +180,8 @@ RID XRInterface::get_vrs_texture() {
|
|||
const uint8_t densities[] = {
|
||||
0, // 1x1
|
||||
1, // 1x2
|
||||
// 2, // 1x4 - not supported
|
||||
// 3, // 1x8 - not supported
|
||||
// 4, // 2x1
|
||||
5, // 2x2
|
||||
6, // 2x4
|
||||
|
|
Loading…
Reference in a new issue