Skip to content

Commit

Permalink
Add a reflection mask to the reflection probes.
Browse files Browse the repository at this point in the history
Co-authored-by: Bastiaan Olij <[email protected]>
  • Loading branch information
m4rr5 and BastiaanOlij committed Dec 12, 2023
1 parent 84692c6 commit 133122e
Show file tree
Hide file tree
Showing 13 changed files with 57 additions and 3 deletions.
6 changes: 5 additions & 1 deletion doc/classes/ReflectionProbe.xml
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@
[b]Note:[/b] To better fit rectangle-shaped rooms that are not aligned to the grid, you can rotate the [ReflectionProbe] node.
</member>
<member name="cull_mask" type="int" setter="set_cull_mask" getter="get_cull_mask" default="1048575">
Sets the cull mask which determines what objects are drawn by this probe. Every [VisualInstance3D] with a layer included in this cull mask will be rendered by the probe. To improve performance, it is best to only include large objects which are likely to take up a lot of space in the reflection.
Sets the cull mask which determines what objects have reflections applied from this probe. Every [VisualInstance3D] with a layer included in this cull mask will have reflections applied from this probe. See also [member reflection_mask], which can be used to exclude objects from appearing in the reflection while still making them affected by the [ReflectionProbe].
</member>
<member name="enable_shadows" type="bool" setter="set_enable_shadows" getter="are_shadows_enabled" default="false">
If [code]true[/code], computes shadows in the reflection probe. This makes the reflection probe slower to render; you may want to disable this if using the [constant UPDATE_ALWAYS] [member update_mode].
Expand All @@ -50,6 +50,10 @@
<member name="origin_offset" type="Vector3" setter="set_origin_offset" getter="get_origin_offset" default="Vector3(0, 0, 0)">
Sets the origin offset to be used when this [ReflectionProbe] is in [member box_projection] mode. This can be set to a non-zero value to ensure a reflection fits a rectangle-shaped room, while reducing the number of objects that "get in the way" of the reflection.
</member>
<member name="reflection_mask" type="int" setter="set_reflection_mask" getter="get_reflection_mask" default="1048575">
Sets the reflection mask which determines what objects are drawn by this probe. Every [VisualInstance3D] with a layer included in this reflection mask will be rendered by the probe. It is best to only include large objects which are likely to take up a lot of space in the reflection in order to save on rendering cost.
This can also be used to prevent an object from reflecting upon itself (for instance, a [ReflectionProbe] centered on a vehicle).
</member>
<member name="size" type="Vector3" setter="set_size" getter="get_size" default="Vector3(20, 20, 20)">
The size of the reflection probe. The larger the size, the more space covered by the probe, which will lower the perceived resolution. It is best to keep the size only as large as you need it.
[b]Note:[/b] To better fit areas that are not aligned to the grid, you can rotate the [ReflectionProbe] node.
Expand Down
2 changes: 1 addition & 1 deletion doc/classes/RenderingServer.xml
Original file line number Diff line number Diff line change
Expand Up @@ -2894,7 +2894,7 @@
<param index="0" name="probe" type="RID" />
<param index="1" name="layers" type="int" />
<description>
Sets the render cull mask for this reflection probe. Only instances with a matching cull mask will be rendered by this probe. Equivalent to [member ReflectionProbe.cull_mask].
Sets the render cull mask for this reflection probe. Only instances with a matching cull mask will have reflections applied from this probe. Equivalent to [member ReflectionProbe.cull_mask].
</description>
</method>
<method name="reflection_probe_set_enable_box_projection">
Expand Down
7 changes: 7 additions & 0 deletions drivers/gles3/storage/light_storage.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -468,6 +468,9 @@ void LightStorage::reflection_probe_set_enable_shadows(RID p_probe, bool p_enabl
void LightStorage::reflection_probe_set_cull_mask(RID p_probe, uint32_t p_layers) {
}

void LightStorage::reflection_probe_set_reflection_mask(RID p_probe, uint32_t p_layers) {
}

void LightStorage::reflection_probe_set_resolution(RID p_probe, int p_resolution) {
}

Expand All @@ -483,6 +486,10 @@ uint32_t LightStorage::reflection_probe_get_cull_mask(RID p_probe) const {
return 0;
}

uint32_t LightStorage::reflection_probe_get_reflection_mask(RID p_probe) const {
return 0;
}

Vector3 LightStorage::reflection_probe_get_size(RID p_probe) const {
return Vector3();
}
Expand Down
2 changes: 2 additions & 0 deletions drivers/gles3/storage/light_storage.h
Original file line number Diff line number Diff line change
Expand Up @@ -575,13 +575,15 @@ class LightStorage : public RendererLightStorage {
virtual void reflection_probe_set_enable_box_projection(RID p_probe, bool p_enable) override;
virtual void reflection_probe_set_enable_shadows(RID p_probe, bool p_enable) override;
virtual void reflection_probe_set_cull_mask(RID p_probe, uint32_t p_layers) override;
virtual void reflection_probe_set_reflection_mask(RID p_probe, uint32_t p_layers) override;
virtual void reflection_probe_set_resolution(RID p_probe, int p_resolution) override;
virtual void reflection_probe_set_mesh_lod_threshold(RID p_probe, float p_ratio) override;
virtual float reflection_probe_get_mesh_lod_threshold(RID p_probe) const override;

virtual AABB reflection_probe_get_aabb(RID p_probe) const override;
virtual RS::ReflectionProbeUpdateMode reflection_probe_get_update_mode(RID p_probe) const override;
virtual uint32_t reflection_probe_get_cull_mask(RID p_probe) const override;
virtual uint32_t reflection_probe_get_reflection_mask(RID p_probe) const override;
virtual Vector3 reflection_probe_get_size(RID p_probe) const override;
virtual Vector3 reflection_probe_get_origin_offset(RID p_probe) const override;
virtual float reflection_probe_get_origin_max_distance(RID p_probe) const override;
Expand Down
13 changes: 13 additions & 0 deletions scene/3d/reflection_probe.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -165,6 +165,15 @@ uint32_t ReflectionProbe::get_cull_mask() const {
return cull_mask;
}

void ReflectionProbe::set_reflection_mask(uint32_t p_layers) {
reflection_mask = p_layers;
RS::get_singleton()->reflection_probe_set_reflection_mask(probe, p_layers);
}

uint32_t ReflectionProbe::get_reflection_mask() const {
return reflection_mask;
}

void ReflectionProbe::set_update_mode(UpdateMode p_mode) {
update_mode = p_mode;
RS::get_singleton()->reflection_probe_set_update_mode(probe, RS::ReflectionProbeUpdateMode(p_mode));
Expand Down Expand Up @@ -237,6 +246,9 @@ void ReflectionProbe::_bind_methods() {
ClassDB::bind_method(D_METHOD("set_cull_mask", "layers"), &ReflectionProbe::set_cull_mask);
ClassDB::bind_method(D_METHOD("get_cull_mask"), &ReflectionProbe::get_cull_mask);

ClassDB::bind_method(D_METHOD("set_reflection_mask", "layers"), &ReflectionProbe::set_reflection_mask);
ClassDB::bind_method(D_METHOD("get_reflection_mask"), &ReflectionProbe::get_reflection_mask);

ClassDB::bind_method(D_METHOD("set_update_mode", "mode"), &ReflectionProbe::set_update_mode);
ClassDB::bind_method(D_METHOD("get_update_mode"), &ReflectionProbe::get_update_mode);

Expand All @@ -249,6 +261,7 @@ void ReflectionProbe::_bind_methods() {
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "interior"), "set_as_interior", "is_set_as_interior");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "enable_shadows"), "set_enable_shadows", "are_shadows_enabled");
ADD_PROPERTY(PropertyInfo(Variant::INT, "cull_mask", PROPERTY_HINT_LAYERS_3D_RENDER), "set_cull_mask", "get_cull_mask");
ADD_PROPERTY(PropertyInfo(Variant::INT, "reflection_mask", PROPERTY_HINT_LAYERS_3D_RENDER), "set_reflection_mask", "get_reflection_mask");
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "mesh_lod_threshold", PROPERTY_HINT_RANGE, "0,1024,0.1"), "set_mesh_lod_threshold", "get_mesh_lod_threshold");

