Project idea:Instancing & crowds.

Threads related to Google Summer of Code
Post Reply
Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

I'm preparing the implementaion of the crowd, and here is how I see this.

-During the creation of the first batch, create 1 skeleton instance per InstancedObject.
so Each InstancedObject has 1 skeleton Instance, 1 mBoneMatrices Matrix 4 array, containing the positions of the bones in the local space, 1mWorldBoneMatrices, containing the same thing but in world space(to send it to the vertex shader), and one animation state.

-After that, provide an acess method to the animation state to do the right things.


-In private method, basically a "simple" method retrieving the bone position according to the animation state:

Code: Select all

            mSkeletonInstance->setAnimationState(*mAnimationState);
 mSkeletonInstance->_getBoneMatrices(mBoneMatrices);
Multiply the mBoneMatrices by the local transformation, and send it to the shader.
(maybe I'm totally wrong with the meaning of this code, extract form OgreEntity, but it seems to be the good one)

This will be an "updateAnimation" method called in the _updateRenderQueue() method.

:arrow: If I'm not wrong, stencils need to be software animated. But this is not possible to do with instancing.

:arrow: Same thing with the vertex animation. Hardly possible to do I think.

So: questions? remarks? :lol:
Follow la Moustache on Twitter or on Facebook
Image

User avatar
sinbad
OGRE Retired Team Member
OGRE Retired Team Member
Posts: 19265
Joined: Sun Oct 06, 2002 11:19 pm
Location: Guernsey, Channel Islands
x 66
Contact:

Post by sinbad »

You're right about stencils, but vertex animation can be done in a shader too, we provide examples of morph and pose animation in vertex shaders in Example_Basic.cg.

However, it will be difficult to organise and will take up a lot more vertex bindings. Probably not that practical for the moment, even though it's technically possible.

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

Just another question :)
I'm looking at the origin of the crash when the mesh has a skeleton.

I've modified the code so that the vertex blend indices and blend weights are not deleted of the vertex data.
But as before, if the mesh has a link to a skeleton, the sample crashes.

It is easily visible with the ninja2(I give it in the zip) and the default ninja.

Both have the blend informations, but the ninja2 has no references to the skeleton.
Ninja2 is ok, ninja crashes.

The error I get is simply "Cannot create D3D9 vertex declaration: An undetermined error occurred. "

But I don't really see why the skeleton has an influance on the vertex declaration.
If someone has a tip :)

new sources, wiht 2 translate and one getLocalAxes methods

http://crashy.cartman.free.fr/SOC/samples.rar
Follow la Moustache on Twitter or on Facebook
Image

User avatar
jacmoe
OGRE Retired Moderator
OGRE Retired Moderator
Posts: 20570
Joined: Thu Jan 22, 2004 10:13 am
Location: Denmark
x 179
Contact:

Post by jacmoe »

Just wanted to say that I am excited about your project, Crashy! :)

Really looking forward to seeing what a difference it makes! :wink:
/* Less noise. More signal. */
Ogitor Scenebuilder - powered by Ogre, presented by Qt, fueled by Passion.
OgreAddons - the Ogre code suppository.

User avatar
sinbad
OGRE Retired Team Member
OGRE Retired Team Member
Posts: 19265
Joined: Sun Oct 06, 2002 11:19 pm
Location: Guernsey, Channel Islands
x 66
Contact:

Post by sinbad »

The error I get is simply "Cannot create D3D9 vertex declaration: An undetermined error occurred. "

But I don't really see why the skeleton has an influance on the vertex declaration.
For 2 reasons, normally:
1. Positions and normals are split off into their own buffers so software skinning can be done without uploading other vertex elements. Not applicable if you're only supporting hardware skinning of course.
2. Vertex bone assignments have to be encoded into a VET_UBYTE4 for hardware skinning.

Your best bet - enable the DirectX Debug Runtime, it's the only way you'll get more information.

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

2. Vertex bone assignments have to be encoded into a VET_UBYTE4 for hardware skinning.
Mmhh yes, but aren't the VES_BLEND_INDICES/WEIGHT present in the mesh already into this format?

