Archived

This topic is now archived and is closed to further replies.

Mithrandir

Performance of updating the vertex buffer every frame?

Recommended Posts

Yes it is a bad thing.
In my experimental d3d engine lock() writing and unlock() costs between 20 and 40 frames per second, depending on the system, and the number of vertices you write into the buffer.

Share this post


Link to post
Share on other sites
Funny I was just posting my question near from yours when I saw your post my title would have been:
"How fast is fast"

In my game everythings move and deform, sea , trail , shadow, texture on sky.

So I have mutliple vertex buffer that I lock each frame and with
about 19''000 poly (576000 second) it still run at about 24 fps when the view is very busy. (p400 tnt2 very midle gamer machine)
When I have no boat on view (mean only sea, trail, sun, sky) my FPS increase to 100+fps and I still have the vertex buffer of the sea (3200+400 poly)that is updated each frame.
The main slowdown come with the boat that don''t have vertex buffer changed. (normal x model)

I update each frame independant array with all my vertex value that are computed in real time and copied at the end.
(WRITEONLY)

  
for(i=0;I<NbrVertex;I++)
{
sourcearray.p.x=122.0f;
sourcearray.p.y=12.0f;
sourcearray.p.tu=1.0f;
//etc ...

}
Lock()
memcpy(&vertexbuffer,&sourcearray,Numberofvertice);
unlock()


So while I see so much msg about avoiding locking vertex buffer
I wonder how we are supposed to make real time model such as trail, smoke , sea ect ect...

At least it seam to work for me.

Share this post


Link to post
Share on other sites
Why are you updating the vertices? That''s what the transformation matrices are for.

I almost never lock the vertex buffers (except to fill them initially). In most cases, there is a better way...

Share this post


Link to post
Share on other sites
Sea is impossible to modelise with a tranformation matrice keeping all the control that I have now on it and I also need the value of each poly to clamp the boat onto.
Same for the sail trail that must clamp onto the sea.
And I wonder how doing a missille trail without updating the vertex If you have a solution I will be very glad to ear it.
Sure that for texture moving I must look into projection matrice
(is this the right ways to just scroll a texture?) but this will save only few vertex buffer updating.

Howewer it seem to run fine for now on a medium computer.

Dan

Share this post


Link to post
Share on other sites
I''m updating the vertex''s every frame because that is how my system works.

I am doing my own transformations (special purposes, cant be done with matricies, etc) of objects from object->world->camera space, then sending everything to DX to draw it.

In essence, I want to use DirectX as a rasterizing engine, but not a transformation engine.

Share this post


Link to post
Share on other sites
Mith - just curious, what types of transformations are you doing? One possible answer is to go with shaders, but you can do quite a bit with matrices.

Dan - I''m not sure exactly what you want out of a missle trail, but you would probably be able to do *something* with the matrices.

Also, to change the texture coordinates, use a texture matrix, not the projection matrix.

If both of you are getting acceptable framerates, that''s good. The point is that it may be easy to make changes that free up more horsepower for new features. (maybe??)

Share this post


Link to post
Share on other sites
Writing vertices on real-time every frame is OK (when needed)
The SDK documentation has a couple of pages about Dynamic vertex buffers and their usage (presenting 3 different methods to lock/fill/unlock, one of them requiring at least thousands of vertices per frame)

The CD3DFont class uses a dynamic vertex buffer filled with vertices on each call.

If your vertices are static, make them static, otherwise don''t

Share this post


Link to post
Share on other sites
quote:
Original post by CrazedGenius
Dan - I'm not sure exactly what you want out of a missle trail, but you would probably be able to do *something* with the matrices.



I will really be glad that can work with matrice but I cannot see any solution for that.

In fact a loooong trail that follow a missile can only be created in real time so I transform the point of the rear bounding box into world point and create my polygon

let me try ascii art



fig 1:
poly
******* missile
* * -------------* * -------------/
*******

fig 2:
when it reach a certain height the poly is broken and another one started so we have smooth curve. (strip)

those two vertex follow the missle until
height is reached
|
poly |
************** missile
* * * -------------* * * -------------/
**************


While an image worth thousand word here was my first test:



and the result:


As you see matrix cannot help here or I missed something :-)

Dan

Edited by - dansteph on October 31, 2001 5:07:22 PM

Share this post


Link to post
Share on other sites
That looks pretty darn good!

I also have a situation that might require updating the vertex buffer per frame. I have a particle system with a vertex buffer of a set size that holds all the vertices for the particles. Now the particles have to move in all sorts of different directions, so I manipulate the attributes of the individual particles, then refill the vertex buffer, then render them all in a big bunch. They say that you should batch polys as much as possible, so whats slower, refilling the vertex buffer or rendering 2000 triangles 2 at a time (1000 calls to DrawPrimitive!)?

Share this post


