ephysics: support body material

Using material_set it will be easier to set density, friction
and restitution to a body, simulating properties of the selected
material.



SVN revision: 77462
This commit is contained in:
Bruno Dilly 2012-10-04 22:39:42 +00:00
parent f0b85f701d
commit 0bdec67255
5 changed files with 166 additions and 5 deletions

View File

@ -1465,6 +1465,28 @@ typedef enum _EPhysics_Callback_Body_Type
EPHYSICS_CALLBACK_BODY_LAST, /**< kept as sentinel, not really an event */
} EPhysics_Callback_Body_Type; /**< The types of events triggering a callback */
/**
* @enum _EPhysics_Body_Material
* @typedef EPhysics_Body_Material
*
* EPhysics bodies materials. Each material has specific properties to be
* applied on the body, as density, friction and restitution.
*
* @see ephysics_body_material_set() for details.
*
* @ingroup EPhysics_Body
*/
typedef enum _EPhysics_Body_Material
{
EPHYSICS_BODY_MATERIAL_CUSTOM, /**< Custom properties set by the user */
EPHYSICS_BODY_MATERIAL_CONCRETE, /**< Density:2300,Fric:0.65,Rest:0.75 */
EPHYSICS_BODY_MATERIAL_IRON, /**< Density:7400,Fric:0.8,Rest:0.85 */
EPHYSICS_BODY_MATERIAL_PLASTIC, /**< Density:1300,Fric:0.35,Rest:0.6 */
EPHYSICS_BODY_MATERIAL_POLYSTYRENE, /**< Density:80,Fric:0.5,Rest:0.5*/
EPHYSICS_BODY_MATERIAL_RUBBER, /**< Density:920,Fric:0.75,Rest:0.3*/
EPHYSICS_BODY_MATERIAL_WOOD, /**< Density:680,Fric:0.4,Rest:0.7*/
EPHYSICS_BODY_MATERIAL_LAST, /**< kept as sentinel, not really a material */
} EPhysics_Body_Material; /**< The types of materials to be set on a body */
/**
* @typedef EPhysics_Body_Event_Cb
@ -2892,6 +2914,46 @@ EAPI void ephysics_body_density_set(EPhysics_Body *body, double density);
*/
EAPI double ephysics_body_density_get(const EPhysics_Body *body);
/**
* @brief
* Set body's material.
*
* This function makes properties setting easy. When a material is set to
* a body, it will update its friction, restitution and density,
* recalculating its mass.
*
* EPhysics support some materials defined by @ref EPhysics_Body_Material.
*
* So, for example, if @ref EPHYSICS_BODY_MATERIAL_WOOD is set, it will
* set body's density to @ref EPHYSICS_BODY_DENSITY_WOOD, restitution
* to @ref EPHSYICS_BODY_RESTITUTION_WOOD and friction to
* @ref EPHYSICS_BODY_FRICTION_WOOD.
*
* If any of these values are later explicitely set, the material will
* be set back to @ref EPHYSICS_BODY_MATERIAL_CUSTOM, the default.
*
* @param body The body to has its material set.
* @param material The @p material to be used by the body.
*
* @see ephysics_body_material_get().
*
* @ingroup EPhysics_Body
*/
EAPI void ephysics_body_material_set(EPhysics_Body *body, EPhysics_Body_Material material);
/**
* @brief
* Get body's material.
*
* @param body The physics body.
* @return the @p material used by the body.
*
* @see ephysics_body_body_set() for more details.
*
* @ingroup EPhysics_Body
*/
EAPI EPhysics_Body_Material ephysics_body_material_get(const EPhysics_Body *body);
/**
* @}
*/

View File

@ -26,4 +26,4 @@ libephysics_la_SOURCES = $(base_sources)
libephysics_la_LIBADD = @EPHYSICS_LIBS@ @EVIL_LIBS@ -lm
libephysics_la_LDFLAGS = -no-undefined @lt_enable_auto_import@ -version-info @version_info@ @release_info@
EXTRA_DIST = ephysics_private.h ephysics_trimesh.h
EXTRA_DIST = ephysics_private.h ephysics_trimesh.h ephysics_body_materials.h

View File