In fact what seemed strange to me is that it works well with static geometry, but as soon as I add a new vertex element to the declaration, it crashes.
Your best bet - enable the DirectX Debug Runtime, it's the only way you'll get more information.
Don't know what it is but I'll search :lol:
(edit:ok I've found what it is)

thanks
Follow la Moustache on Twitter or on Facebook
Image

User avatar
Kentamanos
Minaton
Posts: 980
Joined: Sat Aug 07, 2004 12:08 am
Location: Dallas, TX

Post by Kentamanos »

Crashy wrote:Don't know what it is but I'll search :lol:
When you install the DirectX SDK, it's an option presented to you. It basically causes DirectX to spit out a lot of debugging information (ala OutputDebugString), so this will show up in your IDE etc. It runs a bit slower than the normal runtimes, but obviously you get more information.

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

Yep, as edited, I've found it in a Sinbad post .
But thanks to have answered :)
Here is my error message.
Direct3D9: Decl Validator: X269: (Element Error) (Decl Element [5]) Stream 0 was defined earlier. Current stream index is 0. All vertex element entries for a given stream index must be contiguous.
Direct3D9: (ERROR) :Failed to create vertex declaration

Simple to understand->the vertex element used to store the index must be before the blend informations in the vertex declaration.

I've a lot of work to do to resolve it :D
Follow la Moustache on Twitter or on Facebook
Image

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

//edit: oops , forget this post.
Follow la Moustache on Twitter or on Facebook
Image

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

I' m not so far of the end of crowd animation.
The implementation of the hardware skinning is almost completed.

However, I've a little problem with the bones matrices.
I get them with the following code

Code: Select all

mSkeletonInstance->_getBoneMatrices(mBoneMatrices);
But the result is absolutely not good
(Little screen->
http://crashy.cartman.free.fr/SOC/hardwareskin.JPG)

I made a debug to check the validity of the matrices, especially for the angles, and I've seen that the angles are inverted.
For example, if the bone is rotated from 0 to 0.2 radians during the animation, the angle in the matrice is between 0 and -0.2!
:?
I didn't check for the positions, but I think they're not good too.

I made the skeleton visible to have a vision of the animation, which looks good.
Follow la Moustache on Twitter or on Facebook
Image

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

new sources with the "wip" crowd.

http://crashy.cartman.free.fr/SOC/instancing_demo.rar

Still same problem, but I've made a little optimisation, now the skeleton is unique for the whole InstancedGeometry, and is shared for every objects.

About the problem, I tried with bone not at (0,0,0), here is the result:
The bone pivot is good, but the object don't rotate with this pivot, and in the bad direction.
But I really don't know where is the problem.
Image
Follow la Moustache on Twitter or on Facebook
Image

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

Ahahha yes it works!!!

I simply compiled the shader as a cg one and not in hlsl.
Some matrix computation are inverted in cg and Hlsl, and I was using the ogre's hardware skinning shader :lol:

Now the object is moving right, I'll try with more bones and more instanced objects 8)
Follow la Moustache on Twitter or on Facebook
Image

sharkyx
Halfling
Posts: 45
Joined: Sat Jan 03, 2004 5:09 am
Contact:

Post by sharkyx »

Very cool project. What shader version is required to run it?

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

For simple instancing you can run it on vs 1.1. But vs 2.0 is recommanded.

For the crowd, vs 2.0, because with vs 1.1 the number of constant is too limited to have more than 1 object per batch. and the objective is to have more thant 1 object, so vs 2.0 minimum :)

For the moment the crowd-rendering is near to be finished, as I succeded to have hardware skinning on the batch instances. However only the first object of each batch instance is visible, there is still a little bug, but I'm on it :lol:
Follow la Moustache on Twitter or on Facebook
Image

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

Yeah, it works:
Image

Source &demo update tomorrow :D

Notice that every animation is independant.
My previous problem was with this line:

Code: Select all

params->setNamedAutoConstant ("numBones", GpuProgramParameters::ACT_CUSTOM,mBaseSkeleton->getNumBones());
But in the shader the numBones was always equal to 0
I replaced by
params->setNamedConstant("numBones",mBaseSkeleton->getNumBones());
It works now, but the problem is that the numbones is no more dependant of the renderable, but of the material, which is not totally good.

I'm working to see a solution. But I was very happy to see this simple crowd working good
:)
Follow la Moustache on Twitter or on Facebook
Image

User avatar
Game_Ender
Ogre Magi
Posts: 1269
Joined: Wed May 25, 2005 2:31 am
Location: Rockville, MD, USA

Post by Game_Ender »

Are you using Vista Beta? Or just a Vista skin for XP?

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

It is just a vista like msstyle :)
http://vistaxp-v2-vs.en.softonic.com/ie/45452
Follow la Moustache on Twitter or on Facebook
Image

