summaryrefslogtreecommitdiff
path: root/scene/2d
diff options
context:
space:
mode:
Diffstat (limited to 'scene/2d')
-rw-r--r--scene/2d/area_2d.cpp8
-rw-r--r--scene/2d/audio_stream_player_2d.cpp67
-rw-r--r--scene/2d/canvas_item.cpp1
-rw-r--r--scene/2d/line_builder.cpp55
-rw-r--r--scene/2d/path_2d.cpp3
-rw-r--r--scene/2d/physics_body_2d.cpp224
-rw-r--r--scene/2d/physics_body_2d.h52
7 files changed, 232 insertions, 178 deletions
diff --git a/scene/2d/area_2d.cpp b/scene/2d/area_2d.cpp
index 1124904963..9fc6c8d23a 100644
--- a/scene/2d/area_2d.cpp
+++ b/scene/2d/area_2d.cpp
@@ -596,7 +596,7 @@ void Area2D::_bind_methods() {
ClassDB::bind_method(D_METHOD("_area_enter_tree", "id"), &Area2D::_area_enter_tree);
ClassDB::bind_method(D_METHOD("_area_exit_tree", "id"), &Area2D::_area_exit_tree);
- ClassDB::bind_method(D_METHOD("set_space_override_mode", "enable"), &Area2D::set_space_override_mode);
+ ClassDB::bind_method(D_METHOD("set_space_override_mode", "space_override_mode"), &Area2D::set_space_override_mode);
ClassDB::bind_method(D_METHOD("get_space_override_mode"), &Area2D::get_space_override_mode);
ClassDB::bind_method(D_METHOD("set_gravity_is_point", "enable"), &Area2D::set_gravity_is_point);
@@ -680,6 +680,12 @@ void Area2D::_bind_methods() {
ADD_GROUP("Audio Bus", "audio_bus_");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "audio_bus_override"), "set_audio_bus_override", "is_overriding_audio_bus");
ADD_PROPERTY(PropertyInfo(Variant::STRING, "audio_bus_name", PROPERTY_HINT_ENUM, ""), "set_audio_bus", "get_audio_bus");
+
+ BIND_ENUM_CONSTANT(SPACE_OVERRIDE_DISABLED);
+ BIND_ENUM_CONSTANT(SPACE_OVERRIDE_COMBINE);
+ BIND_ENUM_CONSTANT(SPACE_OVERRIDE_COMBINE_REPLACE);
+ BIND_ENUM_CONSTANT(SPACE_OVERRIDE_REPLACE);
+ BIND_ENUM_CONSTANT(SPACE_OVERRIDE_REPLACE_COMBINE);
}
Area2D::Area2D()
diff --git a/scene/2d/audio_stream_player_2d.cpp b/scene/2d/audio_stream_player_2d.cpp
index 39d3f2d6bf..b6abe90035 100644
--- a/scene/2d/audio_stream_player_2d.cpp
+++ b/scene/2d/audio_stream_player_2d.cpp
@@ -57,52 +57,32 @@ void AudioStreamPlayer2D::_mix_audio() {
AudioFrame vol_inc = (current.vol - prev_outputs[i].vol) / float(buffer_size);
AudioFrame vol = current.vol;
- switch (AudioServer::get_singleton()->get_speaker_mode()) {
+ int cc = AudioServer::get_singleton()->get_channel_count();
- case AudioServer::SPEAKER_MODE_STEREO: {
- AudioFrame *target = AudioServer::get_singleton()->thread_get_channel_mix_buffer(current.bus_index, 0);
+ if (cc == 1) {
+ AudioFrame *target = AudioServer::get_singleton()->thread_get_channel_mix_buffer(current.bus_index, 0);
- for (int j = 0; j < buffer_size; j++) {
+ for (int j = 0; j < buffer_size; j++) {
- target[j] += buffer[j] * vol;
- vol += vol_inc;
- }
-
- } break;
- case AudioServer::SPEAKER_SURROUND_51: {
-
- AudioFrame *targets[2] = {
- AudioServer::get_singleton()->thread_get_channel_mix_buffer(current.bus_index, 1),
- AudioServer::get_singleton()->thread_get_channel_mix_buffer(current.bus_index, 2),
- };
-
- for (int j = 0; j < buffer_size; j++) {
-
- AudioFrame frame = buffer[j] * vol;
- targets[0][j] += frame;
- targets[1][j] += frame;
- vol += vol_inc;
- }
+ target[j] += buffer[j] * vol;
+ vol += vol_inc;
+ }
- } break;
- case AudioServer::SPEAKER_SURROUND_71: {
+ } else {
+ AudioFrame *targets[4];
- AudioFrame *targets[3] = {
- AudioServer::get_singleton()->thread_get_channel_mix_buffer(current.bus_index, 1),
- AudioServer::get_singleton()->thread_get_channel_mix_buffer(current.bus_index, 2),
- AudioServer::get_singleton()->thread_get_channel_mix_buffer(current.bus_index, 3)
- };
+ for (int k = 0; k < cc; k++) {
+ targets[k] = AudioServer::get_singleton()->thread_get_channel_mix_buffer(current.bus_index, k);
+ }
- for (int j = 0; j < buffer_size; j++) {
+ for (int j = 0; j < buffer_size; j++) {
- AudioFrame frame = buffer[j] * vol;
- targets[0][j] += frame;
- targets[1][j] += frame;
- targets[2][j] += frame;
- vol += vol_inc;
+ AudioFrame frame = buffer[j] * vol;
+ for (int k = 0; k < cc; k++) {
+ targets[k][j] += frame;
}
-
- } break;
+ vol += vol_inc;
+ }
}
prev_outputs[i] = current;
@@ -217,13 +197,15 @@ void AudioStreamPlayer2D::_notification(int p_what) {
setseek = setplay;
active = true;
setplay = -1;
- _change_notify("playing"); //update property in editor
+ //do not update, this makes it easier to animate (will shut off otherise)
+ //_change_notify("playing"); //update property in editor
}
//stop playing if no longer active
if (!active) {
set_fixed_process_internal(false);
- _change_notify("playing"); //update property in editor
+ //do not update, this makes it easier to animate (will shut off otherise)
+ //_change_notify("playing"); //update property in editor
emit_signal("finished");
}
}
@@ -252,8 +234,6 @@ void AudioStreamPlayer2D::set_stream(Ref<AudioStream> p_stream) {
stream.unref();
ERR_FAIL_COND(stream_playback.is_null());
}
-
-
}
Ref<AudioStream> AudioStreamPlayer2D::get_stream() const {
@@ -439,7 +419,7 @@ void AudioStreamPlayer2D::_bind_methods() {
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "stream", PROPERTY_HINT_RESOURCE_TYPE, "AudioStream"), "set_stream", "get_stream");
ADD_PROPERTY(PropertyInfo(Variant::REAL, "volume_db", PROPERTY_HINT_RANGE, "-80,24"), "set_volume_db", "get_volume_db");
- ADD_PROPERTY(PropertyInfo(Variant::BOOL, "playing", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR), "_set_playing", "_is_active");
+ ADD_PROPERTY(PropertyInfo(Variant::BOOL, "playing", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_EDITOR), "_set_playing", "is_playing");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "autoplay"), "set_autoplay", "is_autoplay_enabled");
ADD_PROPERTY(PropertyInfo(Variant::REAL, "max_distance", PROPERTY_HINT_RANGE, "1,65536,1"), "set_max_distance", "get_max_distance");
ADD_PROPERTY(PropertyInfo(Variant::REAL, "attenuation", PROPERTY_HINT_EXP_EASING), "set_attenuation", "get_attenuation");
@@ -447,7 +427,6 @@ void AudioStreamPlayer2D::_bind_methods() {
ADD_PROPERTY(PropertyInfo(Variant::INT, "area_mask", PROPERTY_HINT_LAYERS_2D_PHYSICS), "set_area_mask", "get_area_mask");
ADD_SIGNAL(MethodInfo("finished"));
-
}
AudioStreamPlayer2D::AudioStreamPlayer2D() {
diff --git a/scene/2d/canvas_item.cpp b/scene/2d/canvas_item.cpp
index a7c5d1adbb..ec1ea7df38 100644
--- a/scene/2d/canvas_item.cpp
+++ b/scene/2d/canvas_item.cpp
@@ -338,7 +338,6 @@ void CanvasItem::_update_callback() {
notification(NOTIFICATION_DRAW);
emit_signal(SceneStringNames::get_singleton()->draw);
if (get_script_instance()) {
- Variant::CallError err;
get_script_instance()->call_multilevel_reversed(SceneStringNames::get_singleton()->_draw, NULL, 0);
}
drawing = false;
diff --git a/scene/2d/line_builder.cpp b/scene/2d/line_builder.cpp
index 1235013af4..53db30e3ce 100644
--- a/scene/2d/line_builder.cpp
+++ b/scene/2d/line_builder.cpp
@@ -173,13 +173,15 @@ void LineBuilder::build() {
strip_begin(pos_up0, pos_down0, color0, uvx0);
- // pos_up0 ------------- pos_up1 --------------------
- // | |
- // pos0 - - - - - - - - - pos1 - - - - - - - - - pos2
- // | |
- // pos_down0 ------------ pos_down1 ------------------
- //
- // i-1 i i+1
+ /*
+ * pos_up0 ------------- pos_up1 --------------------
+ * | |
+ * pos0 - - - - - - - - - pos1 - - - - - - - - - pos2
+ * | |
+ * pos_down0 ------------ pos_down1 ------------------
+ *
+ * i-1 i i+1
+ */
// http://labs.hyperandroid.com/tag/opengl-lines
// (not the same implementation but visuals help a lot)
@@ -206,17 +208,19 @@ void LineBuilder::build() {
inner_normal1 = -u1 * hw;
}
- // ---------------------------
- // /
- // 0 / 1
- // / /
- // --------------------x------ /
- // / / (here shown with orientation == DOWN)
- // / /
- // / /
- // / /
- // 2 /
- // /
+ /*
+ * ---------------------------
+ * /
+ * 0 / 1
+ * / /
+ * --------------------x------ /
+ * / / (here shown with orientation == DOWN)
+ * / /
+ * / /
+ * / /
+ * 2 /
+ * /
+ */
// Find inner intersection at the joint
Vector2 corner_pos_in, corner_pos_out;
@@ -315,13 +319,14 @@ void LineBuilder::build() {
// Add joint geometry
if (current_joint_mode != LINE_JOINT_SHARP) {
- // ________________ cbegin
- // / \
- // / \
- // ____________/_ _ _\ cend
- // | |
- // | |
- // | |
+ /* ________________ cbegin
+ * / \
+ * / \
+ * ____________/_ _ _\ cend
+ * | |
+ * | |
+ * | |
+ */
Vector2 cbegin, cend;
if (orientation == UP) {
diff --git a/scene/2d/path_2d.cpp b/scene/2d/path_2d.cpp
index 1d7bd8fc2a..9bd5576d91 100644
--- a/scene/2d/path_2d.cpp
+++ b/scene/2d/path_2d.cpp
@@ -137,7 +137,8 @@ void PathFollow2D::_notification(int p_what) {
case NOTIFICATION_ENTER_TREE: {
- if ((path = Object::cast_to<Path2D>(get_parent()))) {
+ path = Object::cast_to<Path2D>(get_parent());
+ if (path) {
_update_transform();
}
diff --git a/scene/2d/physics_body_2d.cpp b/scene/2d/physics_body_2d.cpp
index b1eb2ba267..c6cd3677cd 100644
--- a/scene/2d/physics_body_2d.cpp
+++ b/scene/2d/physics_body_2d.cpp
@@ -955,35 +955,25 @@ RigidBody2D::~RigidBody2D() {
//////////////////////////
-Dictionary KinematicBody2D::_move(const Vector2 &p_motion) {
+Ref<KinematicCollision2D> KinematicBody2D::_move(const Vector2 &p_motion) {
Collision col;
- if (move(p_motion, col)) {
- Dictionary d;
- d["position"] = col.collision;
- d["normal"] = col.normal;
- d["local_shape"] = col.local_shape;
- d["travel"] = col.travel;
- d["remainder"] = col.remainder;
- d["collider_id"] = col.collider;
- d["collider_velocity"] = col.collider_vel;
- if (col.collider) {
- d["collider"] = ObjectDB::get_instance(col.collider);
- } else {
- d["collider"] = Variant();
- }
- d["collider_shape_index"] = col.collider_shape;
- d["collider_metadata"] = col.collider_metadata;
+ if (move_and_collide(p_motion, col)) {
+ if (motion_cache.is_null()) {
+ motion_cache.instance();
+ motion_cache->owner = this;
+ }
- return d;
+ motion_cache->collision = col;
- } else {
- return Dictionary();
+ return motion_cache;
}
+
+ return Ref<KinematicCollision2D>();
}
-bool KinematicBody2D::move(const Vector2 &p_motion, Collision &r_collision) {
+bool KinematicBody2D::move_and_collide(const Vector2 &p_motion, Collision &r_collision) {
Transform2D gt = get_global_transform();
Physics2DServer::MotionResult result;
@@ -1007,7 +997,7 @@ bool KinematicBody2D::move(const Vector2 &p_motion, Collision &r_collision) {
return colliding;
}
-Vector2 KinematicBody2D::move_and_slide(const Vector2 &p_linear_velocity, const Vector2 &p_floor_direction, float p_slope_stop_min_velocity, int p_max_bounces, float p_floor_max_angle) {
+Vector2 KinematicBody2D::move_and_slide(const Vector2 &p_linear_velocity, const Vector2 &p_floor_direction, float p_slope_stop_min_velocity, int p_max_slides, float p_floor_max_angle) {
Vector2 motion = (floor_velocity + p_linear_velocity) * get_fixed_process_delta_time();
Vector2 lv = p_linear_velocity;
@@ -1018,11 +1008,11 @@ Vector2 KinematicBody2D::move_and_slide(const Vector2 &p_linear_velocity, const
colliders.clear();
floor_velocity = Vector2();
- while (p_max_bounces) {
+ while (p_max_slides) {
Collision collision;
- bool collided = move(motion, collision);
+ bool collided = move_and_collide(motion, collision);
if (collided) {
@@ -1060,7 +1050,7 @@ Vector2 KinematicBody2D::move_and_slide(const Vector2 &p_linear_velocity, const
break;
}
- p_max_bounces--;
+ p_max_slides--;
if (motion == Vector2())
break;
}
@@ -1103,75 +1093,35 @@ float KinematicBody2D::get_safe_margin() const {
return margin;
}
-int KinematicBody2D::get_collision_count() const {
+int KinematicBody2D::get_slide_count() const {
return colliders.size();
}
-Vector2 KinematicBody2D::get_collision_position(int p_collision) const {
-
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), Vector2());
- return colliders[p_collision].collision;
-}
-Vector2 KinematicBody2D::get_collision_normal(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), Vector2());
- return colliders[p_collision].normal;
+KinematicBody2D::Collision KinematicBody2D::get_slide_collision(int p_bounce) const {
+ ERR_FAIL_INDEX_V(p_bounce, colliders.size(), Collision());
+ return colliders[p_bounce];
}
-Vector2 KinematicBody2D::get_collision_travel(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), Vector2());
- return colliders[p_collision].travel;
-}
-Vector2 KinematicBody2D::get_collision_remainder(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), Vector2());
- return colliders[p_collision].remainder;
-}
-Object *KinematicBody2D::get_collision_local_shape(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), NULL);
- uint32_t owner = shape_find_owner(colliders[p_collision].local_shape);
- return shape_owner_get_owner(owner);
-}
-Object *KinematicBody2D::get_collision_collider(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), NULL);
+Ref<KinematicCollision2D> KinematicBody2D::_get_slide_collision(int p_bounce) {
- if (colliders[p_collision].collider) {
- return ObjectDB::get_instance(colliders[p_collision].collider);
+ ERR_FAIL_INDEX_V(p_bounce, colliders.size(), Ref<KinematicCollision2D>());
+ if (p_bounce >= slide_colliders.size()) {
+ slide_colliders.resize(p_bounce + 1);
}
- return NULL;
-}
-ObjectID KinematicBody2D::get_collision_collider_id(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), 0);
-
- return colliders[p_collision].collider;
-}
-Object *KinematicBody2D::get_collision_collider_shape(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), NULL);
- Object *collider = get_collision_collider(p_collision);
- CollisionObject2D *obj2d = Object::cast_to<CollisionObject2D>(collider);
- if (obj2d) {
- uint32_t owner = shape_find_owner(colliders[p_collision].collider_shape);
- return obj2d->shape_owner_get_owner(owner);
+ if (slide_colliders[p_bounce].is_null()) {
+ slide_colliders[p_bounce].instance();
+ slide_colliders[p_bounce]->owner = this;
}
- return NULL;
-}
-int KinematicBody2D::get_collision_collider_shape_index(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), -1);
- return colliders[p_collision].collider_shape;
-}
-Vector2 KinematicBody2D::get_collision_collider_velocity(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), Vector2());
- return colliders[p_collision].collider_vel;
-}
-Variant KinematicBody2D::get_collision_collider_metadata(int p_collision) const {
- ERR_FAIL_INDEX_V(p_collision, colliders.size(), Variant());
- return colliders[p_collision].collider_metadata;
+ slide_colliders[p_bounce]->collision = colliders[p_bounce];
+ return slide_colliders[p_bounce];
}
void KinematicBody2D::_bind_methods() {
- ClassDB::bind_method(D_METHOD("move", "rel_vec"), &KinematicBody2D::_move);
+ ClassDB::bind_method(D_METHOD("move_and_collide", "rel_vec"), &KinematicBody2D::_move);
ClassDB::bind_method(D_METHOD("move_and_slide", "linear_velocity", "floor_normal", "slope_stop_min_velocity", "max_bounces", "floor_max_angle"), &KinematicBody2D::move_and_slide, DEFVAL(Vector2(0, 0)), DEFVAL(5), DEFVAL(4), DEFVAL(Math::deg2rad((float)45)));
ClassDB::bind_method(D_METHOD("test_move", "from", "rel_vec"), &KinematicBody2D::test_move);
@@ -1184,18 +1134,8 @@ void KinematicBody2D::_bind_methods() {
ClassDB::bind_method(D_METHOD("set_safe_margin", "pixels"), &KinematicBody2D::set_safe_margin);
ClassDB::bind_method(D_METHOD("get_safe_margin"), &KinematicBody2D::get_safe_margin);
- ClassDB::bind_method(D_METHOD("get_collision_count"), &KinematicBody2D::get_collision_count);
- ClassDB::bind_method(D_METHOD("get_collision_position", "collision"), &KinematicBody2D::get_collision_position);
- ClassDB::bind_method(D_METHOD("get_collision_normal", "collision"), &KinematicBody2D::get_collision_normal);
- ClassDB::bind_method(D_METHOD("get_collision_travel", "collision"), &KinematicBody2D::get_collision_travel);
- ClassDB::bind_method(D_METHOD("get_collision_remainder", "collision"), &KinematicBody2D::get_collision_remainder);
- ClassDB::bind_method(D_METHOD("get_collision_local_shape", "collision"), &KinematicBody2D::get_collision_local_shape);
- ClassDB::bind_method(D_METHOD("get_collision_collider", "collision"), &KinematicBody2D::get_collision_collider);
- ClassDB::bind_method(D_METHOD("get_collision_collider_id", "collision"), &KinematicBody2D::get_collision_collider_id);
- ClassDB::bind_method(D_METHOD("get_collision_collider_shape", "collision"), &KinematicBody2D::get_collision_collider_shape);
- ClassDB::bind_method(D_METHOD("get_collision_collider_shape_index", "collision"), &KinematicBody2D::get_collision_collider_shape_index);
- ClassDB::bind_method(D_METHOD("get_collision_collider_velocity", "collision"), &KinematicBody2D::get_collision_collider_velocity);
- ClassDB::bind_method(D_METHOD("get_collision_collider_metadata", "collision"), &KinematicBody2D::get_collision_collider_metadata);
+ ClassDB::bind_method(D_METHOD("get_slide_count"), &KinematicBody2D::get_slide_count);
+ ClassDB::bind_method(D_METHOD("get_slide_collision", "slide_idx"), &KinematicBody2D::_get_slide_collision);
ADD_PROPERTY(PropertyInfo(Variant::REAL, "collision/safe_margin", PROPERTY_HINT_RANGE, "0.001,256,0.001"), "set_safe_margin", "get_safe_margin");
}
@@ -1210,4 +1150,106 @@ KinematicBody2D::KinematicBody2D()
on_wall = false;
}
KinematicBody2D::~KinematicBody2D() {
+ if (motion_cache.is_valid()) {
+ motion_cache->owner = NULL;
+ }
+
+ for (int i = 0; i < slide_colliders.size(); i++) {
+ if (slide_colliders[i].is_valid()) {
+ slide_colliders[i]->owner = NULL;
+ }
+ }
+}
+
+////////////////////////
+
+Vector2 KinematicCollision2D::get_position() const {
+
+ return collision.collision;
+}
+Vector2 KinematicCollision2D::get_normal() const {
+ return collision.normal;
+}
+Vector2 KinematicCollision2D::get_travel() const {
+ return collision.travel;
+}
+Vector2 KinematicCollision2D::get_remainder() const {
+ return collision.remainder;
+}
+Object *KinematicCollision2D::get_local_shape() const {
+ ERR_FAIL_COND_V(!owner, NULL);
+ uint32_t ownerid = owner->shape_find_owner(collision.local_shape);
+ return owner->shape_owner_get_owner(ownerid);
+}
+
+Object *KinematicCollision2D::get_collider() const {
+
+ if (collision.collider) {
+ return ObjectDB::get_instance(collision.collider);
+ }
+
+ return NULL;
+}
+ObjectID KinematicCollision2D::get_collider_id() const {
+
+ return collision.collider;
+}
+Object *KinematicCollision2D::get_collider_shape() const {
+
+ Object *collider = get_collider();
+ if (collider) {
+ CollisionObject2D *obj2d = Object::cast_to<CollisionObject2D>(collider);
+ if (obj2d) {
+ uint32_t ownerid = obj2d->shape_find_owner(collision.collider_shape);
+ return obj2d->shape_owner_get_owner(ownerid);
+ }
+ }
+
+ return NULL;
+}
+int KinematicCollision2D::get_collider_shape_index() const {
+
+ return collision.collider_shape;
+}
+Vector2 KinematicCollision2D::get_collider_velocity() const {
+
+ return collision.collider_vel;
+}
+Variant KinematicCollision2D::get_collider_metadata() const {
+
+ return Variant();
+}
+
+void KinematicCollision2D::_bind_methods() {
+
+ ClassDB::bind_method(D_METHOD("get_position"), &KinematicCollision2D::get_position);
+ ClassDB::bind_method(D_METHOD("get_normal"), &KinematicCollision2D::get_normal);
+ ClassDB::bind_method(D_METHOD("get_travel"), &KinematicCollision2D::get_travel);
+ ClassDB::bind_method(D_METHOD("get_remainder"), &KinematicCollision2D::get_remainder);
+ ClassDB::bind_method(D_METHOD("get_local_shape"), &KinematicCollision2D::get_local_shape);
+ ClassDB::bind_method(D_METHOD("get_collider"), &KinematicCollision2D::get_collider);
+ ClassDB::bind_method(D_METHOD("get_collider_id"), &KinematicCollision2D::get_collider_id);
+ ClassDB::bind_method(D_METHOD("get_collider_shape"), &KinematicCollision2D::get_collider_shape);
+ ClassDB::bind_method(D_METHOD("get_collider_shape_index"), &KinematicCollision2D::get_collider_shape_index);
+ ClassDB::bind_method(D_METHOD("get_collider_velocity"), &KinematicCollision2D::get_collider_velocity);
+ ClassDB::bind_method(D_METHOD("get_collider_metadata"), &KinematicCollision2D::get_collider_metadata);
+
+ ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "position"), "", "get_position");
+ ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "normal"), "", "get_normal");
+ ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "travel"), "", "get_travel");
+ ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "remainder"), "", "get_remainder");
+ ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "local_shape"), "", "get_local_shape");
+ ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "collider"), "", "get_collider");
+ ADD_PROPERTY(PropertyInfo(Variant::INT, "collider_id"), "", "get_collider_id");
+ ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "collider_shape"), "", "get_collider_shape");
+ ADD_PROPERTY(PropertyInfo(Variant::INT, "collider_shape_index"), "", "get_collider_shape_index");
+ ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "collider_velocity"), "", "get_collider_velocity");
+ ADD_PROPERTY(PropertyInfo(Variant::NIL, "collider_metadata", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NIL_IS_VARIANT), "", "get_collider_metadata");
+}
+
+KinematicCollision2D::KinematicCollision2D() {
+ collision.collider = 0;
+ collision.collider_shape = 0;
+ collision.local_shape = 0;
+ owner = NULL;
}
diff --git a/scene/2d/physics_body_2d.h b/scene/2d/physics_body_2d.h
index 1a4b0c0f5c..b82771a8f4 100644
--- a/scene/2d/physics_body_2d.h
+++ b/scene/2d/physics_body_2d.h
@@ -34,6 +34,8 @@
#include "servers/physics_2d_server.h"
#include "vset.h"
+class KinematicCollision2D;
+
class PhysicsBody2D : public CollisionObject2D {
GDCLASS(PhysicsBody2D, CollisionObject2D);
@@ -288,42 +290,62 @@ private:
bool on_ceiling;
bool on_wall;
Vector<Collision> colliders;
+ Vector<Ref<KinematicCollision2D> > slide_colliders;
+ Ref<KinematicCollision2D> motion_cache;
_FORCE_INLINE_ bool _ignores_mode(Physics2DServer::BodyMode) const;
- Dictionary _move(const Vector2 &p_motion);
+ Ref<KinematicCollision2D> _move(const Vector2 &p_motion);
+ Ref<KinematicCollision2D> _get_slide_collision(int p_bounce);
protected:
static void _bind_methods();
public:
- bool move(const Vector2 &p_motion, Collision &r_collision);
+ bool move_and_collide(const Vector2 &p_motion, Collision &r_collision);
bool test_move(const Transform2D &p_from, const Vector2 &p_motion);
void set_safe_margin(float p_margin);
float get_safe_margin() const;
- Vector2 move_and_slide(const Vector2 &p_linear_velocity, const Vector2 &p_floor_direction = Vector2(0, 0), float p_slope_stop_min_velocity = 5, int p_max_bounces = 4, float p_floor_max_angle = Math::deg2rad((float)45));
+ Vector2 move_and_slide(const Vector2 &p_linear_velocity, const Vector2 &p_floor_direction = Vector2(0, 0), float p_slope_stop_min_velocity = 5, int p_max_slides = 4, float p_floor_max_angle = Math::deg2rad((float)45));
bool is_on_floor() const;
bool is_on_wall() const;
bool is_on_ceiling() const;
Vector2 get_floor_velocity() const;
- int get_collision_count() const;
- Vector2 get_collision_position(int p_collision) const;
- Vector2 get_collision_normal(int p_collision) const;
- Vector2 get_collision_travel(int p_collision) const;
- Vector2 get_collision_remainder(int p_collision) const;
- Object *get_collision_local_shape(int p_collision) const;
- Object *get_collision_collider(int p_collision) const;
- ObjectID get_collision_collider_id(int p_collision) const;
- Object *get_collision_collider_shape(int p_collision) const;
- int get_collision_collider_shape_index(int p_collision) const;
- Vector2 get_collision_collider_velocity(int p_collision) const;
- Variant get_collision_collider_metadata(int p_collision) const;
+ int get_slide_count() const;
+ Collision get_slide_collision(int p_bounce) const;
KinematicBody2D();
~KinematicBody2D();
};
+class KinematicCollision2D : public Reference {
+
+ GDCLASS(KinematicCollision2D, Reference);
+
+ KinematicBody2D *owner;
+ friend class KinematicBody2D;
+ KinematicBody2D::Collision collision;
+
+protected:
+ static void _bind_methods();
+
+public:
+ Vector2 get_position() const;
+ Vector2 get_normal() const;
+ Vector2 get_travel() const;
+ Vector2 get_remainder() const;
+ Object *get_local_shape() const;
+ Object *get_collider() const;
+ ObjectID get_collider_id() const;
+ Object *get_collider_shape() const;
+ int get_collider_shape_index() const;
+ Vector2 get_collider_velocity() const;
+ Variant get_collider_metadata() const;
+
+ KinematicCollision2D();
+};
+
#endif // PHYSICS_BODY_2D_H