我刚开始使用 XNA 的着色器,我遇到了一些我几乎没有立即理解的行为。
我创建了一个简单的场景,其中包含一个带纹理的盒子和一些地面,由一个使用重复纹理的单个纹理四边形组成(所以我的纹理坐标从 0,0 到 10,10 使其重复 10 次)。最初,这两个都使用了 BasicEffect 类。
然后我按照教程创建了我的第一个着色器并将其用于立方体 - 只不过是一个着色器,它在坐标坐标处返回纹理的颜色,为我提供与以前相同的纹理立方体。
然而奇怪的事情发生了——突然间,地面大部分是纯色的,有两个模糊的边缘和一个角落里的正确纹理实例。纹理不再重复。我将绘制立方体和地面的顺序更改为无效,仅注释掉立方体解决的问题。
然后我查看了我的着色器代码,大部分只是从教程中复制的,发现它为 AddressU 和 AddressV 指定了 Clamp。将其更改为 Wrap 解决了所有问题,但仍然给我留下了一个问题 - 为什么一个着色器的纹理环绕逻辑会影响基本着色器?这是一种正常的行为,我需要做某种状态保存吗,或者这是否表明我的代码中可能有另一个错误?
groundEffect.View = camera1.View; // BasicEffect
groundEffect.Projection = projection;
groundEffect.World = Matrix.CreateTranslation(0, -1.5f, 0);
groundEffect.TextureEnabled = true;
groundEffect.Texture = groundTexture;
GraphicsDevice.Indices = groundIndexBuffer;
GraphicsDevice.SetVertexBuffer(groundVertexBuffer);
foreach (EffectPass pass in groundEffect.CurrentTechnique.Passes)
{
pass.Apply();
GraphicsDevice.DrawIndexedPrimitives(PrimitiveType.TriangleList, 0, 0, groundVertexBuffer.VertexCount, 0, groundIndexBuffer.IndexCount / 3);
}
shaderEffect.Parameters["View"].SetValue(camera1.View);
shaderEffect.Parameters["Projection"].SetValue(projection);
shaderEffect.Parameters["World"].SetValue(modelPosition);
shaderEffect.Parameters["ModelTexture"].SetValue(boxTexture);
GraphicsDevice.Indices = model.IndexBuffer;
GraphicsDevice.SetVertexBuffer(model.VertexBuffer);
foreach (EffectPass pass in shaderEffect.CurrentTechnique.Passes)
{
pass.Apply();
GraphicsDevice.DrawIndexedPrimitives(PrimitiveType.TriangleList, 0, 0, model.VertexBuffer.VertexCount, 0, model.IndexBuffer.IndexCount / 3);
}