Any known cylinder contact or friction issues?

A place to discuss everything related to Newton Dynamics.

Moderators: Sascha Willems, walaber

Any known cylinder contact or friction issues?

Postby Cannos » Fri Mar 12, 2010 10:16 pm

I didn't see anything related in the bugs forum, so I thought I'd ask here. Are there any known issues with the contact forces generated for the flat part of cylinders and chamfer cylinders sliding across flat ground? I am seeing an issue where applying only a forward and gravity force on a cylinder it will slide across the ground, but randomly jitter or hitch. It appears that it is colliding with something, or generating extra friction. It isn't generating any extra torque, just the velocity drops suddenly.

Doing the exact same test with a box or sphere is fine, they slide perfectly smoothly, that's why I'm asking about the cylinder shapes specifically.

If this is not a known issue and you don't have any ideas on what may be causing this, I'll see if I can put together a sample to share. Thanks for the help!
Cannos
 
Posts: 129
Joined: Thu Mar 04, 2010 5:41 pm

Re: Any known cylinder contact or friction issues?

Postby Dave Gravel » Fri Mar 12, 2010 11:40 pm

Maybe a little video showing the bug in action can help to see and understand.
You search a nice physics solution, if you can read this message you're at the good place :wink:
OrionX3D Projects & Demos:
https://orionx3d.sytes.net
https://www.facebook.com/dave.gravel1
https://www.youtube.com/user/EvadLevarg/videos
User avatar
Dave Gravel
 
Posts: 801
Joined: Sat Apr 01, 2006 9:31 pm
Location: Quebec in Canada.

Re: Any known cylinder contact or friction issues?

Postby Cannos » Mon Mar 15, 2010 2:45 am

Here's a video, you can see the hitch that occurs at about 4 seconds in: http://www.youtube.com/watch?v=jGSC9gJT640. Just to be clear, this isn't a framerate or update time hitch.

I've found out a little more info too. It seems that this only happens when continuous collision is enabled. And again, I'm not seeing this with a box shape, just the cylinder shapes. I've started looking at all the contact information I can get to, but I haven't figured out the cause yet. With continuous collision I am seeing an occasional contact with a higher "normal speed" than the ones without continuous collision. But I don't know why this would produce a force along the tangent.

Any ideas on the cause of this problem, or any tips on what I can look at for debugging? I might be able to get away without continuous collision on the ground, but I'd like to keep it on and figure out if this is a bug or something I can work around by disabling / modifying some contact properties. Thanks.
Cannos
 
Posts: 129
Joined: Thu Mar 04, 2010 5:41 pm

Re: Any known cylinder contact or friction issues?

Postby Cannos » Mon Mar 15, 2010 4:35 pm

I thought it might help to add a demo here to try out. Here's a modified BasicFriction.cpp you can drop in to see a similar problem:

Code: Select all
/* Copyright (c) <2009> <Newton Game Dynamics>
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely
*/

#include <toolbox_stdafx.h>
#include "SkyBox.h"
#include "RenderPrimitive.h"
#include "../OGLMesh.h"
#include "../SceneManager.h"
#include "../PhysicsUtils.h"
#include "../toolBox/MousePick.h"
#include "../toolBox/OpenGlUtil.h"
#include "../toolBox/DebugDisplay.h"

NewtonBody* pCylinderBody = NULL;
dVector prevPos(0.0f, 0.0f, 0.0f);
float speed = 0.0f;

// Cannos - custom control callback to override the camera position to follow the cylinder
void CustomFrictionDemoKeyboard(SceneManager& me)
{
    // Get cylinder position to position camera and output speed
    if (pCylinderBody)
    {
        dMatrix mtx;
        NewtonBodyGetMatrix(pCylinderBody, &mtx[0][0]);

        // Follow the cylinder
        const float angle = 20.0f * 3.1415926f / 180.0f;
        dVector dir(cosf(angle), -sinf(angle), 0.0f);
        const float dist = 10.0f;
        dVector origin(mtx.m_posit - dir.Scale(dist));
        InitEyePoint(dir, origin);

        // Output the current speed for debugging
        printf("Speed = %f\n", speed);
    }

    Keyboard(me);
}

