屏幕空间正方形看起来在PIX中扭曲

时间:2011-08-29 10:02:54

标签: geometry directx slimdx direct3d11 pix

我有一个简单的功能,可以创建一个覆盖整个屏幕的方块,我用它来应用后期处理效果,但据我所知,这是无数错误的原因。

当我在PIX中运行我的代码时,我得到以下网格,但是正方形应该是直的并覆盖屏幕,不应该吗?

Mesh information from PIX capture

我的顶点着色器不进行变换,只是将位置信息传递给像素着色器。

创建正方形的函数如下:

private void InitializeGeometry()
    {
        meshes = new Dictionary<Vector3, Mesh>();
        //build array of vertices for one square
        ppVertex[] vertexes = new ppVertex[4];
        //vertexes[0].Position = new Vector3(-1f, -1f, 0.25f);

        vertexes[0].Position = new Vector3(-1, -1, 1f);
        vertexes[1].Position = new Vector3(-1, 1, 1f);
        vertexes[2].Position = new Vector3(1, -1, 1f);
        vertexes[3].Position = new Vector3(1, 1, 1f);

        vertexes[0].TexCoords = new Vector2(0, 0);
        vertexes[1].TexCoords = new Vector2(0, 1);
        vertexes[2].TexCoords = new Vector2(1, 0);
        vertexes[3].TexCoords = new Vector2(1, 1);

        //build index array for the vertices to build a quad from two triangles
        short[] indexes = { 0, 1, 2, 1, 3, 2 };

        //create the data stream to push the vertex data into the buffer
        DataStream vertices = new DataStream(Marshal.SizeOf(typeof(Vertex)) * 4, true, true);
        //load the data stream
        vertices.WriteRange(vertexes);
        //reset the data position
        vertices.Position = 0;

        //create the data stream to push the index data into the buffer
        DataStream indices = new DataStream(sizeof(short) * 6, true, true);
        //load the data stream
        indices.WriteRange(indexes);
        //reset the data position
        indices.Position = 0;

        //create the mesh object
        Mesh mesh = new Mesh();

        //create the description of the vertex buffer
        D3D.BufferDescription vbd = new BufferDescription();
        vbd.BindFlags = D3D.BindFlags.VertexBuffer;
        vbd.CpuAccessFlags = D3D.CpuAccessFlags.None;
        vbd.OptionFlags = ResourceOptionFlags.None;
        vbd.SizeInBytes = Marshal.SizeOf(typeof(Vertex)) * 4;
        vbd.Usage = ResourceUsage.Default;
        //create and assign the vertex buffer to the mesh, filling it with data
        mesh.VertexBuffer = new D3D.Buffer(device, vertices, vbd);

        //create the description of the index buffer
        D3D.BufferDescription ibd = new BufferDescription();
        ibd.BindFlags = D3D.BindFlags.IndexBuffer;
        ibd.CpuAccessFlags = D3D.CpuAccessFlags.None;
        ibd.OptionFlags = ResourceOptionFlags.None;
        ibd.SizeInBytes = sizeof(short) * 6;
        ibd.Usage = ResourceUsage.Default;
        //create and assign the index buffer to the mesh, filling it with data
        mesh.IndexBuffer = new D3D.Buffer(device, indices, ibd);

        //get vertex and index counts
        mesh.vertices = vertexes.GetLength(0);
        mesh.indices = indexes.Length;

        //close the data streams
        indices.Close();
        vertices.Close();

        meshes.Add(new Vector3(0), mesh);
    }

当我渲染广场时:

private void DrawScene()
    {
        lock (meshes)
        {
            foreach (Mesh mesh in meshes.Values)
            {
                if (mesh.indices > 0)
                {
                    try
                    {
                        //if (camera.SphereInFrustum(mesh.BoundingSphere, sphereRadius))
                        //{
                            context.InputAssembler.SetVertexBuffers(0, new VertexBufferBinding(mesh.VertexBuffer, Marshal.SizeOf(typeof(Vertex)), 0));
                            context.InputAssembler.SetIndexBuffer(mesh.IndexBuffer, Format.R16_UInt, 0);
                            context.DrawIndexed(mesh.indices, 0, 0);
                        //}
                    }
                    catch (Exception err)
                    {
                        MessageBox.Show(err.Message);
                    }
                }
            }
        }
    }