User avatar
sinbad
OGRE Retired Team Member
OGRE Retired Team Member
Posts: 19265
Joined: Sun Oct 06, 2002 11:19 pm
Location: Guernsey, Channel Islands
x 66
Contact:

Post by sinbad »

Nice work Crashy ;)

You've just got the setup wrong for binding per-renderable parameters. The idea is that you have a 2-step binding - firstly you tell the renderable what value you want to propagate, and what arbitrary 'custom parameter' number you want to associate it with:

Code: Select all

// Define a custom parameter index - doesn't matter what this is so long
// as it's unique per renderable / shader
#define SOME_UNIQUE_NUMBER 69
Vector4 vec(mBaseSkeleton->getNumBones(), 0, 0, 0);
renderable->setCustomParameter(SOME_UNIQUE_NUMBER, vec);
Then, you tell the shader that you want to pull in that 'source' of custom parameter from each renderable it works with.

Code: Select all

gpuParams->setNamedAutoConstant("numBones", GpuProgramParameters::ACT_CUSTOM, SOME_UNIQUE_NUMBER);
At runtime Ogre matches up the SOME_UNIQUE_NUMBER from the shader and the renderable and causes them to make sweet music together. ;)

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

*hhoooohh*
yes in fact it is what I make for the simple instancing, but I "stupidely" forgot how to proceed :lol:

Thanks a lot Sinbad ! Without you I surely would have been searching for hours
:)
Follow la Moustache on Twitter or on Facebook
Image

User avatar
guilderstein
Halfling
Posts: 66
Joined: Wed Jan 04, 2006 11:48 am
Location: Hungary, Budapest

Post by guilderstein »

Hullo Crashy!

I've been following this thread since it started, and I'm VERY impressed :D
Cannot wait to integrate your incredible instancing stuff with Monster.
BTW we plan to do some crowd eye candy at OpenFrag with your code.

guilderstein
"I go where I please, and I please where I go"
- Duke Nukem

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

Well, there might be something wrong in my code...
The crowd rendering using instancing is always slower than the entity-based method :cry:
With 4 objects, 100,500 or 2000, the result is the same.

I'll make some investigations, but that sounds very strange to me.

oh, just a little edit: as for the bones, I don't think that the last column of the transformation matrix for the static object is usefull. Deleting this column, I can pass more matrix in the shader, and then increase the batch size from 50 to 70 objects, and then increase the performance for static objects! I think this is a good point.
Follow la Moustache on Twitter or on Facebook
Image

klauss
Hobgoblin
Posts: 559
Joined: Wed Oct 19, 2005 4:57 pm
Location: LS87, Buenos Aires, República Argentina.

Post by klauss »

You mean you could use a 3x3 instead of a 3x4?
If you did, you can't send translations. That is, you're stuck with linear transforms, rather than affine transforms.
I don't think skeletal animation would work without translations... does it?
Unless you're talking about 4x4 vs 3x4 (last row), in which case you're right.
Oíd mortales, el grito sagrado...
Hey! What is it with that that?
Wing Commander Universe

Crashy
Google Summer of Code Student
Google Summer of Code Student
Posts: 997
Joined: Wed Jan 08, 2003 9:15 pm
Location: Lyon, France
x 48
Contact:

Post by Crashy »

3x4 vs 4x4 for static objects;) I was already using 3x4 matrices for the bones of animated objects.
I just tried, I win some fps with 70 objects per batch instead of 50, nice little gain.
Now optimize the animated objects :)
Follow la Moustache on Twitter or on Facebook
Image

klauss
Hobgoblin
Posts: 559
Joined: Wed Oct 19, 2005 4:57 pm
Location: LS87, Buenos Aires, República Argentina.

Post by klauss »

Ah... then you definitely can ditch the last row, as it's only used to derive the fourth coordinate, which you can programatically derive if you want. Though it's more expensive to do so. IIRC, w = 1/z... right?
Oíd mortales, el grito sagrado...
Hey! What is it with that that?
Wing Commander Universe

User avatar
Lee04
Minaton
Posts: 944
Joined: Mon Jul 05, 2004 4:06 pm
Location: Sweden
x 1

Post by Lee04 »

Good work keep it up!

In DX10 you have constant buffers instead of C registers.

Which suggests more or less that in DX9 you can try to have the
transformes in a texture.



cheers

Lee04
Ph.D. student in game development

Post Reply