void applyForcesCB(const NewtonBody* body, float timestep, int threadIndex)
{
    dFloat Ixx;
    dFloat Iyy;
    dFloat Izz;
    dFloat mass;

    // Update speed variable for debug output
    dMatrix mtx;
    NewtonBodyGetMatrix(body, &mtx[0][0]);
    dVector posDiff = mtx.m_posit - prevPos;
    speed = sqrtf(posDiff % posDiff) / timestep;
    prevPos = mtx.m_posit;

    // Set constant velocity
    dVector vel(15.0, 0.0f, 0.0f);
    NewtonBodySetVelocity(body, &vel.m_x);

    // Add gravity force (yes, I know that the above SetVelocity call zeroes out gravitational acceleration)
    NewtonBodyGetMassMatrix (body, &mass, &Ixx, &Iyy, &Izz);
    dVector force (0.0f, -mass * 10.0f, 0.0f);
    NewtonBodySetForce (body, &force.m_x);
}


static void SetDemoCallbacks (SceneManager& system)
{
   system.m_control = CustomFrictionDemoKeyboard;
   system.m_autoSleep = AutoSleep;
   system.m_showIslands = SetShowIslands;
   system.m_showContacts = SetShowContacts;
   system.m_setMeshCollision = SetShowMeshCollision;
//   system.m_scene = scene;
}


static void BuildFloorAndSceneRoot (SceneManager& system)
{
   NewtonWorld* world;
   RenderPrimitive* floor;
   NewtonBody* floorBody;
   NewtonCollision* floorCollision;
   OGLMesh* meshInstance;
//   dSceneNode* scene;

   world = system.m_world;

   // /////////////////////////////////////////////////////////////////////
   //
   // create the sky box,
   system.AddModel (new SkyBox ());


   // create the the floor graphic objects
   dVector floorSize (600.0f, 2.0f, 600.0f);
   dMatrix location (GetIdentityMatrix());
   location.m_posit.m_y = 5.0f;

   // create a box for floor
   floorCollision = NewtonCreateBox (world, floorSize.m_x, floorSize.m_y, floorSize.m_z, 0, NULL);

   //   meshInstance = OGLMesh::MakeBox (world, size.m_x, size.m_y, size.m_z, "GrassAndDirt.tga");
   meshInstance = new OGLMesh (floorCollision, "GrassAndDirt.tga", "GrassAndDirt.tga", "GrassAndDirt.tga");
   floor = new RenderPrimitive (location, meshInstance);
   system.AddModel (floor);
   meshInstance->Release();

   // create the the floor collision, and body with default values
   floorBody = NewtonCreateBody (world, floorCollision);
   NewtonReleaseCollision (world, floorCollision);


   // set the transformation for this rigid body
   NewtonBodySetMatrix (floorBody, &location[0][0]);

   // save the pointer to the graphic object with the body.
   NewtonBodySetUserData (floorBody, floor);

   // set a destructor for this rigid body
   NewtonBodySetDestructorCallback (floorBody, PhysicsBodyDestructor);


   // get the default material ID
   int defaultID;
   defaultID = NewtonMaterialGetDefaultGroupID (world);

   // set default material properties
   //NewtonMaterialSetDefaultSoftness (world, defaultID, defaultID, 0.05f);
   //NewtonMaterialSetDefaultElasticity (world, defaultID, defaultID, 0.4f);
   //NewtonMaterialSetDefaultCollidable (world, defaultID, defaultID, 1);
   //NewtonMaterialSetDefaultFriction (world, defaultID, defaultID, 1.0f, 0.5f);
   //NewtonMaterialSetCollisionCallback (world, defaultID, defaultID, NULL, NULL, GenericContactProcess);

//   NewtonMaterialSetSurfaceThickness(world, materialID, materialID, 0.1f);
   //NewtonMaterialSetSurfaceThickness(world, defaultID, defaultID, 0.0f);

   // set the island update callback
   NewtonSetIslandUpdateEvent (world, PhysicsIslandUpdate);

   // save the callback
   SetDemoCallbacks (system);

    // Set world size
    dVector worldMin(-300.0f, -10.0f, -300.0f);
    dVector worldMax(300.0f, 100.0f, 300.0f);
    NewtonSetWorldSize(world, &worldMin[0], &worldMax[0]);

   InitEyePoint (dVector (1.0f, 0.0f, 0.0f), dVector (-40.0f, 10.0f, 0.0f));
}

