Make transform elements BitField in RetargetModifier

This commit is contained in:
Silc Lizard (Tokage) Renew 2024-12-26 07:42:57 +09:00
parent 0f95e9f8e6
commit 24f5361b8a
3 changed files with 121 additions and 33 deletions

View File

@ -10,19 +10,54 @@
</description>
<tutorials>
</tutorials>
<methods>
<method name="is_position_enabled" qualifiers="const">
<return type="bool" />
<description>
Returns [code]true[/code] if [member enable] has [constant TRANSFORM_FLAG_POSITION].
</description>
</method>
<method name="is_rotation_enabled" qualifiers="const">
<return type="bool" />
<description>
Returns [code]true[/code] if [member enable] has [constant TRANSFORM_FLAG_ROTATION].
</description>
</method>
<method name="is_scale_enabled" qualifiers="const">
<return type="bool" />
<description>
Returns [code]true[/code] if [member enable] has [constant TRANSFORM_FLAG_SCALE].
</description>
</method>
<method name="set_position_enabled">
<return type="void" />
<param index="0" name="enabled" type="bool" />
<description>
Sets [constant TRANSFORM_FLAG_POSITION] into [member enable].
</description>
</method>
<method name="set_rotation_enabled">
<return type="void" />
<param index="0" name="enabled" type="bool" />
<description>
Sets [constant TRANSFORM_FLAG_ROTATION] into [member enable].
</description>
</method>
<method name="set_scale_enabled">
<return type="void" />
<param index="0" name="enabled" type="bool" />
<description>
Sets [constant TRANSFORM_FLAG_SCALE] into [member enable].
</description>
</method>
</methods>
<members>
<member name="position_enabled" type="bool" setter="set_position_enabled" getter="is_position_enabled" default="true">
If [code]true[/code], allows to retarget the position.
<member name="enable" type="int" setter="set_enable_flags" getter="get_enable_flags" enum="RetargetModifier3D.TransformFlag" is_bitfield="true" default="7">
Flags to control the process of the transform elements individually when [member use_global_pose] is disabled.
</member>
<member name="profile" type="SkeletonProfile" setter="set_profile" getter="get_profile">
[SkeletonProfile] for retargeting bones with names matching the bone list.
</member>
<member name="rotation_enabled" type="bool" setter="set_rotation_enabled" getter="is_rotation_enabled" default="true">
If [code]true[/code], allows to retarget the rotation.
</member>
<member name="scale_enabled" type="bool" setter="set_scale_enabled" getter="is_scale_enabled" default="true">
If [code]true[/code], allows to retarget the scale.
</member>
<member name="use_global_pose" type="bool" setter="set_use_global_pose" getter="is_using_global_pose" default="false">
If [code]false[/code], in case the target skeleton has fewer bones than the source skeleton, the source bone parent's transform will be ignored.
Instead, it is possible to retarget between models with different body shapes, and position, rotation, and scale can be retargeted separately.
@ -31,4 +66,18 @@
This is useful for using dummy bone with length [code]0[/code] to match postures when retargeting between models with different number of bones.
</member>
</members>
<constants>
<constant name="TRANSFORM_FLAG_POSITION" value="1" enum="TransformFlag" is_bitfield="true">
If set, allows to retarget the position.
</constant>
<constant name="TRANSFORM_FLAG_ROTATION" value="2" enum="TransformFlag" is_bitfield="true">
If set, allows to retarget the rotation.
</constant>
<constant name="TRANSFORM_FLAG_SCALE" value="4" enum="TransformFlag" is_bitfield="true">
If set, allows to retarget the scale.
</constant>
<constant name="TRANSFORM_FLAG_ALL" value="7" enum="TransformFlag" is_bitfield="true">
If set, allows to retarget the position/rotation/scale.
</constant>
</constants>
</class>

View File

