[英]directx11 Point light issue. Objects translated from the origin are not lit correctly
如標題中所述,我的問題是我的點光源似乎沒有考慮任何對象的當前位置。 它似乎照亮了對象,好像仍在原點周圍繪制對象一樣。
示例:我正在使用的當前場景包含兩個框,第一個尚未平移,因此仍位於原點周圍,我為此框增加了z軸的比例,將其拉伸,並且光源似乎可以與新框一起正常工作對象的大小。 第二個框已沿z軸平移回去,並且x和y軸按比例放大以創建一種牆。 在此盒子上看不到任何光,直到光源本身從盒子上移開,在該點上,表面上出現了一個亮點,就像光線從盒子上的該點發出一樣。
當光線到達原本應該位於盒子表面的位置時,就會發生這種情況。
我希望上面的示例解釋了我遇到的問題,這可能是由於我將矩陣傳遞給着色器而導致無法找到問題所在。
更新矩陣並渲染代碼
//Temporary Matricies
XMMATRIX worldMatrix;
XMMATRIX modelMatrix;
worldMatrix = worldMx;
//Rotate the model Matrix
XMFLOAT3 TempRot = m_GeometryList[ID].GetRotation();
worldMatrix = XMMatrixRotationRollPitchYaw(TempRot.x, TempRot.y, TempRot.z);
//Scale the model matrix
XMFLOAT3 TempScale = m_GeometryList[ID].GetScale();
worldMatrix *=XMMatrixScaling(TempScale.x, TempScale.y, TempScale.z);
//translate into world space
XMFLOAT3 TempPos = m_GeometryList[ID].GetPosition();
worldMatrix *= XMMatrixTranslation(TempPos.x, TempPos.y, TempPos.z);
//Create the model matrix
modelMatrix = XMMatrixIdentity();
modelMatrix = worldMatrix * viewMx * projMx;
// Update the constant buffer
_WorldViewProjMx->SetMatrix((float*)&modelMatrix);
// Update the World Matrix
//worldMatrix = XMMatrixTranspose(worldMatrix);
_WorldMx->SetMatrix((float*)&worldMatrix);
////(Earlier in the code)
_WorldViewProjMx = _fX->GetVariableByName("worldViewProj")->AsMatrix();
_WorldMx = _fX->GetVariableByName("worldMatrix")->AsMatrix();
/////
着色器
// Shaders
struct VertexIn {
float3 pos : POSITION;
float4 color : COLOR;
float2 TexCoord : TEXCOORD;
float3 Normal : NORMAL;
};
struct VertexOut {
float4 posH : SV_POSITION;
float4 color : COLOR;
float2 TexCoord : TEXCOORD0;
float3 Normal : NORMAL;
float3 ViewDirection : TEXCOORD1;
float4 posW : POSITION;
};
VertexOut RenderSceneVS(VertexIn vin) {
VertexOut vout;
vout.posH = mul(float4(vin.pos, 1.0f), worldViewProj);
vout.Normal = mul(vin.Normal, worldMatrix);//worldInverseTranspose);
vout.color = vin.color;
vout.TexCoord = vin.TexCoord;
// needed for point lights
vout.posW = mul(vin.pos, worldMatrix);
// needed for specular lighting
vout.ViewDirection = cameraPosition.xyz - vout.posW.xyz;
vout.ViewDirection = normalize(vout.ViewDirection);
return vout;
}
float4 RenderPointDiffusePS(VertexOut pin) : SV_TARGET0
{
float4 colour = Texture.Sample(Sampler, pin.TexCoord);
//Create the vector between light position and pixels position
float3 lightToPixelVec = light.pos - pin.posW;
//Find the distance between the light pos and pixel pos
float d = length(lightToPixelVec);
//Create the ambient light
float3 finalAmbient = colour * light.ambient;
//If pixel is too far, return pixel color with ambient light
if( d > light.range )
{
return float4(finalAmbient, colour.a);
}
//Turn lightToPixelVec into a unit length vector describing
//the pixels direction from the lights position
lightToPixelVec /= d;
//Calculate how much light the pixel gets by the angle
//in which the light strikes the pixels surface
float howMuchLight = dot(lightToPixelVec, pin.Normal);
float3 tempColor = float3(0.0f, 0.0f, 0.0f);
//If light is striking the front side of the pixel
if( howMuchLight > 0.0f )
{
//Add light to the finalColor of the pixel
tempColor += howMuchLight * colour * light.diffuse;
//Calculate Light's Falloff factor
tempColor /= light.att[0] + (light.att[1] * d) + (light.att[2] * (d*d));
}
float3 finalColor = saturate(tempColor + finalAmbient);
return float4(finalColor, colour.a);
}
任何幫助/建議都將受到歡迎,我無法理解導致此問題的原因。 如果您需要更多信息,請告訴我。
預先感謝您的幫助。
這行代碼: vout.posW = mul(vin.pos, worldMatrix);
應為: vout.posW = mul( float4(vin.pos,1), worldMatrix);
因為現在您沒有將轉換應用於posW向量。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.