Nudge Physics
A single file, header-only 3D physics library
Loading...
Searching...
No Matches
Add-Bodies Functions

Set of functions regarding creation and removal of physic bodies. More...

Functions

unsigned nudge::add_box (context_t *c, float mass, float hsizex, float hsizey, float hsizez, const Transform *T=NULL, const float comOffset[3]=NULL)
 Adds a new body to the simulation with a single box collider.
 
unsigned nudge::add_box (context_t *c, float mass, float hsizex, float hsizey, float hsizez, const float *mMatrix16WithoutScaling, const float comOffset[3]=NULL)
 
unsigned nudge::add_sphere (context_t *c, float mass, float radius, const Transform *T=NULL, const float comOffset[3]=NULL)
 Adds a new body to the simulation with a single sphere collider.
 
unsigned nudge::add_sphere (context_t *c, float mass, float radius, const float *mMatrix16WithoutScaling, const float comOffset[3]=NULL)
 
unsigned nudge::add_compound (context_t *c, float mass, float inertia[3], unsigned num_boxes, const float *hsizeTriplets, const Transform *boxOffsetTransforms, unsigned num_spheres, const float *radii, const Transform *sphereOffsetTransforms, const Transform *T=NULL, const float comOffset[3]=NULL, float *centerMeshAndRetrieveOldCenter3Out=NULL)
 Adds a new body to the simulation with a compound collider made up of num_boxes box colliders and num_spheres sphere colliders.
 
unsigned nudge::add_compound (context_t *c, float mass, float inertia[3], unsigned num_boxes, const float *hsizeTriplets, const float *boxOffsetMatrices16WithoutScaling, unsigned num_spheres, const float *radii, const float *sphereOffsetMatrices16WithoutScaling, const float *mMatrix16WithoutScaling=NULL, const float comOffset[3]=NULL, float *centerMeshAndRetrieveOldCenter3Out=NULL)
 
unsigned nudge::add_clone (context_t *c, unsigned body_to_clone, float mass, const Transform *T=NULL, float scale_factor=1.f, const float newComOffsetInPreScaledUnits[3]=NULL)
 [Experimental] Adds a new body to the simulation cloning an existing body
 
unsigned nudge::add_clone (context_t *c, unsigned body_to_clone, float mass, const float *mMatrix16WithoutScaling, float scale_factor=1.f, const float newComOffsetInPreScaledUnits[3]=NULL)
 
void nudge::remove_body (context_t *c, unsigned body)
 Removes a body from the simulation.
 
uint32_t nudge::colliders_get_num_remaining_boxes (context_t *c)
 Return the number of box colliders that can still be added to the physic world.
 
uint32_t nudge::colliders_get_num_remaining_spheres (context_t *c)
 Return the number of sphere colliders that can still be added to the physic world.
 
int nudge::can_add_box (context_t *c)
 
int nudge::can_add_sphere (context_t *c)
 
int nudge::can_add_compound (context_t *c, unsigned num_boxes, unsigned num_spheres)
 
int nudge::can_add_clone (context_t *c, unsigned body_to_clone)
 
unsigned nudge::get_next_add_body_index (context_t *c)
 Allows to peek the body index that is going to be returned in next add_xxx(...) call.
 
void nudge::body_recalculate_bounding_box (context_t *c, uint32_t body)
 Recalculates the bounding box of the body (BodyInfo::aabb_center and BodyInfo::aabb_extents)
 
void nudge::body_change_motion_state (nudge::context_t *c, unsigned body, nudge::FlagMask new_motion_state, float mass_fallback=1.f)
 [Experimental] Changes the body motion state (i.e. the BF_IS_STATIC_OR_KINEMATIC_OR_DYNAMIC group of body flags)
 
void nudge::body_scale (nudge::context_t *c, unsigned body, float scale_factor, float mass_scale_factor=0.f)
 [Experimental] Uniformly scales the specified body incrementally
 

Detailed Description

Set of functions regarding creation and removal of physic bodies.

Function Documentation

◆ add_box() [1/2]

unsigned nudge::add_box ( context_t c,
float  mass,
float  hsizex,
float  hsizey,
float  hsizez,
const Transform T = NULL,
const float  comOffset[3] = NULL 
)

Adds a new body to the simulation with a single box collider.

