diff options
-rw-r--r-- | doc/classes/SpriteFrames.xml | 7 | ||||
-rw-r--r-- | editor/connections_dialog.cpp | 16 | ||||
-rw-r--r-- | editor/plugins/visual_shader_editor_plugin.cpp | 10 | ||||
-rw-r--r-- | main/performance.cpp | 5 | ||||
-rw-r--r-- | main/performance.h | 1 | ||||
-rw-r--r-- | platform/android/export/export.cpp | 9 | ||||
-rw-r--r-- | scene/2d/animated_sprite.cpp | 12 | ||||
-rw-r--r-- | scene/2d/animated_sprite.h | 1 | ||||
-rw-r--r-- | scene/2d/collision_object_2d.cpp | 25 | ||||
-rw-r--r-- | scene/2d/collision_object_2d.h | 4 | ||||
-rw-r--r-- | scene/2d/node_2d.cpp | 1 | ||||
-rw-r--r-- | scene/2d/physics_body_2d.cpp | 109 | ||||
-rw-r--r-- | scene/2d/physics_body_2d.h | 17 | ||||
-rw-r--r-- | scene/register_scene_types.cpp | 8 | ||||
-rw-r--r-- | scene/resources/animation.cpp | 8 | ||||
-rwxr-xr-x | scene/resources/default_theme/make_header.py | 26 | ||||
-rw-r--r-- | scene/resources/visual_shader_nodes.cpp | 112 | ||||
-rw-r--r-- | scene/resources/visual_shader_nodes.h | 24 | ||||
-rw-r--r-- | servers/audio_server.cpp | 9 | ||||
-rw-r--r-- | servers/audio_server.h | 5 | ||||
-rw-r--r-- | servers/physics_2d/physics_2d_server_sw.cpp | 10 | ||||
-rw-r--r-- | servers/visual/shader_language.cpp | 8 |
22 files changed, 302 insertions, 125 deletions
diff --git a/doc/classes/SpriteFrames.xml b/doc/classes/SpriteFrames.xml index 91129b5850..68373ebc4f 100644 --- a/doc/classes/SpriteFrames.xml +++ b/doc/classes/SpriteFrames.xml @@ -127,6 +127,13 @@ Changes the animation's name to [code]newname[/code]. </description> </method> + <method name="get_animation_names"> + <return type="PoolStringArray"> + </return> + <description> + Returns an array containing the names associated to each animation. Values are placed in alphabetical order. + </description> + </method> <method name="set_animation_loop"> <return type="void"> </return> diff --git a/editor/connections_dialog.cpp b/editor/connections_dialog.cpp index 7f93917744..8933fd7fe8 100644 --- a/editor/connections_dialog.cpp +++ b/editor/connections_dialog.cpp @@ -428,6 +428,13 @@ void ConnectionsDock::_make_or_edit_connection() { bool oshot = connect_dialog->get_oneshot(); cToMake.flags = CONNECT_PERSIST | (defer ? CONNECT_DEFERRED : 0) | (oshot ? CONNECT_ONESHOT : 0); + bool add_script_function = connect_dialog->get_make_callback(); + PoolStringArray script_function_args; + if (add_script_function) { + // pick up args here before "it" is deleted by update_tree + script_function_args = it->get_metadata(0).operator Dictionary()["args"]; + } + if (connect_dialog->is_editing()) { _disconnect(*it); _connect(cToMake); @@ -435,9 +442,12 @@ void ConnectionsDock::_make_or_edit_connection() { _connect(cToMake); } - if (connect_dialog->get_make_callback()) { - PoolStringArray args = it->get_metadata(0).operator Dictionary()["args"]; - editor->emit_signal("script_add_function_request", target, cToMake.method, args); + // IMPORTANT NOTE: _disconnect and _connect cause an update_tree, + // which will delete the object "it" is pointing to + it = NULL; + + if (add_script_function) { + editor->emit_signal("script_add_function_request", target, cToMake.method, script_function_args); hide(); } diff --git a/editor/plugins/visual_shader_editor_plugin.cpp b/editor/plugins/visual_shader_editor_plugin.cpp index 9a351c26fa..682ca744ff 100644 --- a/editor/plugins/visual_shader_editor_plugin.cpp +++ b/editor/plugins/visual_shader_editor_plugin.cpp @@ -768,17 +768,17 @@ VisualShaderEditor::VisualShaderEditor() { add_options.push_back(AddOption("VectorOp", "Operators", "VisualShaderNodeVectorOp")); add_options.push_back(AddOption("ColorOp", "Operators", "VisualShaderNodeColorOp")); add_options.push_back(AddOption("TransformMult", "Operators", "VisualShaderNodeTransformMult")); - add_options.push_back(AddOption("TransformVecMult", "Operators", "VisualShaderNodeTransformVecMult")); + add_options.push_back(AddOption("TransformVectorMult", "Operators", "VisualShaderNodeTransformVecMult")); add_options.push_back(AddOption("ScalarFunc", "Functions", "VisualShaderNodeScalarFunc")); add_options.push_back(AddOption("VectorFunc", "Functions", "VisualShaderNodeVectorFunc")); add_options.push_back(AddOption("DotProduct", "Functions", "VisualShaderNodeDotProduct")); add_options.push_back(AddOption("VectorLen", "Functions", "VisualShaderNodeVectorLen")); add_options.push_back(AddOption("ScalarInterp", "Interpolation", "VisualShaderNodeScalarInterp")); add_options.push_back(AddOption("VectorInterp", "Interpolation", "VisualShaderNodeVectorInterp")); - add_options.push_back(AddOption("VectorConstruct", "Construct", "VisualShaderNodeVectorConstruct")); - add_options.push_back(AddOption("TransformConstruct", "Construct", "VisualShaderNodeTransformConstruct")); - add_options.push_back(AddOption("VectorDestruct", "Destruct", "VisualShaderNodeVectorDestruct")); - add_options.push_back(AddOption("TransformDestruct", "Destruct", "VisualShaderNodeTransformDestruct")); + add_options.push_back(AddOption("VectorCompose", "Compose", "VisualShaderNodeVectorCompose")); + add_options.push_back(AddOption("TransformCompose", "Compose", "VisualShaderNodeTransformCompose")); + add_options.push_back(AddOption("VectorDecompose", "Decompose", "VisualShaderNodeVectorDecompose")); + add_options.push_back(AddOption("TransformDecompose", "Decompose", "VisualShaderNodeTransformDecompose")); add_options.push_back(AddOption("Scalar", "Uniforms", "VisualShaderNodeScalarUniform")); add_options.push_back(AddOption("Vector", "Uniforms", "VisualShaderNodeVec3Uniform")); add_options.push_back(AddOption("Color", "Uniforms", "VisualShaderNodeColorUniform")); diff --git a/main/performance.cpp b/main/performance.cpp index fc915e2e76..70e0a5f7aa 100644 --- a/main/performance.cpp +++ b/main/performance.cpp @@ -32,6 +32,7 @@ #include "message_queue.h" #include "os/os.h" #include "scene/main/scene_tree.h" +#include "servers/audio_server.h" #include "servers/physics_2d_server.h" #include "servers/physics_server.h" #include "servers/visual_server.h" @@ -68,6 +69,7 @@ void Performance::_bind_methods() { BIND_ENUM_CONSTANT(PHYSICS_3D_ACTIVE_OBJECTS); BIND_ENUM_CONSTANT(PHYSICS_3D_COLLISION_PAIRS); BIND_ENUM_CONSTANT(PHYSICS_3D_ISLAND_COUNT); + BIND_ENUM_CONSTANT(AUDIO_OUTPUT_LATENCY); BIND_ENUM_CONSTANT(MONITOR_MAX); } @@ -104,6 +106,7 @@ String Performance::get_monitor_name(Monitor p_monitor) const { "physics_3d/active_objects", "physics_3d/collision_pairs", "physics_3d/islands", + "audio/output_latency", }; @@ -147,6 +150,7 @@ float Performance::get_monitor(Monitor p_monitor) const { case PHYSICS_3D_ACTIVE_OBJECTS: return PhysicsServer::get_singleton()->get_process_info(PhysicsServer::INFO_ACTIVE_OBJECTS); case PHYSICS_3D_COLLISION_PAIRS: return PhysicsServer::get_singleton()->get_process_info(PhysicsServer::INFO_COLLISION_PAIRS); case PHYSICS_3D_ISLAND_COUNT: return PhysicsServer::get_singleton()->get_process_info(PhysicsServer::INFO_ISLAND_COUNT); + case AUDIO_OUTPUT_LATENCY: return AudioServer::get_singleton()->get_output_latency(); default: {} } @@ -186,6 +190,7 @@ Performance::MonitorType Performance::get_monitor_type(Monitor p_monitor) const MONITOR_TYPE_QUANTITY, MONITOR_TYPE_QUANTITY, MONITOR_TYPE_QUANTITY, + MONITOR_TYPE_TIME, }; diff --git a/main/performance.h b/main/performance.h index 464226b517..de00df5ff9 100644 --- a/main/performance.h +++ b/main/performance.h @@ -77,6 +77,7 @@ public: PHYSICS_3D_COLLISION_PAIRS, PHYSICS_3D_ISLAND_COUNT, //physics + AUDIO_OUTPUT_LATENCY, MONITOR_MAX }; diff --git a/platform/android/export/export.cpp b/platform/android/export/export.cpp index c3ff157f99..c562a47b00 100644 --- a/platform/android/export/export.cpp +++ b/platform/android/export/export.cpp @@ -228,7 +228,7 @@ class EditorExportAndroid : public EditorExportPlatform { }; Vector<Device> devices; - bool devices_changed; + volatile bool devices_changed; Mutex *device_lock; Thread *device_thread; volatile bool quit_request; @@ -1154,7 +1154,10 @@ public: virtual bool poll_devices() { bool dc = devices_changed; - devices_changed = false; + if (dc) { + // don't clear unless we're reporting true, to avoid race + devices_changed = false; + } return dc; } @@ -1857,9 +1860,9 @@ public: run_icon->create_from_image(img); device_lock = Mutex::create(); - device_thread = Thread::create(_device_poll_thread, this); devices_changed = true; quit_request = false; + device_thread = Thread::create(_device_poll_thread, this); } ~EditorExportAndroid() { diff --git a/scene/2d/animated_sprite.cpp b/scene/2d/animated_sprite.cpp index e3d1592be0..b56eedabc7 100644 --- a/scene/2d/animated_sprite.cpp +++ b/scene/2d/animated_sprite.cpp @@ -192,6 +192,16 @@ void SpriteFrames::get_animation_list(List<StringName> *r_animations) const { } } +Vector<String> SpriteFrames::get_animation_names() const { + + Vector<String> names; + for (const Map<StringName, Anim>::Element *E = animations.front(); E; E = E->next()) { + names.push_back(E->key()); + } + names.sort(); + return names; +} + void SpriteFrames::set_animation_speed(const StringName &p_anim, float p_fps) { ERR_FAIL_COND(p_fps < 0); @@ -283,6 +293,8 @@ void SpriteFrames::_bind_methods() { ClassDB::bind_method(D_METHOD("remove_animation", "anim"), &SpriteFrames::remove_animation); ClassDB::bind_method(D_METHOD("rename_animation", "anim", "newname"), &SpriteFrames::rename_animation); + ClassDB::bind_method(D_METHOD("get_animation_names"), &SpriteFrames::get_animation_names); + ClassDB::bind_method(D_METHOD("set_animation_speed", "anim", "speed"), &SpriteFrames::set_animation_speed); ClassDB::bind_method(D_METHOD("get_animation_speed", "anim"), &SpriteFrames::get_animation_speed); diff --git a/scene/2d/animated_sprite.h b/scene/2d/animated_sprite.h index 806052a696..f6586aff36 100644 --- a/scene/2d/animated_sprite.h +++ b/scene/2d/animated_sprite.h @@ -72,6 +72,7 @@ public: void rename_animation(const StringName &p_prev, const StringName &p_next); void get_animation_list(List<StringName> *r_animations) const; + Vector<String> get_animation_names() const; void set_animation_speed(const StringName &p_anim, float p_fps); float get_animation_speed(const StringName &p_anim) const; diff --git a/scene/2d/collision_object_2d.cpp b/scene/2d/collision_object_2d.cpp index d05c818ae1..cabd7fddc2 100644 --- a/scene/2d/collision_object_2d.cpp +++ b/scene/2d/collision_object_2d.cpp @@ -38,10 +38,14 @@ void CollisionObject2D::_notification(int p_what) { case NOTIFICATION_ENTER_TREE: { + Transform2D global_transform = get_global_transform(); + if (area) - Physics2DServer::get_singleton()->area_set_transform(rid, get_global_transform()); + Physics2DServer::get_singleton()->area_set_transform(rid, global_transform); else - Physics2DServer::get_singleton()->body_set_state(rid, Physics2DServer::BODY_STATE_TRANSFORM, get_global_transform()); + Physics2DServer::get_singleton()->body_set_state(rid, Physics2DServer::BODY_STATE_TRANSFORM, global_transform); + + last_transform = global_transform; RID space = get_world_2d()->get_space(); if (area) { @@ -60,10 +64,18 @@ void CollisionObject2D::_notification(int p_what) { } break; case NOTIFICATION_TRANSFORM_CHANGED: { + Transform2D global_transform = get_global_transform(); + + if (only_update_transform_changes && global_transform == last_transform) { + return; + } + if (area) - Physics2DServer::get_singleton()->area_set_transform(rid, get_global_transform()); + Physics2DServer::get_singleton()->area_set_transform(rid, global_transform); else - Physics2DServer::get_singleton()->body_set_state(rid, Physics2DServer::BODY_STATE_TRANSFORM, get_global_transform()); + Physics2DServer::get_singleton()->body_set_state(rid, Physics2DServer::BODY_STATE_TRANSFORM, global_transform); + + last_transform = global_transform; } break; case NOTIFICATION_EXIT_TREE: { @@ -318,6 +330,10 @@ void CollisionObject2D::_mouse_exit() { emit_signal(SceneStringNames::get_singleton()->mouse_exited); } +void CollisionObject2D::set_only_update_transform_changes(bool p_enable) { + only_update_transform_changes = p_enable; +} + void CollisionObject2D::_update_pickable() { if (!is_inside_tree()) return; @@ -384,6 +400,7 @@ CollisionObject2D::CollisionObject2D(RID p_rid, bool p_area) { pickable = true; set_notify_transform(true); total_subshapes = 0; + only_update_transform_changes = false; if (p_area) { diff --git a/scene/2d/collision_object_2d.h b/scene/2d/collision_object_2d.h index 6da63d1a0b..29a00bd9f9 100644 --- a/scene/2d/collision_object_2d.h +++ b/scene/2d/collision_object_2d.h @@ -65,6 +65,8 @@ class CollisionObject2D : public Node2D { int total_subshapes; Map<uint32_t, ShapeData> shapes; + Transform2D last_transform; + bool only_update_transform_changes; //this is used for sync physics in KinematicBody protected: CollisionObject2D(RID p_rid, bool p_area); @@ -78,6 +80,8 @@ protected: void _mouse_enter(); void _mouse_exit(); + void set_only_update_transform_changes(bool p_enable); + public: uint32_t create_shape_owner(Object *p_owner); void remove_shape_owner(uint32_t owner); diff --git a/scene/2d/node_2d.cpp b/scene/2d/node_2d.cpp index 3813bd96fe..7252602a93 100644 --- a/scene/2d/node_2d.cpp +++ b/scene/2d/node_2d.cpp @@ -130,7 +130,6 @@ void Node2D::_update_xform_values() { void Node2D::_update_transform() { - Transform2D mat(angle, pos); _mat.set_rotation_and_scale(angle, _scale); _mat.elements[2] = pos; diff --git a/scene/2d/physics_body_2d.cpp b/scene/2d/physics_body_2d.cpp index 713d1daeef..8787a2c735 100644 --- a/scene/2d/physics_body_2d.cpp +++ b/scene/2d/physics_body_2d.cpp @@ -971,11 +971,11 @@ RigidBody2D::~RigidBody2D() { ////////////////////////// -Ref<KinematicCollision2D> KinematicBody2D::_move(const Vector2 &p_motion, bool p_infinite_inertia, bool p_exclude_raycast_shapes) { +Ref<KinematicCollision2D> KinematicBody2D::_move(const Vector2 &p_motion, bool p_infinite_inertia, bool p_exclude_raycast_shapes, bool p_test_only) { Collision col; - if (move_and_collide(p_motion, p_infinite_inertia, col, p_exclude_raycast_shapes)) { + if (move_and_collide(p_motion, p_infinite_inertia, col, p_exclude_raycast_shapes, p_test_only)) { if (motion_cache.is_null()) { motion_cache.instance(); motion_cache->owner = this; @@ -1026,7 +1026,7 @@ bool KinematicBody2D::separate_raycast_shapes(bool p_infinite_inertia, Collision } } -bool KinematicBody2D::move_and_collide(const Vector2 &p_motion, bool p_infinite_inertia, Collision &r_collision, bool p_exclude_raycast_shapes) { +bool KinematicBody2D::move_and_collide(const Vector2 &p_motion, bool p_infinite_inertia, Collision &r_collision, bool p_exclude_raycast_shapes, bool p_test_only) { Transform2D gt = get_global_transform(); Physics2DServer::MotionResult result; @@ -1039,23 +1039,36 @@ bool KinematicBody2D::move_and_collide(const Vector2 &p_motion, bool p_infinite_ r_collision.collision = result.collision_point; r_collision.normal = result.collision_normal; r_collision.collider = result.collider_id; + r_collision.collider_rid = result.collider; r_collision.travel = result.motion; r_collision.remainder = result.remainder; r_collision.local_shape = result.collision_local_shape; } - gt.elements[2] += result.motion; - set_global_transform(gt); + if (!p_test_only) { + gt.elements[2] += result.motion; + set_global_transform(gt); + } return colliding; } Vector2 KinematicBody2D::move_and_slide(const Vector2 &p_linear_velocity, const Vector2 &p_floor_direction, bool p_infinite_inertia, float p_slope_stop_min_velocity, int p_max_slides, float p_floor_max_angle) { - Vector2 motion = (floor_velocity + p_linear_velocity) * get_physics_process_delta_time(); + Vector2 floor_motion = floor_velocity; + if (on_floor && on_floor_body.is_valid()) { + //this approach makes sure there is less delay between the actual body velocity and the one we saved + Physics2DDirectBodyState *bs = Physics2DServer::get_singleton()->body_get_direct_state(on_floor_body); + if (bs) { + floor_motion = bs->get_linear_velocity(); + } + } + + Vector2 motion = (floor_motion + p_linear_velocity) * get_physics_process_delta_time(); Vector2 lv = p_linear_velocity; on_floor = false; + on_floor_body = RID(); on_ceiling = false; on_wall = false; colliders.clear(); @@ -1096,6 +1109,7 @@ Vector2 KinematicBody2D::move_and_slide(const Vector2 &p_linear_velocity, const if (collision.normal.dot(p_floor_direction) >= Math::cos(p_floor_max_angle)) { //floor on_floor = true; + on_floor_body = collision.collider_rid; floor_velocity = collision.collider_vel; Vector2 rel_v = lv - floor_velocity; @@ -1133,20 +1147,29 @@ Vector2 KinematicBody2D::move_and_slide(const Vector2 &p_linear_velocity, const return lv; } -bool KinematicBody2D::snap_to_floor(const Vector2 &p_direction, float p_floor_max_angle) { +Vector2 KinematicBody2D::move_and_slide_with_snap(const Vector2 &p_linear_velocity, const Vector2 &p_snap, const Vector2 &p_floor_direction, bool p_infinite_inertia, float p_slope_stop_min_velocity, int p_max_slides, float p_floor_max_angle) { + + bool was_on_floor = on_floor; + + Vector2 ret = move_and_slide(p_linear_velocity, p_floor_direction, p_infinite_inertia, p_slope_stop_min_velocity, p_max_slides, p_floor_max_angle); + if (!was_on_floor || p_snap == Vector2()) { + return ret; + } + Collision col; Transform2D gt = get_global_transform(); - Physics2DServer::MotionResult result; - bool colliding = Physics2DServer::get_singleton()->body_test_motion(get_rid(), gt, p_direction, false, margin, &result, false); - if (colliding) { - gt.elements[2] += result.motion; - if (Math::acos(p_direction.normalized().dot(-result.collision_normal)) < p_floor_max_angle) { + + if (move_and_collide(p_snap, p_infinite_inertia, col, false, true)) { + gt.elements[2] += col.travel; + if (p_floor_direction != Vector2() && Math::acos(p_floor_direction.normalized().dot(col.normal)) < p_floor_max_angle) { on_floor = true; + on_floor_body = col.collider_rid; + floor_velocity = col.collider_vel; } set_global_transform(gt); } - return colliding; + return ret; } bool KinematicBody2D::is_on_floor() const { @@ -1210,11 +1233,60 @@ Ref<KinematicCollision2D> KinematicBody2D::_get_slide_collision(int p_bounce) { return slide_colliders[p_bounce]; } +void KinematicBody2D::set_sync_to_physics(bool p_enable) { + + if (sync_to_physics == p_enable) { + return; + } + sync_to_physics = p_enable; + if (p_enable) { + Physics2DServer::get_singleton()->body_set_force_integration_callback(get_rid(), this, "_direct_state_changed"); + set_only_update_transform_changes(true); + set_notify_local_transform(true); + } else { + Physics2DServer::get_singleton()->body_set_force_integration_callback(get_rid(), NULL, ""); + set_only_update_transform_changes(false); + set_notify_local_transform(false); + } +} + +bool KinematicBody2D::is_sync_to_physics_enabled() const { + return sync_to_physics; +} + +void KinematicBody2D::_direct_state_changed(Object *p_state) { + + if (!sync_to_physics) + return; + + Physics2DDirectBodyState *state = Object::cast_to<Physics2DDirectBodyState>(p_state); + + last_valid_transform = state->get_transform(); + set_notify_local_transform(false); + set_global_transform(last_valid_transform); + set_notify_local_transform(true); +} + +void KinematicBody2D::_notification(int p_what) { + if (p_what == NOTIFICATION_ENTER_TREE) { + last_valid_transform = get_global_transform(); + } + + if (p_what == NOTIFICATION_LOCAL_TRANSFORM_CHANGED) { + //used by sync to physics, send the new transform to the physics + Transform2D new_transform = get_global_transform(); + Physics2DServer::get_singleton()->body_set_state(get_rid(), Physics2DServer::BODY_STATE_TRANSFORM, new_transform); + //but then revert changes + set_notify_local_transform(false); + set_global_transform(last_valid_transform); + set_notify_local_transform(true); + } +} void KinematicBody2D::_bind_methods() { - ClassDB::bind_method(D_METHOD("move_and_collide", "rel_vec", "infinite_inertia", "exclude_raycast_shapes"), &KinematicBody2D::_move, DEFVAL(true), DEFVAL(true)); + ClassDB::bind_method(D_METHOD("move_and_collide", "rel_vec", "infinite_inertia", "exclude_raycast_shapes", "test_only"), &KinematicBody2D::_move, DEFVAL(true), DEFVAL(true), DEFVAL(false)); ClassDB::bind_method(D_METHOD("move_and_slide", "linear_velocity", "floor_normal", "infinite_inertia", "slope_stop_min_velocity", "max_bounces", "floor_max_angle"), &KinematicBody2D::move_and_slide, DEFVAL(Vector2(0, 0)), DEFVAL(true), DEFVAL(5), DEFVAL(4), DEFVAL(Math::deg2rad((float)45))); - ClassDB::bind_method(D_METHOD("snap_to_floor", "motion", "max_floor_angle"), &KinematicBody2D::snap_to_floor, DEFVAL(Math::deg2rad(45.0))); + ClassDB::bind_method(D_METHOD("move_and_slide_with_snap", "linear_velocity", "snap", "floor_normal", "infinite_inertia", "slope_stop_min_velocity", "max_bounces", "floor_max_angle"), &KinematicBody2D::move_and_slide_with_snap, DEFVAL(Vector2(0, 0)), DEFVAL(true), DEFVAL(5), DEFVAL(4), DEFVAL(Math::deg2rad((float)45))); ClassDB::bind_method(D_METHOD("test_move", "from", "rel_vec", "infinite_inertia"), &KinematicBody2D::test_move); @@ -1229,7 +1301,13 @@ void KinematicBody2D::_bind_methods() { 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); + ClassDB::bind_method(D_METHOD("set_sync_to_physics", "enable"), &KinematicBody2D::set_sync_to_physics); + ClassDB::bind_method(D_METHOD("is_sync_to_physics_enabled"), &KinematicBody2D::is_sync_to_physics_enabled); + + ClassDB::bind_method(D_METHOD("_direct_state_changed"), &KinematicBody2D::_direct_state_changed); + ADD_PROPERTY(PropertyInfo(Variant::REAL, "collision/safe_margin", PROPERTY_HINT_RANGE, "0.001,256,0.001"), "set_safe_margin", "get_safe_margin"); + ADD_PROPERTY(PropertyInfo(Variant::BOOL, "motion/sync_to_physics"), "set_sync_to_physics", "is_sync_to_physics_enabled"); } KinematicBody2D::KinematicBody2D() : @@ -1240,6 +1318,7 @@ KinematicBody2D::KinematicBody2D() : on_floor = false; on_ceiling = false; on_wall = false; + sync_to_physics = false; } KinematicBody2D::~KinematicBody2D() { if (motion_cache.is_valid()) { diff --git a/scene/2d/physics_body_2d.h b/scene/2d/physics_body_2d.h index 1873c977a9..7bda6ce817 100644 --- a/scene/2d/physics_body_2d.h +++ b/scene/2d/physics_body_2d.h @@ -276,6 +276,7 @@ public: Vector2 normal; Vector2 collider_vel; ObjectID collider; + RID collider_rid; int collider_shape; Variant collider_metadata; Vector2 remainder; @@ -287,9 +288,11 @@ private: float margin; Vector2 floor_velocity; + RID on_floor_body; bool on_floor; bool on_ceiling; bool on_wall; + bool sync_to_physics; Vector<Collision> colliders; Vector<Ref<KinematicCollision2D> > slide_colliders; @@ -297,15 +300,19 @@ private: _FORCE_INLINE_ bool _ignores_mode(Physics2DServer::BodyMode) const; - Ref<KinematicCollision2D> _move(const Vector2 &p_motion, bool p_infinite_inertia = true, bool p_exclude_raycast_shapes = true); + Ref<KinematicCollision2D> _move(const Vector2 &p_motion, bool p_infinite_inertia = true, bool p_exclude_raycast_shapes = true, bool p_test_only = false); Ref<KinematicCollision2D> _get_slide_collision(int p_bounce); + Transform2D last_valid_transform; + void _direct_state_changed(Object *p_state); + protected: + void _notification(int p_what); static void _bind_methods(); public: - bool move_and_collide(const Vector2 &p_motion, bool p_infinite_inertia, Collision &r_collision, bool p_exclude_raycast_shapes = true); - bool snap_to_floor(const Vector2 &p_direction, float p_floor_max_angle = Math::deg2rad((float)45)); + bool move_and_collide(const Vector2 &p_motion, bool p_infinite_inertia, Collision &r_collision, bool p_exclude_raycast_shapes = true, bool p_test_only = false); + bool test_move(const Transform2D &p_from, const Vector2 &p_motion, bool p_infinite_inertia); bool separate_raycast_shapes(bool p_infinite_inertia, Collision &r_collision); @@ -314,6 +321,7 @@ public: float get_safe_margin() const; Vector2 move_and_slide(const Vector2 &p_linear_velocity, const Vector2 &p_floor_direction = Vector2(0, 0), bool p_infinite_inertia = true, float p_slope_stop_min_velocity = 5, int p_max_slides = 4, float p_floor_max_angle = Math::deg2rad((float)45)); + Vector2 move_and_slide_with_snap(const Vector2 &p_linear_velocity, const Vector2 &p_snap, const Vector2 &p_floor_direction = Vector2(0, 0), bool p_infinite_inertia = true, 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; @@ -322,6 +330,9 @@ public: int get_slide_count() const; Collision get_slide_collision(int p_bounce) const; + void set_sync_to_physics(bool p_enable); + bool is_sync_to_physics_enabled() const; + KinematicBody2D(); ~KinematicBody2D(); }; diff --git a/scene/register_scene_types.cpp b/scene/register_scene_types.cpp index 8dd378c319..8f78e137b4 100644 --- a/scene/register_scene_types.cpp +++ b/scene/register_scene_types.cpp @@ -477,10 +477,10 @@ void register_scene_types() { ClassDB::register_class<VisualShaderNodeVectorLen>(); ClassDB::register_class<VisualShaderNodeScalarInterp>(); ClassDB::register_class<VisualShaderNodeVectorInterp>(); - ClassDB::register_class<VisualShaderNodeVectorConstruct>(); - ClassDB::register_class<VisualShaderNodeTransformConstruct>(); - ClassDB::register_class<VisualShaderNodeVectorDestruct>(); - ClassDB::register_class<VisualShaderNodeTransformDestruct>(); + ClassDB::register_class<VisualShaderNodeVectorCompose>(); + ClassDB::register_class<VisualShaderNodeTransformCompose>(); + ClassDB::register_class<VisualShaderNodeVectorDecompose>(); + ClassDB::register_class<VisualShaderNodeTransformDecompose>(); ClassDB::register_class<VisualShaderNodeTexture>(); ClassDB::register_class<VisualShaderNodeCubeMap>(); ClassDB::register_virtual_class<VisualShaderNodeUniform>(); diff --git a/scene/resources/animation.cpp b/scene/resources/animation.cpp index e57a2b68c8..8acfdc482a 100644 --- a/scene/resources/animation.cpp +++ b/scene/resources/animation.cpp @@ -2329,13 +2329,14 @@ float Animation::bezier_track_interpolate(int p_track, float p_time) const { int iterations = 10; - float low = 0; - float high = bt->values[idx + 1].time - bt->values[idx].time; + float duration = bt->values[idx + 1].time - bt->values[idx].time; // time duration between our two keyframes + float low = 0; // 0% of the current animation segment + float high = 1; // 100% of the current animation segment float middle = 0; Vector2 start(0, bt->values[idx].value.value); Vector2 start_out = start + bt->values[idx].value.out_handle; - Vector2 end(high, bt->values[idx + 1].value.value); + Vector2 end(duration, bt->values[idx + 1].value.value); Vector2 end_in = end + bt->values[idx + 1].value.in_handle; //narrow high and low as much as possible @@ -2355,7 +2356,6 @@ float Animation::bezier_track_interpolate(int p_track, float p_time) const { //interpolate the result: Vector2 low_pos = _bezier_interp(low, start, start_out, end_in, end); Vector2 high_pos = _bezier_interp(high, start, start_out, end_in, end); - float c = (t - low_pos.x) / (high_pos.x - low_pos.x); return low_pos.linear_interpolate(high_pos, c).y; diff --git a/scene/resources/default_theme/make_header.py b/scene/resources/default_theme/make_header.py index db449f9417..73b1ae0b0b 100755 --- a/scene/resources/default_theme/make_header.py +++ b/scene/resources/default_theme/make_header.py @@ -4,15 +4,16 @@ import os import glob import string +enc = "utf-8" # Generate include files f = open("theme_data.h", "wb") -f.write("// THIS FILE HAS BEEN AUTOGENERATED, DON'T EDIT!!\n") +f.write(b"// THIS FILE HAS BEEN AUTOGENERATED, DON\'T EDIT!!\n") # Generate png image block -f.write("\n// png image block\n"); +f.write(b"\n// png image block\n") pixmaps = glob.glob("*.png") pixmaps.sort() @@ -21,22 +22,23 @@ for x in pixmaps: var_str = x[:-4] + "_png" - f.write("\nstatic const unsigned char " + var_str + "[] = {\n\t") + s = "\nstatic const unsigned char " + var_str + "[] = {\n\t" + f.write(s.encode(enc)) pngf = open(x, "rb") b = pngf.read(1) while(len(b) == 1): - f.write(hex(ord(b))) + f.write(hex(ord(b)).encode(enc)) b = pngf.read(1) if (len(b) == 1): - f.write(", ") + f.write(b", ") - f.write("\n};\n") + f.write(b"\n};\n") pngf.close() # Generate shaders block -f.write("\n// shaders block\n"); +f.write(b"\n// shaders block\n"); shaders = glob.glob("*.gsl") shaders.sort() @@ -45,7 +47,8 @@ for x in shaders: var_str = x[:-4] + "_shader_code" - f.write("\nstatic const char *" + var_str + " = \n") + s = "\nstatic const char *" + var_str + " = \n" + f.write(s.encode(enc)) sf = open(x, "rb") @@ -55,12 +58,13 @@ for x in shaders: b = b[:-2] if (b.endswith("\n")): b = b[:-1] - f.write(" \"" + b) + s = ' \"' + b + f.write(s.encode(enc)) b = sf.readline() if (b != ""): - f.write("\"\n") + f.write(b'"\n') - f.write("\";\n") + f.write(b'";\n') sf.close() f.close() diff --git a/scene/resources/visual_shader_nodes.cpp b/scene/resources/visual_shader_nodes.cpp index 90af312870..e850aaa44c 100644 --- a/scene/resources/visual_shader_nodes.cpp +++ b/scene/resources/visual_shader_nodes.cpp @@ -183,7 +183,7 @@ VisualShaderNodeVec3Constant::VisualShaderNodeVec3Constant() { ////////////// Transform String VisualShaderNodeTransformConstant::get_caption() const { - return "Transform4x3"; + return "Transform"; } int VisualShaderNodeTransformConstant::get_input_port_count() const { @@ -681,7 +681,7 @@ VisualShaderNodeScalarOp::VisualShaderNodeScalarOp() { ////////////// Vector Op String VisualShaderNodeVectorOp::get_caption() const { - return "VecOp"; + return "VectorOp"; } int VisualShaderNodeVectorOp::get_input_port_count() const { @@ -905,7 +905,7 @@ VisualShaderNodeColorOp::VisualShaderNodeColorOp() { ////////////// Transform Mult String VisualShaderNodeTransformMult::get_caption() const { - return "TransMult"; + return "TransformMult"; } int VisualShaderNodeTransformMult::get_input_port_count() const { @@ -971,7 +971,7 @@ VisualShaderNodeTransformMult::VisualShaderNodeTransformMult() { ////////////// TransformVec Mult String VisualShaderNodeTransformVecMult::get_caption() const { - return "TransVecMult"; + return "TransformVectorMult"; } int VisualShaderNodeTransformVecMult::get_input_port_count() const { @@ -1150,7 +1150,7 @@ VisualShaderNodeScalarFunc::VisualShaderNodeScalarFunc() { ////////////// Vector Func String VisualShaderNodeVectorFunc::get_caption() const { - return "VecFunc"; + return "VectorFunc"; } int VisualShaderNodeVectorFunc::get_input_port_count() const { @@ -1251,7 +1251,7 @@ VisualShaderNodeVectorFunc::VisualShaderNodeVectorFunc() { ////////////// Dot Product String VisualShaderNodeDotProduct::get_caption() const { - return "DotProd"; + return "DotProduct"; } int VisualShaderNodeDotProduct::get_input_port_count() const { @@ -1286,7 +1286,7 @@ VisualShaderNodeDotProduct::VisualShaderNodeDotProduct() { ////////////// Vector Len String VisualShaderNodeVectorLen::get_caption() const { - return "VecLen"; + return "VectorLen"; } int VisualShaderNodeVectorLen::get_input_port_count() const { @@ -1362,7 +1362,7 @@ VisualShaderNodeScalarInterp::VisualShaderNodeScalarInterp() { ////////////// Vector Interp String VisualShaderNodeVectorInterp::get_caption() const { - return "VecInterp"; + return "VectorInterp"; } int VisualShaderNodeVectorInterp::get_input_port_count() const { @@ -1401,18 +1401,18 @@ VisualShaderNodeVectorInterp::VisualShaderNodeVectorInterp() { set_input_port_default_value(2, Vector3()); } -////////////// Vector Construct -String VisualShaderNodeVectorConstruct::get_caption() const { - return "VecConstr"; +////////////// Vector Compose +String VisualShaderNodeVectorCompose::get_caption() const { + return "VectorCompose"; } -int VisualShaderNodeVectorConstruct::get_input_port_count() const { +int VisualShaderNodeVectorCompose::get_input_port_count() const { return 3; } -VisualShaderNodeVectorConstruct::PortType VisualShaderNodeVectorConstruct::get_input_port_type(int p_port) const { +VisualShaderNodeVectorCompose::PortType VisualShaderNodeVectorCompose::get_input_port_type(int p_port) const { return PORT_TYPE_SCALAR; } -String VisualShaderNodeVectorConstruct::get_input_port_name(int p_port) const { +String VisualShaderNodeVectorCompose::get_input_port_name(int p_port) const { if (p_port == 0) { return "x"; } else if (p_port == 1) { @@ -1422,40 +1422,40 @@ String VisualShaderNodeVectorConstruct::get_input_port_name(int p_port) const { } } -int VisualShaderNodeVectorConstruct::get_output_port_count() const { +int VisualShaderNodeVectorCompose::get_output_port_count() const { return 1; } -VisualShaderNodeVectorConstruct::PortType VisualShaderNodeVectorConstruct::get_output_port_type(int p_port) const { +VisualShaderNodeVectorCompose::PortType VisualShaderNodeVectorCompose::get_output_port_type(int p_port) const { return PORT_TYPE_VECTOR; } -String VisualShaderNodeVectorConstruct::get_output_port_name(int p_port) const { +String VisualShaderNodeVectorCompose::get_output_port_name(int p_port) const { return "vec"; } -String VisualShaderNodeVectorConstruct::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const { +String VisualShaderNodeVectorCompose::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const { return "\t" + p_output_vars[0] + " = vec3( " + p_input_vars[0] + " , " + p_input_vars[1] + " , " + p_input_vars[2] + " );\n"; } -VisualShaderNodeVectorConstruct::VisualShaderNodeVectorConstruct() { +VisualShaderNodeVectorCompose::VisualShaderNodeVectorCompose() { set_input_port_default_value(0, 0.0); set_input_port_default_value(1, 0.0); set_input_port_default_value(2, 0.0); } -////////////// Transform Construct +////////////// Transform Compose -String VisualShaderNodeTransformConstruct::get_caption() const { - return "TransConstr"; +String VisualShaderNodeTransformCompose::get_caption() const { + return "TransformCompose"; } -int VisualShaderNodeTransformConstruct::get_input_port_count() const { +int VisualShaderNodeTransformCompose::get_input_port_count() const { return 4; } -VisualShaderNodeTransformConstruct::PortType VisualShaderNodeTransformConstruct::get_input_port_type(int p_port) const { +VisualShaderNodeTransformCompose::PortType VisualShaderNodeTransformCompose::get_input_port_type(int p_port) const { return PORT_TYPE_VECTOR; } -String VisualShaderNodeTransformConstruct::get_input_port_name(int p_port) const { +String VisualShaderNodeTransformCompose::get_input_port_name(int p_port) const { if (p_port == 0) { return "x"; } else if (p_port == 1) { @@ -1467,21 +1467,21 @@ String VisualShaderNodeTransformConstruct::get_input_port_name(int p_port) const } } -int VisualShaderNodeTransformConstruct::get_output_port_count() const { +int VisualShaderNodeTransformCompose::get_output_port_count() const { return 1; } -VisualShaderNodeTransformConstruct::PortType VisualShaderNodeTransformConstruct::get_output_port_type(int p_port) const { +VisualShaderNodeTransformCompose::PortType VisualShaderNodeTransformCompose::get_output_port_type(int p_port) const { return PORT_TYPE_TRANSFORM; } -String VisualShaderNodeTransformConstruct::get_output_port_name(int p_port) const { +String VisualShaderNodeTransformCompose::get_output_port_name(int p_port) const { return "xform"; } -String VisualShaderNodeTransformConstruct::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const { +String VisualShaderNodeTransformCompose::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const { return "\t" + p_output_vars[0] + " = mat4( vec4(" + p_input_vars[0] + ", 0.0) , vec4(" + p_input_vars[1] + ", 0.0) , vec4(" + p_input_vars[2] + ",0.0), vec4(" + p_input_vars[3] + ",1.0) );\n"; } -VisualShaderNodeTransformConstruct::VisualShaderNodeTransformConstruct() { +VisualShaderNodeTransformCompose::VisualShaderNodeTransformCompose() { set_input_port_default_value(0, Vector3()); set_input_port_default_value(1, Vector3()); @@ -1489,28 +1489,28 @@ VisualShaderNodeTransformConstruct::VisualShaderNodeTransformConstruct() { set_input_port_default_value(3, Vector3()); } -////////////// Vector Destruct -String VisualShaderNodeVectorDestruct::get_caption() const { - return "VecDestr"; +////////////// Vector Decompose +String VisualShaderNodeVectorDecompose::get_caption() const { + return "VectorDecompose"; } -int VisualShaderNodeVectorDestruct::get_input_port_count() const { +int VisualShaderNodeVectorDecompose::get_input_port_count() const { return 1; } -VisualShaderNodeVectorDestruct::PortType VisualShaderNodeVectorDestruct::get_input_port_type(int p_port) const { +VisualShaderNodeVectorDecompose::PortType VisualShaderNodeVectorDecompose::get_input_port_type(int p_port) const { return PORT_TYPE_VECTOR; } -String VisualShaderNodeVectorDestruct::get_input_port_name(int p_port) const { +String VisualShaderNodeVectorDecompose::get_input_port_name(int p_port) const { return "vec"; } -int VisualShaderNodeVectorDestruct::get_output_port_count() const { +int VisualShaderNodeVectorDecompose::get_output_port_count() const { return 3; } -VisualShaderNodeVectorDestruct::PortType VisualShaderNodeVectorDestruct::get_output_port_type(int p_port) const { +VisualShaderNodeVectorDecompose::PortType VisualShaderNodeVectorDecompose::get_output_port_type(int p_port) const { return PORT_TYPE_SCALAR; } -String VisualShaderNodeVectorDestruct::get_output_port_name(int p_port) const { +String VisualShaderNodeVectorDecompose::get_output_port_name(int p_port) const { if (p_port == 0) { return "x"; } else if (p_port == 1) { @@ -1520,7 +1520,7 @@ String VisualShaderNodeVectorDestruct::get_output_port_name(int p_port) const { } } -String VisualShaderNodeVectorDestruct::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const { +String VisualShaderNodeVectorDecompose::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const { String code; code += "\t" + p_output_vars[0] + " = " + p_input_vars[0] + ".x;\n"; code += "\t" + p_output_vars[1] + " = " + p_input_vars[0] + ".y;\n"; @@ -1528,33 +1528,33 @@ String VisualShaderNodeVectorDestruct::generate_code(Shader::Mode p_mode, Visual return code; } -VisualShaderNodeVectorDestruct::VisualShaderNodeVectorDestruct() { +VisualShaderNodeVectorDecompose::VisualShaderNodeVectorDecompose() { set_input_port_default_value(0, Vector3()); } -////////////// Transform Destruct +////////////// Transform Decompose -String VisualShaderNodeTransformDestruct::get_caption() const { - return "TransDestr"; +String VisualShaderNodeTransformDecompose::get_caption() const { + return "TransformDecompose"; } -int VisualShaderNodeTransformDestruct::get_input_port_count() const { +int VisualShaderNodeTransformDecompose::get_input_port_count() const { return 1; } -VisualShaderNodeTransformDestruct::PortType VisualShaderNodeTransformDestruct::get_input_port_type(int p_port) const { +VisualShaderNodeTransformDecompose::PortType VisualShaderNodeTransformDecompose::get_input_port_type(int p_port) const { return PORT_TYPE_TRANSFORM; } -String VisualShaderNodeTransformDestruct::get_input_port_name(int p_port) const { +String VisualShaderNodeTransformDecompose::get_input_port_name(int p_port) const { return "xform"; } -int VisualShaderNodeTransformDestruct::get_output_port_count() const { +int VisualShaderNodeTransformDecompose::get_output_port_count() const { return 4; } -VisualShaderNodeTransformDestruct::PortType VisualShaderNodeTransformDestruct::get_output_port_type(int p_port) const { +VisualShaderNodeTransformDecompose::PortType VisualShaderNodeTransformDecompose::get_output_port_type(int p_port) const { return PORT_TYPE_VECTOR; } -String VisualShaderNodeTransformDestruct::get_output_port_name(int p_port) const { +String VisualShaderNodeTransformDecompose::get_output_port_name(int p_port) const { if (p_port == 0) { return "x"; } else if (p_port == 1) { @@ -1566,7 +1566,7 @@ String VisualShaderNodeTransformDestruct::get_output_port_name(int p_port) const } } -String VisualShaderNodeTransformDestruct::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const { +String VisualShaderNodeTransformDecompose::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const { String code; code += "\t" + p_output_vars[0] + " = " + p_input_vars[0] + "[0].xyz;\n"; code += "\t" + p_output_vars[1] + " = " + p_input_vars[0] + "[1].xyz;\n"; @@ -1575,7 +1575,7 @@ String VisualShaderNodeTransformDestruct::generate_code(Shader::Mode p_mode, Vis return code; } -VisualShaderNodeTransformDestruct::VisualShaderNodeTransformDestruct() { +VisualShaderNodeTransformDecompose::VisualShaderNodeTransformDecompose() { set_input_port_default_value(0, Transform()); } @@ -1658,7 +1658,7 @@ VisualShaderNodeColorUniform::VisualShaderNodeColorUniform() { ////////////// Vector Uniform String VisualShaderNodeVec3Uniform::get_caption() const { - return "VecUniform"; + return "VectorUniform"; } int VisualShaderNodeVec3Uniform::get_input_port_count() const { @@ -1694,7 +1694,7 @@ VisualShaderNodeVec3Uniform::VisualShaderNodeVec3Uniform() { ////////////// Transform Uniform String VisualShaderNodeTransformUniform::get_caption() const { - return "TransUniform"; + return "TransformUniform"; } int VisualShaderNodeTransformUniform::get_input_port_count() const { @@ -1730,7 +1730,7 @@ VisualShaderNodeTransformUniform::VisualShaderNodeTransformUniform() { ////////////// Texture Uniform String VisualShaderNodeTextureUniform::get_caption() const { - return "TexUniform"; + return "TextureUniform"; } int VisualShaderNodeTextureUniform::get_input_port_count() const { @@ -1848,7 +1848,7 @@ VisualShaderNodeTextureUniform::VisualShaderNodeTextureUniform() { ////////////// CubeMap Uniform String VisualShaderNodeCubeMapUniform::get_caption() const { - return "CubeMap"; + return "CubeMapUniform"; } int VisualShaderNodeCubeMapUniform::get_input_port_count() const { diff --git a/scene/resources/visual_shader_nodes.h b/scene/resources/visual_shader_nodes.h index cf46ee3189..2ede36fbc8 100644 --- a/scene/resources/visual_shader_nodes.h +++ b/scene/resources/visual_shader_nodes.h @@ -621,8 +621,8 @@ public: /////////////////////////////////////// -class VisualShaderNodeVectorConstruct : public VisualShaderNode { - GDCLASS(VisualShaderNodeVectorConstruct, VisualShaderNode) +class VisualShaderNodeVectorCompose : public VisualShaderNode { + GDCLASS(VisualShaderNodeVectorCompose, VisualShaderNode) public: virtual String get_caption() const; @@ -637,13 +637,13 @@ public: virtual String generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const; //if no output is connected, the output var passed will be empty. if no input is connected and input is NIL, the input var passed will be empty - VisualShaderNodeVectorConstruct(); + VisualShaderNodeVectorCompose(); }; /////////////////////////////////////// -class VisualShaderNodeTransformConstruct : public VisualShaderNode { - GDCLASS(VisualShaderNodeTransformConstruct, VisualShaderNode) +class VisualShaderNodeTransformCompose : public VisualShaderNode { + GDCLASS(VisualShaderNodeTransformCompose, VisualShaderNode) public: virtual String get_caption() const; @@ -658,13 +658,13 @@ public: virtual String generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const; //if no output is connected, the output var passed will be empty. if no input is connected and input is NIL, the input var passed will be empty - VisualShaderNodeTransformConstruct(); + VisualShaderNodeTransformCompose(); }; /////////////////////////////////////// -class VisualShaderNodeVectorDestruct : public VisualShaderNode { - GDCLASS(VisualShaderNodeVectorDestruct, VisualShaderNode) +class VisualShaderNodeVectorDecompose : public VisualShaderNode { + GDCLASS(VisualShaderNodeVectorDecompose, VisualShaderNode) public: virtual String get_caption() const; @@ -679,13 +679,13 @@ public: virtual String generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const; //if no output is connected, the output var passed will be empty. if no input is connected and input is NIL, the input var passed will be empty - VisualShaderNodeVectorDestruct(); + VisualShaderNodeVectorDecompose(); }; /////////////////////////////////////// -class VisualShaderNodeTransformDestruct : public VisualShaderNode { - GDCLASS(VisualShaderNodeTransformDestruct, VisualShaderNode) +class VisualShaderNodeTransformDecompose : public VisualShaderNode { + GDCLASS(VisualShaderNodeTransformDecompose, VisualShaderNode) public: virtual String get_caption() const; @@ -700,7 +700,7 @@ public: virtual String generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars) const; //if no output is connected, the output var passed will be empty. if no input is connected and input is NIL, the input var passed will be empty - VisualShaderNodeTransformDestruct(); + VisualShaderNodeTransformDecompose(); }; /////////////////////////////////////// diff --git a/servers/audio_server.cpp b/servers/audio_server.cpp index f2df7119e7..69c1318a48 100644 --- a/servers/audio_server.cpp +++ b/servers/audio_server.cpp @@ -234,6 +234,13 @@ void AudioServer::_driver_process(int p_frames, int32_t *p_buffer) { todo -= to_copy; to_mix -= to_copy; } + + // Calculate latency for Performance.AUDIO_OUTPUT_LATENCY + if (OS::get_singleton()) { + uint64_t ticks = OS::get_singleton()->get_ticks_usec(); + output_latency = (ticks - output_latency_ticks) / 1000000.f; + output_latency_ticks = ticks; + } } void AudioServer::_mix_step() { @@ -1178,6 +1185,8 @@ AudioServer::AudioServer() { mix_frames = 0; channel_count = 0; to_mix = 0; + output_latency = 0; + output_latency_ticks = 0; } AudioServer::~AudioServer() { diff --git a/servers/audio_server.h b/servers/audio_server.h index b7fcd9c093..f928acc7b5 100644 --- a/servers/audio_server.h +++ b/servers/audio_server.h @@ -190,6 +190,9 @@ private: Mutex *audio_data_lock; + float output_latency; + uint64_t output_latency_ticks; + void init_channels_and_buffers(); void _mix_step(); @@ -306,6 +309,8 @@ public: String get_device(); void set_device(String device); + float get_output_latency() { return output_latency; } + AudioServer(); virtual ~AudioServer(); }; diff --git a/servers/physics_2d/physics_2d_server_sw.cpp b/servers/physics_2d/physics_2d_server_sw.cpp index faabed84e9..a473e0beb2 100644 --- a/servers/physics_2d/physics_2d_server_sw.cpp +++ b/servers/physics_2d/physics_2d_server_sw.cpp @@ -984,10 +984,18 @@ int Physics2DServerSW::body_test_ray_separation(RID p_body, const Transform2D &p Physics2DDirectBodyState *Physics2DServerSW::body_get_direct_state(RID p_body) { + if ((using_threads && !doing_sync)) { + ERR_EXPLAIN("Body state is inaccessible right now, wait for iteration or physics process notification."); + ERR_FAIL_V(NULL); + } + + if (!body_owner.owns(p_body)) + return NULL; + Body2DSW *body = body_owner.get(p_body); ERR_FAIL_COND_V(!body, NULL); - if ((using_threads && !doing_sync) || body->get_space()->is_locked()) { + if (body->get_space()->is_locked()) { ERR_EXPLAIN("Body state is inaccessible right now, wait for iteration or physics process notification."); ERR_FAIL_V(NULL); diff --git a/servers/visual/shader_language.cpp b/servers/visual/shader_language.cpp index 346b04f070..fd1eb77143 100644 --- a/servers/visual/shader_language.cpp +++ b/servers/visual/shader_language.cpp @@ -2545,7 +2545,9 @@ ShaderLanguage::Node *ShaderLanguage::_parse_expression(BlockNode *p_block, cons TkPos pos = _get_tkpos(); tk = _get_token(); - if (tk.type == TK_PERIOD) { + if (tk.type == TK_CURSOR) { + //do nothing + } else if (tk.type == TK_PERIOD) { StringName identifier; if (_get_completable_identifier(p_block, COMPLETION_INDEX, identifier)) { @@ -4130,8 +4132,8 @@ Error ShaderLanguage::complete(const String &p_code, const Map<StringName, Funct switch (completion_type) { case COMPLETION_NONE: { - //do none - return ERR_PARSE_ERROR; + //do nothing + return OK; } break; case COMPLETION_RENDER_MODE: { for (int i = 0; i < p_render_modes.size(); i++) { |