void Friction (SceneManager& system)
{
   int defaultMaterialID;
   NewtonWorld* world;
   NewtonBody* body;

   world = system.m_world;

   // create the sky box and the floor,
   BuildFloorAndSceneRoot (system);

   defaultMaterialID = NewtonMaterialGetDefaultGroupID (system.m_world);

    // Create cylinder to slide across floor
   dVector cylSize (0.5f, 0.1f, 0.0f, 0.0f);
    float angle = 0.0f;
    dVector front(sinf(angle), cosf(angle), 0.0f);
    dVector right(0.0f, 0.0f, 1.0f);
    dVector up = front * right;
    dMatrix cylMtx(front, up, right, dVector(-250.0f, 6.1f, 0.0f));
    body = CreateGenericSolid(system.m_world, &system, 1.0f, cylMtx, cylSize, _CHAMFER_CYLINDER_PRIMITIVE, defaultMaterialID);

    // Set force callback
    NewtonBodySetForceAndTorqueCallback(body, applyForcesCB);

    // Turn on continuous collision mode
    NewtonBodySetContinuousCollisionMode(body, 1);

    // Save off pointer for later use
    pCylinderBody = body;

   InitEyePoint (dVector (1.0f, 0.0f, 0.0f), dVector (-70.0f, 10.0f, 0.0f));   
}


This isn't the exact same problem or conditions that I was seeing in the video posted earlier, but I think they are similar or related. In this example I am applying a constant velocity of (15, 0, 0) to the cylinder plus gravity (the gravity isn't accumulated since I'm using SetVelocity, but that shouldn't matter for the purpose of this demo). I output the current speed to the debug console window. With the above code you'll see that it only travels at about 5.6 units/second instead of the specified 15. If I turn off continuous collision mode, the cylinder will slide very close to 15 units/seconds (minus some friction) as expected.

Let me know if this helps narrow down the problem. The only other weirdness I'm seeing is that in my earlier demo it isn't constantly slowed down with continuous mode on, it only slows down / hitches occassionally as seen in the video. But again, I think these are related problems. Thanks for the help.
Cannos
 
Posts: 129
Joined: Thu Mar 04, 2010 5:41 pm

Re: Any known cylinder contact or friction issues?

Postby Cannos » Thu Mar 18, 2010 5:11 pm

Just checking again if anyone has any information on this continuous collision issue. In the meantime I have disabled continuous collision on the ground to work around the issue. Not really the longterm solution I'm looking for, but it has to do for now.
Cannos
 
Posts: 129
Joined: Thu Mar 04, 2010 5:41 pm

Re: Any known cylinder contact or friction issues?

Postby Julio Jerez » Thu Jun 10, 2010 3:45 pm

you say that that demo reproduce the bug you see in the video?
This could be part of an edeg bug I am lokking for a long time, but hart to reproduce.

can you explain me what the demo you posted do?
Julio Jerez
Moderator
Moderator
 
Posts: 12426
Joined: Sun Sep 14, 2003 2:18 pm
Location: Los Angeles

Re: Any known cylinder contact or friction issues?

Postby Cannos » Thu Jun 10, 2010 6:26 pm

Both in the video and in the demo I am applying a constant velocity to a body so that it slides along the ground. In the video it will slide at the correct velocity most of the time but occasionally it looks like it gets a bad contact so that it slows to a stop before sliding again.

In the demo is does something slightly different. It looks like it has a constant drag to it when continuous collision is turned on. Instead of sliding at a speed of 15, it slides at 5.6 instead. When turning off continuous collision, it will correctly slide at 15. The speed is output in the console window.

If you need more detail or need me to rework the demo in any way, let me know.
Cannos
 
Posts: 129
Joined: Thu Mar 04, 2010 5:41 pm

Re: Any known cylinder contact or friction issues?

Postby Julio Jerez » Thu Jun 10, 2010 6:38 pm

That sounds very bad, and we cannot have that, can we?

I will check it out.
Thank you.
Julio Jerez
Moderator
Moderator
 
Posts: 12426
Joined: Sun Sep 14, 2003 2:18 pm
Location: Los Angeles

Re: Any known cylinder contact or friction issues?

Postby Cannos » Thu Jun 10, 2010 6:44 pm

:)

