Hinge Joint collision problem

A place to discuss everything related to Newton Dynamics.

Moderators: Sascha Willems, walaber

Re: Hinge Joint collision problem

Postby Julio Jerez » Sat Jul 14, 2012 12:03 pm

Neo wrote:Well, my mistake...assert error occurs when I try to add body...
error information:
file:dgBody.h
line:762
Expression: dgAbsf (val-1.0f)<1.0e-5f
application break at the line NewtonCreateBody


I beleive that's what causes the bug, I am guessing you are using matrices with scale. Newton 300 can handle scale graciuslly now by use scaled collision.
can you post the trace stack?
also the values of the matrix you are passing tha function.
Julio Jerez
Moderator
Moderator
 
Posts: 12426
Joined: Sun Sep 14, 2003 2:18 pm
Location: Los Angeles

Re: Hinge Joint collision problem

Postby Neo » Sat Jul 14, 2012 12:14 pm

I beleive that's what causes the bug, I am guessing you are using matrices with scale. Newton 300 can handle scale graciuslly now by use scaled collision.
can you post the trace stack?
also the values of the matrix you are passing tha function.

Trace stack?
I this stuff?:
newton_d.dll!00514617()
[Frame blow might be incorrect or missing,no symbol loaded for newton_d.dll]
newton_d.dll!004c5e95()
> irrnewt.exe!main() line108 + 0x22 byte C++
irrnewt.exe!__tmainCRTStartup() line582 + 0x19 byte C
irrnewt.exe!mainCRTStartup() line399 C
kernel32.dll!7c817067()
msvcr90d.dll!_mbsnbcpy_l(unsigned char * dst=0xcccccccc, const unsigned char * src=0xcccccccc, unsigned int cnt=3435973836, localeinfo_struct * plocinfo=0xcccccccc) 行57 + 0x29 byte C++
cccccccc()
Last edited by Neo on Sat Jul 14, 2012 12:15 pm, edited 1 time in total.
Neo
 
Posts: 127
Joined: Fri May 11, 2012 12:29 pm
Location: China,Sichuan

Re: Hinge Joint collision problem

Postby JoeJ » Sat Jul 14, 2012 12:15 pm

The asserts are usually a hint that you made a mistake - never turn them off, as they are very helpful.
Ther must be something buggy in the way you create a body.
Example is giving bad matrices - that's why i asked for asserts and to plot them...

You have the assert when you create the first body? That's good, so the problem will be easy to find.
dgBody.h, line:762 is your first assert? any following asserts may be caused by the first usually.
Close to this line is debug function which checks each matrix number for ininity and NaN,
so i need to ask for the ploted given matrix (now at body creation) again.
Often people forget to set the last row of matrix properly (0,0,0,1).

Edit: Julios Idea of scaled matrices gives sense - maybe newton fixes them afterwards to the nice values you posted previously,
but at joint setup its local matrices will be wrong (CustomHinge::m_localMatrix0+1).
Last edited by JoeJ on Sat Jul 14, 2012 12:25 pm, edited 1 time in total.
User avatar
JoeJ
 
Posts: 1489
Joined: Tue Dec 21, 2010 6:18 pm

Re: Hinge Joint collision problem

Postby Neo » Sat Jul 14, 2012 12:18 pm

and the matirx:
Code: Select all
1.0000000     0.00000000     0.00000000  0.00000000
0.00000000 0.0099999998 0.00000000  0.00000000
0.00000000 0.00000000    1.0000000    0.00000000
0.00000000  -3.0000000    0.00000000 1.0000000
Neo
 
Posts: 127
Joined: Fri May 11, 2012 12:29 pm
Location: China,Sichuan

Re: Hinge Joint collision problem

Postby JoeJ » Sat Jul 14, 2012 12:26 pm

0.00000000 0.0099999998 0.00000000 0.00000000


There ist it: y axis is a vector with nearly zero length, bust be:
0 1 0 0


How do you produce that numbers?
User avatar
JoeJ
 
Posts: 1489
Joined: Tue Dec 21, 2010 6:18 pm

Re: Hinge Joint collision problem

Postby Neo » Sat Jul 14, 2012 12:33 pm

JoeJ wrote:
0.00000000 0.0099999998 0.00000000 0.00000000


There ist it: y axis is a vector with nearly zero length, bust be:
0 1 0 0


How do you produce that numbers?

This is because I have scaled the mesh by y axis. initialy irrlicht gave me a cube, but I want a thin plate-like stuff.
So I set the scale like(1,0,01f,1)
And this matrix is the outcome of the getRelativeTranform function.
Neo
 
Posts: 127
Joined: Fri May 11, 2012 12:29 pm
Location: China,Sichuan

Re: Hinge Joint collision problem

Postby Neo » Sat Jul 14, 2012 1:03 pm

