PBRT_V2 总结记录 <2> SamplerRenderer

SamplerRenderer 类

class SamplerRenderer : public Renderer {
public:
	// SamplerRenderer Public Methods
	SamplerRenderer(Sampler *s, Camera *c, SurfaceIntegrator *si,
		VolumeIntegrator *vi, bool visIds);
	~SamplerRenderer();
	void Render(const Scene *scene);
	Spectrum Li(const Scene *scene, const RayDifferential &ray,
		const Sample *sample, RNG &rng, MemoryArena &arena,
		Intersection *isect = NULL, Spectrum *T = NULL) const;
	Spectrum Transmittance(const Scene *scene, const RayDifferential &ray,
		const Sample *sample, RNG &rng, MemoryArena &arena) const;
private:
	// SamplerRenderer Private Data
	bool visualizeObjectIds;
	Sampler *sampler;
	Camera *camera;
	SurfaceIntegrator *surfaceIntegrator;
	VolumeIntegrator *volumeIntegrator;
};

类的作用 : (SamplerRenderer 这个类渲染出来的图片 主要是受采样点影响的,之所以这样命名,主要是采样点影响图片上的像素点)

SamplerRenderer is so named because its rendering process is driven by(被驱动) a stream of(一连串) samples from a Sampler; each such sample identifies a point on the image at which to compute the arriving light to form the image.

Sampler *sampler; 作用 :(sampler 负责 选择图片上哪一些点 进行光线追踪,负责提供 采样点 给 integrators 使用)

The SamplerRenderer stores a pointer to a Sampler. The role of this class is subtle(微妙), but
its implementation can substantially affect the quality of the images that the system generates.
First, the sampler is responsible for choosing the points on the image plane from
which rays are traced. Second, it is responsible for supplying the sample positions used by
the integrators in their light transport computations;
for example, some integrators need
to choose random points on light sources to compute illumination fromarea lights. Generating
a good distribution of these samples is an important part of the rendering process
that can substantially affect overall efficiency.

Camera *camera;  作用 :(生成射线)

The Camera object controls the viewing and lens parameters such as position, orientation,
focus, and field of view. A Film member variable inside the Camera class handles
image storage.The Film is responsible for writing the final image to disk and possibly displaying
it on the screen as it is being computed.

SurfaceIntegrator *surfaceIntegrator;
VolumeIntegrator *volumeIntegrator;  

作用 : 

Integrators handle the task of simulating the propagation of light in the scene in order
to compute how much light arrives at image sample positions on the film plane.

They are so named because they numerically evaluate the integrals in the surface and
volume light transport equations that describe the distribution of light in the environment.
SurfaceIntegrators compute reflected light from geometric surfaces, while
VolumeIntegrators handle the scattering from volumetric primitives.

void Render(const Scene *scene);  作用 : (Imgae 上进行采样,每一个采样点发射出一条Ray,Integrators 计算这条Ray的radiance, 然后Film利用radiance 生成一张Image)

In the SamplerRenderer’s implementation of this method, at each of a
series of positions on the image plane, the method uses the Camera and the Sampler to
generate a ray into the scene, and then uses its integrators to determine the amount of
light arriving at the image plane along that ray. This value is passed to the Film, which
records the light’s contribution.
Figure 1.17 summarizes the main classes used in this
method and the flow of data among them.

The Sampler provides a sequence of sample values, one for each
image sample to be taken. The Camera turns a sample into a corresponding ray from the film plane,
and the Integrators compute the radiance along that ray arriving at the film. The sample and its
radiance are given to the Film, which stores their contribution in an image. This process repeats until
the Sampler has provided as many samples as are necessary to generate the final image.

void Render(const Scene *scene);  代码细节 :

void SamplerRenderer::Render(const Scene *scene) {
	surfaceIntegrator->Preprocess(scene, camera, this);
	volumeIntegrator->Preprocess(scene, camera, this);

	// Allocate and initialize _sample_
	Sample *sample = new Sample(sampler, surfaceIntegrator,
		volumeIntegrator, scene);

	// Create and launch _SamplerRendererTask_s for rendering image
	// Compute number of _SamplerRendererTask_s to create for rendering

	int nPixels = camera->film->xResolution * camera->film->yResolution;
	int nTasks = max(32 * NumSystemCores(), nPixels / (16 * 16));
	nTasks = RoundUpPow2(nTasks);
	ProgressReporter reporter(nTasks, "Rendering");

	vector<Task *> renderTasks;
	for (int i = 0; i < nTasks; ++i)
		renderTasks.push_back(new SamplerRendererTask(scene, this, camera,
		reporter, sampler, sample,
		visualizeObjectIds,
		nTasks - 1 - i, nTasks));

	EnqueueTasks(renderTasks);
	WaitForAllTasks();

	for (uint32_t i = 0; i < renderTasks.size(); ++i)
		delete renderTasks[i];
	reporter.Done();
	// Clean up after rendering and store final image
	delete sample;

	camera->film->WriteImage();
}

a. 

surfaceIntegrator->Preprocess(scene, camera, this);
volumeIntegrator->Preprocess(scene, camera, this);  

作用 :

Before rendering can begin, the SamplerRenderer calls the Preprocess() methods of the
integrators. Because information like the specific light sources and geometry of the scene
aren’t available when the integrators are first created, the Preprocess() method gives
them an opportunity to do any necessary scene-dependent initialization or preprocessing.

For example, the PhotonIntegrator in Section 15.6 uses this opportunity to create
data structures that hold a representation of the distribution of illumination in the scene.

b. 

Sample *sample = new Sample(sampler, surfaceIntegrator,
        volumeIntegrator, scene); 

作用 :(这里其实就是 生成一个 Sample 模板,这个模板 主要是 由 integrators 来决定的,在Sample 的构造函数里面调用了 Integrator->RequestSamples() 来修改Sample模板,之后直接利用这个模板,直接克隆出多个Sample出来使用 )

the Render() method also creates a Sample object, into which the
Sampler will store the samples it generates during the main loop.
Because the number
and types of samples that need to be generated are partially dependent on the integrators,
the Sample constructor takes pointers to the integrators so they can be queried for their
requirements. See Section 7.2.1 for more information about how integrators request
particular sets of samples.

c.

剩下的代码主要是的作用 : 创建多个 SamplerRendererTask 来渲染图片,当 SamplerRendererTask 完成了,就把渲染好的图片写到 磁盘上。

猜你喜欢

转载自blog.csdn.net/aa20274270/article/details/82884317