diff options
Diffstat (limited to 'servers/rendering')
13 files changed, 201 insertions, 70 deletions
diff --git a/servers/rendering/renderer_compositor.h b/servers/rendering/renderer_compositor.h index 919ae2c6da..41aaba0f4c 100644 --- a/servers/rendering/renderer_compositor.h +++ b/servers/rendering/renderer_compositor.h @@ -59,7 +59,22 @@ public: struct BlitToScreen { RID render_target; Rect2i rect; - //lens distorted parameters for VR should go here + + struct { + bool use_layer = false; + uint32_t layer = 0; + } multi_view; + + struct { + //lens distorted parameters for VR + bool apply = false; + Vector2 eye_center; + float k1 = 0.0; + float k2 = 0.0; + + float upscale = 1.0; + float aspect_ratio = 1.0; + } lens_distortion; }; virtual void prepare_for_blitting_render_targets() = 0; diff --git a/servers/rendering/renderer_rd/forward_clustered/scene_shader_forward_clustered.cpp b/servers/rendering/renderer_rd/forward_clustered/scene_shader_forward_clustered.cpp index f7ed0205af..c96c541461 100644 --- a/servers/rendering/renderer_rd/forward_clustered/scene_shader_forward_clustered.cpp +++ b/servers/rendering/renderer_rd/forward_clustered/scene_shader_forward_clustered.cpp @@ -749,7 +749,7 @@ void SceneShaderForwardClustered::init(RendererStorageRD *p_storage, const Strin actions.default_filter = ShaderLanguage::FILTER_LINEAR_MIPMAP; actions.default_repeat = ShaderLanguage::REPEAT_ENABLE; actions.global_buffer_array_variable = "global_variables.data"; - actions.instance_uniform_index_variable = "draw_call.instance_uniforms_ofs"; + actions.instance_uniform_index_variable = "instances.data[instance_index].instance_uniforms_ofs"; compiler.initialize(actions); } diff --git a/servers/rendering/renderer_rd/renderer_compositor_rd.cpp b/servers/rendering/renderer_rd/renderer_compositor_rd.cpp index cb3e67e990..0012ba9c27 100644 --- a/servers/rendering/renderer_rd/renderer_compositor_rd.cpp +++ b/servers/rendering/renderer_rd/renderer_compositor_rd.cpp @@ -44,32 +44,40 @@ void RendererCompositorRD::blit_render_targets_to_screen(DisplayServer::WindowID ERR_CONTINUE(texture.is_null()); RID rd_texture = storage->texture_get_rd_texture(texture); ERR_CONTINUE(rd_texture.is_null()); + if (!render_target_descriptors.has(rd_texture) || !RD::get_singleton()->uniform_set_is_valid(render_target_descriptors[rd_texture])) { Vector<RD::Uniform> uniforms; RD::Uniform u; u.uniform_type = RD::UNIFORM_TYPE_SAMPLER_WITH_TEXTURE; u.binding = 0; - u.ids.push_back(copy_viewports_sampler); + u.ids.push_back(blit.sampler); u.ids.push_back(rd_texture); uniforms.push_back(u); - RID uniform_set = RD::get_singleton()->uniform_set_create(uniforms, copy_viewports_rd_shader, 0); + RID uniform_set = RD::get_singleton()->uniform_set_create(uniforms, blit.shader.version_get_shader(blit.shader_version, BLIT_MODE_NORMAL), 0); render_target_descriptors[rd_texture] = uniform_set; } Size2 screen_size(RD::get_singleton()->screen_get_width(p_screen), RD::get_singleton()->screen_get_height(p_screen)); - - RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, copy_viewports_rd_pipeline); - RD::get_singleton()->draw_list_bind_index_array(draw_list, copy_viewports_rd_array); + BlitMode mode = p_render_targets[i].lens_distortion.apply ? BLIT_MODE_LENS : p_render_targets[i].multi_view.use_layer ? BLIT_MODE_USE_LAYER : + BLIT_MODE_NORMAL; + RD::get_singleton()->draw_list_bind_render_pipeline(draw_list, blit.pipelines[mode]); + RD::get_singleton()->draw_list_bind_index_array(draw_list, blit.array); RD::get_singleton()->draw_list_bind_uniform_set(draw_list, render_target_descriptors[rd_texture], 0); - float push_constant[4] = { - p_render_targets[i].rect.position.x / screen_size.width, - p_render_targets[i].rect.position.y / screen_size.height, - p_render_targets[i].rect.size.width / screen_size.width, - p_render_targets[i].rect.size.height / screen_size.height, - }; - RD::get_singleton()->draw_list_set_push_constant(draw_list, push_constant, 4 * sizeof(float)); + blit.push_constant.rect[0] = p_render_targets[i].rect.position.x / screen_size.width; + blit.push_constant.rect[1] = p_render_targets[i].rect.position.y / screen_size.height; + blit.push_constant.rect[2] = p_render_targets[i].rect.size.width / screen_size.width; + blit.push_constant.rect[3] = p_render_targets[i].rect.size.height / screen_size.height; + blit.push_constant.layer = p_render_targets[i].multi_view.layer; + blit.push_constant.eye_center[0] = p_render_targets[i].lens_distortion.eye_center.x; + blit.push_constant.eye_center[1] = p_render_targets[i].lens_distortion.eye_center.y; + blit.push_constant.k1 = p_render_targets[i].lens_distortion.k1; + blit.push_constant.k2 = p_render_targets[i].lens_distortion.k2; + blit.push_constant.upscale = p_render_targets[i].lens_distortion.upscale; + blit.push_constant.aspect_ratio = p_render_targets[i].lens_distortion.aspect_ratio; + + RD::get_singleton()->draw_list_set_push_constant(draw_list, &blit.push_constant, sizeof(BlitPushConstant)); RD::get_singleton()->draw_list_draw(draw_list, true); } @@ -96,40 +104,22 @@ void RendererCompositorRD::end_frame(bool p_swap_buffers) { } void RendererCompositorRD::initialize() { - { //create framebuffer copy shader - RenderingDevice::ShaderStageData vert; - vert.shader_stage = RenderingDevice::SHADER_STAGE_VERTEX; - vert.spir_v = RenderingDevice::get_singleton()->shader_compile_from_source(RenderingDevice::SHADER_STAGE_VERTEX, - "#version 450\n" - "layout(push_constant, binding = 0, std140) uniform Pos { vec4 dst_rect; } pos;\n" - "layout(location =0) out vec2 uv;\n" - "void main() { \n" - " 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));\n" - " uv = base_arr[gl_VertexIndex];\n" - " vec2 vtx = pos.dst_rect.xy+uv*pos.dst_rect.zw;\n" - " gl_Position = vec4(vtx * 2.0 - 1.0,0.0,1.0);\n" - "}\n"); - - RenderingDevice::ShaderStageData frag; - frag.shader_stage = RenderingDevice::SHADER_STAGE_FRAGMENT; - frag.spir_v = RenderingDevice::get_singleton()->shader_compile_from_source(RenderingDevice::SHADER_STAGE_FRAGMENT, - "#version 450\n" - "layout (location = 0) in vec2 uv;\n" - "layout (location = 0) out vec4 color;\n" - "layout (binding = 0) uniform sampler2D src_rt;\n" - "void main() { color=texture(src_rt,uv); }\n"); - - Vector<RenderingDevice::ShaderStageData> source; - source.push_back(vert); - source.push_back(frag); - String error; - copy_viewports_rd_shader = RD::get_singleton()->shader_create(source); - if (!copy_viewports_rd_shader.is_valid()) { - print_line("Failed compilation: " + error); + { + // Initialize blit + Vector<String> blit_modes; + blit_modes.push_back("\n"); + blit_modes.push_back("\n#define USE_LAYER\n"); + blit_modes.push_back("\n#define USE_LAYER\n#define APPLY_LENS_DISTORTION\n"); + + blit.shader.initialize(blit_modes); + + blit.shader_version = blit.shader.version_create(); + + for (int i = 0; i < BLIT_MODE_MAX; i++) { + blit.pipelines[i] = RD::get_singleton()->render_pipeline_create(blit.shader.version_get_shader(blit.shader_version, i), RD::get_singleton()->screen_get_framebuffer_format(), RD::INVALID_ID, RD::RENDER_PRIMITIVE_TRIANGLES, RD::PipelineRasterizationState(), RD::PipelineMultisampleState(), RD::PipelineDepthStencilState(), RenderingDevice::PipelineColorBlendState::create_disabled(), 0); } - } - { //create index array for copy shader + //create index array for copy shader Vector<uint8_t> pv; pv.resize(6 * 4); { @@ -142,15 +132,10 @@ void RendererCompositorRD::initialize() { p32[4] = 2; p32[5] = 3; } - copy_viewports_rd_index_buffer = RD::get_singleton()->index_buffer_create(6, RenderingDevice::INDEX_BUFFER_FORMAT_UINT32, pv); - copy_viewports_rd_array = RD::get_singleton()->index_array_create(copy_viewports_rd_index_buffer, 0, 6); - } + blit.index_buffer = RD::get_singleton()->index_buffer_create(6, RenderingDevice::INDEX_BUFFER_FORMAT_UINT32, pv); + blit.array = RD::get_singleton()->index_array_create(blit.index_buffer, 0, 6); - { //pipeline - copy_viewports_rd_pipeline = RD::get_singleton()->render_pipeline_create(copy_viewports_rd_shader, RD::get_singleton()->screen_get_framebuffer_format(), RD::INVALID_ID, RD::RENDER_PRIMITIVE_TRIANGLES, RD::PipelineRasterizationState(), RD::PipelineMultisampleState(), RD::PipelineDepthStencilState(), RenderingDevice::PipelineColorBlendState::create_disabled(), 0); - } - { // sampler - copy_viewports_sampler = RD::get_singleton()->sampler_create(RD::SamplerState()); + blit.sampler = RD::get_singleton()->sampler_create(RD::SamplerState()); } } @@ -162,9 +147,9 @@ void RendererCompositorRD::finalize() { memdelete(storage); //only need to erase these, the rest are erased by cascade - RD::get_singleton()->free(copy_viewports_rd_index_buffer); - RD::get_singleton()->free(copy_viewports_rd_shader); - RD::get_singleton()->free(copy_viewports_sampler); + blit.shader.version_free(blit.shader_version); + RD::get_singleton()->free(blit.index_buffer); + RD::get_singleton()->free(blit.sampler); } RendererCompositorRD *RendererCompositorRD::singleton = nullptr; diff --git a/servers/rendering/renderer_rd/renderer_compositor_rd.h b/servers/rendering/renderer_rd/renderer_compositor_rd.h index b3865de2bf..52552f7ee3 100644 --- a/servers/rendering/renderer_rd/renderer_compositor_rd.h +++ b/servers/rendering/renderer_rd/renderer_compositor_rd.h @@ -38,6 +38,7 @@ #include "servers/rendering/renderer_rd/forward_mobile/render_forward_mobile.h" #include "servers/rendering/renderer_rd/renderer_canvas_render_rd.h" #include "servers/rendering/renderer_rd/renderer_storage_rd.h" +#include "servers/rendering/renderer_rd/shaders/blit.glsl.gen.h" class RendererCompositorRD : public RendererCompositor { protected: @@ -45,11 +46,35 @@ protected: RendererStorageRD *storage; RendererSceneRenderRD *scene; - RID copy_viewports_rd_shader; - RID copy_viewports_rd_pipeline; - RID copy_viewports_rd_index_buffer; - RID copy_viewports_rd_array; - RID copy_viewports_sampler; + enum BlitMode { + BLIT_MODE_NORMAL, + BLIT_MODE_USE_LAYER, + BLIT_MODE_LENS, + BLIT_MODE_MAX + }; + + struct BlitPushConstant { + float rect[4]; + + float eye_center[2]; + float k1; + float k2; + + float upscale; + float aspect_ratio; + uint32_t layer; + uint32_t pad1; + }; + + struct Blit { + BlitPushConstant push_constant; + BlitShaderRD shader; + RID shader_version; + RID pipelines[BLIT_MODE_MAX]; + RID index_buffer; + RID array; + RID sampler; + } blit; Map<RID, RID> render_target_descriptors; diff --git a/servers/rendering/renderer_rd/shader_compiler_rd.cpp b/servers/rendering/renderer_rd/shader_compiler_rd.cpp index 24ac85bb35..3a000bd06e 100644 --- a/servers/rendering/renderer_rd/shader_compiler_rd.cpp +++ b/servers/rendering/renderer_rd/shader_compiler_rd.cpp @@ -1280,6 +1280,9 @@ String ShaderCompilerRD::_dump_node_code(const SL::Node *p_node, int p_level, Ge } else if (mnode->assign_expression != nullptr) { code += "="; code += _dump_node_code(mnode->assign_expression, p_level, r_gen_code, p_actions, p_default_actions, true, false); + } else if (mnode->call_expression != nullptr) { + code += "."; + code += _dump_node_code(mnode->call_expression, p_level, r_gen_code, p_actions, p_default_actions, p_assigning, false); } } break; } diff --git a/servers/rendering/renderer_rd/shaders/blit.glsl b/servers/rendering/renderer_rd/shaders/blit.glsl new file mode 100644 index 0000000000..967da1e6e4 --- /dev/null +++ b/servers/rendering/renderer_rd/shaders/blit.glsl @@ -0,0 +1,95 @@ +#[vertex] + +#version 450 + +#VERSION_DEFINES + +layout(push_constant, binding = 0, std140) uniform Pos { + vec4 dst_rect; + + vec2 eye_center; + float k1; + float k2; + + float upscale; + float aspect_ratio; + uint layer; + uint pad1; +} +data; + +layout(location = 0) out vec2 uv; + +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 = base_arr[gl_VertexIndex]; + vec2 vtx = data.dst_rect.xy + uv * data.dst_rect.zw; + gl_Position = vec4(vtx * 2.0 - 1.0, 0.0, 1.0); +} + +#[fragment] + +#version 450 + +#VERSION_DEFINES + +layout(push_constant, binding = 0, std140) uniform Pos { + vec4 dst_rect; + + vec2 eye_center; + float k1; + float k2; + + float upscale; + float aspect_ratio; + uint layer; + uint pad1; +} +data; + +layout(location = 0) in vec2 uv; + +layout(location = 0) out vec4 color; + +#ifdef USE_LAYER +layout(binding = 0) uniform sampler2DArray src_rt; +#else +layout(binding = 0) uniform sampler2D src_rt; +#endif + +void main() { +#ifdef APPLY_LENS_DISTORTION + vec2 coords = uv * 2.0 - 1.0; + vec2 offset = coords - data.eye_center; + + // take aspect ratio into account + offset.y /= data.aspect_ratio; + + // distort + vec2 offset_sq = offset * offset; + float radius_sq = offset_sq.x + offset_sq.y; + float radius_s4 = radius_sq * radius_sq; + float distortion_scale = 1.0 + (data.k1 * radius_sq) + (data.k2 * radius_s4); + offset *= distortion_scale; + + // reapply aspect ratio + offset.y *= data.aspect_ratio; + + // add our eye center back in + coords = offset + data.eye_center; + coords /= data.upscale; + + // and check our color + if (coords.x < -1.0 || coords.y < -1.0 || coords.x > 1.0 || coords.y > 1.0) { + color = vec4(0.0, 0.0, 0.0, 1.0); + } else { + // layer is always used here + coords = (coords + vec2(1.0)) / vec2(2.0); + color = texture(src_rt, vec3(coords, data.layer)); + } +#elif defined(USE_LAYER) + color = texture(src_rt, vec3(uv, data.layer)); +#else + color = texture(src_rt, uv); +#endif +} diff --git a/servers/rendering/renderer_rd/shaders/scene_forward_clustered.glsl b/servers/rendering/renderer_rd/shaders/scene_forward_clustered.glsl index 1d67a3f1df..e09b8f15be 100644 --- a/servers/rendering/renderer_rd/shaders/scene_forward_clustered.glsl +++ b/servers/rendering/renderer_rd/shaders/scene_forward_clustered.glsl @@ -662,7 +662,7 @@ void main() { #endif #ifdef ALPHA_ANTIALIASING_EDGE_USED -// If alpha scissor is used, we must further the edge threshold, otherwise we wont get any edge feather +// If alpha scissor is used, we must further the edge threshold, otherwise we won't get any edge feather #ifdef ALPHA_SCISSOR_USED alpha_antialiasing_edge = clamp(alpha_scissor_threshold + alpha_antialiasing_edge, 0.0, 1.0); #endif diff --git a/servers/rendering/renderer_rd/shaders/scene_forward_mobile.glsl b/servers/rendering/renderer_rd/shaders/scene_forward_mobile.glsl index b38b8d803d..d488c99b6d 100644 --- a/servers/rendering/renderer_rd/shaders/scene_forward_mobile.glsl +++ b/servers/rendering/renderer_rd/shaders/scene_forward_mobile.glsl @@ -622,7 +622,7 @@ void main() { #endif #ifdef ALPHA_ANTIALIASING_EDGE_USED -// If alpha scissor is used, we must further the edge threshold, otherwise we wont get any edge feather +// If alpha scissor is used, we must further the edge threshold, otherwise we won't get any edge feather #ifdef ALPHA_SCISSOR_USED alpha_antialiasing_edge = clamp(alpha_scissor_threshold + alpha_antialiasing_edge, 0.0, 1.0); #endif diff --git a/servers/rendering/renderer_scene_cull.h b/servers/rendering/renderer_scene_cull.h index a61b04afc8..930ac0df70 100644 --- a/servers/rendering/renderer_scene_cull.h +++ b/servers/rendering/renderer_scene_cull.h @@ -845,7 +845,7 @@ public: RID_PtrOwner<Instance, true> instance_owner; - uint32_t geometry_instance_pair_mask; // used in traditional forward, unnecesary on clustered + uint32_t geometry_instance_pair_mask; // used in traditional forward, unnecessary on clustered virtual RID instance_allocate(); virtual void instance_initialize(RID p_rid); diff --git a/servers/rendering/renderer_viewport.cpp b/servers/rendering/renderer_viewport.cpp index f7be6c6c60..9ac2c1918f 100644 --- a/servers/rendering/renderer_viewport.cpp +++ b/servers/rendering/renderer_viewport.cpp @@ -322,7 +322,7 @@ void RendererViewport::_draw_viewport(Viewport *p_viewport, XRInterface::Eyes p_ Vector2 point = clip_rect.position + clip_rect.size * signs[j]; if (sign_cmp == light_dir_sign) { - //both point in same direction, plot offseted + //both point in same direction, plot offsetted points[point_count++] = point + light_dir * cull_distance; } else if (sign_cmp.x == light_dir_sign.x || sign_cmp.y == light_dir_sign.y) { int next_j = (j + 1) % 4; diff --git a/servers/rendering/rendering_device.h b/servers/rendering/rendering_device.h index d86c44a206..27bded9810 100644 --- a/servers/rendering/rendering_device.h +++ b/servers/rendering/rendering_device.h @@ -982,7 +982,7 @@ public: enum InitialAction { INITIAL_ACTION_CLEAR, //start rendering and clear the whole framebuffer (region or not) (supply params) INITIAL_ACTION_CLEAR_REGION, //start rendering and clear the framebuffer in the specified region (supply params) - INITIAL_ACTION_CLEAR_REGION_CONTINUE, //countinue rendering and clear the framebuffer in the specified region (supply params) + INITIAL_ACTION_CLEAR_REGION_CONTINUE, //continue rendering and clear the framebuffer in the specified region (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) diff --git a/servers/rendering/shader_language.cpp b/servers/rendering/shader_language.cpp index a81306b97d..e92940b31a 100644 --- a/servers/rendering/shader_language.cpp +++ b/servers/rendering/shader_language.cpp @@ -3186,7 +3186,7 @@ bool ShaderLanguage::_check_node_constness(const Node *p_node) const { switch (p_node->type) { case Node::TYPE_OPERATOR: { OperatorNode *op_node = (OperatorNode *)p_node; - for (int i = (1 ? op_node->op == OP_CALL : 0); i < op_node->arguments.size(); i++) { + for (int i = int(op_node->op == OP_CALL); i < op_node->arguments.size(); i++) { if (!_check_node_constness(op_node->arguments[i])) { return false; } @@ -4301,8 +4301,15 @@ ShaderLanguage::Node *ShaderLanguage::_parse_expression(BlockNode *p_block, cons } mn->assign_expression = assign_expression; } else if (tk.type == TK_PERIOD) { - _set_error("Nested array length() is not yet implemented"); - return nullptr; + completion_class = TAG_ARRAY; + p_block->block_tag = SubClassTag::TAG_ARRAY; + Node *call_expression = _parse_and_reduce_expression(p_block, p_function_info); + p_block->block_tag = SubClassTag::TAG_GLOBAL; + if (!call_expression) { + return nullptr; + } + mn->datatype = call_expression->get_datatype(); + mn->call_expression = call_expression; } else if (tk.type == TK_BRACKET_OPEN) { Node *index_expression = _parse_and_reduce_expression(p_block, p_function_info); if (!index_expression) { diff --git a/servers/rendering/shader_language.h b/servers/rendering/shader_language.h index e00f4dce19..cdedc5edbb 100644 --- a/servers/rendering/shader_language.h +++ b/servers/rendering/shader_language.h @@ -546,6 +546,7 @@ public: Node *owner = nullptr; Node *index_expression = nullptr; Node *assign_expression = nullptr; + Node *call_expression = nullptr; bool has_swizzling_duplicates = false; virtual DataType get_datatype() const { return datatype; } |