Parameters
cthe nudge context
masspositive => dynamic; 0 => static; negative => kinematic (where the absolute value will be used as mass internally)
hsizexhalf box size in the x direction
hsizeyhalf box size in the y direction
hsizezhalf box size in the z direction
Ta pointer to a Transform
comOffsetan optional array of 3 floats that determines the center of mass offset of the body
Returns
the body index, or NUDGE_INVALID_BODY_ID if no more boxes can be added
Note
Internally mass_inverse and inertia_inverse are always stored as positive values (except for static bodies): this makes kinematic to dynamic body conversions a bit easier
Every time an add_xxx(...) function is called, if c->global_data.finalized_removed_bodies_count>0, the body c->global_data.removed_bodies[0] is always reused and returned

◆ add_box() [2/2]

unsigned nudge::add_box ( context_t c,
float  mass,
float  hsizex,
float  hsizey,
float  hsizez,
const float *  mMatrix16WithoutScaling,
const float  comOffset[3] = NULL 
)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Parameters
mMatrix16WithoutScalinga pointer to a 4x4 column-major matrix with only translation and rotation

◆ add_sphere() [1/2]

unsigned nudge::add_sphere ( context_t c,
float  mass,
float  radius,
const Transform T = NULL,
const float  comOffset[3] = NULL 
)

Adds a new body to the simulation with a single sphere collider.

Parameters
cthe nudge context
masspositive => dynamic; 0 => static; negative => kinematic (where the absolute value will be used as mass internally)
radiusthe sphere radius
Ta pointer to a Transform
comOffsetan optional array of 3 floats that determines the center of mass offset of the body
Returns
the body index, or NUDGE_INVALID_BODY_ID if no more spheres can be added
Note
Internally mass_inverse and inertia_inverse are always stored as positive values (except for static bodies): this makes kinematic to dynamic body conversions a bit easier
Every time an add_xxx(...) function is called, if c->global_data.finalized_removed_bodies_count>0, the body c->global_data.removed_bodies[0] is always reused and returned

◆ add_sphere() [2/2]

unsigned nudge::add_sphere ( context_t c,
float  mass,
float  radius,
const float *  mMatrix16WithoutScaling,
const float  comOffset[3] = NULL 
)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Parameters
mMatrix16WithoutScalinga pointer to a 4x4 column-major matrix with only translation and rotation

◆ add_compound() [1/2]

unsigned nudge::add_compound ( context_t c,
float  mass,
float  inertia[3],
unsigned  num_boxes,
const float *  hsizeTriplets,
const Transform boxOffsetTransforms,
unsigned  num_spheres,
const float *  radii,
const Transform sphereOffsetTransforms,
const Transform T = NULL,
const float  comOffset[3] = NULL,
float *  centerMeshAndRetrieveOldCenter3Out = NULL 
)

Adds a new body to the simulation with a compound collider made up of num_boxes box colliders and num_spheres sphere colliders.

Parameters
cthe nudge context
masspositive => dynamic; 0 => static; negative => kinematic (where the absolute value will be used as mass internally)
inertiaan inertia tensor in a 3-float array form that is used only if mass is not zero (see also the inertia helper functions); it can be NULL (in that case a box inertia on the body axis-aligned bounding box extents is used)
num_boxes
hsizeTripletspointer to an array of size 3*num_boxes floats
boxOffsetTransformspointer to an array of num_boxes Transforms
num_spheres
radiipointer to an array of num_sphere floats
sphereOffsetTransformspointer to an array of num_sphere Transforms
Ta pointer to a Transform
comOffsetan optional input array of 3 floats that determines the center of mass offset of the body
centerMeshAndRetrieveOldCenter3Out[experimental] an optional output array of 3 floats: if set, the input mesh is recentered (before applying the comOffset) and the axis-aligned bounding box center that has been subtracted from the mesh is returned
Returns
the body index, or NUDGE_INVALID_BODY_ID if no more boxes can be added
Note
Internally mass_inverse and inertia_inverse are always stored as positive values (except for static bodies): this makes kinematic to dynamic body conversions a bit easier
Every time an add_xxx(...) function is called, if c->global_data.finalized_removed_bodies_count>0, the body c->global_data.removed_bodies[0] is always reused and returned

◆ add_compound() [2/2]

