From 7a41bd562bdb945fbb69a11ff31c1e607965a36a Mon Sep 17 00:00:00 2001 From: Sergey Yablokov Date: Mon, 29 Jul 2024 05:24:12 +0200 Subject: [PATCH] Doublesided area lights support --- SceneBase.h | 2 ++ internal/SceneCPU.cpp | 12 +++++++----- internal/SceneGPU.h | 8 +++++--- 3 files changed, 14 insertions(+), 8 deletions(-) diff --git a/SceneBase.h b/SceneBase.h index 87886cb3..f458bffd 100644 --- a/SceneBase.h +++ b/SceneBase.h @@ -233,6 +233,7 @@ struct spot_light_desc_t { struct rect_light_desc_t { float color[3] = {1.0f, 1.0f, 1.0f}; float width = 1.0f, height = 1.0f; + bool doublesided = false; bool sky_portal = false; bool visible = true; bool cast_shadow = true; @@ -245,6 +246,7 @@ struct rect_light_desc_t { struct disk_light_desc_t { float color[3] = {1.0f, 1.0f, 1.0f}; float size_x = 1.0f, size_y = 1.0f; + bool doublesided = false; bool sky_portal = false; bool visible = true; bool cast_shadow = true; diff --git a/internal/SceneCPU.cpp b/internal/SceneCPU.cpp index 503d8328..bcf78b9a 100644 --- a/internal/SceneCPU.cpp +++ b/internal/SceneCPU.cpp @@ -655,6 +655,7 @@ Ray::LightHandle Ray::Cpu::Scene::AddLight(const rect_light_desc_t &_l, const fl light_t l = {}; l.type = LIGHT_TYPE_RECT; + l.doublesided = _l.doublesided; l.visible = _l.visible; l.cast_shadow = _l.cast_shadow; l.sky_portal = _l.sky_portal; @@ -689,6 +690,7 @@ Ray::LightHandle Ray::Cpu::Scene::AddLight(const disk_light_desc_t &_l, const fl light_t l = {}; l.type = LIGHT_TYPE_DISK; + l.doublesided = _l.doublesided; l.visible = _l.visible; l.cast_shadow = _l.cast_shadow; l.sky_portal = _l.sky_portal; @@ -813,10 +815,10 @@ Ray::MeshInstanceHandle Ray::Cpu::Scene::AddMeshInstance(const mesh_instance_des new_lights.emplace_back(); light_t &new_light = new_lights.back(); - new_light.visible = 0; - new_light.cast_shadow = 1; new_light.type = LIGHT_TYPE_TRI; new_light.doublesided = (back_emissive != 0xffff) ? 1 : 0; + new_light.cast_shadow = 1; + new_light.visible = 0; new_light.sky_portal = 0; new_light.ray_visibility = mi.ray_visibility; new_light.ray_visibility &= ~RAY_TYPE_CAMERA_BIT; @@ -1258,7 +1260,7 @@ void Ray::Cpu::Scene::RebuildLightTree_nolock() { area = l.rect.area; axis = normalize(Ray::Cpu::cross(u, v)); - omega_n = 0.0f; // single normal + omega_n = l.doublesided ? PI : 0.0f; omega_e = PI / 2.0f; } break; case LIGHT_TYPE_DISK: { @@ -1272,7 +1274,7 @@ void Ray::Cpu::Scene::RebuildLightTree_nolock() { area = l.disk.area; axis = normalize(Ray::Cpu::cross(u, v)); - omega_n = 0.0f; // single normal + omega_n = l.doublesided ? PI : 0.0f; omega_e = PI / 2.0f; } break; case LIGHT_TYPE_TRI: { @@ -1297,7 +1299,7 @@ void Ray::Cpu::Scene::RebuildLightTree_nolock() { area = 0.5f * length(light_forward); axis = normalize(light_forward); - omega_n = PI; // normals in all directions (triangle lights are double-sided) + omega_n = l.doublesided ? PI : 0.0f; omega_e = PI / 2.0f; } break; case LIGHT_TYPE_ENV: { diff --git a/internal/SceneGPU.h b/internal/SceneGPU.h index 04e3246a..dc921c66 100644 --- a/internal/SceneGPU.h +++ b/internal/SceneGPU.h @@ -1257,6 +1257,7 @@ inline Ray::LightHandle Ray::NS::Scene::AddLight(const rect_light_desc_t &_l, co light_t l = {}; l.type = LIGHT_TYPE_RECT; + l.doublesided = _l.doublesided; l.visible = _l.visible; l.cast_shadow = _l.cast_shadow; l.sky_portal = _l.sky_portal; @@ -1291,6 +1292,7 @@ inline Ray::LightHandle Ray::NS::Scene::AddLight(const disk_light_desc_t &_l, co light_t l = {}; l.type = LIGHT_TYPE_DISK; + l.doublesided = _l.doublesided; l.visible = _l.visible; l.cast_shadow = _l.cast_shadow; l.sky_portal = _l.sky_portal; @@ -2276,7 +2278,7 @@ inline void Ray::NS::Scene::RebuildLightTree_nolock() { area = l.rect.area; axis = normalize(NS::cross(u, v)); - omega_n = 0.0f; // single normal + omega_n = l.doublesided ? PI : 0.0f; omega_e = PI / 2.0f; } break; case LIGHT_TYPE_DISK: { @@ -2290,7 +2292,7 @@ inline void Ray::NS::Scene::RebuildLightTree_nolock() { area = l.disk.area; axis = normalize(NS::cross(u, v)); - omega_n = 0.0f; // single normal + omega_n = l.doublesided ? PI : 0.0f; omega_e = PI / 2.0f; } break; case LIGHT_TYPE_TRI: { @@ -2315,7 +2317,7 @@ inline void Ray::NS::Scene::RebuildLightTree_nolock() { area = 0.5f * length(light_forward); axis = normalize(light_forward); - omega_n = PI; // normals in all directions (triangle lights are double-sided) + omega_n = l.doublesided ? PI : 0.0f; omega_e = PI / 2.0f; } break; case LIGHT_TYPE_ENV: {