# SSAO Problem

Jo0oker

31-05-2011 18:06:21

Dear Mogre user,
i have ported this SSAO-Code:
http://www.ogre3d.org/forums/viewtopic.php?t=42350
to C# and Mogre. It compiles, but doesn't work. It only makes everything confusing.

This are the main classes:
``` using System; using System.Collections.Generic; using System.Linq; using System.Text; using Mogre; namespace Tehadon.Gfx.TEffect { public unsafe class QuadRenderer { #region Private Member private ManualObject myQuad; private Camera myCamera; #endregion #region Konstruktor public QuadRenderer(Camera Cam) { //Create the Quad myCamera = Cam; myQuad = myCamera.SceneManager.CreateManualObject("QuadRenderer:quad"); Vector3* Corners = myCamera.WorldSpaceCorners; myQuad.Begin("Chuck Norris", RenderOperation.OperationTypes.OT_TRIANGLE_LIST); { // top-left myQuad.Position(new Vector3(-1, 1, 0)); myQuad.Normal(Corners[5]); myQuad.TextureCoord(new Vector2(0, 0)); // bottom-left myQuad.Position(new Vector3(-1, -1, 0)); myQuad.Normal(Corners[6]); myQuad.TextureCoord(new Vector2(0, 1)); // bottom-right myQuad.Position(new Vector3(1, -1, 0)); myQuad.Normal(Corners[7]); myQuad.TextureCoord(new Vector2(1, 1)); // top-right myQuad.Position(new Vector3(1, 1, 0)); myQuad.Normal(Corners[4]); myQuad.TextureCoord(new Vector2(1, 0)); // we put the vertices in anti-clockwise, // so just start at 0 and go to 3 myQuad.Quad(0, 1, 2, 3); } myQuad.End(); } #endregion #region Go /// <summary> /// Go /// </summary> /// <param name="Pass">Pass</param> /// <param name="ViewPort">Viewport</param> public void Go(Pass Pass, Viewport ViewPort) { RenderSystem cRS = Root.Singleton.RenderSystem; SceneManager cSceneManager; RenderOperation cROp = new RenderOperation(); myQuad.GetSection(0).GetRenderOperation(cROp); cRS._beginFrame(); cRS._setViewport(ViewPort); cSceneManager = myQuad._getManager(); cSceneManager._setPass(Pass, true, false); if (Pass.HasVertexProgram) cRS.BindGpuProgramParameters( GpuProgramType.GPT_VERTEX_PROGRAM, Pass.GetVertexProgramParameters(), 0); //Not sure, if it works else cRS.UnbindGpuProgram(GpuProgramType.GPT_VERTEX_PROGRAM); if (Pass.HasFragmentProgram) cRS.BindGpuProgramParameters( GpuProgramType.GPT_FRAGMENT_PROGRAM, Pass.GetFragmentProgramParameters(), 0); //Not sure, if it works else cRS.UnbindGpuProgram(GpuProgramType.GPT_FRAGMENT_PROGRAM); cRS._setWorldMatrix(Matrix4.IDENTITY); cRS._setViewMatrix(Matrix4.IDENTITY); cRS._setProjectionMatrix(Matrix4.IDENTITY); cRS._render(cROp); cRS._endFrame(); } #endregion #region Public Member public ManualObject Quad { get { return myQuad; } set { myQuad = value; } } public Camera Camera { get { return myCamera; } set { myCamera = value; } } #endregion } } ```

