Path: blob/master/drivers/gles3/rasterizer_scene_gles3.h
9973 views
/**************************************************************************/1/* rasterizer_scene_gles3.h */2/**************************************************************************/3/* This file is part of: */4/* GODOT ENGINE */5/* https://godotengine.org */6/**************************************************************************/7/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */8/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */9/* */10/* Permission is hereby granted, free of charge, to any person obtaining */11/* a copy of this software and associated documentation files (the */12/* "Software"), to deal in the Software without restriction, including */13/* without limitation the rights to use, copy, modify, merge, publish, */14/* distribute, sublicense, and/or sell copies of the Software, and to */15/* permit persons to whom the Software is furnished to do so, subject to */16/* the following conditions: */17/* */18/* The above copyright notice and this permission notice shall be */19/* included in all copies or substantial portions of the Software. */20/* */21/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */22/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */23/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */24/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */25/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */26/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */27/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */28/**************************************************************************/2930#pragma once3132#include "platform_gl.h"33#ifdef GLES3_ENABLED3435#include "core/math/projection.h"36#include "core/templates/paged_allocator.h"37#include "core/templates/rid_owner.h"38#include "core/templates/self_list.h"39#include "drivers/gles3/shaders/effects/cubemap_filter.glsl.gen.h"40#include "drivers/gles3/shaders/sky.glsl.gen.h"41#include "scene/resources/mesh.h"42#include "servers/rendering/renderer_compositor.h"43#include "servers/rendering/renderer_scene_render.h"44#include "servers/rendering_server.h"45#include "shader_gles3.h"46#include "storage/light_storage.h"47#include "storage/material_storage.h"48#include "storage/render_scene_buffers_gles3.h"49#include "storage/utilities.h"5051enum RenderListType {52RENDER_LIST_OPAQUE, //used for opaque objects53RENDER_LIST_ALPHA, //used for transparent objects54RENDER_LIST_SECONDARY, //used for shadows and other objects55RENDER_LIST_MAX56};5758enum PassMode {59PASS_MODE_COLOR,60PASS_MODE_COLOR_TRANSPARENT,61PASS_MODE_SHADOW,62PASS_MODE_DEPTH,63PASS_MODE_MATERIAL,64};6566// These should share as much as possible with SkyUniform Location67enum SceneUniformLocation {68SCENE_TONEMAP_UNIFORM_LOCATION,69SCENE_GLOBALS_UNIFORM_LOCATION,70SCENE_DATA_UNIFORM_LOCATION,71SCENE_MATERIAL_UNIFORM_LOCATION,72SCENE_EMPTY1, // Unused, put here to avoid conflicts with SKY_DIRECTIONAL_LIGHT_UNIFORM_LOCATION.73SCENE_OMNILIGHT_UNIFORM_LOCATION,74SCENE_SPOTLIGHT_UNIFORM_LOCATION,75SCENE_DIRECTIONAL_LIGHT_UNIFORM_LOCATION,76SCENE_MULTIVIEW_UNIFORM_LOCATION,77SCENE_POSITIONAL_SHADOW_UNIFORM_LOCATION,78SCENE_DIRECTIONAL_SHADOW_UNIFORM_LOCATION,79SCENE_EMPTY2, // Unused, put here to avoid conflicts with SKY_MULTIVIEW_UNIFORM_LOCATION.80};8182enum SkyUniformLocation {83SKY_TONEMAP_UNIFORM_LOCATION,84SKY_GLOBALS_UNIFORM_LOCATION,85SKY_EMPTY1, // Unused, put here to avoid conflicts with SCENE_DATA_UNIFORM_LOCATION.86SKY_MATERIAL_UNIFORM_LOCATION,87SKY_DIRECTIONAL_LIGHT_UNIFORM_LOCATION,88SKY_EMPTY2, // Unused, put here to avoid conflicts with SCENE_OMNILIGHT_UNIFORM_LOCATION.89SKY_EMPTY3, // Unused, put here to avoid conflicts with SCENE_SPOTLIGHT_UNIFORM_LOCATION.90SKY_EMPTY4, // Unused, put here to avoid conflicts with SCENE_DIRECTIONAL_LIGHT_UNIFORM_LOCATION.91SKY_EMPTY5, // Unused, put here to avoid conflicts with SCENE_MULTIVIEW_UNIFORM_LOCATION.92SKY_EMPTY6, // Unused, put here to avoid conflicts with SCENE_POSITIONAL_SHADOW_UNIFORM_LOCATION.93SKY_EMPTY7, // Unused, put here to avoid conflicts with SCENE_DIRECTIONAL_SHADOW_UNIFORM_LOCATION.94SKY_MULTIVIEW_UNIFORM_LOCATION,95};9697struct RenderDataGLES3 {98Ref<RenderSceneBuffersGLES3> render_buffers;99bool transparent_bg = false;100Rect2i render_region;101102Transform3D cam_transform;103Transform3D inv_cam_transform;104Projection cam_projection;105bool cam_orthogonal = false;106bool cam_frustum = false;107uint32_t camera_visible_layers = 0xFFFFFFFF;108109// For billboards to cast correct shadows.110Transform3D main_cam_transform;111112// For stereo rendering113uint32_t view_count = 1;114Vector3 view_eye_offset[RendererSceneRender::MAX_RENDER_VIEWS];115Projection view_projection[RendererSceneRender::MAX_RENDER_VIEWS];116117float z_near = 0.0;118float z_far = 0.0;119120const PagedArray<RenderGeometryInstance *> *instances = nullptr;121const PagedArray<RID> *lights = nullptr;122const PagedArray<RID> *reflection_probes = nullptr;123RID environment;124RID camera_attributes;125RID shadow_atlas;126RID reflection_probe;127int reflection_probe_pass = 0;128129float lod_distance_multiplier = 0.0;130float screen_mesh_lod_threshold = 0.0;131132uint32_t directional_light_count = 0;133uint32_t directional_shadow_count = 0;134135uint32_t spot_light_count = 0;136uint32_t omni_light_count = 0;137138float luminance_multiplier = 1.0;139140RenderingMethod::RenderInfo *render_info = nullptr;141142/* Shadow data */143const RendererSceneRender::RenderShadowData *render_shadows = nullptr;144int render_shadow_count = 0;145};146147class RasterizerCanvasGLES3;148149class RasterizerSceneGLES3 : public RendererSceneRender {150private:151static RasterizerSceneGLES3 *singleton;152RS::ViewportDebugDraw debug_draw = RS::VIEWPORT_DEBUG_DRAW_DISABLED;153uint64_t scene_pass = 0;154155template <typename T>156struct InstanceSort {157float depth;158T *instance = nullptr;159bool operator<(const InstanceSort &p_sort) const {160return depth < p_sort.depth;161}162};163164struct SceneGlobals {165RID shader_default_version;166RID default_material;167RID default_shader;168RID overdraw_material;169RID overdraw_shader;170} scene_globals;171172GLES3::SceneMaterialData *default_material_data_ptr = nullptr;173GLES3::SceneMaterialData *overdraw_material_data_ptr = nullptr;174175/* LIGHT INSTANCE */176177struct LightData {178float position[3];179float inv_radius;180181float direction[3]; // Only used by SpotLight182float size;183184float color[3];185float attenuation;186187float inv_spot_attenuation;188float cos_spot_angle;189float specular_amount;190float shadow_opacity;191192float pad[3];193uint32_t bake_mode;194};195static_assert(sizeof(LightData) % 16 == 0, "LightData size must be a multiple of 16 bytes");196197struct DirectionalLightData {198float direction[3];199float energy;200201float color[3];202float size;203204uint32_t enabled; // For use by SkyShaders205uint32_t bake_mode;206float shadow_opacity;207float specular;208};209static_assert(sizeof(DirectionalLightData) % 16 == 0, "DirectionalLightData size must be a multiple of 16 bytes");210211struct ShadowData {212float shadow_matrix[16];213214float light_position[3];215float shadow_normal_bias;216217float pad[3];218float shadow_atlas_pixel_size;219};220static_assert(sizeof(ShadowData) % 16 == 0, "ShadowData size must be a multiple of 16 bytes");221222struct DirectionalShadowData {223float direction[3];224float shadow_atlas_pixel_size;225float shadow_normal_bias[4];226float shadow_split_offsets[4];227float shadow_matrices[4][16];228float fade_from;229float fade_to;230uint32_t blend_splits; // Not exposed to the shader.231uint32_t pad;232};233static_assert(sizeof(DirectionalShadowData) % 16 == 0, "DirectionalShadowData size must be a multiple of 16 bytes");234235class GeometryInstanceGLES3;236237// Cached data for drawing surfaces238struct GeometryInstanceSurface {239enum {240FLAG_PASS_DEPTH = 1,241FLAG_PASS_OPAQUE = 2,242FLAG_PASS_ALPHA = 4,243FLAG_PASS_SHADOW = 8,244FLAG_USES_SHARED_SHADOW_MATERIAL = 128,245FLAG_USES_SCREEN_TEXTURE = 2048,246FLAG_USES_DEPTH_TEXTURE = 4096,247FLAG_USES_NORMAL_TEXTURE = 8192,248FLAG_USES_DOUBLE_SIDED_SHADOWS = 16384,249FLAG_USES_STENCIL = 32768,250};251252union {253struct {254uint64_t sort_key1;255uint64_t sort_key2;256};257struct {258uint64_t lod_index : 8;259uint64_t surface_index : 8;260uint64_t geometry_id : 32;261uint64_t material_id_low : 16;262263uint64_t material_id_hi : 16;264uint64_t shader_id : 32;265uint64_t uses_softshadow : 1;266uint64_t uses_projector : 1;267uint64_t uses_forward_gi : 1;268uint64_t uses_lightmap : 1;269uint64_t depth_layer : 4;270uint64_t priority : 8;271};272} sort;273274RS::PrimitiveType primitive = RS::PRIMITIVE_MAX;275uint32_t flags = 0;276uint32_t surface_index = 0;277uint32_t lod_index = 0;278uint32_t index_count = 0;279int32_t light_pass_index = -1;280bool finished_base_pass = false;281282void *surface = nullptr;283GLES3::SceneShaderData *shader = nullptr;284GLES3::SceneMaterialData *material = nullptr;285286void *surface_shadow = nullptr;287GLES3::SceneShaderData *shader_shadow = nullptr;288GLES3::SceneMaterialData *material_shadow = nullptr;289290GeometryInstanceSurface *next = nullptr;291GeometryInstanceGLES3 *owner = nullptr;292};293294struct GeometryInstanceLightmapSH {295Color sh[9];296};297298class GeometryInstanceGLES3 : public RenderGeometryInstanceBase {299public:300//used during rendering301bool store_transform_cache = true;302303int32_t instance_count = 0;304305bool can_sdfgi = false;306bool using_projectors = false;307bool using_softshadows = false;308309struct LightPass {310int32_t light_id = -1; // Position in the light uniform buffer.311int32_t shadow_id = -1; // Position in the shadow uniform buffer.312RID light_instance_rid;313bool is_omni = false;314};315316LocalVector<LightPass> light_passes;317318uint32_t paired_omni_light_count = 0;319uint32_t paired_spot_light_count = 0;320LocalVector<RID> paired_omni_lights;321LocalVector<RID> paired_spot_lights;322LocalVector<uint32_t> omni_light_gl_cache;323LocalVector<uint32_t> spot_light_gl_cache;324325LocalVector<RID> paired_reflection_probes;326LocalVector<RID> reflection_probe_rid_cache;327LocalVector<Transform3D> reflection_probes_local_transform_cache;328329RID lightmap_instance;330Rect2 lightmap_uv_scale;331uint32_t lightmap_slice_index;332GeometryInstanceLightmapSH *lightmap_sh = nullptr;333334// Used during setup.335GeometryInstanceSurface *surface_caches = nullptr;336SelfList<GeometryInstanceGLES3> dirty_list_element;337338GeometryInstanceGLES3() :339dirty_list_element(this) {}340341virtual void _mark_dirty() override;342virtual void set_use_lightmap(RID p_lightmap_instance, const Rect2 &p_lightmap_uv_scale, int p_lightmap_slice_index) override;343virtual void set_lightmap_capture(const Color *p_sh9) override;344345virtual void pair_light_instances(const RID *p_light_instances, uint32_t p_light_instance_count) override;346virtual void pair_reflection_probe_instances(const RID *p_reflection_probe_instances, uint32_t p_reflection_probe_instance_count) override;347virtual void pair_decal_instances(const RID *p_decal_instances, uint32_t p_decal_instance_count) override {}348virtual void pair_voxel_gi_instances(const RID *p_voxel_gi_instances, uint32_t p_voxel_gi_instance_count) override {}349350virtual void set_softshadow_projector_pairing(bool p_softshadow, bool p_projector) override {}351};352353enum {354INSTANCE_DATA_FLAGS_DYNAMIC = 1 << 3,355INSTANCE_DATA_FLAGS_NON_UNIFORM_SCALE = 1 << 4,356INSTANCE_DATA_FLAG_USE_GI_BUFFERS = 1 << 5,357INSTANCE_DATA_FLAG_USE_LIGHTMAP_CAPTURE = 1 << 7,358INSTANCE_DATA_FLAG_USE_LIGHTMAP = 1 << 8,359INSTANCE_DATA_FLAG_USE_SH_LIGHTMAP = 1 << 9,360INSTANCE_DATA_FLAG_USE_VOXEL_GI = 1 << 10,361INSTANCE_DATA_FLAG_PARTICLES = 1 << 11,362INSTANCE_DATA_FLAG_MULTIMESH = 1 << 12,363INSTANCE_DATA_FLAG_MULTIMESH_FORMAT_2D = 1 << 13,364INSTANCE_DATA_FLAG_MULTIMESH_HAS_COLOR = 1 << 14,365INSTANCE_DATA_FLAG_MULTIMESH_HAS_CUSTOM_DATA = 1 << 15,366};367368static void _geometry_instance_dependency_changed(Dependency::DependencyChangedNotification p_notification, DependencyTracker *p_tracker);369static void _geometry_instance_dependency_deleted(const RID &p_dependency, DependencyTracker *p_tracker);370371SelfList<GeometryInstanceGLES3>::List geometry_instance_dirty_list;372373// Use PagedAllocator instead of RID to maximize performance374PagedAllocator<GeometryInstanceGLES3> geometry_instance_alloc;375PagedAllocator<GeometryInstanceSurface> geometry_instance_surface_alloc;376377void _geometry_instance_add_surface_with_material(GeometryInstanceGLES3 *ginstance, uint32_t p_surface, GLES3::SceneMaterialData *p_material, uint32_t p_material_id, uint32_t p_shader_id, RID p_mesh);378void _geometry_instance_add_surface_with_material_chain(GeometryInstanceGLES3 *ginstance, uint32_t p_surface, GLES3::SceneMaterialData *p_material, RID p_mat_src, RID p_mesh);379void _geometry_instance_add_surface(GeometryInstanceGLES3 *ginstance, uint32_t p_surface, RID p_material, RID p_mesh);380void _geometry_instance_update(RenderGeometryInstance *p_geometry_instance);381void _update_dirty_geometry_instances();382383struct SceneState {384struct UBO {385float projection_matrix[16];386float inv_projection_matrix[16];387float inv_view_matrix[16];388float view_matrix[16];389390float main_cam_inv_view_matrix[16];391392float viewport_size[2];393float screen_pixel_size[2];394395float ambient_light_color_energy[4];396397float ambient_color_sky_mix;398uint32_t pad2;399float emissive_exposure_normalization;400uint32_t use_ambient_light = 0;401402uint32_t use_ambient_cubemap = 0;403uint32_t use_reflection_cubemap = 0;404float fog_aerial_perspective;405float time;406407float radiance_inverse_xform[12];408409uint32_t directional_light_count;410float z_far;411float z_near;412float IBL_exposure_normalization;413414uint32_t fog_enabled;415uint32_t fog_mode;416float fog_density;417float fog_height;418419float fog_height_density;420float fog_depth_curve;421float fog_sun_scatter;422float fog_depth_begin;423424float fog_light_color[3];425float fog_depth_end;426427float shadow_bias;428float luminance_multiplier;429uint32_t camera_visible_layers;430bool pancake_shadows;431};432static_assert(sizeof(UBO) % 16 == 0, "Scene UBO size must be a multiple of 16 bytes");433static_assert(sizeof(UBO) < 16384, "Scene UBO size must be 16384 bytes or smaller");434435struct MultiviewUBO {436float projection_matrix_view[RendererSceneRender::MAX_RENDER_VIEWS][16];437float inv_projection_matrix_view[RendererSceneRender::MAX_RENDER_VIEWS][16];438float eye_offset[RendererSceneRender::MAX_RENDER_VIEWS][4];439};440static_assert(sizeof(MultiviewUBO) % 16 == 0, "Multiview UBO size must be a multiple of 16 bytes");441static_assert(sizeof(MultiviewUBO) < 16384, "MultiviewUBO size must be 16384 bytes or smaller");442443struct TonemapUBO {444float exposure = 1.0;445float white = 1.0;446int32_t tonemapper = 0;447int32_t pad = 0;448449int32_t pad2 = 0;450float brightness = 1.0;451float contrast = 1.0;452float saturation = 1.0;453};454static_assert(sizeof(TonemapUBO) % 16 == 0, "Tonemap UBO size must be a multiple of 16 bytes");455456UBO ubo;457GLuint ubo_buffer = 0;458MultiviewUBO multiview_ubo;459GLuint multiview_buffer = 0;460GLuint tonemap_buffer = 0;461462bool used_depth_prepass = false;463464GLES3::SceneShaderData::BlendMode current_blend_mode = GLES3::SceneShaderData::BLEND_MODE_MIX;465RS::CullMode cull_mode = RS::CULL_MODE_BACK;466GLenum current_depth_function = GL_GEQUAL;467468bool current_blend_enabled = false;469bool current_depth_draw_enabled = false;470bool current_depth_test_enabled = false;471bool current_scissor_test_enabled = false;472473void reset_gl_state() {474glDisable(GL_BLEND);475current_blend_enabled = false;476477glDisable(GL_SCISSOR_TEST);478current_scissor_test_enabled = false;479480glCullFace(GL_BACK);481glEnable(GL_CULL_FACE);482cull_mode = RS::CULL_MODE_BACK;483484glDepthMask(GL_FALSE);485current_depth_draw_enabled = false;486glDisable(GL_DEPTH_TEST);487current_depth_test_enabled = false;488489glDepthFunc(GL_GEQUAL);490current_depth_function = GL_GEQUAL;491492glDisable(GL_STENCIL_TEST);493current_stencil_test_enabled = false;494glStencilMask(255);495current_stencil_write_mask = 255;496glStencilFunc(GL_ALWAYS, 0, 255);497current_stencil_compare = GL_ALWAYS;498current_stencil_reference = 0;499current_stencil_compare_mask = 255;500}501502void set_gl_cull_mode(RS::CullMode p_mode) {503if (cull_mode != p_mode) {504if (p_mode == RS::CULL_MODE_DISABLED) {505glDisable(GL_CULL_FACE);506} else {507if (cull_mode == RS::CULL_MODE_DISABLED) {508// Last time was disabled, so enable and set proper face.509glEnable(GL_CULL_FACE);510}511glCullFace(p_mode == RS::CULL_MODE_FRONT ? GL_FRONT : GL_BACK);512}513cull_mode = p_mode;514}515}516517void enable_gl_blend(bool p_enabled) {518if (current_blend_enabled != p_enabled) {519if (p_enabled) {520glEnable(GL_BLEND);521} else {522glDisable(GL_BLEND);523}524current_blend_enabled = p_enabled;525}526}527528void enable_gl_scissor_test(bool p_enabled) {529if (current_scissor_test_enabled != p_enabled) {530if (p_enabled) {531glEnable(GL_SCISSOR_TEST);532} else {533glDisable(GL_SCISSOR_TEST);534}535current_scissor_test_enabled = p_enabled;536}537}538539void enable_gl_depth_draw(bool p_enabled) {540if (current_depth_draw_enabled != p_enabled) {541glDepthMask(p_enabled ? GL_TRUE : GL_FALSE);542current_depth_draw_enabled = p_enabled;543}544}545546void enable_gl_depth_test(bool p_enabled) {547if (current_depth_test_enabled != p_enabled) {548if (p_enabled) {549glEnable(GL_DEPTH_TEST);550} else {551glDisable(GL_DEPTH_TEST);552}553current_depth_test_enabled = p_enabled;554}555}556557void set_gl_depth_func(GLenum p_depth_func) {558if (current_depth_function != p_depth_func) {559glDepthFunc(p_depth_func);560current_depth_function = p_depth_func;561}562}563564void enable_gl_stencil_test(bool p_enabled) {565if (current_stencil_test_enabled != p_enabled) {566if (p_enabled) {567glEnable(GL_STENCIL_TEST);568} else {569glDisable(GL_STENCIL_TEST);570}571current_stencil_test_enabled = p_enabled;572}573}574575void set_gl_stencil_func(GLenum p_compare, GLint p_reference, GLenum p_compare_mask) {576if (current_stencil_compare != p_compare || current_stencil_reference != p_reference || current_stencil_compare_mask != p_compare_mask) {577glStencilFunc(p_compare, p_reference, p_compare_mask);578current_stencil_compare = p_compare;579current_stencil_reference = p_reference;580current_stencil_compare_mask = p_compare_mask;581}582}583584void set_gl_stencil_write_mask(GLuint p_mask) {585if (current_stencil_write_mask != p_mask) {586glStencilMask(p_mask);587current_stencil_write_mask = p_mask;588}589}590591void set_gl_stencil_op(GLenum p_op_fail, GLenum p_op_dpfail, GLenum p_op_dppass) {592if (current_stencil_op_fail != p_op_fail || current_stencil_op_dpfail != p_op_dpfail || current_stencil_op_dppass != p_op_dppass) {593glStencilOp(p_op_fail, p_op_dpfail, p_op_dppass);594current_stencil_op_fail = p_op_fail;595current_stencil_op_dpfail = p_op_dpfail;596current_stencil_op_dppass = p_op_dppass;597}598}599600GLenum current_stencil_compare = GL_ALWAYS;601GLuint current_stencil_compare_mask = 255;602GLuint current_stencil_write_mask = 255;603GLint current_stencil_reference = 0;604GLenum current_stencil_op_fail = GL_KEEP;605GLenum current_stencil_op_dpfail = GL_KEEP;606GLenum current_stencil_op_dppass = GL_KEEP;607bool current_stencil_test_enabled = false;608609bool texscreen_copied = false;610bool used_screen_texture = false;611bool used_normal_texture = false;612bool used_depth_texture = false;613bool used_opaque_stencil = false;614615LightData *omni_lights = nullptr;616LightData *spot_lights = nullptr;617ShadowData *positional_shadows = nullptr;618619InstanceSort<GLES3::LightInstance> *omni_light_sort;620InstanceSort<GLES3::LightInstance> *spot_light_sort;621GLuint omni_light_buffer = 0;622GLuint spot_light_buffer = 0;623GLuint positional_shadow_buffer = 0;624uint32_t omni_light_count = 0;625uint32_t spot_light_count = 0;626RS::ShadowQuality positional_shadow_quality = RS::ShadowQuality::SHADOW_QUALITY_SOFT_LOW;627628DirectionalLightData *directional_lights = nullptr;629GLuint directional_light_buffer = 0;630DirectionalShadowData *directional_shadows = nullptr;631GLuint directional_shadow_buffer = 0;632RS::ShadowQuality directional_shadow_quality = RS::ShadowQuality::SHADOW_QUALITY_SOFT_LOW;633} scene_state;634635struct RenderListParameters {636GeometryInstanceSurface **elements = nullptr;637int element_count = 0;638bool reverse_cull = false;639uint64_t spec_constant_base_flags = 0;640bool force_wireframe = false;641Vector2 uv_offset = Vector2(0, 0);642643RenderListParameters(GeometryInstanceSurface **p_elements, int p_element_count, bool p_reverse_cull, uint64_t p_spec_constant_base_flags, bool p_force_wireframe = false, Vector2 p_uv_offset = Vector2()) {644elements = p_elements;645element_count = p_element_count;646reverse_cull = p_reverse_cull;647spec_constant_base_flags = p_spec_constant_base_flags;648force_wireframe = p_force_wireframe;649uv_offset = p_uv_offset;650}651};652653struct RenderList {654LocalVector<GeometryInstanceSurface *> elements;655656void clear() {657elements.clear();658}659660//should eventually be replaced by radix661662struct SortByKey {663_FORCE_INLINE_ bool operator()(const GeometryInstanceSurface *A, const GeometryInstanceSurface *B) const {664return (A->sort.sort_key2 == B->sort.sort_key2) ? (A->sort.sort_key1 < B->sort.sort_key1) : (A->sort.sort_key2 < B->sort.sort_key2);665}666};667668void sort_by_key() {669SortArray<GeometryInstanceSurface *, SortByKey> sorter;670sorter.sort(elements.ptr(), elements.size());671}672673void sort_by_key_range(uint32_t p_from, uint32_t p_size) {674SortArray<GeometryInstanceSurface *, SortByKey> sorter;675sorter.sort(elements.ptr() + p_from, p_size);676}677678struct SortByDepth {679_FORCE_INLINE_ bool operator()(const GeometryInstanceSurface *A, const GeometryInstanceSurface *B) const {680return (A->owner->depth < B->owner->depth);681}682};683684void sort_by_depth() { //used for shadows685686SortArray<GeometryInstanceSurface *, SortByDepth> sorter;687sorter.sort(elements.ptr(), elements.size());688}689690struct SortByReverseDepthAndPriority {691_FORCE_INLINE_ bool operator()(const GeometryInstanceSurface *A, const GeometryInstanceSurface *B) const {692return (A->sort.priority == B->sort.priority) ? (A->owner->depth > B->owner->depth) : (A->sort.priority < B->sort.priority);693}694};695696void sort_by_reverse_depth_and_priority() { //used for alpha697698SortArray<GeometryInstanceSurface *, SortByReverseDepthAndPriority> sorter;699sorter.sort(elements.ptr(), elements.size());700}701702_FORCE_INLINE_ void add_element(GeometryInstanceSurface *p_element) {703elements.push_back(p_element);704}705};706707RenderList render_list[RENDER_LIST_MAX];708709void _setup_lights(const RenderDataGLES3 *p_render_data, bool p_using_shadows, uint32_t &r_directional_light_count, uint32_t &r_omni_light_count, uint32_t &r_spot_light_count, uint32_t &r_directional_shadow_count);710void _setup_environment(const RenderDataGLES3 *p_render_data, bool p_no_fog, const Size2i &p_screen_size, bool p_flip_y, const Color &p_default_bg_color, bool p_pancake_shadows, float p_shadow_bias = 0.0);711void _fill_render_list(RenderListType p_render_list, const RenderDataGLES3 *p_render_data, PassMode p_pass_mode, bool p_append = false);712void _render_shadows(const RenderDataGLES3 *p_render_data, const Size2i &p_viewport_size = Size2i(1, 1));713void _render_shadow_pass(RID p_light, RID p_shadow_atlas, int p_pass, const PagedArray<RenderGeometryInstance *> &p_instances, float p_lod_distance_multiplier = 0, float p_screen_mesh_lod_threshold = 0.0, RenderingMethod::RenderInfo *p_render_info = nullptr, const Size2i &p_viewport_size = Size2i(1, 1), const Transform3D &p_main_cam_transform = Transform3D());714void _render_post_processing(const RenderDataGLES3 *p_render_data);715716template <PassMode p_pass_mode>717_FORCE_INLINE_ void _render_list_template(RenderListParameters *p_params, const RenderDataGLES3 *p_render_data, uint32_t p_from_element, uint32_t p_to_element, bool p_alpha_pass = false);718719protected:720double time;721double time_step = 0;722723bool screen_space_roughness_limiter = false;724float screen_space_roughness_limiter_amount = 0.25;725float screen_space_roughness_limiter_limit = 0.18;726727void _render_buffers_debug_draw(Ref<RenderSceneBuffersGLES3> p_render_buffers, RID p_shadow_atlas, GLuint p_fbo);728729/* Camera Attributes */730731struct CameraAttributes {732float exposure_multiplier = 1.0;733float exposure_normalization = 1.0;734};735736bool use_physical_light_units = false;737mutable RID_Owner<CameraAttributes, true> camera_attributes_owner;738739/* Environment */740741RS::EnvironmentSSAOQuality ssao_quality = RS::ENV_SSAO_QUALITY_MEDIUM;742bool ssao_half_size = false;743float ssao_adaptive_target = 0.5;744int ssao_blur_passes = 2;745float ssao_fadeout_from = 50.0;746float ssao_fadeout_to = 300.0;747748bool glow_bicubic_upscale = false;749RS::EnvironmentSSRRoughnessQuality ssr_roughness_quality = RS::ENV_SSR_ROUGHNESS_QUALITY_LOW;750751bool lightmap_bicubic_upscale = false;752753/* Sky */754755struct SkyGlobals {756float fog_aerial_perspective = 0.0;757Color fog_light_color;758float fog_sun_scatter = 0.0;759bool fog_enabled = false;760float fog_density = 0.0;761float z_far = 0.0;762uint32_t directional_light_count = 0;763764DirectionalLightData *directional_lights = nullptr;765DirectionalLightData *last_frame_directional_lights = nullptr;766uint32_t last_frame_directional_light_count = 0;767GLuint directional_light_buffer = 0;768769RID shader_default_version;770RID default_material;771RID default_shader;772RID fog_material;773RID fog_shader;774GLuint screen_triangle = 0;775GLuint screen_triangle_array = 0;776uint32_t max_directional_lights = 4;777uint32_t roughness_layers = 8;778} sky_globals;779780struct Sky {781// Screen Buffers782GLuint half_res_pass = 0;783GLuint half_res_framebuffer = 0;784GLuint quarter_res_pass = 0;785GLuint quarter_res_framebuffer = 0;786Size2i screen_size = Size2i(0, 0);787788// Radiance Cubemap789GLuint radiance = 0;790GLuint radiance_framebuffer = 0;791GLuint raw_radiance = 0;792793RID material;794GLuint uniform_buffer;795796int radiance_size = 256;797int mipmap_count = 1;798799RS::SkyMode mode = RS::SKY_MODE_AUTOMATIC;800801//ReflectionData reflection;802bool reflection_dirty = false;803bool dirty = false;804int processing_layer = 0;805Sky *dirty_list = nullptr;806float baked_exposure = 1.0;807808//State to track when radiance cubemap needs updating809GLES3::SkyMaterialData *prev_material = nullptr;810Vector3 prev_position = Vector3(0.0, 0.0, 0.0);811float prev_time = 0.0f;812};813814Sky *dirty_sky_list = nullptr;815mutable RID_Owner<Sky, true> sky_owner;816817void _setup_sky(const RenderDataGLES3 *p_render_data, const PagedArray<RID> &p_lights, const Projection &p_projection, const Transform3D &p_transform, const Size2i p_screen_size);818void _invalidate_sky(Sky *p_sky);819void _update_dirty_skys();820void _update_sky_radiance(RID p_env, const Projection &p_projection, const Transform3D &p_transform, float p_sky_energy_multiplier);821void _draw_sky(RID p_env, const Projection &p_projection, const Transform3D &p_transform, float p_sky_energy_multiplier, float p_luminance_multiplier, bool p_use_multiview, bool p_flip_y, bool p_apply_color_adjustments_in_post);822void _free_sky_data(Sky *p_sky);823824// Needed for a single argument calls (material and uv2).825PagedArrayPool<RenderGeometryInstance *> cull_argument_pool;826PagedArray<RenderGeometryInstance *> cull_argument;827828public:829static RasterizerSceneGLES3 *get_singleton() { return singleton; }830831RasterizerCanvasGLES3 *canvas = nullptr;832833RenderGeometryInstance *geometry_instance_create(RID p_base) override;834void geometry_instance_free(RenderGeometryInstance *p_geometry_instance) override;835836uint32_t geometry_instance_get_pair_mask() override;837838/* PIPELINES */839840virtual void mesh_generate_pipelines(RID p_mesh, bool p_background_compilation) override {}841virtual uint32_t get_pipeline_compilations(RS::PipelineSource p_source) override { return 0; }842843/* SDFGI UPDATE */844845void sdfgi_update(const Ref<RenderSceneBuffers> &p_render_buffers, RID p_environment, const Vector3 &p_world_position) override {}846int sdfgi_get_pending_region_count(const Ref<RenderSceneBuffers> &p_render_buffers) const override {847return 0;848}849AABB sdfgi_get_pending_region_bounds(const Ref<RenderSceneBuffers> &p_render_buffers, int p_region) const override {850return AABB();851}852uint32_t sdfgi_get_pending_region_cascade(const Ref<RenderSceneBuffers> &p_render_buffers, int p_region) const override {853return 0;854}855856/* SKY API */857858RID sky_allocate() override;859void sky_initialize(RID p_rid) override;860void sky_set_radiance_size(RID p_sky, int p_radiance_size) override;861void sky_set_mode(RID p_sky, RS::SkyMode p_mode) override;862void sky_set_material(RID p_sky, RID p_material) override;863Ref<Image> sky_bake_panorama(RID p_sky, float p_energy, bool p_bake_irradiance, const Size2i &p_size) override;864float sky_get_baked_exposure(RID p_sky) const;865866/* ENVIRONMENT API */867868void environment_glow_set_use_bicubic_upscale(bool p_enable) override;869870void environment_set_ssr_roughness_quality(RS::EnvironmentSSRRoughnessQuality p_quality) override;871872void environment_set_ssao_quality(RS::EnvironmentSSAOQuality p_quality, bool p_half_size, float p_adaptive_target, int p_blur_passes, float p_fadeout_from, float p_fadeout_to) override;873874void environment_set_ssil_quality(RS::EnvironmentSSILQuality p_quality, bool p_half_size, float p_adaptive_target, int p_blur_passes, float p_fadeout_from, float p_fadeout_to) override;875876void environment_set_sdfgi_ray_count(RS::EnvironmentSDFGIRayCount p_ray_count) override;877void environment_set_sdfgi_frames_to_converge(RS::EnvironmentSDFGIFramesToConverge p_frames) override;878void environment_set_sdfgi_frames_to_update_light(RS::EnvironmentSDFGIFramesToUpdateLight p_update) override;879880void environment_set_volumetric_fog_volume_size(int p_size, int p_depth) override;881void environment_set_volumetric_fog_filter_active(bool p_enable) override;882883Ref<Image> environment_bake_panorama(RID p_env, bool p_bake_irradiance, const Size2i &p_size) override;884885_FORCE_INLINE_ bool is_using_physical_light_units() {886return use_physical_light_units;887}888889void positional_soft_shadow_filter_set_quality(RS::ShadowQuality p_quality) override;890void directional_soft_shadow_filter_set_quality(RS::ShadowQuality p_quality) override;891892RID fog_volume_instance_create(RID p_fog_volume) override;893void fog_volume_instance_set_transform(RID p_fog_volume_instance, const Transform3D &p_transform) override;894void fog_volume_instance_set_active(RID p_fog_volume_instance, bool p_active) override;895RID fog_volume_instance_get_volume(RID p_fog_volume_instance) const override;896Vector3 fog_volume_instance_get_position(RID p_fog_volume_instance) const override;897898RID voxel_gi_instance_create(RID p_voxel_gi) override;899void voxel_gi_instance_set_transform_to_data(RID p_probe, const Transform3D &p_xform) override;900bool voxel_gi_needs_update(RID p_probe) const override;901void voxel_gi_update(RID p_probe, bool p_update_light_instances, const Vector<RID> &p_light_instances, const PagedArray<RenderGeometryInstance *> &p_dynamic_objects) override;902903void voxel_gi_set_quality(RS::VoxelGIQuality) override;904905void render_scene(const Ref<RenderSceneBuffers> &p_render_buffers, const CameraData *p_camera_data, const CameraData *p_prev_camera_data, const PagedArray<RenderGeometryInstance *> &p_instances, const PagedArray<RID> &p_lights, const PagedArray<RID> &p_reflection_probes, const PagedArray<RID> &p_voxel_gi_instances, const PagedArray<RID> &p_decals, const PagedArray<RID> &p_lightmaps, const PagedArray<RID> &p_fog_volumes, RID p_environment, RID p_camera_attributes, RID p_compositor, RID p_shadow_atlas, RID p_occluder_debug_tex, RID p_reflection_atlas, RID p_reflection_probe, int p_reflection_probe_pass, float p_screen_mesh_lod_threshold, const RenderShadowData *p_render_shadows, int p_render_shadow_count, const RenderSDFGIData *p_render_sdfgi_regions, int p_render_sdfgi_region_count, const RenderSDFGIUpdateData *p_sdfgi_update_data = nullptr, RenderingMethod::RenderInfo *r_render_info = nullptr) override;906void render_material(const Transform3D &p_cam_transform, const Projection &p_cam_projection, bool p_cam_orthogonal, const PagedArray<RenderGeometryInstance *> &p_instances, RID p_framebuffer, const Rect2i &p_region) override;907void render_particle_collider_heightfield(RID p_collider, const Transform3D &p_transform, const PagedArray<RenderGeometryInstance *> &p_instances) override;908909void set_scene_pass(uint64_t p_pass) override {910scene_pass = p_pass;911}912913_FORCE_INLINE_ uint64_t get_scene_pass() {914return scene_pass;915}916917void set_time(double p_time, double p_step) override;918void set_debug_draw_mode(RS::ViewportDebugDraw p_debug_draw) override;919_FORCE_INLINE_ RS::ViewportDebugDraw get_debug_draw_mode() const {920return debug_draw;921}922923Ref<RenderSceneBuffers> render_buffers_create() override;924void gi_set_use_half_resolution(bool p_enable) override;925926void screen_space_roughness_limiter_set_active(bool p_enable, float p_amount, float p_curve) override;927bool screen_space_roughness_limiter_is_active() const override;928929void sub_surface_scattering_set_quality(RS::SubSurfaceScatteringQuality p_quality) override;930void sub_surface_scattering_set_scale(float p_scale, float p_depth_scale) override;931932TypedArray<Image> bake_render_uv2(RID p_base, const TypedArray<RID> &p_material_overrides, const Size2i &p_image_size) override;933void _render_uv2(const PagedArray<RenderGeometryInstance *> &p_instances, GLuint p_framebuffer, const Rect2i &p_region);934935bool free(RID p_rid) override;936void update() override;937void sdfgi_set_debug_probe_select(const Vector3 &p_position, const Vector3 &p_dir) override;938939void decals_set_filter(RS::DecalFilter p_filter) override;940void light_projectors_set_filter(RS::LightProjectorFilter p_filter) override;941virtual void lightmaps_set_bicubic_filter(bool p_enable) override;942943RasterizerSceneGLES3();944~RasterizerSceneGLES3();945};946947#endif // GLES3_ENABLED948949950