Я пытаюсь добиться следующего: мой проход вернет огромный массив с несколькими уникальными числами, повторяющимися снова и снова, которые мне нужно получить и обработать на ЦП.
Я попытался выполнить рендеринг в текстуру 2000x1, а затем сэмплировал ее на ЦП с помощью RenderTarget2d.GetData‹>() и цикла foreach. Это было ужасно медленно :). Поэтому я обошел свою проблему, и теперь идея состоит в том, чтобы многократно отображать текстуру 1x1. В промежутках между проходами я буду расширять массив параметров в своем шейдере, чтобы включить уже возвращенные числа. Каждый пиксель будет затем запрашивать массив и обрезать себя, если он содержит уже появившееся число.
Проблема сейчас в том, что цвет пикселя никогда не меняется независимо от того, что я визуализирую - он всегда возвращает какие-то случайные числа. Когда я добавил Game.GraphicsDevice.Clear(Color.Transparent);
перед вызовом отрисовки, он начал возвращать нули, хотя код шейдера должен возвращать 0.2f (или его эквивалент от 0 до 255). Может ли это быть из-за того, что я визуализирую в нем слишком маленький контент (я рисую линию на экране и пробую цвет сцены вдоль линии), и в какой-то момент он прерывается?
Код С#/XNA:
CollisionRT = new RenderTarget2D(Game.GraphicsDevice, 1, 1, false, SurfaceFormat.Color, DepthFormat.None);
...
Game.GraphicsDevice.BlendState = BlendState.AlphaBlend;
Game.GraphicsDevice.SetRenderTarget(CollisionRT);
Game.GraphicsDevice.Clear(Color.Transparent);
Game.GraphicsDevice.DepthStencilState = DepthStencilState.None;
foreach (ModelMesh mesh in PPCBulletInvis.Model.Meshes)
// PPCBulletInvis is a line that covers 1/18 of the screen (approx).
{
foreach (Effect effect in mesh.Effects)
{
//effect.Parameters["Texture"].SetValue(vfTex);
effect.Parameters["halfPixel"].SetValue(halfPixel);
effect.Parameters["sceneMap"].SetValue(sceneRT);
effect.Parameters["World"].SetValue(testVWall.World);
effect.Parameters["View"].SetValue(camera.View);
effect.Parameters["Projection"].SetValue(camera.Projection);
}
mesh.Draw();
}
Game.GraphicsDevice.SetRenderTarget(null);
Rectangle sourceRectangle =
new Rectangle(0, 0, 1, 1);
Color[] retrievedColor = new Color[1];
CollisionRT.GetData<Color>(retrievedColor);
Console.WriteLine(retrievedColor[0].R); // Returns zeroes.
Код шейдера:
float4x4 World;
float4x4 View;
float4x4 Projection;
texture sceneMap;
sampler sceneSampler = sampler_state
{
Texture = (sceneMap);
AddressU = CLAMP;
AddressV = CLAMP;
MagFilter = POINT;
MinFilter = POINT;
Mipfilter = POINT;
};
float2 halfPixel;
struct VS_INPUT
{
float4 Position : POSITION0;
};
struct VS_OUTPUT
{
float4 Position : POSITION0;
float4 ScreenPosition : TEXCOORD2;
};
VS_OUTPUT VertexShaderFunction(VS_INPUT input)
{
VS_OUTPUT output;
float4 worldPosition = mul(input.Position, World);
float4 viewPosition = mul(worldPosition, View);
output.Position = mul(viewPosition, Projection);
output.ScreenPosition = output.Position;
return output;
}
float4 PixelShaderFunction(VS_OUTPUT input) : COLOR0
{
input.ScreenPosition.xy /= input.ScreenPosition.w;
float2 screenTexCoord = 0.5f * (float2(input.ScreenPosition.x,-input.ScreenPosition.y) + 1);
screenTexCoord -=halfPixel;
return (0.2f,0.2f,0.2f,0.2f);//tex2D(sceneSampler, screenTexCoord);
}
technique Technique1
{
pass Pass1
{
VertexShader = compile vs_3_0 VertexShaderFunction();
PixelShader = compile ps_3_0 PixelShaderFunction();
}
}