Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
erincatto committed Oct 13, 2024
1 parent 6417f21 commit dff4193
Show file tree
Hide file tree
Showing 9 changed files with 212 additions and 45 deletions.
15 changes: 15 additions & 0 deletions include/box2d/box2d.h
Original file line number Diff line number Diff line change
Expand Up @@ -858,6 +858,21 @@ B2_API float b2MouseJoint_GetMaxForce( b2JointId jointId );

/**@}*/

/**
* @defgroup null_joint Null Joint
* @brief Functions for the null joint.
*
* The null joint is used to disable collision between two bodies. As a side effect of being a joint, it also
* keeps the two bodies in the same simulation island.
* @{
*/

/// Create a null joint.
/// @see b2NullJointDef for details
B2_API b2JointId b2CreateNullJoint( b2WorldId worldId, const b2NullJointDef* def );

/**@}*/

/**
* @defgroup prismatic_joint Prismatic Joint
* @brief A prismatic joint allows for translation along a single axis with no rotation.
Expand Down
24 changes: 24 additions & 0 deletions include/box2d/types.h
Original file line number Diff line number Diff line change
Expand Up @@ -132,6 +132,7 @@ typedef struct b2WorldDef
/// User context that is provided to enqueueTask and finishTask
void* userTaskContext;

/// User data
/// Used internally to detect a valid definition. DO NOT SET.
int32_t internalValue;
} b2WorldDef;
Expand Down Expand Up @@ -480,6 +481,7 @@ typedef enum b2JointType
b2_distanceJoint,
b2_motorJoint,
b2_mouseJoint,
b2_nullJoint,
b2_prismaticJoint,
b2_revoluteJoint,
b2_weldJoint,
Expand Down Expand Up @@ -632,6 +634,28 @@ typedef struct b2MouseJointDef
/// @ingroup mouse_joint
B2_API b2MouseJointDef b2DefaultMouseJointDef( void );

/// A null joint is used to disable collision between two specific bodies.
///
/// @ingroup null_joint
typedef struct b2NullJointDef
{
/// The first attached body.
b2BodyId bodyIdA;

/// The second attached body.
b2BodyId bodyIdB;

/// User data pointer
void* userData;

/// Used internally to detect a valid definition. DO NOT SET.
int32_t internalValue;
} b2NullJointDef;

/// Use this to initialize your joint definition
/// @ingroup null_joint
B2_API b2NullJointDef b2DefaultNullJointDef( void );

/// Prismatic joint definition
///
/// This requires defining a line of motion using an axis and an anchor point.
Expand Down
55 changes: 38 additions & 17 deletions samples/human.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -37,11 +37,16 @@ void Human::Spawn( b2WorldId worldId, b2Vec2 position, float scale, float fricti
b2ShapeDef shapeDef = b2DefaultShapeDef();
shapeDef.friction = 0.2f;
shapeDef.filter.groupIndex = -groupIndex;
shapeDef.filter.maskBits = 1;
shapeDef.filter.categoryBits = 2;
shapeDef.filter.maskBits = (1 | 2);

b2ShapeDef footShapeDef = shapeDef;
footShapeDef.friction = 0.05f;

// feet don't collide with ragdolls
footShapeDef.filter.categoryBits = 2;
footShapeDef.filter.maskBits = 1;

if ( colorize )
{
footShapeDef.customColor = b2_colorSaddleBrown;
Expand Down Expand Up @@ -85,7 +90,7 @@ void Human::Spawn( b2WorldId worldId, b2Vec2 position, float scale, float fricti

bodyDef.position = b2Add( { 0.0f, 1.2f * s }, position );
bodyDef.linearDamping = 0.0f;
// bodyDef.type = b2_staticBody;
//bodyDef.type = b2_staticBody;
bone->bodyId = b2CreateBody( worldId, &bodyDef );
bone->frictionScale = 0.5f;
bodyDef.type = b2_dynamicBody;
Expand Down Expand Up @@ -122,7 +127,7 @@ void Human::Spawn( b2WorldId worldId, b2Vec2 position, float scale, float fricti
Bone* bone = m_bones + Bone::e_head;
bone->parentIndex = Bone::e_torso;

bodyDef.position = b2Add( { 0.0f * s, 1.5f * s }, position );
bodyDef.position = b2Add( { 0.0f * s, 1.475f * s }, position );
bodyDef.linearDamping = 0.1f;

bone->bodyId = b2CreateBody( worldId, &bodyDef );
Expand All @@ -133,12 +138,12 @@ void Human::Spawn( b2WorldId worldId, b2Vec2 position, float scale, float fricti
shapeDef.customColor = skinColor;
}

b2Capsule capsule = { { 0.0f, -0.0325f * s }, { 0.0f, 0.0325f * s }, 0.08f * s };
b2Capsule capsule = { { 0.0f, -0.038f * s }, { 0.0f, 0.039f * s }, 0.075f * s };
b2CreateCapsuleShape( bone->bodyId, &shapeDef, &capsule );

// neck
capsule = { { 0.0f, -0.12f * s }, { 0.0f, -0.08f * s }, 0.05f * s };
b2CreateCapsuleShape( bone->bodyId, &shapeDef, &capsule );
//// neck
// capsule = { { 0.0f, -0.12f * s }, { 0.0f, -0.08f * s }, 0.05f * s };
// b2CreateCapsuleShape( bone->bodyId, &shapeDef, &capsule );

b2Vec2 pivot = b2Add( { 0.0f, 1.4f * s }, position );
b2RevoluteJointDef jointDef = b2DefaultRevoluteJointDef();
Expand Down Expand Up @@ -196,6 +201,16 @@ void Human::Spawn( b2WorldId worldId, b2Vec2 position, float scale, float fricti
bone->jointId = b2CreateRevoluteJoint( worldId, &jointDef );
}

b2Vec2 points[4] = {
{ -0.03f * s, -0.185f * s },
{ 0.11f * s, -0.185f * s },
{ 0.11f * s, -0.16f * s },
{ -0.03f * s, -0.14f * s },
};

b2Hull footHull = b2ComputeHull( points, 4 );
b2Polygon footPolygon = b2MakePolygon( &footHull, 0.015f * s );

// lower left leg
{
Bone* bone = m_bones + Bone::e_lowerLeftLeg;
Expand All @@ -211,14 +226,16 @@ void Human::Spawn( b2WorldId worldId, b2Vec2 position, float scale, float fricti
shapeDef.customColor = pantColor;
}

b2Capsule capsule = { { 0.0f, -0.14f * s }, { 0.0f, 0.125f * s }, 0.05f * s };
b2Capsule capsule = { { 0.0f, -0.155f * s }, { 0.0f, 0.125f * s }, 0.045f * s };
b2CreateCapsuleShape( bone->bodyId, &shapeDef, &capsule );

// b2Polygon box = b2MakeOffsetBox(0.1f * s, 0.03f * s, {0.05f * s, -0.175f * s}, 0.0f);
// b2CreatePolygonShape(bone->bodyId, &shapeDef, &box);

capsule = { { -0.02f * s, -0.175f * s }, { 0.13f * s, -0.175f * s }, 0.03f * s };
b2CreateCapsuleShape( bone->bodyId, &footShapeDef, &capsule );
//capsule = { { -0.02f * s, -0.175f * s }, { 0.13f * s, -0.175f * s }, 0.03f * s };
//b2CreateCapsuleShape( bone->bodyId, &footShapeDef, &capsule );

b2CreatePolygonShape( bone->bodyId, &footShapeDef, &footPolygon );

b2Vec2 pivot = b2Add( { 0.0f, 0.625f * s }, position );
b2RevoluteJointDef jointDef = b2DefaultRevoluteJointDef();
Expand Down Expand Up @@ -291,14 +308,16 @@ void Human::Spawn( b2WorldId worldId, b2Vec2 position, float scale, float fricti
shapeDef.customColor = pantColor;
}

b2Capsule capsule = { { 0.0f, -0.14f * s }, { 0.0f, 0.125f * s }, 0.05f * s };
b2Capsule capsule = { { 0.0f, -0.155f * s }, { 0.0f, 0.125f * s }, 0.045f * s };
b2CreateCapsuleShape( bone->bodyId, &shapeDef, &capsule );

// b2Polygon box = b2MakeOffsetBox(0.1f * s, 0.03f * s, {0.05f * s, -0.175f * s}, 0.0f);
// b2CreatePolygonShape(bone->bodyId, &shapeDef, &box);

capsule = { { -0.02f * s, -0.175f * s }, { 0.13f * s, -0.175f * s }, 0.03f * s };
b2CreateCapsuleShape( bone->bodyId, &footShapeDef, &capsule );
//capsule = { { -0.02f * s, -0.175f * s }, { 0.13f * s, -0.175f * s }, 0.03f * s };
//b2CreateCapsuleShape( bone->bodyId, &footShapeDef, &capsule );

b2CreatePolygonShape( bone->bodyId, &footShapeDef, &footPolygon );

b2Vec2 pivot = b2Add( { 0.0f, 0.625f * s }, position );
b2RevoluteJointDef jointDef = b2DefaultRevoluteJointDef();
Expand Down Expand Up @@ -380,9 +399,10 @@ void Human::Spawn( b2WorldId worldId, b2Vec2 position, float scale, float fricti
jointDef.bodyIdB = bone->bodyId;
jointDef.localAnchorA = b2Body_GetLocalPoint( jointDef.bodyIdA, pivot );
jointDef.localAnchorB = b2Body_GetLocalPoint( jointDef.bodyIdB, pivot );
jointDef.referenceAngle = 0.25f * b2_pi;
jointDef.enableLimit = enableLimit;
jointDef.lowerAngle = 0.01f * b2_pi;
jointDef.upperAngle = 0.5f * b2_pi;
jointDef.lowerAngle = -0.2f * b2_pi;
jointDef.upperAngle = 0.3f * b2_pi;
jointDef.enableMotor = enableMotor;
jointDef.maxMotorTorque = bone->frictionScale * maxTorque;
jointDef.enableSpring = hertz > 0.0f;
Expand Down Expand Up @@ -454,9 +474,10 @@ void Human::Spawn( b2WorldId worldId, b2Vec2 position, float scale, float fricti
jointDef.bodyIdB = bone->bodyId;
jointDef.localAnchorA = b2Body_GetLocalPoint( jointDef.bodyIdA, pivot );
jointDef.localAnchorB = b2Body_GetLocalPoint( jointDef.bodyIdB, pivot );
jointDef.referenceAngle = 0.25f * b2_pi;
jointDef.enableLimit = enableLimit;
jointDef.lowerAngle = 0.01f * b2_pi;
jointDef.upperAngle = 0.5f * b2_pi;
jointDef.lowerAngle = -0.2f * b2_pi;
jointDef.upperAngle = 0.3f * b2_pi;
jointDef.enableMotor = enableMotor;
jointDef.maxMotorTorque = bone->frictionScale * maxTorque;
jointDef.enableSpring = hertz > 0.0f;
Expand Down
61 changes: 45 additions & 16 deletions samples/sample_benchmark.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ class BenchmarkBarrel : public Sample
enum
{
e_maxColumns = 26,
e_maxRows = 130,
e_maxRows = 150,
};

explicit BenchmarkBarrel( Settings& settings )
Expand All @@ -42,32 +42,51 @@ class BenchmarkBarrel : public Sample

settings.drawJoints = false;

float groundSize = 25.0f;

{
float gridSize = 1.0f;

b2BodyDef bodyDef = b2DefaultBodyDef();
b2BodyId groundId = b2CreateBody( m_worldId, &bodyDef );

b2Polygon box = b2MakeBox( groundSize, 1.2f );
b2ShapeDef shapeDef = b2DefaultShapeDef();
b2CreatePolygonShape( groundId, &shapeDef, &box );

box = b2MakeOffsetBox( 1.2f, 2.0f * groundSize, { -groundSize, 2.0f * groundSize }, b2Rot_identity );
b2CreatePolygonShape( groundId, &shapeDef, &box );
float y = 0.0f;
float x = -40.0f * gridSize;
for (int i = 0; i < 81; ++i)
{
b2Polygon box = b2MakeOffsetBox( 0.5f * gridSize, 0.5f * gridSize, {x, y}, b2Rot_identity );
b2CreatePolygonShape( groundId, &shapeDef, &box );
x += gridSize;
}

y = gridSize;
x = -40.0f * gridSize;
for (int i = 0; i < 100; ++i)
{
b2Polygon box = b2MakeOffsetBox( 0.5f * gridSize, 0.5f * gridSize, { x, y }, b2Rot_identity );
b2CreatePolygonShape( groundId, &shapeDef, &box );
y += gridSize;
}

box = b2MakeOffsetBox( 1.2f, 2.0f * groundSize, { groundSize, 2.0f * groundSize }, b2Rot_identity );
b2CreatePolygonShape( groundId, &shapeDef, &box );
y = gridSize;
x = 40.0f * gridSize;
for ( int i = 0; i < 100; ++i )
{
b2Polygon box = b2MakeOffsetBox( 0.5f * gridSize, 0.5f * gridSize, { x, y }, b2Rot_identity );
b2CreatePolygonShape( groundId, &shapeDef, &box );
y += gridSize;
}

box = b2MakeOffsetBox( 800.0f, 10.0f, { 0.0f, -80.0f }, b2Rot_identity );
b2CreatePolygonShape( groundId, &shapeDef, &box );
b2Segment segment = { { -800.0f, -80.0f }, { 800.0f, -80.f } };
b2CreateSegmentShape( groundId, &shapeDef, &segment );
}

for ( int i = 0; i < e_maxRows * e_maxColumns; ++i )
{
m_bodies[i] = b2_nullBodyId;
}

m_shapeType = e_circleShape;
m_shapeType = e_compoundShape;

CreateScene();
}
Expand Down Expand Up @@ -109,8 +128,7 @@ class BenchmarkBarrel : public Sample
}
else
{
m_columnCount = 15;
m_rowCount = 50;
m_rowCount = 30;
}
}

Expand All @@ -123,6 +141,12 @@ class BenchmarkBarrel : public Sample
b2BodyDef bodyDef = b2DefaultBodyDef();
bodyDef.type = b2_dynamicBody;

// todo eliminate this once rolling resistance is added
if (m_shapeType == e_mixShape)
{
bodyDef.angularDamping = 0.3f;
}

b2ShapeDef shapeDef = b2DefaultShapeDef();
shapeDef.density = 1.0f;
shapeDef.friction = 0.5f;
Expand Down Expand Up @@ -170,14 +194,15 @@ class BenchmarkBarrel : public Sample
}

int index = 0;
float yStart = m_shapeType == e_humanShape ? 2.0f : 100.0f;

for ( int i = 0; i < m_columnCount; ++i )
{
float x = i * shift - centerx;

for ( int j = 0; j < m_rowCount; ++j )
{
float y = j * ( shift + extray ) + centery + 2.0f;
float y = j * ( shift + extray ) + centery + yStart;

bodyDef.position = { x + side, y };
side = -side;
Expand Down Expand Up @@ -244,7 +269,11 @@ class BenchmarkBarrel : public Sample
}
else if ( m_shapeType == e_humanShape )
{
m_humans[index].Spawn( m_worldId, bodyDef.position, 3.5f, 0.05f, 0.0f, 0.0f, index + 1, nullptr, false );
float scale = 3.5f;
float jointFriction = 0.05f;
float jointHertz = 5.0f;
float jointDamping = 0.5f;
m_humans[index].Spawn( m_worldId, bodyDef.position, scale, jointFriction, jointHertz, jointDamping, index + 1, nullptr, false );
}

index += 1;
Expand Down
7 changes: 6 additions & 1 deletion samples/sample_events.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -178,7 +178,12 @@ class SensorEvent : public Sample
else
{
Human* human = m_humans + index;
human->Spawn( m_worldId, center, 2.0f, 0.05f, 0.0f, 0.0f, index + 1, human, false );
float scale = 2.0f;
float jointFriction = 0.05f;
float jointHertz = 6.0f;
float jointDamping = 0.5f;
bool colorize = true;
human->Spawn( m_worldId, center, scale, jointFriction, jointHertz, jointDamping, index + 1, human, colorize );
}

m_isSpawned[index] = true;
Expand Down
25 changes: 19 additions & 6 deletions samples/sample_joints.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2110,8 +2110,11 @@ class Ragdoll : public Sample
{
if ( settings.restart == false )
{
g_camera.m_center = { 0.0f, 3.0f };
g_camera.m_zoom = 25.0f * 0.15f;
g_camera.m_center = { 0.0f, 12.0f };
g_camera.m_zoom = 16.0f;

//g_camera.m_center = { 0.0f, 26.0f };
//g_camera.m_zoom = 1.0f;
}

{
Expand All @@ -2122,12 +2125,17 @@ class Ragdoll : public Sample
b2CreateSegmentShape( groundId, &shapeDef, &segment );
}

m_jointFrictionTorque = 0.05f;
m_jointHertz = 0.0f;
m_jointFrictionTorque = 0.03f;
m_jointHertz = 5.0f;
m_jointDampingRatio = 0.5f;

m_human.Spawn( m_worldId, { 0.0f, 5.0f }, 1.0f, m_jointFrictionTorque, m_jointHertz, m_jointDampingRatio, 1, nullptr,
true );
Spawn();
}

void Spawn()
{
m_human.Spawn( m_worldId, { 0.0f, 25.0f }, 1.0f, m_jointFrictionTorque, m_jointHertz, m_jointDampingRatio, 1, nullptr,
false );
m_human.ApplyRandomAngularImpulse( 10.0f );
}

Expand Down Expand Up @@ -2155,6 +2163,11 @@ class Ragdoll : public Sample
m_human.SetJointDampingRatio( m_jointDampingRatio );
}

if ( ImGui::Button( "Respawn" ) )
{
m_human.Despawn();
Spawn();
}
ImGui::PopItemWidth();
ImGui::End();
}
Expand Down
Loading

0 comments on commit dff4193

Please sign in to comment.