JoeJ, I've made a joint with similiar complex constructure of my tank, then let the bullet shoot from left, but it turns out alright....
I'm totally confused... :?
It must be something wrong in building the newtonbody of the tank, or, is the material callback and hinge mortorized function affact the collsion?
Neo
 
Posts: 127
Joined: Fri May 11, 2012 12:29 pm
Location: China,Sichuan

Re: Hinge Joint collision problem

Postby Neo » Sat Jul 14, 2012 1:13 pm

@JoeJ,@Julio:
I got the problem!
All is this line:
NewtonBodySetContinuousCollisionMode(body_newt,1);
if I add this line, that problem occurs!!
And every thing goes back to normal when I comment this line.
Now all I want know is: Why?
Neo
 
Posts: 127
Joined: Fri May 11, 2012 12:29 pm
Location: China,Sichuan

Re: Hinge Joint collision problem

Postby Julio Jerez » Sat Jul 14, 2012 1:20 pm

this will be a problem yes NewtonBodySetContinuousCollisionMode yes, for nwo you need to use discrecte collision.

but this 0.0099 is also a bug.
Newton does not fixes matrices it only check then in debug mode, It is working because quaternion rotations are invariant respect to scale.
However when the body collide with some other body then the collision will be totally off.

If you are scale a mesh then you need to do the same to the collision.
There is code in the utility math library that can be use to extract the scale, and othornormal rotation of a matrix. you will need to use that when you set the matrix.

can you show me the part of the code where you do that?
Julio Jerez
Moderator
Moderator
 
Posts: 12426
Joined: Sun Sep 14, 2003 2:18 pm
Location: Los Angeles

Re: Hinge Joint collision problem

Postby JoeJ » Sat Jul 14, 2012 1:23 pm

Oh, missed some posts, again... I talk about the scaling here:

Ok, so that's the root of all of your problems.
Newton expects an orthonormalized orientation in the matrix.
That means, each axis must have a length of 1, at each angle is seperated by 90 degrees from each other axis.
That's not a newton limitation - it is standart. It represents an orientation / rotation and nothing else (like a quaternions too).
Try to avoid scaling in general - especially nonuniform scaling like you have here - there may come unexpected problems.
Imagine you have an arm parent body, and a hand child body.
Now you scale the arm to make it longer - then, if you rotate the hand, the hand will be longer too when it's aligned with the arm, but it will be not scald if it is oriented 90 degrees perpendicular to the arm.
The hand will change its length dependent on its orientation! Do we want that? no!
I saw exactly this happening in a program called adobe after effects and got a big smile on my face.
To handle such stuff properly you need to handle scale seperately, which can be a little tricky for a transformation hirarchy.

