渲染引擎开发笔记5.1

场景管理

Posted Kongouuu's Blog on December 26, 2021

前言

上一章节比较草草了事的简单提了一下Input Assembly部分的一些思路吧,并没有特别的细节,毕竟也只是个人反思。

实际上我们加载很多物体的时候我们不能像DX12龙书那种功能示范性代码一样去直接的去直接的建立不同的Mesh然后不对他们进行管理。想当然我们肯定是要对物体建立一个管理类。

很多的引擎的做法是用一个Scene Graph去管理场景的物体。如果我没有理解错的话这就是像UE,Unity一样,上级的Node的变换会套用到下级的Node上的一个设计,但目前我还没有要用到他的想法。我现在只想要一个在引擎侧能集中管理所有的物体的一个管理类。

所以我这里要建立一个 SceneManager类,是用来管理所有跟场景相关的信息的,例如摄像机,灯光,物体等。

正文

场景管理

为了之后更好的控制整个场景和物体,这里设置了一个场景管理类。整个类包含这对:

  1. 渲染物体
  2. 灯光
  3. 摄像机

三方面的管理。整体还是一个比较简单的结构。

物体管理

实际上对物体的管理就只是对所有的物体添加一个编号,并且储存在一个线性的数据结构上,这里考虑到以后发展的时候可能会有生命周期的问题,使用的是STL的Deque

只要我们通过一个中间类去储存物体,那么在我们需要的时候只需要靠一个id就能拿出对应的物体对他的内容进行更新,当然也可以一次拿到所有的Render Object

这样的话我们在实际使用的情况让我们需要更新一个方块的坐标,只需要像下面操作:

1
2
3
4
5
6
void MoveBox(float distanceRight)
{
	std::shared_ptr<RenderObject> box = SceneManager::GetRenderObject(0);
	box->position.x += ridstanceRight;
	SceneManager::UpdateRenderObject(box); // 把更新提交到渲染器
}

灯光

目前还没有写点光源,所以只有单个平行光。平行光的定义是分为两个层面,一个是要传进Shader的信息,一个是我们用于在外侧去调整平行光的信息:

Shader 需要
  1. 光强度
  2. 光方向(一个normalized的float3)
  3. 投影矩阵: 用于阴影贴图计算
外部控制
  1. 光的旋转:在控制平行光的时候比起去写一个方向,更直观的办法是储存一个基于一个初始向量的旋转。然后在我们对旋转操作之后,再对我们的方向向量进行更新。这里因为DX12的数学库里旋转考虑的是弧度,所以转换的时候还要先转过去:

  2. 光的位置: 平行光在计算光照的时候我们是不需要考虑位置的,不过如果需要计算阴影的话我们还是需要保留一个位置信息。无论我们是手动调整位置还是根据围绕摄像机/世界的包围球去自动计算阴影贴图需要的平行光的转换矩阵,我们都需要这个位置信息。

摄像机

摄像机没有什么讲究,这里直接是使用的龙书的代码。在那之上只加了一个设定平行投影的摄像机的初始化设置用于阴影贴图。

类定义

基本上这个类就是含有场景的摄像机、物品、灯光。然后负责在每次更新中向渲染器去提交更新。算是半个连接引擎和渲染器的中间件了。

在目前的开发使用中这个类最重要的地方就是能让我们通过使用Imgui去调整所有物体的信息。