Link to post
Share on other sites
Thats exactly what I''ve been trying to find out with my posts (moving D3D points quickly)... Its really stumping me how I''m suppose to "animate" objects without locking... The particle system is a great example of a situation I''m thinking of... I hope someone answers soon... CrazedGenius please save us!

Share this post


Link to post
Share on other sites
I can tell you for a fact that for a particle system of any significant size, you CANNOT use transformation matrices (except in very special situations...), because of a major slowdown. This comes from a test I did a while abck while working on a fire p system. The particles had to scale down as they went up (so the fire tapered). To get an acceptable frame rate, i had to clamp the number of particles in the system to 8. On the other hand, for a snow system, i had 650 particles going at once (my vid card really sucks, to explain the low numbers). Both systems lock on every frame, but the fire system had to set a scaling matrix, and render each particle individually, while the snow just set a simgle scale matrix as per the first particle, and then drew every particle in a single call.

The only real situation that i can think of at the moment is for a particle system in the basic shape of a sphere that is scaled up or down.

Z.

Share this post


Link to post
Share on other sites
Whenever you need to modify the vertices in an object individually instead of the object as an aggregate, you cannot just use a transformation matrix (because all vertices are affected uniformly). You do have a few options:

1) Lock the vertex buffer and update it. If you do this, you obviously need to minimize lock calls, and work on local copies -- never READ the buffer.

2) Store different meshes for different frames of the animation, and just display the appropriate mesh. This is the fastest (and usually takes the most memory) way, but obviously only works if animation is predicatable and small enough to store.

3)Try to fake if with textures.

4) Divide the mesh into subcomponents and use one of the above on each portion.

Which method you choose depends on what you are trying to do and what you are willing to pay in terms of flexibilty vs performance. Its not necessarily "bad" to lock the buffer; it is bad to not use locks as minimally or efficiently as possible (ie. don''t lock and copy on every frame -- only on those frames where something visible has changed).

Share this post


Link to post
Share on other sites
quote:
Original post by Moe
That looks pretty darn good!

I also have a situation that might require updating the vertex buffer per frame. I have a particle system with a vertex buffer of a set size that holds all the vertices for the particles. Now the particles have to move in all sorts of different directions, so I manipulate the attributes of the individual particles, then refill the vertex buffer, then render them all in a big bunch. They say that you should batch polys as much as possible, so whats slower, refilling the vertex buffer or rendering 2000 triangles 2 at a time (1000 calls to DrawPrimitive!)?

G''day!

In a situation like this, locking and updating your VB is going to be much faster than drawing them individually. When doing this, make your VB''s write-only and lock using DISCARD. If you need read-write, then have an array of vertices that you update, then lock the VB (again using discard) and copy your array in.


Stay Casual,

Ken
Drunken Hyena

Share this post


Link to post
Share on other sites
As ususal, this post is about a month too late for me. I had a problem stretching a VB (couldn''t use Matrix transforms because only the y cood changed and it is relative to the x coord). DISCARD (it took me 2 weeks to change that) made a big difference, as well as only changing the .z coords that needed changing and leaving all the rest. I ended up only having 20 lines (in a 200 vert mesh) of code between ->lock() and ->unlock(), but i still had to pay about 18-20 fps for it. I guess it comes down to can you afford the fps for the effect (and if YOU can''t, you can always set the system requirements to something bigger than YOU own hehehe). btw that is some very nice rendering with the ship and missile there (i like the waves too)

Brett Lynnes
cheez_keeper@hotmail.com

Share this post


Link to post
Share on other sites
Now, maybe i''m just not understanding what use Vertex buffers are for.


I mean, are you supposed to have 50 million VB''s, one for each object, or what?

Or are you supposed to have one big VB, representing every object in the system? How then, does one remove objects from the system without totally mucking up the VB?

I''m just very confused, VB''s seem like a bloated piece of crap that has absolutely no real-world use.

Share this post


Link to post
Share on other sites
It really depends on the project. I have 2 examples of the extremes.

Example 1:

I had a 3D Scene that had one part of it moving but the rest was fairly static. I created one HUGE vb with everything in it. Drew the first several hundered triangles using strips and fans, then drew the remaining moving buffer using triangle lists. all a VB holds is the points, so you can choose where to start and stop rendering those points (ie. do the world matrix move and THEN render a triangle list from vertex 2801 for 12 triangles)

I also have a 2D one where I maintain about 70 different arrays of VBs... I like this better for 2D because it gives me more control (i have to ->Lock and ->Unlock) but it does make for some nasty init/drawing/update routines... infact I had to spilt up the file 4 times JUST to keep track of the VBs without having 100K lines of code in a file....

both ways run at very resonable speeds. I have heard that having EVERTHING in one VB can go quicker on the newer cards, but seriously you should look at practicality of programming rather than speed in this.

Brett Lynnes
cheez_keeper@hotmail.com

Share this post


Link to post
Share on other sites
Want to know something scary? In the DirectX SDK for the one using point sprites, they draw each particle seperately so they can make them look like they streak.

Share this post


Link to post
Share on other sites