In your case, you need to create bodies with orthonormalized matrices generally.
You can use nonuniform scaling for all newton bodies on top af that. (I don't know the name of that function now)
User avatar
JoeJ
 
Posts: 1489
Joined: Tue Dec 21, 2010 6:18 pm

Re: Hinge Joint collision problem

Postby Neo » Sat Jul 14, 2012 1:35 pm

Julio Jerez wrote:this will be a problem yes NewtonBodySetContinuousCollisionMode yes, for nwo you need to use discrecte collision.

but this 0.0099 is also a bug.
Newton does not fixes matrices it only check then in debug mode, It is working because quaternion rotations are invariant respect to scale.
However when the body collide with some other body then the collision will be totally off.

If you are scale a mesh then you need to do the same to the collision.
There is code in the utility math library that can be use to extract the scale, and othornormal rotation of a matrix. you will need to use that when you set the matrix.

can you show me the part of the code where you do that?

irrlicht provide a set of matrix operations...and I have got used to convert matrix bitween newton and irrlicht...
class: matrix4
for example, an instance matrix4 mat;
extract scale: mat.getScale()
that would return a 3d vector,
and just by using mat.setScale(vector3d), the scale infomation could ve written into matrix.
As for othornormal rotation, I don't have a clear idea now, all I know is that I can use mat.setRotationDegrees(vector3d) or mat.setRotationRadius(vector3d)
to rotate the pin direction...
Neo
 
Posts: 127
Joined: Fri May 11, 2012 12:29 pm
Location: China,Sichuan

Re: Hinge Joint collision problem

Postby Neo » Sat Jul 14, 2012 1:47 pm

JoeJ wrote:In your case, you need to create bodies with orthonormalized matrices generally.
You can use nonuniform scaling for all newton bodies on top af that. (I don't know the name of that function now)

So you mean I have to use indentity matrix,or with maybe some rotation infomation in it to create Newton Body?
And just scale the collision object, right?
Neo
 
Posts: 127
Joined: Fri May 11, 2012 12:29 pm
Location: China,Sichuan

Re: Hinge Joint collision problem

Postby Julio Jerez » Sat Jul 14, 2012 2:06 pm

if you print the code fragment where you set the matrix and the collision, I can show you how to get the scale and apply the scale to the collision while teh body matrix remain orthonormal.

Then in in the trasnform callback all you need to do is to multi[ply the matrix by the scale of the collsion shape of the body. It is quite trivial.
Julio Jerez
Moderator
Moderator
 
Posts: 12426
Joined: Sun Sep 14, 2003 2:18 pm
Location: Los Angeles

Re: Hinge Joint collision problem

Postby JoeJ » Sat Jul 14, 2012 5:06 pm

Neo wrote:As for othornormal rotation, I don't have a clear idea now

I'll try to explain that a little, as it is one of the most important things you need to understand.
Let's begin with 2d, here a orientation matrix wood look like:

1,0 // X axis
0,1 // Y axis
graphically: |_ (y points up, x points right)
Both those vectors have length of one and are prependicular.
Also this is identity (no rotation)

Another orientation, rotated slightly counterclockwise could be:

0.8,0.6 // X axis now points right and slightly upwards
-0.6,0.8 // Y axis points slightly left and upwards
graphically like: \/
Note: Both axis have length 1: sqrt(0.8*0.8+0.6*0.6)==1, so they are normalized.
And they are perpenducular to each other == normal == 90 degrees
So this is rotated, not identity, but it is orthonormal.

You can build any valid 2d rotation matrix like:
cos(angle), sin(angle)
-sin(angle), cos(angle)


In 3d it's the same:
1,0,0 // x axis pointing right
0,1,0 // y pointing up
0,0,1 // z pointing out of the screen
this is identity.

Now we want some rotation around the z axis (so the z axis stays untouched, as anything rotates around it):
0.8, 0.6, 0
-0.6, 0.8, 0
0, 0, 1

Now we want some rotation around the y axis:
0.8, 0, 0.6
0, 1, 0
-0.6, 0, 0.8

It get's harder to imagine how that would look like and is really boring (and useless too),
but i hope you get the point: The topleft 3x3 values af a 3D orthonormalized Transformation matrix are 3 axis vectors.
They are unit length and normal to each other - if you get that you really understood what those matrices are (for our use case).
Note that this holds for both if you treat the axis vectors as rows OR columns of the matrix.


Now, let's add some evil scaling (2d again):
1,0
0,1
scaled uniformily by 10 becomes
10,0 // simply larger axis
0,10
and if we want a nonuniform scale, say x axis stretched by 10 we get
10,0
0,1
and if we'd want to rotate that again it should get:
8.0, 6.0 // long X axis scaled by 10 pointing right and upwards
-0.6, 0.8 // Y axis stays unit length

This is exactly what you have and is not good.
We want to seperate the scale from the orientation, first isolate scale:
xScale = length(8,6) = 10 // how long is x axis?
yScale = length(-0.6,0.8) = 1 // how long y?

now, divide both axis by their lengths to normalize them:
0.8,0.6
-0.6,0.8
Now you have the orthonormal orientation you want to create the body, and you also have the scale you need to bring it back to your wanted shape.



I'll leave the 3d case as an exercise to you, but don't worry - this (and little more) is what julio will give you after you posted your code.
But read this and try to imagine until you understand - this is bread and butter of 3d programming, and you should get able to help yourself in such cases.
Note that we did not cover any calculations with matrices (famous matrix multiplication f.ex.), so a big part of the picture is missing to give it real sense.
However, it should be clear now, why we use those 9 numbers to represent 3D orientation.
User avatar
JoeJ
 
Posts: 1489
Joined: Tue Dec 21, 2010 6:18 pm

Re: Hinge Joint collision problem

Postby Neo » Sun Jul 15, 2012 1:32 am

Julio Jerez wrote:if you print the code fragment where you set the matrix and the collision, I can show you how to get the scale and apply the scale to the collision while teh body matrix remain orthonormal.

Then in in the trasnform callback all you need to do is to multi[ply the matrix by the scale of the collsion shape of the body. It is quite trivial.

Okey, I'll print that test box's code here:
Code: Select all
        IMeshSceneNode *floor=smgr->addCubeSceneNode(500);
   //
         add texture here
        //
        floor->setScale(vector3df(1,0.01f,1));//scale the y aixs,because I want a plate, not a cube box
        floor->setPosition(vector3df(0,-30,0));
   aabbox3df fbox=floor->getTransformedBoundingBox();
   vector3df sz=fbox.getExtent();
   matrix4 mt=floor->getRelativeTransformation();
   NewtonCollision*coll=NewtonCreateBox(nWorld,sz.X,sz.Y,sz.Z,shapeID++,NULL);
   NewtonBody* floorBd=NewtonCreateBody(nWorld,coll,&mt.pointer()[0]);

   NewtonBodySetTransformCallback(floorBd,transformCallback);
   NewtonBodySetUserData(floorBd,static_cast<void*>(floor));
Neo
 
Posts: 127
Joined: Fri May 11, 2012 12:29 pm
Location: China,Sichuan

PreviousNext

Return to General Discussion

Who is online

Users browsing this forum: No registered users and 1 guest