• Advertisement
Sign in to follow this  

DrawInstanced problem

This topic is 1878 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

I suppose DrawInstanced() 4th parameter, last parameter, makes this...
If i have this
DrawInstanced( 1, 80000,0,1 );
it should draw 79999 intances and when drawing the first intace, in the vertex shader, the SV_InstanceID variable starts with 1 intead of 0.
But it doesnt matters what number I put in the 4th parameter, it does the same thing as DrawInstanced( 1, 80000,0,0 );... it can even be bigger that 80000 and there is no difference.

I just want to know if what i think the 4th parameter does is correct. Edited by lomateron

Share this post


Link to post
Share on other sites
Advertisement
It doesn't add to SV_InstanceId, the only difference is on the vertex buffer on the instance part. the SV_InstanceID 0 should have the data from the second instance on the vertex buffer. Hope I made myself clear. Edited by Such1

Share this post


Link to post
Share on other sites
I have never thought about instances inside a vertex buffer, where can i found more about that. I thought an instance could only be a whole vertex buffer.

Share this post


Link to post
Share on other sites
Sorry, I guess you didn't understand.
You have this:(hypotetically)
VERTEX* vertexBuffer0;
INSTANCE* vertexBuffer1:

that 4th parameter change which one will be the SV_InstanceID data. If you say the 4th parameter is x, the hypotetical formula would be:
InstanceData = vertexBuffer1[SV_InstanceID + x];

I think this way is easier to understand.

Share this post


Link to post
Share on other sites
wait!... i still dont undesrtand
isn't the data the same in all intances?
"data" is the vertex buffer
i dont understand your second post
you could tell me what DrawInstanced( 1, 80000,0,1 ); is really doing to explain me, supposing that the vertex buffer just has one vertice in it... or 3 if that 4th parameter doesn't works when you have just 1 vertice. Edited by lomateron

Share this post


Link to post
Share on other sites
Think of it this way (pseudo code):

[CODE]
void DrawInstanced(..., int vertexCount, int instanceCount, ...)
{
for (int instanceId = 0; instanceId < instanceCount; instanceId++)
{
for (int vertexId = 0; vertexId < vertexCount; vertexId++)
{
Vertex vertex;
for (int inputLayoutIndex = 0; inputLayoutIndex < inputLayout.getCount(); inputLayoutIndex++)
{
InputLayoutElement element = inputLayout.get(inputLayoutIndex);
int vertexBufferIndex = element.getVertexBufferIndex();
int vertexBufferOffset = element.getVertexBufferOffset();

VertexBuffer vertexBuffer = vertexBuffers[vertexBufferIndex];
int stride = vertexBuffer.getByteStride();

Object value;
if (element.getClassification() == Classification.Instance)
{
value = vertexBuffer[instanceId * stride + vertexBufferOffset];
}
else
{
value = vertexBuffer[vertexId * stride + vertexBufferOffset];
}

String semantic = element.getSemantic();
vertex.setValue(semantic, value);
}

VertexShader(vertex);
}
}
}
[/CODE]

That means that your input layout could look like this:

[Semantic, VertexBufferIndex, VertexBufferOffset, Classification]
["VERTEX_VALUE_0", 0, 0, Vertex]
["VERTEX_VALUE_1", 0, 8, Vertex]
["VERTEX_VALUE_2", 0, 16, Vertex]
["INSTANCE_VALUE_0", 1, 0, Instance]
["INSTANCE_VALUE_1", 1, 8, Instance]

You than simply use 2 vertex buffers:

VertexBuffer 0: [[vertexValue0, vertexValue1, vertexValue2], [vertexValue0, vertexValue1, vertexValue2], [vertexValue0, vertexValue1, vertexValue2], ...]
VertexBuffer 1: [[instanceValue0, instanceValue1], [instanceValue0, instanceValue1], [instanceValue0, instanceValue1], ...]

And it basically takes a cartesian product of both sets to call the vertex shader. Edited by CryZe

Share this post


Link to post
Share on other sites
When you have intance drawing you have 2 vertex buffers, one for the vertices and the other for the instances data. I guess thats what you are confused about.

Share this post


Link to post
Share on other sites
[quote name='Such1' timestamp='1354051979' post='5004684']
When you have intance drawing you have 2 vertex buffers, one for the vertices and the other for the instances data. I guess thats what you are confused about.
[/quote]

You don't necessary need a second vertex stream for the instancing data. DrawInstanced provides you a instance ID in the shader and it may be used to index a constant buffer or generic buffer object.

Cheers! Edited by kauna

Share this post


Link to post
Share on other sites
You can, but I think the vertex buffer is a better idea. And the 4th parameter only matters if you are using the vertex buffer to pass instances data.

Share this post


Link to post
Share on other sites
[quote name='Such1' timestamp='1354080698' post='5004855']
You can, but I think the vertex buffer is a better idea.
[/quote]

Sometines you might not even need any per instance data, you could generate it in the vertex shader. For example if I was drawing an NxN square of objects I might do

[code]
// game code
int squareSide = 10;
SetVertexShaderInt("SquareSide", squareSide);
DrawInstanced(numVertices, squareSide*squareSide);

// shader
int SquareSide;

VertexShader(instanceID : SV_INSTANCEID)
{
instance_pos.x = instanceID / SquareSide;
instance_pos.z = instanceID % SquareSide
...
}
[/code]

fairly contrived example I concede

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement