Cycles: Use denoising device info to pick automatic denoiser

Ever since the introduction of GPU OIDN denoising on CPU devices,
using the path_tracing_device info to pick the automatic denoiser has
typically led to incorrect results.

This commit fixes this issue by using the denoising device info to pick
the denoiser.

Pull Request: https://projects.blender.org/blender/blender/pulls/123593
This commit is contained in:
Alaska 2024-06-24 11:28:02 +02:00 committed by Brecht Van Lommel
parent 37e2a27bdd
commit 9e267bbd57
5 changed files with 18 additions and 16 deletions

@ -405,7 +405,7 @@ void BlenderSession::render(BL::Depsgraph &b_depsgraph_)
width,
height,
&python_thread_state,
session_params.device);
session_params.denoise_device);
/* At the moment we only free if we are not doing multi-view
* (or if we are rendering the last view). See #58142/D4239 for discussion.
@ -702,7 +702,7 @@ void BlenderSession::bake(BL::Depsgraph &b_depsgraph_,
width,
height,
&python_thread_state,
session_params.device);
session_params.denoise_device);
/* Save the current state of the denoiser, as it might be disabled by the pass configuration (for
* passed which do not support denoising). */
@ -827,7 +827,7 @@ void BlenderSession::synchronize(BL::Depsgraph &b_depsgraph_)
width,
height,
&python_thread_state,
session_params.device);
session_params.denoise_device);
if (b_rv3d) {
sync->sync_view(b_v3d, b_rv3d, width, height);

@ -254,7 +254,7 @@ void BlenderSync::sync_data(BL::RenderSettings &b_render,
int width,
int height,
void **python_thread_state,
const DeviceInfo &device_info)
const DeviceInfo &denoise_device_info)
{
/* For auto refresh images. */
ImageManager *image_manager = scene->image_manager;
@ -274,7 +274,7 @@ void BlenderSync::sync_data(BL::RenderSettings &b_render,
const bool background = !b_v3d;
sync_view_layer(b_view_layer);
sync_integrator(b_view_layer, background, device_info);
sync_integrator(b_view_layer, background, denoise_device_info);
sync_film(b_view_layer, b_v3d);
sync_shaders(b_depsgraph, b_v3d, auto_refresh_update);
sync_images();
@ -303,7 +303,7 @@ void BlenderSync::sync_data(BL::RenderSettings &b_render,
void BlenderSync::sync_integrator(BL::ViewLayer &b_view_layer,
bool background,
const DeviceInfo &device_info)
const DeviceInfo &denoise_device_info)
{
PointerRNA cscene = RNA_pointer_get(&b_scene.ptr, "cycles");
@ -488,7 +488,7 @@ void BlenderSync::sync_integrator(BL::ViewLayer &b_view_layer,
}
DenoiseParams denoise_params = get_denoise_params(
b_scene, b_view_layer, background, device_info);
b_scene, b_view_layer, background, denoise_device_info);
/* No denoising support for vertex color baking, vertices packed into image
* buffer have no relation to neighbors. */
@ -990,7 +990,7 @@ SessionParams BlenderSync::get_session_params(BL::RenderEngine &b_engine,
DenoiseParams BlenderSync::get_denoise_params(BL::Scene &b_scene,
BL::ViewLayer &b_view_layer,
bool background,
const DeviceInfo &device_info)
const DeviceInfo &denoise_device_info)
{
enum DenoiserInput {
DENOISER_INPUT_RGB = 1,
@ -1042,7 +1042,7 @@ DenoiseParams BlenderSync::get_denoise_params(BL::Scene &b_scene,
/* Auto select fastest denoiser. */
if (denoising.type == DENOISER_NONE) {
denoising.type = Denoiser::automatic_viewport_denoiser_type(device_info);
denoising.type = Denoiser::automatic_viewport_denoiser_type(denoise_device_info);
if (denoising.type == DENOISER_NONE) {
denoising.use = false;
}

@ -66,12 +66,12 @@ class BlenderSync {
int width,
int height,
void **python_thread_state,
const DeviceInfo &device_info);
const DeviceInfo &denoise_device_info);
void sync_view_layer(BL::ViewLayer &b_view_layer);
void sync_render_passes(BL::RenderLayer &b_render_layer, BL::ViewLayer &b_view_layer);
void sync_integrator(BL::ViewLayer &b_view_layer,
bool background,
const DeviceInfo &device_info);
const DeviceInfo &denoise_device_info);
void sync_camera(BL::RenderSettings &b_render,
BL::Object &b_override,
int width,
@ -105,7 +105,7 @@ class BlenderSync {
static DenoiseParams get_denoise_params(BL::Scene &b_scene,
BL::ViewLayer &b_view_layer,
bool background,
const DeviceInfo &device);
const DeviceInfo &denoise_device);
private:
/* sync */

@ -122,14 +122,16 @@ unique_ptr<Denoiser> Denoiser::create(Device *denoiser_device,
is_cpu_denoiser_device ? single_denoiser_device : cpu_fallback_device, oidn_params);
}
DenoiserType Denoiser::automatic_viewport_denoiser_type(const DeviceInfo &path_trace_device_info)
DenoiserType Denoiser::automatic_viewport_denoiser_type(const DeviceInfo &denoise_device_info)
{
#ifdef WITH_OPENIMAGEDENOISE
if (OIDNDenoiserGPU::is_device_supported(path_trace_device_info)) {
if (denoise_device_info.type != DEVICE_CPU &&
OIDNDenoiserGPU::is_device_supported(denoise_device_info))
{
return DENOISER_OPENIMAGEDENOISE;
}
#else
(void)path_trace_device_info;
(void)denoise_device_info;
#endif
#ifdef WITH_OPTIX

@ -45,7 +45,7 @@ class Denoiser {
const DenoiseParams &get_params() const;
/* Recommended type for viewport denoising. */
static DenoiserType automatic_viewport_denoiser_type(const DeviceInfo &path_trace_device_info);
static DenoiserType automatic_viewport_denoiser_type(const DeviceInfo &denoise_device_info);
/* Create devices and load kernels needed for denoising.
* The progress is used to communicate state when kernels actually needs to be loaded.