Expose bullet shape margin to UI.

The margin value is exposed into the UI for shape ressource.
This value can be modified through set_margin and get from get_margin
or by using the property margin. Each time the margin is modified
the associated collision shape is recreated and the margin value is
used in ShapeBullet::prepare.
This commit is contained in:
Tristan Porteries 2018-07-10 12:50:14 +00:00 committed by Porteries Tristan
parent b01f036fb4
commit e5bfa98d0f
9 changed files with 98 additions and 31 deletions

View File

@ -159,6 +159,18 @@ Variant BulletPhysicsServer::shape_get_data(RID p_shape) const {
return shape->get_data(); return shape->get_data();
} }
void BulletPhysicsServer::shape_set_margin(RID p_shape, real_t p_margin) {
ShapeBullet *shape = shape_owner.get(p_shape);
ERR_FAIL_COND(!shape);
shape->set_margin(p_margin);
}
real_t BulletPhysicsServer::shape_get_margin(RID p_shape) const {
ShapeBullet *shape = shape_owner.get(p_shape);
ERR_FAIL_COND_V(!shape, 0.0);
return shape->get_margin();
}
real_t BulletPhysicsServer::shape_get_custom_solver_bias(RID p_shape) const { real_t BulletPhysicsServer::shape_get_custom_solver_bias(RID p_shape) const {
//WARN_PRINT("Bias not supported by Bullet physics engine"); //WARN_PRINT("Bias not supported by Bullet physics engine");
return 0.; return 0.;

View File

@ -99,6 +99,9 @@ public:
virtual ShapeType shape_get_type(RID p_shape) const; virtual ShapeType shape_get_type(RID p_shape) const;
virtual Variant shape_get_data(RID p_shape) const; virtual Variant shape_get_data(RID p_shape) const;
virtual void shape_set_margin(RID p_shape, real_t p_margin);
virtual real_t shape_get_margin(RID p_shape) const;
/// Not supported /// Not supported
virtual void shape_set_custom_solver_bias(RID p_shape, real_t p_bias); virtual void shape_set_custom_solver_bias(RID p_shape, real_t p_bias);
/// Not supported /// Not supported

View File

@ -44,19 +44,20 @@
@author AndreaCatania @author AndreaCatania
*/ */
ShapeBullet::ShapeBullet() {} ShapeBullet::ShapeBullet() :
margin(0.04) {}
ShapeBullet::~ShapeBullet() {} ShapeBullet::~ShapeBullet() {}
btCollisionShape *ShapeBullet::create_bt_shape(const Vector3 &p_implicit_scale, real_t p_margin) { btCollisionShape *ShapeBullet::create_bt_shape(const Vector3 &p_implicit_scale, real_t p_extra_edge) {
btVector3 s; btVector3 s;
G_TO_B(p_implicit_scale, s); G_TO_B(p_implicit_scale, s);
return create_bt_shape(s, p_margin); return create_bt_shape(s, p_extra_edge);
} }
btCollisionShape *ShapeBullet::prepare(btCollisionShape *p_btShape) const { btCollisionShape *ShapeBullet::prepare(btCollisionShape *p_btShape) const {
p_btShape->setUserPointer(const_cast<ShapeBullet *>(this)); p_btShape->setUserPointer(const_cast<ShapeBullet *>(this));
p_btShape->setMargin(0.); p_btShape->setMargin(margin);
return p_btShape; return p_btShape;
} }
@ -93,6 +94,15 @@ const Map<ShapeOwnerBullet *, int> &ShapeBullet::get_owners() const {
return owners; return owners;
} }
void ShapeBullet::set_margin(real_t p_margin) {
margin = p_margin;
notifyShapeChanged();
}
real_t ShapeBullet::get_margin() const {
return margin;
}
btEmptyShape *ShapeBullet::create_shape_empty() { btEmptyShape *ShapeBullet::create_shape_empty() {
return bulletnew(btEmptyShape); return bulletnew(btEmptyShape);
} }
@ -162,7 +172,7 @@ void PlaneShapeBullet::setup(const Plane &p_plane) {
notifyShapeChanged(); notifyShapeChanged();
} }
btCollisionShape *PlaneShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin) { btCollisionShape *PlaneShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge) {
btVector3 btPlaneNormal; btVector3 btPlaneNormal;
G_TO_B(plane.normal, btPlaneNormal); G_TO_B(plane.normal, btPlaneNormal);
return prepare(PlaneShapeBullet::create_shape_plane(btPlaneNormal, plane.d)); return prepare(PlaneShapeBullet::create_shape_plane(btPlaneNormal, plane.d));
@ -190,8 +200,8 @@ void SphereShapeBullet::setup(real_t p_radius) {
notifyShapeChanged(); notifyShapeChanged();
} }
btCollisionShape *SphereShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin) { btCollisionShape *SphereShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge) {
return prepare(ShapeBullet::create_shape_sphere(radius * p_implicit_scale[0] + p_margin)); return prepare(ShapeBullet::create_shape_sphere(radius * p_implicit_scale[0] + p_extra_edge));
} }
/* Box */ /* Box */
@ -217,8 +227,8 @@ void BoxShapeBullet::setup(const Vector3 &p_half_extents) {
notifyShapeChanged(); notifyShapeChanged();
} }
btCollisionShape *BoxShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin) { btCollisionShape *BoxShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge) {
return prepare(ShapeBullet::create_shape_box((half_extents * p_implicit_scale) + btVector3(p_margin, p_margin, p_margin))); return prepare(ShapeBullet::create_shape_box((half_extents * p_implicit_scale) + btVector3(p_extra_edge, p_extra_edge, p_extra_edge)));
} }
/* Capsule */ /* Capsule */
@ -250,8 +260,8 @@ void CapsuleShapeBullet::setup(real_t p_height, real_t p_radius) {
notifyShapeChanged(); notifyShapeChanged();
} }
btCollisionShape *CapsuleShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin) { btCollisionShape *CapsuleShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge) {
return prepare(ShapeBullet::create_shape_capsule(radius * p_implicit_scale[0] + p_margin, height * p_implicit_scale[1] + p_margin)); return prepare(ShapeBullet::create_shape_capsule(radius * p_implicit_scale[0] + p_extra_edge, height * p_implicit_scale[1] + p_extra_edge));
} }
/* Convex polygon */ /* Convex polygon */
@ -292,11 +302,10 @@ void ConvexPolygonShapeBullet::setup(const Vector<Vector3> &p_vertices) {
notifyShapeChanged(); notifyShapeChanged();
} }
btCollisionShape *ConvexPolygonShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin) { btCollisionShape *ConvexPolygonShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge) {
btCollisionShape *cs(ShapeBullet::create_shape_convex(vertices)); btCollisionShape *cs(ShapeBullet::create_shape_convex(vertices));
cs->setLocalScaling(p_implicit_scale); cs->setLocalScaling(p_implicit_scale);
prepare(cs); prepare(cs);
cs->setMargin(p_margin);
return cs; return cs;
} }
@ -365,14 +374,13 @@ void ConcavePolygonShapeBullet::setup(PoolVector<Vector3> p_faces) {
notifyShapeChanged(); notifyShapeChanged();
} }
btCollisionShape *ConcavePolygonShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin) { btCollisionShape *ConcavePolygonShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge) {
btCollisionShape *cs = ShapeBullet::create_shape_concave(meshShape); btCollisionShape *cs = ShapeBullet::create_shape_concave(meshShape);
if (!cs) if (!cs)
// This is necessary since if 0 faces the creation of concave return NULL // This is necessary since if 0 faces the creation of concave return NULL
cs = ShapeBullet::create_shape_empty(); cs = ShapeBullet::create_shape_empty();
cs->setLocalScaling(p_implicit_scale); cs->setLocalScaling(p_implicit_scale);
prepare(cs); prepare(cs);
cs->setMargin(p_margin);
return cs; return cs;
} }
@ -458,11 +466,10 @@ void HeightMapShapeBullet::setup(PoolVector<real_t> &p_heights, int p_width, int
notifyShapeChanged(); notifyShapeChanged();
} }
btCollisionShape *HeightMapShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin) { btCollisionShape *HeightMapShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge) {
btCollisionShape *cs(ShapeBullet::create_shape_height_field(heights, width, depth, min_height, max_height)); btCollisionShape *cs(ShapeBullet::create_shape_height_field(heights, width, depth, min_height, max_height));
cs->setLocalScaling(p_implicit_scale); cs->setLocalScaling(p_implicit_scale);
prepare(cs); prepare(cs);
cs->setMargin(p_margin);
return cs; return cs;
} }
@ -496,6 +503,6 @@ void RayShapeBullet::setup(real_t p_length, bool p_slips_on_slope) {
notifyShapeChanged(); notifyShapeChanged();
} }
btCollisionShape *RayShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin) { btCollisionShape *RayShapeBullet::create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge) {
return prepare(ShapeBullet::create_shape_ray(length * p_implicit_scale[1] + p_margin, slips_on_slope)); return prepare(ShapeBullet::create_shape_ray(length * p_implicit_scale[1] + p_extra_edge, slips_on_slope));
} }