@ -236,7 +236,7 @@ void RetargetModifier3D::remove_child_notify(Node *p_child) {
void RetargetModifier3D::_validate_property(PropertyInfo &p_property) const {
if (use_global_pose) {
if (p_property.name == "position_enabled" || p_property.name == "rotation_enabled" || p_property.name == "scale_enabled") {
if (p_property.name == "enable_flags") {
p_property.usage = PROPERTY_USAGE_NONE;
}
}
@ -247,6 +247,9 @@ void RetargetModifier3D::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_profile"), &RetargetModifier3D::get_profile);
ClassDB::bind_method(D_METHOD("set_use_global_pose", "use_global_pose"), &RetargetModifier3D::set_use_global_pose);
ClassDB::bind_method(D_METHOD("is_using_global_pose"), &RetargetModifier3D::is_using_global_pose);
ClassDB::bind_method(D_METHOD("set_enable_flags", "enable_flags"), &RetargetModifier3D::set_enable_flags);
ClassDB::bind_method(D_METHOD("get_enable_flags"), &RetargetModifier3D::get_enable_flags);
ClassDB::bind_method(D_METHOD("set_position_enabled", "enabled"), &RetargetModifier3D::set_position_enabled);
ClassDB::bind_method(D_METHOD("is_position_enabled"), &RetargetModifier3D::is_position_enabled);
ClassDB::bind_method(D_METHOD("set_rotation_enabled", "enabled"), &RetargetModifier3D::set_rotation_enabled);
@ -256,9 +259,12 @@ void RetargetModifier3D::_bind_methods() {
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "profile", PROPERTY_HINT_RESOURCE_TYPE, "SkeletonProfile"), "set_profile", "get_profile");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "use_global_pose"), "set_use_global_pose", "is_using_global_pose");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "position_enabled"), "set_position_enabled", "is_position_enabled");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "rotation_enabled"), "set_rotation_enabled", "is_rotation_enabled");
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "scale_enabled"), "set_scale_enabled", "is_scale_enabled");
ADD_PROPERTY(PropertyInfo(Variant::INT, "enable", PROPERTY_HINT_FLAGS, "Position,Rotation,Scale"), "set_enable_flags", "get_enable_flags");
BIND_BITFIELD_FLAG(TRANSFORM_FLAG_POSITION);
BIND_BITFIELD_FLAG(TRANSFORM_FLAG_ROTATION);
BIND_BITFIELD_FLAG(TRANSFORM_FLAG_SCALE);
BIND_BITFIELD_FLAG(TRANSFORM_FLAG_ALL);
}
void RetargetModifier3D::_set_active(bool p_active) {
@ -338,17 +344,15 @@ void RetargetModifier3D::_retarget_pose() {
extracted_transform.basis = E.humanoid_bone_rests[i].pre_basis * extracted_transform.basis * E.humanoid_bone_rests[i].post_basis;
extracted_transform.origin = E.humanoid_bone_rests[i].pre_basis.xform((extracted_transform.origin - source_skeleton->get_bone_rest(source_bone_id).origin) * motion_scale_ratio) + target_skeleton->get_bone_rest(target_bone_id).origin;
Transform3D retarget_pose = target_skeleton->get_bone_pose(target_bone_id);
if (enable_position) {
retarget_pose.origin = extracted_transform.origin;
if (enable_flags.has_flag(TRANSFORM_FLAG_POSITION)) {
target_skeleton->set_bone_pose_position(target_bone_id, extracted_transform.origin);
}
if (enable_rotation) {
retarget_pose.basis = extracted_transform.basis.get_rotation_quaternion();
if (enable_flags.has_flag(TRANSFORM_FLAG_ROTATION)) {
target_skeleton->set_bone_pose_rotation(target_bone_id, extracted_transform.basis.get_rotation_quaternion());
}
if (enable_scale) {
retarget_pose.basis.scale_local(extracted_transform.basis.get_scale());
if (enable_flags.has_flag(TRANSFORM_FLAG_SCALE)) {
target_skeleton->set_bone_pose_scale(target_bone_id, extracted_transform.basis.get_scale());
}
target_skeleton->set_bone_pose(target_bone_id, retarget_pose);
}
}
}
@ -387,37 +391,60 @@ bool RetargetModifier3D::is_using_global_pose() const {
return use_global_pose;
}
void RetargetModifier3D::set_position_enabled(bool p_enabled) {
if (enable_position != p_enabled) {
void RetargetModifier3D::set_enable_flags(BitField<TransformFlag> p_enable_flag) {
if (enable_flags != p_enable_flag) {
_reset_child_skeleton_poses();
}
enable_position = p_enabled;
enable_flags = p_enable_flag;
}
BitField<RetargetModifier3D::TransformFlag> RetargetModifier3D::get_enable_flags() const {
return enable_flags;
}
void RetargetModifier3D::set_position_enabled(bool p_enabled) {
if (enable_flags.has_flag(TRANSFORM_FLAG_POSITION) != p_enabled) {
_reset_child_skeleton_poses();
}
if (p_enabled) {
enable_flags.set_flag(TRANSFORM_FLAG_POSITION);
} else {
enable_flags.clear_flag(TRANSFORM_FLAG_POSITION);
}
}
bool RetargetModifier3D::is_position_enabled() const {
return enable_position;
return enable_flags.has_flag(TRANSFORM_FLAG_POSITION);
}
void RetargetModifier3D::set_rotation_enabled(bool p_enabled) {
if (enable_rotation != p_enabled) {
if (enable_flags.has_flag(TRANSFORM_FLAG_ROTATION) != p_enabled) {
_reset_child_skeleton_poses();
}
enable_rotation = p_enabled;
if (p_enabled) {
enable_flags.set_flag(TRANSFORM_FLAG_ROTATION);
} else {
enable_flags.clear_flag(TRANSFORM_FLAG_ROTATION);
}
}
bool RetargetModifier3D::is_rotation_enabled() const {
return enable_rotation;
return enable_flags.has_flag(TRANSFORM_FLAG_ROTATION);
}
void RetargetModifier3D::set_scale_enabled(bool p_enabled) {
if (enable_scale != p_enabled) {
if (enable_flags.has_flag(TRANSFORM_FLAG_SCALE) != p_enabled) {
_reset_child_skeleton_poses();
}
enable_scale = p_enabled;
if (p_enabled) {
enable_flags.set_flag(TRANSFORM_FLAG_SCALE);
} else {
enable_flags.clear_flag(TRANSFORM_FLAG_SCALE);
}
}
bool RetargetModifier3D::is_scale_enabled() const {
return enable_scale;
return enable_flags.has_flag(TRANSFORM_FLAG_SCALE);
}
void RetargetModifier3D::_notification(int p_what) {

View File

@ -37,12 +37,19 @@
class RetargetModifier3D : public SkeletonModifier3D {
GDCLASS(RetargetModifier3D, SkeletonModifier3D);
public:
enum TransformFlag {
TRANSFORM_FLAG_POSITION = 1,
TRANSFORM_FLAG_ROTATION = 2,
TRANSFORM_FLAG_SCALE = 4,
TRANSFORM_FLAG_ALL = TRANSFORM_FLAG_POSITION | TRANSFORM_FLAG_ROTATION | TRANSFORM_FLAG_SCALE,
};
private:
Ref<SkeletonProfile> profile;
bool use_global_pose = false;
bool enable_position = true;
bool enable_rotation = true;
bool enable_scale = true;
BitField<TransformFlag> enable_flags = TRANSFORM_FLAG_ALL;
struct RetargetBoneInfo {
int bone_id = -1;
@ -93,6 +100,9 @@ public:
void set_use_global_pose(bool p_use_global_pose);
bool is_using_global_pose() const;
void set_enable_flags(BitField<TransformFlag> p_enable_flags);
BitField<TransformFlag> get_enable_flags() const;
void set_position_enabled(bool p_enabled);
bool is_position_enabled() const;
void set_rotation_enabled(bool p_enabled);
@ -107,4 +117,6 @@ public:
virtual ~RetargetModifier3D();
};
VARIANT_BITFIELD_CAST(RetargetModifier3D::TransformFlag);
#endif // RETARGET_MODIFIER_3D_H