Skip to content

Commit b310e5e

Browse files
committed
Merge pull request godotengine#92842 from mihe/multi-node-keying
Allow keying properties when selecting multiple nodes
2 parents 4c6bac1 + 351f454 commit b310e5e

4 files changed

+47
-109
lines changed

editor/animation_track_editor.cpp

+35-97
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,7 @@
4141
#include "editor/gui/editor_spin_slider.h"
4242
#include "editor/gui/scene_tree_editor.h"
4343
#include "editor/inspector_dock.h"
44+
#include "editor/multi_node_edit.h"
4445
#include "editor/plugins/animation_player_editor_plugin.h"
4546
#include "editor/themes/editor_scale.h"
4647
#include "scene/3d/mesh_instance_3d.h"
@@ -3661,7 +3662,7 @@ void AnimationTrackEditor::update_keying() {
36613662
EditorSelectionHistory *editor_history = EditorNode::get_singleton()->get_editor_selection_history();
36623663
if (is_visible_in_tree() && animation.is_valid() && editor_history->get_path_size() > 0) {
36633664
Object *obj = ObjectDB::get_instance(editor_history->get_path_object(0));
3664-
keying_enabled = Object::cast_to<Node>(obj) != nullptr;
3665+
keying_enabled = Object::cast_to<Node>(obj) != nullptr || Object::cast_to<MultiNodeEdit>(obj) != nullptr;
36653666
}
36663667

36673668
if (keying_enabled == keying) {
@@ -4078,19 +4079,20 @@ void AnimationTrackEditor::_insert_animation_key(NodePath p_path, const Variant
40784079
_query_insert(id);
40794080
}
40804081

4081-
void AnimationTrackEditor::insert_node_value_key(Node *p_node, const String &p_property, const Variant &p_value, bool p_only_if_exists) {
4082+
void AnimationTrackEditor::insert_node_value_key(Node *p_node, const String &p_property, bool p_only_if_exists, bool p_advance) {
40824083
ERR_FAIL_NULL(root);
40834084

40844085
// Let's build a node path.
4085-
Node *node = p_node;
4086-
String path = root->get_path_to(node, true);
4086+
String path = root->get_path_to(p_node, true);
4087+
4088+
Variant value = p_node->get(p_property);
40874089

4088-
if (Object::cast_to<AnimationPlayer>(node) && p_property == "current_animation") {
4089-
if (node == AnimationPlayerEditor::get_singleton()->get_player()) {
4090+
if (Object::cast_to<AnimationPlayer>(p_node) && p_property == "current_animation") {
4091+
if (p_node == AnimationPlayerEditor::get_singleton()->get_player()) {
40904092
EditorNode::get_singleton()->show_warning(TTR("AnimationPlayer can't animate itself, only other players."));
40914093
return;
40924094
}
4093-
_insert_animation_key(path, p_value);
4095+
_insert_animation_key(path, value);
40944096
return;
40954097
}
40964098

@@ -4118,26 +4120,26 @@ void AnimationTrackEditor::insert_node_value_key(Node *p_node, const String &p_p
41184120
InsertData id;
41194121
id.path = np;
41204122
id.track_idx = i;
4121-
id.value = p_value;
4123+
id.value = value;
41224124
id.type = Animation::TYPE_VALUE;
41234125
// TRANSLATORS: This describes the target of new animation track, will be inserted into another string.
41244126
id.query = vformat(TTR("property '%s'"), p_property);
4125-
id.advance = false;
4127+
id.advance = p_advance;
41264128
// Dialog insert.
41274129
_query_insert(id);
41284130
inserted = true;
41294131
} else if (animation->track_get_type(i) == Animation::TYPE_BEZIER) {
4130-
Variant value;
4132+
Variant actual_value;
41314133
String track_path = animation->track_get_path(i);
41324134
if (track_path == np) {
4133-
value = p_value; // All good.
4135+
actual_value = value; // All good.
41344136
} else {
41354137
int sep = track_path.rfind(":");
41364138
if (sep != -1) {
41374139
String base_path = track_path.substr(0, sep);
41384140
if (base_path == np) {
41394141
String value_name = track_path.substr(sep + 1);
4140-
value = p_value.get(value_name);
4142+
actual_value = value.get(value_name);
41414143
} else {
41424144
continue;
41434145
}
@@ -4149,10 +4151,10 @@ void AnimationTrackEditor::insert_node_value_key(Node *p_node, const String &p_p
41494151
InsertData id;
41504152
id.path = animation->track_get_path(i);
41514153
id.track_idx = i;
4152-
id.value = value;
4154+
id.value = actual_value;
41534155
id.type = Animation::TYPE_BEZIER;
41544156
id.query = vformat(TTR("property '%s'"), p_property);
4155-
id.advance = false;
4157+
id.advance = p_advance;
41564158
// Dialog insert.
41574159
_query_insert(id);
41584160
inserted = true;
@@ -4165,105 +4167,41 @@ void AnimationTrackEditor::insert_node_value_key(Node *p_node, const String &p_p
41654167
InsertData id;
41664168
id.path = np;
41674169
id.track_idx = -1;
4168-
id.value = p_value;
4170+
id.value = value;
41694171
id.type = Animation::TYPE_VALUE;
41704172
id.query = vformat(TTR("property '%s'"), p_property);
4171-
id.advance = false;
4173+
id.advance = p_advance;
41724174
// Dialog insert.
41734175
_query_insert(id);
41744176
}
41754177

4176-
void AnimationTrackEditor::insert_value_key(const String &p_property, const Variant &p_value, bool p_advance) {
4178+
void AnimationTrackEditor::insert_value_key(const String &p_property, bool p_advance) {
41774179
EditorSelectionHistory *history = EditorNode::get_singleton()->get_editor_selection_history();
41784180

41794181
ERR_FAIL_NULL(root);
41804182
ERR_FAIL_COND(history->get_path_size() == 0);
41814183
Object *obj = ObjectDB::get_instance(history->get_path_object(0));
4182-
ERR_FAIL_NULL(Object::cast_to<Node>(obj));
4183-
4184-
// Let's build a node path.
4185-
Node *node = Object::cast_to<Node>(obj);
4186-
String path = root->get_path_to(node, true);
4187-
4188-
if (Object::cast_to<AnimationPlayer>(node) && p_property == "current_animation") {
4189-
if (node == AnimationPlayerEditor::get_singleton()->get_player()) {
4190-
EditorNode::get_singleton()->show_warning(TTR("AnimationPlayer can't animate itself, only other players."));
4191-
return;
4192-
}
4193-
_insert_animation_key(path, p_value);
4194-
return;
4195-
}
4196-
4197-
for (int i = 1; i < history->get_path_size(); i++) {
4198-
String prop = history->get_path_property(i);
4199-
ERR_FAIL_COND(prop.is_empty());
4200-
path += ":" + prop;
4201-
}
4202-
4203-
path += ":" + p_property;
42044184

4205-
NodePath np = path;
4185+
Ref<MultiNodeEdit> multi_node_edit(obj);
4186+
if (multi_node_edit.is_valid()) {
4187+
Node *edited_scene = EditorNode::get_singleton()->get_edited_scene();
4188+
ERR_FAIL_NULL(edited_scene);
42064189

4207-
// Locate track.
4208-
4209-
bool inserted = false;
4190+
make_insert_queue();
42104191

4211-
make_insert_queue();
4212-
for (int i = 0; i < animation->get_track_count(); i++) {
4213-
if (animation->track_get_type(i) == Animation::TYPE_VALUE) {
4214-
if (animation->track_get_path(i) != np) {
4215-
continue;
4216-
}
4217-
4218-
InsertData id;
4219-
id.path = np;
4220-
id.track_idx = i;
4221-
id.value = p_value;
4222-
id.type = Animation::TYPE_VALUE;
4223-
id.query = vformat(TTR("property '%s'"), p_property);
4224-
id.advance = p_advance;
4225-
// Dialog insert.
4226-
_query_insert(id);
4227-
inserted = true;
4228-
} else if (animation->track_get_type(i) == Animation::TYPE_BEZIER) {
4229-
Variant value;
4230-
if (animation->track_get_path(i) == np) {
4231-
value = p_value; // All good.
4232-
} else {
4233-
String tpath = animation->track_get_path(i);
4234-
int index = tpath.rfind(":");
4235-
if (NodePath(tpath.substr(0, index + 1)) == np) {
4236-
String subindex = tpath.substr(index + 1, tpath.length() - index);
4237-
value = p_value.get(subindex);
4238-
} else {
4239-
continue;
4240-
}
4241-
}
4242-
4243-
InsertData id;
4244-
id.path = animation->track_get_path(i);
4245-
id.track_idx = i;
4246-
id.value = value;
4247-
id.type = Animation::TYPE_BEZIER;
4248-
id.query = vformat(TTR("property '%s'"), p_property);
4249-
id.advance = p_advance;
4250-
// Dialog insert.
4251-
_query_insert(id);
4252-
inserted = true;
4192+
for (int i = 0; i < multi_node_edit->get_node_count(); ++i) {
4193+
Node *node = edited_scene->get_node(multi_node_edit->get_node(i));
4194+
insert_node_value_key(node, p_property, false, p_advance);
42534195
}
4254-
}
4255-
commit_insert_queue();
42564196

4257-
if (!inserted) {
4258-
InsertData id;
4259-
id.path = np;
4260-
id.track_idx = -1;
4261-
id.value = p_value;
4262-
id.type = Animation::TYPE_VALUE;
4263-
id.query = vformat(TTR("property '%s'"), p_property);
4264-
id.advance = p_advance;
4265-
// Dialog insert.
4266-
_query_insert(id);
4197+
commit_insert_queue();
4198+
} else {
4199+
Node *node = Object::cast_to<Node>(obj);
4200+
ERR_FAIL_NULL(node);
4201+
4202+
make_insert_queue();
4203+
insert_node_value_key(node, p_property, false, p_advance);
4204+
commit_insert_queue();
42674205
}
42684206
}
42694207

editor/animation_track_editor.h

+2-2
Original file line numberDiff line numberDiff line change
@@ -713,8 +713,8 @@ class AnimationTrackEditor : public VBoxContainer {
713713
void cleanup();
714714

715715
void set_anim_pos(float p_pos);
716-
void insert_node_value_key(Node *p_node, const String &p_property, const Variant &p_value, bool p_only_if_exists = false);
717-
void insert_value_key(const String &p_property, const Variant &p_value, bool p_advance);
716+
void insert_node_value_key(Node *p_node, const String &p_property, bool p_only_if_exists = false, bool p_advance = false);
717+
void insert_value_key(const String &p_property, bool p_advance);
718718
void insert_transform_key(Node3D *p_node, const String &p_sub, const Animation::TrackType p_type, const Variant &p_value);
719719
bool has_track(Node3D *p_node, const String &p_sub, const Animation::TrackType p_type);
720720
void make_insert_queue();

editor/plugins/animation_player_editor_plugin.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -2165,7 +2165,7 @@ void AnimationPlayerEditorPlugin::_property_keyed(const String &p_keyed, const V
21652165
return;
21662166
}
21672167
te->_clear_selection();
2168-
te->insert_value_key(p_keyed, p_value, p_advance);
2168+
te->insert_value_key(p_keyed, p_advance);
21692169
}
21702170

21712171
void AnimationPlayerEditorPlugin::_transform_key_request(Object *sp, const String &p_sub, const Transform3D &p_key) {

editor/plugins/canvas_item_editor_plugin.cpp

+9-9
Original file line numberDiff line numberDiff line change
@@ -4331,13 +4331,13 @@ void CanvasItemEditor::_insert_animation_keys(bool p_location, bool p_rotation,
43314331
Node2D *n2d = Object::cast_to<Node2D>(ci);
43324332

43334333
if (key_pos && p_location) {
4334-
te->insert_node_value_key(n2d, "position", n2d->get_position(), p_on_existing);
4334+
te->insert_node_value_key(n2d, "position", p_on_existing);
43354335
}
43364336
if (key_rot && p_rotation) {
4337-
te->insert_node_value_key(n2d, "rotation", n2d->get_rotation(), p_on_existing);
4337+
te->insert_node_value_key(n2d, "rotation", p_on_existing);
43384338
}
43394339
if (key_scale && p_scale) {
4340-
te->insert_node_value_key(n2d, "scale", n2d->get_scale(), p_on_existing);
4340+
te->insert_node_value_key(n2d, "scale", p_on_existing);
43414341
}
43424342

43434343
if (n2d->has_meta("_edit_bone_") && n2d->get_parent_item()) {
@@ -4363,13 +4363,13 @@ void CanvasItemEditor::_insert_animation_keys(bool p_location, bool p_rotation,
43634363
if (has_chain && ik_chain.size()) {
43644364
for (Node2D *&F : ik_chain) {
43654365
if (key_pos) {
4366-
te->insert_node_value_key(F, "position", F->get_position(), p_on_existing);
4366+
te->insert_node_value_key(F, "position", p_on_existing);
43674367
}
43684368
if (key_rot) {
4369-
te->insert_node_value_key(F, "rotation", F->get_rotation(), p_on_existing);
4369+
te->insert_node_value_key(F, "rotation", p_on_existing);
43704370
}
43714371
if (key_scale) {
4372-
te->insert_node_value_key(F, "scale", F->get_scale(), p_on_existing);
4372+
te->insert_node_value_key(F, "scale", p_on_existing);
43734373
}
43744374
}
43754375
}
@@ -4379,13 +4379,13 @@ void CanvasItemEditor::_insert_animation_keys(bool p_location, bool p_rotation,
43794379
Control *ctrl = Object::cast_to<Control>(ci);
43804380

43814381
if (key_pos) {
4382-
te->insert_node_value_key(ctrl, "position", ctrl->get_position(), p_on_existing);
4382+
te->insert_node_value_key(ctrl, "position", p_on_existing);
43834383
}
43844384
if (key_rot) {
4385-
te->insert_node_value_key(ctrl, "rotation", ctrl->get_rotation(), p_on_existing);
4385+
te->insert_node_value_key(ctrl, "rotation", p_on_existing);
43864386
}
43874387
if (key_scale) {
4388-
te->insert_node_value_key(ctrl, "size", ctrl->get_size(), p_on_existing);
4388+
te->insert_node_value_key(ctrl, "size", p_on_existing);
43894389
}
43904390
}
43914391
}

0 commit comments

Comments
 (0)