diff options
author | Rémi Verschelde <rverschelde@gmail.com> | 2024-09-17 09:17:35 +0200 |
---|---|---|
committer | Rémi Verschelde <rverschelde@gmail.com> | 2024-09-17 09:17:35 +0200 |
commit | e72a70de8e7fc64fae7859fe30fffa9732da5602 (patch) | |
tree | 96dba1d697bca625d804b073e2d21dba582ecec0 /scene/3d | |
parent | 13064c4ac848d7d8207a8a8b0d1eb02db91f9e62 (diff) | |
parent | 0468bea899fe4806d8358c1cab078f700ab84d22 (diff) | |
download | redot-engine-e72a70de8e7fc64fae7859fe30fffa9732da5602.tar.gz |
Merge pull request #87150 from demolke/bones
Add per-bone meta to Skeleton3D
Diffstat (limited to 'scene/3d')
-rw-r--r-- | scene/3d/skeleton_3d.cpp | 65 | ||||
-rw-r--r-- | scene/3d/skeleton_3d.h | 9 |
2 files changed, 74 insertions, 0 deletions
diff --git a/scene/3d/skeleton_3d.cpp b/scene/3d/skeleton_3d.cpp index c6ece84cdd..db9c4db30d 100644 --- a/scene/3d/skeleton_3d.cpp +++ b/scene/3d/skeleton_3d.cpp @@ -103,6 +103,8 @@ bool Skeleton3D::_set(const StringName &p_path, const Variant &p_value) { set_bone_pose_rotation(which, p_value); } else if (what == "scale") { set_bone_pose_scale(which, p_value); + } else if (what == "bone_meta") { + set_bone_meta(which, path.get_slicec('/', 3), p_value); #ifndef DISABLE_DEPRECATED } else if (what == "pose" || what == "bound_children") { // Kept for compatibility from 3.x to 4.x. @@ -170,6 +172,8 @@ bool Skeleton3D::_get(const StringName &p_path, Variant &r_ret) const { r_ret = get_bone_pose_rotation(which); } else if (what == "scale") { r_ret = get_bone_pose_scale(which); + } else if (what == "bone_meta") { + r_ret = get_bone_meta(which, path.get_slicec('/', 3)); } else { return false; } @@ -187,6 +191,11 @@ void Skeleton3D::_get_property_list(List<PropertyInfo> *p_list) const { p_list->push_back(PropertyInfo(Variant::VECTOR3, prep + PNAME("position"), PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NO_EDITOR)); p_list->push_back(PropertyInfo(Variant::QUATERNION, prep + PNAME("rotation"), PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NO_EDITOR)); p_list->push_back(PropertyInfo(Variant::VECTOR3, prep + PNAME("scale"), PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NO_EDITOR)); + + for (const KeyValue<StringName, Variant> &K : bones[i].metadata) { + PropertyInfo pi = PropertyInfo(bones[i].metadata[K.key].get_type(), prep + PNAME("bone_meta/") + K.key, PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NO_EDITOR); + p_list->push_back(pi); + } } for (PropertyInfo &E : *p_list) { @@ -531,6 +540,57 @@ void Skeleton3D::set_bone_name(int p_bone, const String &p_name) { version++; } +Variant Skeleton3D::get_bone_meta(int p_bone, const StringName &p_key) const { + const int bone_size = bones.size(); + ERR_FAIL_INDEX_V(p_bone, bone_size, Variant()); + + if (!bones[p_bone].metadata.has(p_key)) { + return Variant(); + } + return bones[p_bone].metadata[p_key]; +} + +TypedArray<StringName> Skeleton3D::_get_bone_meta_list_bind(int p_bone) const { + const int bone_size = bones.size(); + ERR_FAIL_INDEX_V(p_bone, bone_size, TypedArray<StringName>()); + + TypedArray<StringName> _metaret; + for (const KeyValue<StringName, Variant> &K : bones[p_bone].metadata) { + _metaret.push_back(K.key); + } + return _metaret; +} + +void Skeleton3D::get_bone_meta_list(int p_bone, List<StringName> *p_list) const { + const int bone_size = bones.size(); + ERR_FAIL_INDEX(p_bone, bone_size); + + for (const KeyValue<StringName, Variant> &K : bones[p_bone].metadata) { + p_list->push_back(K.key); + } +} + +bool Skeleton3D::has_bone_meta(int p_bone, const StringName &p_key) const { + const int bone_size = bones.size(); + ERR_FAIL_INDEX_V(p_bone, bone_size, false); + + return bones[p_bone].metadata.has(p_key); +} + +void Skeleton3D::set_bone_meta(int p_bone, const StringName &p_key, const Variant &p_value) { + const int bone_size = bones.size(); + ERR_FAIL_INDEX(p_bone, bone_size); + + if (p_value.get_type() == Variant::NIL) { + if (bones.write[p_bone].metadata.has(p_key)) { + bones.write[p_bone].metadata.erase(p_key); + } + return; + } + + bones.write[p_bone].metadata.insert(p_key, p_value, false); +} + bool Skeleton3D::is_bone_parent_of(int p_bone, int p_parent_bone_id) const { int parent_of_bone = get_bone_parent(p_bone); @@ -1014,6 +1074,11 @@ void Skeleton3D::_bind_methods() { ClassDB::bind_method(D_METHOD("get_bone_name", "bone_idx"), &Skeleton3D::get_bone_name); ClassDB::bind_method(D_METHOD("set_bone_name", "bone_idx", "name"), &Skeleton3D::set_bone_name); + ClassDB::bind_method(D_METHOD("get_bone_meta", "bone_idx", "key"), &Skeleton3D::get_bone_meta); + ClassDB::bind_method(D_METHOD("get_bone_meta_list", "bone_idx"), &Skeleton3D::_get_bone_meta_list_bind); + ClassDB::bind_method(D_METHOD("has_bone_meta", "bone_idx", "key"), &Skeleton3D::has_bone_meta); + ClassDB::bind_method(D_METHOD("set_bone_meta", "bone_idx", "key", "value"), &Skeleton3D::set_bone_meta); + ClassDB::bind_method(D_METHOD("get_concatenated_bone_names"), &Skeleton3D::get_concatenated_bone_names); ClassDB::bind_method(D_METHOD("get_bone_parent", "bone_idx"), &Skeleton3D::get_bone_parent); diff --git a/scene/3d/skeleton_3d.h b/scene/3d/skeleton_3d.h index a009383f45..07bdeccf2f 100644 --- a/scene/3d/skeleton_3d.h +++ b/scene/3d/skeleton_3d.h @@ -116,6 +116,8 @@ private: } } + HashMap<StringName, Variant> metadata; + #ifndef DISABLE_DEPRECATED Transform3D pose_global_no_override; real_t global_pose_override_amount = 0.0; @@ -193,6 +195,7 @@ protected: void _get_property_list(List<PropertyInfo> *p_list) const; void _validate_property(PropertyInfo &p_property) const; void _notification(int p_what); + TypedArray<StringName> _get_bone_meta_list_bind(int p_bone) const; static void _bind_methods(); virtual void add_child_notify(Node *p_child) override; @@ -238,6 +241,12 @@ public: void set_motion_scale(float p_motion_scale); float get_motion_scale() const; + // bone metadata + Variant get_bone_meta(int p_bone, const StringName &p_key) const; + void get_bone_meta_list(int p_bone, List<StringName> *p_list) const; + bool has_bone_meta(int p_bone, const StringName &p_key) const; + void set_bone_meta(int p_bone, const StringName &p_key, const Variant &p_value); + // Posing API Transform3D get_bone_pose(int p_bone) const; Vector3 get_bone_pose_position(int p_bone) const; |