1
$\begingroup$

As mentioned in the title I need to convert rotation values from world space to a pose bone. The script should work with any given rig and regardless of the orientation and roll value of the pose bone.

Essentially, I want to emulate the behavior of the Copy Rotation constraint with the Mix mode set to Before Original.

Here is what I got so far:

# ... rot is the world space quaternion that I want to add to the head bone.

roll_matrix = Matrix.Rotation(self.head_bone_roll, 4, 'Y')

new_rot = self.head_bone.matrix.inverted() @ rot.to_matrix().to_4x4() @ roll_matrix.inverted()

self.head_bone.rotation_quaternion = new_rot.to_quaternion()

The rotation itself is correct, but it needs to be added as a relative offset exactly like in the pose bone constraint. Currently, the bone rotation is overwritten in a way that I don't fully understand and depending on the bone roll. It would be really great if someone could help me solve this problem or point me in the right direction (I am pretty sure that questions like this have been answered sufficiently here and else where, but I haven't been able to solve this yet...) Thanks!

$\endgroup$

1 Answer 1

1
$\begingroup$

Ok, after some back and forth, I was able to solve this. Here is what worked for me:

# Get the initial rotation in world space:
world_head_mat = self.head_obj.convert_space(pose_bone=self.head_bone, matrix=self.head_bone.matrix, to_space='WORLD', from_space='POSE')
self.initial_head_rotation = world_head_mat.to_quaternion()
# This is how I am applying the animation to the bone.
# I tested it on various rigs with different roll and bone orientations.
rot = rot.rotation_difference(self.initial_head_rotation)
rot = self.initial_head_rotation.inverted() @ rot
self.head_bone.rotation_quaternion = rot
$\endgroup$

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .