feat: modules moved and engine moved to submodule

This commit is contained in:
Jan van der Weide 2025-04-12 18:40:44 +02:00
parent dfb5e645cd
commit c33d2130cc
5136 changed files with 225275 additions and 64485 deletions

View file

@ -43,19 +43,26 @@
#include "scene/gui/control.h"
#include "scene/main/multiplayer_api.h"
#include "scene/main/viewport.h"
#include "scene/main/window.h"
#include "scene/resources/environment.h"
#include "scene/resources/image_texture.h"
#include "scene/resources/material.h"
#include "scene/resources/mesh.h"
#include "scene/resources/packed_scene.h"
#include "scene/resources/world_2d.h"
#include "servers/physics_server_2d.h"
#ifndef _3D_DISABLED
#include "scene/3d/node_3d.h"
#include "scene/resources/3d/world_3d.h"
#include "servers/physics_server_3d.h"
#endif // _3D_DISABLED
#include "window.h"
#ifndef PHYSICS_2D_DISABLED
#include "servers/physics_server_2d.h"
#endif // PHYSICS_2D_DISABLED
#ifndef PHYSICS_3D_DISABLED
#include "servers/physics_server_3d.h"
#endif // PHYSICS_3D_DISABLED
void SceneTreeTimer::_bind_methods() {
ClassDB::bind_method(D_METHOD("set_time_left", "time"), &SceneTreeTimer::set_time_left);
@ -130,7 +137,7 @@ void SceneTree::ClientPhysicsInterpolation::physics_process() {
}
}
}
#endif
#endif // _3D_DISABLED
void SceneTree::tree_changed() {
emit_signal(tree_changed_name);
@ -202,6 +209,104 @@ void SceneTree::flush_transform_notifications() {
}
}
bool SceneTree::is_accessibility_enabled() const {
if (!DisplayServer::get_singleton()->has_feature(DisplayServer::FEATURE_ACCESSIBILITY_SCREEN_READER)) {
return false;
}
DisplayServer::AccessibilityMode accessibility_mode = DisplayServer::accessibility_get_mode();
int screen_reader_acvite = DisplayServer::get_singleton()->accessibility_screen_reader_active();
if ((accessibility_mode == DisplayServer::AccessibilityMode::ACCESSIBILITY_DISABLED) || ((accessibility_mode == DisplayServer::AccessibilityMode::ACCESSIBILITY_AUTO) && (screen_reader_acvite == 0))) {
return false;
}
return true;
}
bool SceneTree::is_accessibility_supported() const {
if (!DisplayServer::get_singleton()->has_feature(DisplayServer::FEATURE_ACCESSIBILITY_SCREEN_READER)) {
return false;
}
DisplayServer::AccessibilityMode accessibility_mode = DisplayServer::accessibility_get_mode();
if (accessibility_mode == DisplayServer::AccessibilityMode::ACCESSIBILITY_DISABLED) {
return false;
}
return true;
}
void SceneTree::_accessibility_force_update() {
accessibility_force_update = true;
}
void SceneTree::_accessibility_notify_change(const Node *p_node, bool p_remove) {
if (p_node) {
if (p_remove) {
accessibility_change_queue.erase(p_node->get_instance_id());
} else {
accessibility_change_queue.insert(p_node->get_instance_id());
}
}
}
void SceneTree::_process_accessibility_changes(DisplayServer::WindowID p_window_id) {
// Process NOTIFICATION_ACCESSIBILITY_UPDATE.
Vector<ObjectID> processed;
for (const ObjectID &id : accessibility_change_queue) {
Node *node = Object::cast_to<Node>(ObjectDB::get_instance(id));
if (!node || !node->get_window()) {
processed.push_back(id);
continue; // Invalid node, remove from list and skip.
} else if (node->get_window()->get_window_id() != p_window_id) {
continue; // Another window, skip.
}
node->notification(Node::NOTIFICATION_ACCESSIBILITY_UPDATE);
processed.push_back(id);
}
// Track focus change.
// Note: Do not use `Window::get_focused_window()`, it returns both native and embedded windows, and we only care about focused element in the currently processed native window.
// Native window focus is handled in the DisplayServer, or AccessKit subclassing adapter.
ObjectID oid = DisplayServer::get_singleton()->window_get_attached_instance_id(p_window_id);
Window *w_this = (Window *)ObjectDB::get_instance(oid);
if (w_this) {
Window *w_focus = w_this->get_focused_subwindow();
if (w_focus && !w_focus->is_part_of_edited_scene()) {
w_this = w_focus;
}
RID new_focus_element;
Control *n_focus = w_this->gui_get_focus_owner();
if (n_focus && !n_focus->is_part_of_edited_scene()) {
new_focus_element = n_focus->get_focused_accessibility_element();
} else {
new_focus_element = w_this->get_focused_accessibility_element();
}
DisplayServer::get_singleton()->accessibility_update_set_focus(new_focus_element);
}
// Cleanup.
for (const ObjectID &id : processed) {
accessibility_change_queue.erase(id);
}
}
void SceneTree::_flush_accessibility_changes() {
if (is_accessibility_enabled()) {
uint64_t time = OS::get_singleton()->get_ticks_msec();
if (!accessibility_force_update) {
if (time - accessibility_last_update < 1000 / accessibility_upd_per_sec) {
return;
}
}
accessibility_force_update = false;
accessibility_last_update = time;
// Push update to the accessibility driver.
DisplayServer::get_singleton()->accessibility_update_if_active(callable_mp(this, &SceneTree::_process_accessibility_changes));
}
}
void SceneTree::_flush_ugc() {
ugc_locked = true;
@ -526,7 +631,9 @@ bool SceneTree::physics_process(double p_time) {
emit_signal(SNAME("physics_frame"));
#if !defined(PHYSICS_2D_DISABLED) || !defined(PHYSICS_3D_DISABLED)
call_group(SNAME("_picking_viewports"), SNAME("_process_picking"));
#endif // !defined(PHYSICS_2D_DISABLED) || !defined(PHYSICS_3D_DISABLED)
_process(true);
@ -540,6 +647,7 @@ bool SceneTree::physics_process(double p_time) {
// This should happen last because any processing that deletes something beforehand might expect the object to be removed in the same frame.
_flush_delete_queue();
_call_idle_callbacks();
return _quit;
@ -586,7 +694,7 @@ bool SceneTree::process(double p_time) {
MessageQueue::get_singleton()->flush(); //small little hack
flush_transform_notifications(); //transforms after world update, to avoid unnecessary enter/exit notifications
if (unlikely(pending_new_scene)) {
if (unlikely(pending_new_scene_id.is_valid())) {
_flush_scene_change();
}
@ -598,6 +706,8 @@ bool SceneTree::process(double p_time) {
// This should happen last because any processing that deletes something beforehand might expect the object to be removed in the same frame.
_flush_delete_queue();
_flush_accessibility_changes();
_call_idle_callbacks();
#ifdef TOOLS_ENABLED
@ -769,9 +879,7 @@ void SceneTree::_main_window_focus_in() {
void SceneTree::_notification(int p_notification) {
switch (p_notification) {
case NOTIFICATION_TRANSLATION_CHANGED: {
if (!Engine::get_singleton()->is_editor_hint()) {
get_root()->propagate_notification(p_notification);
}
get_root()->propagate_notification(p_notification);
} break;
case NOTIFICATION_OS_MEMORY_WARNING:
@ -972,10 +1080,12 @@ void SceneTree::set_pause(bool p_enabled) {
paused = p_enabled;
#ifndef _3D_DISABLED
#ifndef PHYSICS_3D_DISABLED
PhysicsServer3D::get_singleton()->set_active(!p_enabled);
#endif // _3D_DISABLED
#endif // PHYSICS_3D_DISABLED
#ifndef PHYSICS_2D_DISABLED
PhysicsServer2D::get_singleton()->set_active(!p_enabled);
#endif // PHYSICS_2D_DISABLED
if (get_root()) {
get_root()->_propagate_pause_notification(p_enabled);
}
@ -996,10 +1106,12 @@ void SceneTree::set_suspend(bool p_enabled) {
Engine::get_singleton()->set_freeze_time_scale(p_enabled);
#ifndef _3D_DISABLED
#ifndef PHYSICS_3D_DISABLED
PhysicsServer3D::get_singleton()->set_active(!p_enabled && !paused);
#endif // _3D_DISABLED
#endif // PHYSICS_3D_DISABLED
#ifndef PHYSICS_2D_DISABLED
PhysicsServer2D::get_singleton()->set_active(!p_enabled && !paused);
#endif // PHYSICS_2D_DISABLED
if (get_root()) {
get_root()->_propagate_suspend_notification(p_enabled);
}
@ -1340,7 +1452,7 @@ void SceneTree::_call_input_pause(const StringName &p_group, CallInputType p_cal
if (p_viewport->is_input_handled()) {
break;
}
Node *n = Object::cast_to<Node>(ObjectDB::get_instance(id));
Node *n = ObjectDB::get_instance<Node>(id);
if (n) {
n->_call_shortcut_input(p_input);
}
@ -1508,15 +1620,33 @@ Node *SceneTree::get_current_scene() const {
}
void SceneTree::_flush_scene_change() {
if (prev_scene) {
memdelete(prev_scene);
prev_scene = nullptr;
if (prev_scene_id.is_valid()) {
// Might have already been freed externally.
Node *prev_scene = ObjectDB::get_instance<Node>(prev_scene_id);
if (prev_scene) {
memdelete(prev_scene);
}
prev_scene_id = ObjectID();
}
DEV_ASSERT(pending_new_scene_id.is_valid());
Node *pending_new_scene = ObjectDB::get_instance<Node>(pending_new_scene_id);
if (pending_new_scene) {
// Ensure correct state before `add_child` (might enqueue subsequent scene change).
current_scene = pending_new_scene;
pending_new_scene_id = ObjectID();
root->add_child(pending_new_scene);
// Update display for cursor instantly.
root->update_mouse_cursor_state();
// Only on successful scene change.
emit_signal(SNAME("scene_changed"));
} else {
current_scene = nullptr;
pending_new_scene_id = ObjectID();
ERR_PRINT("Scene instance has been freed before becoming the current scene. No current scene is set.");
}
current_scene = pending_new_scene;
root->add_child(pending_new_scene);
pending_new_scene = nullptr;
// Update display for cursor instantly.
root->update_mouse_cursor_state();
}
Error SceneTree::change_scene_to_file(const String &p_path) {
@ -1536,21 +1666,23 @@ Error SceneTree::change_scene_to_packed(const Ref<PackedScene> &p_scene) {
ERR_FAIL_NULL_V(new_scene, ERR_CANT_CREATE);
// If called again while a change is pending.
if (pending_new_scene) {
queue_delete(pending_new_scene);
pending_new_scene = nullptr;
if (pending_new_scene_id.is_valid()) {
Node *pending_new_scene = ObjectDB::get_instance<Node>(pending_new_scene_id);
if (pending_new_scene) {
queue_delete(pending_new_scene);
}
pending_new_scene_id = ObjectID();
}
prev_scene = current_scene;
if (current_scene) {
prev_scene_id = current_scene->get_instance_id();
// Let as many side effects as possible happen or be queued now,
// so they are run before the scene is actually deleted.
root->remove_child(current_scene);
}
DEV_ASSERT(!current_scene);
pending_new_scene = new_scene;
pending_new_scene_id = new_scene->get_instance_id();
return OK;
}
@ -1701,6 +1833,9 @@ void SceneTree::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_root"), &SceneTree::get_root);
ClassDB::bind_method(D_METHOD("has_group", "name"), &SceneTree::has_group);
ClassDB::bind_method(D_METHOD("is_accessibility_enabled"), &SceneTree::is_accessibility_enabled);
ClassDB::bind_method(D_METHOD("is_accessibility_supported"), &SceneTree::is_accessibility_supported);
ClassDB::bind_method(D_METHOD("is_auto_accept_quit"), &SceneTree::is_auto_accept_quit);
ClassDB::bind_method(D_METHOD("set_auto_accept_quit", "enabled"), &SceneTree::set_auto_accept_quit);
ClassDB::bind_method(D_METHOD("is_quit_on_go_back"), &SceneTree::is_quit_on_go_back);
@ -1784,6 +1919,7 @@ void SceneTree::_bind_methods() {
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "physics_interpolation"), "set_physics_interpolation_enabled", "is_physics_interpolation_enabled");
ADD_SIGNAL(MethodInfo("tree_changed"));
ADD_SIGNAL(MethodInfo("scene_changed"));
ADD_SIGNAL(MethodInfo("tree_process_mode_changed")); //editor only signal, but due to API hash it can't be removed in run-time
ADD_SIGNAL(MethodInfo("node_added", PropertyInfo(Variant::OBJECT, "node", PROPERTY_HINT_RESOURCE_TYPE, "Node")));
ADD_SIGNAL(MethodInfo("node_removed", PropertyInfo(Variant::OBJECT, "node", PROPERTY_HINT_RESOURCE_TYPE, "Node")));
@ -1847,6 +1983,7 @@ SceneTree::SceneTree() {
debug_paths_color = GLOBAL_DEF("debug/shapes/paths/geometry_color", Color(0.1, 1.0, 0.7, 0.4));
debug_paths_width = GLOBAL_DEF(PropertyInfo(Variant::FLOAT, "debug/shapes/paths/geometry_width", PROPERTY_HINT_RANGE, "0.01,10,0.001,or_greater"), 2.0);
collision_debug_contacts = GLOBAL_DEF(PropertyInfo(Variant::INT, "debug/shapes/collision/max_contacts_displayed", PROPERTY_HINT_RANGE, "0,20000,1"), 10000);
accessibility_upd_per_sec = GLOBAL_GET(SNAME("accessibility/general/updates_per_second"));
GLOBAL_DEF("debug/shapes/collision/draw_2d_outlines", true);
@ -1992,7 +2129,9 @@ SceneTree::SceneTree() {
}
#endif // _3D_DISABLED
#if !defined(PHYSICS_2D_DISABLED) || !defined(PHYSICS_3D_DISABLED)
root->set_physics_object_picking(GLOBAL_DEF("physics/common/enable_object_picking", true));
#endif // !defined(PHYSICS_2D_DISABLED) || !defined(PHYSICS_3D_DISABLED)
root->connect("close_requested", callable_mp(this, &SceneTree::_main_window_close));
root->connect("go_back_requested", callable_mp(this, &SceneTree::_main_window_go_back));
@ -2006,13 +2145,19 @@ SceneTree::SceneTree() {
}
SceneTree::~SceneTree() {
if (prev_scene) {
memdelete(prev_scene);
prev_scene = nullptr;
if (prev_scene_id.is_valid()) {
Node *prev_scene = ObjectDB::get_instance<Node>(prev_scene_id);
if (prev_scene) {
memdelete(prev_scene);
}
prev_scene_id = ObjectID();
}
if (pending_new_scene) {
memdelete(pending_new_scene);
pending_new_scene = nullptr;
if (pending_new_scene_id.is_valid()) {
Node *pending_new_scene = ObjectDB::get_instance<Node>(pending_new_scene_id);
if (pending_new_scene) {
memdelete(pending_new_scene);
}
pending_new_scene_id = ObjectID();
}
if (root) {
root->_set_tree(nullptr);