Project::OSiRiON - Git repositories
Project::OSiRiON
News . About . Screenshots . Downloads . Forum . Wiki . Tracker . Git
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'src/game/base/projectile.cc')
-rw-r--r--src/game/base/projectile.cc115
1 files changed, 108 insertions, 7 deletions
diff --git a/src/game/base/projectile.cc b/src/game/base/projectile.cc
index 6bcbad9..4dd483d 100644
--- a/src/game/base/projectile.cc
+++ b/src/game/base/projectile.cc
@@ -13,16 +13,16 @@
namespace game
{
-Projectile::Projectile(unsigned long lifespan) : EntityDynamic()
+EntityProjectile::EntityProjectile(unsigned long lifespan) : EntityDynamic()
{
entity_moduletypeid = projectile_enttype;
//set_name("");
- //set_label("");
+ set_label("projectile");
//set_serverside(true);
set_flag(core::Entity::KeepAlive);
set_shape(core::Entity::Sphere);
- set_radius(0.02f);
+ set_radius(0.01f);
set_mass(radius());
//reset();
@@ -36,17 +36,17 @@ Projectile::Projectile(unsigned long lifespan) : EntityDynamic()
projectile_ownerid = 0;
}
-Projectile::~Projectile()
+EntityProjectile::~EntityProjectile()
{
}
-void Projectile::upkeep(const unsigned long timestamp)
+void EntityProjectile::upkeep(const unsigned long timestamp)
{
die();
}
-void Projectile::collision(core::Entity *other)
+void EntityProjectile::collision(core::Entity *other)
{
if (state() == core::Entity::Destroyed) {
return;
@@ -56,7 +56,7 @@ void Projectile::collision(core::Entity *other)
// this method is a bullet callback, we can not reset() here
}
-void Projectile::frame(const unsigned long elapsed)
+void EntityProjectile::frame(const unsigned long elapsed)
{
EntityDynamic::frame(elapsed);
@@ -69,5 +69,106 @@ void Projectile::frame(const unsigned long elapsed)
}
}
+void EntityProjectile::reset()
+{
+ // no bullet physics on NonSolid entities
+ if (!radius() || has_flag(NonSolid)) {
+ return;
+ }
+
+ // remove Docked and Destroyed entities from the physics simulation
+ if (destroyed() || (state() == core::Entity::Docked) || (state() == core::Entity::Destroyed)) {
+
+ if (entity_body) {
+
+ if (entity_motionstate) {
+ delete entity_motionstate;
+ entity_motionstate = 0;
+ }
+
+ if (zone() && zone()->physics()) {
+ entity_zone->physics()->removeRigidBody(body());
+ }
+
+ if (entity_collision_shape) {
+ delete entity_collision_shape;
+ entity_collision_shape = 0;
+ }
+
+ for (CollisionShapes::iterator sit = entity_collision_child_shapes.begin(); sit != entity_collision_child_shapes.end(); sit++) {
+ delete (*sit);
+ (*sit) = 0;
+ }
+ entity_collision_child_shapes.clear();
+
+ if (entity_body) {
+ delete entity_body;
+ entity_body = 0;
+ }
+
+ if (entity_body_info) {
+ delete entity_body_info;
+ entity_body_info = 0;
+ }
+ }
+
+ return;
+ }
+
+ // location and orientation
+ btTransform t;
+ t.setIdentity();
+ t.setOrigin(to_btVector3(location()));
+ t.setBasis(to_btMatrix3x3(axis()));
+
+ // construct physics body if necessary
+ if (!entity_body) {
+ // use a sphere with a radius matching the entity
+ btSphereShape *sphereshape = new btSphereShape(radius());
+ entity_collision_shape = sphereshape;
+
+ // set margin
+ //entity_collision_shape->setMargin(core::Cvar::sv_collisionmargin->value());
+
+ // calculate inertia
+ btVector3 inertia(0, 0, 0);
+ if (entity_mass)
+ entity_collision_shape->calculateLocalInertia(entity_mass, inertia);
+
+ // create motion state
+ entity_motionstate = new btDefaultMotionState(t);
+
+ // create physics body
+ entity_body_info = new btRigidBody::btRigidBodyConstructionInfo(entity_mass, entity_motionstate, entity_collision_shape, inertia);
+ entity_body = new btRigidBody(*entity_body_info);
+ // point the bullet user pointer to the entity
+ entity_body->setUserPointer((void *) this);
+ // enable custom collision callback
+ entity_body->setCollisionFlags(entity_body->getCollisionFlags() | btCollisionObject::CF_CUSTOM_MATERIAL_CALLBACK);
+ //entity_body->setCollisionFlags(entity_body->getCollisionFlags() | btCollisionObject::CF_NO_CONTACT_RESPONSE);
+
+ if (entity_mass) {
+ entity_body->setActivationState(DISABLE_DEACTIVATION);
+ } else {
+ entity_body->setActivationState(ISLAND_SLEEPING);
+ }
+
+ if (zone())
+ zone()->physics()->addRigidBody(entity_body);
+ }
+
+ // transfer entity location to motion state
+ body()->setLinearVelocity(btVector3(0.0f, 0.0f, 0.0f));
+ body()->setAngularVelocity(btVector3(0.0f, 0.0f, 0.0f));
+ body()->setWorldTransform(t);
+ body()->clearForces();
+
+ if (motionstate()) {
+ motionstate()->setWorldTransform(t);
+ }
+
+ set_dirty();
+}
+
} // namespace game