void SampleGeneratorBase::generate_samples( const size_t sample_count, SampleAccumulationBuffer& buffer, IAbortSwitch& abort_switch) { assert(sample_count > 0); clear_keep_memory(m_samples); m_samples.reserve(sample_count); size_t stored_sample_count = 0; while (stored_sample_count < sample_count) { stored_sample_count += generate_samples(m_sequence_index, m_samples); ++m_sequence_index; if (++m_current_batch_size == SampleBatchSize) { m_current_batch_size = 0; m_sequence_index += m_stride; if (abort_switch.is_aborted()) break; } } if (stored_sample_count > 0) buffer.store_samples(stored_sample_count, &m_samples[0]); }
void SPPMPassCallback::pre_render( const Frame& frame, JobQueue& job_queue, IAbortSwitch& abort_switch) { if (m_initial_lookup_radius > 0.0f) { RENDERER_LOG_INFO( "sppm lookup radius is %f (%s of initial radius).", m_lookup_radius, pretty_percent(m_lookup_radius, m_initial_lookup_radius, 3).c_str()); } m_stopwatch.start(); // Create a new set of photons. m_photons.clear_keep_memory(); m_photon_tracer.trace_photons( m_photons, hash_uint32(m_pass_number), job_queue, abort_switch); // Stop there if rendering was aborted. if (abort_switch.is_aborted()) return; // Build a new photon map. m_photon_map.reset(new SPPMPhotonMap(m_photons)); }
// Render a frame until completed or aborted and handle restart events. IRendererController::Status render_frame( RendererComponents& components, IAbortSwitch& abort_switch) { while (true) { // The `on_frame_begin()` method of the renderer controller might alter the scene // (e.g. transform the camera), thus it needs to be called before the `on_frame_begin()` // of the scene which assumes the scene is up-to-date and ready to be rendered. m_renderer_controller->on_frame_begin(); // Discard recorded light paths. m_project.get_light_path_recorder().clear(); // Perform pre-frame actions. Don't proceed if that failed. OnFrameBeginRecorder recorder; if (!components.on_frame_begin(recorder, &abort_switch) || !m_project.on_frame_begin(m_project, nullptr, recorder, &abort_switch) || abort_switch.is_aborted()) { recorder.on_frame_end(m_project); m_renderer_controller->on_frame_end(); return IRendererController::AbortRendering; } // Print settings of key entities. m_project.get_frame()->print_settings(); m_project.get_scene()->get_active_camera()->print_settings(); IFrameRenderer& frame_renderer = components.get_frame_renderer(); assert(!frame_renderer.is_rendering()); // Start rendering the frame. frame_renderer.start_rendering(); // Wait until the the frame is completed or rendering is aborted. const IRendererController::Status status = wait_for_event(frame_renderer); switch (status) { case IRendererController::TerminateRendering: case IRendererController::AbortRendering: case IRendererController::ReinitializeRendering: frame_renderer.terminate_rendering(); break; case IRendererController::RestartRendering: frame_renderer.stop_rendering(); break; assert_otherwise; } assert(!frame_renderer.is_rendering()); // Perform post-frame actions. recorder.on_frame_end(m_project); m_renderer_controller->on_frame_end(); switch (status) { case IRendererController::TerminateRendering: case IRendererController::AbortRendering: case IRendererController::ReinitializeRendering: return status; case IRendererController::RestartRendering: break; assert_otherwise; } } }