Note that this demo was made with version 2.18 of Newton I think. I can remake it with the latest version if you need. It is just a simple modification of the existing BasicFriction.cpp from sdkDemos.
Cannos
 
Posts: 129
Joined: Thu Mar 04, 2010 5:41 pm

Re: Any known cylinder contact or friction issues?

Postby Julio Jerez » Thu Jun 10, 2010 6:48 pm

Oh do that please. I made some updates to CC in 2.22.
Download sdk 2.22 and see if the demo still behaves as bad as in 2.18.
Julio Jerez
Moderator
Moderator
 
Posts: 12426
Joined: Sun Sep 14, 2003 2:18 pm
Location: Los Angeles

Re: Any known cylinder contact or friction issues?

Postby Cannos » Thu Jun 10, 2010 6:52 pm

I will do that right now and report back soon.
Cannos
 
Posts: 129
Joined: Thu Mar 04, 2010 5:41 pm

Re: Any known cylinder contact or friction issues?

Postby Cannos » Thu Jun 10, 2010 7:44 pm

Yes, the problem is still there in 2.22. Here is the updated demo code, replace BasicFriction.cpp with this one. All the changes I have made to the demo are in the CONTINUOUS_SLIDE_TEST ifdef.

Code: Select all
/* Copyright (c) <2009> <Newton Game Dynamics>
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely
*/

#include <toolbox_stdafx.h>
#include "SkyBox.h"
#include "RenderPrimitive.h"
#include "../OGLMesh.h"
#include "../MainFrame.h"
#include "../SceneManager.h"
#include "../PhysicsUtils.h"
#include "../toolBox/MousePick.h"
#include "../toolBox/OpenGlUtil.h"
#include "../toolBox/DebugDisplay.h"

#define CONTINUOUS_SLIDE_TEST 1
#ifdef CONTINUOUS_SLIDE_TEST

NewtonBody* pCylinderBody = NULL;
dVector prevPos(-60.0f, 6.1f, 0.0f);
float speed = 0.0f;

// Cannos - custom control callback to override the camera position to follow the cylinder
void CustomFrictionDemoKeyboard(SceneManager& me)
{
    // Get cylinder position to position camera and output speed
    if (pCylinderBody)
    {
        dMatrix mtx;
        NewtonBodyGetMatrix(pCylinderBody, &mtx[0][0]);

        // Follow the cylinder
        const float angle = 20.0f * 3.1415926f / 180.0f;
        dVector dir(cosf(angle), -sinf(angle), 0.0f);
        const float dist = 10.0f;
        dVector origin(mtx.m_posit - dir.Scale(dist));
        InitEyePoint(dir, origin);

        // Output the current speed for debugging
        //printf("Speed = %f\n", speed);
    }

    Keyboard(me);
}

void applyForcesCB(const NewtonBody* body, float timestep, int threadIndex)
{
    dFloat Ixx;
    dFloat Iyy;
    dFloat Izz;
    dFloat mass;

    // Update speed variable for debug output
    dMatrix mtx;
    NewtonBodyGetMatrix(body, &mtx[0][0]);
    dVector posDiff = mtx.m_posit - prevPos;
    speed = sqrtf(posDiff % posDiff) / timestep;
    prevPos = mtx.m_posit;
    char str[256];
    sprintf(str, "Speed = %f\n", speed);
    OutputDebugString(str);

    // Set constant velocity
    dVector vel(15.0, 0.0f, 0.0f);
    NewtonBodySetVelocity(body, &vel.m_x);

    // Add gravity force (yes, I know that the above SetVelocity call zeroes out gravitational acceleration)
    NewtonBodyGetMassMatrix (body, &mass, &Ixx, &Iyy, &Izz);
    dVector force (0.0f, -mass * 10.0f, 0.0f);
    NewtonBodySetForce (body, &force.m_x);
}

#endif