View File

@ -52,6 +52,7 @@ class btBvhTriangleMeshShape;
class ShapeBullet : public RIDBullet { class ShapeBullet : public RIDBullet {
Map<ShapeOwnerBullet *, int> owners; Map<ShapeOwnerBullet *, int> owners;
real_t margin;
protected: protected:
/// return self /// return self
@ -62,14 +63,17 @@ public:
ShapeBullet(); ShapeBullet();
virtual ~ShapeBullet(); virtual ~ShapeBullet();
btCollisionShape *create_bt_shape(const Vector3 &p_implicit_scale, real_t p_margin = 0); btCollisionShape *create_bt_shape(const Vector3 &p_implicit_scale, real_t p_extra_edge = 0);
virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin = 0) = 0; virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge = 0) = 0;
void add_owner(ShapeOwnerBullet *p_owner); void add_owner(ShapeOwnerBullet *p_owner);
void remove_owner(ShapeOwnerBullet *p_owner, bool p_permanentlyFromThisBody = false); void remove_owner(ShapeOwnerBullet *p_owner, bool p_permanentlyFromThisBody = false);
bool is_owner(ShapeOwnerBullet *p_owner) const; bool is_owner(ShapeOwnerBullet *p_owner) const;
const Map<ShapeOwnerBullet *, int> &get_owners() const; const Map<ShapeOwnerBullet *, int> &get_owners() const;
void set_margin(real_t p_margin);
real_t get_margin() const;
/// Setup the shape /// Setup the shape
virtual void set_data(const Variant &p_data) = 0; virtual void set_data(const Variant &p_data) = 0;
virtual Variant get_data() const = 0; virtual Variant get_data() const = 0;
@ -99,7 +103,7 @@ public:
virtual void set_data(const Variant &p_data); virtual void set_data(const Variant &p_data);
virtual Variant get_data() const; virtual Variant get_data() const;
virtual PhysicsServer::ShapeType get_type() const; virtual PhysicsServer::ShapeType get_type() const;
virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin = 0); virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge = 0);
private: private:
void setup(const Plane &p_plane); void setup(const Plane &p_plane);
@ -116,7 +120,7 @@ public:
virtual void set_data(const Variant &p_data); virtual void set_data(const Variant &p_data);
virtual Variant get_data() const; virtual Variant get_data() const;
virtual PhysicsServer::ShapeType get_type() const; virtual PhysicsServer::ShapeType get_type() const;
virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin = 0); virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge = 0);
private: private:
void setup(real_t p_radius); void setup(real_t p_radius);
@ -133,7 +137,7 @@ public:
virtual void set_data(const Variant &p_data); virtual void set_data(const Variant &p_data);
virtual Variant get_data() const; virtual Variant get_data() const;
virtual PhysicsServer::ShapeType get_type() const; virtual PhysicsServer::ShapeType get_type() const;
virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin = 0); virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge = 0);
private: private:
void setup(const Vector3 &p_half_extents); void setup(const Vector3 &p_half_extents);
@ -152,7 +156,7 @@ public:
virtual void set_data(const Variant &p_data); virtual void set_data(const Variant &p_data);
virtual Variant get_data() const; virtual Variant get_data() const;
virtual PhysicsServer::ShapeType get_type() const; virtual PhysicsServer::ShapeType get_type() const;
virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin = 0); virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge = 0);
private: private:
void setup(real_t p_height, real_t p_radius); void setup(real_t p_height, real_t p_radius);
@ -169,7 +173,7 @@ public:
void get_vertices(Vector<Vector3> &out_vertices); void get_vertices(Vector<Vector3> &out_vertices);
virtual Variant get_data() const; virtual Variant get_data() const;
virtual PhysicsServer::ShapeType get_type() const; virtual PhysicsServer::ShapeType get_type() const;
virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin = 0); virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge = 0);
private: private:
void setup(const Vector<Vector3> &p_vertices); void setup(const Vector<Vector3> &p_vertices);
@ -187,7 +191,7 @@ public:
virtual void set_data(const Variant &p_data); virtual void set_data(const Variant &p_data);
virtual Variant get_data() const; virtual Variant get_data() const;
virtual PhysicsServer::ShapeType get_type() const; virtual PhysicsServer::ShapeType get_type() const;
virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin = 0); virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge = 0);
private: private:
void setup(PoolVector<Vector3> p_faces); void setup(PoolVector<Vector3> p_faces);
@ -207,7 +211,7 @@ public:
virtual void set_data(const Variant &p_data); virtual void set_data(const Variant &p_data);
virtual Variant get_data() const; virtual Variant get_data() const;
virtual PhysicsServer::ShapeType get_type() const; virtual PhysicsServer::ShapeType get_type() const;
virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin = 0); virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge = 0);
private: private:
void setup(PoolVector<real_t> &p_heights, int p_width, int p_depth, real_t p_min_height, real_t p_max_height); void setup(PoolVector<real_t> &p_heights, int p_width, int p_depth, real_t p_min_height, real_t p_max_height);
@ -224,7 +228,7 @@ public:
virtual void set_data(const Variant &p_data); virtual void set_data(const Variant &p_data);
virtual Variant get_data() const; virtual Variant get_data() const;
virtual PhysicsServer::ShapeType get_type() const; virtual PhysicsServer::ShapeType get_type() const;
virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_margin = 0); virtual btCollisionShape *create_bt_shape(const btVector3 &p_implicit_scale, real_t p_extra_edge = 0);
private: private:
void setup(real_t p_length, bool p_slips_on_slope); void setup(real_t p_length, bool p_slips_on_slope);

View File

@ -50,6 +50,15 @@ void Shape::add_vertices_to_array(PoolVector<Vector3> &array, const Transform &p
} }
} }
real_t Shape::get_margin() const {
return margin;
}
void Shape::set_margin(real_t p_margin) {
margin = p_margin;
PhysicsServer::get_singleton()->shape_set_margin(shape, margin);
}
Ref<ArrayMesh> Shape::get_debug_mesh() { Ref<ArrayMesh> Shape::get_debug_mesh() {
if (debug_mesh_cache.is_valid()) if (debug_mesh_cache.is_valid())
@ -87,12 +96,22 @@ Ref<ArrayMesh> Shape::get_debug_mesh() {
return debug_mesh_cache; return debug_mesh_cache;
} }
Shape::Shape() { void Shape::_bind_methods() {
ClassDB::bind_method(D_METHOD("set_margin", "margin"), &Shape::set_margin);
ClassDB::bind_method(D_METHOD("get_margin"), &Shape::get_margin);
ADD_PROPERTY(PropertyInfo(Variant::REAL, "margin", PROPERTY_HINT_RANGE, "0.04,10,0.01"), "set_margin", "get_margin");
}
Shape::Shape() :
margin(0.04) {
ERR_PRINT("Constructor must not be called!"); ERR_PRINT("Constructor must not be called!");
} }
Shape::Shape(RID p_shape) { Shape::Shape(RID p_shape) :
margin(0.04) {
shape = p_shape; shape = p_shape;
} }

View File

@ -40,10 +40,13 @@ class Shape : public Resource {
OBJ_SAVE_TYPE(Shape); OBJ_SAVE_TYPE(Shape);
RES_BASE_EXTENSION("shape"); RES_BASE_EXTENSION("shape");
RID shape; RID shape;
real_t margin;
Ref<ArrayMesh> debug_mesh_cache; Ref<ArrayMesh> debug_mesh_cache;
protected: protected:
static void _bind_methods();
_FORCE_INLINE_ RID get_shape() const { return shape; } _FORCE_INLINE_ RID get_shape() const { return shape; }
Shape(RID p_shape); Shape(RID p_shape);
@ -55,6 +58,9 @@ public:
void add_vertices_to_array(PoolVector<Vector3> &array, const Transform &p_xform); void add_vertices_to_array(PoolVector<Vector3> &array, const Transform &p_xform);
real_t get_margin() const;
void set_margin(real_t p_margin);
Shape(); Shape();
~Shape(); ~Shape();
}; };

