Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[3.x] Expose body_test_motion in 3D physics server #50103

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 17 additions & 0 deletions doc/classes/PhysicsServer.xml
Original file line number Diff line number Diff line change
Expand Up @@ -815,6 +815,23 @@
Sets a body state (see [enum BodyState] constants).
</description>
</method>
<method name="body_test_motion">
<return type="bool">
</return>
<argument index="0" name="body" type="RID">
</argument>
<argument index="1" name="from" type="Transform">
</argument>
<argument index="2" name="motion" type="Vector3">
</argument>
<argument index="3" name="infinite_inertia" type="bool">
</argument>
<argument index="4" name="result" type="PhysicsTestMotionResult" default="null">
</argument>
<description>
Returns [code]true[/code] if a collision would result from moving in the given direction from a given point in space. [PhysicsTestMotionResult] can be passed to return additional information in.
</description>
</method>
<method name="cone_twist_joint_get_param" qualifiers="const">
<return type="float">
</return>
Expand Down
33 changes: 33 additions & 0 deletions doc/classes/PhysicsTestMotionResult.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
<?xml version="1.0" encoding="UTF-8" ?>
<class name="PhysicsTestMotionResult" inherits="Reference" version="3.4">
<brief_description>
</brief_description>
<description>
</description>
<tutorials>
</tutorials>
<methods>
</methods>
<members>
<member name="collider" type="Object" setter="" getter="get_collider">
</member>
<member name="collider_id" type="int" setter="" getter="get_collider_id" default="0">
</member>
<member name="collider_rid" type="RID" setter="" getter="get_collider_rid">
</member>
<member name="collider_shape" type="int" setter="" getter="get_collider_shape" default="0">
</member>
<member name="collider_velocity" type="Vector3" setter="" getter="get_collider_velocity" default="Vector3( 0, 0, 0 )">
</member>
<member name="collision_normal" type="Vector3" setter="" getter="get_collision_normal" default="Vector3( 0, 0, 0 )">
</member>
<member name="collision_point" type="Vector3" setter="" getter="get_collision_point" default="Vector3( 0, 0, 0 )">
</member>
<member name="motion" type="Vector3" setter="" getter="get_motion" default="Vector3( 0, 0, 0 )">
</member>
<member name="motion_remainder" type="Vector3" setter="" getter="get_motion_remainder" default="Vector3( 0, 0, 0 )">
</member>
</members>
<constants>
</constants>
</class>
4 changes: 2 additions & 2 deletions servers/physics_2d/physics_2d_server_sw.h
Original file line number Diff line number Diff line change
Expand Up @@ -246,8 +246,8 @@ class Physics2DServerSW : public Physics2DServer {

virtual void body_set_pickable(RID p_body, bool p_pickable);

virtual bool body_test_motion(RID p_body, const Transform2D &p_from, const Vector2 &p_motion, bool p_infinite_inertia, real_t p_margin = 0.001, MotionResult *r_result = nullptr, bool p_exclude_raycast_shapes = true);
virtual int body_test_ray_separation(RID p_body, const Transform2D &p_transform, bool p_infinite_inertia, Vector2 &r_recover_motion, SeparationResult *r_results, int p_result_max, float p_margin = 0.001);
virtual bool body_test_motion(RID p_body, const Transform2D &p_from, const Vector2 &p_motion, bool p_infinite_inertia, real_t p_margin = 0.08, MotionResult *r_result = nullptr, bool p_exclude_raycast_shapes = true);
virtual int body_test_ray_separation(RID p_body, const Transform2D &p_transform, bool p_infinite_inertia, Vector2 &r_recover_motion, SeparationResult *r_results, int p_result_max, float p_margin = 0.08);

// this function only works on physics process, errors and returns null otherwise
virtual Physics2DDirectBodyState *body_get_direct_state(RID p_body);
Expand Down
4 changes: 2 additions & 2 deletions servers/physics_2d/physics_2d_server_wrap_mt.h
Original file line number Diff line number Diff line change
Expand Up @@ -251,12 +251,12 @@ class Physics2DServerWrapMT : public Physics2DServer {

FUNC2(body_set_pickable, RID, bool);

bool body_test_motion(RID p_body, const Transform2D &p_from, const Vector2 &p_motion, bool p_infinite_inertia, real_t p_margin = 0.001, MotionResult *r_result = nullptr, bool p_exclude_raycast_shapes = true) {
bool body_test_motion(RID p_body, const Transform2D &p_from, const Vector2 &p_motion, bool p_infinite_inertia, real_t p_margin = 0.08, MotionResult *r_result = nullptr, bool p_exclude_raycast_shapes = true) {
ERR_FAIL_COND_V(main_thread != Thread::get_caller_id(), false);
return physics_2d_server->body_test_motion(p_body, p_from, p_motion, p_infinite_inertia, p_margin, r_result, p_exclude_raycast_shapes);
}

int body_test_ray_separation(RID p_body, const Transform2D &p_transform, bool p_infinite_inertia, Vector2 &r_recover_motion, SeparationResult *r_results, int p_result_max, float p_margin = 0.001) {
int body_test_ray_separation(RID p_body, const Transform2D &p_transform, bool p_infinite_inertia, Vector2 &r_recover_motion, SeparationResult *r_results, int p_result_max, float p_margin = 0.08) {
ERR_FAIL_COND_V(main_thread != Thread::get_caller_id(), false);
return physics_2d_server->body_test_ray_separation(p_body, p_transform, p_infinite_inertia, r_recover_motion, r_results, p_result_max, p_margin);
}
Expand Down
11 changes: 5 additions & 6 deletions servers/physics_2d_server.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -438,22 +438,27 @@ void Physics2DShapeQueryResult::_bind_methods() {
Vector2 Physics2DTestMotionResult::get_motion() const {
return result.motion;
}

Vector2 Physics2DTestMotionResult::get_motion_remainder() const {
return result.remainder;
}

Vector2 Physics2DTestMotionResult::get_collision_point() const {
return result.collision_point;
}

Vector2 Physics2DTestMotionResult::get_collision_normal() const {
return result.collision_normal;
}

Vector2 Physics2DTestMotionResult::get_collider_velocity() const {
return result.collider_velocity;
}

ObjectID Physics2DTestMotionResult::get_collider_id() const {
return result.collider_id;
}

RID Physics2DTestMotionResult::get_collider_rid() const {
return result.collider;
}
Expand Down Expand Up @@ -488,12 +493,6 @@ void Physics2DTestMotionResult::_bind_methods() {
ADD_PROPERTY(PropertyInfo(Variant::INT, "collider_shape"), "", "get_collider_shape");
}

Physics2DTestMotionResult::Physics2DTestMotionResult() {
colliding = false;
result.collider_id = 0;
result.collider_shape = 0;
}

///////////////////////////////////////

bool Physics2DServer::_body_test_motion(RID p_body, const Transform2D &p_from, const Vector2 &p_motion, bool p_infinite_inertia, float p_margin, const Ref<Physics2DTestMotionResult> &p_result) {
Expand Down
20 changes: 6 additions & 14 deletions servers/physics_2d_server.h
Original file line number Diff line number Diff line change
Expand Up @@ -491,20 +491,14 @@ class Physics2DServer : public Object {
Vector2 collision_point;
Vector2 collision_normal;
Vector2 collider_velocity;
int collision_local_shape;
ObjectID collider_id;
int collision_local_shape = 0;
ObjectID collider_id = 0;
RID collider;
int collider_shape;
int collider_shape = 0;
Variant collider_metadata;

MotionResult() {
collision_local_shape = 0;
collider_shape = 0;
collider_id = 0;
}
};

virtual bool body_test_motion(RID p_body, const Transform2D &p_from, const Vector2 &p_motion, bool p_infinite_inertia, float p_margin = 0.001, MotionResult *r_result = nullptr, bool p_exclude_raycast_shapes = true) = 0;
virtual bool body_test_motion(RID p_body, const Transform2D &p_from, const Vector2 &p_motion, bool p_infinite_inertia, float p_margin = 0.08, MotionResult *r_result = nullptr, bool p_exclude_raycast_shapes = true) = 0;

struct SeparationResult {
float collision_depth;
Expand All @@ -518,7 +512,7 @@ class Physics2DServer : public Object {
Variant collider_metadata;
};

virtual int body_test_ray_separation(RID p_body, const Transform2D &p_transform, bool p_infinite_inertia, Vector2 &r_recover_motion, SeparationResult *r_results, int p_result_max, float p_margin = 0.001) = 0;
virtual int body_test_ray_separation(RID p_body, const Transform2D &p_transform, bool p_infinite_inertia, Vector2 &r_recover_motion, SeparationResult *r_results, int p_result_max, float p_margin = 0.08) = 0;

/* JOINT API */

Expand Down Expand Up @@ -602,7 +596,7 @@ class Physics2DTestMotionResult : public Reference {
GDCLASS(Physics2DTestMotionResult, Reference);

Physics2DServer::MotionResult result;
bool colliding;
bool colliding = false;
friend class Physics2DServer;

protected:
Expand All @@ -622,8 +616,6 @@ class Physics2DTestMotionResult : public Reference {
RID get_collider_rid() const;
Object *get_collider() const;
int get_collider_shape() const;

Physics2DTestMotionResult();
};

typedef Physics2DServer *(*CreatePhysics2DServerCallback)();
Expand Down
70 changes: 70 additions & 0 deletions servers/physics_server.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -381,8 +381,76 @@ void PhysicsShapeQueryResult::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_result_object_shape", "idx"), &PhysicsShapeQueryResult::get_result_object_shape);
}

///////////////////////////////

Vector3 PhysicsTestMotionResult::get_motion() const {
return result.motion;
}

Vector3 PhysicsTestMotionResult::get_motion_remainder() const {
return result.remainder;
}

Vector3 PhysicsTestMotionResult::get_collision_point() const {
return result.collision_point;
}

Vector3 PhysicsTestMotionResult::get_collision_normal() const {
return result.collision_normal;
}

Vector3 PhysicsTestMotionResult::get_collider_velocity() const {
return result.collider_velocity;
}

ObjectID PhysicsTestMotionResult::get_collider_id() const {
return result.collider_id;
}

RID PhysicsTestMotionResult::get_collider_rid() const {
return result.collider;
}

Object *PhysicsTestMotionResult::get_collider() const {
return ObjectDB::get_instance(result.collider_id);
}

int PhysicsTestMotionResult::get_collider_shape() const {
return result.collider_shape;
}

void PhysicsTestMotionResult::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_motion"), &PhysicsTestMotionResult::get_motion);
ClassDB::bind_method(D_METHOD("get_motion_remainder"), &PhysicsTestMotionResult::get_motion_remainder);
ClassDB::bind_method(D_METHOD("get_collision_point"), &PhysicsTestMotionResult::get_collision_point);
ClassDB::bind_method(D_METHOD("get_collision_normal"), &PhysicsTestMotionResult::get_collision_normal);
ClassDB::bind_method(D_METHOD("get_collider_velocity"), &PhysicsTestMotionResult::get_collider_velocity);
ClassDB::bind_method(D_METHOD("get_collider_id"), &PhysicsTestMotionResult::get_collider_id);
ClassDB::bind_method(D_METHOD("get_collider_rid"), &PhysicsTestMotionResult::get_collider_rid);
ClassDB::bind_method(D_METHOD("get_collider"), &PhysicsTestMotionResult::get_collider);
ClassDB::bind_method(D_METHOD("get_collider_shape"), &PhysicsTestMotionResult::get_collider_shape);

ADD_PROPERTY(PropertyInfo(Variant::VECTOR3, "motion"), "", "get_motion");
ADD_PROPERTY(PropertyInfo(Variant::VECTOR3, "motion_remainder"), "", "get_motion_remainder");
ADD_PROPERTY(PropertyInfo(Variant::VECTOR3, "collision_point"), "", "get_collision_point");
ADD_PROPERTY(PropertyInfo(Variant::VECTOR3, "collision_normal"), "", "get_collision_normal");
ADD_PROPERTY(PropertyInfo(Variant::VECTOR3, "collider_velocity"), "", "get_collider_velocity");
ADD_PROPERTY(PropertyInfo(Variant::INT, "collider_id", PROPERTY_HINT_OBJECT_ID), "", "get_collider_id");
ADD_PROPERTY(PropertyInfo(Variant::_RID, "collider_rid"), "", "get_collider_rid");
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "collider"), "", "get_collider");
ADD_PROPERTY(PropertyInfo(Variant::INT, "collider_shape"), "", "get_collider_shape");
}

///////////////////////////////////////

bool PhysicsServer::_body_test_motion(RID p_body, const Transform &p_from, const Vector3 &p_motion, bool p_infinite_inertia, const Ref<PhysicsTestMotionResult> &p_result) {
MotionResult *r = nullptr;
if (p_result.is_valid()) {
r = p_result->get_result_ptr();
}
return body_test_motion(p_body, p_from, p_motion, p_infinite_inertia, r);
}

void PhysicsServer::_bind_methods() {
#ifndef _3D_DISABLED

Expand Down Expand Up @@ -504,6 +572,8 @@ void PhysicsServer::_bind_methods() {
ClassDB::bind_method(D_METHOD("body_set_ray_pickable", "body", "enable"), &PhysicsServer::body_set_ray_pickable);
ClassDB::bind_method(D_METHOD("body_is_ray_pickable", "body"), &PhysicsServer::body_is_ray_pickable);

ClassDB::bind_method(D_METHOD("body_test_motion", "body", "from", "motion", "infinite_inertia", "result"), &PhysicsServer::_body_test_motion, DEFVAL(Variant()));

ClassDB::bind_method(D_METHOD("body_get_direct_state", "body"), &PhysicsServer::body_get_direct_state);

/* JOINT API */
Expand Down
41 changes: 33 additions & 8 deletions servers/physics_server.h
Original file line number Diff line number Diff line change
Expand Up @@ -214,11 +214,15 @@ class PhysicsShapeQueryResult : public Reference {
PhysicsShapeQueryResult();
};

class PhysicsTestMotionResult;

class PhysicsServer : public Object {
GDCLASS(PhysicsServer, Object);

static PhysicsServer *singleton;

virtual bool _body_test_motion(RID p_body, const Transform &p_from, const Vector3 &p_motion, bool p_infinite_inertia, const Ref<PhysicsTestMotionResult> &p_result = Ref<PhysicsTestMotionResult>());

protected:
static void _bind_methods();

Expand Down Expand Up @@ -479,16 +483,11 @@ class PhysicsServer : public Object {
Vector3 collision_point;
Vector3 collision_normal;
Vector3 collider_velocity;
int collision_local_shape;
ObjectID collider_id;
int collision_local_shape = 0;
ObjectID collider_id = 0;
RID collider;
int collider_shape;
int collider_shape = 0;
Variant collider_metadata;
MotionResult() {
collision_local_shape = 0;
collider_id = 0;
collider_shape = 0;
}
};

virtual bool body_test_motion(RID p_body, const Transform &p_from, const Vector3 &p_motion, bool p_infinite_inertia, MotionResult *r_result = nullptr, bool p_exclude_raycast_shapes = true) = 0;
Expand Down Expand Up @@ -762,6 +761,32 @@ class PhysicsServer : public Object {
~PhysicsServer();
};

class PhysicsTestMotionResult : public Reference {
GDCLASS(PhysicsTestMotionResult, Reference);

PhysicsServer::MotionResult result;
bool colliding = false;
friend class PhysicsServer;

protected:
static void _bind_methods();

public:
PhysicsServer::MotionResult *get_result_ptr() const { return const_cast<PhysicsServer::MotionResult *>(&result); }

//bool is_colliding() const;
Vector3 get_motion() const;
Vector3 get_motion_remainder() const;

Vector3 get_collision_point() const;
Vector3 get_collision_normal() const;
Vector3 get_collider_velocity() const;
ObjectID get_collider_id() const;
RID get_collider_rid() const;
Object *get_collider() const;
int get_collider_shape() const;
};

typedef PhysicsServer *(*CreatePhysicsServerCallback)();

class PhysicsServerManager {
Expand Down
1 change: 1 addition & 0 deletions servers/register_server_types.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -183,6 +183,7 @@ void register_server_types() {
ClassDB::register_virtual_class<PhysicsDirectBodyState>();
ClassDB::register_virtual_class<PhysicsDirectSpaceState>();
ClassDB::register_virtual_class<PhysicsShapeQueryResult>();
ClassDB::register_class<PhysicsTestMotionResult>();

ScriptDebuggerRemote::resource_usage_func = _debugger_get_resource_usage;

Expand Down