unsigned nudge::add_compound ( context_t c,
float  mass,
float  inertia[3],
unsigned  num_boxes,
const float *  hsizeTriplets,
const float *  boxOffsetMatrices16WithoutScaling,
unsigned  num_spheres,
const float *  radii,
const float *  sphereOffsetMatrices16WithoutScaling,
const float *  mMatrix16WithoutScaling = NULL,
const float  comOffset[3] = NULL,
float *  centerMeshAndRetrieveOldCenter3Out = NULL 
)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Parameters
mMatrix16WithoutScalinga pointer to a 4x4 column-major matrix with only translation and rotation

◆ add_clone() [1/2]

unsigned nudge::add_clone ( context_t c,
unsigned  body_to_clone,
float  mass,
const Transform T = NULL,
float  scale_factor = 1.f,
const float  newComOffsetInPreScaledUnits[3] = NULL 
)

[Experimental] Adds a new body to the simulation cloning an existing body

Parameters
cthe nudge context
body_to_clonethe body to clone
masspositive => dynamic; 0 => static; negative => kinematic (where the absolute value will be used as mass internally)
Ta pointer to a Transform
scale_factorpositive => the uniform scaling factor to apply (to each single axis); negative => scale so that the half bounding box y-component of the body becomes exactly -scaling_factor; 0 => invalid value (asserts)
newComOffsetInPreScaledUnitsif set, an absolute new center of mass offset will be added (replacing the old one if present) using the pre-scaled coordinates; otherwise the old center of mass offset (if present) is kept (and possibly scaled)
Returns
the body index, or NUDGE_INVALID_BODY_ID if no more boxes can be added
Note
Internally mass_inverse and inertia_inverse are always stored as positive values (except for static bodies): this makes kinematic to dynamic body conversions a bit easier
Every time an add_xxx(...) function is called, if c->global_data.finalized_removed_bodies_count>0, the body c->global_data.removed_bodies[0] is always reused and returned

◆ add_clone() [2/2]

unsigned nudge::add_clone ( context_t c,
unsigned  body_to_clone,
float  mass,
const float *  mMatrix16WithoutScaling,
float  scale_factor = 1.f,
const float  newComOffsetInPreScaledUnits[3] = NULL 
)

This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.

Parameters
mMatrix16WithoutScalinga pointer to a 4x4 column-major matrix with only translation and rotation

◆ remove_body()

void nudge::remove_body ( context_t c,
unsigned  body 
)

Removes a body from the simulation.

Note
The body is actually removed next time simulation_step(...) is called (the call 'finalizes' the removal of all pending bodies). The body can't be reused after this call and could still be present in ContactData for some (1?) frames. In any case user can detect it with: ((*body_get_flags(...))&BF_IS_REMOVED). Also removed bodies are NOT subtracted from c->bodies.count, but are reused when new bodies are added with: add_xxx(...).
Internally, removed bodies are kept in the c->global_data.removed_bodies array.
If you just want to reuse the body WITH THE SAME (optionally rescaled) collider(s) soon, you should not remove the body, but just change its properties (more efficient + no delay).
Sometimes it's better to just disable a body, instead of removing it, using: (*body_get_flags(...))|=BF_IS_DISABLED: this way the body can be optionally put into a user-side custom list for later reusage/reactivation. This way the body colliders are preserved.
Every time an add_xxx(...) function is called, if c->global_data.finalized_removed_bodies_count>0, the body: c->global_data.removed_bodies[0] is always returned.
User data in the BodyInfo struct are NOT reset when a body is removed, but most of the other data are reset when removed bodies are finalized at the beginning of next simulation_step(...) call.
That means that when bodies are reused in add_xxx(...) functions, their old user data are preserved.
Kinematic animations referencing removed bodies are assigned to NUDGE_INVALID_BODY_ID when removed bodies are finalized (there's an optional definition NUDGE_DELETE_KINEMATIC_ANIMATIONS_REFERENCING_REMOVED_BODIES to delete the kinematic animations instead).

◆ colliders_get_num_remaining_boxes()

uint32_t nudge::colliders_get_num_remaining_boxes ( context_t c)

Return the number of box colliders that can still be added to the physic world.

Note
The maximum number can be set in init_context_with(...) and can't be changed at runtime

◆ colliders_get_num_remaining_spheres()

uint32_t nudge::colliders_get_num_remaining_spheres ( context_t c)

Return the number of sphere colliders that can still be added to the physic world.

Note
The maximum number can be set in init_context_with(...) and can't be changed at runtime

◆ can_add_box()

int nudge::can_add_box ( context_t c)
inline
Returns
1 if add_box(...) can be called successfully

◆ can_add_sphere()

int nudge::can_add_sphere ( context_t c)
inline
Returns
1 if add_sphere(...) can be called successfully

◆ can_add_compound()

int nudge::can_add_compound ( context_t c,
unsigned  num_boxes,
unsigned  num_spheres 
)
inline
Returns
1 if add_compound(...) can be called successfully with num_boxes and num_spheres

◆ can_add_clone()

int nudge::can_add_clone ( context_t c,
unsigned  body_to_clone 
)
inline
Returns
1 if add_clone(...) can be called successfully

◆ get_next_add_body_index()

unsigned nudge::get_next_add_body_index ( context_t c)
inline

Allows to peek the body index that is going to be returned in next add_xxx(...) call.

Parameters
cthe nudge context
Returns
one of the following values: c->bodies.count, c->global_data.removed_bodies[0] or NUDGE_INVALID_BODY_ID
Note
Next call to any add_xxx(...) function can still return NUDGE_INVALID_BODY_ID, if the number of available colliders runs out (that condition can be queried before adding the body using colliders_get_num_remaining_boxes(...), colliders_get_num_remaining_spheres(...) or can_add_box(...), can_add_sphere(...), can_add_compound(...))
The returned body is valid until next simulation_step(...) call
A returned value of c->bodies.count can still be used, because the arrays are allocated at context init time, with a size of c->MAX_NUM_BODIES

◆ body_recalculate_bounding_box()

void nudge::body_recalculate_bounding_box ( context_t c,
uint32_t  body 
)

Recalculates the bounding box of the body (BodyInfo::aabb_center and BodyInfo::aabb_extents)

Parameters
cthe nudge context
bodythe body index
Note
This function is already called when bodies are added (see add_xxx functions); so it's almost pointless to call it again (except maybe when manually changing the size of some collider)
nudge.h does not use the body bounding box at all: it has been added just to ease user experience

◆ body_change_motion_state()

void nudge::body_change_motion_state ( nudge::context_t c,
unsigned  body,
nudge::FlagMask  new_motion_state,
float  mass_fallback = 1.f 
)

[Experimental] Changes the body motion state (i.e. the BF_IS_STATIC_OR_KINEMATIC_OR_DYNAMIC group of body flags)

Parameters
cthe nudge context
bodythe index of the body
new_motion_statethe desired new motion state; it must be: BF_IS_STATIC, BF_IS_KINEMATIC or BF_IS_DYNAMIC
mass_fallbacka mass fallback used only when 'new_motion_state' is BF_IS_DYNAMIC and the body had zero mass (the body was static)
Note
Experimental feature: use it at your own risk and for a limited and selected amount of bodies
This function resets the body velocities
In case of BF_IS_DYNAMIC 'new_motion_state' this function can replace the components of inertia of the body, if it was not set before (the body was static) with a box inertia on the body axis aligned bounding box
It's better to leave static bodies alone, and just make kinematic bodies dynamic or viceversa

◆ body_scale()

void nudge::body_scale ( nudge::context_t c,
unsigned  body,
float  scale_factor,
float  mass_scale_factor = 0.f 
)

[Experimental] Uniformly scales the specified body incrementally

Parameters
cthe nudge context
bodythe target body
scale_factorpositive => the uniform scaling factor to apply (to each single axis); negative => scale so that the half bounding box y-component of the body becomes exactly -scaling_factor; 0 => invalid value (asserts)
mass_scale_factorpositive => the scaling amount to apply to the mass; 0 => sets 'mass_scale_factor' to the cube of the 'scaling_factor' argument; negative => sets the new mass exactly to -mass_scale_factor
Note
Experimental feature: use it at your own risk and for a limited and selected amount of bodies
Since the scaling is incremental, floating point errors are introduced when this function is called multiple times (e.g. calling it with 2.f and then with 0.5f is not perfectly equivalent to leaving the body unscaled), and it's not possible to retrieve the scaling factor that has been applied
In case 'mass_scale_factor' is negative and the body has no inertia set, a box inertia for the body is calculated on the body axis aligned bounding box