chore: 优化config设计,将光线追踪配置类直接作为RendererConfig成员变量

master
ternaryop8479 2026-04-07 17:09:40 +08:00
parent 08910e48d7
commit fdbe96af40
6 changed files with 131 additions and 139 deletions

Binary file not shown.

View File

@ -299,7 +299,7 @@ void setup_cornell_box() {
g_scene->add_mesh(tall_box); g_scene->add_mesh(tall_box);
// Metal sphere (replacing the glass box, positioned on the right side) // Metal sphere (replacing the glass box, positioned on the right side)
auto metal_sphere = create_sphere(0.5f, 64, 32, /*metal_id*/white_id); auto metal_sphere = create_sphere(0.5f, 32, 16, /*metal_id*/white_id);
metal_sphere->set_position(Vec3(0.55f, -1.5f, 0.35f)); metal_sphere->set_position(Vec3(0.55f, -1.5f, 0.35f));
metal_sphere->upload_to_gpu(); metal_sphere->upload_to_gpu();
g_scene->add_mesh(metal_sphere); g_scene->add_mesh(metal_sphere);
@ -529,12 +529,12 @@ int main() {
ARE_LOG_INFO("Initializing renderer..."); ARE_LOG_INFO("Initializing renderer...");
RendererConfig config; RendererConfig config;
config.width_ = WINDOW_WIDTH; config.output_width = WINDOW_WIDTH;
config.height_ = WINDOW_HEIGHT; config.output_height = WINDOW_HEIGHT;
config.samples_per_pixel_ = 1; config.rt_config.samples_per_pixel = 1;
config.max_ray_depth_ = 4; config.rt_config.max_depth = 4;
config.enable_accumulation_ = true; config.rt_config.enable_accumulation = true;
config.enable_denoising_ = false; config.enable_denoising = false;
g_renderer = std::make_unique<Renderer>(config); g_renderer = std::make_unique<Renderer>(config);
if (!g_renderer->initialize()) { if (!g_renderer->initialize()) {

View File

@ -7,21 +7,12 @@
#include "resource/buffer.h" #include "resource/buffer.h"
#include "resource/shader.h" #include "resource/shader.h"
#include "scene/scene.h" #include "scene/scene.h"
#include "utils/config.h"
#include <glad/glad.h> #include <glad/glad.h>
#include <memory> #include <memory>
namespace are { namespace are {
// Ray tracing configuration
struct RayTracerConfig {
uint samples_per_pixel_;
uint max_depth_;
bool enable_shadows_;
bool enable_reflections_;
bool enable_accumulation_;
bool use_bvh_;
};
// Compute shader based ray tracer // Compute shader based ray tracer
class RayTracer { class RayTracer {
public: public:

View File

@ -6,14 +6,25 @@
namespace are { namespace are {
// Ray tracing configuration
struct RayTracerConfig {
uint samples_per_pixel = 1;
uint max_depth = 4;
bool enable_shadows = true;
bool enable_reflections = true;
bool enable_accumulation = true;
bool use_bvh = true;
};
// Configuration struct for renderer // Configuration struct for renderer
struct RendererConfig { struct RendererConfig {
uint width_; uint output_width;
uint height_; uint output_height;
uint samples_per_pixel_; RayTracerConfig rt_config;
uint max_ray_depth_; bool enable_denoising;
bool enable_denoising_; bool enable_sr; // Enable the super resolution mode
bool enable_accumulation_; double sr_scaling; // The magnification of super-resolution
}; };
} // namespace are } // namespace are

View File

@ -84,7 +84,7 @@ bool RayTracer::initialize(const std::shared_ptr<Shader> &shader) {
} }
// Initialize BVH if enabled // Initialize BVH if enabled
if (config_.use_bvh_) { if (config_.use_bvh) {
bvh_ = std::make_unique<BVH>(); bvh_ = std::make_unique<BVH>();
} }
@ -134,7 +134,7 @@ void RayTracer::release() {
} }
bool RayTracer::rebuild_bvh(const Scene &scene) { bool RayTracer::rebuild_bvh(const Scene &scene) {
if (!config_.use_bvh_) { if (!config_.use_bvh) {
ARE_LOG_WARN("BVH is disabled in configuration"); ARE_LOG_WARN("BVH is disabled in configuration");
return false; return false;
} }
@ -173,7 +173,7 @@ void RayTracer::trace(const Scene &scene, const GBuffer &gbuffer, TextureHandle
} }
// Build BVH if enabled and not built yet // Build BVH if enabled and not built yet
if (config_.use_bvh_ && !bvh_built_) { if (config_.use_bvh && !bvh_built_) {
rebuild_bvh(scene); rebuild_bvh(scene);
} }
@ -222,7 +222,7 @@ void RayTracer::trace(const Scene &scene, const GBuffer &gbuffer, TextureHandle
glBindImageTexture(4, accumulation_texture_, 0, GL_FALSE, 0, GL_READ_WRITE, GL_RGBA32F); glBindImageTexture(4, accumulation_texture_, 0, GL_FALSE, 0, GL_READ_WRITE, GL_RGBA32F);
// Bind BVH buffers if enabled // Bind BVH buffers if enabled
if (config_.use_bvh_ && bvh_built_) { if (config_.use_bvh && bvh_built_) {
bvh_node_buffer_.bind_base(2); bvh_node_buffer_.bind_base(2);
bvh_triangle_buffer_.bind_base(3); bvh_triangle_buffer_.bind_base(3);
bvh_attr_buffer_.bind_base(4); bvh_attr_buffer_.bind_base(4);
@ -234,10 +234,10 @@ void RayTracer::trace(const Scene &scene, const GBuffer &gbuffer, TextureHandle
// Set uniforms // Set uniforms
compute_shader_->set_uint("u_frame_count", frame_count_); compute_shader_->set_uint("u_frame_count", frame_count_);
compute_shader_->set_uint("u_samples_per_pixel", config_.samples_per_pixel_); compute_shader_->set_uint("u_samples_per_pixel", config_.samples_per_pixel);
compute_shader_->set_uint("u_max_depth", config_.max_depth_); compute_shader_->set_uint("u_max_depth", config_.max_depth);
compute_shader_->set_uint("u_light_count", static_cast<uint>(scene.get_lights().size())); compute_shader_->set_uint("u_light_count", static_cast<uint>(scene.get_lights().size()));
compute_shader_->set_bool("u_enable_accumulation", config_.enable_accumulation_); compute_shader_->set_bool("u_enable_accumulation", config_.enable_accumulation);
// Enable/disable textures based on material usage // Enable/disable textures based on material usage
compute_shader_->set_bool("u_enable_textures", has_textures); compute_shader_->set_bool("u_enable_textures", has_textures);
@ -257,7 +257,7 @@ void RayTracer::trace(const Scene &scene, const GBuffer &gbuffer, TextureHandle
glMemoryBarrier(GL_SHADER_IMAGE_ACCESS_BARRIER_BIT); glMemoryBarrier(GL_SHADER_IMAGE_ACCESS_BARRIER_BIT);
// Increment frame count for accumulation // Increment frame count for accumulation
if (config_.enable_accumulation_) { if (config_.enable_accumulation) {
frame_count_++; frame_count_++;
} }
} }
@ -288,16 +288,16 @@ void RayTracer::reset_accumulation() {
} }
void RayTracer::set_config(const RayTracerConfig &config) { void RayTracer::set_config(const RayTracerConfig &config) {
bool bvh_changed = (config.use_bvh_ != config_.use_bvh_); bool bvh_changed = (config.use_bvh != config_.use_bvh);
config_ = config; config_ = config;
reset_accumulation(); reset_accumulation();
if (bvh_changed) { if (bvh_changed) {
if (config_.use_bvh_ && !bvh_) { if (config_.use_bvh && !bvh_) {
bvh_ = std::make_unique<BVH>(); bvh_ = std::make_unique<BVH>();
bvh_built_ = false; bvh_built_ = false;
} else if (!config_.use_bvh_) { } else if (!config_.use_bvh) {
bvh_.reset(); bvh_.reset();
bvh_built_ = false; bvh_built_ = false;
} }

View File

@ -33,24 +33,18 @@ bool Renderer::initialize() {
} }
// Initialize G-Buffer // Initialize G-Buffer
gbuffer_ = std::make_unique<GBuffer>(config_.width_, config_.height_); gbuffer_ = std::make_unique<GBuffer>(config_.output_width, config_.output_height);
if (!gbuffer_->initialize()) { if (!gbuffer_->initialize()) {
ARE_LOG_ERROR("Failed to initialize G-Buffer"); ARE_LOG_ERROR("Failed to initialize G-Buffer");
return false; return false;
} }
// Initialize ray tracer // Initialize ray tracer
RayTracerConfig rt_config; RayTracerConfig rt_config = config_.rt_config;
rt_config.samples_per_pixel_ = config_.samples_per_pixel_;
rt_config.max_depth_ = config_.max_ray_depth_;
rt_config.enable_shadows_ = true;
rt_config.enable_reflections_ = true;
rt_config.enable_accumulation_ = config_.enable_accumulation_;
rt_config.use_bvh_ = true;
// Initialize ray tracer // Initialize ray tracer
raytracer_ = std::make_unique<RayTracer>(config_.width_, config_.height_, rt_config); raytracer_ = std::make_unique<RayTracer>(config_.output_width, config_.output_height, rt_config);
const auto& rt_shader = shader_manager_->get_raytracing_shader(); const auto &rt_shader = shader_manager_->get_raytracing_shader();
if (!raytracer_->initialize(rt_shader)) { if (!raytracer_->initialize(rt_shader)) {
ARE_LOG_ERROR("Failed to initialize ray tracer"); ARE_LOG_ERROR("Failed to initialize ray tracer");
return false; return false;
@ -58,14 +52,14 @@ bool Renderer::initialize() {
// Initialize screen blit // Initialize screen blit
screen_blit_ = std::make_unique<ScreenBlit>(); screen_blit_ = std::make_unique<ScreenBlit>();
const auto& screen_blit_shader = shader_manager_->get_screen_blit_shader(); const auto &screen_blit_shader = shader_manager_->get_screen_blit_shader();
if (!screen_blit_->initialize(screen_blit_shader)) { if (!screen_blit_->initialize(screen_blit_shader)) {
ARE_LOG_ERROR("Failed to initialize screen blit"); ARE_LOG_ERROR("Failed to initialize screen blit");
return false; return false;
} }
denoiser_ = std::make_unique<Denoiser>(config_.width_, config_.height_); denoiser_ = std::make_unique<Denoiser>(config_.output_width, config_.output_height);
const auto& denoise_shader = shader_manager_->get_denoise_shader(); const auto &denoise_shader = shader_manager_->get_denoise_shader();
if (!denoiser_->initialize(denoise_shader)) { if (!denoiser_->initialize(denoise_shader)) {
ARE_LOG_ERROR("Failed to initialize denoiser"); ARE_LOG_ERROR("Failed to initialize denoiser");
return false; return false;
@ -73,7 +67,7 @@ bool Renderer::initialize() {
// Create ray tracing output texture (reused every frame) // Create ray tracing output texture (reused every frame)
ResourceManager &rm = ResourceManager::instance(); ResourceManager &rm = ResourceManager::instance();
rt_output_texture_ = rm.create_texture(config_.width_, config_.height_, TextureFormat::RGBA32F); rt_output_texture_ = rm.create_texture(config_.output_width, config_.output_height, TextureFormat::RGBA32F);
initialized_ = true; initialized_ = true;
ARE_LOG_INFO("Aurora Rendering Engine initialized successfully"); ARE_LOG_INFO("Aurora Rendering Engine initialized successfully");
@ -103,7 +97,7 @@ void Renderer::shutdown() {
ARE_LOG_INFO("Aurora Rendering Engine shut down"); ARE_LOG_INFO("Aurora Rendering Engine shut down");
} }
RenderStats Renderer::render(const Scene& scene, TextureHandle output_texture) { RenderStats Renderer::render(const Scene &scene, TextureHandle output_texture) {
RenderStats stats = {}; RenderStats stats = {};
if (!initialized_) { if (!initialized_) {
@ -117,7 +111,7 @@ RenderStats Renderer::render(const Scene& scene, TextureHandle output_texture) {
// Phase 1: G-Buffer pass // Phase 1: G-Buffer pass
auto gbuffer_start = std::chrono::high_resolution_clock::now(); auto gbuffer_start = std::chrono::high_resolution_clock::now();
const auto& gbuffer_shader = shader_manager_->get_gbuffer_shader(); const auto &gbuffer_shader = shader_manager_->get_gbuffer_shader();
if (!gbuffer_shader || !gbuffer_shader->is_valid()) { if (!gbuffer_shader || !gbuffer_shader->is_valid()) {
ARE_LOG_ERROR("G-Buffer shader is invalid"); ARE_LOG_ERROR("G-Buffer shader is invalid");
return stats; return stats;
@ -141,7 +135,7 @@ RenderStats Renderer::render(const Scene& scene, TextureHandle output_texture) {
// Phase 3: Denoise texture // Phase 3: Denoise texture
TextureHandle final_output = rt_output; TextureHandle final_output = rt_output;
if (config_.enable_denoising_ && denoiser_) { if (config_.enable_denoising && denoiser_) {
// Use temporal accumulation with weight 0.1 (10% blend of new frame) // Use temporal accumulation with weight 0.1 (10% blend of new frame)
float temporal_weight = 0.1f; float temporal_weight = 0.1f;
final_output = denoiser_->denoise(rt_output, 1, temporal_weight); final_output = denoiser_->denoise(rt_output, 1, temporal_weight);
@ -157,13 +151,13 @@ RenderStats Renderer::render(const Scene& scene, TextureHandle output_texture) {
stats.frame_time_ms_ = std::chrono::duration<float, std::milli>(end_time - start_time).count(); stats.frame_time_ms_ = std::chrono::duration<float, std::milli>(end_time - start_time).count();
// Count triangles // Count triangles
const auto& meshes = scene.get_meshes(); const auto &meshes = scene.get_meshes();
for (const auto& mesh : meshes) { for (const auto &mesh : meshes) {
stats.triangle_count_ += mesh->get_indices().size() / 3; stats.triangle_count_ += mesh->get_indices().size() / 3;
} }
// Estimate ray count (very rough) // Estimate ray count (very rough)
stats.ray_count_ = config_.width_ * config_.height_ * config_.samples_per_pixel_ * config_.max_ray_depth_; stats.ray_count_ = config_.output_width * config_.output_height * config_.rt_config.samples_per_pixel * config_.rt_config.max_depth;
frame_count_++; frame_count_++;
@ -171,11 +165,11 @@ RenderStats Renderer::render(const Scene& scene, TextureHandle output_texture) {
} }
void Renderer::resize(uint width, uint height) { void Renderer::resize(uint width, uint height) {
if (width == config_.width_ && height == config_.height_) if (width == config_.output_width && height == config_.output_height)
return; return;
config_.width_ = width; config_.output_width = width;
config_.height_ = height; config_.output_height = height;
if (initialized_) { if (initialized_) {
ResourceManager &rm = ResourceManager::instance(); ResourceManager &rm = ResourceManager::instance();
@ -195,21 +189,17 @@ void Renderer::resize(uint width, uint height) {
} }
void Renderer::set_config(const RendererConfig &config) { void Renderer::set_config(const RendererConfig &config) {
bool size_changed = (config.width_ != config_.width_ || config.height_ != config_.height_); bool size_changed = (config.output_width != config_.output_width || config.output_height != config_.output_height);
config_ = config; config_ = config;
if (initialized_) { if (initialized_) {
if (size_changed) { if (size_changed) {
resize(config_.width_, config_.height_); resize(config_.output_width, config_.output_height);
} }
// Update ray tracer config // Update ray tracer config
RayTracerConfig rt_config = raytracer_->get_config(); raytracer_->set_config(config_.rt_config);
rt_config.samples_per_pixel_ = config_.samples_per_pixel_;
rt_config.max_depth_ = config_.max_ray_depth_;
rt_config.enable_accumulation_ = config_.enable_accumulation_;
raytracer_->set_config(rt_config);
} }
} }