আমি হার্ডওয়্যার ইনস্ট্যান্সিং করার চেষ্টা করছি তবে আমি কিছু অদ্ভুত পারফরম্যান্স সমস্যা হিট করছি। গড় ফ্রেমরেট 45 এর কাছাকাছি, তবে এটি অত্যন্ত চপ্পল।
- বাতায়নযুক্ত
- SyncronizeWithVericalRetrace = মিথ্যা
- ইসফিক্সডটাইমস্টেপ = মিথ্যা
- উপস্থাপনা-অন্তর্ভুক্ত = উপস্থাপনা
নীচের চিত্রটি আমার পরিমাপের সময় (সহ Stopwatch
) দেখায় । শীর্ষস্থানীয় গ্রাফটি Draw
পদ্ধতিতে ব্যয় করা সময় এবং নীচের গ্রাফটি শেষ থেকে Draw
শুরু না হওয়া পর্যন্ত সময়Update
স্পাইকগুলি প্রায় 1 সেকেন্ডের ব্যবধানে দূরে থাকে এবং সর্বদা স্বাভাবিক সময়ের সাথে 2,3,4 বা 5 বার থাকে। তত্ক্ষণাত্ স্পাইক অনুসারে ফ্রেমগুলি মোটেই সময় নেয় না। আমি দেখেছি এটি আবর্জনা সংগ্রহকারী নয়।
আমি বর্তমানে একটি ত্রিভুজ তালিকা হিসাবে 12 টি ত্রিভুজ এবং 36 টি সূক্ষ্ম সমন্বয়ে একটি জাল ইনস্ট্যান্স করছি (আমি জানি এটি অনুকূল নয়, তবে এটি কেবল পরীক্ষার জন্য) 1 মিলিয়ন দৃষ্টান্ত দিয়ে। আমি যদি ইনস্ট্যান্সিংয়ের কলগুলিকে 250 টি দৃষ্টান্তের ছোট্ট অংশগুলিতে কল করি তবে প্রতিটি সমস্যা উপশম হয় তবে সিপিইউ ব্যবহার উল্লেখযোগ্যভাবে বৃদ্ধি পায়। উপরের রানটি প্রতি কল কল 10000 ইনস্টেন্সে, যা সিপুতে খুব সহজ।
আমি যদি গেমটি পুরো স্ক্রিনে চালিত করি তবে নীচের গ্রাফটি প্রায় অস্তিত্বহীন, তবে Draw
পদ্ধতিতে এখন একই সমস্যা দেখা দেয় ।
এখানে পিআইএক্সের ভিতরে একটি রান রয়েছে যা আমার কাছে মোটেই বোঝায় না। কিছু ফ্রেমের জন্য মনে হচ্ছে কোনও রেন্ডারিং করা হয়নি ...
কোন ধারণা, কি কারণ হতে পারে?
সম্পাদনা : অনুরোধ হিসাবে, রেন্ডার কোড সম্পর্কিত প্রাসঙ্গিক অংশ
এ CubeBuffer
তৈরি এবং সূচনা হয়, তারপরে কিউব দিয়ে ভরা হয়। যদি কিউবসের পরিমাণ নির্দিষ্ট সীমা ছাড়িয়ে যায় তবে একটি নতুন CubeBuffer
তৈরি করা হবে ইত্যাদি। প্রতিটি বাফার সমস্ত কলকে একটি কলে কল করে।
শুধুমাত্র একবারের জন্য প্রয়োজনীয় তথ্য হ'ল static
(ভার্টেক্স, সূচক বাফার এবং শীর্ষস্থানীয় ঘোষণা; যদিও এটি এখন পর্যন্ত কোনও পার্থক্য রাখে না)। টেক্সচারটি 512x512
আঁকুন ()
device.Clear(Color.DarkSlateGray);
device.RasterizerState = new RasterizerState() { };
device.BlendState = new BlendState { };
device.DepthStencilState = new DepthStencilState() { DepthBufferEnable = true };
//samplerState=new SamplerState() { AddressU = TextureAddressMode.Mirror, AddressV = TextureAddressMode.Mirror, Filter = TextureFilter.Linear };
device.SamplerStates[0] = samplerState
effect.CurrentTechnique = effect.Techniques["InstancingTexColorLight"];
effect.Parameters["xView"].SetValue(cam.viewMatrix);
effect.Parameters["xProjection"].SetValue(projectionMatrix);
effect.Parameters["xWorld"].SetValue(worldMatrix);
effect.Parameters["cubeTexture"].SetValue(texAtlas);
foreach (EffectPass pass in effect.CurrentTechnique.Passes)
pass.Apply();
foreach (var buf in CubeBuffers)
buf.Draw();
base.Draw(gameTime);
CubeBuffer
[StructLayout(LayoutKind.Sequential)]
struct InstanceInfoOpt9
{
public Matrix World;
public Vector2 Texture;
public Vector4 Light;
};
static VertexBuffer geometryBuffer = null;
static IndexBuffer geometryIndexBuffer = null;
static VertexDeclaration instanceVertexDeclaration = null;
VertexBuffer instanceBuffer = null;
InstanceInfoOpt9[] Buffer = new InstanceInfoOpt9[MaxCubeCount];
Int32 bufferCount=0
Init()
{
if (geometryBuffer == null)
{
geometryBuffer = new VertexBuffer(Device, typeof (VertexPositionTexture), 36, BufferUsage.WriteOnly);
geometryIndexBuffer = new IndexBuffer(Device, typeof (Int32), 36, BufferUsage.WriteOnly);
vertices = new[]{...}
geometryBuffer.SetData(vertices);
indices = new[]{...}
geometryIndexBuffer.SetData(indices);
var instanceStreamElements = new VertexElement[6];
instanceStreamElements[0] = new VertexElement(sizeof (float)*0, VertexElementFormat.Vector4, VertexElementUsage.TextureCoordinate, 1);
instanceStreamElements[1] = new VertexElement(sizeof (float)*4, VertexElementFormat.Vector4, VertexElementUsage.TextureCoordinate, 2);
instanceStreamElements[2] = new VertexElement(sizeof (float)*8, VertexElementFormat.Vector4, VertexElementUsage.TextureCoordinate, 3);
instanceStreamElements[3] = new VertexElement(sizeof (float)*12, VertexElementFormat.Vector4, VertexElementUsage.TextureCoordinate, 4);
instanceStreamElements[4] = new VertexElement(sizeof (float)*16, VertexElementFormat.Vector2, VertexElementUsage.TextureCoordinate, 5);
instanceStreamElements[5] = new VertexElement(sizeof (float)*18, VertexElementFormat.Vector4, VertexElementUsage.TextureCoordinate, 6);
instanceVertexDeclaration = new VertexDeclaration(instanceStreamElements);
}
instanceBuffer = new VertexBuffer(Device, instanceVertexDeclaration, MaxCubeCount, BufferUsage.WriteOnly);
instanceBuffer.SetData(Buffer);
bindings = new[]
{
new VertexBufferBinding(geometryBuffer),
new VertexBufferBinding(instanceBuffer, 0, 1),
};
}
AddRandomCube(Vector3 pos)
{
if(cubes.Count >= MaxCubeCount)
return null;
Vector2 tex = new Vector2(rnd.Next(0, 16), rnd.Next(0, 16))
Vector4 l= new Vector4((float)rnd.Next(), (float)rnd.Next(), (float)rnd.Next(), (float)rnd.Next());
var cube = new InstanceInfoOpt9(Matrix.CreateTranslation(pos),tex, l);
Buffer[bufferCount++] = cube;
return cube;
}
Draw()
{
Device.Indices = geometryIndexBuffer;
Device.SetVertexBuffers(bindings);
Device.DrawInstancedPrimitives(PrimitiveType.TriangleList, 0, 0, 36, 0, 12, bufferCount);
}
Shader
float4x4 xView;
float4x4 xProjection;
float4x4 xWorld;
texture cubeTexture;
sampler TexColorLightSampler = sampler_state
{
texture = <cubeTexture>;
mipfilter = LINEAR;
minfilter = LINEAR;
magfilter = LINEAR;
};
struct InstancingVSTexColorLightInput
{
float4 Position : POSITION0;
float2 TexCoord : TEXCOORD0;
};
struct InstancingVSTexColorLightOutput
{
float4 Position : POSITION0;
float2 TexCoord : TEXCOORD0;
float4 Light : TEXCOORD1;
};
InstancingVSTexColorLightOutput InstancingVSTexColorLight(InstancingVSTexColorLightInput input, float4x4 instanceTransform : TEXCOORD1, float2 instanceTex : TEXCOORD5, float4 instanceLight : TEXCOORD6)
{
float4x4 preViewProjection = mul (xView, xProjection);
float4x4 preWorldViewProjection = mul (xWorld, preViewProjection);
InstancingVSTexColorLightOutput output;
float4 pos = input.Position;
pos = mul(pos, transpose(instanceTransform));
pos = mul(pos, preWorldViewProjection);
output.Position = pos;
output.Light = instanceLight;
output.TexCoord = float2((input.TexCoord.x / 16.0f) + (1.0f / 16.0f * instanceTex.x),
(input.TexCoord.y / 16.0f) + (1.0f / 16.0f * instanceTex.y));
return output;
}
float4 InstancingPSTexColorLight(InstancingVSTexColorLightOutput input) : COLOR0
{
float4 color = tex2D(TexColorLightSampler, input.TexCoord);
color.r = color.r * input.Light.r;
color.g = color.g * input.Light.g;
color.b = color.b * input.Light.b;
color.a = color.a * input.Light.a;
return color;
}
technique InstancingTexColorLight
{
pass Pass0
{
VertexShader = compile vs_3_0 InstancingVSTexColorLight();
PixelShader = compile ps_3_0 InstancingPSTexColorLight();
}
}