09 1月

渲染第一张图片

在这一章节,我来教大家怎么来用光线追踪来渲染第一张图片,把场景中的一个球渲染出来,我们假设这个球的颜色是红色。

sphere

我们要渲染一张图片,需要将三维的模型投射到一个平面上,我们先称它为画布,画布就是观察者的屏幕,实体化的画布就是电脑的显示屏,我们需要将画布在三维场景里面表示出来。所以我们定义:

画布的位置,朝向: 我们先定义画布在世界坐标的原点pos(0,0,0),面朝Z轴方向dir(0,0,1)。

画布的大小:这个画布都宽高多少,我们先定义画布宽(Aperture):41.4214m(houdini默认的摄像机的宽度)。画布高度这里是根据像素的宽高比来算出来。

注意,宽高不是指的是像素,这不是一个概念,像素指的是画布宽高在一个指定长度里面被划分成多少格数,一个格子代表一个像素。

像素:Hres8宽,Vres6高(如下图)

像素大小:因为像素一般都是一个正方形,所以我们只要求出像素宽就行了。

pixel_size=Aperture/Hres=41.4214/8(m)

viewplane

好了,现在每个有8*6个像素点,每个像素点我要射出去一根光线来判断我这个像素到底显示什么内容,如果这个线射出去碰到了场景中的红球,那么对应的像素点就填上红色。如果没有碰到红球,相对应的就显示黑色(背景)。

那么问题来了,我现在有48个像素对应要射出48根光线,那么这48根光线从哪里?方向?射出呢?

我们先不考虑透视的关系,现在我们假定每根线光线的方向都是沿着z轴的方向,定义ray.dir=(0,0,1);

下面,我们来确定他们的位置,如何确定光线的位置就相当于确定每个像素点的位置。我们来规定画布的中心正好在世界坐标的原点(0,0,0)。

画布的左下角等于:(0-8/2, 0-6/2)=(-4,-3) 单位是像素格。

画布的右上角等于: (3,2)   左上角:(-4,2) 右下角:(3,-3) 单位是像素格。

注意,这些数字现在都是以每个像素点的左下角为起点的。我们现在想让光想从每个像素的中心点出发。那么我们分别要向右和向上移动半格像素:

左下角(-3.5,-2.5) 右上角等于: (3.5,2.5)   左上角:(-3.5,2.5) 右下角:(3.5,-2.5)  单位是像素格。

既然我们在之前求出了像素的大小(pixel_size)那么我们可以知道每个像素的中心点的坐标了。

例:左下角:(-3.5,-2.5)*pixel_size=(-18.13,-12.95) 单位(m)

那么每个光线的位置ray.pos和方向ray.dir=(0,0,1)我们都已经确定了。遍历所有像素的

输出ppm:

结果如果下,球的位置坐标为(0,0,10),半径为1:

first1

大家感到很奇怪,为什会是个正方形?下面我们增加像素再来渲染看看。

middlefirsthigh

通过上面三张图比较,我们知道。像素越高,这个圆的还原度就越好。如果像素太低,那么图像的细节就会丢失很多,当然像素越高图像所花的渲染时间也就月多。

8*6:48根光线

80*60:4800根光线

800*600:4800000根光线

这是处理数据量的对比。

 

好了。这章我们讲完了。下面留下课后思考:如果场景中有多个球怎么办?并且他们从摄像机看去还有重叠关系。如何区分前后关系?留给大家思考吧

think

有任何问题,欢迎来信或者留言,我很乐意提供解答和帮助。

谢谢