Я пишу приложение, которое отображает графику на экране. Приложение может переключаться между графическими модулями Direct3D9 и Direct3D10 (я написал библиотеки DLL, которые обертывают как D3D9, так и D3D10). При попытке визуализировать тестовую сетку (то есть то, что в D3DX9 и в библиотеке DXUT вы можете найти как стандартную сетку, которую можно найти в примерах DirectX10), модуль Direct3D10 ведет себя довольно странно. Вот что я получаю.
D3D9:
D3D10:
Матрицы вида, проекции и мира одинаковы для обоих случаев. Единственное, что отличается, это код инициализации устройства и файлы эффектов HLSL (для простоты я применяю только окружающие цвета и не использую расширенное освещение, текстурирование и т. Д.). Может ли это быть из-за неправильной инициализации устройства или из-за плохих шейдеров? Буду признателен за любую подсказку. Я могу опубликовать любой кусок кода по запросу.
Парень из Game Dev StackExchange предположил, что это возможно из-за транспонированной матрицы проекции. Я попытался заменить порядок умножения матриц в файле шейдера, я попробовал почти каждую перестановку, которую смог получить, но на экране не было правильного вывода.
Заранее спасибо.
РЕДАКТИРОВАТЬ: Вот файл .fx. Вы можете игнорировать PS, там ничего интересного не происходит.
//Basic ambient light shader with no textures
matrix World;
matrix View;
matrix Projection;
float4 AmbientColor : AMBIENT = float4(1.0, 1.0, 1.0, 1.0);
float AmbientIntensity = 1.0;
struct VS_OUTPUT
{
float4 Position : SV_POSITION; // vertex position
float4 Color : COLOR0; // vertex color
};
RasterizerState rsWireframe { FillMode = WireFrame; };
VS_OUTPUT RenderSceneVS( float4 vPos : POSITION)
{
VS_OUTPUT output;
matrix WorldProjView = mul(World, mul(View, Projection));
vPos = mul(vPos, WorldProjView);
output.Position = vPos;
output.Color.rgb = AmbientColor * AmbientIntensity;
output.Color.a = AmbientColor.a;
return output;
}
struct PS_OUTPUT
{
float4 RGBColor : SV_Target; // Pixel color
};
PS_OUTPUT RenderScenePS( VS_OUTPUT In )
{
PS_OUTPUT output;
output.RGBColor = In.Color;
return output;
}
technique10 Ambient
{
pass P0
{
SetRasterizerState( rsWireframe );
SetVertexShader( CompileShader( vs_4_0, RenderSceneVS( ) ) );
SetGeometryShader( NULL );
SetPixelShader( CompileShader( ps_4_0, RenderScenePS( ) ) );
}
}
Убедитесь, что ваш vPos.w = 1.0f.
Если это не так, умножение матриц станет диким и приведет к странным результатам.
Не уверен, что вызывает проблему, но вы можете проверить следующее:
Редактировать: также может быть хорошей идеей просто поместить некоторую простую сетку в буфер, например, куб (даже треугольник) и проверить, правильно ли он рисует.
Вы должны транспонировать свои матрицы перед тем, как устанавливать их как константы шейдера. Если вы используете xnamath, используйте функцию XMMatrixTranspose () для каждого из миров, просмотрите и проецируйте матрицы, прежде чем устанавливать их в свой постоянный буфер.