SSEffect:
``` using System; using System.Collections.Generic; using System.Linq; using System.Text; using Mogre; namespace Tehadon.Gfx.TEffect { public class ProjectionMatrix { #region Constants public static Matrix4 PROJECTIONCLIPSPACE2DTOIMAGESPACE_PERSPECTIVE = new Matrix4( 0.5f, 0, 0, 0.5f, 0, -0.5f, 0, 0.5f, 0, 0, 1, 0, 0, 0, 0, 1); #endregion } public class SSEffect { #region Private Member private Camera myCamera; private Viewport myViewPort; private Texture myTexture; private bool myTexIsExtern; private RenderTarget myRenderTarget; private Pass myPass; private bool myEnabled; private string myName; private QuadRenderer myQuadRenderer; #endregion #region Construktor /// <summary> /// Constructor /// </summary> /// <param name="Name"></param> /// <param name="QuadRenderer"></param> public SSEffect(string Name, QuadRenderer QuadRenderer) { myName = Name; myQuadRenderer = QuadRenderer; myEnabled = true; myTexIsExtern = false; } #endregion #region Create /// <summary> /// Create the SSEffect and a new Rendertexture /// </summary> /// <param name="Weidht"></param> /// <param name="Height"></param> /// <param name="PixelFormat"></param> public void Create(uint Weidht, uint Height, PixelFormat PixelFormat) { Destroy(); TexturePtr cMidPtr = TextureManager.Singleton.CreateManual( myName + "_tex", "Internal", TextureType.TEX_TYPE_2D, Weidht, Height, 0, PixelFormat, 512); //512 = TU_RENDERTARGET myTexture = cMidPtr; myTexIsExtern = false; myRenderTarget = myTexture.GetBuffer(0).GetRenderTarget(0); myRenderTarget.IsAutoUpdated = (false); myCamera = myQuadRenderer.Camera.SceneManager.CreateCamera(myName + "_cam"); myViewPort = myRenderTarget.AddViewport(myCamera, myRenderTarget.NumViewports); myViewPort.BackgroundColour = (ColourValue.White); myViewPort.SetClearEveryFrame(false); myViewPort.ShadowsEnabled = (false); myViewPort.OverlaysEnabled = (false); myCamera.AspectRatio = ((float)(Weidht / (float)Height)); myCamera.FOVy = (new Degree(90)); } /// <summary> /// Create the SSEffect with an existing Rendertexture /// </summary> /// <param name="RenderTexture"></param> public void Create(Texture RenderTexture) { Destroy(); myTexture = RenderTexture; myTexIsExtern = true; myRenderTarget = myTexture.GetBuffer(0).GetRenderTarget(0); myViewPort = myRenderTarget.GetViewport(0); myCamera = myViewPort.Camera; } #endregion #region Destroy /// <summary> /// Destroy the SSEffect /// </summary> public void Destroy() { if (!myTexIsExtern) { if (myTexture != null) { TextureManager.Singleton.Remove(myTexture.Name); } if (myCamera != null) { myCamera.SceneManager.DestroyCamera(myCamera); } myTexture = null; myCamera = null; myRenderTarget = null; myViewPort = null; } } #endregion #region Update /// <summary> /// Update the SSEffect /// </summary> public void Update() { if (!myEnabled || myPass == null) { return; } //Update myQuadRenderer.Go(myPass, myViewPort); } #endregion #region Clear /// <summary> /// Clear the SSEffect /// </summary> public void Clear() { RenderSystem cRenderSystem = Root.Singleton.RenderSystem; cRenderSystem._setViewport(myViewPort); cRenderSystem.ClearFrameBuffer( 1 | 2 | 4, //-> Mogre.FrameBufferType.FBT_COLOUR | FrameBufferType.FBT_DEPTH | FrameBufferType.FBT_STENCIL myViewPort.BackgroundColour); } #endregion #region Public Member public Camera Camera { get { return myCamera; } set { myCamera = value; } } public Viewport ViewPort { get { return myViewPort; } set { myViewPort = value; } } public bool TexIsExtern { get { return myTexIsExtern; } set { myTexIsExtern = value; } } public RenderTarget RenderTarget { get { return myRenderTarget; } set { myRenderTarget = value; } } public Texture Texture { get { return myTexture; } set { myTexture = value; } } public Pass Pass { get { return myPass; } set { myPass = value; } } public bool Enabled { get { return myEnabled; } set { myEnabled = value; } } public QuadRenderer QuadRenderer { get { return myQuadRenderer; } set { myQuadRenderer = value; } } #endregion } } ```

SSAO
``` using System; using System.Collections.Generic; using System.Linq; using System.Text; using Mogre; namespace Tehadon.Gfx.TEffect { public class SSAO : SSEffect { #region Private Member #endregion #region Constructor /// <summary> /// Constructor /// </summary> /// <param name="Name"></param> /// <param name="QuadRenderer"></param> public SSAO(string Name, QuadRenderer QuadRenderer) : base(Name, QuadRenderer) { MaterialPtr cMidPtr = MaterialManager.Singleton.Load("ssao", "Internal"); base.Pass = cMidPtr.GetBestTechnique().GetPass(0); base.Pass.GetTextureUnitState(0).SetTextureName("geom_tex"); base.Pass._load(); } #endregion #region Create /// <summary> /// Create the SSAO /// </summary> /// <param name="Texture"></param> private void Create(Texture Texture) { } /// <summary> /// Create the SSAO /// </summary> /// <param name="Weidth"></param> /// <param name="Height"></param> /// <param name="PixelFormat"></param> public void Create(uint Weidth, uint Height, PixelFormat PixelFormat = PixelFormat.PF_R8G8B8) { base.Create(Weidth, Height, PixelFormat); } #endregion #region Update /// <summary> /// Update SSAO /// </summary> public void Update() { if (!Enabled || base.Pass == null) { return; } GpuProgramParametersSharedPtr cParams = base.Pass.GetFragmentProgramParameters(); if (!cParams._findNamedConstantDefinition("pMat").IsNull) { cParams.SetNamedConstant( "pMat", ProjectionMatrix.PROJECTIONCLIPSPACE2DTOIMAGESPACE_PERSPECTIVE * base.QuadRenderer.Camera.ProjectionMatrixWithRSDepth); } if (!cParams._findNamedConstantDefinition("far").IsNull) { cParams.SetNamedConstant("far", base.QuadRenderer.Camera.FarClipDistance); } base.Update(); } #endregion #region Public Member #endregion } } ```