编辑:我添加了正在运行的顶点着色器

cbuffer EveryFrame : register(cb0)
{
    float3 diffuseColor : packoffset(c0);
    float3 lightdir : packoffset(c1);
};

cbuffer EveryMotion : register(cb1)
{
    float4x4 WorldViewProjection : packoffset(c0);
    float4x4 LightWorldViewProjection : packoffset(c4);
};

struct VS_IN
{
    float3 position : POSITION;
    float3 normal : NORMAL;
    float4 col : TEXCOORD;
};

struct PS_IN
{
    float4 position : SV_POSITION;
    float4 col : TEXCOORD;
    float3 normal : NORMAL;
};

PS_IN VS(VS_IN input)
{
    PS_IN output;
    output.position = float4(input.position,1);
    output.col = input.col;
    output.normal = input.normal;
    return output;
}

这是PIX的顶点输出。

PreVS:

preVS

PostVS:

postVS

这是我选择调试顶点0

时生成的反汇编PIX
//
// Generated by Microsoft (R) HLSL Shader Compiler 9.29.952.3111
//
//
//
// Input signature:
//
// Name             Index   Mask Register SysValue Format   Used
// ---------------- ----- ------ -------- -------- ------ ------
// POSITION             0   xyz         0     NONE  float   xyz 
// NORMAL               0   xyz         1     NONE  float   xyz 
// TEXCOORD             0   xyzw        2     NONE  float       
//
//
// Output signature:
//
// Name             Index   Mask Register SysValue Format   Used
// ---------------- ----- ------ -------- -------- ------ ------
// SV_POSITION          0   xyzw        0      POS  float   xyzw
// TEXCOORD             0   xyzw        1     NONE  float   xyzw
// NORMAL               0   xyz         2     NONE  float   xyz 
//
vs_4_0
dcl_input v0.xyz
dcl_input v1.xyz
dcl_output_siv  o0.xyzw , position
dcl_output o1.xyzw
dcl_output o2.xyz
mov o0.xyz, v0.xyzx
mov o0.w, l(1.000000)
mov o1.xyzw, l(1.000000, 1.000000, 1.000000, 1.000000)
mov o2.xyz, v1.xyzx
ret 
// Approximately 5 instruction slots used

我还添加了输入汇编程序:

private void SetPPInputAssembler(Shader shader)
        {
            InputElement[] elements = new[] {
                new InputElement("POSITION",0,Format.R32G32B32_Float,0),
                new InputElement("NORMAL",0,Format.R32G32B32_Float,12,0),
                new InputElement("TEXCOORD",0,Format.R32G32_Float,24,0),
            };

            InputLayout layout = new InputLayout(device, shader.InputSignature, elements);

            context.InputAssembler.InputLayout = layout;
            context.InputAssembler.PrimitiveTopology = PrimitiveTopology.TriangleList;
        }

1 个答案:

答案 0 :(得分:3)

显然,您的顶点输入位置与您想要输入的值不匹配。

对于第一个顶点,值在纹理坐标的z坐标之前看起来很好。 您正在程序Vertex-struct中定义Vector2D,但Vertexshader Vertex-struct中的Vector4D会混淆。

只需将VS_IN更改为:

struct VS_IN
{
    float3 position : POSITION;
    float3 normal : NORMAL;
    float2 col : TEXCOORD; // float2 instead of float4
};

我不确定你是否真的想要有颜色或者更喜欢texcoords。如果你真的想要有颜色float4是正确的,但是你必须改变

vertexes[0].TexCoords = new Vector2(0, 0);

进入

vertexes[0].TexCoords = new Vector4(0, 0, 0, 0);

无论哪种方式,其中一个变量都是错误名称,可能是造成混淆的原因。