diff --git a/.gitignore b/.gitignore
index 6f0d751..e30afbe 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,5 +1,4 @@
# Binaries
-*.os
*.os.tmp
*.o
*.dblite
@@ -10,3 +9,4 @@ bin/addons/godot-box2d/bin/libgodot-box2d.macos.template_release.framework/libgo
.DS_Store
.vscode
+*.os
diff --git a/.gitmodules b/.gitmodules
index 6582456..77fc99c 100644
--- a/.gitmodules
+++ b/.gitmodules
@@ -4,8 +4,8 @@
branch = 4.1
[submodule "box2d"]
path = box2d
- url = https://github.com/appsinacup/box2d
- branch = common-assert-noop
+ url = https://github.com/erincatto/box2c
+ branch = main
[submodule "Godot-Physics-Tests"]
path = Godot-Physics-Tests
url = https://github.com/fabriceci/Godot-Physics-Tests
diff --git a/README.md b/README.md
index abb10d2..45b36c5 100644
--- a/README.md
+++ b/README.md
@@ -7,8 +7,8 @@
-
-
+
+
diff --git a/SConstruct b/SConstruct
index fae82cc..51fcaee 100644
--- a/SConstruct
+++ b/SConstruct
@@ -3,66 +3,22 @@ import os
import sys
env = SConscript("godot-cpp/SConstruct")
-box2d_folder = "box2d/"
-box2d_include = [
- "include/",
- "src/"
-]
-box2d_src = [
- "collision/b2_broad_phase.cpp",
- "collision/b2_chain_shape.cpp",
- "collision/b2_circle_shape.cpp",
- "collision/b2_collide_circle.cpp",
- "collision/b2_collide_edge.cpp",
- "collision/b2_collide_polygon.cpp",
- "collision/b2_collision.cpp",
- "collision/b2_distance.cpp",
- "collision/b2_dynamic_tree.cpp",
- "collision/b2_edge_shape.cpp",
- "collision/b2_polygon_shape.cpp",
- "collision/b2_time_of_impact.cpp",
- "common/b2_block_allocator.cpp",
- "common/b2_draw.cpp",
- "common/b2_math.cpp",
- "common/b2_settings.cpp",
- "common/b2_stack_allocator.cpp",
- "common/b2_timer.cpp",
- "dynamics/b2_body.cpp",
- "dynamics/b2_chain_circle_contact.cpp",
- "dynamics/b2_chain_polygon_contact.cpp",
- "dynamics/b2_circle_contact.cpp",
- "dynamics/b2_contact.cpp",
- "dynamics/b2_contact_manager.cpp",
- "dynamics/b2_contact_solver.cpp",
- "dynamics/b2_distance_joint.cpp",
- "dynamics/b2_edge_circle_contact.cpp",
- "dynamics/b2_edge_polygon_contact.cpp",
- "dynamics/b2_fixture.cpp",
- "dynamics/b2_friction_joint.cpp",
- "dynamics/b2_gear_joint.cpp",
- "dynamics/b2_island.cpp",
- "dynamics/b2_joint.cpp",
- "dynamics/b2_motor_joint.cpp",
- "dynamics/b2_mouse_joint.cpp",
- "dynamics/b2_polygon_circle_contact.cpp",
- "dynamics/b2_polygon_contact.cpp",
- "dynamics/b2_prismatic_joint.cpp",
- "dynamics/b2_pulley_joint.cpp",
- "dynamics/b2_revolute_joint.cpp",
- "dynamics/b2_weld_joint.cpp",
- "dynamics/b2_wheel_joint.cpp",
- "dynamics/b2_world.cpp",
- "dynamics/b2_world_callbacks.cpp",
- "rope/b2_rope.cpp",
- ]
-env.Prepend(CPPPATH=[box2d_folder + folder for folder in box2d_include])
-env.Append(CPPDEFINES="B2_USER_SETTINGS")
+
+env.Append(
+ CPPDEFINES=[
+ "BOX2D_LENGTH_UNIT_PER_METER=100.0",
+ "BOX2D_MAX_POLYGON_VERTICES=64",
+ "BOX2D_AVX2=ON"
+ ]
+)
+
+env.Prepend(CPPPATH=["box2d/extern/simde", "box2d/include"])
# For the reference:
# - CCFLAGS are compilation flags shared between C and C++
# tweak this if you want to use different folders, or more folders, to store your source code in.
env.Append(CPPPATH=["src/"])
sources = [Glob("src/*.cpp"),Glob("src/bodies/*.cpp"),Glob("src/joints/*.cpp"),Glob("src/servers/*.cpp"),Glob("src/shapes/*.cpp"),Glob("src/spaces/*.cpp"),Glob("src/box2d-wrapper/*.cpp")]
-sources.extend([box2d_folder + 'src/' + box2d_src_file for box2d_src_file in box2d_src])
+sources.extend([Glob("box2d/src/*.c")])
if env["platform"] == "macos":
library = env.SharedLibrary(
diff --git a/bin/addons/godot-box2d/godot-box2d.gd b/bin/addons/godot-box2d/godot-box2d.gd
deleted file mode 100644
index 13fff26..0000000
--- a/bin/addons/godot-box2d/godot-box2d.gd
+++ /dev/null
@@ -1,10 +0,0 @@
-@tool
-extends EditorPlugin
-
-
-func _enter_tree():
- ProjectSettings.set_setting("physics/2d/physics_engine", "Box2D")
-
-
-func _exit_tree():
- ProjectSettings.set_setting("physics/2d/physics_engine", "DEFAULT")
diff --git a/bin/addons/godot-box2d/plugin.cfg b/bin/addons/godot-box2d/plugin.cfg
index 5c33b1d..dd1cac5 100644
--- a/bin/addons/godot-box2d/plugin.cfg
+++ b/bin/addons/godot-box2d/plugin.cfg
@@ -3,5 +3,4 @@
name="Godot Box2d"
description="A Box2D physics server for Godot Engine"
version="1.0"
-script="godot-box2d.gd"
author="ughuuu"
diff --git a/box2d b/box2d
index b31e89d..29adfcf 160000
--- a/box2d
+++ b/box2d
@@ -1 +1 @@
-Subproject commit b31e89d5d923b485d72bf58899304a8863e5caa0
+Subproject commit 29adfcfb4dbc371a50e37d8e17b072d990ad7ae6
diff --git a/godot.code-workspace b/godot.code-workspace
index ddb15ea..636b483 100644
--- a/godot.code-workspace
+++ b/godot.code-workspace
@@ -24,5 +24,26 @@
"string_view": "cpp",
"__config": "cpp"
}
+ },
+ "launch": {
+ "version": "0.2.0",
+ "configurations": [
+ {
+ "name": "Launch",
+ "program": "/Users/dragosdaian/Documents/GitHub/godot/bin/godot.macos.editor.arm64",
+ "type": "cppdbg",
+ "request": "launch",
+ "cwd": "/Users/dragosdaian/Documents/GitHub/godot-box2d",
+ "osx": {
+ "MIMode": "lldb"
+ },
+ "args": [
+ "--path",
+ "/Users/dragosdaian/Documents/GitHub/godot-box2d/Godot-Physics-Tests",
+ "--debug-collisions",
+ "test.tscn"
+ ]
+ }
+ ]
}
}
diff --git a/src/b2_user_settings.h b/src/b2_user_settings.h
deleted file mode 100644
index 0de97d5..0000000
--- a/src/b2_user_settings.h
+++ /dev/null
@@ -1,76 +0,0 @@
-#pragma once
-
-#include
-#include
-
-#include
-#include
-#include
-
-#include
-#include
-
-// Tunable Constants
-
-// You can use this to change the length scale used by your game.
-// For example for inches you could use 39.4.
-#define b2_lengthUnitsPerMeter 100.0f
-
-// The maximum number of vertices on a convex polygon. You cannot increase
-// this too much because b2BlockAllocator has a maximum object size.
-#define b2_maxPolygonVertices 64
-
-class Box2DCollisionObject2D;
-class Box2DShape2D;
-
-// You can define this to inject whatever data you want in b2Body
-struct B2_API b2BodyUserData {
- b2BodyUserData() :
- old_linear_velocity(0, 0), old_angular_velocity(0), constant_force(0, 0), constant_torque(0), collision_object(nullptr) {}
-
- // for kinematic body
- godot::Vector2 old_linear_velocity;
- real_t old_angular_velocity;
- godot::Vector2 constant_force;
- real_t constant_torque;
- Box2DCollisionObject2D *collision_object;
-};
-
-// You can define this to inject whatever data you want in b2Fixture
-struct B2_API b2FixtureUserData {
- b2FixtureUserData() :
- shape_idx(-1), transform(), collision_object(nullptr) {}
-
- godot::Transform2D transform;
- int shape_idx;
- Box2DCollisionObject2D *collision_object;
-};
-
-/// You can define this to inject whatever data you want in b2Joint
-struct B2_API b2JointUserData {
- b2JointUserData() :
- pointer(0) {}
-
- uintptr_t pointer; // For legacy compatibility
-};
-
-// Memory Allocation using Godot's functions
-
-inline void *b2Alloc(int32 size) {
- return memalloc(size);
-}
-
-inline void b2Free(void *mem) {
- memfree(mem);
-}
-
-// Default logging function
-B2_API void b2Log_Default(const char *string, va_list args);
-
-// Implement this to use your own logging.
-inline void b2Log(const char *string, ...) {
- va_list args;
- va_start(args, string);
- b2Log_Default(string, args);
- va_end(args);
-}
diff --git a/src/bodies/box2d_area_2d.cpp b/src/bodies/box2d_area_2d.cpp
index d1eeb37..1a2f230 100644
--- a/src/bodies/box2d_area_2d.cpp
+++ b/src/bodies/box2d_area_2d.cpp
@@ -31,7 +31,7 @@ void Box2DArea2D::set_space(Box2DSpace2D *p_space) {
_set_space(p_space);
}
-void Box2DArea2D::on_body_enter(b2Fixture *p_collider_handle, Box2DBody2D *p_body, uint32_t p_body_shape, RID p_body_rid, ObjectID p_body_instance_id, b2Fixture *p_area_collider_handle, uint32_t p_area_shape) {
+void Box2DArea2D::on_body_enter(b2ShapeId p_collider_handle, Box2DBody2D *p_body, uint32_t p_body_shape, RID p_body_rid, ObjectID p_body_instance_id, b2ShapeId p_area_collider_handle, uint32_t p_area_shape) {
ERR_FAIL_COND(!p_body); // Shouldn't happen after removal
// Add to keep track of currently detected bodies
@@ -56,7 +56,7 @@ void Box2DArea2D::on_body_enter(b2Fixture *p_collider_handle, Box2DBody2D *p_bod
}
}
-void Box2DArea2D::on_body_exit(b2Fixture *p_collider_handle, Box2DBody2D *p_body, uint32_t p_body_shape, RID p_body_rid, ObjectID p_body_instance_id, b2Fixture *p_area_collider_handle, uint32_t p_area_shape, bool p_update_detection) {
+void Box2DArea2D::on_body_exit(b2ShapeId p_collider_handle, Box2DBody2D *p_body, uint32_t p_body_shape, RID p_body_rid, ObjectID p_body_instance_id, b2ShapeId p_area_collider_handle, uint32_t p_area_shape, bool p_update_detection) {
if (p_update_detection) {
// Remove from currently detected bodies
auto foundIt = detected_bodies.find(p_body_rid);
@@ -93,7 +93,7 @@ void Box2DArea2D::on_body_exit(b2Fixture *p_collider_handle, Box2DBody2D *p_body
}
}
-void Box2DArea2D::on_area_enter(b2Fixture *p_collider_handle, Box2DArea2D *p_other_area, uint32_t p_other_area_shape, RID p_other_area_rid, ObjectID p_other_area_instance_id, b2Fixture *p_area_collider_handle, uint32_t p_area_shape) {
+void Box2DArea2D::on_area_enter(b2ShapeId p_collider_handle, Box2DArea2D *p_other_area, uint32_t p_other_area_shape, RID p_other_area_rid, ObjectID p_other_area_instance_id, b2ShapeId p_area_collider_handle, uint32_t p_area_shape) {
ERR_FAIL_COND(!p_other_area); // Shouldn't happen after removal
if (area_monitor_callback.is_null()) {
@@ -117,7 +117,7 @@ void Box2DArea2D::on_area_enter(b2Fixture *p_collider_handle, Box2DArea2D *p_oth
}
}
-void Box2DArea2D::on_area_exit(b2Fixture *p_collider_handle, Box2DArea2D *p_other_area, uint32_t p_other_area_shape, RID p_other_area_rid, ObjectID p_other_area_instance_id, b2Fixture *p_area_collider_handle, uint32_t p_area_shape) {
+void Box2DArea2D::on_area_exit(b2ShapeId p_collider_handle, Box2DArea2D *p_other_area, uint32_t p_other_area_shape, RID p_other_area_rid, ObjectID p_other_area_instance_id, b2ShapeId p_area_collider_handle, uint32_t p_area_shape) {
if (area_monitor_callback.is_null()) {
return;
}
diff --git a/src/bodies/box2d_area_2d.h b/src/bodies/box2d_area_2d.h
index 086296d..c36d96f 100644
--- a/src/bodies/box2d_area_2d.h
+++ b/src/bodies/box2d_area_2d.h
@@ -55,11 +55,11 @@ class Box2DArea2D : public Box2DCollisionObject2D {
void _reset_space_override();
public:
- void on_body_enter(b2Fixture *p_collider_handle, Box2DBody2D *p_body, uint32_t p_body_shape, RID p_body_rid, ObjectID p_body_instance_id, b2Fixture *p_area_collider_handle, uint32_t p_area_shape);
- void on_body_exit(b2Fixture *p_collider_handle, Box2DBody2D *p_body, uint32_t p_body_shape, RID p_body_rid, ObjectID p_body_instance_id, b2Fixture *p_area_collider_handle, uint32_t p_area_shape, bool p_update_detection = true);
+ void on_body_enter(b2ShapeId p_collider_handle, Box2DBody2D *p_body, uint32_t p_body_shape, RID p_body_rid, ObjectID p_body_instance_id, b2ShapeId p_area_collider_handle, uint32_t p_area_shape);
+ void on_body_exit(b2ShapeId p_collider_handle, Box2DBody2D *p_body, uint32_t p_body_shape, RID p_body_rid, ObjectID p_body_instance_id, b2ShapeId p_area_collider_handle, uint32_t p_area_shape, bool p_update_detection = true);
- void on_area_enter(b2Fixture *p_collider_handle, Box2DArea2D *p_other_area, uint32_t p_other_area_shape, RID p_other_area_rid, ObjectID p_other_area_instance_id, b2Fixture *p_area_collider_handle, uint32_t p_area_shape);
- void on_area_exit(b2Fixture *p_collider_handle, Box2DArea2D *p_other_area, uint32_t p_other_area_shape, RID p_other_area_rid, ObjectID p_other_area_instance_id, b2Fixture *p_area_collider_handle, uint32_t p_area_shape);
+ void on_area_enter(b2ShapeId p_collider_handle, Box2DArea2D *p_other_area, uint32_t p_other_area_shape, RID p_other_area_rid, ObjectID p_other_area_instance_id, b2ShapeId p_area_collider_handle, uint32_t p_area_shape);
+ void on_area_exit(b2ShapeId p_collider_handle, Box2DArea2D *p_other_area, uint32_t p_other_area_shape, RID p_other_area_rid, ObjectID p_other_area_instance_id, b2ShapeId p_area_collider_handle, uint32_t p_area_shape);
void update_area_override();
bool has_any_space_override() const;
diff --git a/src/bodies/box2d_body_2d.cpp b/src/bodies/box2d_body_2d.cpp
index 662a11d..511b4de 100644
--- a/src/bodies/box2d_body_2d.cpp
+++ b/src/bodies/box2d_body_2d.cpp
@@ -4,11 +4,7 @@
#include "box2d_direct_body_state_2d.h"
void Box2DBody2D::_mass_properties_changed() {
- if (!get_space()) {
- return;
- }
-
- if (mode < PhysicsServer2D::BODY_MODE_RIGID) {
+ if (!get_space() || mode < PhysicsServer2D::BODY_MODE_RIGID) {
return;
}
@@ -22,26 +18,20 @@ void Box2DBody2D::_mass_properties_changed() {
}
void Box2DBody2D::_apply_mass_properties(bool force_update) {
- ERR_FAIL_COND(!get_space());
+ if (mode < PhysicsServer2D::BODY_MODE_RIGID || !box2d::is_handle_valid(body_handle)) {
+ return;
+ }
- ERR_FAIL_COND(mode < PhysicsServer2D::BODY_MODE_RIGID);
real_t inertia_value = (mode == PhysicsServer2D::BODY_MODE_RIGID_LINEAR) ? 0.0 : inertia;
-
- b2Vec2 com = { center_of_mass.x, center_of_mass.y };
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
-
- // Force update means local properties will be re-calculated internally,
- // it's needed for applying forces right away (otherwise it's updated on next step)
- box2d::body_set_mass_properties(space_handle, body_handle, mass, inertia_value, com, false, force_update);
+ box2d::body_set_mass_properties(body_handle, mass, inertia_value, { center_of_mass.x, center_of_mass.y });
}
void Box2DBody2D::update_mass_properties(bool force_update) {
- mass_properties_update_list.remove_from_list();
+ if (mode < PhysicsServer2D::BODY_MODE_RIGID) {
+ return;
+ }
- ERR_FAIL_COND(mode < PhysicsServer2D::BODY_MODE_RIGID);
+ mass_properties_update_list.remove_from_list();
real_t total_area = 0;
for (int i = 0; i < get_shape_count(); i++) {
@@ -138,12 +128,10 @@ void Box2DBody2D::set_active(bool p_active) {
}
void Box2DBody2D::set_can_sleep(bool p_can_sleep) {
- ERR_FAIL_COND(!get_space());
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- box2d::body_set_can_sleep(space_handle, body_handle, p_can_sleep);
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
+ box2d::body_set_can_sleep(body_handle, p_can_sleep);
}
void Box2DBody2D::on_marked_active() {
@@ -151,7 +139,7 @@ void Box2DBody2D::on_marked_active() {
ERR_FAIL_COND(!get_space());
// TODO: Check how that happens, probably not good for performance
- //ERR_FAIL_COND(mode == PhysicsServer2D::BODY_MODE_STATIC);
+ ERR_FAIL_COND(mode == PhysicsServer2D::BODY_MODE_STATIC);
if (mode == PhysicsServer2D::BODY_MODE_STATIC) {
return;
}
@@ -199,18 +187,13 @@ void Box2DBody2D::set_param(PhysicsServer2D::BodyParameter p_param, const Varian
} else {
friction = p_value;
}
-
- if (!get_space()) {
- return;
- }
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
box2d::Material mat;
mat.friction = friction;
mat.restitution = bounce;
- box2d::body_update_material(space_handle, body_handle, &mat);
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
+ box2d::body_update_material(body_handle, mat);
} break;
case PhysicsServer2D::BODY_PARAM_MASS: {
real_t mass_value = p_value;
@@ -346,14 +329,14 @@ void Box2DBody2D::set_mode(PhysicsServer2D::BodyMode p_mode) {
if (get_space()) {
switch (p_mode) {
case PhysicsServer2D::BODY_MODE_KINEMATIC: {
- box2d::body_change_mode(get_space()->get_handle(), get_body_handle(), b2BodyType::b2_kinematicBody, true, false);
+ box2d::body_change_mode(get_body_handle(), b2BodyType::b2_kinematicBody, false);
} break;
case PhysicsServer2D::BODY_MODE_STATIC: {
- box2d::body_change_mode(get_space()->get_handle(), get_body_handle(), b2BodyType::b2_staticBody, true, false);
+ box2d::body_change_mode(get_body_handle(), b2BodyType::b2_staticBody, false);
} break;
case PhysicsServer2D::BODY_MODE_RIGID:
case PhysicsServer2D::BODY_MODE_RIGID_LINEAR: {
- box2d::body_change_mode(get_space()->get_handle(), get_body_handle(), b2BodyType::b2_dynamicBody, true, p_mode == PhysicsServer2D::BODY_MODE_RIGID_LINEAR);
+ box2d::body_change_mode(get_body_handle(), b2BodyType::b2_dynamicBody, p_mode == PhysicsServer2D::BODY_MODE_RIGID_LINEAR);
} break;
}
}
@@ -398,7 +381,7 @@ void Box2DBody2D::_shapes_changed() {
void Box2DBody2D::set_state(PhysicsServer2D::BodyState p_state, const Variant &p_variant) {
switch (p_state) {
case PhysicsServer2D::BODY_STATE_TRANSFORM: {
- set_transform(p_variant, true);
+ set_transform(p_variant);
} break;
case PhysicsServer2D::BODY_STATE_LINEAR_VELOCITY: {
set_linear_velocity(p_variant);
@@ -460,20 +443,16 @@ Variant Box2DBody2D::get_state(PhysicsServer2D::BodyState p_state) const {
}
void Box2DBody2D::set_continuous_collision_detection_mode(PhysicsServer2D::CCDMode p_mode) {
+ if (!box2d::is_handle_valid(body_handle) || mode < PhysicsServer2D::BODY_MODE_RIGID) {
+ return;
+ }
if (ccd_mode == p_mode) {
return;
}
- ERR_FAIL_COND(mode < PhysicsServer2D::BODY_MODE_RIGID);
-
ccd_mode = p_mode;
- if (get_space()) {
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- box2d::body_set_ccd_enabled(space_handle, body_handle, ccd_mode != PhysicsServer2D::CCD_MODE_DISABLED);
- }
+ box2d::body_set_ccd_enabled(body_handle, ccd_mode != PhysicsServer2D::CCD_MODE_DISABLED);
}
void Box2DBody2D::_init_material(box2d::Material &mat) const {
@@ -483,15 +462,14 @@ void Box2DBody2D::_init_material(box2d::Material &mat) const {
void Box2DBody2D::_init_collider(box2d::FixtureHandle collider_handle) const {
ERR_FAIL_COND(!get_space());
- b2World *space_handle = get_space()->get_handle();
+ b2WorldId space_handle = get_space()->get_handle();
ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
// Send contact infos for dynamic bodies
if (mode >= PhysicsServer2D::BODY_MODE_KINEMATIC) {
// Only send contacts if contact monitor is enabled
bool send_contacts = can_report_contacts();
- // TODO set contacts callback only if needed
- //box2d::collider_set_contact_force_events_enabled(space_handle, collider_handle, send_contacts);
+ box2d::collider_set_contact_force_events_enabled(collider_handle, send_contacts);
}
}
@@ -574,11 +552,10 @@ void Box2DBody2D::set_space(Box2DSpace2D *p_space) {
apply_torque(torque_force);
torque_force = 0.0;
}
- b2World *space_handle = get_space()->get_handle();
box2d::Material mat;
mat.friction = friction;
mat.restitution = bounce;
- box2d::body_update_material(space_handle, body_handle, &mat);
+ box2d::body_update_material(body_handle, mat);
}
}
}
@@ -650,13 +627,11 @@ void Box2DBody2D::apply_central_impulse(const Vector2 &p_impulse) {
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
b2Vec2 impulse = { p_impulse.x, p_impulse.y };
- box2d::body_apply_impulse(space_handle, body_handle, impulse);
+ box2d::body_apply_impulse(body_handle, impulse);
}
void Box2DBody2D::apply_impulse(const Vector2 &p_impulse, const Vector2 &p_position) {
@@ -670,33 +645,26 @@ void Box2DBody2D::apply_impulse(const Vector2 &p_impulse, const Vector2 &p_posit
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
b2Vec2 impulse = { p_impulse.x, p_impulse.y };
Vector2 point_centered = get_transform().get_origin() + p_position + get_center_of_mass();
b2Vec2 pos = { point_centered.x, point_centered.y };
- box2d::body_apply_impulse_at_point(space_handle, body_handle, impulse, pos);
+ box2d::body_apply_impulse_at_point(body_handle, impulse, pos);
}
void Box2DBody2D::apply_torque_impulse(real_t p_torque) {
torque += p_torque;
- if (!get_space()) {
- return;
- }
if (mass_properties_update_list.in_list()) {
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- box2d::body_apply_torque_impulse(space_handle, body_handle, p_torque);
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
+ box2d::body_apply_torque_impulse(body_handle, p_torque);
}
void Box2DBody2D::apply_central_force(const Vector2 &p_force) {
@@ -709,15 +677,14 @@ void Box2DBody2D::apply_central_force(const Vector2 &p_force) {
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
// Note: using last delta assuming constant physics time
real_t last_delta = get_space()->get_last_step();
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
b2Vec2 force = { p_force.x * last_delta, p_force.y * last_delta };
- box2d::body_apply_impulse(space_handle, body_handle, force);
+ box2d::body_apply_impulse(body_handle, force);
}
void Box2DBody2D::apply_force(const Vector2 &p_force, const Vector2 &p_position) {
@@ -732,15 +699,15 @@ void Box2DBody2D::apply_force(const Vector2 &p_force, const Vector2 &p_position)
update_mass_properties(true);
}
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
// Note: using last delta assuming constant physics time
real_t last_delta = get_space()->get_last_step();
b2Vec2 force = { p_force.x * last_delta, p_force.y * last_delta };
Vector2 point_centered = get_transform().get_origin() + p_position + get_center_of_mass();
b2Vec2 pos = { point_centered.x, point_centered.y };
- box2d::body_apply_impulse_at_point(space_handle, body_handle, force, pos);
+ box2d::body_apply_impulse_at_point(body_handle, force, pos);
}
void Box2DBody2D::apply_torque(real_t p_torque) {
@@ -753,140 +720,99 @@ void Box2DBody2D::apply_torque(real_t p_torque) {
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
// Note: using last delta assuming constant physics time
real_t last_delta = get_space()->get_last_step();
- box2d::body_apply_torque_impulse(space_handle, body_handle, p_torque * last_delta);
+ box2d::body_apply_torque_impulse(body_handle, p_torque * last_delta);
}
void Box2DBody2D::add_constant_central_force(const Vector2 &p_force) {
constant_force += p_force;
- if (!get_space()) {
- return;
- }
if (mass_properties_update_list.in_list()) {
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
b2Vec2 force = { p_force.x, p_force.y };
- box2d::body_add_force(space_handle, body_handle, force);
+ box2d::body_add_force(body_handle, force);
}
void Box2DBody2D::add_constant_force(const Vector2 &p_force, const Vector2 &p_position) {
constant_torque += (p_position - get_center_of_mass()).cross(p_force);
constant_force += p_force;
- if (!get_space()) {
- return;
- }
if (mass_properties_update_list.in_list()) {
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
b2Vec2 force = { p_force.x, p_force.y };
b2Vec2 pos = { p_position.x, p_position.y };
- box2d::body_add_force(space_handle, body_handle, force);
- box2d::body_add_torque(space_handle, body_handle, (p_position - get_center_of_mass()).cross(p_force));
+ box2d::body_add_force(body_handle, force);
+ box2d::body_add_torque(body_handle, (p_position - get_center_of_mass()).cross(p_force));
}
void Box2DBody2D::add_constant_torque(real_t p_torque) {
constant_torque += p_torque;
- if (!get_space()) {
- return;
- }
-
if (mass_properties_update_list.in_list()) {
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- box2d::body_add_torque(space_handle, body_handle, p_torque);
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
+ box2d::body_add_torque(body_handle, p_torque);
}
void Box2DBody2D::set_constant_force(const Vector2 &p_force) {
constant_force = p_force;
- if (!get_space()) {
- return;
- }
-
if (mass_properties_update_list.in_list()) {
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
b2Vec2 force = { p_force.x, p_force.y };
- box2d::body_reset_forces(space_handle, body_handle);
- box2d::body_add_force(space_handle, body_handle, force);
+ box2d::body_reset_forces(body_handle);
+ box2d::body_add_force(body_handle, force);
}
Vector2 Box2DBody2D::get_constant_force() const {
- if (!get_space()) {
+ if (!box2d::is_handle_valid(body_handle)) {
return constant_force;
}
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND_V(!box2d::is_handle_valid(space_handle), Vector2());
-
- ERR_FAIL_COND_V(!box2d::is_handle_valid(body_handle), Vector2());
-
- b2Vec2 force = box2d::body_get_constant_force(space_handle, body_handle);
+ b2Vec2 force = box2d::body_get_constant_force(body_handle);
return Vector2(force.x, force.y);
}
void Box2DBody2D::set_constant_torque(real_t p_torque) {
constant_torque = p_torque;
- if (!get_space()) {
- return;
- }
-
if (mass_properties_update_list.in_list()) {
// Force update internal mass properties to calculate proper impulse
update_mass_properties(true);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- box2d::body_reset_torques(space_handle, body_handle);
- box2d::body_add_torque(space_handle, body_handle, p_torque);
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
+ box2d::body_reset_torques(body_handle);
+ box2d::body_add_torque(body_handle, p_torque);
}
real_t Box2DBody2D::get_constant_torque() const {
- if (!get_space()) {
+ if (!box2d::is_handle_valid(body_handle)) {
return constant_torque;
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND_V(!box2d::is_handle_valid(space_handle), 0.0);
-
- ERR_FAIL_COND_V(!box2d::is_handle_valid(body_handle), 0.0);
-
- return box2d::body_get_constant_torque(space_handle, body_handle);
+ return box2d::body_get_constant_torque(body_handle);
}
void Box2DBody2D::wakeup() {
@@ -894,28 +820,18 @@ void Box2DBody2D::wakeup() {
if (mode == PhysicsServer2D::BODY_MODE_STATIC) {
return;
}
-
- if (!get_space()) {
+ if (!box2d::is_handle_valid(body_handle)) {
return;
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- box2d::body_wake_up(space_handle, body_handle, true);
+ box2d::body_wake_up(body_handle);
}
void Box2DBody2D::force_sleep() {
sleep = true;
- if (!get_space() || !can_sleep) {
+ if (!box2d::is_handle_valid(body_handle)) {
return;
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- box2d::body_force_sleep(space_handle, body_handle);
+ box2d::body_force_sleep(body_handle);
}
Box2DDirectBodyState2D *Box2DBody2D::get_direct_state() {
@@ -958,30 +874,18 @@ void Box2DBody2D::set_linear_velocity(const Vector2 &p_linear_velocity) {
if (mode == PhysicsServer2D::BODY_MODE_STATIC) {
return;
}
-
- if (!get_space()) {
+ if (!box2d::is_handle_valid(body_handle)) {
return;
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- // TODO: apply delta
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
b2Vec2 velocity = { linear_velocity.x, linear_velocity.y };
- box2d::body_set_linear_velocity(space_handle, body_handle, velocity);
+ box2d::body_set_linear_velocity(body_handle, velocity);
}
Vector2 Box2DBody2D::get_linear_velocity() const {
- if (!get_space()) {
+ if (!box2d::is_handle_valid(body_handle)) {
return linear_velocity;
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND_V(!box2d::is_handle_valid(space_handle), Vector2());
-
- ERR_FAIL_COND_V(!box2d::is_handle_valid(body_handle), Vector2());
- b2Vec2 vel = box2d::body_get_linear_velocity(space_handle, body_handle);
+ b2Vec2 vel = box2d::body_get_linear_velocity(body_handle);
return Vector2(vel.x, vel.y);
}
@@ -991,32 +895,17 @@ Vector2 Box2DBody2D::get_static_linear_velocity() const {
void Box2DBody2D::set_angular_velocity(real_t p_angular_velocity) {
angular_velocity = p_angular_velocity;
- if (mode == PhysicsServer2D::BODY_MODE_STATIC) {
- return;
- }
-
- if (!get_space()) {
+ if (mode == PhysicsServer2D::BODY_MODE_STATIC || !box2d::is_handle_valid(body_handle)) {
return;
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- // TODO: apply delta
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- box2d::body_set_angular_velocity(space_handle, body_handle, angular_velocity);
+ box2d::body_set_angular_velocity(body_handle, angular_velocity);
}
real_t Box2DBody2D::get_angular_velocity() const {
- if (!get_space()) {
+ if (!get_space() || !box2d::is_handle_valid(body_handle)) {
return angular_velocity;
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND_V(!box2d::is_handle_valid(space_handle), 0.0f);
-
- ERR_FAIL_COND_V(!box2d::is_handle_valid(body_handle), 0.0f);
- return box2d::body_get_angular_velocity(space_handle, body_handle);
+ return box2d::body_get_angular_velocity(body_handle);
}
real_t Box2DBody2D::get_static_angular_velocity() const {
@@ -1033,12 +922,10 @@ void Box2DBody2D::_apply_linear_damping(real_t new_value, bool apply_default) {
if (apply_default) {
total_linear_damping += (real_t)get_space()->get_default_area_param(PhysicsServer2D::AREA_PARAM_LINEAR_DAMP);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- box2d::body_set_linear_damping(space_handle, body_handle, total_linear_damping);
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
+ box2d::body_set_linear_damping(body_handle, total_linear_damping);
}
void Box2DBody2D::_apply_angular_damping(real_t new_value, bool apply_default) {
@@ -1051,24 +938,20 @@ void Box2DBody2D::_apply_angular_damping(real_t new_value, bool apply_default) {
if (apply_default) {
total_angular_damping += (real_t)get_space()->get_default_area_param(PhysicsServer2D::AREA_PARAM_ANGULAR_DAMP);
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- box2d::body_set_angular_damping(space_handle, body_handle, total_angular_damping);
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
+ box2d::body_set_angular_damping(body_handle, total_angular_damping);
}
void Box2DBody2D::_apply_gravity_scale(real_t new_value) {
if (!get_space()) {
return;
}
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- box2d::body_set_gravity_scale(space_handle, body_handle, new_value, true);
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
+ box2d::body_set_gravity_scale(body_handle, new_value);
}
void Box2DBody2D::update_area_override() {
@@ -1202,16 +1085,13 @@ void Box2DBody2D::update_area_override() {
void Box2DBody2D::update_gravity(real_t p_step) {
ERR_FAIL_COND(!using_area_gravity);
- ERR_FAIL_COND(!get_space());
Vector2 gravity_impulse = total_gravity * mass * p_step;
-
- b2World *space_handle = get_space()->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
- ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
+ if (!box2d::is_handle_valid(body_handle)) {
+ return;
+ }
b2Vec2 impulse = { gravity_impulse.x, gravity_impulse.y };
- box2d::body_apply_impulse(space_handle, body_handle, impulse);
+ box2d::body_apply_impulse(body_handle, impulse);
}
Rect2 Box2DBody2D::get_aabb() {
diff --git a/src/bodies/box2d_collision_object_2d.cpp b/src/bodies/box2d_collision_object_2d.cpp
index d0a05d0..a2a666e 100644
--- a/src/bodies/box2d_collision_object_2d.cpp
+++ b/src/bodies/box2d_collision_object_2d.cpp
@@ -1,6 +1,5 @@
#include "box2d_collision_object_2d.h"
-#include "../b2_user_settings.h"
#include "../servers/box2d_physics_server_2d.h"
#include "../spaces/box2d_space_2d.h"
@@ -20,10 +19,6 @@ void Box2DCollisionObject2D::add_shape(Box2DShape2D *p_shape, const Transform2D
shapes.push_back(shape);
p_shape->add_owner(this);
- //if (!pending_shape_update_list.in_list()) {
- // Box2DPhysicsServer2D::singleton->pending_shape_update_list.add(&pending_shape_update_list);
- //}
-
if (space) {
_shapes_changed();
}
@@ -46,10 +41,6 @@ void Box2DCollisionObject2D::set_shape(int p_index, Box2DShape2D *p_shape) {
_update_shape_transform(shape);
}
- //if (!pending_shape_update_list.in_list()) {
- // Box2DPhysicsServer2D::singleton->pending_shape_update_list.add(&pending_shape_update_list);
- //}
-
if (space) {
_shapes_changed();
}
@@ -63,10 +54,6 @@ void Box2DCollisionObject2D::set_shape_transform(int p_index, const Transform2D
_update_shape_transform(shape);
- //if (!pending_shape_update_list.in_list()) {
- // Box2DPhysicsServer2D::singleton->pending_shape_update_list.add(&pending_shape_update_list);
- //}
-
if (space) {
_shapes_changed();
}
@@ -89,22 +76,6 @@ void Box2DCollisionObject2D::set_shape_disabled(int p_index, bool p_disabled) {
_update_shape_transform(shape);
}
- // if (p_disabled && shape.bpid != 0) {
- // space->get_broadphase()->remove(shape.bpid);
- // shape.bpid = 0;
- // if (!pending_shape_update_list.in_list()) {
- // Box2DPhysicsServer2D::singleton->pending_shape_update_list.add(&pending_shape_update_list);
- // }
- // } else if (!p_disabled && shape.bpid == 0) {
- // if (!pending_shape_update_list.in_list()) {
- // Box2DPhysicsServer2D::singleton->pending_shape_update_list.add(&pending_shape_update_list);
- // }
- // }
-
- //if (!pending_shape_update_list.in_list()) {
- // Box2DPhysicsServer2D::singleton->pending_shape_update_list.add(&pending_shape_update_list);
- //}
-
if (space) {
_shapes_changed();
}
@@ -133,10 +104,6 @@ void Box2DCollisionObject2D::remove_shape(int p_index) {
shape.shape->remove_owner(this);
shapes.remove_at(p_index);
- //if (!pending_shape_update_list.in_list()) {
- // Box2DPhysicsServer2D::singleton->pending_shape_update_list.add(&pending_shape_update_list);
- //}
-
if (space) {
_shapes_changed();
}
@@ -146,17 +113,10 @@ void Box2DCollisionObject2D::_unregister_shapes() {
}
void Box2DCollisionObject2D::_update_transform() {
- if (!space) {
- return;
- }
-
- b2World *space_handle = space->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
- b2Vec2 position = box2d::body_get_position(space_handle, body_handle);
- real_t angle = box2d::body_get_angle(space_handle, body_handle);
+ b2Vec2 position = box2d::body_get_position(body_handle);
+ real_t angle = box2d::body_get_angle(body_handle);
transform.set_origin(Vector2(position.x, position.y));
transform.set_rotation(angle);
@@ -164,12 +124,12 @@ void Box2DCollisionObject2D::_update_transform() {
inv_transform = transform.affine_inverse();
}
-void Box2DCollisionObject2D::set_transform(const Transform2D &p_transform, bool wake_up) {
+void Box2DCollisionObject2D::set_transform(const Transform2D &p_transform) {
transform = p_transform;
inv_transform = transform.affine_inverse();
if (space) {
- b2World *space_handle = space->get_handle();
+ b2WorldId space_handle = space->get_handle();
ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
@@ -177,7 +137,7 @@ void Box2DCollisionObject2D::set_transform(const Transform2D &p_transform, bool
const Vector2 &origin = transform.get_origin();
b2Vec2 position = { origin.x, origin.y };
real_t rotation = transform.get_rotation();
- box2d::body_set_transform(space_handle, body_handle, position, rotation, wake_up, space->get_last_step());
+ box2d::body_set_transform(body_handle, position, rotation, space->get_last_step());
for (uint32_t i = 0; i < shapes.size(); i++) {
Shape &shape = shapes[i];
@@ -195,7 +155,7 @@ void Box2DCollisionObject2D::_create_shape(Shape &shape, uint32_t p_shape_index)
return;
}
- b2World *space_handle = space->get_handle();
+ b2WorldId space_handle = space->get_handle();
ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
ERR_FAIL_COND(box2d::is_handle_valid(shape.collider_handle));
@@ -206,12 +166,12 @@ void Box2DCollisionObject2D::_create_shape(Shape &shape, uint32_t p_shape_index)
box2d::ShapeHandle shape_handle = shape.shape->get_box2d_shape();
ERR_FAIL_COND(!box2d::is_handle_valid(shape_handle));
- b2FixtureUserData user_data;
- set_collider_user_data(user_data, p_shape_index);
+ b2FixtureUserData *user_data = memnew(b2FixtureUserData);
+ set_collider_user_data(*user_data, p_shape_index);
switch (type) {
case TYPE_BODY: {
- shape.collider_handle = box2d::collider_create_solid(space_handle, shape_handle, &mat, body_handle, user_data);
+ shape.collider_handle = box2d::collider_create_solid(space_handle, shape_handle, mat, body_handle, user_data);
} break;
case TYPE_AREA: {
shape.collider_handle = box2d::collider_create_sensor(space_handle, shape_handle, body_handle, user_data);
@@ -226,19 +186,15 @@ void Box2DCollisionObject2D::_destroy_shape(Shape &shape, uint32_t p_shape_index
if (!space) {
return;
}
-
- b2World *space_handle = space->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
ERR_FAIL_COND(!box2d::is_handle_valid(shape.collider_handle));
if (area_detection_counter > 0) {
// Keep track of body information for delayed removal
- for (int i = 0; i < shape.collider_handle.count; i++) {
+ for (int i = 0; i < shape.collider_handle.handles.size(); i++) {
space->add_removed_collider(shape.collider_handle.handles[i], this, p_shape_index);
}
}
- box2d::collider_destroy(space_handle, shape.collider_handle);
+ box2d::collider_destroy(shape.collider_handle);
shape.collider_handle = box2d::invalid_fixture_handle(); // collider_handle = box2d ID
}
@@ -247,7 +203,7 @@ void Box2DCollisionObject2D::_update_shape_transform(const Shape &shape) {
return;
}
- b2World *space_handle = space->get_handle();
+ b2WorldId space_handle = space->get_handle();
ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
@@ -261,9 +217,6 @@ void Box2DCollisionObject2D::_update_shape_transform(const Shape &shape) {
void Box2DCollisionObject2D::_set_space(Box2DSpace2D *p_space) {
if (space) {
- b2World *space_handle = space->get_handle();
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
-
ERR_FAIL_COND(!box2d::is_handle_valid(body_handle));
for (uint32_t i = 0; i < shapes.size(); i++) {
@@ -275,7 +228,7 @@ void Box2DCollisionObject2D::_set_space(Box2DSpace2D *p_space) {
_destroy_shape(shape, i);
}
// This call also destroys the colliders
- box2d::body_destroy(space_handle, body_handle);
+ box2d::body_destroy(body_handle);
body_handle = box2d::invalid_body_handle();
// Reset area detection counter to keep it consistent for new detections
@@ -285,13 +238,13 @@ void Box2DCollisionObject2D::_set_space(Box2DSpace2D *p_space) {
space = p_space;
if (space) {
- b2World *space_handle = space->get_handle();
+ b2WorldId space_handle = space->get_handle();
ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
ERR_FAIL_COND(box2d::is_handle_valid(body_handle));
- b2BodyUserData user_data;
- set_body_user_data(user_data);
+ b2BodyUserData *user_data = memnew(b2BodyUserData);
+ set_body_user_data(*user_data);
b2Vec2 position = { transform.get_origin().x, transform.get_origin().y };
real_t angle = transform.get_rotation();
@@ -303,8 +256,8 @@ void Box2DCollisionObject2D::_set_space(Box2DSpace2D *p_space) {
body_handle = box2d::body_create(space_handle, position, angle, user_data, b2BodyType::b2_dynamicBody);
}
if (type == TYPE_AREA) {
- box2d::body_set_can_sleep(space_handle, body_handle, false);
- box2d::body_set_gravity_scale(space_handle, body_handle, 0.0, true);
+ box2d::body_set_can_sleep(body_handle, false);
+ box2d::body_set_gravity_scale(body_handle, 0.0);
}
for (uint32_t i = 0; i < shapes.size(); i++) {
@@ -361,6 +314,5 @@ void Box2DCollisionObject2D::_shape_changed(Box2DShape2D *p_shape) {
}
Box2DCollisionObject2D::Box2DCollisionObject2D(Type p_type) {
- //: pending_shape_update_list(this) {
type = p_type;
}
diff --git a/src/bodies/box2d_collision_object_2d.h b/src/bodies/box2d_collision_object_2d.h
index 3430219..1923dd0 100644
--- a/src/bodies/box2d_collision_object_2d.h
+++ b/src/bodies/box2d_collision_object_2d.h
@@ -49,7 +49,7 @@ class Box2DCollisionObject2D : public Box2DShapeOwner2D {
protected:
PhysicsServer2D::BodyMode mode = PhysicsServer2D::BODY_MODE_RIGID;
- b2Body *body_handle = box2d::invalid_body_handle();
+ b2BodyId body_handle = box2d::invalid_body_handle();
uint32_t area_detection_counter = 0;
void _unregister_shapes();
@@ -70,7 +70,7 @@ class Box2DCollisionObject2D : public Box2DShapeOwner2D {
_FORCE_INLINE_ void set_instance_id(const ObjectID &p_instance_id) { instance_id = p_instance_id; }
_FORCE_INLINE_ ObjectID get_instance_id() const { return instance_id; }
- _FORCE_INLINE_ b2Body *get_body_handle() { return body_handle; }
+ _FORCE_INLINE_ b2BodyId get_body_handle() { return body_handle; }
_FORCE_INLINE_ void set_canvas_instance_id(const ObjectID &p_canvas_instance_id) { canvas_instance_id = p_canvas_instance_id; }
_FORCE_INLINE_ ObjectID get_canvas_instance_id() const { return canvas_instance_id; }
@@ -100,7 +100,7 @@ class Box2DCollisionObject2D : public Box2DShapeOwner2D {
return shapes[p_index].xform;
}
- void set_transform(const Transform2D &p_transform, bool wake_up = false);
+ void set_transform(const Transform2D &p_transform);
_FORCE_INLINE_ const Transform2D &get_transform() const { return transform; }
_FORCE_INLINE_ const Transform2D &get_inv_transform() const { return inv_transform; }
diff --git a/src/bodies/box2d_direct_body_state_2d.cpp b/src/bodies/box2d_direct_body_state_2d.cpp
index 034c5d1..8bcd0e9 100644
--- a/src/bodies/box2d_direct_body_state_2d.cpp
+++ b/src/bodies/box2d_direct_body_state_2d.cpp
@@ -57,7 +57,7 @@ double Box2DDirectBodyState2D::_get_angular_velocity() const {
}
void Box2DDirectBodyState2D::_set_transform(const Transform2D &p_transform) {
- body->set_transform(p_transform, true);
+ body->set_transform(p_transform);
}
Transform2D Box2DDirectBodyState2D::_get_transform() const {
diff --git a/src/box2d-wrapper/box2d_wrapper.cpp b/src/box2d-wrapper/box2d_wrapper.cpp
index f2dedb9..36f95eb 100644
--- a/src/box2d-wrapper/box2d_wrapper.cpp
+++ b/src/box2d-wrapper/box2d_wrapper.cpp
@@ -1,73 +1,67 @@
#include "box2d_wrapper.h"
-#include "../b2_user_settings.h"
#include "../bodies/box2d_collision_object_2d.h"
-#include
-#include
#include
+#include
+#include
+#include
#include
+#include
using namespace box2d;
using namespace godot;
-enum class ShapeType {
- Circle = 0,
- Segment,
- Polygon,
-};
+#define B2_DEBUG true
struct Box2DHolder {
- HashMap active_body_callbacks;
- HashMap active_objects;
+ HashMap active_body_callbacks;
};
Box2DHolder holder;
-
-bool is_toi_intersected(const b2TOIOutput &output) {
- return output.state == b2TOIOutput::State::e_failed || output.state == b2TOIOutput::State::e_overlapped || output.state == b2TOIOutput::State::e_touching;
-}
-
-b2TOIOutput _time_of_impact(b2Shape *shape_A, const b2Transform &p_xfA, b2Vec2 local_centerA, const b2Vec2 &motion_A, b2Shape *shape_B, const b2Transform &p_xfB, b2Vec2 local_centerB, const b2Vec2 &motion_B) {
- b2TOIOutput output;
- b2TOIInput input;
- input.tMax = 1.0;
- input.sweepA.a0 = p_xfA.q.GetAngle();
- input.sweepA.a = input.sweepA.a0;
- input.sweepA.localCenter = b2Vec2_zero;
- input.sweepA.c0 = p_xfA.p;
- input.sweepA.c = input.sweepA.c0 + motion_A;
- input.sweepA.alpha0 = 0.0;
- input.sweepB.a0 = p_xfB.q.GetAngle();
- input.sweepB.a = input.sweepB.a0;
- input.sweepB.localCenter = b2Vec2_zero;
- input.sweepB.c0 = p_xfB.p;
- input.sweepB.c = input.sweepB.c0 + motion_B;
- input.sweepB.alpha0 = 0.0;
- for (int i = 0; i < shape_A->GetChildCount(); i++) {
- input.proxyA.Set(shape_A, i);
- for (int j = 0; j < shape_B->GetChildCount(); j++) {
- input.proxyB.Set(shape_B, j);
- b2TimeOfImpact(&output, &input);
- bool intersects = is_toi_intersected(output);
- if (intersects) {
- return output;
- }
- }
- }
- return output;
-}
-
-b2DistanceOutput _call_b2_distance(b2Transform p_transformA, b2Shape *shapeA, int child_index_A, b2Transform p_transformB, b2Shape *shapeB, int child_index_B) {
- b2DistanceOutput output;
- b2DistanceInput input;
- b2SimplexCache cache;
- cache.count = 0;
- input.proxyA.Set(shapeA, child_index_A);
- input.proxyB.Set(shapeB, child_index_B);
- input.transformA = p_transformA;
- input.transformB = p_transformB;
- input.useRadii = true;
- b2Distance(&output, &cache, &input);
- return output;
+bool logging_enabled = false;
+
+bool is_toi_intersected(b2TOIOutput output) {
+ return output.state == b2TOIState::b2_toiStateFailed || output.state == b2TOIState::b2_toiStateOverlapped || output.state == b2TOIState::b2_toiStateHit;
+}
+
+// TODO
+b2TOIOutput _time_of_impact(b2ShapeId shape_A_id, b2Transform p_xfA, b2Vec2 local_centerA, b2Vec2 motion_A, b2ShapeId shape_B_id, b2Transform p_xfB, b2Vec2 local_centerB, b2Vec2 motion_B) {
+ float angle_A = b2Rot_GetAngle(p_xfA.q);
+ float angle_B = b2Rot_GetAngle(p_xfB.q);
+ // TODO
+ b2TOIInput input = {
+ b2DistanceProxy{}, //b2MakeShapeDistanceProxy(&shapeA),
+ b2DistanceProxy{}, //b2MakeShapeDistanceProxy(&shapeB),
+ {
+ b2Vec2_zero,
+ p_xfA.p,
+ b2Vec2_add(p_xfA.p, motion_A),
+ angle_A,
+ angle_A,
+ },
+ {
+ b2Vec2_zero,
+ p_xfB.p,
+ b2Vec2_add(p_xfB.p, motion_B),
+ angle_B,
+ angle_B,
+ },
+ 1.0
+ };
+ // TODO figure out how to create a chain proxy
+ return b2TimeOfImpact(&input);
+}
+// TODO
+b2DistanceOutput _call_b2_distance(b2Transform p_transformA, b2ShapeId shapeA, b2Transform p_transformB, b2ShapeId shapeB) {
+ b2DistanceInput input{
+ b2DistanceProxy{}, //b2MakeShapeDistanceProxy(&shapeA),
+ b2DistanceProxy{}, //b2MakeShapeDistanceProxy(&shapeB),
+ p_transformA,
+ p_transformB,
+ true
+ };
+ b2DistanceCache cache = { 0 };
+ // TODO figure out how to set proxy of chain
+ return b2ShapeDistance(&cache, &input);
}
struct IntersectionManifoldResult {
@@ -78,86 +72,74 @@ struct IntersectionManifoldResult {
return manifold.pointCount > 0;
}
};
-
+// TODO
// from https://github.com/briansemrau/godot_box2d/blob/5f55923fac81386e5735573e99d908d18efec6a1/scene/2d/box2d_world.cpp#L731
-IntersectionManifoldResult _evaluate_intersection_manifold(const b2Shape *p_shapeA, const int p_child_index_A, const b2Transform &p_xfA, const b2Shape *p_shapeB, const int p_child_index_B, const b2Transform &p_xfB) {
+IntersectionManifoldResult _evaluate_intersection_manifold(b2ShapeId p_shapeA, b2Transform p_xfA, b2ShapeId p_shapeB, b2Transform p_xfB) {
b2Manifold manifold{};
bool flipped = false;
-
- // Convert chains to edges
- b2EdgeShape shapeA_as_edge;
- if (p_shapeA->GetType() == b2Shape::Type::e_chain) {
- static_cast(p_shapeA)->GetChildEdge(&shapeA_as_edge, p_child_index_A);
- p_shapeA = &shapeA_as_edge;
- }
-
- b2EdgeShape shapeB_as_edge;
- if (p_shapeB->GetType() == b2Shape::Type::e_chain) {
- static_cast(p_shapeB)->GetChildEdge(&shapeB_as_edge, p_child_index_B);
- p_shapeB = &shapeB_as_edge;
- }
-
- // This is, as far as I know, the cleanest way to implement this.
- switch (p_shapeA->GetType()) {
- case b2Shape::Type::e_circle: {
- switch (p_shapeB->GetType()) {
- case b2Shape::Type::e_circle: {
- b2CollideCircles(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
- } break;
- case b2Shape::Type::e_edge: {
- b2CollideEdgeAndCircle(&manifold, static_cast(p_shapeB), p_xfB, static_cast(p_shapeA), p_xfA);
- flipped = true;
- } break;
- case b2Shape::Type::e_polygon: {
- b2CollidePolygonAndCircle(&manifold, static_cast(p_shapeB), p_xfB, static_cast(p_shapeA), p_xfA);
- flipped = true;
- } break;
- default: {
- ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "Unexpected shape type.");
- } break;
- }
- } break;
- case b2Shape::Type::e_edge: {
- switch (p_shapeB->GetType()) {
- case b2Shape::Type::e_circle: {
- b2CollideEdgeAndCircle(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
- } break;
- case b2Shape::Type::e_edge: {
- ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "There are no contacts between two edges in Box2D. This is an invalid manifold query.");
- } break;
- case b2Shape::Type::e_polygon: {
- b2CollideEdgeAndPolygon(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
- } break;
- default: {
- ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "Unexpected shape type.");
- } break;
- }
- } break;
- case b2Shape::Type::e_polygon: {
- switch (p_shapeB->GetType()) {
- case b2Shape::Type::e_circle: {
- b2CollidePolygonAndCircle(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
- } break;
- case b2Shape::Type::e_edge: {
- b2CollideEdgeAndPolygon(&manifold, static_cast(p_shapeB), p_xfB, static_cast(p_shapeA), p_xfA);
- flipped = true;
- } break;
- case b2Shape::Type::e_polygon: {
- b2CollidePolygons(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
- } break;
- default: {
- ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "Unexpected shape type.");
- } break;
- }
- } break;
- default: {
- ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "Unexpected shape type.");
- } break;
- }
-
+ // TODO fix here
+ /*
+ // This is, as far as I know, the cleanest way to implement this.
+ switch (p_shapeA->GetType()) {
+ case b2Shape::Type::e_circle: {
+ switch (p_shapeB->GetType()) {
+ case b2Shape::Type::e_circle: {
+ b2CollideCircles(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
+ } break;
+ case b2Shape::Type::e_edge: {
+ b2CollideEdgeAndCircle(&manifold, static_cast(p_shapeB), p_xfB, static_cast(p_shapeA), p_xfA);
+ flipped = true;
+ } break;
+ case b2Shape::Type::e_polygon: {
+ b2CollidePolygonAndCircle(&manifold, static_cast(p_shapeB), p_xfB, static_cast(p_shapeA), p_xfA);
+ flipped = true;
+ } break;
+ default: {
+ ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "Unexpected shape type.");
+ } break;
+ }
+ } break;
+ case b2Shape::Type::e_edge: {
+ switch (p_shapeB->GetType()) {
+ case b2Shape::Type::e_circle: {
+ b2CollideEdgeAndCircle(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
+ } break;
+ case b2Shape::Type::e_edge: {
+ ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "There are no contacts between two edges in Box2D. This is an invalid manifold query.");
+ } break;
+ case b2Shape::Type::e_polygon: {
+ b2CollideEdgeAndPolygon(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
+ } break;
+ default: {
+ ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "Unexpected shape type.");
+ } break;
+ }
+ } break;
+ case b2Shape::Type::e_polygon: {
+ switch (p_shapeB->GetType()) {
+ case b2Shape::Type::e_circle: {
+ b2CollidePolygonAndCircle(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
+ } break;
+ case b2Shape::Type::e_edge: {
+ b2CollideEdgeAndPolygon(&manifold, static_cast(p_shapeB), p_xfB, static_cast(p_shapeA), p_xfA);
+ flipped = true;
+ } break;
+ case b2Shape::Type::e_polygon: {
+ b2CollidePolygons(&manifold, static_cast(p_shapeA), p_xfA, static_cast(p_shapeB), p_xfB);
+ } break;
+ default: {
+ ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "Unexpected shape type.");
+ } break;
+ }
+ } break;
+ default: {
+ ERR_FAIL_V_MSG((IntersectionManifoldResult{ manifold, flipped }), "Unexpected shape type.");
+ } break;
+ }
+ */
return IntersectionManifoldResult{ manifold, flipped };
}
-
+/*
struct IntersectionResult {
b2WorldManifold world_manifold;
b2Manifold manifold;
@@ -204,315 +186,459 @@ IntersectionResult _intersect_shape(b2Shape *shape_A, const b2Transform &p_xfA,
distance_output,
};
}
+*/
-bool box2d::are_handles_equal(b2World *handle1, b2World *handle2) {
- return handle1 == handle2;
-}
-bool box2d::are_handles_equal(b2Body *handle1, b2Body *handle2) {
- return handle1 == handle2;
-}
-bool box2d::are_handles_equal(FixtureHandle handle1, FixtureHandle handle2) {
- if (handle1.count != handle2.count) {
- return false;
- }
- for (int i = 0; i < handle1.count; i++) {
- if (handle1.handles[i] != handle2.handles[i]) {
- return false;
- }
- }
- return true;
-}
-bool box2d::are_handles_equal(ShapeHandle handle1, ShapeHandle handle2) {
- if (handle1.count != handle2.count) {
- return false;
- }
- for (int i = 0; i < handle1.count; i++) {
- if (handle1.handles[i] != handle2.handles[i]) {
- return false;
- }
- }
- return true;
-}
-bool box2d::are_handles_equal(b2Joint *handle1, b2Joint *handle2) {
- return handle1 == handle2;
-}
-bool box2d::are_handles_equal(b2Fixture *handle1, b2Fixture *handle2) {
- return handle1 == handle2;
+b2BodyUserData *get_body_user_data(b2BodyId body_handle) {
+ return static_cast(b2Body_GetUserData(body_handle));
}
-void box2d::body_add_force(b2World *world_handle, b2Body *body_handle, const b2Vec2 force) {
- body_handle->GetUserData().constant_force += b2Vec2_to_Vector2(force);
+void box2d::body_add_force(b2BodyId body_handle, b2Vec2 force) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_add_force: ", rtos(body_handle.index), ", ", rtos(force.x), ", ", rtos(force.y));
+#endif
+ b2BodyUserData *body_user_data = get_body_user_data(body_handle);
+ ERR_FAIL_NULL(body_user_data);
+ body_user_data->constant_force += b2Vec2_to_Vector2(force);
}
-void box2d::body_add_torque(b2World *world_handle, b2Body *body_handle, real_t torque) {
- body_handle->GetUserData().constant_torque += torque;
+void box2d::body_add_torque(b2BodyId body_handle, real_t torque) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_add_torque: ", rtos(body_handle.index), ", ", rtos(torque));
+#endif
+ b2BodyUserData *body_user_data = get_body_user_data(body_handle);
+ ERR_FAIL_NULL(body_user_data);
+ body_user_data->constant_torque += torque;
}
-void box2d::body_apply_impulse(b2World *world_handle, b2Body *body_handle, const b2Vec2 impulse) {
- body_handle->ApplyLinearImpulseToCenter(impulse, true);
+void box2d::body_apply_impulse(b2BodyId body_handle, b2Vec2 impulse) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_apply_impulse: ", rtos(body_handle.index), ", ", rtos(impulse.x), ", ", rtos(impulse.y));
+#endif
+ b2Body_ApplyLinearImpulseToCenter(body_handle, impulse, true);
}
-void box2d::body_apply_impulse_at_point(b2World *world_handle,
- b2Body *body_handle,
- const b2Vec2 impulse,
- const b2Vec2 point) {
- body_handle->ApplyLinearImpulse(impulse, point, true);
+void box2d::body_apply_impulse_at_point(b2BodyId body_handle, b2Vec2 impulse, b2Vec2 point) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_apply_impulse_at_point: ", rtos(body_handle.index), ", ", rtos(impulse.x), ", ", rtos(impulse.y), ", ", rtos(point.x), ", ", rtos(point.y));
+#endif
+ b2Body_ApplyLinearImpulse(body_handle, impulse, point, true);
}
-void box2d::body_apply_torque_impulse(b2World *world_handle, b2Body *body_handle, real_t torque_impulse) {
- body_handle->ApplyAngularImpulse(torque_impulse, true);
+void box2d::body_apply_torque_impulse(b2BodyId body_handle, real_t torque_impulse) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_apply_torque_impulse: ", rtos(body_handle.index), ", ", rtos(torque_impulse));
+#endif
+ b2Body_ApplyAngularImpulse(body_handle, torque_impulse, true);
}
-void box2d::body_change_mode(b2World *world_handle, b2Body *body_handle, b2BodyType body_type, bool wakeup, bool fixed_rotation) {
- body_handle->SetType(body_type);
- body_handle->SetFixedRotation(fixed_rotation);
+void box2d::body_change_mode(b2BodyId body_handle, b2BodyType body_type, bool fixed_rotation) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_change_mode: ", rtos(body_handle.index), ", ", rtos(body_type), ", ", fixed_rotation);
+#endif
+ // this updates body mass too
+ b2Body_SetType(body_handle, body_type);
+ b2Body_Wake(body_handle);
+ // todo set fixed rotation
+ //body_handle->SetFixedRotation(fixed_rotation);
}
-b2Body *box2d::body_create(b2World *world_handle,
- const b2Vec2 pos,
+b2BodyId box2d::body_create(b2WorldId world_handle,
+ b2Vec2 pos,
real_t rot,
- const b2BodyUserData &user_data,
+ b2BodyUserData *user_data,
b2BodyType body_type) {
- b2BodyDef body_def;
- body_def.position = pos;
- body_def.angle = rot;
- body_def.userData = user_data;
- body_def.type = body_type;
- return world_handle->CreateBody(&body_def);
-}
-
-void box2d::body_destroy(b2World *world_handle, b2Body *body_handle) {
- world_handle->DestroyBody(body_handle);
-}
-
-void box2d::body_force_sleep(b2World *world_handle, b2Body *body_handle) {
- if (body_handle->IsSleepingAllowed()) {
- body_handle->SetAwake(false);
- }
-}
-
-real_t box2d::body_get_angle(b2World *world_handle, b2Body *body_handle) {
- return body_handle->GetAngle();
-}
-
-real_t box2d::body_get_angular_velocity(b2World *world_handle, b2Body *body_handle) {
- if (body_handle->GetType() == b2_kinematicBody) {
- return body_handle->GetUserData().old_angular_velocity;
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_create: ", rtos(world_handle.index), ", ", rtos(pos.x), ", ", rtos(pos.y), ", ", rtos(rot), ", ", rtos(body_type));
+#endif
+ b2BodyDef body_def = {
+ body_type, // bodyType
+ pos, // position
+ rot, // angle
+ { 0.0f, 0.0f }, // linearVelocity
+ 0.0f, // angularVelocity
+ 0.0f, // linearDamping
+ 0.0f, // angularDamping
+ 1.0f, // gravityScale
+ user_data, // userData
+ true, // enableSleep
+ true, // isAwake
+ false, // fixedRotation
+ false, // isBullet
+ true, // isEnabled
+ };
+ return b2CreateBody(world_handle, &body_def);
+}
+
+void box2d::body_destroy(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_destroy: ", rtos(body_handle.index));
+#endif
+ // TODO destroy user data too
+ b2DestroyBody(body_handle);
+}
+
+void box2d::body_force_sleep(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_force_sleep: ", rtos(body_handle.index));
+#endif
+ // TODO no function yet
+ //if (body_handle->IsSleepingAllowed()) {
+ // body_handle->SetAwake(false);
+ //}
+}
+
+real_t box2d::body_get_angle(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_get_angle: ", rtos(body_handle.index));
+#endif
+ return b2Body_GetAngle(body_handle);
+}
+
+real_t box2d::body_get_angular_velocity(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_get_angular_velocity: ", rtos(body_handle.index));
+#endif
+ if (b2Body_GetType(body_handle) == b2_kinematicBody) {
+ b2BodyUserData *body_user_data = get_body_user_data(body_handle);
+ ERR_FAIL_NULL_V(body_user_data, 0.0);
+ return body_user_data->old_angular_velocity;
}
- return body_handle->GetAngularVelocity();
-}
-
-b2Vec2 box2d::body_get_constant_force(b2World *world_handle, b2Body *body_handle) {
- return Vector2_to_b2Vec2(body_handle->GetUserData().constant_force);
-}
-
-real_t box2d::body_get_constant_torque(b2World *world_handle, b2Body *body_handle) {
- return body_handle->GetUserData().constant_torque;
-}
-
-b2Vec2 box2d::body_get_linear_velocity(b2World *world_handle, b2Body *body_handle) {
- if (body_handle->GetType() == b2_kinematicBody) {
- return Vector2_to_b2Vec2(body_handle->GetUserData().old_linear_velocity);
+ return b2Body_GetAngularVelocity(body_handle);
+}
+
+b2Vec2 box2d::body_get_constant_force(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_get_constant_force: ", rtos(body_handle.index));
+#endif
+ b2BodyUserData *body_user_data = get_body_user_data(body_handle);
+ ERR_FAIL_NULL_V(body_user_data, b2Vec2_zero);
+ return Vector2_to_b2Vec2(body_user_data->constant_force);
+}
+
+real_t box2d::body_get_constant_torque(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_get_constant_torque: ", rtos(body_handle.index));
+#endif
+ b2BodyUserData *body_user_data = get_body_user_data(body_handle);
+ ERR_FAIL_NULL_V(body_user_data, 0.0);
+ return body_user_data->constant_torque;
+}
+
+b2Vec2 box2d::body_get_linear_velocity(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_get_linear_velocity: ", rtos(body_handle.index));
+#endif
+ if (b2Body_GetType(body_handle) == b2_kinematicBody) {
+ b2BodyUserData *body_user_data = get_body_user_data(body_handle);
+ ERR_FAIL_NULL_V(body_user_data, b2Vec2_zero);
+ return Vector2_to_b2Vec2(body_user_data->old_linear_velocity);
}
- return body_handle->GetLinearVelocity();
-}
-
-b2Vec2 box2d::body_get_position(b2World *world_handle, b2Body *body_handle) {
- return body_handle->GetPosition();
-}
-
-bool box2d::body_is_ccd_enabled(b2World *world_handle, b2Body *body_handle) {
- return body_handle->IsBullet();
-}
-
-void box2d::body_reset_forces(b2World *world_handle, b2Body *body_handle) {
- body_handle->GetUserData().constant_force = Vector2();
-}
-
-void box2d::body_reset_torques(b2World *world_handle, b2Body *body_handle) {
- body_handle->GetUserData().constant_torque = 0.0;
-}
-
-void box2d::body_set_angular_damping(b2World *world_handle, b2Body *body_handle, real_t angular_damping) {
- body_handle->SetAngularDamping(angular_damping);
-}
-
-void box2d::body_set_angular_velocity(b2World *world_handle, b2Body *body_handle, real_t vel) {
- body_handle->SetAngularVelocity(vel);
-}
-
-void box2d::body_set_can_sleep(b2World *world_handle, b2Body *body_handle, bool can_sleep) {
- body_handle->SetSleepingAllowed(can_sleep);
-}
-
-void box2d::body_set_ccd_enabled(b2World *world_handle, b2Body *body_handle, bool enable) {
- body_handle->SetBullet(enable);
-}
-
-void box2d::body_set_gravity_scale(b2World *world_handle,
- b2Body *body_handle,
- real_t gravity_scale,
- bool wake_up) {
- body_handle->SetGravityScale(gravity_scale);
-}
-
-void box2d::body_set_linear_damping(b2World *world_handle, b2Body *body_handle, real_t linear_damping) {
- body_handle->SetLinearDamping(linear_damping);
-}
-
-void box2d::body_set_linear_velocity(b2World *world_handle, b2Body *body_handle, const b2Vec2 vel) {
- if (body_handle->GetType() == b2_kinematicBody) {
+ return b2Body_GetLinearVelocity(body_handle);
+}
+
+b2Vec2 box2d::body_get_position(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_get_position: ", rtos(body_handle.index));
+#endif
+ return b2Body_GetPosition(body_handle);
+}
+
+bool box2d::body_is_ccd_enabled(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_is_ccd_enabled: ", rtos(body_handle.index));
+#endif
+ return false;
+ // TODO no function yet
+ //return b2Body_GetBullet(body_handle);
+}
+
+void box2d::body_reset_forces(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_reset_forces: ", rtos(body_handle.index));
+#endif
+ b2BodyUserData *body_user_data = get_body_user_data(body_handle);
+ ERR_FAIL_NULL(body_user_data);
+ body_user_data->constant_force = Vector2();
+}
+
+void box2d::body_reset_torques(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_reset_torques: ", rtos(body_handle.index));
+#endif
+ b2BodyUserData *body_user_data = get_body_user_data(body_handle);
+ ERR_FAIL_NULL(body_user_data);
+ body_user_data->constant_torque = 0.0;
+}
+
+void box2d::body_set_angular_damping(b2BodyId body_handle, real_t angular_damping) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_set_angular_damping: ", rtos(body_handle.index), ", ", rtos(angular_damping));
+#endif
+ b2Body_SetAngularDamping(body_handle, angular_damping);
+}
+
+void box2d::body_set_angular_velocity(b2BodyId body_handle, real_t vel) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_set_angular_velocity: ", rtos(body_handle.index), ", ", rtos(vel));
+#endif
+ b2Body_SetAngularVelocity(body_handle, vel);
+}
+
+void box2d::body_set_can_sleep(b2BodyId body_handle, bool can_sleep) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_set_can_sleep: ", rtos(body_handle.index), ", ", rtos(can_sleep));
+#endif
+ // TODO no function yet
+ //b2Body_SetSleepingAllowed(body_handle, can_sleep);
+}
+
+void box2d::body_set_ccd_enabled(b2BodyId body_handle, bool enable) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_set_ccd_enabled: ", rtos(body_handle.index), ", ", rtos(enable));
+#endif
+ // TODO no function yet
+ // body_handle->SetBullet(enable);
+}
+
+void box2d::body_set_gravity_scale(b2BodyId body_handle,
+ real_t gravity_scale) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_set_gravity_scale: ", rtos(body_handle.index), ", ", rtos(gravity_scale));
+#endif
+ b2Body_SetGravityScale(body_handle, gravity_scale);
+}
+
+void box2d::body_set_linear_damping(b2BodyId body_handle, real_t linear_damping) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_set_linear_damping: ", rtos(body_handle.index), ", ", rtos(linear_damping));
+#endif
+ b2Body_SetLinearDamping(body_handle, linear_damping);
+}
+
+void box2d::body_set_linear_velocity(b2BodyId body_handle, b2Vec2 vel) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_set_linear_velocity: ", rtos(body_handle.index));
+#endif
+ if (b2Body_GetType(body_handle) == b2_kinematicBody) {
// for kinematic setting velocity is like moving the object, we want it to happen all the time
- body_handle->SetLinearVelocity(vel + body_handle->GetLinearVelocity());
+ b2Body_SetLinearVelocity(body_handle, b2Vec2_add(vel, b2Body_GetLinearVelocity(body_handle)));
} else {
- body_handle->SetLinearVelocity(vel);
+ b2Body_SetLinearVelocity(body_handle, vel);
}
}
-void box2d::body_set_mass_properties(b2World *world_handle,
- b2Body *body_handle,
- real_t mass,
- real_t inertia,
- const b2Vec2 local_com,
- bool wake_up,
- bool force_update) {
- b2MassData mass_data{
- mass,
- local_com,
- inertia
- };
- body_handle->SetMassData(&mass_data);
+void box2d::body_set_mass_properties(b2BodyId body_handle, real_t mass, real_t inertia, b2Vec2 local_com) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_set_mass_properties: ", rtos(body_handle.index), ", ", rtos(mass), ", ", rtos(inertia), ", ", rtos(local_com.x), ", ", rtos(local_com.y));
+#endif
+ b2MassData mass_data{ mass, local_com, inertia };
+ b2Body_SetMassData(body_handle, mass_data);
}
-void box2d::body_set_transform(b2World *world_handle,
- b2Body *body_handle,
- const b2Vec2 pos,
- real_t rot,
- bool wake_up,
- real_t step) {
- b2Vec2 new_pos = (pos - body_handle->GetPosition());
+void box2d::body_set_transform(b2BodyId body_handle, b2Vec2 pos, real_t rot, real_t step) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_set_transform: ", rtos(body_handle.index), ", ", rtos(pos.x), ", ", rtos(pos.y), ", ", rtos(rot), ", ", rtos(step));
+#endif
+ b2Vec2 new_pos = b2Vec2_sub(pos, b2Body_GetPosition(body_handle));
new_pos.x /= step;
new_pos.y /= step;
- if (body_handle->GetType() == b2BodyType::b2_kinematicBody) {
- real_t new_rot1 = (rot - body_handle->GetAngle()) / step;
- real_t new_rot2 = -(2.0 * b2_pi - rot + body_handle->GetAngle()) / step;
+ if (b2Body_GetType(body_handle) == b2BodyType::b2_kinematicBody) {
+ real_t new_rot1 = (rot - b2Body_GetAngle(body_handle)) / step;
+ real_t new_rot2 = -(2.0 * b2_pi - rot + b2Body_GetAngle(body_handle)) / step;
real_t new_rot = new_rot1;
if (ABS(new_rot2) < ABS(new_rot1)) {
new_rot = new_rot2;
}
- body_handle->SetLinearVelocity(new_pos);
- body_handle->SetAngularVelocity(new_rot);
+ b2Body_SetLinearVelocity(body_handle, new_pos);
+ b2Body_SetAngularVelocity(body_handle, new_rot);
} else {
- body_handle->SetTransform(pos, rot);
- if (body_handle->IsSleepingAllowed()) {
- body_handle->SetAwake(wake_up);
- } else {
- body_handle->SetAwake(true);
- }
+ b2Body_SetTransform(body_handle, pos, rot);
+ //b2Body_Wake(true);
}
}
-void box2d::body_update_material(b2World *world_handle, b2Body *body_handle, const Material *mat) {
- for (b2Fixture *fixture = body_handle->GetFixtureList(); fixture != nullptr; fixture = fixture->GetNext()) {
- fixture->SetFriction(mat->friction);
- fixture->SetRestitution(mat->restitution);
+void box2d::body_update_material(b2BodyId body_handle, Material mat) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_update_material: ", rtos(body_handle.index), ", ", rtos(mat.friction), ", ", rtos(mat.restitution));
+#endif
+ for (b2ShapeId shape_handle = b2Body_GetFirstShape(body_handle); B2_IS_NON_NULL(shape_handle); shape_handle = b2Body_GetNextShape(shape_handle)) {
+ b2Shape_SetFriction(shape_handle, mat.friction);
+ b2Shape_SetRestitution(shape_handle, mat.restitution);
}
}
-void box2d::body_wake_up(b2World *world_handle, b2Body *body_handle, bool strong) {
- body_handle->SetAwake(true);
+void box2d::body_wake_up(b2BodyId body_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::body_wake_up: ", rtos(body_handle.index));
+#endif
+ if (b2Body_GetType(body_handle) == b2BodyType::b2_kinematicBody) {
+ b2Body_Wake(body_handle);
+ }
}
-FixtureHandle box2d::collider_create_sensor(b2World *world_handle,
- ShapeHandle shape_handle,
- b2Body *body_handle,
- b2FixtureUserData user_data) {
- FixtureHandle fixture_handle{
- (b2Fixture **)memalloc((shape_handle.count) * sizeof(b2Fixture *)),
- shape_handle.count
- };
- b2MassData mass_data = body_handle->GetMassData();
- for (int i = 0; i < shape_handle.count; i++) {
- b2FixtureDef fixture_def;
- fixture_def.shape = shape_handle.handles[i];
- fixture_def.density = 1.0;
- fixture_def.isSensor = true;
- fixture_def.userData = user_data;
- b2Fixture *fixture = body_handle->CreateFixture(&fixture_def);
- fixture_handle.handles[i] = fixture;
+b2ShapeId create_collider(b2BodyId body_handle, b2FixtureUserData *user_data, Material mat, ShapeData shape_data, bool isSensor) {
+ b2ShapeId shapeId = b2_nullShapeId;
+ b2ShapeDef shape_def = b2DefaultShapeDef();
+ shape_def.userData = user_data;
+ shape_def.friction = mat.friction;
+ shape_def.restitution = mat.restitution;
+ shape_def.density = 1.0;
+ shape_def.isSensor = isSensor;
+ switch (shape_data.type) {
+ case b2ShapeType::b2_capsuleShape: {
+ shapeId = b2CreateCapsuleShape(body_handle, &shape_def, &shape_data.data.capsule);
+ } break;
+ case b2ShapeType::b2_circleShape: {
+ shapeId = b2CreateCircleShape(body_handle, &shape_def, &shape_data.data.circle);
+ } break;
+ case b2ShapeType::b2_polygonShape: {
+ shapeId = b2CreatePolygonShape(body_handle, &shape_def, &shape_data.data.polygon);
+ } break;
+ case b2ShapeType::b2_segmentShape: {
+ shapeId = b2CreateSegmentShape(body_handle, &shape_def, &shape_data.data.segment);
+ } break;
+ default: {
+ ERR_PRINT("Wrong shape type.");
+ } break;
+ }
+ return shapeId;
+}
+
+FixtureHandle box2d::collider_create_sensor(b2WorldId world_handle,
+ ShapeHandle shape_handles,
+ b2BodyId body_handle,
+ b2FixtureUserData *user_data) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::collider_create_sensor: ", rtos(world_handle.index), ", ", rtos(shape_handles.handles.size()), ", ", rtos(body_handle.index));
+#endif
+ FixtureHandle fixture_handle{};
+ b2MassData mass_data = b2Body_GetMassData(body_handle);
+ for (int i = 0; i < shape_handles.handles.size(); i++) {
+ ShapeData shape_data = shape_handles.handles[i];
+ fixture_handle.handles.push_back(create_collider(body_handle, user_data, Material{}, shape_data, true));
}
- body_handle->SetMassData(&mass_data);
+ b2Body_SetMassData(body_handle, mass_data);
return fixture_handle;
}
-FixtureHandle box2d::collider_create_solid(b2World *world_handle,
- ShapeHandle shape_handle,
- const Material *mat,
- b2Body *body_handle,
- b2FixtureUserData user_data) {
- FixtureHandle fixture_handle{
- (b2Fixture **)memalloc((shape_handle.count) * sizeof(b2Fixture *)),
- shape_handle.count
- };
- b2MassData mass_data = body_handle->GetMassData();
- for (int i = 0; i < shape_handle.count; i++) {
- b2FixtureDef fixture_def;
- fixture_def.shape = shape_handle.handles[i];
- fixture_def.density = 1.0;
- fixture_def.restitution = mat->restitution;
- fixture_def.friction = mat->friction;
- fixture_def.isSensor = false;
- fixture_def.userData = user_data;
- b2Fixture *fixture = body_handle->CreateFixture(&fixture_def);
- fixture_handle.handles[i] = fixture;
+FixtureHandle box2d::collider_create_solid(b2WorldId world_handle,
+ ShapeHandle shape_handles,
+ Material mat,
+ b2BodyId body_handle,
+ b2FixtureUserData *user_data) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::collider_create_solid: ", rtos(world_handle.index), ", ", rtos(shape_handles.handles.size()), ", ", rtos(body_handle.index));
+#endif
+ FixtureHandle fixture_handle{};
+ b2MassData mass_data = b2Body_GetMassData(body_handle);
+ for (int i = 0; i < shape_handles.handles.size(); i++) {
+ ShapeData shape_data = shape_handles.handles[i];
+ fixture_handle.handles.push_back(create_collider(body_handle, user_data, mat, shape_data, false));
}
- body_handle->SetMassData(&mass_data);
+ b2Body_SetMassData(body_handle, mass_data);
return fixture_handle;
}
-void box2d::collider_destroy(b2World *world_handle, FixtureHandle handle) {
- ERR_FAIL_COND(!is_handle_valid(handle));
- b2Body *body = handle.handles[0]->GetBody();
- if (!is_handle_valid(body)) {
- // already destroyed
- return;
+void box2d::collider_set_contact_force_events_enabled(FixtureHandle collider_handle, bool send_contacts) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::collider_set_contact_force_events_enabled: ", rtos(collider_handle.handles.size()), ", ", rtos(send_contacts));
+#endif
+ for (int i = 0; i < collider_handle.handles.size(); i++) {
+ b2ShapeId shape_id = collider_handle.handles[i];
+ // TODO when API exists for enableContactEvents
+ // b2Shape_
}
- for (b2Fixture *fixture = body->GetFixtureList(); fixture != nullptr; fixture = fixture->GetNext()) {
- for (int i = 0; i < handle.count; i++) {
- if (fixture == handle.handles[i]) {
- body->DestroyFixture(fixture);
- }
- }
+}
+
+void box2d::collider_destroy(FixtureHandle handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::collider_destroy: ", rtos(handle.handles.size()));
+#endif
+ for (b2ShapeId shapeId : handle.handles) {
+ b2DestroyShape(shapeId);
}
}
b2Vec2 box2d::Vector2_to_b2Vec2(Vector2 vec) {
- return b2Vec2(vec.x, vec.y);
+ return b2Vec2{ vec.x, vec.y };
}
b2Transform Transform2D_to_b2Transform(Transform2D transform) {
- return b2Transform(Vector2_to_b2Vec2(transform.get_origin()), b2Rot(transform.get_rotation()));
+ return b2Transform{ Vector2_to_b2Vec2(transform.get_origin()), b2Rot{ transform.get_rotation() } };
}
Transform2D b2Transform_to_Transform2D(b2Transform transform) {
- return Transform2D(transform.q.GetAngle(), b2Vec2_to_Vector2(transform.p));
+ return Transform2D(b2Rot_GetAngle(transform.q), b2Vec2_to_Vector2(transform.p));
}
Vector2 box2d::b2Vec2_to_Vector2(b2Vec2 vec) {
return Vector2(vec.x, vec.y);
}
+b2Vec2 box2d::b2Vec2_add(b2Vec2 vec, b2Vec2 other) {
+ vec.x += other.x;
+ vec.y += other.y;
+ return vec;
+}
+b2Vec2 box2d::b2Vec2_mul(b2Vec2 vec, real_t other) {
+ vec.x *= other;
+ vec.y *= other;
+ return vec;
+}
+
+b2Vec2 box2d::b2Vec2_sub(b2Vec2 vec, b2Vec2 other) {
+ vec.x -= other.x;
+ vec.y -= other.y;
+ return vec;
+}
b2Vec2 xform_b2Vec2(b2Vec2 vec, Transform2D transform) {
return Vector2_to_b2Vec2(transform.xform(b2Vec2_to_Vector2(vec)));
}
-void box2d::collider_set_transform(b2World *world_handle, FixtureHandle handles, ShapeInfo shape_info) {
- for (int i = 0; i < handles.count; i++) {
- b2Fixture *handle = handles.handles[i];
- handle->GetUserData().transform = shape_info.transform;
- ERR_FAIL_COND(!handle);
- ERR_FAIL_COND(!is_handle_valid(shape_info.handle));
- ERR_FAIL_COND(handles.count != shape_info.handle.count);
+// TODO
+void box2d::collider_set_transform(b2WorldId world_handle, FixtureHandle handles, ShapeInfo shape_info) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::collider_set_transform: ", rtos(world_handle.index), ", ", rtos(handles.handles.size()));
+#endif
+ ERR_FAIL_COND(!is_handle_valid(shape_info.handle));
+ for (b2ShapeId handle : handles.handles) {
+ b2FixtureUserData *user_data = static_cast(b2Shape_GetUserData(handle));
+ user_data->transform = shape_info.transform;
+ /*
b2Shape *shape_template = shape_info.handle.handles[i];
b2Shape *shape = handle->GetShape();
ERR_FAIL_COND(!shape);
@@ -566,36 +692,52 @@ void box2d::collider_set_transform(b2World *world_handle, FixtureHandle handles,
ERR_FAIL_MSG("Invalid Shape Type");
}
}
+ */
}
}
-Transform2D box2d::collider_get_transform(b2World *world_handle, FixtureHandle handle) {
+Transform2D box2d::collider_get_transform(b2WorldId world_handle, FixtureHandle handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::collider_get_transform: ", rtos(world_handle.index));
+#endif
ERR_FAIL_COND_V(!is_handle_valid(handle), Transform2D());
- return handle.handles[0]->GetUserData().transform;
+ b2FixtureUserData *user_data = static_cast(b2Shape_GetUserData(handle.handles[0]));
+ ERR_FAIL_NULL_V(user_data, Transform2D());
+ return user_data->transform;
}
-Transform2D box2d::collider_get_transform(b2World *world_handle, b2Fixture *handle) {
- return handle->GetUserData().transform;
+Transform2D box2d::collider_get_transform(b2WorldId world_handle, b2ShapeId handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::collider_get_transform: ", rtos(world_handle.index), ", ", rtos(handle.index));
+#endif
+ ERR_FAIL_COND_V(!is_handle_valid(handle), Transform2D());
+ b2FixtureUserData *user_data = static_cast(b2Shape_GetUserData(handle));
+ ERR_FAIL_NULL_V(user_data, Transform2D());
+ return user_data->transform;
}
Material box2d::default_material() {
return Material{};
}
+// TODO
QueryExcludedInfo box2d::default_query_excluded_info() {
- return QueryExcludedInfo{ 0, 0, nullptr, 0, 0 };
+ //return QueryExcludedInfo{ 0, 0, nullptr, 0, 0 };
+ return QueryExcludedInfo{};
}
WorldSettings box2d::default_world_settings() {
return WorldSettings{};
}
-class AABBQueryCallback : public b2QueryCallback {
+class AABBQueryCallback {
public:
int count = 0;
bool test_point = false;
b2Vec2 point;
- b2World *world;
+ b2WorldId world;
bool collide_with_body;
bool collide_with_area;
PointHitInfo *hit_info_array;
@@ -603,16 +745,18 @@ class AABBQueryCallback : public b2QueryCallback {
QueryHandleExcludedCallback handle_excluded_callback;
const QueryExcludedInfo *handle_excluded_info;
+ // TODO
/// Called for each fixture found in the query AABB.
/// @return false to terminate the query.
- virtual bool ReportFixture(b2Fixture *fixture) override {
- if (fixture->IsSensor() && !collide_with_area) {
+ bool ReportFixture(b2ShapeId shapeId, void *context) {
+ if (b2Shape_IsSensor(shapeId) && !collide_with_area) {
return true;
}
- if (!fixture->IsSensor() && !collide_with_body) {
+ if (!b2Shape_IsSensor(shapeId) && !collide_with_body) {
return true;
}
- if (!handle_excluded_callback(world, fixture, fixture->GetUserData(), handle_excluded_info)) {
+ /*
+ if (!handle_excluded_callback(world, shapeId, fixture->GetUserData(), handle_excluded_info)) {
hit_info_array[count++] = PointHitInfo{
fixture,
fixture->GetUserData()
@@ -623,11 +767,12 @@ class AABBQueryCallback : public b2QueryCallback {
return true;
}
}
+ */
return count < hit_info_length;
}
};
-size_t box2d::intersect_aabb(b2World *world_handle,
+size_t box2d::intersect_aabb(b2WorldId world_handle,
const b2Vec2 aabb_min,
const b2Vec2 aabb_max,
bool collide_with_body,
@@ -636,6 +781,10 @@ size_t box2d::intersect_aabb(b2World *world_handle,
size_t hit_info_length,
QueryHandleExcludedCallback handle_excluded_callback,
const QueryExcludedInfo *handle_excluded_info) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::intersect_aabb: ", rtos(world_handle.index));
+#endif
AABBQueryCallback callback;
callback.world = world_handle;
callback.collide_with_body = collide_with_body;
@@ -644,11 +793,14 @@ size_t box2d::intersect_aabb(b2World *world_handle,
callback.hit_info_length = hit_info_length;
callback.handle_excluded_callback = handle_excluded_callback;
callback.handle_excluded_info = handle_excluded_info;
- world_handle->QueryAABB(&callback, b2AABB{ aabb_min, aabb_max });
+ b2QueryFilter filter{};
+ // TODO
+ //b2World_QueryAABB(world_handle, &callback.ReportFixture, b2AABB{ aabb_min, aabb_max }, filter, context)
+ //world_handle->QueryAABB(&callback, );
return callback.count;
}
-size_t box2d::intersect_point(b2World *world_handle,
+size_t box2d::intersect_point(b2WorldId world_handle,
const b2Vec2 position,
bool collide_with_body,
bool collide_with_area,
@@ -656,6 +808,10 @@ size_t box2d::intersect_point(b2World *world_handle,
size_t hit_info_length,
QueryHandleExcludedCallback handle_excluded_callback,
const QueryExcludedInfo *handle_excluded_info) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::intersect_point: ", rtos(world_handle.index));
+#endif
AABBQueryCallback callback;
callback.world = world_handle;
callback.collide_with_body = collide_with_body;
@@ -666,14 +822,15 @@ size_t box2d::intersect_point(b2World *world_handle,
callback.handle_excluded_info = handle_excluded_info;
callback.test_point = true;
callback.point = position;
- world_handle->QueryAABB(&callback, b2AABB{ position - b2Vec2(1, 1), position + b2Vec2(1, 1) });
+ // TODO
+ //world_handle->QueryAABB(&callback, b2AABB{ position - b2Vec2(1, 1), position + b2Vec2(1, 1) });
return callback.count;
}
-class RayCastQueryCallback : public b2RayCastCallback {
+class RayCastQueryCallback {
public:
int count = 0;
- b2World *world;
+ b2WorldId world;
bool collide_with_body;
bool collide_with_area;
RayHitInfo *hit_info_array;
@@ -692,14 +849,16 @@ class RayCastQueryCallback : public b2RayCastCallback {
/// @param fraction the fraction along the ray at the point of intersection
/// @return -1 to filter, 0 to terminate, fraction to clip the ray for
/// closest hit, 1 to continue
- virtual float ReportFixture(b2Fixture *fixture, const b2Vec2 &point,
- const b2Vec2 &normal, float fraction) override {
- if (fixture->IsSensor() && !collide_with_area) {
+ float ReportFixture(b2ShapeId fixture, const b2Vec2 &point,
+ const b2Vec2 &normal, float fraction) {
+ if (b2Shape_IsSensor(fixture) && !collide_with_area) {
return -1;
}
- if (!fixture->IsSensor() && !collide_with_body) {
+ if (!b2Shape_IsSensor(fixture) && !collide_with_body) {
return -1;
}
+ // TODO
+ /*
if (!handle_excluded_callback(world, fixture, fixture->GetUserData(), handle_excluded_info)) {
hit_info_array[0] = RayHitInfo{
point,
@@ -709,11 +868,12 @@ class RayCastQueryCallback : public b2RayCastCallback {
};
count = 1;
}
+ */
return 1;
}
};
-bool box2d::intersect_ray(b2World *world_handle,
+bool box2d::intersect_ray(b2WorldId world_handle,
const b2Vec2 from,
const b2Vec2 dir,
real_t length,
@@ -723,6 +883,10 @@ bool box2d::intersect_ray(b2World *world_handle,
RayHitInfo *hit_info,
QueryHandleExcludedCallback handle_excluded_callback,
const QueryExcludedInfo *handle_excluded_info) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::intersect_ray: ", rtos(world_handle.index));
+#endif
RayCastQueryCallback callback;
callback.world = world_handle;
callback.collide_with_body = collide_with_body;
@@ -730,36 +894,31 @@ bool box2d::intersect_ray(b2World *world_handle,
callback.hit_info_array = hit_info;
callback.handle_excluded_callback = handle_excluded_callback;
callback.handle_excluded_info = handle_excluded_info;
- world_handle->RayCast(&callback, from, from + length * dir);
+ // TODO
+ //world_handle->RayCast(&callback, from, from + length * dir);
if (callback.count) {
return callback.count;
}
if (hit_from_inside) {
- world_handle->RayCast(&callback, from + length * dir, from);
+ //world_handle->RayCast(&callback, from + length * dir, from);
}
return callback.count;
}
-b2World *box2d::invalid_world_handle() {
- return nullptr;
+b2WorldId box2d::invalid_world_handle() {
+ return b2_nullWorldId;
}
FixtureHandle box2d::invalid_fixture_handle() {
- return FixtureHandle{
- nullptr,
- 0
- };
+ return FixtureHandle{};
}
-b2Body *box2d::invalid_body_handle() {
- return nullptr;
+b2BodyId box2d::invalid_body_handle() {
+ return b2_nullBodyId;
}
ShapeHandle box2d::invalid_shape_handle() {
- return ShapeHandle{
- nullptr,
- 0
- };
+ return ShapeHandle{};
}
-b2Joint *box2d::invalid_joint_handle() {
- return nullptr;
+b2JointId box2d::invalid_joint_handle() {
+ return b2_nullJointId;
}
b2FixtureUserData box2d::invalid_fixture_user_data() {
@@ -776,53 +935,59 @@ bool box2d::is_user_data_valid(b2BodyUserData user_data) {
}
bool box2d::is_handle_valid(FixtureHandle handle) {
- return handle.count > 0 || handle.handles != nullptr;
+ return handle.handles.size() > 0;
}
-bool box2d::is_handle_valid(b2World *handle) {
- return handle != nullptr;
+bool box2d::is_handle_valid(b2WorldId handle) {
+ return B2_IS_NON_NULL(handle);
}
-bool box2d::is_handle_valid(b2Fixture *handle) {
- return handle != nullptr;
+bool box2d::is_handle_valid(b2ShapeId handle) {
+ return B2_IS_NON_NULL(handle);
}
bool box2d::is_handle_valid(ShapeHandle handle) {
- return handle.count > 0 || handle.handles != nullptr;
+ return !handle.handles.empty();
}
-bool box2d::is_handle_valid(b2Body *handle) {
- return handle != nullptr;
+bool box2d::is_handle_valid(b2BodyId handle) {
+ return B2_IS_NON_NULL(handle);
}
-bool box2d::is_handle_valid(b2Joint *handle) {
- return handle != nullptr;
+bool box2d::is_handle_valid(b2JointId handle) {
+ return B2_IS_NON_NULL(handle);
}
-void box2d::joint_set_disable_collision(b2Joint *joint_handle,
+void box2d::joint_set_disable_collision(b2JointId joint_handle,
bool disable_collision) {
- joint_handle->SetCollideConnected(!disable_collision);
+ b2Joint_SetCollideConnected(joint_handle, !disable_collision);
}
-void box2d::joint_change_revolute_params(b2World *world_handle,
- b2Joint *joint_handle,
+// TODO
+void box2d::joint_change_revolute_params(b2JointId joint_handle,
real_t angular_limit_lower,
real_t angular_limit_upper,
bool angular_limit_enabled,
real_t motor_target_velocity,
bool motor_enabled) {
- b2RevoluteJoint *joint = (b2RevoluteJoint *)joint_handle;
- joint->SetLimits(angular_limit_lower, angular_limit_upper);
- joint->EnableLimit(angular_limit_enabled);
- joint->SetMotorSpeed(motor_target_velocity);
- joint->EnableMotor(motor_enabled);
-}
-
-b2Joint *box2d::joint_create_prismatic(b2World *world_handle,
- b2Body *body_handle_1,
- b2Body *body_handle_2,
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::joint_change_revolute_params: ", rtos(joint_handle.index));
+#endif
+ //joint->SetLimits(angular_limit_lower, angular_limit_upper);
+ b2RevoluteJoint_EnableMotor(joint_handle, motor_enabled);
+ b2RevoluteJoint_SetMotorSpeed(joint_handle, motor_target_velocity);
+ b2RevoluteJoint_EnableLimit(joint_handle, angular_limit_enabled);
+}
+
+b2JointId box2d::joint_create_prismatic(b2WorldId world_handle,
+ b2BodyId body_handle_1,
+ b2BodyId body_handle_2,
const b2Vec2 axis,
const b2Vec2 anchor_1,
const b2Vec2 anchor_2,
const b2Vec2 limits,
bool disable_collision) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::joint_create_prismatic: ", rtos(world_handle.index));
+#endif
b2PrismaticJointDef joint_def;
- joint_def.Initialize(body_handle_1, body_handle_2, anchor_1, axis);
joint_def.localAnchorA = anchor_1;
joint_def.localAnchorB = anchor_2;
joint_def.localAxisA = axis;
@@ -830,12 +995,12 @@ b2Joint *box2d::joint_create_prismatic(b2World *world_handle,
joint_def.upperTranslation = limits.x + limits.y * 2;
joint_def.enableLimit = true;
joint_def.collideConnected = !disable_collision;
- return world_handle->CreateJoint(&joint_def);
+ return b2CreatePrismaticJoint(world_handle, &joint_def);
}
-b2Joint *box2d::joint_create_revolute(b2World *world_handle,
- b2Body *body_handle_1,
- b2Body *body_handle_2,
+b2JointId box2d::joint_create_revolute(b2WorldId world_handle,
+ b2BodyId body_handle_1,
+ b2BodyId body_handle_2,
const b2Vec2 anchor_1,
const b2Vec2 anchor_2,
real_t angular_limit_lower,
@@ -844,8 +1009,11 @@ b2Joint *box2d::joint_create_revolute(b2World *world_handle,
real_t motor_target_velocity,
bool motor_enabled,
bool disable_collision) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::joint_create_revolute: ", rtos(world_handle.index));
+#endif
b2RevoluteJointDef joint_def;
- joint_def.Initialize(body_handle_1, body_handle_2, anchor_1);
joint_def.localAnchorA = anchor_1;
joint_def.localAnchorB = anchor_2;
joint_def.enableLimit = angular_limit_enabled;
@@ -855,23 +1023,24 @@ b2Joint *box2d::joint_create_revolute(b2World *world_handle,
joint_def.motorSpeed = motor_target_velocity;
joint_def.maxMotorTorque = 100000.0;
joint_def.collideConnected = !disable_collision;
- return world_handle->CreateJoint(&joint_def);
+ return b2CreateRevoluteJoint(world_handle, &joint_def);
}
-void box2d::joint_change_distance_joint(b2World *world_handle,
- b2Joint *joint_handle,
+void box2d::joint_change_distance_joint(b2JointId joint_handle,
real_t rest_length,
real_t stiffness,
real_t damping) {
- b2DistanceJoint *joint = (b2DistanceJoint *)joint_handle;
- joint->SetDamping(damping);
- joint->SetStiffness(stiffness);
- joint->SetLength(rest_length);
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::joint_change_distance_joint: ", rtos(joint_handle.index));
+#endif
+ b2DistanceJoint_SetLength(joint_handle, rest_length);
+ b2DistanceJoint_SetTuning(joint_handle, stiffness, damping);
}
-b2Joint *box2d::joint_create_distance_joint(b2World *world_handle,
- b2Body *body_handle_1,
- b2Body *body_handle_2,
+b2JointId box2d::joint_create_distance_joint(b2WorldId world_handle,
+ b2BodyId body_handle_1,
+ b2BodyId body_handle_2,
const b2Vec2 anchor_1,
const b2Vec2 anchor_2,
real_t rest_length,
@@ -879,25 +1048,34 @@ b2Joint *box2d::joint_create_distance_joint(b2World *world_handle,
real_t stiffness,
real_t damping,
bool disable_collision) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::joint_create_distance_joint: ", rtos(world_handle.index));
+#endif
b2DistanceJointDef joint_def;
- joint_def.bodyA = body_handle_1;
- joint_def.bodyB = body_handle_2;
+ joint_def.bodyIdA = body_handle_1;
+ joint_def.bodyIdB = body_handle_2;
joint_def.localAnchorA = anchor_1;
joint_def.localAnchorB = anchor_2;
joint_def.length = rest_length;
joint_def.maxLength = max_length;
joint_def.minLength = 0.0;
- joint_def.stiffness = stiffness;
- joint_def.damping = damping;
+ joint_def.hertz = stiffness;
+ joint_def.dampingRatio = damping;
joint_def.collideConnected = !disable_collision;
- return world_handle->CreateJoint(&joint_def);
+ return b2CreateDistanceJoint(world_handle, &joint_def);
}
-void box2d::joint_destroy(b2World *world_handle, b2Joint *joint_handle) {
- world_handle->DestroyJoint(joint_handle);
+void box2d::joint_destroy(b2JointId joint_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::joint_destroy: ", rtos(joint_handle.index));
+#endif
+ b2DestroyJoint(joint_handle);
}
-ShapeCastResult box2d::shape_casting(b2World *world_handle,
+// TODO
+ShapeCastResult box2d::shape_casting(b2WorldId world_handle,
const b2Vec2 motion,
ShapeInfo shape_info,
bool collide_with_body,
@@ -905,14 +1083,20 @@ ShapeCastResult box2d::shape_casting(b2World *world_handle,
QueryHandleExcludedCallback handle_excluded_callback,
const QueryExcludedInfo *handle_excluded_info,
double margin) {
- for (int i = 0; i < shape_info.handle.count; i++) {
- shape_info.handle.handles[i]->m_radius += margin;
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shape_casting: ", rtos(world_handle.index));
+#endif
+ for (int i = 0; i < shape_info.handle.handles.size(); i++) {
+ // TODO
+ //shape_info.handle.handles[i].m_radius += margin;
b2AABB shape_aabb;
b2AABB shape_aabb_motion;
b2AABB shape_aabb_total;
bool first_time = true;
b2Transform shape_transform = Transform2D_to_b2Transform(shape_info.body_transform * shape_info.transform);
b2Transform shape_transform_motion = shape_transform;
+ /*
shape_transform_motion.p += motion;
for (int j = 0; j < shape_info.handle.handles[i]->GetChildCount(); j++) {
shape_info.handle.handles[i]->ComputeAABB(&shape_aabb, shape_transform, j);
@@ -932,7 +1116,7 @@ ShapeCastResult box2d::shape_casting(b2World *world_handle,
ShapeCastResult result;
result.collided = false;
for (int j = 0; j < count; j++) {
- b2Body *other_body = hit_info_array[j].collider->GetBody();
+ b2BodyId other_body = hit_info_array[j].collider->GetBody();
Transform2D other_transform = collider_get_transform(world_handle, hit_info_array[j].collider);
// TODO take into consideration scale here?
Transform2D other_body_transform = b2Transform_to_Transform2D(other_body->GetTransform());
@@ -962,20 +1146,27 @@ ShapeCastResult box2d::shape_casting(b2World *world_handle,
if (result.collided) {
return result;
}
+ */
}
return ShapeCastResult{
false
};
}
+// TODO
ShapeCollideResult box2d::shape_collide(const b2Vec2 motion1,
ShapeInfo shape_info1,
const b2Vec2 motion2,
ShapeInfo shape_info2) {
- for (int i = 0; i < shape_info1.handle.count; i++) {
- for (int j = 0; j < shape_info2.handle.count; j++) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shape_collide: ");
+#endif
+ for (int i = 0; i < shape_info1.handle.handles.size(); i++) {
+ for (int j = 0; j < shape_info2.handle.handles.size(); j++) {
b2Transform transformA = Transform2D_to_b2Transform(shape_info1.body_transform * shape_info1.transform);
b2Transform transformB = Transform2D_to_b2Transform(shape_info2.body_transform * shape_info2.transform);
+ /*
b2TOIOutput toi_output = _time_of_impact(shape_info1.handle.handles[i],
transformA,
b2Vec2_zero,
@@ -995,6 +1186,7 @@ ShapeCollideResult box2d::shape_collide(const b2Vec2 motion1,
result.witness1 = distance_output.pointA;
result.witness2 = distance_output.pointB;
return result;
+ */
}
}
return ShapeCollideResult{
@@ -1003,114 +1195,141 @@ ShapeCollideResult box2d::shape_collide(const b2Vec2 motion1,
}
ShapeHandle box2d::shape_create_box(const b2Vec2 size) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shape_create_box: ");
+#endif
ERR_FAIL_COND_V(size.x < CMP_EPSILON, invalid_shape_handle());
ERR_FAIL_COND_V(size.y < CMP_EPSILON, invalid_shape_handle());
- b2Shape **shapes = (b2Shape **)memalloc((1) * sizeof(b2Shape *));
- b2PolygonShape *shape = memnew(b2PolygonShape);
- shape->SetAsBox(size.x * 0.5, size.y * 0.5);
- shapes[0] = shape;
+ b2Polygon polygon_shape = b2MakeBox(size.x * 0.5, size.y * 0.5);
return ShapeHandle{
- shapes,
- 1
+ std::vector{
+ { b2_polygonShape, { .polygon = polygon_shape } } }
};
}
ShapeHandle box2d::shape_create_capsule(real_t half_height, real_t radius) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shape_create_capsule: ");
+#endif
ERR_FAIL_COND_V(radius < CMP_EPSILON, invalid_shape_handle());
ERR_FAIL_COND_V(half_height < CMP_EPSILON, invalid_shape_handle());
ERR_FAIL_COND_V(half_height < radius, invalid_shape_handle());
- real_t half_height_circle = half_height - radius;
- ShapeHandle top_circle = shape_create_circle(radius, { 0.0, -half_height_circle });
- ERR_FAIL_COND_V(!is_handle_valid(top_circle), invalid_shape_handle());
- if (half_height - radius == 0.0) {
- return top_circle;
- }
- ShapeHandle bottom_circle = shape_create_circle(radius, { 0.0, half_height_circle });
- ERR_FAIL_COND_V(!is_handle_valid(bottom_circle), invalid_shape_handle());
- ShapeHandle square = shape_create_box({ radius * 2, half_height * 2 - radius * 2 });
- ERR_FAIL_COND_V(!is_handle_valid(square), invalid_shape_handle());
- b2Shape **shapes = (b2Shape **)memalloc((3) * sizeof(b2Shape *));
- // TODO fix this leak.
- shapes[0] = top_circle.handles[0];
- shapes[1] = bottom_circle.handles[0];
- shapes[2] = square.handles[0];
+ b2Capsule capsule_shape = {
+ { 0, -half_height },
+ { 0, half_height },
+ radius
+ };
return ShapeHandle{
- shapes,
- 3
+ std::vector{
+ { b2_capsuleShape, { .capsule = capsule_shape } } }
};
}
ShapeHandle box2d::shape_create_circle(real_t radius, b2Vec2 pos) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shape_create_circle: ");
+#endif
ERR_FAIL_COND_V(radius < CMP_EPSILON, invalid_shape_handle());
- b2Shape **shapes = (b2Shape **)memalloc((1) * sizeof(b2Shape *));
- b2CircleShape *shape = memnew(b2CircleShape);
- shape->m_radius = radius;
- shape->m_p = pos;
- shapes[0] = shape;
+ b2Circle circle_shape = {
+ pos,
+ radius
+ };
return ShapeHandle{
- shapes,
- 1
+ std::vector{
+ { b2_circleShape, { .circle = circle_shape } } }
};
}
+// TODO
ShapeHandle box2d::shape_create_concave_polyline(const b2Vec2 *points, size_t point_count) {
- b2Shape **shapes = (b2Shape **)memalloc((1) * sizeof(b2Shape *));
- b2ChainShape *shape = memnew(b2ChainShape);
- shape->CreateLoop(points, point_count);
- shapes[0] = shape;
- ERR_FAIL_COND_V(!shape->m_count, invalid_shape_handle());
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shape_create_concave_polyline: ");
+#endif
+ b2Hull hull;
+ ERR_FAIL_COND_V(point_count > b2_maxPolygonVertices, invalid_shape_handle());
+ for (int i = 0; i < point_count; i++) {
+ hull.points[i] = points[i];
+ }
+ hull.count = point_count;
+ b2Polygon polygon_shape = b2MakePolygon(&hull, 0.0);
return ShapeHandle{
- shapes,
- 1
+ std::vector{
+ { b2_polygonShape, { .polygon = polygon_shape } } }
};
}
+// TODO
ShapeHandle box2d::shape_create_convex_polyline(const b2Vec2 *points, size_t point_count) {
- b2Shape **shapes = (b2Shape **)memalloc((1) * sizeof(b2Shape *));
- b2PolygonShape *shape = memnew(b2PolygonShape);
- shape->Set(points, point_count);
- if (shape->m_count == 0) {
- ERR_FAIL_V(invalid_shape_handle());
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shape_create_convex_polyline: ");
+#endif
+ b2Hull hull;
+ ERR_FAIL_COND_V(point_count > b2_maxPolygonVertices, invalid_shape_handle());
+ for (int i = 0; i < point_count; i++) {
+ hull.points[i] = points[i];
}
- shapes[0] = shape;
+ hull.count = point_count;
+ b2Polygon polygon_shape = b2MakePolygon(&hull, 0.0);
return ShapeHandle{
- shapes,
- 1
+ std::vector{
+ { b2_polygonShape, polygon_shape } }
};
}
ShapeHandle box2d::shape_create_halfspace(const b2Vec2 normal, real_t distance) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shape_create_halfspace: ");
+#endif
real_t world_size = 1000000.0;
- b2Shape **shapes = (b2Shape **)memalloc((1) * sizeof(b2Shape *));
- b2PolygonShape *shape = memnew(b2PolygonShape);
b2Vec2 points[4];
- b2Vec2 right(normal.y, -normal.x);
- b2Vec2 left(-right);
- left *= world_size;
- right *= world_size;
- left = left + distance * normal;
- right = right + distance * normal;
+ b2Vec2 right{ normal.y, -normal.x };
+ b2Vec2 left{ -right.x, -right.y };
+ left = b2Vec2_mul(left, world_size);
+ right = b2Vec2_mul(right, world_size);
+ left = b2Vec2_add(left, b2Vec2_mul(normal, distance));
+ right = b2Vec2_add(right, b2Vec2_mul(normal, distance));
points[0] = left;
points[1] = right;
- points[2] = right - world_size * normal;
- points[3] = right - world_size * normal;
- bool result = shape->Set(points, 4);
- shapes[0] = shape;
- ERR_FAIL_COND_V(!result, invalid_shape_handle());
+ points[2] = b2Vec2_sub(right, b2Vec2_mul(normal, world_size));
+ points[3] = b2Vec2_sub(right, b2Vec2_mul(normal, world_size));
+
+ b2Hull hull;
+ ERR_FAIL_COND_V(4 > b2_maxPolygonVertices, invalid_shape_handle());
+ for (int i = 0; i < 4; i++) {
+ hull.points[i] = points[i];
+ }
+ hull.count = 4;
+ b2Polygon polygon_shape = b2MakePolygon(&hull, 0.0);
return ShapeHandle{
- shapes,
- 1
+ std::vector{
+ { b2_polygonShape, polygon_shape } }
};
}
void box2d::shape_destroy(ShapeHandle shape_handle) {
- memfree(shape_handle.handles);
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shape_destroy: ");
+#endif
+ shape_handle.handles.clear();
}
-ContactResult box2d::shapes_contact(b2World *world_handle,
+// TODO
+ContactResult box2d::shapes_contact(b2WorldId world_handle,
ShapeInfo shape_info1,
ShapeInfo shape_info2,
real_t margin) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::shapes_contact: ", rtos(world_handle.index));
+#endif
+ /*
for (int i = 0; i < shape_info1.handle.count; i++) {
for (int j = 0; j < shape_info2.handle.count; j++) {
b2Transform transform_A = Transform2D_to_b2Transform(shape_info1.body_transform * shape_info1.transform);
@@ -1170,65 +1389,99 @@ ContactResult box2d::shapes_contact(b2World *world_handle,
};
}
}
+ */
return ContactResult{
false
};
}
-b2World *box2d::world_create(const WorldSettings *settings) {
- return memnew(b2World(b2Vec2_zero));
+b2WorldId box2d::world_create(WorldSettings settings, SimulationSettings simulation_settings) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::world_create");
+#endif
+ b2WorldDef world_def = b2DefaultWorldDef();
+ world_def.gravity = simulation_settings.gravity;
+ return b2CreateWorld(&world_def);
}
-void box2d::world_destroy(b2World *world_handle) {
- memdelete(world_handle);
+void box2d::world_destroy(b2WorldId world_handle) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::world_destroy", rtos(world_handle.index));
+#endif
+ b2DestroyWorld(world_handle);
}
-size_t box2d::world_get_active_objects_count(b2World *world_handle) {
- return holder.active_objects[world_handle];
+void box2d::world_set_active_body_callback(b2WorldId world_handle, ActiveBodyCallback callback) {
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::world_set_active_body_callback", rtos(world_handle.index));
+#endif
+ holder.active_body_callbacks[handle_hash(world_handle)] = callback;
}
-void box2d::world_set_active_body_callback(b2World *world_handle, ActiveBodyCallback callback) {
- holder.active_body_callbacks[world_handle] = callback;
+bool presolve_fcn(b2ShapeId shapeIdA, b2ShapeId shapeIdB, b2Manifold *manifold, void *context) {
+ b2ContactFilter *callback = static_cast(context);
+ return callback->ShouldCollide(shapeIdA, shapeIdB, manifold);
}
-void box2d::world_set_collision_filter_callback(b2World *world_handle,
+void box2d::world_set_collision_filter_callback(b2WorldId world_handle,
b2ContactFilter *callback) {
- world_handle->SetContactFilter(callback);
-}
-
-void box2d::world_set_contact_listener(b2World *world_handle,
- b2ContactListener *callback) {
- world_handle->SetContactListener(callback);
-}
-
-void box2d::world_step(b2World *world_handle, const SimulationSettings *settings) {
- world_handle->SetGravity(settings->gravity);
- world_handle->Step(settings->dt, settings->max_velocity_iterations, settings->max_position_iterations);
- int active_objects = 0;
- if (holder.active_body_callbacks.has(world_handle)) {
- ActiveBodyCallback callback = holder.active_body_callbacks[world_handle];
- for (b2Body *body = world_handle->GetBodyList(); body != nullptr; body = body->GetNext()) {
- if (body->GetType() == b2_kinematicBody) {
- b2BodyUserData &userData = body->GetUserData();
- userData.old_angular_velocity = body->GetAngularVelocity();
- userData.old_linear_velocity = b2Vec2_to_Vector2(body->GetLinearVelocity());
- body->SetLinearVelocity(b2Vec2_zero);
- body->SetAngularVelocity(0);
+#ifdef B2_DEBUG
+ if (logging_enabled)
+ UtilityFunctions::print("box2d::world_set_collision_filter_callback", rtos(world_handle.index));
+#endif
+ b2World_SetPreSolveCallback(world_handle, presolve_fcn, callback);
+}
+
+// TODO
+void box2d::world_step(b2WorldId world_handle, SimulationSettings settings, std::vector active_bodies) {
+#ifdef B2_DEBUG
+ if (logging_enabled) {
+ UtilityFunctions::print("box2d::world_step", rtos(world_handle.index));
+ }
+#endif
+
+ //world_handle->SetGravity(settings->gravity);
+ // TODO set world gravity
+ b2World_Step(world_handle, settings.dt, settings.sub_step_count);
+ if (holder.active_body_callbacks.has(handle_hash(world_handle))) {
+ ActiveBodyCallback callback = holder.active_body_callbacks[handle_hash(world_handle)];
+ b2BodyEvents bodyEvents = b2World_GetBodyEvents(world_handle);
+ b2SensorEvents sensorEvents = b2World_GetSensorEvents(world_handle);
+ // get bodies from active_bodies vector
+ for (b2BodyId body_handle : active_bodies) {
+ b2BodyType type = b2Body_GetType(body_handle);
+ b2BodyUserData *userData = get_body_user_data(body_handle);
+ if (type == b2_kinematicBody) {
+ userData->old_angular_velocity = b2Body_GetAngularVelocity(body_handle);
+ userData->old_linear_velocity = b2Vec2_to_Vector2(b2Body_GetLinearVelocity(body_handle));
+ b2Body_SetLinearVelocity(body_handle, b2Vec2_zero);
+ b2Body_SetAngularVelocity(body_handle, 0.0);
}
- Vector2 constant_force = body->GetUserData().constant_force;
+ Vector2 constant_force = userData->constant_force;
if (constant_force != Vector2()) {
- body->ApplyForceToCenter(Vector2_to_b2Vec2(constant_force), true);
+ b2Body_ApplyForceToCenter(body_handle, Vector2_to_b2Vec2(constant_force), true);
}
- real_t constant_torque = body->GetUserData().constant_torque;
+ real_t constant_torque = userData->constant_torque;
if (constant_torque != 0.0) {
- body->ApplyTorque(constant_torque, true);
+ b2Body_ApplyTorque(body_handle, constant_torque, true);
}
- if (body->IsAwake() && body->GetUserData().collision_object->get_type() == Box2DCollisionObject2D::Type::TYPE_BODY) {
- active_objects++;
- ActiveBodyInfo info{ body, body->GetUserData() };
+ if (userData->collision_object->get_type() == Box2DCollisionObject2D::Type::TYPE_BODY) {
+ ActiveBodyInfo info{ body_handle, *userData };
callback(info);
}
}
}
- holder.active_objects[world_handle] = active_objects;
}
+
+int box2d::assert_callback(const char *condition, const char *fileName, int lineNumber) {
+ ERR_PRINT("Assertion failed: " + String(condition) + " at " + String(fileName) + ":" + rtos(lineNumber));
+ return 0;
+}
+
+// TODO maybe make a class if we have this exposed like so.
+void box2d::set_logging_enabled(bool enabled) {
+ logging_enabled = enabled;
+}
\ No newline at end of file
diff --git a/src/box2d-wrapper/box2d_wrapper.h b/src/box2d-wrapper/box2d_wrapper.h
index d612a56..09af4c9 100644
--- a/src/box2d-wrapper/box2d_wrapper.h
+++ b/src/box2d-wrapper/box2d_wrapper.h
@@ -1,18 +1,59 @@
#ifndef BOX2D_WRAPPER_H
#define BOX2D_WRAPPER_H
-#include "../b2_user_settings.h"
-
#include
+#include
#include
#include
#include
+#include
#include
+#include
+
+// Tunable Constants
+
+// You can use this to change the length scale used by your game.
+// For example for inches you could use 39.4.
+#ifdef b2_lengthUnitsPerMeter
+#undef b2_lengthUnitsPerMeter
+#endif
+#define b2_lengthUnitsPerMeter 100.0f
+
+// The maximum number of vertices on a convex polygon. You cannot increase
+// this too much because b2BlockAllocator has a maximum object size.
+#ifdef b2_maxPolygonVertices
+#undef b2_maxPolygonVertices
+#endif
+#define b2_maxPolygonVertices 64
+
+class Box2DCollisionObject2D;
+class Box2DShape2D;
+
+class b2ContactFilter {
+public:
+ virtual bool ShouldCollide(b2ShapeId fixtureA, b2ShapeId fixtureB, b2Manifold *manifold) = 0;
+};
-/* Generated with cbindgen:0.26.0 */
+// You can define this to inject whatever data you want in b2Fixture
+struct b2FixtureUserData {
+ b2FixtureUserData() :
+ shape_idx(-1), transform(), collision_object(nullptr) {}
-class b2FixtureUserData;
-class b2BodyUserData;
+ godot::Transform2D transform;
+ int shape_idx;
+ Box2DCollisionObject2D *collision_object;
+};
+struct b2BodyUserData {
+ b2BodyUserData() :
+ old_linear_velocity(0, 0), old_angular_velocity(0), constant_force(0, 0), constant_torque(0), collision_object(nullptr) {}
+
+ // for kinematic body
+ godot::Vector2 old_linear_velocity;
+ real_t old_angular_velocity;
+ godot::Vector2 constant_force;
+ real_t constant_torque;
+ Box2DCollisionObject2D *collision_object;
+};
namespace box2d {
@@ -21,14 +62,22 @@ struct Material {
real_t restitution;
};
-struct ShapeHandle {
- b2Shape **handles;
- int count;
+struct ShapeData {
+ b2ShapeType type;
+ union {
+ b2Polygon polygon;
+ b2Circle circle;
+ b2Capsule capsule;
+ b2Segment segment;
+ } data;
};
struct FixtureHandle {
- b2Fixture **handles;
- int count;
+ std::vector handles;
+};
+
+struct ShapeHandle {
+ std::vector handles;
};
struct ShapeInfo {
@@ -40,7 +89,7 @@ struct ShapeInfo {
struct QueryExcludedInfo {
uint32_t query_collision_layer_mask;
uint64_t query_canvas_instance_id;
- b2Fixture **query_exclude;
+ b2ShapeId *query_exclude;
uint32_t query_exclude_size;
int64_t query_exclude_body;
};
@@ -53,19 +102,19 @@ struct WorldSettings {
};
struct PointHitInfo {
- b2Fixture *collider;
+ //b2ShapeId collider;
b2FixtureUserData user_data;
};
-using QueryHandleExcludedCallback = bool (*)(b2World *world_handle,
- b2Fixture *collider_handle,
+using QueryHandleExcludedCallback = bool (*)(b2WorldId world_handle,
+ b2ShapeId collider_handle,
b2FixtureUserData user_data,
const QueryExcludedInfo *handle_excluded_info);
struct RayHitInfo {
b2Vec2 position;
b2Vec2 normal;
- b2Fixture *collider;
+ //b2ShapeId collider;
b2FixtureUserData user_data;
};
@@ -82,7 +131,7 @@ struct ShapeCastResult {
b2Vec2 witness2;
b2Vec2 normal1;
b2Vec2 normal2;
- b2Fixture *collider;
+ b2ShapeId collider;
b2FixtureUserData user_data;
};
@@ -97,7 +146,7 @@ struct ContactResult {
};
struct ActiveBodyInfo {
- b2Body *body_handle;
+ b2BodyId body_handle;
b2BodyUserData body_user_data;
};
@@ -109,11 +158,11 @@ struct CollisionFilterInfo {
bool is_valid;
};
-using CollisionFilterCallback = bool (*)(b2World *world_handle, const CollisionFilterInfo *filter_info);
+using CollisionFilterCallback = bool (*)(b2WorldId world_handle, const CollisionFilterInfo *filter_info);
struct CollisionEventInfo {
- b2Fixture *collider1;
- b2Fixture *collider2;
+ //b2ShapeId collider1;
+ //b2ShapeId collider2;
b2FixtureUserData user_data1;
b2FixtureUserData user_data2;
bool is_sensor;
@@ -122,18 +171,18 @@ struct CollisionEventInfo {
bool is_valid;
};
-using CollisionEventCallback = void (*)(b2World *world_handle, const CollisionEventInfo *event_info);
+using CollisionEventCallback = void (*)(b2WorldId world_handle, const CollisionEventInfo *event_info);
struct ContactForceEventInfo {
- b2Fixture *collider1;
- b2Fixture *collider2;
+ //b2ShapeId collider1;
+ //b2ShapeId collider2;
b2FixtureUserData user_data1;
b2FixtureUserData user_data2;
bool is_valid;
};
-using ContactForceEventCallback = bool (*)(b2World *world_handle,
- const ContactForceEventInfo *event_info);
+using ContactForceEventCallback = bool (*)(b2WorldId world_handle,
+ const ContactForceEventInfo &event_info);
struct ContactPointInfo {
b2Vec2 local_pos_1;
@@ -150,9 +199,9 @@ struct ContactPointInfo {
real_t tangent_impulse_2;
};
-using ContactPointCallback = bool (*)(b2World *world_handle,
- const ContactPointInfo *contact_info,
- const ContactForceEventInfo *event_info);
+using ContactPointCallback = bool (*)(b2WorldId world_handle,
+ const ContactPointInfo &contact_info,
+ const ContactForceEventInfo &event_info);
struct OneWayDirection {
bool body1;
@@ -162,122 +211,101 @@ struct OneWayDirection {
real_t last_timestep;
};
-using CollisionModifyContactsCallback = OneWayDirection (*)(b2World *world_handle,
- const CollisionFilterInfo *filter_info);
+using CollisionModifyContactsCallback = OneWayDirection (*)(b2WorldId world_handle,
+ const CollisionFilterInfo &filter_info);
struct SimulationSettings {
real_t dt;
- size_t max_velocity_iterations;
- size_t max_position_iterations;
+ size_t sub_step_count;
b2Vec2 gravity;
};
b2Vec2 Vector2_to_b2Vec2(godot::Vector2 vec);
godot::Vector2 b2Vec2_to_Vector2(b2Vec2 vec);
-bool are_handles_equal(b2World *handle1, b2World *handle2);
-bool are_handles_equal(b2Body *handle1, b2Body *handle2);
-bool are_handles_equal(FixtureHandle handle1, FixtureHandle handle2);
-bool are_handles_equal(ShapeHandle handle1, ShapeHandle handle2);
-bool are_handles_equal(b2Joint *handle1, b2Joint *handle2);
-bool are_handles_equal(b2Fixture *handle1, b2Fixture *handle2);
+b2Vec2 b2Vec2_add(b2Vec2 vec, b2Vec2 other);
+b2Vec2 b2Vec2_mul(b2Vec2 vec, real_t other);
+b2Vec2 b2Vec2_sub(b2Vec2 vec, b2Vec2 other);
-void body_add_force(b2World *world_handle, b2Body *body_handle, const b2Vec2 force);
+void body_add_force(b2BodyId body_handle, b2Vec2 force);
-void body_add_torque(b2World *world_handle, b2Body *body_handle, real_t torque);
+void body_add_torque(b2BodyId body_handle, real_t torque);
-void body_apply_impulse(b2World *world_handle, b2Body *body_handle, const b2Vec2 impulse);
+void body_apply_impulse(b2BodyId body_handle, b2Vec2 impulse);
-void body_apply_impulse_at_point(b2World *world_handle,
- b2Body *body_handle,
- const b2Vec2 impulse,
- const b2Vec2 point);
+void body_apply_impulse_at_point(b2BodyId body_handle, b2Vec2 impulse, b2Vec2 point);
-void body_apply_torque_impulse(b2World *world_handle, b2Body *body_handle, real_t torque_impulse);
+void body_apply_torque_impulse(b2BodyId body_handle, real_t torque_impulse);
-void body_change_mode(b2World *world_handle, b2Body *body_handle, b2BodyType body_type, bool wakeup, bool fixed_rotation);
+void body_change_mode(b2BodyId body_handle, b2BodyType body_type, bool fixed_rotation);
-b2Body *body_create(b2World *world_handle,
- const b2Vec2 pos,
+b2BodyId body_create(b2WorldId world_handle,
+ b2Vec2 pos,
real_t rot,
- const b2BodyUserData &user_data,
+ b2BodyUserData *user_data,
b2BodyType body_type);
-void body_destroy(b2World *world_handle, b2Body *body_handle);
+void body_destroy(b2BodyId body_handle);
-void body_force_sleep(b2World *world_handle, b2Body *body_handle);
+void body_force_sleep(b2BodyId body_handle);
-real_t body_get_angle(b2World *world_handle, b2Body *body_handle);
+real_t body_get_angle(b2BodyId body_handle);
-real_t body_get_angular_velocity(b2World *world_handle, b2Body *body_handle);
+real_t body_get_angular_velocity(b2BodyId body_handle);
-b2Vec2 body_get_constant_force(b2World *world_handle, b2Body *body_handle);
+b2Vec2 body_get_constant_force(b2BodyId body_handle);
-real_t body_get_constant_torque(b2World *world_handle, b2Body *body_handle);
+real_t body_get_constant_torque(b2BodyId body_handle);
-b2Vec2 body_get_linear_velocity(b2World *world_handle, b2Body *body_handle);
+b2Vec2 body_get_linear_velocity(b2BodyId body_handle);
-b2Vec2 body_get_position(b2World *world_handle, b2Body *body_handle);
+b2Vec2 body_get_position(b2BodyId body_handle);
-bool body_is_ccd_enabled(b2World *world_handle, b2Body *body_handle);
+bool body_is_ccd_enabled(b2BodyId body_handle);
-void body_reset_forces(b2World *world_handle, b2Body *body_handle);
+void body_reset_forces(b2BodyId body_handle);
-void body_reset_torques(b2World *world_handle, b2Body *body_handle);
+void body_reset_torques(b2BodyId body_handle);
-void body_set_angular_damping(b2World *world_handle, b2Body *body_handle, real_t angular_damping);
+void body_set_angular_damping(b2BodyId body_handle, real_t angular_damping);
-void body_set_angular_velocity(b2World *world_handle, b2Body *body_handle, real_t vel);
+void body_set_angular_velocity(b2BodyId body_handle, real_t vel);
-void body_set_can_sleep(b2World *world_handle, b2Body *body_handle, bool can_sleep);
+void body_set_can_sleep(b2BodyId body_handle, bool can_sleep);
-void body_set_ccd_enabled(b2World *world_handle, b2Body *body_handle, bool enable);
+void body_set_ccd_enabled(b2BodyId body_handle, bool enable);
-void body_set_gravity_scale(b2World *world_handle,
- b2Body *body_handle,
- real_t gravity_scale,
- bool wake_up);
+void body_set_gravity_scale(b2BodyId body_handle, real_t gravity_scale);
-void body_set_linear_damping(b2World *world_handle, b2Body *body_handle, real_t linear_damping);
+void body_set_linear_damping(b2BodyId body_handle, real_t linear_damping);
-void body_set_linear_velocity(b2World *world_handle, b2Body *body_handle, const b2Vec2 vel);
+void body_set_linear_velocity(b2BodyId body_handle, b2Vec2 vel);
-void body_set_mass_properties(b2World *world_handle,
- b2Body *body_handle,
- real_t mass,
- real_t inertia,
- const b2Vec2 local_com,
- bool wake_up,
- bool force_update);
+void body_set_mass_properties(b2BodyId body_handle, real_t mass, real_t inertia, b2Vec2 local_com);
-void body_set_transform(b2World *world_handle,
- b2Body *body_handle,
- const b2Vec2 pos,
- real_t rot,
- bool wake_up,
- real_t step);
+void body_set_transform(b2BodyId body_handle, b2Vec2 pos, real_t rot, real_t step);
-void body_update_material(b2World *world_handle, b2Body *body_handle, const Material *mat);
+void body_update_material(b2BodyId body_handle, Material mat);
-void body_wake_up(b2World *world_handle, b2Body *body_handle, bool strong);
+void body_wake_up(b2BodyId body_handle);
-FixtureHandle collider_create_sensor(b2World *world_handle,
- ShapeHandle shape_handle,
- b2Body *body_handle,
- b2FixtureUserData user_data);
+FixtureHandle collider_create_sensor(b2WorldId world_handle,
+ ShapeHandle shape_handles,
+ b2BodyId body_handle,
+ b2FixtureUserData *user_data);
-FixtureHandle collider_create_solid(b2World *world_handle,
+FixtureHandle collider_create_solid(b2WorldId world_handle,
ShapeHandle shape_handle,
- const Material *mat,
- b2Body *body_handle,
- b2FixtureUserData user_data);
+ Material mat,
+ b2BodyId body_handle,
+ b2FixtureUserData *user_data);
-void collider_destroy(b2World *world_handle, FixtureHandle handle);
+void collider_destroy(FixtureHandle handle);
-void collider_set_transform(b2World *world_handle, FixtureHandle handle, ShapeInfo shape_info);
+void collider_set_transform(b2WorldId world_handle, FixtureHandle handle, ShapeInfo shape_info);
-godot::Transform2D collider_get_transform(b2World *world_handle, FixtureHandle handle);
-godot::Transform2D collider_get_transform(b2World *world_handle, b2Fixture *handle);
+godot::Transform2D collider_get_transform(b2WorldId world_handle, FixtureHandle handle);
+godot::Transform2D collider_get_transform(b2WorldId world_handle, b2ShapeId handle);
Material default_material();
@@ -285,7 +313,7 @@ QueryExcludedInfo default_query_excluded_info();
WorldSettings default_world_settings();
-size_t intersect_aabb(b2World *world_handle,
+size_t intersect_aabb(b2WorldId world_handle,
const b2Vec2 aabb_min,
const b2Vec2 aabb_max,
bool collide_with_body,
@@ -295,7 +323,7 @@ size_t intersect_aabb(b2World *world_handle,
QueryHandleExcludedCallback handle_excluded_callback,
const QueryExcludedInfo *handle_excluded_info);
-size_t intersect_point(b2World *world_handle,
+size_t intersect_point(b2WorldId world_handle,
const b2Vec2 position,
bool collide_with_body,
bool collide_with_area,
@@ -304,7 +332,7 @@ size_t intersect_point(b2World *world_handle,
QueryHandleExcludedCallback handle_excluded_callback,
const QueryExcludedInfo *handle_excluded_info);
-bool intersect_ray(b2World *world_handle,
+bool intersect_ray(b2WorldId world_handle,
const b2Vec2 from,
const b2Vec2 dir,
real_t length,
@@ -315,7 +343,7 @@ bool intersect_ray(b2World *world_handle,
QueryHandleExcludedCallback handle_excluded_callback,
const QueryExcludedInfo *handle_excluded_info);
-size_t intersect_shape(b2World *world_handle,
+size_t intersect_shape(b2WorldId world_handle,
ShapeInfo shape_info,
bool collide_with_body,
bool collide_with_area,
@@ -325,48 +353,47 @@ size_t intersect_shape(b2World *world_handle,
const QueryExcludedInfo *handle_excluded_info,
double margin);
-b2World *invalid_world_handle();
+b2WorldId invalid_world_handle();
FixtureHandle invalid_fixture_handle();
-b2Body *invalid_body_handle();
+b2BodyId invalid_body_handle();
ShapeHandle invalid_shape_handle();
-b2Joint *invalid_joint_handle();
+b2JointId invalid_joint_handle();
b2FixtureUserData invalid_fixture_user_data();
b2BodyUserData invalid_body_user_data();
bool is_handle_valid(FixtureHandle handle);
-bool is_handle_valid(b2World *handle);
+bool is_handle_valid(b2WorldId handle);
bool is_handle_valid(ShapeHandle handle);
-bool is_handle_valid(b2Body *handle);
-bool is_handle_valid(b2Joint *handle);
-bool is_handle_valid(b2Fixture *handle);
+bool is_handle_valid(b2BodyId handle);
+bool is_handle_valid(b2JointId handle);
+bool is_handle_valid(b2ShapeId handle);
bool is_user_data_valid(b2FixtureUserData user_data);
bool is_user_data_valid(b2BodyUserData user_data);
-void joint_set_disable_collision(b2Joint *joint_handle,
+void joint_set_disable_collision(b2JointId joint_handle,
bool disable_collision);
-void joint_change_revolute_params(b2World *world_handle,
- b2Joint *joint_handle,
+void joint_change_revolute_params(b2JointId joint_handle,
real_t angular_limit_lower,
real_t angular_limit_upper,
bool angular_limit_enabled,
real_t motor_target_velocity,
bool motor_enabled);
-b2Joint *joint_create_prismatic(b2World *world_handle,
- b2Body *body_handle_1,
- b2Body *body_handle_2,
+b2JointId joint_create_prismatic(b2WorldId world_handle,
+ b2BodyId body_handle_1,
+ b2BodyId body_handle_2,
const b2Vec2 axis,
const b2Vec2 anchor_1,
const b2Vec2 anchor_2,
const b2Vec2 limits,
bool disable_collision);
-b2Joint *joint_create_revolute(b2World *world_handle,
- b2Body *body_handle_1,
- b2Body *body_handle_2,
+b2JointId joint_create_revolute(b2WorldId world_handle,
+ b2BodyId body_handle_1,
+ b2BodyId body_handle_2,
const b2Vec2 anchor_1,
const b2Vec2 anchor_2,
real_t angular_limit_lower,
@@ -376,9 +403,9 @@ b2Joint *joint_create_revolute(b2World *world_handle,
bool motor_enabled,
bool disable_collision);
-b2Joint *joint_create_distance_joint(b2World *world_handle,
- b2Body *body_handle_1,
- b2Body *body_handle_2,
+b2JointId joint_create_distance_joint(b2WorldId world_handle,
+ b2BodyId body_handle_1,
+ b2BodyId body_handle_2,
const b2Vec2 anchor_1,
const b2Vec2 anchor_2,
real_t rest_length,
@@ -387,15 +414,14 @@ b2Joint *joint_create_distance_joint(b2World *world_handle,
real_t damping,
bool disable_collision);
-void joint_change_distance_joint(b2World *world_handle,
- b2Joint *joint_handle,
+void joint_change_distance_joint(b2JointId joint_handle,
real_t rest_length,
real_t stiffness,
real_t damping);
-void joint_destroy(b2World *world_handle, b2Joint *joint_handle);
+void joint_destroy(b2JointId joint_handle);
-ShapeCastResult shape_casting(b2World *world_handle,
+ShapeCastResult shape_casting(b2WorldId world_handle,
const b2Vec2 motion,
ShapeInfo shape_info,
bool collide_with_body,
@@ -413,7 +439,7 @@ ShapeHandle shape_create_box(const b2Vec2 size);
ShapeHandle shape_create_capsule(real_t half_height, real_t radius);
-ShapeHandle shape_create_circle(real_t radius, b2Vec2 = b2Vec2_zero);
+ShapeHandle shape_create_circle(real_t radius, b2Vec2 = { 0, 0 });
ShapeHandle shape_create_concave_polyline(const b2Vec2 *points, size_t point_count);
@@ -423,26 +449,27 @@ ShapeHandle shape_create_halfspace(const b2Vec2 normal, real_t distance);
void shape_destroy(ShapeHandle shape_handle);
-ContactResult shapes_contact(b2World *world_handle,
+ContactResult shapes_contact(b2WorldId world_handle,
ShapeInfo shape_info1,
ShapeInfo shape_info2,
real_t margin);
-b2World *world_create(const WorldSettings *settings);
+b2WorldId world_create(WorldSettings settings, SimulationSettings simulation_settings);
-void world_destroy(b2World *world_handle);
+void world_destroy(b2WorldId world_handle);
-size_t world_get_active_objects_count(b2World *world_handle);
+void world_set_active_body_callback(b2WorldId world_handle, ActiveBodyCallback callback);
-void world_set_active_body_callback(b2World *world_handle, ActiveBodyCallback callback);
-
-void world_set_collision_filter_callback(b2World *world_handle,
+void world_set_collision_filter_callback(b2WorldId world_handle,
b2ContactFilter *callback);
-void world_set_contact_listener(b2World *world_handle,
- b2ContactListener *callback);
+void collider_set_contact_force_events_enabled(FixtureHandle collider_handle, bool send_contacts);
+
+void world_step(b2WorldId world_handle, const SimulationSettings settings, std::vector active_bodies);
+
+int assert_callback(const char *condition, const char *fileName, int lineNumber);
-void world_step(b2World *world_handle, const SimulationSettings *settings);
+void set_logging_enabled(bool enabled);
} // namespace box2d
diff --git a/src/box2d_include.h b/src/box2d_include.h
index b483603..021f308 100644
--- a/src/box2d_include.h
+++ b/src/box2d_include.h
@@ -1,7 +1,6 @@
#ifndef BOX2D_INCLUDE_H
#define BOX2D_INCLUDE_H
-#include "b2_user_settings.h"
#include "box2d-wrapper/box2d_wrapper.h"
#include
@@ -11,23 +10,21 @@ using namespace godot;
namespace box2d {
-inline uint32_t handle_hash(b2World *handle) {
- return hash_one_uint64(uint64_t(handle));
- //uint64_t combined = uint64_t(handle.id) + (uint64_t(handle.generation) << 32);
- //return hash_one_uint64(combined);
+inline uint32_t handle_hash(b2WorldId handle) {
+ uint64_t combined = uint64_t(handle.index) + (uint64_t(handle.revision) << 32);
+ return hash_one_uint64(combined);
}
-inline uint32_t handle_hash(b2Fixture *handle) {
- return hash_one_uint64(uint64_t(handle));
- //uint64_t combined = uint64_t(handle.id) + (uint64_t(handle.generation) << 32);
- //return hash_one_uint64(combined);
+inline uint32_t handle_hash(b2ShapeId handle) {
+ uint64_t combined = uint64_t(handle.index) + (uint64_t(handle.world) << 32) + (uint64_t(handle.revision) << 48);
+ return hash_one_uint64(combined);
}
-inline uint64_t handle_pair_hash(b2World *handle1, b2World *handle2) {
+inline uint64_t handle_pair_hash(b2WorldId handle1, b2WorldId handle2) {
uint64_t hash1 = handle_hash(handle1);
uint64_t hash2 = handle_hash(handle2);
return hash1 + (hash2 << 32);
}
-inline uint64_t handle_pair_hash(b2Fixture *handle1, b2Fixture *handle2) {
+inline uint64_t handle_pair_hash(b2ShapeId handle1, b2ShapeId handle2) {
uint64_t hash1 = handle_hash(handle1);
uint64_t hash2 = handle_hash(handle2);
return hash1 + (hash2 << 32);
diff --git a/src/joints/box2d_damped_spring_joint_2d.cpp b/src/joints/box2d_damped_spring_joint_2d.cpp
index c1cb658..13572a0 100644
--- a/src/joints/box2d_damped_spring_joint_2d.cpp
+++ b/src/joints/box2d_damped_spring_joint_2d.cpp
@@ -13,9 +13,8 @@ void Box2DDampedSpringJoint2D::set_param(PhysicsServer2D::DampedSpringParam p_pa
stiffness = p_value;
} break;
}
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
ERR_FAIL_COND(!box2d::is_handle_valid(handle));
- box2d::joint_change_distance_joint(space_handle, handle, rest_length, stiffness, damping);
+ box2d::joint_change_distance_joint(handle, rest_length, stiffness, damping);
}
real_t Box2DDampedSpringJoint2D::get_param(PhysicsServer2D::DampedSpringParam p_param) const {
@@ -44,7 +43,7 @@ Box2DDampedSpringJoint2D::Box2DDampedSpringJoint2D(const Vector2 &p_anchor_a, co
ERR_FAIL_COND(!p_body_a->get_space());
ERR_FAIL_COND(p_body_a->get_space() != p_body_b->get_space());
- space_handle = p_body_a->get_space()->get_handle();
+ b2WorldId space_handle = p_body_a->get_space()->get_handle();
ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
handle = box2d::joint_create_distance_joint(space_handle, p_body_a->get_body_handle(), p_body_b->get_body_handle(), box2d_anchor_A, box2d_anchor_B, rest_length, p_anchor_a.distance_to(p_anchor_b), stiffness, damping, is_disabled_collisions_between_bodies());
ERR_FAIL_COND(!box2d::is_handle_valid(handle));
diff --git a/src/joints/box2d_groove_joint_2d.cpp b/src/joints/box2d_groove_joint_2d.cpp
index b202ce9..844fe99 100644
--- a/src/joints/box2d_groove_joint_2d.cpp
+++ b/src/joints/box2d_groove_joint_2d.cpp
@@ -20,7 +20,7 @@ Box2DGrooveJoint2D::Box2DGrooveJoint2D(const Vector2 &p_a_groove1, const Vector2
ERR_FAIL_COND(!p_body_a->get_space());
ERR_FAIL_COND(p_body_a->get_space() != p_body_b->get_space());
- space_handle = p_body_a->get_space()->get_handle();
+ b2WorldId space_handle = p_body_a->get_space()->get_handle();
ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
handle = box2d::joint_create_prismatic(space_handle, p_body_a->get_body_handle(), p_body_b->get_body_handle(), box2d_axis, box2d_anchor_A, box2d_anchor_B, box2d_limits, is_disabled_collisions_between_bodies());
ERR_FAIL_COND(!box2d::is_handle_valid(handle));
diff --git a/src/joints/box2d_joint_2d.cpp b/src/joints/box2d_joint_2d.cpp
index 69a94ee..7abcb93 100644
--- a/src/joints/box2d_joint_2d.cpp
+++ b/src/joints/box2d_joint_2d.cpp
@@ -22,7 +22,6 @@ void Box2DJoint2D::disable_collisions_between_bodies(const bool p_disabled) {
Box2DJoint2D::~Box2DJoint2D() {
if (box2d::is_handle_valid(handle)) {
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
- box2d::joint_destroy(space_handle, handle);
+ box2d::joint_destroy(handle);
}
};
diff --git a/src/joints/box2d_joint_2d.h b/src/joints/box2d_joint_2d.h
index 5d6d8f3..5e27917 100644
--- a/src/joints/box2d_joint_2d.h
+++ b/src/joints/box2d_joint_2d.h
@@ -17,8 +17,7 @@ class Box2DJoint2D {
Box2DBody2D *A;
Box2DBody2D *B;
- b2World *space_handle = box2d::invalid_world_handle();
- b2Joint *handle = box2d::invalid_joint_handle();
+ b2JointId handle = box2d::invalid_joint_handle();
public:
_FORCE_INLINE_ void set_rid(const RID &p_rid) { rid = p_rid; }
diff --git a/src/joints/box2d_pin_joint_2d.cpp b/src/joints/box2d_pin_joint_2d.cpp
index 89d291c..43f9e72 100644
--- a/src/joints/box2d_pin_joint_2d.cpp
+++ b/src/joints/box2d_pin_joint_2d.cpp
@@ -16,9 +16,8 @@ void Box2DPinJoint2D::set_param(PhysicsServer2D::PinJointParam p_param, real_t p
return;
}
}
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
ERR_FAIL_COND(!box2d::is_handle_valid(handle));
- box2d::joint_change_revolute_params(space_handle, handle, angular_limit_lower, angular_limit_upper, angular_limit_enabled, motor_target_velocity, motor_enabled);
+ box2d::joint_change_revolute_params(handle, angular_limit_lower, angular_limit_upper, angular_limit_enabled, motor_target_velocity, motor_enabled);
}
real_t Box2DPinJoint2D::get_param(PhysicsServer2D::PinJointParam p_param) const {
@@ -48,9 +47,8 @@ void Box2DPinJoint2D::set_flag(PhysicsServer2D::PinJointFlag p_flag, bool p_enab
motor_enabled = p_enabled;
} break;
}
- ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
ERR_FAIL_COND(!box2d::is_handle_valid(handle));
- box2d::joint_change_revolute_params(space_handle, handle, angular_limit_lower, angular_limit_upper, angular_limit_enabled, motor_target_velocity, motor_enabled);
+ box2d::joint_change_revolute_params(handle, angular_limit_lower, angular_limit_upper, angular_limit_enabled, motor_target_velocity, motor_enabled);
}
bool Box2DPinJoint2D::get_flag(PhysicsServer2D::PinJointFlag p_flag) const {
@@ -75,7 +73,7 @@ Box2DPinJoint2D::Box2DPinJoint2D(const Vector2 &p_pos, Box2DBody2D *p_body_a, Bo
ERR_FAIL_COND(!p_body_a->get_space());
ERR_FAIL_COND(p_body_a->get_space() != p_body_b->get_space());
- space_handle = p_body_a->get_space()->get_handle();
+ b2WorldId space_handle = p_body_a->get_space()->get_handle();
ERR_FAIL_COND(!box2d::is_handle_valid(space_handle));
handle = box2d::joint_create_revolute(space_handle, p_body_a->get_body_handle(), p_body_b->get_body_handle(), box2d_anchor_A, box2d_anchor_B, angular_limit_lower, angular_limit_upper, angular_limit_enabled, motor_target_velocity, motor_enabled, is_disabled_collisions_between_bodies());
ERR_FAIL_COND(!box2d::is_handle_valid(handle));
diff --git a/src/register_types.cpp b/src/register_types.cpp
index 7ef9d6e..139715b 100644
--- a/src/register_types.cpp
+++ b/src/register_types.cpp
@@ -40,6 +40,8 @@ void initialize_box2d_module(ModuleInitializationLevel p_level) {
} break;
case MODULE_INITIALIZATION_LEVEL_SCENE: {
Box2DProjectSettings::register_settings();
+ b2SetAssertFcn(box2d::assert_callback);
+ box2d::set_logging_enabled(Box2DProjectSettings::get_logging_enabled());
} break;
default: {
} break;
diff --git a/src/servers/box2d_physics_server_2d.cpp b/src/servers/box2d_physics_server_2d.cpp
index 8120d28..e154761 100644
--- a/src/servers/box2d_physics_server_2d.cpp
+++ b/src/servers/box2d_physics_server_2d.cpp
@@ -47,9 +47,6 @@ RID Box2DPhysicsServer2D::_shape_create(ShapeType p_shape) {
case SHAPE_CONCAVE_POLYGON: {
shape = memnew(Box2DConcavePolygonShape2D);
} break;
- case SHAPE_CUSTOM: {
- ERR_FAIL_V_MSG(RID(), "Unsupported shape");
- } break;
default:
ERR_FAIL_V_MSG(RID(), "Unsupported shape");
}
diff --git a/src/servers/box2d_physics_server_2d.h b/src/servers/box2d_physics_server_2d.h
index 89bb0ad..321ceaa 100644
--- a/src/servers/box2d_physics_server_2d.h
+++ b/src/servers/box2d_physics_server_2d.h
@@ -286,7 +286,7 @@ class Box2DPhysicsServer2D : public PhysicsServer2DExtension {
int get_frame() { return frame; }
- Box2DSpace2D *get_active_space(b2World *p_handle) const {
+ Box2DSpace2D *get_active_space(b2WorldId p_handle) const {
ERR_FAIL_COND_V(!box2d::is_handle_valid(p_handle), nullptr);
return active_spaces.get(box2d::handle_hash(p_handle));
}
diff --git a/src/servers/box2d_project_settings.cpp b/src/servers/box2d_project_settings.cpp
index cff95a2..ff1bb34 100644
--- a/src/servers/box2d_project_settings.cpp
+++ b/src/servers/box2d_project_settings.cpp
@@ -6,8 +6,8 @@ using namespace godot;
constexpr char RUN_ON_SEPARATE_THREAD[] = "physics/2d/run_on_separate_thread";
constexpr char MAX_THREADS[] = "threading/worker_pool/max_threads";
-constexpr char POSITION_ITERATIONS[] = "physics/box_2d/solver/position_iterations";
-constexpr char VELOCITY_ITERATIONS[] = "physics/box_2d/solver/velocity_iterations";
+constexpr char SUB_STEP_COUNT[] = "physics/box_2d/sub_step_count";
+constexpr char LOGGING_ENABLED[] = "physics/box_2d/logging";
void register_setting(
const String &p_name,
@@ -64,8 +64,8 @@ void register_setting_ranged(
}
void Box2DProjectSettings::register_settings() {
- register_setting_ranged(VELOCITY_ITERATIONS, 8, U"2,16,or_greater");
- register_setting_ranged(POSITION_ITERATIONS, 3, U"1,16,or_greater");
+ register_setting_ranged(SUB_STEP_COUNT, 4, U"1,16,or_greater");
+ register_setting_plain(LOGGING_ENABLED, false, true);
}
template
@@ -88,10 +88,10 @@ int Box2DProjectSettings::get_max_threads() {
return get_setting(MAX_THREADS);
}
-int Box2DProjectSettings::get_position_iterations() {
- return get_setting(POSITION_ITERATIONS);
+int Box2DProjectSettings::get_sub_step_count() {
+ return get_setting(SUB_STEP_COUNT);
}
-int Box2DProjectSettings::get_velocity_iterations() {
- return get_setting(VELOCITY_ITERATIONS);
-}
+bool Box2DProjectSettings::get_logging_enabled() {
+ return get_setting(LOGGING_ENABLED);
+}
\ No newline at end of file
diff --git a/src/servers/box2d_project_settings.h b/src/servers/box2d_project_settings.h
index 15ef42a..6923b4d 100644
--- a/src/servers/box2d_project_settings.h
+++ b/src/servers/box2d_project_settings.h
@@ -10,6 +10,6 @@ class Box2DProjectSettings {
static bool should_run_on_separate_thread();
static int get_max_threads();
- static int get_position_iterations();
- static int get_velocity_iterations();
+ static bool get_logging_enabled();
+ static int get_sub_step_count();
};
diff --git a/src/spaces/box2d_direct_space_state_2d.cpp b/src/spaces/box2d_direct_space_state_2d.cpp
index 7e409f7..8cde524 100644
--- a/src/spaces/box2d_direct_space_state_2d.cpp
+++ b/src/spaces/box2d_direct_space_state_2d.cpp
@@ -130,7 +130,7 @@ bool Box2DDirectSpaceState2D::_collide_shape(const RID &shape_rid, const Transfo
box2d::ShapeInfo shape_info = box2d::shape_info_from_body_shape(shape_handle, Transform2D(), transform);
box2d::QueryExcludedInfo query_excluded_info = box2d::default_query_excluded_info();
query_excluded_info.query_collision_layer_mask = collision_mask;
- query_excluded_info.query_exclude = (b2Fixture **)memalloc((max_results) * sizeof(b2Fixture *));
+ query_excluded_info.query_exclude = (b2ShapeId *)memalloc((max_results) * sizeof(b2ShapeId));
query_excluded_info.query_exclude_size = 0;
int cpt = 0;
@@ -164,7 +164,7 @@ int Box2DDirectSpaceState2D::_intersect_shape(const RID &shape_rid, const Transf
box2d::QueryExcludedInfo query_excluded_info = box2d::default_query_excluded_info();
query_excluded_info.query_collision_layer_mask = collision_mask;
- query_excluded_info.query_exclude = (b2Fixture **)memalloc((p_result_max) * sizeof(b2Fixture *));
+ query_excluded_info.query_exclude = (b2ShapeId *)memalloc((p_result_max) * sizeof(b2ShapeId));
query_excluded_info.query_exclude_size = 0;
int cpt = 0;
diff --git a/src/spaces/box2d_space_2d.cpp b/src/spaces/box2d_space_2d.cpp
index 5b6cfed..8be0a56 100644
--- a/src/spaces/box2d_space_2d.cpp
+++ b/src/spaces/box2d_space_2d.cpp
@@ -37,13 +37,13 @@ void Box2DSpace2D::body_add_to_area_update_list(SelfList *p_body) {
body_area_update_list.add(p_body);
}
-void Box2DSpace2D::add_removed_collider(b2Fixture *p_handle, Box2DCollisionObject2D *p_object, uint32_t p_shape_index) {
+void Box2DSpace2D::add_removed_collider(b2ShapeId p_handle, Box2DCollisionObject2D *p_object, uint32_t p_shape_index) {
uint64_t handle_hash = box2d::handle_hash(p_handle);
ERR_FAIL_COND(removed_colliders.has(handle_hash));
removed_colliders.insert(handle_hash, { p_object->get_rid(), p_object->get_instance_id(), p_shape_index, p_object->get_type() });
}
-bool Box2DSpace2D::get_removed_collider_info(b2Fixture *p_handle, RID &r_rid, ObjectID &r_instance_id, uint32_t &r_shape_index, Box2DCollisionObject2D::Type &r_type) const {
+bool Box2DSpace2D::get_removed_collider_info(b2ShapeId p_handle, RID &r_rid, ObjectID &r_instance_id, uint32_t &r_shape_index, Box2DCollisionObject2D::Type &r_type) const {
uint64_t handle_hash = box2d::handle_hash(p_handle);
auto foundIt = removed_colliders.find(handle_hash);
if (foundIt == removed_colliders.end()) {
@@ -70,7 +70,7 @@ void Box2DSpace2D::active_body_callback(const box2d::ActiveBodyInfo &active_body
pBody->on_marked_active();
}
-bool Box2DSpace2D::collision_filter_common_callback(b2World *world_handle, const box2d::CollisionFilterInfo *filter_info, CollidersInfo &r_colliders_info) {
+bool Box2DSpace2D::collision_filter_common_callback(b2WorldId world_handle, const box2d::CollisionFilterInfo *filter_info, CollidersInfo &r_colliders_info) {
Box2DSpace2D *space = Box2DPhysicsServer2D::singleton->get_active_space(world_handle);
ERR_FAIL_COND_V(!space, false);
@@ -92,11 +92,11 @@ bool Box2DSpace2D::collision_filter_common_callback(b2World *world_handle, const
return true;
}
-bool Box2DSpace2D::ShouldCollide(b2Fixture *fixtureA, b2Fixture *fixtureB) {
+bool Box2DSpace2D::ShouldCollide(b2ShapeId fixtureA, b2ShapeId fixtureB, b2Manifold *manifold) {
ERR_FAIL_COND_V(!box2d::is_handle_valid(fixtureA), false);
ERR_FAIL_COND_V(!box2d::is_handle_valid(fixtureB), false);
- b2FixtureUserData user_dataA = fixtureA->GetUserData();
- b2FixtureUserData user_dataB = fixtureB->GetUserData();
+ b2FixtureUserData user_dataA = *static_cast(b2Shape_GetUserData(fixtureA));
+ b2FixtureUserData user_dataB = *static_cast(b2Shape_GetUserData(fixtureA));
ERR_FAIL_COND_V(!box2d::is_user_data_valid(user_dataA), false);
ERR_FAIL_COND_V(!box2d::is_user_data_valid(user_dataB), false);
CollidersInfo colliders_info;
@@ -117,6 +117,8 @@ bool Box2DSpace2D::ShouldCollide(b2Fixture *fixtureA, b2Fixture *fixtureB) {
return true;
}
+// TODO
+/*
box2d::CollisionEventInfo event_info_from_contact(b2Contact *contact) {
box2d::CollisionEventInfo event_info;
event_info.is_sensor = false;
@@ -159,6 +161,7 @@ box2d::ContactForceEventInfo force_info_from_contact(b2Contact *contact) {
event_info.is_valid = true;
return event_info;
}
+
void Box2DSpace2D::BeginContact(b2Contact *contact) {
box2d::CollisionEventInfo event_info = event_info_from_contact(contact);
if (!event_info.is_valid) {
@@ -184,8 +187,8 @@ void Box2DSpace2D::PreSolve(b2Contact *contact, const b2Manifold *oldManifold) {
ERR_FAIL_COND(!collision_object_1);
ERR_FAIL_COND(!collision_object_2);
if (collision_object_1->interacts_with(collision_object_2)) {
- b2Body *body1 = contact->GetFixtureA()->GetBody();
- b2Body *body2 = contact->GetFixtureB()->GetBody();
+ b2BodyId body1 = contact->GetFixtureA()->GetBody();
+ b2BodyId body2 = contact->GetFixtureB()->GetBody();
Transform2D transform_a = box2d::collider_get_transform(handle, contact->GetFixtureA()) * collision_object_1->get_transform();
Transform2D transform_b = box2d::collider_get_transform(handle, contact->GetFixtureB()) * collision_object_2->get_transform();
Vector2 allowed_local_n1 = transform_a.columns[1].normalized();
@@ -267,8 +270,7 @@ void Box2DSpace2D::PostSolve(b2Contact *contact, const b2ContactImpulse *impulse
}
}
}
-
-void Box2DSpace2D::collision_event_callback(b2World *world_handle, const box2d::CollisionEventInfo *event_info) {
+void Box2DSpace2D::collision_event_callback(b2WorldId world_handle, const box2d::CollisionEventInfo *event_info) {
Box2DSpace2D *space = Box2DPhysicsServer2D::singleton->get_active_space(world_handle);
ERR_FAIL_COND(!space);
@@ -284,8 +286,8 @@ void Box2DSpace2D::collision_event_callback(b2World *world_handle, const box2d::
pObject2 = Box2DCollisionObject2D::get_collider_user_data(event_info->user_data2, shape2);
}
- b2Fixture *collider_handle1 = event_info->collider1;
- b2Fixture *collider_handle2 = event_info->collider2;
+ b2ShapeId collider_handle1 = event_info->collider1;
+ b2ShapeId collider_handle2 = event_info->collider2;
RID rid1, rid2;
ObjectID instanceId1;
@@ -392,7 +394,8 @@ void Box2DSpace2D::collision_event_callback(b2World *world_handle, const box2d::
}
}
-bool Box2DSpace2D::contact_force_event_callback(b2World *world_handle, const box2d::ContactForceEventInfo *event_info) {
+*/
+bool Box2DSpace2D::contact_force_event_callback(b2WorldId world_handle, const box2d::ContactForceEventInfo *event_info) {
Box2DSpace2D *space = Box2DPhysicsServer2D::singleton->get_active_space(world_handle);
ERR_FAIL_COND_V(!space, false);
@@ -429,7 +432,7 @@ bool Box2DSpace2D::contact_force_event_callback(b2World *world_handle, const box
return send_contacts;
}
-bool Box2DSpace2D::contact_point_callback(b2World *world_handle, const box2d::ContactPointInfo *contact_info, const box2d::ContactForceEventInfo *event_info) {
+bool Box2DSpace2D::contact_point_callback(b2WorldId world_handle, const box2d::ContactPointInfo *contact_info, const box2d::ContactForceEventInfo *event_info) {
Box2DSpace2D *space = Box2DPhysicsServer2D::singleton->get_active_space(world_handle);
ERR_FAIL_COND_V(!space, false);
@@ -489,21 +492,15 @@ bool Box2DSpace2D::contact_point_callback(b2World *world_handle, const box2d::Co
void Box2DSpace2D::step(real_t p_step) {
last_step = p_step;
+ std::vector active_bodies;
for (SelfList *body_iterator = active_list.first(); body_iterator;) {
Box2DBody2D *body = body_iterator->self();
+ active_bodies.push_back(body->get_body_handle());
body_iterator = body_iterator->next();
body->reset_contact_count();
}
contact_debug_count = 0;
- ProjectSettings *project_settings = ProjectSettings::get_singleton();
-
- default_gravity_dir = project_settings->get_setting_with_override("physics/2d/default_gravity_vector");
- default_gravity_value = project_settings->get_setting_with_override("physics/2d/default_gravity");
-
- default_linear_damping = project_settings->get_setting_with_override("physics/2d/default_linear_damp");
- default_angular_damping = project_settings->get_setting_with_override("physics/2d/default_angular_damp");
-
for (SelfList *body_iterator = mass_properties_update_list.first(); body_iterator;) {
Box2DBody2D *body = body_iterator->self();
body_iterator = body_iterator->next();
@@ -530,13 +527,12 @@ void Box2DSpace2D::step(real_t p_step) {
box2d::SimulationSettings settings;
settings.dt = p_step;
- settings.max_position_iterations = Box2DProjectSettings::get_position_iterations();
- settings.max_velocity_iterations = Box2DProjectSettings::get_velocity_iterations();
+ settings.sub_step_count = Box2DProjectSettings::get_sub_step_count();
settings.gravity.x = default_gravity_dir.x * default_gravity_value;
settings.gravity.y = default_gravity_dir.y * default_gravity_value;
ERR_FAIL_COND(!box2d::is_handle_valid(handle));
- box2d::world_step(handle, &settings);
+ box2d::world_step(handle, settings, active_bodies);
// Needed only for one physics step to retrieve lost info
removed_colliders.clear();
@@ -546,11 +542,12 @@ void Box2DSpace2D::step(real_t p_step) {
body_iterator = body_iterator->next();
body->on_update_active();
}
- active_objects = box2d::world_get_active_objects_count(handle);
}
+// TODO
// Returns true to ignore the collider
-bool Box2DSpace2D::_is_handle_excluded_callback(b2World *world_handle, b2Fixture *collider_handle, b2FixtureUserData user_data, const box2d::QueryExcludedInfo *handle_excluded_info) {
+bool Box2DSpace2D::_is_handle_excluded_callback(b2WorldId world_handle, b2ShapeId collider_handle, b2FixtureUserData user_data, const box2d::QueryExcludedInfo *handle_excluded_info) {
+ /*
for (uint32_t exclude_index = 0; exclude_index < handle_excluded_info->query_exclude_size; ++exclude_index) {
if (box2d::are_handles_equal(handle_excluded_info->query_exclude[exclude_index], collider_handle)) {
return true;
@@ -574,8 +571,10 @@ bool Box2DSpace2D::_is_handle_excluded_callback(b2World *world_handle, b2Fixture
if (handle_excluded_info->query_exclude_body == collision_object_2d->get_rid().get_id()) {
return true;
}
-
return Box2DPhysicsServer2D::singleton->get_active_space(world_handle)->get_direct_state()->is_body_excluded_from_query(collision_object_2d->get_rid());
+
+ */
+ return false;
}
void Box2DSpace2D::call_queries() {
@@ -729,6 +728,12 @@ Box2DSpace2D::Box2DSpace2D() {
contact_bias = project_settings->get_setting_with_override("physics/2d/solver/default_contact_bias");
constraint_bias = project_settings->get_setting_with_override("physics/2d/solver/default_constraint_bias");
+ default_gravity_dir = project_settings->get_setting_with_override("physics/2d/default_gravity_vector");
+ default_gravity_value = project_settings->get_setting_with_override("physics/2d/default_gravity");
+
+ default_linear_damping = project_settings->get_setting_with_override("physics/2d/default_linear_damp");
+ default_angular_damping = project_settings->get_setting_with_override("physics/2d/default_angular_damp");
+
direct_access = memnew(Box2DDirectSpaceState2D);
direct_access->space = this;
@@ -739,12 +744,15 @@ Box2DSpace2D::Box2DSpace2D() {
world_settings.sleep_angular_threshold = body_angular_velocity_sleep_threshold;
world_settings.sleep_time_until_sleep = body_time_to_sleep;
- handle = box2d::world_create(&world_settings);
+ box2d::SimulationSettings simulation_settings;
+ simulation_settings.sub_step_count = Box2DProjectSettings::get_sub_step_count();
+ simulation_settings.gravity.x = default_gravity_dir.x * default_gravity_value;
+ simulation_settings.gravity.y = default_gravity_dir.y * default_gravity_value;
+ handle = box2d::world_create(world_settings, simulation_settings);
ERR_FAIL_COND(!box2d::is_handle_valid(handle));
box2d::world_set_active_body_callback(handle, active_body_callback);
box2d::world_set_collision_filter_callback(handle, this);
- box2d::world_set_contact_listener(handle, this);
}
Box2DSpace2D::~Box2DSpace2D() {
@@ -813,7 +821,7 @@ int Box2DSpace2D::box2d_intersect_aabb(Rect2 p_aabb, uint32_t p_collision_mask,
b2Vec2 rect_begin{ p_aabb.position.x, p_aabb.position.y };
b2Vec2 rect_end{ p_aabb.get_end().x, p_aabb.get_end().y };
box2d::QueryExcludedInfo handle_excluded_info = box2d::default_query_excluded_info();
- handle_excluded_info.query_exclude = (b2Fixture **)memalloc((p_max_results) * sizeof(b2Fixture *));
+ //handle_excluded_info.query_exclude = (b2ShapeId *)memalloc((p_max_results) * sizeof(b2ShapeId));
handle_excluded_info.query_collision_layer_mask = p_collision_mask;
handle_excluded_info.query_exclude_size = 0;
handle_excluded_info.query_exclude_body = p_exclude_body.get_id();
diff --git a/src/spaces/box2d_space_2d.h b/src/spaces/box2d_space_2d.h
index 087a002..52846c4 100644
--- a/src/spaces/box2d_space_2d.h
+++ b/src/spaces/box2d_space_2d.h
@@ -20,11 +20,11 @@ using namespace godot;
class Box2DSpace2D;
class Box2DDirectSpaceState2D;
-class Box2DSpace2D : public b2ContactFilter, public b2ContactListener {
+class Box2DSpace2D : public b2ContactFilter {
Box2DDirectSpaceState2D *direct_access = nullptr;
RID rid;
- b2World *handle = box2d::invalid_world_handle();
+ b2WorldId handle = box2d::invalid_world_handle();
struct RemovedColliderInfo {
RID rid;
@@ -84,29 +84,30 @@ class Box2DSpace2D : public b2ContactFilter, public b2ContactListener {
Box2DCollisionObject2D *object2 = nullptr;
};
- virtual bool ShouldCollide(b2Fixture *fixtureA, b2Fixture *fixtureB) override;
- virtual void BeginContact(b2Contact *contact) override;
+ virtual bool ShouldCollide(b2ShapeId fixtureA, b2ShapeId fixtureB, b2Manifold *manifold) override;
+ /*
+ void BeginContact(b2Contact *contact);
- virtual void EndContact(b2Contact *contact) override;
- virtual void PreSolve(b2Contact *contact, const b2Manifold *oldManifold) override;
- virtual void PostSolve(b2Contact *contact, const b2ContactImpulse *impulse) override;
+ void EndContact(b2Contact *contact);
+ void PreSolve(b2Contact *contact, const b2Manifold *oldManifold);
+ void PostSolve(b2Contact *contact, const b2ContactImpulse *impulse);
+ */
+ static bool collision_filter_common_callback(b2WorldId world_handle, const box2d::CollisionFilterInfo *filter_info, CollidersInfo &r_colliders_info);
+ static box2d::OneWayDirection collision_modify_contacts_callback(b2WorldId world_handle, const box2d::CollisionFilterInfo *filter_info);
- static bool collision_filter_common_callback(b2World *world_handle, const box2d::CollisionFilterInfo *filter_info, CollidersInfo &r_colliders_info);
- static box2d::OneWayDirection collision_modify_contacts_callback(b2World *world_handle, const box2d::CollisionFilterInfo *filter_info);
+ static void collision_event_callback(b2WorldId world_handle, const box2d::CollisionEventInfo *event_info);
- static void collision_event_callback(b2World *world_handle, const box2d::CollisionEventInfo *event_info);
+ static bool contact_force_event_callback(b2WorldId world_handle, const box2d::ContactForceEventInfo *event_info);
+ static bool contact_point_callback(b2WorldId world_handle, const box2d::ContactPointInfo *contact_info, const box2d::ContactForceEventInfo *event_info);
- static bool contact_force_event_callback(b2World *world_handle, const box2d::ContactForceEventInfo *event_info);
- static bool contact_point_callback(b2World *world_handle, const box2d::ContactPointInfo *contact_info, const box2d::ContactForceEventInfo *event_info);
-
- static bool _is_handle_excluded_callback(b2World *world_handle, b2Fixture *collider_handle, b2FixtureUserData collider, const box2d::QueryExcludedInfo *handle_excluded_info);
+ static bool _is_handle_excluded_callback(b2WorldId world_handle, b2ShapeId collider_handle, b2FixtureUserData collider, const box2d::QueryExcludedInfo *handle_excluded_info);
static Object *_get_object_instance_hack(uint64_t p_object_id) {
return reinterpret_cast