Geom
``` using System; using System.Collections.Generic; using System.Linq; using System.Text; using Mogre; namespace Tehadon.Gfx.TEffect { public class Geom : SSEffect { #region Private Member #endregion #region Constructor /// <summary> /// Constructor /// </summary> /// <param name="Name"></param> /// <param name="QuadRenderer"></param> public Geom(string Name, QuadRenderer QuadRenderer) : base(Name, QuadRenderer) { } #endregion #region Create /// <summary> /// Create the SSAO /// </summary> /// <param name="Texture"></param> private void Create(Texture Texture) { } /// <summary> /// Create the SSAO /// </summary> /// <param name="Weidth"></param> /// <param name="Height"></param> /// <param name="PixelFormat"></param> public void Create(uint Weidth, uint Height, PixelFormat PixelFormat = PixelFormat.PF_R8G8B8) { base.Create(Weidth, Height, PixelFormat); } #endregion #region Update /// <summary> /// Update SSAO /// </summary> public void Update() { if (!Enabled) { return; } ViewPort.MaterialScheme = ("geom"); MaterialManager.Singleton.ActiveScheme = ("geom"); // render using the geom scheme to our viewport // using the main scene camera QuadRenderer.Camera.SceneManager._renderScene(QuadRenderer.Camera, ViewPort, false); base.Update(); } #endregion #region Public Member #endregion } } ```

I also changed some other properties, as in the C++-Code:
``` myWindow.IsAutoUpdated = false; myViewport.BackgroundColour = new ColourValue(0, 0, 0, 0); myViewport.SetClearEveryFrame(false); myCamera.AspectRatio = (float)(myWindow.Width / (float)myWindow.Height); myCamera.FOVy = new Degree(60); ```

And on this way, i created ssao:
``` QuadRenderer cQR = new QuadRenderer(myITOgre.Camera); cGeom = new Geom("geom", cQR); cGeom.Create(myITOgre.RenderWindow.Width, myITOgre.RenderWindow.Height, PixelFormat.PF_FLOAT32_RGBA); cSSAO = new SSAO("ssao", cQR); cSSAO.Create(myITOgre.RenderWindow.Width, myITOgre.RenderWindow.Height); //Debug overlay ssaoDebugMat = MaterialManager.Singleton.Create("ssao_debug", "Internal"); ssaoDebugMat.CreateTechnique().CreatePass().CreateTextureUnitState().SetTextureName(cSSAO.Texture.Name); Overlay cOverlay = OverlayManager.Singleton.GetByName("ssao_debug"); cOverlay.GetChild("ssao_debug_panel").MaterialName = ssaoDebugMat.Name; cOverlay.Show(); ```

Updating everything is done in a Framelistner:
``` cGeom.Clear(); cGeom.Update(); cSSAO.Clear(); cSSAO.Update(); GameContext.GfxManager.TOgreManager.Singelton.Root.RenderSystem._setViewport(GameContext.GfxManager.TOgreManager.Singelton.Viewport); GameContext.GfxManager.TOgreManager.Singelton.Root.RenderSystem.ClearFrameBuffer(1 | 2); GameContext.GfxManager.TOgreManager.Singelton.SceneManager._renderScene(GameContext.GfxManager.TOgreManager.Singelton.Camera, GameContext.GfxManager.TOgreManager.Singelton.Viewport, true); GameContext.GfxManager.TOgreManager.Singelton.RenderWindow.SwapBuffers(true); ```

But nothing really changed, no SSAO.
Also the Debug-Overlay is always white, but i don't get any errors.

It would be very nice, if anyone have an idea!

Best regards,
Jo0oker

Jeason

31-05-2011 21:41:48

Hmmm when i tried the last time this SSAO Example in the normal OGRE it doesn't work too