EEVEE-Next: Per probe viewport display #114176

Merged
Miguel Pozo merged 8 commits from pragma37/blender:pull-eevee-probes-display into main 2023-11-02 17:08:22 +01:00
11 changed files with 140 additions and 1 deletions
Showing only changes of commit 200e5bfaa3 - Show all commits

View File

@ -166,6 +166,10 @@ class DATA_PT_lightprobe_eevee_next(DataButtonsPanel, Panel):
sub.prop(probe, "clip_start", text="Clipping Start")
sub.prop(probe, "clip_end", text="End")
row = col.row(align=True)
row.prop(probe, "show_data_size", text="Display Data")
row.prop(probe, "show_data", text="", toggle=True)
elif probe.type == 'PLANE':
col = layout.column()
row = col.row()

View File

@ -491,6 +491,8 @@ set(GLSL_SRC
engines/eevee_next/shaders/eevee_depth_of_field_tiles_flatten_comp.glsl
engines/eevee_next/shaders/eevee_display_probe_grid_frag.glsl
engines/eevee_next/shaders/eevee_display_probe_grid_vert.glsl
engines/eevee_next/shaders/eevee_display_probe_reflection_frag.glsl
engines/eevee_next/shaders/eevee_display_probe_reflection_vert.glsl
engines/eevee_next/shaders/eevee_film_comp.glsl
engines/eevee_next/shaders/eevee_film_cryptomatte_post_comp.glsl
engines/eevee_next/shaders/eevee_film_frag.glsl

View File

@ -192,6 +192,8 @@ void ReflectionProbeModule::init()
pass.bind_texture("reflection_probes_tx", &probes_tx_);
pass.dispatch(int2(1, 1));
}
do_display_draw_ = false;
}
void ReflectionProbeModule::begin_sync()
@ -269,7 +271,7 @@ void ReflectionProbeModule::sync_object(Object *ob, ObjectHandle &ob_handle)
return;
}
ReflectionProbe &probe = probes_.lookup_or_add_cb(ob_handle.object_key.hash(), []() {
ReflectionProbe &probe = probes_.lookup_or_add_cb(ob_handle.object_key.hash(), [&]() {
ReflectionProbe probe = {};
probe.do_render = true;
probe.type = ReflectionProbe::Type::PROBE;
@ -315,6 +317,9 @@ void ReflectionProbeModule::sync_object(Object *ob, ObjectHandle &ob_handle)
probe.influence_scale = 1.0 / max_ff(1e-8f, influence_falloff);
probe.influence_bias = probe.influence_scale;
probe.parallax_distance = parallax_distance / influence_distance;
probe.viewport_display = light_probe.flag & LIGHTPROBE_FLAG_SHOW_DATA;
probe.viewport_display_size = light_probe.show_data_size;
}
ReflectionProbeAtlasCoordinate ReflectionProbeModule::find_empty_atlas_region(
@ -539,6 +544,22 @@ void ReflectionProbeModule::set_view(View & /*view*/)
}
data_buf_.push_update();
do_display_draw_ = DRW_state_draw_support() && probe_active.size() > 0;
if (do_display_draw_) {
int display_index = 0;
for (int i : probe_active.index_range()) {
if (probe_active[i]->viewport_display) {
display_data_buf_.get_or_resize(display_index++) = {
i, probe_active[i]->viewport_display_size};
}
}
do_display_draw_ = display_index > 0;
if (do_display_draw_) {
display_data_buf_.resize(display_index);
display_data_buf_.push_update();
}
}
/* Add one for world probe. */
reflection_probe_count_ = probe_active.size() + 1;
dispatch_probe_select_.x = divide_ceil_u(reflection_probe_count_,
@ -551,6 +572,24 @@ ReflectionProbeAtlasCoordinate ReflectionProbeModule::world_atlas_coord_get() co
return probes_.lookup(world_object_key_).atlas_coord;
}
void ReflectionProbeModule::viewport_draw(View &view, GPUFrameBuffer *view_fb)
{
if (!do_display_draw_) {
return;
}
viewport_display_ps_.init();
viewport_display_ps_.state_set(DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH |
DRW_STATE_DEPTH_LESS_EQUAL | DRW_STATE_CULL_BACK);
viewport_display_ps_.framebuffer_set(&view_fb);
viewport_display_ps_.shader_set(instance_.shaders.static_shader_get(DISPLAY_PROBE_REFLECTION));
bind_resources(viewport_display_ps_);
viewport_display_ps_.bind_ssbo("display_data_buf", display_data_buf_);
viewport_display_ps_.draw_procedural(GPU_PRIM_TRIS, 1, display_data_buf_.size() * 6);
instance_.manager->submit(viewport_display_ps_, view);
}
/** \} */
/* -------------------------------------------------------------------- */

View File

@ -53,6 +53,10 @@ struct ReflectionProbe : ReflectionProbeData {
*/
float2 clipping_distances;
/** Display debug spheres in the viewport. */
bool viewport_display;
float viewport_display_size;
ReflectionProbe()
{
this->atlas_coord.layer_subdivision = -1;
@ -123,6 +127,11 @@ class ReflectionProbeModule {
bool update_probes_next_sample_ = false;
bool update_probes_this_sample_ = false;
/** Viewport data display drawing. */
bool do_display_draw_ = false;
ReflectionProbeDisplayDataBuf display_data_buf_;
PassSimple viewport_display_ps_ = {"ReflectionProbeModule.Viewport Display"};
public:
ReflectionProbeModule(Instance &instance) : instance_(instance) {}
@ -133,6 +142,8 @@ class ReflectionProbeModule {
void sync_object(Object *ob, ObjectHandle &ob_handle);
void end_sync();
void viewport_draw(View &view, GPUFrameBuffer *view_fb);
template<typename PassType> void bind_resources(PassType &pass)
{
pass.bind_texture(REFLECTION_PROBE_TEX_SLOT, &probes_tx_);

View File

@ -120,6 +120,8 @@ const char *ShaderModule::static_shader_create_info_name_get(eShaderType shader_
return "eevee_debug_irradiance_grid";
case DISPLAY_PROBE_GRID:
return "eevee_display_probe_grid";
case DISPLAY_PROBE_REFLECTION:
return "eevee_display_probe_reflection";
case DOF_BOKEH_LUT:
return "eevee_depth_of_field_bokeh_lut";
case DOF_DOWNSAMPLE:

View File

@ -41,6 +41,7 @@ enum eShaderType {
DEBUG_IRRADIANCE_GRID,
DISPLAY_PROBE_GRID,
DISPLAY_PROBE_REFLECTION,
DOF_BOKEH_LUT,
DOF_DOWNSAMPLE,

View File

@ -1348,6 +1348,15 @@ struct ReflectionProbeData {
};
BLI_STATIC_ASSERT_ALIGN(ReflectionProbeData, 16)
/** Viewport Display Pass. */
struct ReflectionProbeDisplayData {
int probe_index;
float display_size;
float _pad0;
float _pad1;
};
BLI_STATIC_ASSERT_ALIGN(ReflectionProbeDisplayData, 16)
struct ProbePlanarData {
/** Matrices used to render the planar capture. */
float4x4 viewmat;
@ -1484,6 +1493,7 @@ using RayTraceTileBuf = draw::StorageArrayBuffer<uint, 1024, true>;
using SubsurfaceTileBuf = RayTraceTileBuf;
using ReflectionProbeDataBuf =
draw::UniformArrayBuffer<ReflectionProbeData, REFLECTION_PROBES_MAX>;
using ReflectionProbeDisplayDataBuf = draw::StorageArrayBuffer<ReflectionProbeDisplayData>;
using ProbePlanarDataBuf = draw::UniformArrayBuffer<ProbePlanarData, PLANAR_PROBES_MAX>;
using SamplingDataBuf = draw::StorageBuffer<SamplingData>;
using ShadowStatisticsBuf = draw::StorageBuffer<ShadowStatistics>;

View File

@ -150,6 +150,7 @@ void ShadingView::render()
inst_.hiz_buffer.debug_draw(render_view_new_, combined_fb_);
inst_.shadows.debug_draw(render_view_new_, combined_fb_);
inst_.irradiance_cache.viewport_draw(render_view_new_, combined_fb_);
inst_.reflection_probes.viewport_draw(render_view_new_, combined_fb_);
inst_.ambient_occlusion.render_pass(render_view_new_);

View File

@ -0,0 +1,22 @@
/* SPDX-FileCopyrightText: 2023 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
#pragma BLENDER_REQUIRE(draw_view_lib.glsl)
#pragma BLENDER_REQUIRE(eevee_reflection_probe_lib.glsl)
void main()
{
float dist_sqr = dot(lP, lP);
/* Discard outside the circle. */
if (dist_sqr > 1.0) {
discard;
return;
}
vec3 vN = vec3(lP, sqrt(max(0.0, 1.0 - dist_sqr)));
vec3 N = drw_normal_view_to_world(vN);
out_color = reflection_probes_sample(N, 0, reflection_probe_buf[probe_index].atlas_coord);
}

View File

@ -0,0 +1,34 @@
/* SPDX-FileCopyrightText: 2023 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
#pragma BLENDER_REQUIRE(draw_view_lib.glsl)
#pragma BLENDER_REQUIRE(eevee_lightprobe_lib.glsl)
void main()
{
/* Constant array moved inside function scope.
* Minimizes local register allocation in MSL. */
const vec2 pos[6] = vec2[6](vec2(-1.0, -1.0),
vec2(1.0, -1.0),
vec2(-1.0, 1.0),
vec2(1.0, -1.0),
vec2(1.0, 1.0),
vec2(-1.0, 1.0));
lP = pos[gl_VertexID % 6];
int display_index = gl_VertexID / 6;
probe_index = display_data_buf[display_index].probe_index;
float sphere_radius = display_data_buf[display_index].display_size;
vec3 ws_probe_pos = reflection_probe_buf[probe_index].location;
vec3 vs_offset = vec3(lP, 0.0) * sphere_radius;
vec3 vP = drw_point_world_to_view(ws_probe_pos) + vs_offset;
gl_Position = drw_point_view_to_homogenous(vP);
/* Small bias to let the icon draw without Z-fighting. */
gl_Position.z += 0.0001;
}

View File

@ -50,4 +50,17 @@ GPU_SHADER_CREATE_INFO(eevee_reflection_probe_select)
.compute_source("eevee_reflection_probe_select_comp.glsl")
.do_static_compilation(true);
GPU_SHADER_INTERFACE_INFO(eevee_display_probe_reflection_iface, "")
.smooth(Type::VEC2, "lP")
.flat(Type::INT, "probe_index");
GPU_SHADER_CREATE_INFO(eevee_display_probe_reflection)
.additional_info("eevee_shared", "draw_view", "eevee_reflection_probe_data")
.storage_buf(0, Qualifier::READ, "ReflectionProbeDisplayData", "display_data_buf[]")
.vertex_source("eevee_display_probe_reflection_vert.glsl")
.vertex_out(eevee_display_probe_reflection_iface)
.fragment_source("eevee_display_probe_reflection_frag.glsl")
.fragment_out(0, Type::VEC4, "out_color")
.do_static_compilation(true);
/** \} */