Ogre引擎源码——资源之Material

Ogre中资源有以下几种:Texture、Compositor、Font、GpuProgram、Material、Mesh、Skeleton、BspLevel

本文聚焦于材质资源Material。DirectX、Opengl中的材质含义为物体的光学属性,如高光和漫反射光的颜色等。但在Ogre中,材质类所包含的概念更大,涵盖了纹理等设置的信息。从某种意思上来说,Ogre中的Material更接近于Shader 的概念。

 

Ogre中的材质资源相关头文件如下:

OgreMaterial.h

OgreMaterialManager.h

OgrePass.h

OgreTechnique.h

Material、Technique和Pass的UML关系图如下

 

 

从图中可以看出,Ogre中的材质是按三个层次来管理的。

最底层的是Pass(通路),Pass是Ogre最基本的绘制单元。

管理Pass的是Technique(技术),Technique是一组用来绘制一个特定材质的方法。

管理Technique的就是Material了,Material封装了对于一个物体而言的所有可视效果。

 

下面就逐一来解读下Ogre的材质结构。

 

(1)Pass

在Ogre中,Pass是最基本的绘制单元,同时也是Renderable(可绘制对象)用来标识自己绘制状态的基本单元。

Pass中与自身在材质结构中相关的成员变量有

Technique* mParent;
unsigned short mIndex; // pass index
String mName; // optional name for the pass
uint32 mHash; // pass hash
bool mHashDirtyQueued; // needs to be dirtied when next loaded

 

mParent是指向父类Technique的指针。

index用来表示,在父类的pass集合中,自身的序列号。

生成的hash是用来对pass分组排序的。需要提高绘制效率,我们就需要安排尽可能高效的绘制批次(batching)。为了减少绘制批次,我们具有相同绘制状态的绘制请求一起进行。对pass的合理组合,是有效地提高绘制效率的手段。

 

Pass的成员变量非常多,绝大部分都是绘制状态的设置。

大致有以下几类:

  • 颜色
  • 混合
  • 深度缓冲
  • alpha测试
  • 剔除(Culling)模式
  • 光照
  • Shading方式
  • 纹理单元
  • shader
  • 点大小及衰减 

(2)Technique

Technique是对Pass的集中管理,在Technique中,引入了硬件的考量。也就是说,Pass的设置能否在当前硬件上运行,Technique会给出考量后的结果。比如:在一个Pass中,所请求的纹理单元过多了,那么Technique就会自动地进行Pass的分割,使得Pass能够符合硬件的运行要求。

Technique的主要数据结构

typedef vector<Pass*>::type Passes;  
/// List of primary passes  
Passes mPasses;

这是所管理的Pass集合。

/// LOD level  
unsigned short mLodIndex;  
/// Scheme  
unsigned short mSchemeIndex;  

Lod和Scheme是上层Material用来区分不同Technique的度量方式。

 

还有两个比较重要的数据结构体GPUVendorRule和GPUDeviceNameRule。

顾名思义,从硬件获取的信息,通过这两个struct保存,并在编译Pass的过程中使用。

 

(3)Material

Material是管理的Technique的类,主要通过设定Scheme(方案)来进行度量。这里Scheme更符合我们平时对于绘制质量的理解,比如:高质量,中等质量,低质量等。划分好Scheme后,我们就可以把相应的Technique归入其中的一类,在切换Scheme的时候,就可以使用相应的Technique来进行绘制了。

还有一个度量就是Lod(细节等级)。有了相应的Scheme之后,在Technique执行时还需要考虑Lod的影响,根据视点与物体的距离来选择相应的Technique,是Ogre提供的材质绘制策略。

 

上述这两个度量的数据结构如下:

 

typedef map<unsigned short, Technique*>::type LodTechniques;  
typedef map<unsigned short, LodTechniques*>::type BestTechniquesBySchemeList;

 

LodTechniques是将距离与相应的Technique进行绑定。

BestTechniquesBySchemeList则是将Scheme与相应的LodTechniques绑定。

 

Material中管理Technique的数据结构如下:

typedef vector<Technique*>::type Techniques;  
/// All techniques, supported and unsupported  
Techniques mTechniques;  
/// Supported techniques of any sort  
Techniques mSupportedTechniques;  

可以看到,Material保存两份Technique的集合,mTechniques是当资源导入以后就保存的一份集合。而mSupportedTechniques则在每次编译之前清空,根据当前硬件的环境要求,来选择硬件支持的Technique。

 

还值得一提的是,在Pass、Technique和Material中,大部分的成员函数就是用来设置Pass中的绘制状态。设置的过程往往是从上至下传递的,也就是从Material->Technique->Pass的流程进行设置。当底层有需要进行重新编译的请求,都会发送给Material,然后再从Material至下,一步一步地编译所有材质资源。

 

(4)MaterialManager

继承自ResourceManager,对Material进行管理。主要实现了对纹理过滤的设置、Scheme的管理,设置相应的监听等操作。还负责读取材质脚本、初始化材质资源。

转自:http://blog.csdn.net/hunter8777/article/details/6333858

posted @ 2016-12-11 18:51  VZXM  阅读(481)  评论(0编辑  收藏  举报