2012-11-27 63 views
3

我有一個640x480 rendertarget(它的主要backbuffer)。全屏四像素着色器有屏幕座標嗎?

即時傳遞一個全屏四邊形頂點着色器,全屏四具有[-1,1]爲X和Y,這意味着,我只通過座標轉換的像素着色器,沒有計算座標之間:

struct VSInput 
{ 
    float4 Position : SV_POSITION0; 
}; 

struct VSOutput 
{ 
    float4 Position : SV_POSITION0; 
}; 

VSOutput VS(VSInput input) 
{ 
    VSOutput output = (VSOutput)0; 
    output.Position = input.Position; 
    return output; 
} 

,但是,從像素着色器,所述x和y座標的每個片段的屏幕空間(0 < X < 640和0 <ÿ< 480)。 這是爲什麼?我一直認爲座標將在插值到像素着色器的途中插入到-1,1之間,在這種情況下更是如此,因爲我在頂點着色器上硬編碼了-1和1之間的座標。

但事實是,這個像素着色器的工作原理:

float x = input.Position.x; 

if(x < 200) 
    output.Diffuse = float4(1.0, 0.0, 0.0, 1.0); 
else if(x > 400) 
    output.Diffuse = float4(0.0, 0.0, 1.0, 1.0); 
else 
    output.Diffuse = float4(0.0, 1.0, 0.0, 1.0); 

return output; 

它輸出我的呈現窗口上3周色的條紋,但如果我改變從屏幕空間(從上面的代碼中的200和400)將這些值-1,1空格,並使用類似if(x < 0.5)它不會工作。

我已經嘗試過

浮子X = input.Position.x/input.Position.w;

因爲我讀的地方,我可以得到-1,1之間的值,但它也不工作。

在此先感謝。

回答

4

從MSDN上Semantics -page約SV_POSITION:

當在像素着色器中使用,SV_Position描述了像素位置。

所以你看到了預期的行爲。

最好的解決方案是將屏幕空間座標作爲附加參數傳遞。我喜歡用這種「全屏幕三角」頂點着色器:

struct VSQuadOut { 
    float4 position : SV_Position; 
    float2 uv: TexCoord; 
}; 

// outputs a full screen triangle with screen-space coordinates 
// input: three empty vertices 
VSQuadOut VSQuad(uint vertexID : SV_VertexID){ 
    VSQuadOut result; 
    result.uv = float2((vertexID << 1) & 2, vertexID & 2); 
    result.position = float4(result.uv * float2(2.0f, -2.0f) + float2(-1.0f, 1.0f), 0.0f, 1.0f); 
    return result; 
} 

(原始來源:Full screen quad without vertex buffer?

+0

非常感謝,這完美地工作,並沒有頂點緩衝區需要它,甚至更好。 – sap