diff --git a/intern/cycles/kernel/osl/shaders/node_sky_texture.osl b/intern/cycles/kernel/osl/shaders/node_sky_texture.osl index ef066a90585..c615cc66c02 100644 --- a/intern/cycles/kernel/osl/shaders/node_sky_texture.osl +++ b/intern/cycles/kernel/osl/shaders/node_sky_texture.osl @@ -163,28 +163,11 @@ color sky_radiance_nishita(vector dir, float sky_data[11], string filename, stri if (x > 1.0) { x = x - 1.0; } - color rgb_sky; - if (sky_type == "single_scattering" && dir[2] < 0.0) { - /* Fade ground to black for Single Scattering model and disable Sun disc below horizon */ - rgb_sun = color(0.0, 0.0, 0.0); - if (dir[2] < -0.4) { - rgb_sky = color(0.0, 0.0, 0.0); - } - else { - float fade = pow(1.0 + dir[2] * 2.5, 3.0); - color xyz = (color)texture( - filename, x, 0.492, "wrap", "periodic", "interp", "linear", "alpha", alpha); - rgb_sky = xyz_to_rgb(xyz[0], xyz[1], xyz[2]) * fade; - } - } - else { - /* Undo the non-linear transformation from the sky LUT */ - float dir_elevation_abs = (dir_elevation < 0.0) ? -dir_elevation : dir_elevation; - float y = 1.0 - (sqrt(dir_elevation_abs / M_PI_2) * signx(dir_elevation) * 0.5 + 0.5); - color xyz = (color)texture( - filename, x, y, "wrap", "clamp", "interp", "linear", "alpha", alpha); - rgb_sky = xyz_to_rgb(xyz[0], xyz[1], xyz[2]); - } + /* Undo the non-linear transformation from the sky LUT */ + float dir_elevation_abs = (dir_elevation < 0.0) ? -dir_elevation : dir_elevation; + float y = 1.0 - (sqrt(dir_elevation_abs / M_PI_2) * signx(dir_elevation) * 0.5 + 0.5); + color xyz = (color)texture(filename, x, y, "wrap", "clamp", "interp", "linear", "alpha", alpha); + color rgb_sky = xyz_to_rgb(xyz[0], xyz[1], xyz[2]); return rgb_sun * sun_intensity + rgb_sky; } diff --git a/intern/cycles/kernel/svm/sky.h b/intern/cycles/kernel/svm/sky.h index a185837d654..e619669b8c3 100644 --- a/intern/cycles/kernel/svm/sky.h +++ b/intern/cycles/kernel/svm/sky.h @@ -134,7 +134,6 @@ ccl_device float3 geographical_to_direction(const float lat, const float lon) } ccl_device float3 sky_radiance_nishita(KernelGlobals kg, - const NodeSkyType type, const float3 dir, const uint32_t path_flag, const float3 pixel_bottom, @@ -142,7 +141,7 @@ ccl_device float3 sky_radiance_nishita(KernelGlobals kg, const ccl_private float *sky_data, const uint texture_id) { - /* definitions */ + /* Definitions */ const float sun_elevation = sky_data[0]; const float sun_rotation = sky_data[1]; const float angular_diameter = sky_data[2]; @@ -150,49 +149,32 @@ ccl_device float3 sky_radiance_nishita(KernelGlobals kg, const float earth_intersection_angle = sky_data[4]; const bool sun_disc = (angular_diameter >= 0.0f); float3 xyz = zero_float3(); - /* convert dir to spherical coordinates */ const float2 direction = direction_to_spherical(dir); - /* definitions */ const float3 sun_dir = spherical_to_direction(sun_elevation - M_PI_2_F, sun_rotation - M_PI_2_F); const float sun_dir_angle = precise_angle(dir, sun_dir); const float half_angular = angular_diameter * 0.5f; const float dir_elevation = M_PI_2_F - direction.x; - /* If the ray is inside the sun disc, render it, otherwise render the sky. - * Alternatively, ignore the sun if we're evaluating the background texture. */ + /* If the ray is inside the Sun disc, render it, otherwise render the sky. + * Alternatively, ignore the Sun if we're evaluating the background texture. */ if (sun_disc && sun_dir_angle < half_angular && dir_elevation > earth_intersection_angle && !((path_flag & PATH_RAY_IMPORTANCE_BAKE) && kernel_data.background.use_sun_guiding)) { - /* sun interpolation */ + /* Sun interpolation */ const float y = ((dir_elevation - sun_elevation) / angular_diameter) + 0.5f; - /* limb darkening, coefficient is 0.6f */ + /* Limb darkening, coefficient is 0.6f */ const float limb_darkening = (1.0f - 0.6f * (1.0f - sqrtf(1.0f - sqr(sun_dir_angle / half_angular)))); xyz = mix(pixel_bottom, pixel_top, y) * sun_intensity * limb_darkening; } - /* sky */ + /* Sky */ const float x = fractf((-direction.y - M_PI_2_F + sun_rotation) * M_1_2PI_F); - if (dir.z > 0.0f) { - /* sky interpolation */ - /* more pixels toward horizon compensation */ - const float y = safe_sqrtf(dir_elevation * M_2_PI_F) * 0.5f + 0.5f; - xyz += make_float3(kernel_tex_image_interp(kg, texture_id, x, y)); - } - /* ground */ - else if (type == NODE_SKY_MULTIPLE_SCATTERING) { - const float y = -safe_sqrtf(-dir_elevation * M_2_PI_F) * 0.5f + 0.5f; - xyz += make_float3(kernel_tex_image_interp(kg, texture_id, x, y)); - } - else if (dir.z >= -0.4f) { - /* black ground fade */ - float fade = 1.0f + dir.z * 2.5f; - fade = sqr(fade) * fade; - /* interpolation */ - xyz += make_float3(kernel_tex_image_interp(kg, texture_id, x, 0.508f)) * fade; - } + /* Undo the non-linear transformation from the sky LUT */ + const float y = copysignf(sqrtf(fabsf(dir_elevation) * M_2_PI_F), dir_elevation) * 0.5f + 0.5f; + xyz += make_float3(kernel_tex_image_interp(kg, texture_id, x, y)); - /* convert to RGB */ + /* Convert to RGB */ return xyz_to_rgb_clamped(kg, xyz); } @@ -317,8 +299,7 @@ ccl_device_noinline int svm_node_tex_sky(KernelGlobals kg, const uint texture_id = __float_as_uint(data.w); /* Compute Sky */ - rgb = sky_radiance_nishita( - kg, sky_type, dir, path_flag, pixel_bottom, pixel_top, sky_data, texture_id); + rgb = sky_radiance_nishita(kg, dir, path_flag, pixel_bottom, pixel_top, sky_data, texture_id); } stack_store_float3(stack, out_offset, rgb); diff --git a/intern/sky/source/sky_single_scattering.cpp b/intern/sky/source/sky_single_scattering.cpp index d6a8deb368a..aa24dc5bf70 100644 --- a/intern/sky/source/sky_single_scattering.cpp +++ b/intern/sky/source/sky_single_scattering.cpp @@ -308,25 +308,20 @@ void SKY_single_scattering_precompute_texture(float *pixels, const float longitude_step = M_2PI_F / width; const int rows_per_task = std::max(1024 / width, 1); - SKY_parallel_for(0, height, rows_per_task, [=](const size_t begin, const size_t end) { + /* Compute Sky in the upper hemisphere. */ + SKY_parallel_for(half_height, height, rows_per_task, [=](const size_t begin, const size_t end) { for (int y = begin; y < end; y++) { /* Sample more pixels toward the horizon. */ float latitude = M_PI_2_F * sqr(float(y) / half_height - 1.0f); float *pixel_row = pixels + (y * width * stride); for (int x = 0; x < half_width; x++) { - float3 xyz; - if (y > half_height) { - float longitude = longitude_step * x - M_PI_F; - float3 dir = geographical_to_direction(latitude, longitude); - float spectrum[NUM_WAVELENGTHS]; - single_scattering( - dir, sun_dir, cam_pos, air_density, aerosol_density, ozone_density, spectrum); - xyz = spec_to_xyz(spectrum); - } - else { - xyz = make_float3(0.0f, 0.0f, 0.0f); - } + float longitude = longitude_step * x - M_PI_F; + float3 dir = geographical_to_direction(latitude, longitude); + float spectrum[NUM_WAVELENGTHS]; + single_scattering( + dir, sun_dir, cam_pos, air_density, aerosol_density, ozone_density, spectrum); + const float3 xyz = spec_to_xyz(spectrum); /* Store pixels. */ int pos_x = x * stride; @@ -341,6 +336,26 @@ void SKY_single_scattering_precompute_texture(float *pixels, } } }); + + /* Fill in the lower hemisphere by fading out the horizon. */ + for (int y = 0; y < half_height; y++) { + /* Sample more pixels toward the horizon. */ + float latitude = M_PI_2_F * sqr(float(y) / half_height - 1.0f); + float3 dir = geographical_to_direction(latitude, 0.0f); + float fade = 0.0f; + if (dir.z < 0.4f) { + fade = 1.0f - dir.z * 2.5f; + fade = sqr(fade) * fade; + } + float *pixel_row = pixels + (y * width * stride); + float *horizon_row = pixels + (half_height * width * stride); + + for (int x = 0, offset = 0; x < width; x++, offset += stride) { + pixel_row[offset + 0] = horizon_row[offset + 0] * fade; + pixel_row[offset + 1] = horizon_row[offset + 1] * fade; + pixel_row[offset + 2] = horizon_row[offset + 2] * fade; + } + } } /*********** Sun ***********/ diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_tex_sky.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_tex_sky.glsl index affdd7408ca..a2dda2ab289 100644 --- a/source/blender/gpu/shaders/material/gpu_shader_material_tex_sky.glsl +++ b/source/blender/gpu/shaders/material/gpu_shader_material_tex_sky.glsl @@ -165,21 +165,10 @@ void node_tex_sky_nishita(float3 co, float fade = 1.0f; float y; - if (sky_type == 0.0f && co.z < -0.4f) { - /* Black ground if Single Scattering model */ - color = float4(0.0f, 0.0f, 0.0f, 1.0f); - return; - } - if (sky_type == 0.0f && co.z < 0.0f) { - /* Ground fade */ - fade = pow(1.0f + co.z * 2.5f, 3.0f); - y = 0.508f; - } - else { - /* Undo the non-linear transformation from the sky LUT. */ - float dir_elevation_abs = (dir_elevation < 0.0f) ? -dir_elevation : dir_elevation; - y = sqrt(dir_elevation_abs / M_PI_2) * sign(dir_elevation) * 0.5f + 0.5f; - } + /* Undo the non-linear transformation from the sky LUT. */ + float dir_elevation_abs = (dir_elevation < 0.0f) ? -dir_elevation : dir_elevation; + y = sqrt(dir_elevation_abs / M_PI_2) * sign(dir_elevation) * 0.5f + 0.5f; + /* Look up color in the precomputed map and convert to RGB. */ xyz = fade * texture(ima, float3(x, y, layer)).rgb; color = float4(dot(xyz_to_r, xyz), dot(xyz_to_g, xyz), dot(xyz_to_b, xyz), 1.0f); diff --git a/tests/files/render/texture/cycles_renders/sky_single_no_disc_high_altitude.png b/tests/files/render/texture/cycles_renders/sky_single_no_disc_high_altitude.png index 7d65e5fa291..a137fa9211a 100644 --- a/tests/files/render/texture/cycles_renders/sky_single_no_disc_high_altitude.png +++ b/tests/files/render/texture/cycles_renders/sky_single_no_disc_high_altitude.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:25302e9242e16a0bbbb3c8d511468fc4f4ccce1c3f78fec7a6be1d7da393b5ca -size 21667 +oid sha256:defa67dd2380819f1ee1044f59b0cb29c64cb63a4432e99fc1c1651b0d0618dc +size 21747 diff --git a/tests/files/render/volume/cycles_ray_marching_renders/implicit_volume.png b/tests/files/render/volume/cycles_ray_marching_renders/implicit_volume.png index dd615aefbdf..04cfc3a534d 100644 --- a/tests/files/render/volume/cycles_ray_marching_renders/implicit_volume.png +++ b/tests/files/render/volume/cycles_ray_marching_renders/implicit_volume.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:97eae519b8285147f3f9a799886e4973d9d432a50b45497502d023c714b8f7de -size 45924 +oid sha256:2d707c02b88dcabba20565700f9cfe2cbdb754d77e08b08b3712c5ab23e5fc9f +size 45877 diff --git a/tests/files/render/volume/eevee_renders/implicit_volume.png b/tests/files/render/volume/eevee_renders/implicit_volume.png index 9c1c80ad797..0d206e3f198 100644 --- a/tests/files/render/volume/eevee_renders/implicit_volume.png +++ b/tests/files/render/volume/eevee_renders/implicit_volume.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:fef36fe90ddb0b5bda77d2dd27e7b25a5f59c24dd650a90f4292649d817d4621 -size 35428 +oid sha256:cd3e765429c40cfd7244bf6b3707706b999bcb8f6caf74d96b6c3ed78d9c1fd9 +size 35338 diff --git a/tests/files/render/volume/eevee_renders/volume_scatter_fournier-forand.png b/tests/files/render/volume/eevee_renders/volume_scatter_fournier-forand.png index 0bb04aa1d82..94fe53b71d3 100644 --- a/tests/files/render/volume/eevee_renders/volume_scatter_fournier-forand.png +++ b/tests/files/render/volume/eevee_renders/volume_scatter_fournier-forand.png @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:f5cd0873feb03eda4ec32112f2b68e887483cecfc30ab0442e73c1566ca357b7 -size 25206 +oid sha256:8c1ae4b7b98b6e640725dbdcb63719530252dfe43577a5a39796589cd9e7dda6 +size 23686