ADD_GROUP("Ambient", "ambient_");
Expand Down
4 changes: 4 additions & 0 deletions scene/3d/reflection_probe.h
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,7 @@ class ReflectionProbe : public VisualInstance3D {
float mesh_lod_threshold = 1.0;

uint32_t cull_mask = (1 << 20) - 1;
uint32_t reflection_mask = (1 << 20) - 1;
UpdateMode update_mode = UPDATE_ONCE;

protected:
Expand Down Expand Up @@ -113,6 +114,9 @@ class ReflectionProbe : public VisualInstance3D {
void set_cull_mask(uint32_t p_layers);
uint32_t get_cull_mask() const;

void set_reflection_mask(uint32_t p_layers);
uint32_t get_reflection_mask() const;

void set_update_mode(UpdateMode p_mode);
UpdateMode get_update_mode() const;

Expand Down
2 changes: 2 additions & 0 deletions servers/rendering/dummy/storage/light_storage.h
Original file line number Diff line number Diff line change
Expand Up @@ -109,13 +109,15 @@ class LightStorage : public RendererLightStorage {
virtual void reflection_probe_set_enable_box_projection(RID p_probe, bool p_enable) override {}
virtual void reflection_probe_set_enable_shadows(RID p_probe, bool p_enable) override {}
virtual void reflection_probe_set_cull_mask(RID p_probe, uint32_t p_layers) override {}
virtual void reflection_probe_set_reflection_mask(RID p_probe, uint32_t p_layers) override {}
virtual void reflection_probe_set_resolution(RID p_probe, int p_resolution) override {}
virtual void reflection_probe_set_mesh_lod_threshold(RID p_probe, float p_ratio) override {}
virtual float reflection_probe_get_mesh_lod_threshold(RID p_probe) const override { return 0.0; }

virtual AABB reflection_probe_get_aabb(RID p_probe) const override { return AABB(); }
virtual RS::ReflectionProbeUpdateMode reflection_probe_get_update_mode(RID p_probe) const override { return RenderingServer::REFLECTION_PROBE_UPDATE_ONCE; }
virtual uint32_t reflection_probe_get_cull_mask(RID p_probe) const override { return 0; }
virtual uint32_t reflection_probe_get_reflection_mask(RID p_probe) const override { return 0; }
virtual Vector3 reflection_probe_get_size(RID p_probe) const override { return Vector3(); }
virtual Vector3 reflection_probe_get_origin_offset(RID p_probe) const override { return Vector3(); }
virtual float reflection_probe_get_origin_max_distance(RID p_probe) const override { return 0.0; }
Expand Down
15 changes: 15 additions & 0 deletions servers/rendering/renderer_rd/storage_rd/light_storage.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1119,6 +1119,14 @@ void LightStorage::reflection_probe_set_cull_mask(RID p_probe, uint32_t p_layers
reflection_probe->dependency.changed_notify(Dependency::DEPENDENCY_CHANGED_REFLECTION_PROBE);
}

void LightStorage::reflection_probe_set_reflection_mask(RID p_probe, uint32_t p_layers) {
ReflectionProbe *reflection_probe = reflection_probe_owner.get_or_null(p_probe);
ERR_FAIL_NULL(reflection_probe);

reflection_probe->reflection_mask = p_layers;
reflection_probe->dependency.changed_notify(Dependency::DEPENDENCY_CHANGED_REFLECTION_PROBE);
}

void LightStorage::reflection_probe_set_resolution(RID p_probe, int p_resolution) {
ReflectionProbe *reflection_probe = reflection_probe_owner.get_or_null(p_probe);
ERR_FAIL_NULL(reflection_probe);
Expand Down Expand Up @@ -1168,6 +1176,13 @@ uint32_t LightStorage::reflection_probe_get_cull_mask(RID p_probe) const {
return reflection_probe->cull_mask;
}

uint32_t LightStorage::reflection_probe_get_reflection_mask(RID p_probe) const {
const ReflectionProbe *reflection_probe = reflection_probe_owner.get_or_null(p_probe);
ERR_FAIL_NULL_V(reflection_probe, 0);

return reflection_probe->reflection_mask;
}

Vector3 LightStorage::reflection_probe_get_size(RID p_probe) const {
const ReflectionProbe *reflection_probe = reflection_probe_owner.get_or_null(p_probe);
ERR_FAIL_NULL_V(reflection_probe, Vector3());
Expand Down
3 changes: 3 additions & 0 deletions servers/rendering/renderer_rd/storage_rd/light_storage.h
Original file line number Diff line number Diff line change
Expand Up @@ -232,6 +232,7 @@ class LightStorage : public RendererLightStorage {
bool box_projection = false;
bool enable_shadows = false;
uint32_t cull_mask = (1 << 20) - 1;
uint32_t reflection_mask = (1 << 20) - 1;
float mesh_lod_threshold = 0.01;
float baked_exposure = 1.0;

Expand Down Expand Up @@ -797,6 +798,7 @@ class LightStorage : public RendererLightStorage {
virtual void reflection_probe_set_enable_box_projection(RID p_probe, bool p_enable) override;
virtual void reflection_probe_set_enable_shadows(RID p_probe, bool p_enable) override;
virtual void reflection_probe_set_cull_mask(RID p_probe, uint32_t p_layers) override;
virtual void reflection_probe_set_reflection_mask(RID p_probe, uint32_t p_layers) override;
virtual void reflection_probe_set_resolution(RID p_probe, int p_resolution) override;
virtual void reflection_probe_set_mesh_lod_threshold(RID p_probe, float p_ratio) override;

Expand All @@ -805,6 +807,7 @@ class LightStorage : public RendererLightStorage {
virtual AABB reflection_probe_get_aabb(RID p_probe) const override;
virtual RS::ReflectionProbeUpdateMode reflection_probe_get_update_mode(RID p_probe) const override;
virtual uint32_t reflection_probe_get_cull_mask(RID p_probe) const override;
virtual uint32_t reflection_probe_get_reflection_mask(RID p_probe) const override;
virtual Vector3 reflection_probe_get_size(RID p_probe) const override;
virtual Vector3 reflection_probe_get_origin_offset(RID p_probe) const override;
virtual float reflection_probe_get_origin_max_distance(RID p_probe) const override;
Expand Down
2 changes: 1 addition & 1 deletion servers/rendering/renderer_scene_cull.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3465,7 +3465,7 @@ bool RendererSceneCull::_render_reflection_probe_step(Instance *p_instance, int
camera_data.set_camera(xform, cm, false, false);

Ref<RenderSceneBuffers> render_buffers = RSG::light_storage->reflection_probe_atlas_get_render_buffers(scenario->reflection_atlas);
_render_scene(&camera_data, render_buffers, environment, RID(), RSG::light_storage->reflection_probe_get_cull_mask(p_instance->base), p_instance->scenario->self, RID(), shadow_atlas, reflection_probe->instance, p_step, mesh_lod_threshold, use_shadows);
_render_scene(&camera_data, render_buffers, environment, RID(), RSG::light_storage->reflection_probe_get_reflection_mask(p_instance->base), p_instance->scenario->self, RID(), shadow_atlas, reflection_probe->instance, p_step, mesh_lod_threshold, use_shadows);

} else {
//do roughness postprocess step until it believes it's done
Expand Down
1 change: 1 addition & 0 deletions servers/rendering/rendering_server_default.h
Original file line number Diff line number Diff line change
Expand Up @@ -401,6 +401,7 @@ class RenderingServerDefault : public RenderingServer {
FUNC2(reflection_probe_set_enable_box_projection, RID, bool)
FUNC2(reflection_probe_set_enable_shadows, RID, bool)
FUNC2(reflection_probe_set_cull_mask, RID, uint32_t)
FUNC2(reflection_probe_set_reflection_mask, RID, uint32_t)
FUNC2(reflection_probe_set_resolution, RID, int)
FUNC2(reflection_probe_set_mesh_lod_threshold, RID, float)

Expand Down
2 changes: 2 additions & 0 deletions servers/rendering/storage/light_storage.h
Original file line number Diff line number Diff line change
Expand Up @@ -118,11 +118,13 @@ class RendererLightStorage {
virtual void reflection_probe_set_enable_box_projection(RID p_probe, bool p_enable) = 0;
virtual void reflection_probe_set_enable_shadows(RID p_probe, bool p_enable) = 0;
virtual void reflection_probe_set_cull_mask(RID p_probe, uint32_t p_layers) = 0;
virtual void reflection_probe_set_reflection_mask(RID p_probe, uint32_t p_layers) = 0;
virtual void reflection_probe_set_mesh_lod_threshold(RID p_probe, float p_ratio) = 0;

virtual AABB reflection_probe_get_aabb(RID p_probe) const = 0;
virtual RS::ReflectionProbeUpdateMode reflection_probe_get_update_mode(RID p_probe) const = 0;
virtual uint32_t reflection_probe_get_cull_mask(RID p_probe) const = 0;
virtual uint32_t reflection_probe_get_reflection_mask(RID p_probe) const = 0;
virtual Vector3 reflection_probe_get_size(RID p_probe) const = 0;
virtual Vector3 reflection_probe_get_origin_offset(RID p_probe) const = 0;
virtual float reflection_probe_get_origin_max_distance(RID p_probe) const = 0;
Expand Down
1 change: 1 addition & 0 deletions servers/rendering_server.h
Original file line number Diff line number Diff line change
Expand Up @@ -572,6 +572,7 @@ class RenderingServer : public Object {
virtual void reflection_probe_set_enable_box_projection(RID p_probe, bool p_enable) = 0;
virtual void reflection_probe_set_enable_shadows(RID p_probe, bool p_enable) = 0;
virtual void reflection_probe_set_cull_mask(RID p_probe, uint32_t p_layers) = 0;
virtual void reflection_probe_set_reflection_mask(RID p_probe, uint32_t p_layers) = 0;
virtual void reflection_probe_set_resolution(RID p_probe, int p_resolution) = 0;
virtual void reflection_probe_set_mesh_lod_threshold(RID p_probe, float p_pixels) = 0;

Expand Down

0 comments on commit 133122e

Please sign in to comment.