@ -10,6 +10,7 @@
#include "ephysics_private.h"
#include "ephysics_trimesh.h"
#include "ephysics_body_materials.h"
#ifdef __cplusplus
extern "C" {
@ -1418,6 +1419,7 @@ ephysics_body_mass_set(EPhysics_Body *body, double mass)
}
ephysics_world_lock_take(body->world);
body->material = EPHYSICS_BODY_MATERIAL_CUSTOM;
body->density = 0;
_ephysics_body_mass_set(body, mass);
ephysics_world_lock_release(body->world);
@ -1673,6 +1675,13 @@ ephysics_body_event_callback_del_full(EPhysics_Body *body, EPhysics_Callback_Bod
return cb_data;
}
static void
_ephysics_body_restitution_set(EPhysics_Body *body, double restitution)
{
body->rigid_body->setRestitution(btScalar(restitution));
DBG("Body %p restitution set to %lf", body, restitution);
}
EAPI void
ephysics_body_restitution_set(EPhysics_Body *body, double restitution)
{
@ -1683,8 +1692,8 @@ ephysics_body_restitution_set(EPhysics_Body *body, double restitution)
}
ephysics_world_lock_take(body->world);
body->rigid_body->setRestitution(btScalar(restitution));
DBG("Body %p restitution set to %lf", body, restitution);
body->material = EPHYSICS_BODY_MATERIAL_CUSTOM;
_ephysics_body_restitution_set(body, restitution);
ephysics_world_lock_release(body->world);
}
@ -1700,6 +1709,13 @@ ephysics_body_restitution_get(const EPhysics_Body *body)
return body->rigid_body->getRestitution();
}
static void
_ephysics_body_friction_set(EPhysics_Body *body, double friction)
{
body->rigid_body->setFriction(btScalar(friction));
DBG("Body %p friction set to %lf", body, friction);
}
EAPI void
ephysics_body_friction_set(EPhysics_Body *body, double friction)
{
@ -1710,8 +1726,8 @@ ephysics_body_friction_set(EPhysics_Body *body, double friction)
}
ephysics_world_lock_take(body->world);
body->rigid_body->setFriction(btScalar(friction));
DBG("Body %p friction set to %lf", body, friction);
body->material = EPHYSICS_BODY_MATERIAL_CUSTOM;
_ephysics_body_friction_set(body, friction);
ephysics_world_lock_release(body->world);
}
@ -2032,6 +2048,7 @@ ephysics_body_density_set(EPhysics_Body *body, double density)
return;
}
body->material = EPHYSICS_BODY_MATERIAL_CUSTOM;
body->density = density;
ephysics_world_lock_take(body->world);
_ephysics_body_mass_set(body, 0);
@ -2050,6 +2067,50 @@ ephysics_body_density_get(const EPhysics_Body *body)
return body->density;
}
EAPI void
ephysics_body_material_set(EPhysics_Body *body, EPhysics_Body_Material material)
{
if (!body)
{
ERR("Can't set body's material.");
return;
}
if (material >= EPHYSICS_BODY_MATERIAL_LAST)
{
ERR("Invalid material.");
return;
}
if (material != ephysics_material_props[material].material)
{
ERR("Material properties weren't found.");
return;
}
ephysics_world_lock_take(body->world);
body->density = ephysics_material_props[material].density;
_ephysics_body_mass_set(body, 0);
_ephysics_body_friction_set(body,
ephysics_material_props[material].friction);
_ephysics_body_restitution_set(
body, ephysics_material_props[material].restitution);
body->material = material;
ephysics_world_lock_release(body->world);
}
EAPI EPhysics_Body_Material
ephysics_body_material_get(const EPhysics_Body *body)
{
if (!body)
{
ERR("Can't get body's material.");
return EPHYSICS_BODY_MATERIAL_LAST;
}
return body->material;
}
#ifdef __cplusplus
}
#endif

View File

@ -0,0 +1,37 @@
#ifndef _EPHYSICS_BODY_MATERIALS_H
#define _EPHYSICS_BODY_MATERIALS_H
#ifdef __cplusplus
extern "C" {
#endif
typedef struct _EPhysics_Body_Material_Props EPhysics_Body_Material_Props;
struct _EPhysics_Body_Material_Props {
EPhysics_Body_Material material;
int density;
double friction;
double restitution;
};
const EPhysics_Body_Material_Props ephysics_material_props [] = {
{EPHYSICS_BODY_MATERIAL_CUSTOM, 1.0, 0.0, 0.0},
{EPHYSICS_BODY_MATERIAL_CONCRETE, EPHYSICS_BODY_DENSITY_CONCRETE,
EPHYSICS_BODY_FRICTION_CONCRETE, EPHYSICS_BODY_RESTITUTION_CONCRETE},
{EPHYSICS_BODY_MATERIAL_IRON, EPHYSICS_BODY_DENSITY_IRON,
EPHYSICS_BODY_FRICTION_IRON, EPHYSICS_BODY_RESTITUTION_IRON},
{EPHYSICS_BODY_MATERIAL_PLASTIC, EPHYSICS_BODY_DENSITY_PLASTIC,
EPHYSICS_BODY_FRICTION_PLASTIC, EPHYSICS_BODY_RESTITUTION_PLASTIC},
{EPHYSICS_BODY_MATERIAL_POLYSTYRENE, EPHYSICS_BODY_DENSITY_POLYSTYRENE,
EPHYSICS_BODY_FRICTION_POLYSTYRENE,
EPHYSICS_BODY_RESTITUTION_POLYSTYRENE},
{EPHYSICS_BODY_MATERIAL_RUBBER, EPHYSICS_BODY_DENSITY_RUBBER,
EPHYSICS_BODY_FRICTION_RUBBER, EPHYSICS_BODY_RESTITUTION_RUBBER},
{EPHYSICS_BODY_MATERIAL_WOOD, EPHYSICS_BODY_DENSITY_WOOD,
EPHYSICS_BODY_FRICTION_WOOD, EPHYSICS_BODY_RESTITUTION_WOOD}
};
#ifdef __cplusplus
}
#endif
#endif

View File

@ -79,6 +79,7 @@ struct _EPhysics_Body {
Eina_Inlist *callbacks;
Eina_List *collision_groups;
Eina_List *to_delete;
EPhysics_Body_Material material;
double mass;
double density;
struct {