static void UserContactFriction (const NewtonJoint* contactJoint, dFloat timestep, int threadIndex)
{
   dFloat Ixx;
   dFloat Iyy;
   dFloat Izz;
   dFloat mass;
   dFloat friction;
   const NewtonBody* body;
   const NewtonBody* body0;
   const NewtonBody* body1;

   // call  the basic call back
   GenericContactProcess (contactJoint, timestep, threadIndex);

   body0 = NewtonJointGetBody0(contactJoint);
   body1 = NewtonJointGetBody1(contactJoint);

   body = body0;
   NewtonBodyGetMassMatrix (body, &mass, &Ixx, &Iyy, &Izz);
   if (mass == 0.0f) {
      body = body1;
   }

   for (void* contact = NewtonContactJointGetFirstContact (contactJoint); contact; contact = NewtonContactJointGetNextContact (contactJoint, contact)) {
      RenderPrimitive* node;
      NewtonMaterial* material;

      material = NewtonContactGetMaterial (contact);
      node = (RenderPrimitive*) NewtonBodyGetUserData (body);
      
      friction = node->m_density;
      NewtonMaterialSetContactFrictionCoef (material, friction + 0.1f, friction, 0);
      NewtonMaterialSetContactFrictionCoef (material, friction + 0.1f, friction, 1);
   }
}

static void SetDemoCallbacks (NewtonFrame& system)
{
#ifdef CONTINUOUS_SLIDE_TEST
    system.m_control = CustomFrictionDemoKeyboard;
#else
   system.m_control = Keyboard;
#endif
   system.m_autoSleep = AutoSleep;
   system.m_showIslands = SetShowIslands;
   system.m_showContacts = SetShowContacts;
   system.m_setMeshCollision = SetShowMeshCollision;
//   system.m_scene = scene;
}


static void BuildFloorAndSceneRoot (NewtonFrame& system)
{
   NewtonWorld* world;
   RenderPrimitive* floor;
   NewtonBody* floorBody;
   NewtonCollision* floorCollision;
   OGLMesh* meshInstance;
//   dSceneNode* scene;

   world = system.m_world;

   // /////////////////////////////////////////////////////////////////////
   //
   // create the sky box,
   OGLModel* sky = new SkyBox ();
   system.AddModel___ (sky);
   sky->Release();



   // create the the floor graphic objects
#ifdef CONTINUOUS_SLIDE_TEST
   dVector floorSize (600.0f, 2.0f, 600.0f);
   dMatrix location (GetIdentityMatrix());
   location.m_posit.m_y = 5.0f;
#else
   dVector floorSize (100.0f, 2.0f, 100.0f);
   dMatrix location (GetIdentityMatrix());
   location.m_posit.m_y = -5.0f;
#endif

   // create a box for floor
   floorCollision = NewtonCreateBox (world, floorSize.m_x, floorSize.m_y, floorSize.m_z, 0, NULL);

   meshInstance = new OGLMesh ("ground", floorCollision, "GrassAndDirt.tga", "metal_30.tga", "metal_30.tga");
   floor = new RenderPrimitive (location, meshInstance);
   system.AddModel___ (floor);
   floor->Release();
   meshInstance->Release();

   // create the the floor collision, and body with default values
   floorBody = NewtonCreateBody (world, floorCollision);
   NewtonReleaseCollision (world, floorCollision);


   // set the transformation for this rigid body
   NewtonBodySetMatrix (floorBody, &location[0][0]);

   // save the pointer to the graphic object with the body.
   NewtonBodySetUserData (floorBody, floor);

   // set a destructor for this rigid body
   NewtonBodySetDestructorCallback (floorBody, PhysicsBodyDestructor);


   // get the default material ID
   int defaultID;
   defaultID = NewtonMaterialGetDefaultGroupID (world);

   // set default material properties
   NewtonMaterialSetDefaultSoftness (world, defaultID, defaultID, 0.05f);
   NewtonMaterialSetDefaultElasticity (world, defaultID, defaultID, 0.4f);
   NewtonMaterialSetDefaultCollidable (world, defaultID, defaultID, 1);
   NewtonMaterialSetDefaultFriction (world, defaultID, defaultID, 1.0f, 0.5f);
   NewtonMaterialSetCollisionCallback (world, defaultID, defaultID, NULL, NULL, GenericContactProcess);

//   NewtonMaterialSetSurfaceThickness(world, materialID, materialID, 0.1f);
   NewtonMaterialSetSurfaceThickness(world, defaultID, defaultID, 0.0f);

   // set the island update callback
   NewtonSetIslandUpdateEvent (world, PhysicsIslandUpdate);

   // save the callback
   SetDemoCallbacks (system);

    // Set world size
#ifdef CONTINUOUS_SLIDE_TEST
    dVector worldMin(-300.0f, -10.0f, -300.0f);
    dVector worldMax(300.0f, 100.0f, 300.0f);
    NewtonSetWorldSize(world, &worldMin[0], &worldMax[0]);
#endif

   InitEyePoint (dVector (1.0f, 0.0f, 0.0f), dVector (-40.0f, 10.0f, 0.0f));
}


