一、相关类及说明
下图列出了Ogre系统Compositor相关的类
1、CompositorManager
主要负责管理合成器的加载、创建、销毁等操作
2、Compositor
表示合成器对象的类,可类比材质系统中的Ogre::Material类
3、CompositionTechnique
合成器的technique,被包含在Compositor对象中(一个Copositor对象可包含多个CompositionTechnique),可类比材质系统中的Ogre::Technique
4、TextureDefinition
该类定义在CompositonTechnique类中,表示合成器纹理的定义,系统会根据这个定义创建或引用对应的纹理,这些纹理都具有渲染目标属性:TU_RENDERTARGET
5、CompositionTargetPass
表示对一个对RenderTarget或Viewport的渲染,一个CompositonTechnique可以有多个CompositionTargetPass,在脚本中用关键字target或者target_output定义,可以定义多个target,但只能定义一个target_output,表示这个合成器的输出(取决于定义输出目标可是纹理或者窗口)。
6、CompositionPass
表示在合成顺序中的一个操作,用于在渲染队列之间交错渲染系统命令,具体有如下命令:
/** Enumeration that enumerates the various composition pass types.
*/
enum PassType
{
PT_CLEAR, /// Clear target to one colour
PT_STENCIL, /// Set stencil operation
PT_RENDERSCENE, /// Render the scene or part of it
PT_RENDERQUAD, /// Render a full screen quad
PT_RENDERCUSTOM /// Render a custom sequence
};
7、CompositorChain
表示一个合成效果链,包含了多个合成器实例对象,用于达到多个合成效果的有序合成。
8、CompositorInstance
表示一个合成器对象的实例,被包含在CompositorChain中
9、RenderSystemOperation
CompositorInstance的内部类,对先前CompositionPass类的渲染操作的实现,如果系统默认的实现不能够满足需求,则需要自己继承该类,完成相应的渲染操作
10、TargetOperation
表示对一个RenderTarget的操作设置,包含一个或多个RenderSystemOperation对象
11、CompositorLogic
一个监听器类,接口如下:
/** Called when a compositor instance has been created.
@remarks
This happens after its setup was finished, so the chain is also accessible.
This is an ideal method to automatically attach a compositor listener.
*/
virtual void compositorInstanceCreated(CompositorInstance* newInstance) {}
/** Called when a compositor instance has been destroyed
@remarks
The chain that contained the compositor is still alive during this call.
*/
virtual void compositorInstanceDestroyed(CompositorInstance* destroyedInstance) {}
二、合成器脚本
脚本示例如下
涉及到的类有5个,不同颜色的矩形框对应不同的类及内容;需要说明以下几点:
1、TextureDefinition提供纹理定义与创建,为后续的CompositionTargetPass所使用,此例中有3处rt0,指的都是统一纹理对象,第一处是定义与创建;第二处表示rt0作为渲染目标,将内容渲染到rt0纹理中;第三处是将rt0纹理作为输入,替换掉材质中纹理单元索引为0的纹理。
2、CompositionTargetPass这里是用了两种方式定义,如前面讲到的,用target可以定义多个,因为这表示中间过程,此例中input指定了内容的输入来源,如果在合成链中,此合成器前面还有可用的合成器实例,那么输入就是前面一个合成器实例的输出操作(target_output定义的那段),否则就是场景的内容渲染操作作为输入,然后根据操作将内容输出的rt0渲染目标上;而用target_output定义的只能有一个,表示此合成器的输出操作,此段一般是没有输入的,因为后续会将中间过程的结果rt0输入到材质中
3、pass段定义了CompositionPass对象,render_quad表明了此pass的渲染操作是用指定的材质绘制四边形
4、关于合成器的输出,如果在合成器链中,后面还有激活的合成器,且指定输入来源为前面合成器的输出操作(input previous),那么前面一个合成器并不会有输出到渲染目标,而是输出操作被引用而已;如果此实例为最后一个实例,或者合成链中后面没有激活的合成器实例,那么合成器的输出目的为指定视口下的窗口或这RenderTarget
5、正常情况下,如果应用合成器效果,那么原有的场景效果会作为合成链的数据输入,然后经过一系列处理,再将最终结果绘制到窗口或RenderTarget。不比担心场景会绘制多次。
注意:这里rt0只是纹理定义名,而非真正的纹理名;这里提供的材质名也是初始名,Ogre内部会对其进行拷贝和重命名,所以替换的纹理单元只是在新的材质上发生,即使其他地方使用该材质也不会受替换的影响。
三、合成器的使用
Ogre::CompositorManager::getSingleton().addCompositor(vp, compositorName, addPosition);
Ogre::CompositorManager::getSingleton().setCompositorEnabled(vp, compositorName, enabled);