View File

@ -119,6 +119,13 @@ Variant PhysicsServerSW::shape_get_data(RID p_shape) const {
return shape->get_data(); return shape->get_data();
}; };
void PhysicsServerSW::shape_set_margin(RID p_shape, real_t p_margin) {
}
real_t PhysicsServerSW::shape_get_margin(RID p_shape) const {
return 0.0;
}
real_t PhysicsServerSW::shape_get_custom_solver_bias(RID p_shape) const { real_t PhysicsServerSW::shape_get_custom_solver_bias(RID p_shape) const {
const ShapeSW *shape = shape_owner.get(p_shape); const ShapeSW *shape = shape_owner.get(p_shape);
@ -287,6 +294,7 @@ void PhysicsServerSW::area_set_shape(RID p_area, int p_shape_idx, RID p_shape) {
area->set_shape(p_shape_idx, shape); area->set_shape(p_shape_idx, shape);
} }
void PhysicsServerSW::area_set_shape_transform(RID p_area, int p_shape_idx, const Transform &p_transform) { void PhysicsServerSW::area_set_shape_transform(RID p_area, int p_shape_idx, const Transform &p_transform) {
AreaSW *area = area_owner.get(p_area); AreaSW *area = area_owner.get(p_area);

View File

@ -85,6 +85,10 @@ public:
virtual ShapeType shape_get_type(RID p_shape) const; virtual ShapeType shape_get_type(RID p_shape) const;
virtual Variant shape_get_data(RID p_shape) const; virtual Variant shape_get_data(RID p_shape) const;
virtual void shape_set_margin(RID p_shape, real_t p_margin);
virtual real_t shape_get_margin(RID p_shape) const;
virtual real_t shape_get_custom_solver_bias(RID p_shape) const; virtual real_t shape_get_custom_solver_bias(RID p_shape) const;
/* SPACE API */ /* SPACE API */

View File

@ -240,6 +240,10 @@ public:
virtual ShapeType shape_get_type(RID p_shape) const = 0; virtual ShapeType shape_get_type(RID p_shape) const = 0;
virtual Variant shape_get_data(RID p_shape) const = 0; virtual Variant shape_get_data(RID p_shape) const = 0;
virtual void shape_set_margin(RID p_shape, real_t p_margin) = 0;
virtual real_t shape_get_margin(RID p_shape) const = 0;
virtual real_t shape_get_custom_solver_bias(RID p_shape) const = 0; virtual real_t shape_get_custom_solver_bias(RID p_shape) const = 0;
/* SPACE API */ /* SPACE API */