void Friction (NewtonFrame& system)
{
   int zCount;
   int defaultMaterialID;
   dFloat spacing;
   NewtonWorld* world;
   NewtonBody* body;

   world = system.m_world;

   // create the sky box and the floor,
   BuildFloorAndSceneRoot (system);

   defaultMaterialID = NewtonMaterialGetDefaultGroupID (system.m_world);

#ifdef CONTINUOUS_SLIDE_TEST
    // Create cylinder to slide across floor
   dVector cylSize (0.5f, 0.1f, 0.0f, 0.0f);
    float angle = 0.0f;
    dVector front(sinf(angle), cosf(angle), 0.0f);
    dVector right(0.0f, 0.0f, 1.0f);
    dVector up = front * right;
    dMatrix cylMtx(front, up, right, prevPos);
    body = CreateGenericSolid(system.m_world, &system, "cyl", 1.0f, cylMtx, cylSize, _CHAMFER_CYLINDER_PRIMITIVE, defaultMaterialID);

    // Set force callback
    NewtonBodySetForceAndTorqueCallback(body, applyForcesCB);

    // Turn on continuous collision mode
    NewtonBodySetContinuousCollisionMode(body, 1);

    // Save off pointer for later use
    pCylinderBody = body;

#else
   NewtonMaterialSetCollisionCallback (world, defaultMaterialID, defaultMaterialID, NULL, NULL, UserContactFriction);

   // create a friction Ramp
   dVector location (cameraEyepoint + cameraDir.Scale (40.0f));
   dMatrix matrix (dPitchMatrix (20.0f * 3.141592f / 180.0f));
   matrix.m_posit = location;
   matrix.m_posit.m_x -= 5.0f;
   matrix.m_posit.m_y -= 8.0f;
   matrix.m_posit.m_z -= 20.0f;
   dVector size (40.0f, 0.2f, 40.0f, 0.0f);
   NewtonCollision* rampCollision = CreateConvexCollision (system.m_world, GetIdentityMatrix(), size, _BOX_PRIMITIVE, defaultMaterialID);
   OGLMesh* rampMesh = new OGLMesh ("incline", rampCollision, "wood_0.tga", "wood_0.tga", "wood_1.tga");
   body = CreateSimpleSolid (system.m_world, &system, rampMesh, 0, matrix, rampCollision, defaultMaterialID);
   rampMesh->Release();
   NewtonReleaseCollision(system.m_world, rampCollision);

   // create some boxes too
   dVector boxSize (1.0f, 0.5f, 2.0f, 0.0f);
   NewtonCollision* boxCollision = CreateConvexCollision (system.m_world, GetIdentityMatrix(), boxSize, _BOX_PRIMITIVE, defaultMaterialID);
   OGLMesh* boxMesh = new OGLMesh ("box", boxCollision, "wood_0.tga", "wood_0.tga", "wood_1.tga");

   zCount = 10;
   spacing = 2.0f;
   dVector origin (matrix.m_posit);
   origin.m_z -= 10.0f;

   // create
   for (int i = 0; i < zCount; i ++) {
      dFloat z;
      dFloat x;
      dFloat mass;

      z = origin.m_z;
      x = origin.m_x + (i - zCount / 2) * spacing;

      mass = 1.0f;
      matrix.m_posit.m_x = x;
      matrix.m_posit.m_y = FindFloor (system.m_world, x, z) + size.m_y * 0.5f;
      matrix.m_posit.m_z = z;
      
      body = CreateSimpleSolid (system.m_world, &system, boxMesh, mass, matrix, boxCollision, defaultMaterialID);

      // save a coefficient of friction in the the primitive
      RenderPrimitive* node;
      node = (RenderPrimitive*) NewtonBodyGetUserData (body);
      node->m_density = i * 0.03f;
   }

   // release the used collisions
   boxMesh->Release();
   NewtonReleaseCollision(system.m_world, boxCollision);
#endif

   InitEyePoint (dVector (1.0f, 0.0f, 0.0f), dVector (-70.0f, 10.0f, 0.0f));   
}


If you watch the debug output or look at the cylinder speed you will see that after it makes contact with the ground (about 20 updates in), it will start sliding at a speed of 5.65 instead of approximately 15. If you turn off continuous collision, it will slide at around 15 as expected.
Cannos
 
Posts: 129
Joined: Thu Mar 04, 2010 5:41 pm

Re: Any known cylinder contact or friction issues?

Postby Julio Jerez » Fri Jun 11, 2010 12:38 am

Ok I just test your demo and there are few problem, some in my side but some in your size.
Let us first go with the one in your side.

1-you have a wrong matrix, you cannot make non orthonormal matrix
This code make a matrix with a negative determinant, that completely wack out the engine
Code: Select all
    dVector front(sinf(angle), cosf(angle), 0.0f);
    dVector right(0.0f, 0.0f, 1.0f);
    dVector up = front * right;

I changed to this,
Code: Select all
    dVector front(sinf(angle), cosf(angle), 0.0f);
    dVector right(0.0f, 0.0f, 1.0f);
//  dVector up = front * right;
    dVector up = right * front;

in case you are wondering how to know if the rotation part is right or wrong, a matrix is right if the deternimat is positive 1.0
that is: dotproduct (cross product (right, up), right) = 1.0

2-if you are going to place a body to scrapl overthe ground you cannot really measure the velocity by substrating the current position from the previus position and divide that by the timestep.
If you remember from phsyics 101 in college, there is a difference between instanataneus velocity and average velocity. You are measuring the average velocity. Not the instantaneus velocity.

Consider a body bouncing on a floor with in a perfect elastic collision.
If that happens, the position before and after the collision are identical, if you use your method, the velocity will be zero. However in both positions the velocity is very different than zero.
Similarlly if you have a body scraping along the ground with a non zero friction coeficient, then the friction will reduced the speed at each step.
So what you are getting is the body with high speed but the velocity is reduced at the end of each frame,
You will need to set the static and kinetic friction to zero to make it a frictionless test.

3- and this is an engine limitation. Whe you make the collsion shape, you are making a cylinder with thickness 0.1 unit in length.
That means that the maximun distance the body can move conservativatly is 0.05 of a unit.
With that data, when Newton predict how much a body can move before it hits a contact, the allowed time is very, very small.
this is because the body in too thin, it is in contact with the ground, and it is traveling very fast (14 meters per secund is abput 55 kilometer per hour),
the velocity in horizontal therfore the body does not bounce from the floor but the grapvity keeps polling it down,
all this factor combined makes that the next prediction the same thing happens.
The engine keeps doing predictions until is use all teh time step, but for practical reasons the engine only do that up to 8 times.
After that is bailout and this is why you see that it does not move as it should.

You can fix that by making the collision shape a litle thicker, I did that by making it twice as sick. change thsi line.
dVector cylSize (0.5f, 0.1f, 0.0f, 0.0f);

to this
dVector cylSize (0.5f, 0.2f, 0.0f, 0.0f);

those are the compromise we most make in order to make a real time engine.
Leaving the prediction runs until it completel resolve the collision, bogs down the performance to almost zero fps.
Julio Jerez
Moderator
Moderator
 
Posts: 12426
Joined: Sun Sep 14, 2003 2:18 pm
Location: Los Angeles

Re: Any known cylinder contact or friction issues?

Postby Cannos » Fri Jun 11, 2010 1:48 am

Thanks for looking at this, I was afraid I might be running into size or speed limitations. Regarding your other notes:

1) This was a dumb typo reversing the cross product inputs. I must have been thinking left handed for a brief moment. Thanks for pointing it out.
2) I was intentionally measuring average speed here. I didn't need the object to slide at 15 exactly, I only wanted to demonstrate the difference in engine output with continuous collision on and off.

I assume decreasing the fixed step update time will also help with these limitations. I don't plan on doing this as Increasing the size or decreasing the speed are much better, but just curious.

Thanks again for checking this out.
Cannos
 
Posts: 129
Joined: Thu Mar 04, 2010 5:41 pm


Return to General Discussion

Who is online

Users browsing this forum: No registered users and 2 guests

cron