mirror of
https://github.com/godotengine/godot.git
synced 2025-10-19 16:03:29 +00:00
Node3D
and CanvasItem
children change to LocalVector
This commit is contained in:
parent
46c495ca21
commit
af2b9be356
4 changed files with 91 additions and 33 deletions
|
@ -108,12 +108,15 @@ void Node3D::_propagate_transform_changed(Node3D *p_origin) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Node3D *&E : data.children) {
|
for (uint32_t n = 0; n < data.node3d_children.size(); n++) {
|
||||||
if (E->data.top_level) {
|
Node3D *s = data.node3d_children[n];
|
||||||
continue; //don't propagate to a top_level
|
|
||||||
|
// Don't propagate to a toplevel.
|
||||||
|
if (!s->data.top_level) {
|
||||||
|
s->_propagate_transform_changed(p_origin);
|
||||||
}
|
}
|
||||||
E->_propagate_transform_changed(p_origin);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef TOOLS_ENABLED
|
#ifdef TOOLS_ENABLED
|
||||||
if ((!data.gizmos.is_empty() || data.notify_transform) && !data.ignore_notification && !xform_change.in_list()) {
|
if ((!data.gizmos.is_empty() || data.notify_transform) && !data.ignore_notification && !xform_change.in_list()) {
|
||||||
#else
|
#else
|
||||||
|
@ -148,9 +151,11 @@ void Node3D::_notification(int p_what) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (data.parent) {
|
if (data.parent) {
|
||||||
data.C = data.parent->data.children.push_back(this);
|
data.index_in_parent = data.parent->data.node3d_children.size();
|
||||||
} else {
|
data.parent->data.node3d_children.push_back(this);
|
||||||
data.C = nullptr;
|
} else if (data.index_in_parent != UINT32_MAX) {
|
||||||
|
data.index_in_parent = UINT32_MAX;
|
||||||
|
ERR_PRINT("Node3D ENTER_TREE detected without EXIT_TREE, recovering.");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (data.top_level && !Engine::get_singleton()->is_editor_hint()) {
|
if (data.top_level && !Engine::get_singleton()->is_editor_hint()) {
|
||||||
|
@ -202,11 +207,27 @@ void Node3D::_notification(int p_what) {
|
||||||
if (xform_change.in_list()) {
|
if (xform_change.in_list()) {
|
||||||
get_tree()->xform_change_list.remove(&xform_change);
|
get_tree()->xform_change_list.remove(&xform_change);
|
||||||
}
|
}
|
||||||
if (data.C) {
|
|
||||||
data.parent->data.children.erase(data.C);
|
if (data.parent) {
|
||||||
|
if (data.index_in_parent != UINT32_MAX) {
|
||||||
|
// Aliases
|
||||||
|
uint32_t c = data.index_in_parent;
|
||||||
|
LocalVector<Node3D *> &parent_children = data.parent->data.node3d_children;
|
||||||
|
|
||||||
|
parent_children.remove_at_unordered(c);
|
||||||
|
|
||||||
|
// After unordered remove, we need to inform the moved child
|
||||||
|
// what their new id is in the parent children list.
|
||||||
|
if (parent_children.size() > c) {
|
||||||
|
parent_children[c]->data.index_in_parent = c;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
ERR_PRINT("Node3D index_in_parent unset at EXIT_TREE.");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
data.index_in_parent = UINT32_MAX;
|
||||||
|
|
||||||
data.parent = nullptr;
|
data.parent = nullptr;
|
||||||
data.C = nullptr;
|
|
||||||
_update_visibility_parent(true);
|
_update_visibility_parent(true);
|
||||||
_disable_client_physics_interpolation();
|
_disable_client_physics_interpolation();
|
||||||
} break;
|
} break;
|
||||||
|
@ -1063,11 +1084,12 @@ void Node3D::_propagate_visibility_changed() {
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
for (Node3D *c : data.children) {
|
for (uint32_t n = 0; n < data.node3d_children.size(); n++) {
|
||||||
if (!c || !c->data.visible) {
|
Node3D *s = data.node3d_children[n];
|
||||||
continue;
|
|
||||||
|
if (s->data.visible) {
|
||||||
|
s->_propagate_visibility_changed();
|
||||||
}
|
}
|
||||||
c->_propagate_visibility_changed();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1312,7 +1334,7 @@ void Node3D::_update_visibility_parent(bool p_update_root) {
|
||||||
RS::get_singleton()->instance_set_visibility_parent(vi->get_instance(), data.visibility_parent);
|
RS::get_singleton()->instance_set_visibility_parent(vi->get_instance(), data.visibility_parent);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Node3D *c : data.children) {
|
for (Node3D *c : data.node3d_children) {
|
||||||
c->_update_visibility_parent(false);
|
c->_update_visibility_parent(false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -153,8 +153,12 @@ private:
|
||||||
RID visibility_parent;
|
RID visibility_parent;
|
||||||
|
|
||||||
Node3D *parent = nullptr;
|
Node3D *parent = nullptr;
|
||||||
List<Node3D *> children;
|
|
||||||
List<Node3D *>::Element *C = nullptr;
|
// An unordered vector of `Spatial` children only.
|
||||||
|
// This is a subset of the `Node::children`, purely
|
||||||
|
// an optimization for faster traversal.
|
||||||
|
LocalVector<Node3D *> node3d_children;
|
||||||
|
uint32_t index_in_parent = UINT32_MAX;
|
||||||
|
|
||||||
ClientPhysicsInterpolationData *client_physics_interpolation_data = nullptr;
|
ClientPhysicsInterpolationData *client_physics_interpolation_data = nullptr;
|
||||||
|
|
||||||
|
|
|
@ -317,8 +317,15 @@ void CanvasItem::_notification(int p_what) {
|
||||||
|
|
||||||
if (ci) {
|
if (ci) {
|
||||||
parent_visible_in_tree = ci->is_visible_in_tree();
|
parent_visible_in_tree = ci->is_visible_in_tree();
|
||||||
C = ci->children_items.push_back(this);
|
|
||||||
|
data.index_in_parent = ci->data.canvas_item_children.size();
|
||||||
|
ci->data.canvas_item_children.push_back(this);
|
||||||
} else {
|
} else {
|
||||||
|
if (data.index_in_parent != UINT32_MAX) {
|
||||||
|
data.index_in_parent = UINT32_MAX;
|
||||||
|
ERR_PRINT("CanvasItem ENTER_TREE detected without EXIT_TREE, recovering.");
|
||||||
|
}
|
||||||
|
|
||||||
CanvasLayer *cl = Object::cast_to<CanvasLayer>(parent);
|
CanvasLayer *cl = Object::cast_to<CanvasLayer>(parent);
|
||||||
|
|
||||||
if (cl) {
|
if (cl) {
|
||||||
|
@ -388,10 +395,27 @@ void CanvasItem::_notification(int p_what) {
|
||||||
get_tree()->xform_change_list.remove(&xform_change);
|
get_tree()->xform_change_list.remove(&xform_change);
|
||||||
}
|
}
|
||||||
_exit_canvas();
|
_exit_canvas();
|
||||||
if (C) {
|
|
||||||
Object::cast_to<CanvasItem>(get_parent())->children_items.erase(C);
|
CanvasItem *parent = Object::cast_to<CanvasItem>(get_parent());
|
||||||
C = nullptr;
|
if (parent) {
|
||||||
|
if (data.index_in_parent != UINT32_MAX) {
|
||||||
|
// Aliases
|
||||||
|
uint32_t c = data.index_in_parent;
|
||||||
|
LocalVector<CanvasItem *> &parent_children = parent->data.canvas_item_children;
|
||||||
|
|
||||||
|
parent_children.remove_at_unordered(c);
|
||||||
|
|
||||||
|
// After unordered remove, we need to inform the moved child
|
||||||
|
// what their new id is in the parent children list.
|
||||||
|
if (parent_children.size() > c) {
|
||||||
|
parent_children[c]->data.index_in_parent = c;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
ERR_PRINT("CanvasItem index_in_parent unset at EXIT_TREE.");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
data.index_in_parent = UINT32_MAX;
|
||||||
|
|
||||||
if (window) {
|
if (window) {
|
||||||
window->disconnect(SceneStringName(visibility_changed), callable_mp(this, &CanvasItem::_window_visibility_changed));
|
window->disconnect(SceneStringName(visibility_changed), callable_mp(this, &CanvasItem::_window_visibility_changed));
|
||||||
window = nullptr;
|
window = nullptr;
|
||||||
|
@ -1056,11 +1080,11 @@ void CanvasItem::_notify_transform(CanvasItem *p_node) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for (CanvasItem *ci : p_node->children_items) {
|
for (uint32_t n = 0; n < p_node->data.canvas_item_children.size(); n++) {
|
||||||
if (ci->top_level) {
|
CanvasItem *ci = p_node->data.canvas_item_children[n];
|
||||||
continue;
|
if (!ci->top_level) {
|
||||||
|
_notify_transform(ci);
|
||||||
}
|
}
|
||||||
_notify_transform(ci);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1611,9 +1635,11 @@ void CanvasItem::_update_texture_filter_changed(bool p_propagate) {
|
||||||
_update_self_texture_filter(texture_filter_cache);
|
_update_self_texture_filter(texture_filter_cache);
|
||||||
|
|
||||||
if (p_propagate) {
|
if (p_propagate) {
|
||||||
for (CanvasItem *E : children_items) {
|
for (uint32_t n = 0; n < data.canvas_item_children.size(); n++) {
|
||||||
if (!E->top_level && E->texture_filter == TEXTURE_FILTER_PARENT_NODE) {
|
CanvasItem *ci = data.canvas_item_children[n];
|
||||||
E->_update_texture_filter_changed(true);
|
|
||||||
|
if (!ci->top_level && ci->texture_filter == TEXTURE_FILTER_PARENT_NODE) {
|
||||||
|
ci->_update_texture_filter_changed(true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1665,9 +1691,10 @@ void CanvasItem::_update_texture_repeat_changed(bool p_propagate) {
|
||||||
_update_self_texture_repeat(texture_repeat_cache);
|
_update_self_texture_repeat(texture_repeat_cache);
|
||||||
|
|
||||||
if (p_propagate) {
|
if (p_propagate) {
|
||||||
for (CanvasItem *E : children_items) {
|
for (uint32_t n = 0; n < data.canvas_item_children.size(); n++) {
|
||||||
if (!E->top_level && E->texture_repeat == TEXTURE_REPEAT_PARENT_NODE) {
|
CanvasItem *ci = data.canvas_item_children[n];
|
||||||
E->_update_texture_repeat_changed(true);
|
if (!ci->top_level && ci->texture_repeat == TEXTURE_REPEAT_PARENT_NODE) {
|
||||||
|
ci->_update_texture_repeat_changed(true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -83,8 +83,13 @@ private:
|
||||||
Color modulate = Color(1, 1, 1, 1);
|
Color modulate = Color(1, 1, 1, 1);
|
||||||
Color self_modulate = Color(1, 1, 1, 1);
|
Color self_modulate = Color(1, 1, 1, 1);
|
||||||
|
|
||||||
List<CanvasItem *> children_items;
|
struct Data {
|
||||||
List<CanvasItem *>::Element *C = nullptr;
|
// An unordered vector of `CanvasItem` children only.
|
||||||
|
// This is a subset of the `Node::children`, purely
|
||||||
|
// an optimization for faster traversal.
|
||||||
|
LocalVector<CanvasItem *> canvas_item_children;
|
||||||
|
uint32_t index_in_parent = UINT32_MAX;
|
||||||
|
} data;
|
||||||
|
|
||||||
int light_mask = 1;
|
int light_mask = 1;
|
||||||
uint32_t visibility_layer = 1;
|
uint32_t visibility_layer = 1;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue