目录
用循环VS不用循环
用循环:spp=2,t=5min
不用循环:spp=2,t=1min
多线程优化
原Render.cpp思路
(1)发出主射线primary ray,并调用castRay()函数实现对每个像素着色;
(2)UpdateProgres()
(3)保存
实现多线程的步骤
(1)首先要划分出不同的线程
(2)创建出每个线程执行的函数
(3)分行进行步骤(2)函数的调用
(4)别忘记thread需要执行的join
(5)渲染进程结束
多线程完整代码
多线程前后结果对比
提到优化,本次作业体现在渲染时长上面:spp取相同值的情况下,渲染时长越短当然效果是越好的!对于优化,这里有两个方面可以实现优化:
(1)较少循环的使用;
(2)使用多线程;
用循环VS不用循环首先那不得不从代码本身结构去做优化,我们把目光聚焦在Bounds.hpp的IntersectP()函数上。
用循环:spp=2,t=5min先看看最开始利用循环实现的代码:
inline bool Bounds3::IntersectP(const Ray& ray, const Vector3f& invDir,
const std::array& dirIsNeg) const
{
// TODO test if ray bound intersects
//判断包围盒Bounding Box与光线是否相交
//tenter = max{tmin} texit = min{tmax}
//先给个无穷初值
double tenter = -std::numeric_limits::infinity();
double texit = std::numeric_limits::infinity();
for (int i = 0; i < 3; i++) {
//求三个轴的tmin,tmax
// invDir: ray direction(x,y,z), invDir=(1.0/x,1.0/y,1.0/z),
double tmin = (pMin[i] - ray.origin[i]) * invDir[i];
double tmax = (pMax[i] - ray.origin[i]) * invDir[i];
//用dirIsNeg判断光线方向
if (!dirIsNeg[i])//如果i= 0;
}
其他内容不变,spp=2时,渲染时长为5min。
代码为:
inline bool Bounds3::IntersectP(const Ray& ray, const Vector3f& invDir,
const std::array& dirIsNeg) const
{
Vector3f tmin = (pMin - ray.origin) * invDir;
Vector3f tmax = (pMax - ray.origin) * invDir;
if (dirIsNeg[0])
std::swap(tmin.x, tmax.x);
if (dirIsNeg[1])
std::swap(tmin.y, tmax.y);
if (dirIsNeg[2])
std::swap(tmin.z, tmax.z);
float texit = std::min(tmax.x, std::min(tmax.y, tmax.z));
float tenter = std::max(tmin.x, std::max(tmin.y, tmin.z));
return tenter = 0;
}
spp=2,渲染时长为1min。
很直观的可以看到,两个结果没有任何差别,但时间就是缩短了整整4min!循环的使用大幅度延长了渲染时间,这点我在作业6最后也做了一些讨论:
GAMES101作业6-BVH完成全过程_flashinggg的博客-CSDN博客
多线程优化多线程是在Render.cpp中实现的,可以先看看Render.cpp代码的思路是什么:
原Render.cpp思路 (1)发出主射线primary ray,并调用castRay()函数实现对每个像素着色;这部分我在作业5里已经很详细地讲了如何计算方向,指路:
GAMES101作业5-从头到尾理解代码&Whitted光线追踪_flashinggg的博客-CSDN博客
//发射主射线primary ray
void Renderer::Render(const Scene& scene)
{
//Image
std::vector framebuffer(scene.width * scene.height);
//deg2rad() 度数->弧度
float scale = std::tan(deg2rad(scene.fov * 0.5f));
//aspect_radio=width/height
float imageAspectRatio = scene.width / (float)scene.height;
//eye(相机中心)定为(278,273,-800)
Vector3f eye_pos(278, 273, -800);
//遍历每个像素
int m = 0;
int spp = 16;
sitd::cout
关注
打赏