Advertisement Jump to content
Sign in to follow this  

[MDX] Odd Visual Effect from Render to Texture

This topic is 4639 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Ok, so... I enter a method where I create a texture to use for my Fog of War layer... It works fine... it creates the textures and I use the FFP to multitexture the resulting textures with my terrain texture. However, the problem is that something is getting knocked out after I do my texture rendering. All geometry rendered after the Texture updates are like they don't have Z-buffer enabled or something. It is really odd. Here is the code:
    Public Sub UpdateFOWTextures(ByVal lFOWCenterX As Int32, ByVal lFOWCenterZ As Int32)
        Dim X As Int32
        Dim matTemp As Matrix
        Dim matWorld As Matrix
        Dim bForceUpdate As Boolean = False
        Dim lTempFOWX As Int32
        Dim lTempFOWZ As Int32

        Dim lFOWX As Int32
        Dim lFOWZ As Int32
        Dim lFOWTexIdx As Int32

        'Store away our Original Surface so we can set it back when we are done
        Dim oOriginal As Surface 
        Dim oScene As Surface

        Dim lQuadCenterX As Int32
        Dim lQuadCenterZ As Int32

        Dim matView As Matrix
        Dim matProj As Matrix

        'Check if we need to New any of these
        For X = 0 To 8
            If moVisibleTex(X) Is Nothing Then
                moVisibleTex(X) = New Texture(moDevice, 1024, 1024, 1, Usage.RenderTarget, Format.R5G6B5, Pool.Default)
                bForceUpdate = True
            End If
        Next X

        'Interval based updates to increase performance
        If mlLastFOWCenterX = lFOWCenterX AndAlso mlLastFOWCenterZ = lFOWCenterZ AndAlso _
          bForceUpdate = False AndAlso (timeGetTime - mlLastFOWUpdate) < ml_FOW_UPDATE_INTERVAL Then Exit Sub

        'validate that our disk object is something...
        'our visible color is 255,255,255,255 (white)
        'our shroud color is 255,128,128,128 (gray)
        If moDisk Is Nothing Then
            moDisk = CreateFOWDisk(System.Drawing.Color.FromArgb(255, 255, 255, 255), System.Drawing.Color.FromArgb(255, 128, 128, 128))
        End If

        'Store our centerx and z for next update
        mlLastFOWCenterX = lFOWCenterX
        mlLastFOWCenterZ = lFOWCenterZ

        'Store our matrices beforehand...
        matView = moDevice.Transform.View
        matProj = moDevice.Transform.Projection

        'ensure our renderstates are set correctly
        moDevice.RenderState.SourceBlend = Blend.SourceColor
        moDevice.RenderState.DestinationBlend = Blend.DestinationColor
        moDevice.RenderState.BlendOperation = BlendOperation.Add
        'set our material and turn off lighting
        moDevice.Material = moVisibleMat
        moDevice.RenderState.Lighting = False

        For lFOWX = lFOWCenterX - 1 To lFOWCenterX + 1
            For lFOWZ = lFOWCenterZ - 1 To lFOWCenterZ + 1
                'Get our Texture Index for this situation
                'lFOWTexIdx should be between 0 and 8
                lFOWTexIdx = ((lFOWZ - lFOWCenterZ + 1) * 3) + (lFOWX - lFOWCenterX + 1)

                'Ok, store our original surface
                oOriginal = moDevice.GetRenderTarget(0)

                'get our render target texture's surface
                oScene = moVisibleTex(lFOWTexIdx).GetSurfaceLevel(0)

                'Now, set our render target to the texture's surface
                moDevice.SetRenderTarget(0, oScene)

                'Clear out our display
                moDevice.Clear(ClearFlags.Target Or ClearFlags.ZBuffer, System.Drawing.Color.FromArgb(255, 64, 64, 64), 1.0F, 0)

                lQuadCenterX = (lFOWX * 16384) + 8192
                lQuadCenterZ = (lFOWZ * 16384) + 8192

                'Set up our matrices... this view gives us a birds-eye view over all elements on the screen
                moDevice.Transform.View = Matrix.LookAtLH(New Vector3(lQuadCenterX, 1000, lQuadCenterZ), _
                  New Vector3(lQuadCenterX, 0, lQuadCenterZ), New Vector3(0.0F, 0.0F, 1.0F))
                moDevice.Transform.Projection = Matrix.OrthoLH(16384, 16384, 0.1, 1000)

                'Now, loop through the visible entities in this quad...
                ' and draw the disk object as the entity's visible area
                For X = 0 To mlMyLocUB
                    matTemp = Matrix.Identity
                    matWorld = Matrix.Identity
                    matTemp.Scale(mlOptRange(X), 30, mlOptRange(X))
                    matTemp = Matrix.Identity
                    matTemp.Translate(mvecMyLocs(X).X, 0, mvecMyLocs(X).Y)
                    matTemp = Nothing
                    moDevice.Transform.World = matWorld

                Next X

                'Now, restore our original surface to the device
                moDevice.SetRenderTarget(0, oOriginal)

                'End If
            Next lFOWZ
        Next lFOWX

        'restore our matrices
        moDevice.Transform.View = matView
        moDevice.Transform.Projection = matProj

        'Restore our default renderstates
        moDevice.RenderState.SourceBlend = Blend.One
        moDevice.RenderState.DestinationBlend = Blend.Zero
        moDevice.RenderState.Lighting = True

        'Release all of our objects
        oScene = Nothing
        oOriginal = Nothing
    End Sub

Now, I take the results of the textures and I use them in my multi-texture pass. Stage 0 is: Texture = Terrain Texture ColorArg1 = TextureColor ColorArg2 = Diffuse ColorOp = SelectArg1 AlphaOp = Disable Stage 1 is: Texture = FOW Texture ColorArg1 = Current ColorArg2 = TextureColor ColorOp = Modulate2X AlphaOp = Disable I then reset my texture stage states back to their defaults (not sure if I had to do this). I re-enable lighting if it isn't already. I then draw a sphere... the sphere comes out Gray. The lighting I am using is white with a Red Diffuse material (textures set to nothing). This is the result. Now, realize that the sphere should be 'cut' by the terrain in half. But it is not... (its center point is at 0,0,0 while the terrain's height is zeroed out). I shouldn't be able to see half of that sphere, but I can. This seems to be the problem I am having. Also, the sphere is gray while the material should be red. What's going wrong? -E

Share this post

Link to post
Share on other sites
Ok, this is rather odd, I went home last night and tried it on my PC at home which has a newer video card with more video memory... and it worked.

So, what happens if I run out of video memory?

Let's say that my video card at work has 32mb of texture memory. My display size is like 600 x 500 or something... (resizable window)

I then do my work as normal... creating my device and everything... as long as I don't create the textures... it looks fine...

Now, what happens when I create 9 textures @ 1024x1024 each using R5G6B5 (16 bit, assume it takes 2 bytes of memory) = 18.8 mb of video memory. Add that to the texture for the terrain, texture for the display (and backbuffer), I'm probably getting over my video memory size. Now, the Texture construtor takes Default as a required pool for render targets.

If I reduce the number of textures to 1 (instead of 9), and reduce that texture size to 512x512, it works perfectly... argh!

So what is happening behind the scenes that is causing me to lose the Z-buffer?


Share this post

Link to post
Share on other sites
Sign in to follow this  

  • Advertisement

Important Information

By using, you agree to our community Guidelines, Terms of Use, and Privacy Policy. is your game development community. Create an account for your GameDev Portfolio and participate in the largest developer community in the games industry.

Sign me up!